28
28
#include "shared-bindings/busio/UART.h"
29
29
30
30
#include "mpconfigport.h"
31
+ #include "lib/mp-readline/readline.h"
31
32
#include "lib/utils/interrupt_char.h"
32
33
#include "py/gc.h"
33
34
#include "py/mperrno.h"
39
40
40
41
//arrays use 0 based numbering: UART1 is stored at index 0
41
42
STATIC bool reserved_uart [MAX_UART ];
43
+ STATIC bool never_reset_uart [MAX_UART ];
42
44
int errflag ; //Used to restart read halts
43
45
44
46
STATIC void uart_clock_enable (uint16_t mask );
@@ -61,19 +63,25 @@ STATIC USART_TypeDef * assign_uart_or_throw(busio_uart_obj_t* self, bool pin_eva
61
63
}
62
64
63
65
void uart_reset (void ) {
66
+ uint16_t never_reset_mask = 0x00 ;
64
67
for (uint8_t i = 0 ; i < MAX_UART ; i ++ ) {
65
- reserved_uart [i ] = false;
66
- MP_STATE_PORT (cpy_uart_obj_all )[i ] = NULL ;
68
+ if (!never_reset_uart [i ]) {
69
+ reserved_uart [i ] = false;
70
+ MP_STATE_PORT (cpy_uart_obj_all )[i ] = NULL ;
71
+ } else {
72
+ never_reset_mask |= 1 << i ;
73
+ }
67
74
}
68
- uart_clock_disable (ALL_UARTS );
75
+ uart_clock_disable (ALL_UARTS & ~( never_reset_mask ) );
69
76
}
70
77
71
78
void common_hal_busio_uart_construct (busio_uart_obj_t * self ,
72
79
const mcu_pin_obj_t * tx , const mcu_pin_obj_t * rx ,
73
80
const mcu_pin_obj_t * rts , const mcu_pin_obj_t * cts ,
74
81
const mcu_pin_obj_t * rs485_dir , bool rs485_invert ,
75
82
uint32_t baudrate , uint8_t bits , uart_parity_t parity , uint8_t stop ,
76
- mp_float_t timeout , uint16_t receiver_buffer_size ) {
83
+ mp_float_t timeout , uint16_t receiver_buffer_size , byte * receiver_buffer ,
84
+ bool sigint_enabled ) {
77
85
78
86
//match pins to UART objects
79
87
USART_TypeDef * USARTx ;
@@ -209,8 +217,12 @@ void common_hal_busio_uart_construct(busio_uart_obj_t *self,
209
217
210
218
// Init buffer for rx and claim pins
211
219
if (self -> rx != NULL ) {
212
- if (!ringbuf_alloc (& self -> ringbuf , receiver_buffer_size , true)) {
213
- mp_raise_ValueError (translate ("UART Buffer allocation error" ));
220
+ if (receiver_buffer != NULL ) {
221
+ self -> ringbuf = (ringbuf_t ){ receiver_buffer , receiver_buffer_size };
222
+ } else {
223
+ if (!ringbuf_alloc (& self -> ringbuf , receiver_buffer_size , true)) {
224
+ mp_raise_ValueError (translate ("UART Buffer allocation error" ));
225
+ }
214
226
}
215
227
claim_pin (rx );
216
228
}
@@ -219,6 +231,7 @@ void common_hal_busio_uart_construct(busio_uart_obj_t *self,
219
231
}
220
232
self -> baudrate = baudrate ;
221
233
self -> timeout_ms = timeout * 1000 ;
234
+ self -> sigint_enabled = sigint_enabled ;
222
235
223
236
//start the interrupt series
224
237
if ((HAL_UART_GetState (& self -> handle ) & HAL_UART_STATE_BUSY_RX ) == HAL_UART_STATE_BUSY_RX ) {
@@ -234,13 +247,31 @@ void common_hal_busio_uart_construct(busio_uart_obj_t *self,
234
247
errflag = HAL_OK ;
235
248
}
236
249
250
+ void common_hal_busio_uart_never_reset (busio_uart_obj_t * self ) {
251
+ for (size_t i = 0 ; i < MP_ARRAY_SIZE (mcu_uart_banks ); i ++ ) {
252
+ if (mcu_uart_banks [i ] == self -> handle .Instance ) {
253
+ never_reset_uart [i ] = true;
254
+ never_reset_pin_number (self -> tx -> pin -> port , self -> tx -> pin -> number );
255
+ never_reset_pin_number (self -> rx -> pin -> port , self -> rx -> pin -> number );
256
+ break ;
257
+ }
258
+ }
259
+ }
260
+
237
261
bool common_hal_busio_uart_deinited (busio_uart_obj_t * self ) {
238
262
return self -> tx -> pin == NULL ;
239
263
}
240
264
241
265
void common_hal_busio_uart_deinit (busio_uart_obj_t * self ) {
242
266
if (common_hal_busio_uart_deinited (self )) return ;
243
267
268
+ for (size_t i = 0 ; i < MP_ARRAY_SIZE (mcu_uart_banks ); i ++ ) {
269
+ if (mcu_uart_banks [i ] == self -> handle .Instance ) {
270
+ never_reset_uart [i ] = false;
271
+ break ;
272
+ }
273
+ }
274
+
244
275
reset_pin_number (self -> tx -> pin -> port ,self -> tx -> pin -> number );
245
276
reset_pin_number (self -> rx -> pin -> port ,self -> rx -> pin -> number );
246
277
self -> tx = NULL ;
@@ -289,7 +320,8 @@ size_t common_hal_busio_uart_write(busio_uart_obj_t *self, const uint8_t *data,
289
320
bool write_err = false; //write error shouldn't disable interrupts
290
321
291
322
HAL_NVIC_DisableIRQ (self -> irq );
292
- if (HAL_UART_Transmit (& self -> handle , (uint8_t * )data , len , HAL_MAX_DELAY ) != HAL_OK ) {
323
+ HAL_StatusTypeDef ret = HAL_UART_Transmit (& self -> handle , (uint8_t * )data , len , HAL_MAX_DELAY );
324
+ if (ret != HAL_OK ) {
293
325
write_err = true;
294
326
}
295
327
HAL_UART_Receive_IT (& self -> handle , & self -> rx_char , 1 );
@@ -313,6 +345,12 @@ void HAL_UART_RxCpltCallback(UART_HandleTypeDef *handle)
313
345
}
314
346
ringbuf_put_n (& context -> ringbuf , & context -> rx_char , 1 );
315
347
errflag = HAL_UART_Receive_IT (handle , & context -> rx_char , 1 );
348
+ if (context -> sigint_enabled ) {
349
+ if (context -> rx_char == CHAR_CTRL_C ) {
350
+ common_hal_busio_uart_clear_rx_buffer (context );
351
+ mp_keyboard_interrupt ();
352
+ }
353
+ }
316
354
317
355
return ;
318
356
}
0 commit comments