My Marlin configs for Fabrikator Mini and CTC i3 Pro B
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

HAL.cpp 6.6KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200
  1. /* **************************************************************************
  2. Marlin 3D Printer Firmware
  3. Copyright (C) 2016 MarlinFirmware [https://github.com/MarlinFirmware/Marlin]
  4. Copyright (c) 2016 Bob Cousins bobcousins42@googlemail.com
  5. This program is free software: you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation, either version 3 of the License, or
  8. (at your option) any later version.
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. GNU General Public License for more details.
  13. You should have received a copy of the GNU General Public License
  14. along with this program. If not, see <http://www.gnu.org/licenses/>.
  15. ****************************************************************************/
  16. #ifdef TARGET_LPC1768
  17. #include "../../inc/MarlinConfig.h"
  18. extern "C" {
  19. //#include <lpc17xx_adc.h>
  20. //#include <lpc17xx_pinsel.h>
  21. }
  22. HalSerial usb_serial;
  23. //u8glib required fucntions
  24. extern "C" void u8g_xMicroDelay(uint16_t val) {
  25. delayMicroseconds(val);
  26. }
  27. extern "C" void u8g_MicroDelay(void) {
  28. u8g_xMicroDelay(1);
  29. }
  30. extern "C" void u8g_10MicroDelay(void) {
  31. u8g_xMicroDelay(10);
  32. }
  33. extern "C" void u8g_Delay(uint16_t val) {
  34. delay(val);
  35. }
  36. //************************//
  37. // return free heap space
  38. int freeMemory() {
  39. char stack_end;
  40. void *heap_start = malloc(sizeof(uint32_t));
  41. if (heap_start == 0) return 0;
  42. uint32_t result = (uint32_t)&stack_end - (uint32_t)heap_start;
  43. free(heap_start);
  44. return result;
  45. }
  46. // --------------------------------------------------------------------------
  47. // ADC
  48. // --------------------------------------------------------------------------
  49. #define ADC_DONE 0x80000000
  50. #define ADC_OVERRUN 0x40000000
  51. void HAL_adc_init(void) {
  52. LPC_SC->PCONP |= (1 << 12); // Enable CLOCK for internal ADC controller
  53. LPC_SC->PCLKSEL0 &= ~(0x3 << 24);
  54. LPC_SC->PCLKSEL0 |= (0x1 << 24); // 0: 25MHz, 1: 100MHz, 2: 50MHz, 3: 12.5MHZ to ADC clock divider
  55. LPC_ADC->ADCR = (0 << 0) // SEL: 0 = no channels selected
  56. | (0xFF << 8) // select slowest clock for A/D conversion 150 - 190 uS for a complete conversion
  57. | (0 << 16) // BURST: 0 = software control
  58. | (0 << 17) // CLKS: not applicable
  59. | (1 << 21) // PDN: 1 = operational
  60. | (0 << 24) // START: 0 = no start
  61. | (0 << 27); // EDGE: not applicable
  62. }
  63. // externals need to make the call to KILL compile
  64. #include "../../core/language.h"
  65. extern void kill(const char*);
  66. extern const char errormagic[];
  67. void HAL_adc_enable_channel(int ch) {
  68. pin_t pin = analogInputToDigitalPin(ch);
  69. if (pin == -1) {
  70. MYSERIAL.printf("%sINVALID ANALOG PORT:%d\n", errormagic, ch);
  71. kill(MSG_KILLED);
  72. }
  73. int8_t pin_port = LPC1768_PIN_PORT(pin),
  74. pin_port_pin = LPC1768_PIN_PIN(pin),
  75. pinsel_start_bit = pin_port_pin > 15 ? 2 * (pin_port_pin - 16) : 2 * pin_port_pin;
  76. uint8_t pin_sel_register = (pin_port == 0 && pin_port_pin <= 15) ? 0 :
  77. pin_port == 0 ? 1 :
  78. pin_port == 1 ? 3 : 10;
  79. switch (pin_sel_register) {
  80. case 1 :
  81. LPC_PINCON->PINSEL1 &= ~(0x3 << pinsel_start_bit);
  82. LPC_PINCON->PINSEL1 |= (0x1 << pinsel_start_bit);
  83. break;
  84. case 3 :
  85. LPC_PINCON->PINSEL3 &= ~(0x3 << pinsel_start_bit);
  86. LPC_PINCON->PINSEL3 |= (0x3 << pinsel_start_bit);
  87. break;
  88. case 0 :
  89. LPC_PINCON->PINSEL0 &= ~(0x3 << pinsel_start_bit);
  90. LPC_PINCON->PINSEL0 |= (0x2 << pinsel_start_bit);
  91. break;
  92. };
  93. }
  94. uint8_t active_adc = 0;
  95. void HAL_adc_start_conversion(const uint8_t ch) {
  96. if (analogInputToDigitalPin(ch) == -1) {
  97. MYSERIAL.printf("HAL: HAL_adc_start_conversion: invalid channel %d\n", ch);
  98. return;
  99. }
  100. LPC_ADC->ADCR &= ~0xFF; // Reset
  101. SBI(LPC_ADC->ADCR, ch); // Select Channel
  102. SBI(LPC_ADC->ADCR, 24); // Start conversion
  103. active_adc = ch;
  104. }
  105. bool HAL_adc_finished(void) {
  106. return LPC_ADC->ADGDR & ADC_DONE;
  107. }
  108. // possible config options if something similar is extended to more platforms.
  109. #define ADC_USE_MEDIAN_FILTER // filter out erroneous readings
  110. #define ADC_USE_LOWPASS_FILTER // filter out high frequency noise
  111. #define ADC_LOWPASS_K_VALUE 4 // how much to smooth out noise (1:8)
  112. struct MedianFilter {
  113. uint16_t values[3];
  114. uint8_t next_val;
  115. MedianFilter() {
  116. next_val = 0;
  117. values[0] = values[1] = values[2] = 0;
  118. }
  119. uint16_t update(uint16_t value) {
  120. values[next_val++] = value;
  121. next_val = next_val % 3;
  122. return max(min(values[0], values[1]), min(max(values[0], values[1]), values[2])); //median
  123. }
  124. };
  125. uint16_t lowpass_filter(uint16_t value) {
  126. const uint8_t k_data_shift = ADC_LOWPASS_K_VALUE;
  127. static uint32_t data_delay[NUM_ANALOG_INPUTS] = { 0 };
  128. uint32_t &active_filter = data_delay[active_adc];
  129. active_filter = active_filter - (active_filter >> k_data_shift) + value;
  130. return (uint16_t)(active_filter >> k_data_shift);
  131. }
  132. uint16_t HAL_adc_get_result(void) {
  133. uint32_t data = LPC_ADC->ADGDR;
  134. CBI(LPC_ADC->ADCR, 24); // Stop conversion
  135. if (data & ADC_OVERRUN) return 0;
  136. #ifdef ADC_USE_MEDIAN_FILTER
  137. static MedianFilter median_filter[NUM_ANALOG_INPUTS];
  138. data = median_filter[active_adc].update((uint16_t)data);
  139. #endif
  140. #ifdef ADC_USE_LOWPASS_FILTER
  141. data = lowpass_filter((uint16_t)data);
  142. #endif
  143. return ((data >> 6) & 0x3ff); // 10bit
  144. }
  145. #define SBIT_CNTEN 0
  146. #define SBIT_PWMEN 2
  147. #define SBIT_PWMMR0R 1
  148. #define PWM_1 0 //P2_0 (0-1 Bits of PINSEL4)
  149. #define PWM_2 2 //P2_1 (2-3 Bits of PINSEL4)
  150. #define PWM_3 4 //P2_2 (4-5 Bits of PINSEL4)
  151. #define PWM_4 6 //P2_3 (6-7 Bits of PINSEL4)
  152. #define PWM_5 8 //P2_4 (8-9 Bits of PINSEL4)
  153. #define PWM_6 10 //P2_5 (10-11 Bits of PINSEL4)
  154. void HAL_pwm_init(void) {
  155. LPC_PINCON->PINSEL4 = _BV(PWM_5) | _BV(PWM_6);
  156. LPC_PWM1->TCR = _BV(SBIT_CNTEN) | _BV(SBIT_PWMEN);
  157. LPC_PWM1->PR = 0x0; // No prescalar
  158. LPC_PWM1->MCR = _BV(SBIT_PWMMR0R); // Reset on PWMMR0, reset TC if it matches MR0
  159. LPC_PWM1->MR0 = 255; /* set PWM cycle(Ton+Toff)=255) */
  160. LPC_PWM1->MR5 = 0; /* Set 50% Duty Cycle for the channels */
  161. LPC_PWM1->MR6 = 0;
  162. // Trigger the latch Enable Bits to load the new Match Values MR0, MR5, MR6
  163. LPC_PWM1->LER = _BV(0) | _BV(5) | _BV(6);
  164. // Enable the PWM output pins for PWM_5-PWM_6(P2_4 - P2_5)
  165. LPC_PWM1->PCR = _BV(13) | _BV(14);
  166. }
  167. #endif // TARGET_LPC1768