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.

MarlinSerial.cpp 6.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195
  1. /**
  2. * Marlin 3D Printer Firmware
  3. * Copyright (c) 2020 MarlinFirmware [https://github.com/MarlinFirmware/Marlin]
  4. *
  5. * Based on Sprinter and grbl.
  6. * Copyright (c) 2011 Camiel Gubbels / Erik van der Zalm
  7. *
  8. * This program is free software: you can redistribute it and/or modify
  9. * it under the terms of the GNU General Public License as published by
  10. * the Free Software Foundation, either version 3 of the License, or
  11. * (at your option) any later version.
  12. *
  13. * This program is distributed in the hope that it will be useful,
  14. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  16. * GNU General Public License for more details.
  17. *
  18. * You should have received a copy of the GNU General Public License
  19. * along with this program. If not, see <https://www.gnu.org/licenses/>.
  20. *
  21. */
  22. #ifdef __STM32F1__
  23. #include "../../inc/MarlinConfig.h"
  24. #include "MarlinSerial.h"
  25. #include <libmaple/usart.h>
  26. // Copied from ~/.platformio/packages/framework-arduinoststm32-maple/STM32F1/system/libmaple/usart_private.h
  27. // Changed to handle Emergency Parser
  28. static inline __always_inline void my_usart_irq(ring_buffer *rb, ring_buffer *wb, usart_reg_map *regs, MSerialT &serial) {
  29. /* Handle RXNEIE and TXEIE interrupts.
  30. * RXNE signifies availability of a byte in DR.
  31. *
  32. * See table 198 (sec 27.4, p809) in STM document RM0008 rev 15.
  33. * We enable RXNEIE.
  34. */
  35. uint32_t srflags = regs->SR, cr1its = regs->CR1;
  36. if ((cr1its & USART_CR1_RXNEIE) && (srflags & USART_SR_RXNE)) {
  37. if (srflags & USART_SR_FE || srflags & USART_SR_PE ) {
  38. // framing error or parity error
  39. regs->DR; // Read and throw away the data, which also clears FE and PE
  40. }
  41. else {
  42. uint8_t c = (uint8)regs->DR;
  43. #ifdef USART_SAFE_INSERT
  44. // If the buffer is full and the user defines USART_SAFE_INSERT,
  45. // ignore new bytes.
  46. rb_safe_insert(rb, c);
  47. #else
  48. // By default, push bytes around in the ring buffer.
  49. rb_push_insert(rb, c);
  50. #endif
  51. #if ENABLED(EMERGENCY_PARSER)
  52. if (serial.emergency_parser_enabled())
  53. emergency_parser.update(serial.emergency_state, c);
  54. #endif
  55. }
  56. }
  57. else if (srflags & USART_SR_ORE) {
  58. // overrun and empty data, just do a dummy read to clear ORE
  59. // and prevent a raise condition where a continous interrupt stream (due to ORE set) occurs
  60. // (see chapter "Overrun error" ) in STM32 reference manual
  61. regs->DR;
  62. }
  63. // TXE signifies readiness to send a byte to DR.
  64. if ((cr1its & USART_CR1_TXEIE) && (srflags & USART_SR_TXE)) {
  65. if (!rb_is_empty(wb))
  66. regs->DR=rb_remove(wb);
  67. else
  68. regs->CR1 &= ~((uint32)USART_CR1_TXEIE); // disable TXEIE
  69. }
  70. }
  71. // Not every MarlinSerial port should handle emergency parsing.
  72. // It would not make sense to parse GCode from TMC responses, for example.
  73. constexpr bool serial_handles_emergency(int port) {
  74. return false
  75. #ifdef SERIAL_PORT
  76. || (SERIAL_PORT) == port
  77. #endif
  78. #ifdef SERIAL_PORT_2
  79. || (SERIAL_PORT_2) == port
  80. #endif
  81. #ifdef LCD_SERIAL_PORT
  82. || (LCD_SERIAL_PORT) == port
  83. #endif
  84. ;
  85. }
  86. #define DEFINE_HWSERIAL_MARLIN(name, n) \
  87. MSerialT name(serial_handles_emergency(n),\
  88. USART##n, \
  89. BOARD_USART##n##_TX_PIN, \
  90. BOARD_USART##n##_RX_PIN); \
  91. extern "C" void __irq_usart##n(void) { \
  92. my_usart_irq(USART##n->rb, USART##n->wb, USART##n##_BASE, MSerial##n); \
  93. }
  94. #define DEFINE_HWSERIAL_UART_MARLIN(name, n) \
  95. MSerialT name(serial_handles_emergency(n), \
  96. UART##n, \
  97. BOARD_USART##n##_TX_PIN, \
  98. BOARD_USART##n##_RX_PIN); \
  99. extern "C" void __irq_usart##n(void) { \
  100. my_usart_irq(UART##n->rb, UART##n->wb, UART##n##_BASE, MSerial##n); \
  101. }
  102. // Instantiate all UARTs even if they are not needed
  103. // This avoids a bunch of logic to figure out every serial
  104. // port which may be in use on the system.
  105. #if DISABLED(MKS_WIFI_MODULE)
  106. DEFINE_HWSERIAL_MARLIN(MSerial1, 1);
  107. #endif
  108. DEFINE_HWSERIAL_MARLIN(MSerial2, 2);
  109. DEFINE_HWSERIAL_MARLIN(MSerial3, 3);
  110. #if EITHER(STM32_HIGH_DENSITY, STM32_XL_DENSITY)
  111. DEFINE_HWSERIAL_UART_MARLIN(MSerial4, 4);
  112. DEFINE_HWSERIAL_UART_MARLIN(MSerial5, 5);
  113. #endif
  114. // Check the type of each serial port by passing it to a template function.
  115. // HardwareSerial is known to sometimes hang the controller when an error occurs,
  116. // so this case will fail the static assert. All other classes are assumed to be ok.
  117. template <typename T>
  118. constexpr bool IsSerialClassAllowed(const T&) { return true; }
  119. constexpr bool IsSerialClassAllowed(const HardwareSerial&) { return false; }
  120. #define CHECK_CFG_SERIAL(A) static_assert(IsSerialClassAllowed(A), STRINGIFY(A) " is defined incorrectly");
  121. #define CHECK_AXIS_SERIAL(A) static_assert(IsSerialClassAllowed(A##_HARDWARE_SERIAL), STRINGIFY(A) "_HARDWARE_SERIAL must be defined in the form MSerial1, rather than Serial1");
  122. // If you encounter this error, replace SerialX with MSerialX, for example MSerial3.
  123. // Non-TMC ports were already validated in HAL.h, so do not require verbose error messages.
  124. #ifdef MYSERIAL1
  125. CHECK_CFG_SERIAL(MYSERIAL1);
  126. #endif
  127. #ifdef MYSERIAL2
  128. CHECK_CFG_SERIAL(MYSERIAL2);
  129. #endif
  130. #ifdef LCD_SERIAL
  131. CHECK_CFG_SERIAL(LCD_SERIAL);
  132. #endif
  133. #if AXIS_HAS_HW_SERIAL(X)
  134. CHECK_AXIS_SERIAL(X);
  135. #endif
  136. #if AXIS_HAS_HW_SERIAL(X2)
  137. CHECK_AXIS_SERIAL(X2);
  138. #endif
  139. #if AXIS_HAS_HW_SERIAL(Y)
  140. CHECK_AXIS_SERIAL(Y);
  141. #endif
  142. #if AXIS_HAS_HW_SERIAL(Y2)
  143. CHECK_AXIS_SERIAL(Y2);
  144. #endif
  145. #if AXIS_HAS_HW_SERIAL(Z)
  146. CHECK_AXIS_SERIAL(Z);
  147. #endif
  148. #if AXIS_HAS_HW_SERIAL(Z2)
  149. CHECK_AXIS_SERIAL(Z2);
  150. #endif
  151. #if AXIS_HAS_HW_SERIAL(Z3)
  152. CHECK_AXIS_SERIAL(Z3);
  153. #endif
  154. #if AXIS_HAS_HW_SERIAL(Z4)
  155. CHECK_AXIS_SERIAL(Z4);
  156. #endif
  157. #if AXIS_HAS_HW_SERIAL(E0)
  158. CHECK_AXIS_SERIAL(E0);
  159. #endif
  160. #if AXIS_HAS_HW_SERIAL(E1)
  161. CHECK_AXIS_SERIAL(E1);
  162. #endif
  163. #if AXIS_HAS_HW_SERIAL(E2)
  164. CHECK_AXIS_SERIAL(E2);
  165. #endif
  166. #if AXIS_HAS_HW_SERIAL(E3)
  167. CHECK_AXIS_SERIAL(E3);
  168. #endif
  169. #if AXIS_HAS_HW_SERIAL(E4)
  170. CHECK_AXIS_SERIAL(E4);
  171. #endif
  172. #if AXIS_HAS_HW_SERIAL(E5)
  173. CHECK_AXIS_SERIAL(E5);
  174. #endif
  175. #if AXIS_HAS_HW_SERIAL(E6)
  176. CHECK_AXIS_SERIAL(E6);
  177. #endif
  178. #if AXIS_HAS_HW_SERIAL(E7)
  179. CHECK_AXIS_SERIAL(E7);
  180. #endif
  181. #endif // __STM32F1__