stmhal: Enable micropython.schedule().
ExtInt, Timer and CAN IRQ callbacks are made to work with the scheduler. They are still hard IRQs by default, but one can now call micropython.schedule within the hard IRQ to schedule a soft callback.
This commit is contained in:
parent
c138b21ceb
commit
a5159edc20
@ -865,6 +865,7 @@ void can_rx_irq_handler(uint can_id, uint fifo_id) {
|
||||
}
|
||||
|
||||
if (callback != mp_const_none) {
|
||||
mp_sched_lock();
|
||||
gc_lock();
|
||||
nlr_buf_t nlr;
|
||||
if (nlr_push(&nlr) == 0) {
|
||||
@ -877,6 +878,7 @@ void can_rx_irq_handler(uint can_id, uint fifo_id) {
|
||||
mp_obj_print_exception(&mp_plat_print, (mp_obj_t)nlr.ret_val);
|
||||
}
|
||||
gc_unlock();
|
||||
mp_sched_unlock();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -28,7 +28,6 @@
|
||||
#include <stddef.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "py/nlr.h"
|
||||
#include "py/runtime.h"
|
||||
#include "py/gc.h"
|
||||
#include "py/mphal.h"
|
||||
@ -412,6 +411,7 @@ void Handle_EXTI_Irq(uint32_t line) {
|
||||
if (line < EXTI_NUM_VECTORS) {
|
||||
mp_obj_t *cb = &MP_STATE_PORT(pyb_extint_callback)[line];
|
||||
if (*cb != mp_const_none) {
|
||||
mp_sched_lock();
|
||||
// When executing code within a handler we must lock the GC to prevent
|
||||
// any memory allocations. We must also catch any exceptions.
|
||||
gc_lock();
|
||||
@ -427,6 +427,7 @@ void Handle_EXTI_Irq(uint32_t line) {
|
||||
mp_obj_print_exception(&mp_plat_print, (mp_obj_t)nlr.ret_val);
|
||||
}
|
||||
gc_unlock();
|
||||
mp_sched_unlock();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -69,6 +69,8 @@
|
||||
#define MICROPY_MODULE_WEAK_LINKS (1)
|
||||
#define MICROPY_CAN_OVERRIDE_BUILTINS (1)
|
||||
#define MICROPY_USE_INTERNAL_ERRNO (1)
|
||||
#define MICROPY_ENABLE_SCHEDULER (1)
|
||||
#define MICROPY_SCHEDULER_DEPTH (8)
|
||||
#define MICROPY_VFS (1)
|
||||
#define MICROPY_VFS_FAT (1)
|
||||
|
||||
@ -303,6 +305,8 @@ static inline mp_uint_t disable_irq(void) {
|
||||
#if MICROPY_PY_THREAD
|
||||
#define MICROPY_EVENT_POLL_HOOK \
|
||||
do { \
|
||||
extern void mp_handle_pending(void); \
|
||||
mp_handle_pending(); \
|
||||
if (pyb_thread_enabled) { \
|
||||
MP_THREAD_GIL_EXIT(); \
|
||||
pyb_thread_yield(); \
|
||||
@ -312,7 +316,12 @@ static inline mp_uint_t disable_irq(void) {
|
||||
} \
|
||||
} while (0);
|
||||
#else
|
||||
#define MICROPY_EVENT_POLL_HOOK __WFI();
|
||||
#define MICROPY_EVENT_POLL_HOOK \
|
||||
do { \
|
||||
extern void mp_handle_pending(void); \
|
||||
mp_handle_pending(); \
|
||||
__WFI(); \
|
||||
} while (0);
|
||||
#endif
|
||||
|
||||
// There is no classical C heap in bare-metal ports, only Python
|
||||
|
@ -24,6 +24,7 @@
|
||||
* THE SOFTWARE.
|
||||
*/
|
||||
|
||||
#include "py/runtime.h"
|
||||
#include "py/mphal.h"
|
||||
#include "irq.h"
|
||||
#include "systick.h"
|
||||
@ -58,6 +59,7 @@ void mp_hal_delay_ms(mp_uint_t Delay) {
|
||||
// Wraparound of tick is taken care of by 2's complement arithmetic.
|
||||
while (uwTick - start < Delay) {
|
||||
// Enter sleep mode, waiting for (at least) the SysTick interrupt.
|
||||
mp_handle_pending();
|
||||
#if MICROPY_PY_THREAD
|
||||
if (pyb_thread_enabled) {
|
||||
pyb_thread_yield();
|
||||
|
@ -1363,6 +1363,7 @@ STATIC void timer_handle_irq_channel(pyb_timer_obj_t *tim, uint8_t channel, mp_o
|
||||
|
||||
// execute callback if it's set
|
||||
if (callback != mp_const_none) {
|
||||
mp_sched_lock();
|
||||
// When executing code within a handler we must lock the GC to prevent
|
||||
// any memory allocations. We must also catch any exceptions.
|
||||
gc_lock();
|
||||
@ -1382,6 +1383,7 @@ STATIC void timer_handle_irq_channel(pyb_timer_obj_t *tim, uint8_t channel, mp_o
|
||||
mp_obj_print_exception(&mp_plat_print, (mp_obj_t)nlr.ret_val);
|
||||
}
|
||||
gc_unlock();
|
||||
mp_sched_unlock();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user