kopia lustrzana https://github.com/micropython/micropython
nrf/modules/machine: Catch exceptions from pin interrupts.
Exceptions in pin interrupt handlers would end up crashing MicroPython with a "FATAL: uncaught exception". In addition, MicroPython would get stuck trying to output this error message, or generally any print output from inside a pin interrupt handler, through the UART after the first character, so that only "F" was visible. The reason was a matching interrupt priority between the running pin interrupt and the UARTE interrupt signaling completion of the output operation. Fix that by increasing the UARTE interrupt priority. Code taken from the stm32 port and adapted. Signed-off-by: Christian Walther <cwalther@gmx.ch>pull/13497/head
rodzic
b10182bbcc
commit
5e926b2222
|
@ -33,6 +33,7 @@
|
|||
#include "py/nlr.h"
|
||||
#include "py/runtime.h"
|
||||
#include "py/mphal.h"
|
||||
#include "py/gc.h"
|
||||
#include "pin.h"
|
||||
#include "nrf_gpio.h"
|
||||
#include "nrfx_gpiote.h"
|
||||
|
@ -498,7 +499,29 @@ static void pin_common_irq_handler(nrfx_gpiote_pin_t pin, nrf_gpiote_polarity_t
|
|||
mp_obj_t pin_number = MP_OBJ_NEW_SMALL_INT(pin);
|
||||
const pin_obj_t *pin_obj = pin_find(pin_number);
|
||||
|
||||
mp_call_function_1(pin_handler, (mp_obj_t)pin_obj);
|
||||
if (pin_handler != mp_const_none) {
|
||||
#if MICROPY_ENABLE_SCHEDULER
|
||||
mp_sched_lock();
|
||||
#endif
|
||||
// When executing code within a handler we must lock the GC to prevent
|
||||
// any memory allocations. We must also catch any exceptions.
|
||||
gc_lock();
|
||||
nlr_buf_t nlr;
|
||||
if (nlr_push(&nlr) == 0) {
|
||||
mp_call_function_1(pin_handler, (mp_obj_t)pin_obj);
|
||||
nlr_pop();
|
||||
} else {
|
||||
// Uncaught exception; disable the callback so it doesn't run again.
|
||||
MP_STATE_PORT(pin_irq_handlers)[pin] = mp_const_none;
|
||||
nrfx_gpiote_in_uninit(pin);
|
||||
mp_printf(MICROPY_ERROR_PRINTER, "uncaught exception in interrupt handler for Pin('%q')\n", pin_obj->name);
|
||||
mp_obj_print_exception(&mp_plat_print, MP_OBJ_FROM_PTR(nlr.ret_val));
|
||||
}
|
||||
gc_unlock();
|
||||
#if MICROPY_ENABLE_SCHEDULER
|
||||
mp_sched_unlock();
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
static mp_obj_t pin_irq(size_t n_args, const mp_obj_t *pos_args, mp_map_t *kw_args) {
|
||||
|
|
|
@ -214,11 +214,9 @@ static mp_obj_t mp_machine_uart_make_new(const mp_obj_type_t *type, size_t n_arg
|
|||
|
||||
config.hal_cfg.parity = NRF_UART_PARITY_EXCLUDED;
|
||||
|
||||
#if (BLUETOOTH_SD == 100)
|
||||
config.interrupt_priority = 3;
|
||||
#else
|
||||
config.interrupt_priority = 6;
|
||||
#endif
|
||||
// Higher priority than pin interrupts, otherwise printing exceptions from
|
||||
// interrupt handlers gets stuck.
|
||||
config.interrupt_priority = NRFX_GPIOTE_DEFAULT_CONFIG_IRQ_PRIORITY - 1;
|
||||
|
||||
// These baudrates are not supported, it seems.
|
||||
if (args[ARG_baudrate].u_int < 1200 || args[ARG_baudrate].u_int > 1000000) {
|
||||
|
|
Ładowanie…
Reference in New Issue