From c66d86c5ce068e860ceb550ad75bf4da5211276b Mon Sep 17 00:00:00 2001 From: Damien George Date: Fri, 18 Apr 2014 22:38:09 +0100 Subject: [PATCH] stmhal: Big cleanup; merge gpio into Pin; make names consistent. This is an attempt to clean up the Micro Python API on the pyboard. Gpio functionality is now in the Pin object, which seems more natural. Constants for MODE and PULL are now in pyb.Pin. Names of some classes have been adjusted to conform to CamelCase. Other miscellaneous changes and clean up here and there. --- stmhal/Makefile | 4 +- stmhal/adc.c | 62 +++--- stmhal/adc.h | 3 +- stmhal/boards/stm32f4xx-prefix.c | 8 +- stmhal/{exti.c => extint.c} | 176 ++++++++--------- stmhal/{exti.h => extint.h} | 17 +- stmhal/gpio.c | 72 ------- stmhal/gpio.h | 7 - stmhal/main.c | 11 +- stmhal/modpyb.c | 43 ++-- stmhal/modstm.c | 108 ++++++----- stmhal/pin.c | 324 +++++++++++++++++++++++++++---- stmhal/pin.h | 25 +-- stmhal/pin_map.c | 226 --------------------- stmhal/pin_named_pins.c | 14 +- stmhal/qstrdefsport.h | 63 +++--- stmhal/stm32f4xx_it.c | 2 +- stmhal/usart.c | 10 +- stmhal/usrsw.c | 13 +- 19 files changed, 566 insertions(+), 622 deletions(-) rename stmhal/{exti.c => extint.c} (59%) rename stmhal/{exti.h => extint.h} (70%) delete mode 100644 stmhal/gpio.c delete mode 100644 stmhal/gpio.h delete mode 100644 stmhal/pin_map.c diff --git a/stmhal/Makefile b/stmhal/Makefile index 5501c4b8d9..dcffd164af 100644 --- a/stmhal/Makefile +++ b/stmhal/Makefile @@ -65,7 +65,6 @@ SRC_C = \ timer.c \ led.c \ pin.c \ - pin_map.c \ pin_named_pins.c \ usart.c \ usb.c \ @@ -84,8 +83,7 @@ SRC_C = \ modtime.c \ import.c \ lexerfatfs.c \ - gpio.c \ - exti.c \ + extint.c \ usrsw.c \ rng.c \ rtc.c \ diff --git a/stmhal/adc.c b/stmhal/adc.c index b0a7a0749a..78f0820d69 100644 --- a/stmhal/adc.c +++ b/stmhal/adc.c @@ -18,7 +18,7 @@ // adc = pyb.ADC(pin) // val = adc.read() // -// adc = pyb.ADC_all(resolution) +// adc = pyb.ADCAll(resolution) // val = adc.read_channel(channel) // val = adc.read_core_temp() // val = adc.read_core_vbat() @@ -129,7 +129,7 @@ STATIC mp_obj_t adc_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const mp_ if (MP_OBJ_IS_INT(pin_obj)) { channel = mp_obj_get_int(pin_obj); } else { - const pin_obj_t *pin = pin_map_user_obj(pin_obj); + const pin_obj_t *pin = pin_find(pin_obj); if ((pin->adc_num & PIN_ADC1) == 0) { // No ADC1 function on that pin nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "pin %s does not have ADC capabilities", pin->name)); @@ -138,10 +138,10 @@ STATIC mp_obj_t adc_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const mp_ } if (!IS_ADC_CHANNEL(channel)) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Not a valid ADC Channel: %d", channel)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "not a valid ADC Channel: %d", channel)); } if (pin_adc1[channel] == NULL) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Channel %d not available on this board", channel)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "channel %d not available on this board", channel)); } pyb_obj_adc_t *o = m_new_obj(pyb_obj_adc_t); @@ -211,12 +211,12 @@ const mp_obj_type_t pyb_adc_type = { /******************************************************************************/ /* adc all object */ -typedef struct _pyb_obj_adc_all_t { +typedef struct _pyb_adc_all_obj_t { mp_obj_base_t base; ADC_HandleTypeDef handle; -} pyb_obj_adc_all_t; +} pyb_adc_all_obj_t; -void adc_init_all(pyb_obj_adc_all_t *adc_all, uint32_t resolution) { +void adc_init_all(pyb_adc_all_obj_t *adc_all, uint32_t resolution) { switch (resolution) { case 6: resolution = ADC_RESOLUTION6b; break; @@ -314,46 +314,49 @@ float adc_read_core_vref(ADC_HandleTypeDef *adcHandle) { /******************************************************************************/ /* Micro Python bindings : adc_all object */ -STATIC void adc_all_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { - print(env, ""); +STATIC mp_obj_t adc_all_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const mp_obj_t *args) { + // check number of arguments + mp_check_nargs(n_args, 1, 1, n_kw, false); + + // make ADCAll object + pyb_adc_all_obj_t *o = m_new_obj(pyb_adc_all_obj_t); + o->base.type = &pyb_adc_all_type; + adc_init_all(o, mp_obj_get_int(args[0])); // args[0] is the resolution + + return o; } STATIC mp_obj_t adc_all_read_channel(mp_obj_t self_in, mp_obj_t channel) { - pyb_obj_adc_all_t *self = self_in; - + pyb_adc_all_obj_t *self = self_in; uint32_t chan = mp_obj_get_int(channel); uint32_t data = adc_config_and_read_channel(&self->handle, chan); return mp_obj_new_int(data); } +STATIC MP_DEFINE_CONST_FUN_OBJ_2(adc_all_read_channel_obj, adc_all_read_channel); STATIC mp_obj_t adc_all_read_core_temp(mp_obj_t self_in) { - pyb_obj_adc_all_t *self = self_in; - + pyb_adc_all_obj_t *self = self_in; int data = adc_read_core_temp(&self->handle); return mp_obj_new_int(data); } +STATIC MP_DEFINE_CONST_FUN_OBJ_1(adc_all_read_core_temp_obj, adc_all_read_core_temp); STATIC mp_obj_t adc_all_read_core_vbat(mp_obj_t self_in) { - pyb_obj_adc_all_t *self = self_in; - + pyb_adc_all_obj_t *self = self_in; float data = adc_read_core_vbat(&self->handle); return mp_obj_new_float(data); } +STATIC MP_DEFINE_CONST_FUN_OBJ_1(adc_all_read_core_vbat_obj, adc_all_read_core_vbat); STATIC mp_obj_t adc_all_read_core_vref(mp_obj_t self_in) { - pyb_obj_adc_all_t *self = self_in; - + pyb_adc_all_obj_t *self = self_in; float data = adc_read_core_vref(&self->handle); return mp_obj_new_float(data); } - -STATIC MP_DEFINE_CONST_FUN_OBJ_2(adc_all_read_channel_obj, adc_all_read_channel); -STATIC MP_DEFINE_CONST_FUN_OBJ_1(adc_all_read_core_temp_obj, adc_all_read_core_temp); -STATIC MP_DEFINE_CONST_FUN_OBJ_1(adc_all_read_core_vbat_obj, adc_all_read_core_vbat); STATIC MP_DEFINE_CONST_FUN_OBJ_1(adc_all_read_core_vref_obj, adc_all_read_core_vref); STATIC const mp_map_elem_t adc_all_locals_dict_table[] = { - { MP_OBJ_NEW_QSTR(MP_QSTR_read_channel), (mp_obj_t) &adc_all_read_channel_obj}, + { MP_OBJ_NEW_QSTR(MP_QSTR_read_channel), (mp_obj_t)&adc_all_read_channel_obj}, { MP_OBJ_NEW_QSTR(MP_QSTR_read_core_temp), (mp_obj_t)&adc_all_read_core_temp_obj}, { MP_OBJ_NEW_QSTR(MP_QSTR_read_core_vbat), (mp_obj_t)&adc_all_read_core_vbat_obj}, { MP_OBJ_NEW_QSTR(MP_QSTR_read_core_vref), (mp_obj_t)&adc_all_read_core_vref_obj}, @@ -361,18 +364,9 @@ STATIC const mp_map_elem_t adc_all_locals_dict_table[] = { STATIC MP_DEFINE_CONST_DICT(adc_all_locals_dict, adc_all_locals_dict_table); -STATIC const mp_obj_type_t adc_all_type = { +const mp_obj_type_t pyb_adc_all_type = { { &mp_type_type }, - .name = MP_QSTR_ADC, - .print = adc_all_print, + .name = MP_QSTR_ADCAll, + .make_new = adc_all_make_new, .locals_dict = (mp_obj_t)&adc_all_locals_dict, }; - -STATIC mp_obj_t pyb_ADC_all(mp_obj_t resolution) { - pyb_obj_adc_all_t *o = m_new_obj(pyb_obj_adc_all_t); - o->base.type = &adc_all_type; - adc_init_all(o, mp_obj_get_int(resolution)); - return o; -} - -MP_DEFINE_CONST_FUN_OBJ_1(pyb_ADC_all_obj, pyb_ADC_all); diff --git a/stmhal/adc.h b/stmhal/adc.h index c9f16932eb..deedac0112 100644 --- a/stmhal/adc.h +++ b/stmhal/adc.h @@ -1,3 +1,2 @@ extern const mp_obj_type_t pyb_adc_type; - -MP_DECLARE_CONST_FUN_OBJ(pyb_ADC_all_obj); +extern const mp_obj_type_t pyb_adc_all_type; diff --git a/stmhal/boards/stm32f4xx-prefix.c b/stmhal/boards/stm32f4xx-prefix.c index 989b8f0048..4d2313075a 100644 --- a/stmhal/boards/stm32f4xx-prefix.c +++ b/stmhal/boards/stm32f4xx-prefix.c @@ -2,18 +2,18 @@ #include #include -#include + +#include "stm32f4xx_hal.h" #include "misc.h" #include "mpconfig.h" #include "qstr.h" #include "obj.h" - #include "pin.h" #define AF(af_idx, af_fn, af_unit, af_type, af_ptr) \ { \ - { &pin_af_obj_type }, \ + { &pin_af_type }, \ .idx = (af_idx), \ .fn = AF_FN_ ## af_fn, \ .unit = (af_unit), \ @@ -23,7 +23,7 @@ #define PIN(p_port, p_pin, p_num_af, p_af, p_adc_num, p_adc_channel) \ { \ - { &pin_obj_type }, \ + { &pin_type }, \ .name = #p_port #p_pin, \ .port = PORT_ ## p_port, \ .pin = (p_pin), \ diff --git a/stmhal/exti.c b/stmhal/extint.c similarity index 59% rename from stmhal/exti.c rename to stmhal/extint.c index 5ea3db62bb..9ec599cf13 100644 --- a/stmhal/exti.c +++ b/stmhal/extint.c @@ -13,7 +13,7 @@ #include "runtime.h" #include "pin.h" -#include "exti.h" +#include "extint.h" // Usage Model: // @@ -27,8 +27,8 @@ // def callback(line): // print("line =", line) // -// # Note: Exti will automatically configure the gpio line as an input. -// exti = pyb.Exti(pin, pyb.Exti.MODE_IRQ_FALLING, pyb.PULLUP, callback) +// # Note: ExtInt will automatically configure the gpio line as an input. +// extint = pyb.ExtInt(pin, pyb.ExtInt.MODE_IRQ_FALLING, pyb.GPIO.PULL_UP, callback) // // Now every time a falling edge is seen on the X1 pin, the callback will be // called. Caution: mechanical pushbuttons have "bounce" and pushing or @@ -44,27 +44,27 @@ // All other pin objects go through the pin mapper to come up with one of the // gpio pins. // -// exti = pyb.Exti(pin, mode, pull, callback) +// extint = pyb.ExtInt(pin, mode, pull, callback) // -// Valid modes are pyb.Exti.MODE_IRQ_RISING, pyb.Exti.MODE_IRQ_FALLING, -// pyb.Exti.MODE_IRQ_RISING_FALLING, pyb.Exti.MODE_EVT_RISING, -// pyb.Exti.MODE_EVT_FALLING, and pyb.Exti.MODE_EVT_RISING_FALLING. +// Valid modes are pyb.ExtInt.MODE_IRQ_RISING, pyb.ExtInt.MODE_IRQ_FALLING, +// pyb.ExtInt.MODE_IRQ_RISING_FALLING, pyb.ExtInt.MODE_EVT_RISING, +// pyb.ExtInt.MODE_EVT_FALLING, and pyb.ExtInt.MODE_EVT_RISING_FALLING. // -// Only the MODE_IRQ_xxx modes have been tested. The MODE_EVENT_xxx modes have -// something to do with sleep mode and he WFE instruction. +// Only the MODE_IRQ_xxx modes have been tested. The MODE_EVT_xxx modes have +// something to do with sleep mode and the WFE instruction. // -// Valid pull values are pyb.PULL_UP, pyb.PULL_DOWN, pyb.PULL_NONE. +// Valid pull values are pyb.GPIO.PULL_UP, pyb.GPIO.PULL_DOWN, pyb.GPIO.PULL_NONE. // -// exti.line() will return the line number that pin was mapped to. -// exti.disable() can be use to disable the interrupt associated with a given -// exti object. This could be useful for debouncing. -// exti.enable() enables a disabled interrupt -// exti.swint() will allow the callback to be triggered from software. +// extint.line() will return the line number that pin was mapped to. +// extint.disable() can be use to disable the interrupt associated with a given +// exti object. This could be useful for debouncing. +// extint.enable() enables a disabled interrupt +// extint.swint() will allow the callback to be triggered from software. // -// pyb.Exti.regs() will dump the values of the EXTI registers. +// pyb.ExtInt.regs() will dump the values of the EXTI registers. // // There is also a C API, so that drivers which require EXTI interrupt lines -// can also use this code. See exti.h for the available functions and +// can also use this code. See extint.h for the available functions and // usrsw.h for an example of using this. // // TODO Add python method to change callback object. @@ -83,15 +83,15 @@ typedef struct { mp_obj_base_t base; mp_small_int_t line; -} exti_obj_t; +} extint_obj_t; typedef struct { mp_obj_t callback_obj; void *param; uint32_t mode; -} exti_vector_t; +} extint_vector_t; -STATIC exti_vector_t exti_vector[EXTI_NUM_VECTORS]; +STATIC extint_vector_t extint_vector[EXTI_NUM_VECTORS]; #if !defined(ETH) #define ETH_WKUP_IRQn 62 // The 405 doesn't have ETH, but we want a value to put in our table @@ -110,7 +110,7 @@ STATIC const uint8_t nvic_irq_channel[EXTI_NUM_VECTORS] = { // // NOTE: param is for C callers. Python can use closure to get an object bound // with the function. -uint exti_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t pull_obj, mp_obj_t callback_obj, bool override_callback_obj, void *param) { +uint extint_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t pull_obj, mp_obj_t callback_obj, bool override_callback_obj, void *param) { const pin_obj_t *pin = NULL; uint v_line; @@ -120,13 +120,13 @@ uint exti_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t pull_obj, mp_ob // get both the port number and line number. v_line = mp_obj_get_int(pin_obj); if (v_line < 16) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "EXTI vector %d < 16, use a Pin object", v_line)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "ExtInt vector %d < 16, use a Pin object", v_line)); } if (v_line >= EXTI_NUM_VECTORS) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "EXTI vector %d >= max of %d", v_line, EXTI_NUM_VECTORS)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "ExtInt vector %d >= max of %d", v_line, EXTI_NUM_VECTORS)); } } else { - pin = pin_map_user_obj(pin_obj); + pin = pin_find(pin_obj); v_line = pin->pin; } int mode = mp_obj_get_int(mode_obj); @@ -136,24 +136,24 @@ uint exti_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t pull_obj, mp_ob mode != GPIO_MODE_EVT_RISING && mode != GPIO_MODE_EVT_FALLING && mode != GPIO_MODE_EVT_RISING_FALLING) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Invalid EXTI Mode: %d", mode)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Invalid ExtInt Mode: %d", mode)); } int pull = mp_obj_get_int(pull_obj); if (pull != GPIO_NOPULL && pull != GPIO_PULLUP && pull != GPIO_PULLDOWN) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Invalid EXTI Pull: %d", pull)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Invalid ExtInt Pull: %d", pull)); } - exti_vector_t *v = &exti_vector[v_line]; + extint_vector_t *v = &extint_vector[v_line]; if (!override_callback_obj && v->callback_obj != mp_const_none && callback_obj != mp_const_none) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "EXTI vector %d is already in use", v_line)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "ExtInt vector %d is already in use", v_line)); } // We need to update callback and param atomically, so we disable the line // before we update anything. - exti_disable(v_line); + extint_disable(v_line); v->callback_obj = callback_obj; v->param = param; @@ -169,7 +169,7 @@ uint exti_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t pull_obj, mp_ob exti.Speed = GPIO_SPEED_FAST; HAL_GPIO_Init(pin->gpio, &exti); - // Calling HAL_GPIO_Init does an implicit exti_enable + // Calling HAL_GPIO_Init does an implicit extint_enable /* Enable and set NVIC Interrupt to the lowest priority */ HAL_NVIC_SetPriority(nvic_irq_channel[v_line], 0x0F, 0x0F); @@ -178,17 +178,17 @@ uint exti_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t pull_obj, mp_ob return v_line; } -void exti_enable(uint line) { +void extint_enable(uint line) { if (line >= EXTI_NUM_VECTORS) { return; } // Since manipulating IMR/EMR is a read-modify-write, and we want this to // be atomic, we use the bit-band area to just affect the bit we're // interested in. - EXTI_MODE_BB(exti_vector[line].mode, line) = 1; + EXTI_MODE_BB(extint_vector[line].mode, line) = 1; } -void exti_disable(uint line) { +void extint_disable(uint line) { if (line >= EXTI_NUM_VECTORS) { return; } @@ -199,37 +199,37 @@ void exti_disable(uint line) { EXTI_MODE_BB(EXTI_Mode_Event, line) = 0; } -void exti_swint(uint line) { +void extint_swint(uint line) { if (line >= EXTI_NUM_VECTORS) { return; } EXTI->SWIER = (1 << line); } -STATIC mp_obj_t exti_obj_line(mp_obj_t self_in) { - exti_obj_t *self = self_in; +STATIC mp_obj_t extint_obj_line(mp_obj_t self_in) { + extint_obj_t *self = self_in; return MP_OBJ_NEW_SMALL_INT(self->line); } -STATIC mp_obj_t exti_obj_enable(mp_obj_t self_in) { - exti_obj_t *self = self_in; - exti_enable(self->line); +STATIC mp_obj_t extint_obj_enable(mp_obj_t self_in) { + extint_obj_t *self = self_in; + extint_enable(self->line); return mp_const_none; } -STATIC mp_obj_t exti_obj_disable(mp_obj_t self_in) { - exti_obj_t *self = self_in; - exti_disable(self->line); +STATIC mp_obj_t extint_obj_disable(mp_obj_t self_in) { + extint_obj_t *self = self_in; + extint_disable(self->line); return mp_const_none; } -STATIC mp_obj_t exti_obj_swint(mp_obj_t self_in) { - exti_obj_t *self = self_in; - exti_swint(self->line); +STATIC mp_obj_t extint_obj_swint(mp_obj_t self_in) { + extint_obj_t *self = self_in; + extint_swint(self->line); return mp_const_none; } -STATIC mp_obj_t exti_regs(void) { +STATIC mp_obj_t extint_regs(void) { printf("EXTI_IMR %08lx\n", EXTI->IMR); printf("EXTI_EMR %08lx\n", EXTI->EMR); printf("EXTI_RTSR %08lx\n", EXTI->RTSR); @@ -239,62 +239,62 @@ STATIC mp_obj_t exti_regs(void) { return mp_const_none; } -STATIC MP_DEFINE_CONST_FUN_OBJ_1(exti_obj_line_obj, exti_obj_line); -STATIC MP_DEFINE_CONST_FUN_OBJ_1(exti_obj_enable_obj, exti_obj_enable); -STATIC MP_DEFINE_CONST_FUN_OBJ_1(exti_obj_disable_obj, exti_obj_disable); -STATIC MP_DEFINE_CONST_FUN_OBJ_1(exti_obj_swint_obj, exti_obj_swint); -STATIC MP_DEFINE_CONST_FUN_OBJ_0(exti_regs_fun_obj, exti_regs); -STATIC MP_DEFINE_CONST_STATICMETHOD_OBJ(exti_regs_obj, (mp_obj_t)&exti_regs_fun_obj); +// line_obj = pyb.ExtInt(pin, mode, trigger, callback) -STATIC const mp_map_elem_t exti_locals_dict_table[] = { - { MP_OBJ_NEW_QSTR(MP_QSTR_line), (mp_obj_t)&exti_obj_line_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_enable), (mp_obj_t)&exti_obj_enable_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_disable), (mp_obj_t)&exti_obj_disable_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_swint), (mp_obj_t)&exti_obj_swint_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_regs), (mp_obj_t)&exti_regs_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_MODE_IRQ_RISING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_IT_RISING) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_MODE_IRQ_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_IT_FALLING) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_MODE_IRQ_RISING_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_IT_RISING_FALLING) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_MODE_EVT_RISING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_EVT_RISING) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_MODE_EVT_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_EVT_FALLING) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_MODE_EVT_RISING_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_EVT_RISING_FALLING) }, -}; - -STATIC MP_DEFINE_CONST_DICT(exti_locals_dict, exti_locals_dict_table); - -// line_obj = pyb.Exti(pin, mode, trigger, callback) - -STATIC mp_obj_t exti_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const mp_obj_t *args) { - // type_in == exti_obj_type +STATIC mp_obj_t extint_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const mp_obj_t *args) { + // type_in == extint_obj_type mp_check_nargs(n_args, 4, 4, n_kw, false); - exti_obj_t *self = m_new_obj(exti_obj_t); + extint_obj_t *self = m_new_obj(extint_obj_t); self->base.type = type_in; mp_obj_t line_obj = args[0]; mp_obj_t mode_obj = args[1]; mp_obj_t trigger_obj = args[2]; mp_obj_t callback_obj = args[3]; - self->line = exti_register(line_obj, mode_obj, trigger_obj, callback_obj, false, NULL); + self->line = extint_register(line_obj, mode_obj, trigger_obj, callback_obj, false, NULL); return self; } -STATIC void exti_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { - exti_obj_t *self = self_in; - print(env, "", self->line); +STATIC void extint_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { + extint_obj_t *self = self_in; + print(env, "", self->line); } -const mp_obj_type_t exti_obj_type = { - { &mp_type_type }, - .name = MP_QSTR_Exti, - .print = exti_obj_print, - .make_new = exti_make_new, - .locals_dict = (mp_obj_t)&exti_locals_dict, +STATIC MP_DEFINE_CONST_FUN_OBJ_1(extint_obj_line_obj, extint_obj_line); +STATIC MP_DEFINE_CONST_FUN_OBJ_1(extint_obj_enable_obj, extint_obj_enable); +STATIC MP_DEFINE_CONST_FUN_OBJ_1(extint_obj_disable_obj, extint_obj_disable); +STATIC MP_DEFINE_CONST_FUN_OBJ_1(extint_obj_swint_obj, extint_obj_swint); +STATIC MP_DEFINE_CONST_FUN_OBJ_0(extint_regs_fun_obj, extint_regs); +STATIC MP_DEFINE_CONST_STATICMETHOD_OBJ(extint_regs_obj, (mp_obj_t)&extint_regs_fun_obj); + +STATIC const mp_map_elem_t extint_locals_dict_table[] = { + { MP_OBJ_NEW_QSTR(MP_QSTR_line), (mp_obj_t)&extint_obj_line_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_enable), (mp_obj_t)&extint_obj_enable_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_disable), (mp_obj_t)&extint_obj_disable_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_swint), (mp_obj_t)&extint_obj_swint_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_regs), (mp_obj_t)&extint_regs_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_IRQ_RISING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_IT_RISING) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_IRQ_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_IT_FALLING) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_IRQ_RISING_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_IT_RISING_FALLING) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_EVT_RISING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_EVT_RISING) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_EVT_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_EVT_FALLING) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_EVT_RISING_FALLING), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_EVT_RISING_FALLING) }, }; -void exti_init(void) { - for (exti_vector_t *v = exti_vector; v < &exti_vector[EXTI_NUM_VECTORS]; v++) { +STATIC MP_DEFINE_CONST_DICT(extint_locals_dict, extint_locals_dict_table); + +const mp_obj_type_t extint_type = { + { &mp_type_type }, + .name = MP_QSTR_ExtInt, + .print = extint_obj_print, + .make_new = extint_make_new, + .locals_dict = (mp_obj_t)&extint_locals_dict, +}; + +void extint_init(void) { + for (extint_vector_t *v = extint_vector; v < &extint_vector[EXTI_NUM_VECTORS]; v++) { v->callback_obj = mp_const_none; v->param = NULL; v->mode = EXTI_Mode_Interrupt; @@ -306,7 +306,7 @@ void Handle_EXTI_Irq(uint32_t line) { if (__HAL_GPIO_EXTI_GET_FLAG(1 << line)) { __HAL_GPIO_EXTI_CLEAR_FLAG(1 << line); if (line < EXTI_NUM_VECTORS) { - exti_vector_t *v = &exti_vector[line]; + extint_vector_t *v = &extint_vector[line]; if (v->callback_obj != mp_const_none) { // When executing code within a handler we must lock the GC to prevent // any memory allocations. We must also catch any exceptions. @@ -318,8 +318,8 @@ void Handle_EXTI_Irq(uint32_t line) { } else { // Uncaught exception; disable the callback so it doesn't run again. v->callback_obj = mp_const_none; - exti_disable(line); - printf("Uncaught exception in EXTI interrupt handler line %lu\n", line); + extint_disable(line); + printf("Uncaught exception in ExtInt interrupt handler line %lu\n", line); mp_obj_print_exception((mp_obj_t)nlr.ret_val); } gc_unlock(); diff --git a/stmhal/exti.h b/stmhal/extint.h similarity index 70% rename from stmhal/exti.h rename to stmhal/extint.h index 6feb9dceaf..c64931211f 100644 --- a/stmhal/exti.h +++ b/stmhal/extint.h @@ -20,19 +20,14 @@ #define EXTI_TRIGGER_FALLING (offsetof(EXTI_TypeDef, FTSR)) #define EXTI_TRIGGER_RISING_FALLING (EXTI_TRIGGER_RISING + EXTI_TRIGGER_FALLING) // just different from RISING or FALLING -void exti_init(void); +void extint_init(void); -uint exti_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t trigger_obj, mp_obj_t callback_obj, bool override_callback_obj, void *param); +uint extint_register(mp_obj_t pin_obj, mp_obj_t mode_obj, mp_obj_t trigger_obj, mp_obj_t callback_obj, bool override_callback_obj, void *param); -void exti_enable(uint line); -void exti_disable(uint line); -void exti_swint(uint line); +void extint_enable(uint line); +void extint_disable(uint line); +void extint_swint(uint line); void Handle_EXTI_Irq(uint32_t line); -typedef struct { - mp_obj_t callback; - void *param; -} exti_t; - -extern const mp_obj_type_t exti_obj_type; +extern const mp_obj_type_t extint_type; diff --git a/stmhal/gpio.c b/stmhal/gpio.c deleted file mode 100644 index 4548dca587..0000000000 --- a/stmhal/gpio.c +++ /dev/null @@ -1,72 +0,0 @@ -// This is a woefully inadequate set of bindings for GPIO control, and -// needs to be replaced with something much better. - -#include -#include -#include - -#include "nlr.h" -#include "misc.h" -#include "mpconfig.h" -#include "qstr.h" -#include "misc.h" -#include "parse.h" -#include "obj.h" -#include "compile.h" -#include "runtime0.h" -#include "runtime.h" -#include "systick.h" -#include "gpio.h" -#include "pin.h" - -mp_obj_t pyb_gpio(uint n_args, mp_obj_t *args) { - const pin_obj_t *pin = pin_map_user_obj(args[0]); - if (n_args == 1) { - // get pin - return MP_OBJ_NEW_SMALL_INT(HAL_GPIO_ReadPin(pin->gpio, pin->pin_mask)); - } - - // set pin - HAL_GPIO_WritePin(pin->gpio, pin->pin_mask, mp_obj_is_true(args[1])); - return mp_const_none; -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pyb_gpio_obj, 1, 2, pyb_gpio); - -mp_obj_t pyb_gpio_input(uint n_args, mp_obj_t *args) { - const pin_obj_t *pin = pin_map_user_obj(args[0]); - - uint32_t pull = GPIO_NOPULL; - if (n_args > 1) { - pull = mp_obj_get_int(args[1]); - } - GPIO_InitTypeDef GPIO_InitStructure; - GPIO_InitStructure.Pin = pin->pin_mask; - GPIO_InitStructure.Mode = GPIO_MODE_INPUT; - GPIO_InitStructure.Pull = pull; - HAL_GPIO_Init(pin->gpio, &GPIO_InitStructure); - - return mp_const_none; -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pyb_gpio_input_obj, 1, 2, pyb_gpio_input); - -mp_obj_t pyb_gpio_output(uint n_args, mp_obj_t *args) { - const pin_obj_t *pin = pin_map_user_obj(args[0]); - - uint32_t mode = GPIO_MODE_OUTPUT_PP; - if (n_args > 1) { - mode = mp_obj_get_int(args[1]) == GPIO_MODE_OUTPUT_OD ? - GPIO_MODE_OUTPUT_OD: GPIO_MODE_OUTPUT_PP; - } - GPIO_InitTypeDef GPIO_InitStructure; - GPIO_InitStructure.Pin = pin->pin_mask; - GPIO_InitStructure.Mode = mode; - GPIO_InitStructure.Speed = GPIO_SPEED_FAST; - GPIO_InitStructure.Pull = GPIO_NOPULL; - HAL_GPIO_Init(pin->gpio, &GPIO_InitStructure); - - return mp_const_none; -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pyb_gpio_output_obj, 1, 2, pyb_gpio_output); diff --git a/stmhal/gpio.h b/stmhal/gpio.h deleted file mode 100644 index f43adfdac0..0000000000 --- a/stmhal/gpio.h +++ /dev/null @@ -1,7 +0,0 @@ -mp_obj_t pyb_gpio(uint n_args, mp_obj_t *args); -mp_obj_t pyb_gpio_output(uint n_args, mp_obj_t *args); -mp_obj_t pyb_gpio_input(uint n_args, mp_obj_t *args); - -MP_DECLARE_CONST_FUN_OBJ(pyb_gpio_obj); -MP_DECLARE_CONST_FUN_OBJ(pyb_gpio_input_obj); -MP_DECLARE_CONST_FUN_OBJ(pyb_gpio_output_obj); diff --git a/stmhal/main.c b/stmhal/main.c index 4fa5b2a436..5d405453b1 100644 --- a/stmhal/main.c +++ b/stmhal/main.c @@ -21,7 +21,8 @@ #include "usart.h" #include "timer.h" #include "led.h" -#include "exti.h" +#include "pin.h" +#include "extint.h" #include "usrsw.h" #include "usb.h" #include "rtc.h" @@ -34,7 +35,6 @@ #include "accel.h" #include "servo.h" #include "dac.h" -#include "pin.h" #if 0 #include "pybwlan.h" #endif @@ -292,10 +292,11 @@ soft_reset: readline_init(); - exti_init(); + pin_init(); + extint_init(); #if MICROPY_HW_HAS_SWITCH - // must come after exti_init + // must come after extint_init switch_init(); #endif @@ -304,8 +305,6 @@ soft_reset: lcd_init(); #endif - pin_map_init(); - // local filesystem init { // try to mount the flash diff --git a/stmhal/modpyb.c b/stmhal/modpyb.c index be747958ef..bb41f3e355 100644 --- a/stmhal/modpyb.c +++ b/stmhal/modpyb.c @@ -1,7 +1,7 @@ #include #include -#include +#include "stm32f4xx_hal.h" #include "misc.h" #include "mpconfig.h" @@ -15,7 +15,7 @@ #include "led.h" #include "gpio.h" #include "pin.h" -#include "exti.h" +#include "extint.h" #include "usrsw.h" #include "rng.h" #include "rtc.h" @@ -139,6 +139,20 @@ STATIC mp_obj_t pyb_wfi(void) { MP_DEFINE_CONST_FUN_OBJ_0(pyb_wfi_obj, pyb_wfi); +STATIC mp_obj_t pyb_disable_irq(void) { + __disable_irq(); + return mp_const_none; +} + +MP_DEFINE_CONST_FUN_OBJ_0(pyb_disable_irq_obj, pyb_disable_irq); + +STATIC mp_obj_t pyb_enable_irq(void) { + __enable_irq(); + return mp_const_none; +} + +MP_DEFINE_CONST_FUN_OBJ_0(pyb_enable_irq_obj, pyb_enable_irq); + #if 0 STATIC void SYSCLKConfig_STOP(void) { /* After wake-up from STOP reconfigure the system clock */ @@ -235,6 +249,9 @@ STATIC const mp_map_elem_t pyb_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR_repl_info), (mp_obj_t)&pyb_set_repl_info_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_wfi), (mp_obj_t)&pyb_wfi_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_disable_irq), (mp_obj_t)&pyb_disable_irq_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_enable_irq), (mp_obj_t)&pyb_enable_irq_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_stop), (mp_obj_t)&pyb_stop_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_standby), (mp_obj_t)&pyb_standby_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_source_dir), (mp_obj_t)&pyb_source_dir_obj }, @@ -258,6 +275,9 @@ STATIC const mp_map_elem_t pyb_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR_rtc_info), (mp_obj_t)&pyb_rtc_info_obj }, #endif + { MP_OBJ_NEW_QSTR(MP_QSTR_Pin), (mp_obj_t)&pin_type }, + { MP_OBJ_NEW_QSTR(MP_QSTR_ExtInt), (mp_obj_t)&extint_type }, + #if MICROPY_HW_ENABLE_SERVO { MP_OBJ_NEW_QSTR(MP_QSTR_pwm), (mp_obj_t)&pyb_pwm_set_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_servo), (mp_obj_t)&pyb_servo_set_obj }, @@ -274,10 +294,10 @@ STATIC const mp_map_elem_t pyb_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR_Led), (mp_obj_t)&pyb_led_type }, { MP_OBJ_NEW_QSTR(MP_QSTR_I2C), (mp_obj_t)&pyb_i2c_type }, - { MP_OBJ_NEW_QSTR(MP_QSTR_Usart), (mp_obj_t)&pyb_usart_type }, + { MP_OBJ_NEW_QSTR(MP_QSTR_USART), (mp_obj_t)&pyb_usart_type }, { MP_OBJ_NEW_QSTR(MP_QSTR_ADC), (mp_obj_t)&pyb_adc_type }, - { MP_OBJ_NEW_QSTR(MP_QSTR_ADC_all), (mp_obj_t)&pyb_ADC_all_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_ADCAll), (mp_obj_t)&pyb_adc_all_type }, #if MICROPY_HW_ENABLE_DAC { MP_OBJ_NEW_QSTR(MP_QSTR_DAC), (mp_obj_t)&pyb_dac_type }, @@ -290,21 +310,6 @@ STATIC const mp_map_elem_t pyb_module_globals_table[] = { // input { MP_OBJ_NEW_QSTR(MP_QSTR_input), (mp_obj_t)&pyb_input_obj }, - // pin mapper - { MP_OBJ_NEW_QSTR(MP_QSTR_Pin), (mp_obj_t)&pin_map_obj }, - - // GPIO bindings - { MP_OBJ_NEW_QSTR(MP_QSTR_gpio), (mp_obj_t)&pyb_gpio_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_gpio_in), (mp_obj_t)&pyb_gpio_input_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_gpio_out), (mp_obj_t)&pyb_gpio_output_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_PULL_NONE), MP_OBJ_NEW_SMALL_INT(GPIO_NOPULL) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_PULL_UP), MP_OBJ_NEW_SMALL_INT(GPIO_PULLUP) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_PULL_DOWN), MP_OBJ_NEW_SMALL_INT(GPIO_PULLDOWN) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_PUSH_PULL), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_OUTPUT_PP) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_OPEN_DRAIN), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_OUTPUT_OD) }, - - // EXTI bindings - { MP_OBJ_NEW_QSTR(MP_QSTR_Exti), (mp_obj_t)&exti_obj_type }, }; STATIC const mp_obj_dict_t pyb_module_globals = { diff --git a/stmhal/modstm.c b/stmhal/modstm.c index 5e72a75bb2..9134063428 100644 --- a/stmhal/modstm.c +++ b/stmhal/modstm.c @@ -1,7 +1,7 @@ #include #include -#include +#include "stm32f4xx_hal.h" #include "nlr.h" #include "misc.h" @@ -10,11 +10,17 @@ #include "obj.h" #include "modstm.h" +// To use compile-time constants we are restricted to 31-bit numbers (a small int, +// so it fits in a Micro Python object pointer). Thus, when extracting a constant +// from an object, we must clear the MSB. + STATIC uint32_t get_read_addr(mp_obj_t addr_o, uint align) { uint32_t addr = mp_obj_get_int(addr_o) & 0x7fffffff; + /* if (addr < 0x10000000) { nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "cannot read from address %08x", addr)); } + */ if ((addr & (align - 1)) != 0) { nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "address %08x is not aligned to %d bytes", addr, align)); } @@ -24,6 +30,8 @@ STATIC uint32_t get_read_addr(mp_obj_t addr_o, uint align) { STATIC uint32_t get_write_addr(mp_obj_t addr_o, uint align) { uint32_t addr = mp_obj_get_int(addr_o) & 0x7fffffff; if (addr < 0x10000000) { + // Everything below 0x10000000 is either ROM or aliased to something higher, so we don't + // lose anything by restricting writes to this area, and we gain some safety. nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "cannot write to address %08x", addr)); } if ((addr & (align - 1)) != 0) { @@ -32,66 +40,62 @@ STATIC uint32_t get_write_addr(mp_obj_t addr_o, uint align) { return addr; } -STATIC mp_obj_t stm_read8(mp_obj_t addr) { - uint32_t a = get_read_addr(addr, 1); - uint32_t v = *(uint8_t*)a; - return mp_obj_new_int(v); +typedef struct _stm_mem_obj_t { + mp_obj_base_t base; + uint32_t elem_size; // in bytes +} stm_mem_obj_t; + +STATIC void stm_mem_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { + stm_mem_obj_t *self = self_in; + print(env, "<%u-bit memory>", 8 * self->elem_size); } -STATIC MP_DEFINE_CONST_FUN_OBJ_1(stm_read8_obj, stm_read8); - -STATIC mp_obj_t stm_read16(mp_obj_t addr) { - uint32_t a = get_read_addr(addr, 2); - uint32_t v = *(uint16_t*)a; - return mp_obj_new_int(v); +STATIC mp_obj_t stm_mem_subscr(mp_obj_t self_in, mp_obj_t index, mp_obj_t value) { + // TODO support slice index to read/write multiple values at once + stm_mem_obj_t *self = self_in; + if (value == MP_OBJ_NULL) { + // delete + return MP_OBJ_NOT_SUPPORTED; + } else if (value == MP_OBJ_SENTINEL) { + // load + uint32_t addr = get_read_addr(index, self->elem_size); + uint32_t val; + switch (self->elem_size) { + case 1: val = (*(uint8_t*)addr); break; + case 2: val = (*(uint16_t*)addr); break; + default: val = (*(uint32_t*)addr); break; + } + return mp_obj_new_int(val); + } else { + // store + uint32_t addr = get_write_addr(index, self->elem_size); + uint32_t val = mp_obj_get_int(value); + switch (self->elem_size) { + case 1: (*(uint8_t*)addr) = val; break; + case 2: (*(uint16_t*)addr) = val; break; + default: (*(uint32_t*)addr) = val; break; + } + return mp_const_none; + } } -STATIC MP_DEFINE_CONST_FUN_OBJ_1(stm_read16_obj, stm_read16); +STATIC const mp_obj_type_t stm_mem_type = { + { &mp_type_type }, + .name = MP_QSTR_mem, + .print = stm_mem_print, + .subscr = stm_mem_subscr, +}; -STATIC mp_obj_t stm_read32(mp_obj_t addr) { - uint32_t a = get_read_addr(addr, 4); - uint32_t v = *(uint32_t*)a; - return mp_obj_new_int(v); -} - -STATIC MP_DEFINE_CONST_FUN_OBJ_1(stm_read32_obj, stm_read32); - -STATIC mp_obj_t stm_write8(mp_obj_t addr, mp_obj_t val) { - uint32_t a = get_write_addr(addr, 1); - uint32_t v = mp_obj_get_int(val); - *(uint8_t*)a = v; - return mp_const_none; -} - -STATIC MP_DEFINE_CONST_FUN_OBJ_2(stm_write8_obj, stm_write8); - -STATIC mp_obj_t stm_write16(mp_obj_t addr, mp_obj_t val) { - uint32_t a = get_write_addr(addr, 2); - uint32_t v = mp_obj_get_int(val); - *(uint16_t*)a = v; - return mp_const_none; -} - -STATIC MP_DEFINE_CONST_FUN_OBJ_2(stm_write16_obj, stm_write16); - -STATIC mp_obj_t stm_write32(mp_obj_t addr, mp_obj_t val) { - uint32_t a = get_write_addr(addr, 4); - uint32_t v = mp_obj_get_int(val); - *(uint32_t*)a = v; - return mp_const_none; -} - -STATIC MP_DEFINE_CONST_FUN_OBJ_2(stm_write32_obj, stm_write32); +STATIC const stm_mem_obj_t stm_mem8_obj = {{&stm_mem_type}, 1}; +STATIC const stm_mem_obj_t stm_mem16_obj = {{&stm_mem_type}, 2}; +STATIC const stm_mem_obj_t stm_mem32_obj = {{&stm_mem_type}, 4}; STATIC const mp_map_elem_t stm_module_globals_table[] = { { MP_OBJ_NEW_QSTR(MP_QSTR___name__), MP_OBJ_NEW_QSTR(MP_QSTR_stm) }, - { MP_OBJ_NEW_QSTR(MP_QSTR_read8), (mp_obj_t)&stm_read8_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_read16), (mp_obj_t)&stm_read16_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_read32), (mp_obj_t)&stm_read32_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_write8), (mp_obj_t)&stm_write8_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_write16), (mp_obj_t)&stm_write16_obj }, - { MP_OBJ_NEW_QSTR(MP_QSTR_write32), (mp_obj_t)&stm_write32_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_mem8), (mp_obj_t)&stm_mem8_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_mem16), (mp_obj_t)&stm_mem16_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_mem32), (mp_obj_t)&stm_mem32_obj }, { MP_OBJ_NEW_QSTR(MP_QSTR_GPIOA), MP_OBJ_NEW_SMALL_INT(GPIOA_BASE) }, { MP_OBJ_NEW_QSTR(MP_QSTR_GPIOB), MP_OBJ_NEW_SMALL_INT(GPIOB_BASE) }, diff --git a/stmhal/pin.c b/stmhal/pin.c index 735901c306..ed5865d796 100644 --- a/stmhal/pin.c +++ b/stmhal/pin.c @@ -1,78 +1,330 @@ #include #include #include -#include +#include "stm32f4xx_hal.h" + +#include "nlr.h" #include "misc.h" #include "mpconfig.h" #include "qstr.h" #include "obj.h" - +#include "runtime.h" #include "pin.h" -#if 0 -void pin_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { +// Usage Model: +// +// All Board Pins are predefined as pyb.Pin.board.Name +// +// x1_pin = pyb.Pin.board.X1 +// +// g = pyb.gpio(pyb.Pin.board.X1, 0) +// +// CPU pins which correspond to the board pins are available +// as pyb.cpu.Name. For the CPU pins, the names are the port letter +// followed by the pin number. On the PYBV4, pyb.Pin.board.X1 and +// pyb.Pin.cpu.B6 are the same pin. +// +// You can also use strings: +// +// g = pyb.gpio('X1', 0) +// +// Users can add their own names: +// +// pyb.Pin("LeftMotorDir", pyb.Pin.cpu.C12) +// g = pyb.gpio("LeftMotorDir", 0) +// +// and can query mappings +// +// pin = pyb.Pin("LeftMotorDir"); +// +// Users can also add their own mapping function: +// +// def MyMapper(pin_name): +// if pin_name == "LeftMotorDir": +// return pyb.Pin.cpu.A0 +// +// pyb.Pin.mapper(MyMapper) +// +// So, if you were to call: pyb.gpio("LeftMotorDir", 0) +// then "LeftMotorDir" is passed directly to the mapper function. +// +// To summarize, the following order determines how things get mapped into +// an ordinal pin number: +// +// 1 - Directly specify a pin object +// 2 - User supplied mapping function +// 3 - User supplied mapping (object must be usable as a dictionary key) +// 4 - Supply a string which matches a board pin +// 5 - Supply a string which matches a CPU port/pin +// +// You can set pyb.Pin.debug(True) to get some debug information about +// how a particular object gets mapped to a pin. + +// Pin class variables +STATIC mp_obj_t pin_class_mapper; +STATIC mp_obj_t pin_class_map_dict; +STATIC bool pin_class_debug; + +void pin_init(void) { + pin_class_mapper = MP_OBJ_NULL; + pin_class_map_dict = MP_OBJ_NULL; + pin_class_debug = false; +} + +// C API used to convert a user-supplied pin name into an ordinal pin number. +const pin_obj_t *pin_find(mp_obj_t user_obj) { + const pin_obj_t *pin_obj; + + // If a pin was provided, then use it + if (MP_OBJ_IS_TYPE(user_obj, &pin_type)) { + pin_obj = user_obj; + if (pin_class_debug) { + printf("Pin map passed pin "); + mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); + printf("\n"); + } + return pin_obj; + } + + if (pin_class_mapper != MP_OBJ_NULL) { + pin_obj = mp_call_function_1(pin_class_mapper, user_obj); + if (pin_obj != mp_const_none) { + if (!MP_OBJ_IS_TYPE(pin_obj, &pin_type)) { + nlr_raise(mp_obj_new_exception_msg(&mp_type_ValueError, "Pin.mapper didn't return a Pin object")); + } + if (pin_class_debug) { + printf("Pin.mapper maps "); + mp_obj_print(user_obj, PRINT_REPR); + printf(" to "); + mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); + printf("\n"); + } + return pin_obj; + } + // The pin mapping function returned mp_const_none, fall through to + // other lookup methods. + } + + if (pin_class_map_dict != MP_OBJ_NULL) { + mp_map_t *pin_map_map = mp_obj_dict_get_map(pin_class_map_dict); + mp_map_elem_t *elem = mp_map_lookup(pin_map_map, user_obj, MP_MAP_LOOKUP); + if (elem != NULL && elem->value != NULL) { + pin_obj = elem->value; + if (pin_class_debug) { + printf("Pin.map_dict maps "); + mp_obj_print(user_obj, PRINT_REPR); + printf(" to "); + mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); + printf("\n"); + } + return pin_obj; + } + } + + // See if the pin name matches a board pin + const char *pin_name = mp_obj_str_get_str(user_obj); + pin_obj = pin_find_named_pin(pin_board_pins, pin_name); + if (pin_obj) { + if (pin_class_debug) { + printf("Pin.board maps "); + mp_obj_print(user_obj, PRINT_REPR); + printf(" to "); + mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); + printf("\n"); + } + return pin_obj; + } + + // See if the pin name matches a cpu pin + pin_obj = pin_find_named_pin(pin_cpu_pins, pin_name); + if (pin_obj) { + if (pin_class_debug) { + printf("Pin.cpu maps "); + mp_obj_print(user_obj, PRINT_REPR); + printf(" to "); + mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); + printf("\n"); + } + return pin_obj; + } + + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "pin '%s' not a valid pin identifier", pin_name)); +} + +STATIC void pin_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { pin_obj_t *self = self_in; print(env, "", self->name); } -mp_obj_t pin_obj_name(mp_obj_t self_in) { +// Pin constructor +STATIC mp_obj_t pin_make_new(mp_obj_t self_in, uint n_args, uint n_kw, const mp_obj_t *args) { + mp_check_nargs(n_args, 1, 3, n_kw, false); + + // Run an argument through the mapper and return the result. + const pin_obj_t *pin = pin_find(args[0]); + + if (n_args >= 2) { + // pin mode given, so configure this GPIO + + // get io mode + uint mode = mp_obj_get_int(args[1]); + if (!IS_GPIO_MODE(mode)) { + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "invalid pin mode: %d", mode)); + } + + // get pull mode + uint pull = GPIO_NOPULL; + if (n_args >= 3) { + pull = mp_obj_get_int(args[2]); + if (!IS_GPIO_PULL(pull)) { + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "invalid pin pull: %d", pull)); + } + } + + // configure the GPIO as requested + GPIO_InitTypeDef GPIO_InitStructure; + GPIO_InitStructure.Pin = pin->pin_mask; + GPIO_InitStructure.Mode = mode; + GPIO_InitStructure.Pull = pull; + GPIO_InitStructure.Speed = GPIO_SPEED_FAST; + GPIO_InitStructure.Alternate = 0; + HAL_GPIO_Init(pin->gpio, &GPIO_InitStructure); + } + + return (mp_obj_t)pin; +} + +// class method +STATIC mp_obj_t pin_mapper(uint n_args, mp_obj_t *args) { + if (n_args > 1) { + pin_class_mapper = args[1]; + return mp_const_none; + } + return pin_class_mapper; +} +STATIC MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pin_mapper_fun_obj, 1, 2, pin_mapper); +STATIC MP_DEFINE_CONST_CLASSMETHOD_OBJ(pin_mapper_obj, (mp_obj_t)&pin_mapper_fun_obj); + +// class method +STATIC mp_obj_t pin_map_dict(uint n_args, mp_obj_t *args) { + if (n_args > 1) { + pin_class_map_dict = args[1]; + return mp_const_none; + } + return pin_class_map_dict; +} +STATIC MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pin_map_dict_fun_obj, 1, 2, pin_map_dict); +STATIC MP_DEFINE_CONST_CLASSMETHOD_OBJ(pin_map_dict_obj, (mp_obj_t)&pin_map_dict_fun_obj); + +// class method +STATIC mp_obj_t pin_debug(uint n_args, mp_obj_t *args) { + if (n_args > 1) { + pin_class_debug = mp_obj_is_true(args[1]); + return mp_const_none; + } + return MP_BOOL(pin_class_debug); +} +STATIC MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pin_debug_fun_obj, 1, 2, pin_debug); +STATIC MP_DEFINE_CONST_CLASSMETHOD_OBJ(pin_debug_obj, (mp_obj_t)&pin_debug_fun_obj); + +STATIC mp_obj_t pin_value(uint n_args, mp_obj_t *args) { + pin_obj_t *self = args[0]; + if (n_args == 1) { + // get pin + return MP_OBJ_NEW_SMALL_INT((self->gpio->IDR >> self->port) & 1); + } else { + // set pin + if (mp_obj_is_true(args[1])) { + self->gpio->BSRRL = self->pin_mask; + } else { + self->gpio->BSRRH = self->pin_mask; + } + return mp_const_none; + } +} +STATIC MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pin_value_obj, 1, 2, pin_value); + +STATIC mp_obj_t pin_low(mp_obj_t self_in) { + pin_obj_t *self = self_in; + self->gpio->BSRRH = self->pin_mask; + return mp_const_none; +} +STATIC MP_DEFINE_CONST_FUN_OBJ_1(pin_low_obj, pin_low); + +STATIC mp_obj_t pin_high(mp_obj_t self_in) { + pin_obj_t *self = self_in; + self->gpio->BSRRL = self->pin_mask; + return mp_const_none; +} +STATIC MP_DEFINE_CONST_FUN_OBJ_1(pin_high_obj, pin_high); + +STATIC mp_obj_t pin_name(mp_obj_t self_in) { pin_obj_t *self = self_in; return MP_OBJ_NEW_QSTR(qstr_from_str(self->name)); } +STATIC MP_DEFINE_CONST_FUN_OBJ_1(pin_name_obj, pin_name); -mp_obj_t pin_obj_port(mp_obj_t self_in) { +STATIC mp_obj_t pin_port(mp_obj_t self_in) { pin_obj_t *self = self_in; return MP_OBJ_NEW_SMALL_INT((mp_small_int_t)self->port); } +STATIC MP_DEFINE_CONST_FUN_OBJ_1(pin_port_obj, pin_port); -mp_obj_t pin_obj_pin(mp_obj_t self_in) { +STATIC mp_obj_t pin_pin(mp_obj_t self_in) { pin_obj_t *self = self_in; return MP_OBJ_NEW_SMALL_INT((mp_small_int_t)self->pin); } +STATIC MP_DEFINE_CONST_FUN_OBJ_1(pin_pin_obj, pin_pin); -static MP_DEFINE_CONST_FUN_OBJ_1(pin_obj_name_obj, pin_obj_name); -static MP_DEFINE_CONST_FUN_OBJ_1(pin_obj_port_obj, pin_obj_port); -static MP_DEFINE_CONST_FUN_OBJ_1(pin_obj_pin_obj, pin_obj_pin); +STATIC const mp_map_elem_t pin_locals_dict_table[] = { + // instance methods + { MP_OBJ_NEW_QSTR(MP_QSTR_value), (mp_obj_t)&pin_value_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_low), (mp_obj_t)&pin_low_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_high), (mp_obj_t)&pin_high_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_name), (mp_obj_t)&pin_name_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_port), (mp_obj_t)&pin_port_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_pin), (mp_obj_t)&pin_pin_obj }, -static const mp_method_t pin_methods[] = { - { "name", &pin_obj_name_obj }, - { "port", &pin_obj_port_obj }, - { "pin", &pin_obj_pin_obj }, - { NULL, NULL }, + // class methods + { MP_OBJ_NEW_QSTR(MP_QSTR_mapper), (mp_obj_t)&pin_mapper_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_dict), (mp_obj_t)&pin_map_dict_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_debug), (mp_obj_t)&pin_debug_obj }, + + // class attributes + { MP_OBJ_NEW_QSTR(MP_QSTR_board), (mp_obj_t)&pin_board_pins_obj }, + { MP_OBJ_NEW_QSTR(MP_QSTR_cpu), (mp_obj_t)&pin_cpu_pins_obj }, + + // class constants + { MP_OBJ_NEW_QSTR(MP_QSTR_IN), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_INPUT) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_OUT_PP), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_OUTPUT_PP) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_OUT_OD), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_OUTPUT_OD) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_AF_PP), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_AF_PP) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_AF_OD), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_AF_OD) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_ANALOG), MP_OBJ_NEW_SMALL_INT(GPIO_MODE_ANALOG) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_PULL_NONE), MP_OBJ_NEW_SMALL_INT(GPIO_NOPULL) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_PULL_UP), MP_OBJ_NEW_SMALL_INT(GPIO_PULLUP) }, + { MP_OBJ_NEW_QSTR(MP_QSTR_PULL_DOWN), MP_OBJ_NEW_SMALL_INT(GPIO_PULLDOWN) }, }; -#endif -const mp_obj_type_t pin_obj_type = { -#if 0 +STATIC MP_DEFINE_CONST_DICT(pin_locals_dict, pin_locals_dict_table); + +const mp_obj_type_t pin_type = { { &mp_type_type }, -#else - { NULL }, -#endif .name = MP_QSTR_Pin, -#if 0 - .print = pin_obj_print, - .methods = pin_methods, -#endif + .print = pin_print, + .make_new = pin_make_new, + .locals_dict = (mp_obj_t)&pin_locals_dict, }; -#if 0 -void pin_af_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { +STATIC void pin_af_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { pin_af_obj_t *self = self_in; print(env, "", self->idx, self->fn, self->unit, self->type); } -#endif -const mp_obj_type_t pin_af_obj_type = { -#if 0 +const mp_obj_type_t pin_af_type = { { &mp_type_type }, -#else - { NULL }, -#endif .name = MP_QSTR_PinAF, -#if 0 .print = pin_af_obj_print, -#endif }; - diff --git a/stmhal/pin.h b/stmhal/pin.h index 2aa50655b4..0617b13a72 100644 --- a/stmhal/pin.h +++ b/stmhal/pin.h @@ -86,40 +86,29 @@ typedef struct { const pin_af_obj_t *af; } pin_obj_t; -extern const mp_obj_type_t pin_obj_type; -extern const mp_obj_type_t pin_af_obj_type; +extern const mp_obj_type_t pin_type; +extern const mp_obj_type_t pin_af_type; typedef struct { - const char *name; + const char *name; const pin_obj_t *pin; } pin_named_pin_t; extern const pin_named_pin_t pin_board_pins[]; extern const pin_named_pin_t pin_cpu_pins[]; -typedef struct { - mp_obj_base_t base; - mp_obj_t mapper; - mp_obj_t map_dict; - bool debug; -} pin_map_obj_t; - -extern pin_map_obj_t pin_map_obj; +//extern pin_map_obj_t pin_map_obj; typedef struct { mp_obj_base_t base; - const char *name; + qstr name; const pin_named_pin_t *named_pins; } pin_named_pins_obj_t; extern const pin_named_pins_obj_t pin_board_pins_obj; extern const pin_named_pins_obj_t pin_cpu_pins_obj; +void pin_init(void); +const pin_obj_t *pin_find(mp_obj_t user_obj); const pin_obj_t *pin_find_named_pin(const pin_named_pin_t *pins, const char *name); const pin_af_obj_t *pin_find_af(const pin_obj_t *pin, uint8_t fn, uint8_t unit, uint8_t pin_type); - -void pin_map_init(void); - -// C function for mapping python pin identifier into an ordinal pin number. -const pin_obj_t *pin_map_user_obj(mp_obj_t user_obj); - diff --git a/stmhal/pin_map.c b/stmhal/pin_map.c deleted file mode 100644 index c0c6910b2e..0000000000 --- a/stmhal/pin_map.c +++ /dev/null @@ -1,226 +0,0 @@ -#include -#include -#include -#include - -#include "misc.h" -#include "mpconfig.h" -#include "qstr.h" -#include "obj.h" -#include "runtime.h" -#include "nlr.h" - -#include "pin.h" - -// Usage Model: -// -// All Board Pins are predefined as pyb.Pin.board.Name -// -// x1_pin = pyb.Pin.board.X1 -// -// g = pyb.gpio(pyb.Pin.board.X1, 0) -// -// CPU pins which correspond to the board pins are available -// as pyb.cpu.Name. For the CPU pins, the names are the port letter -// followed by the pin number. On the PYBV4, pyb.Pin.board.X1 and -// pyb.Pin.cpu.B6 are the same pin. -// -// You can also use strings: -// -// g = pyb.gpio('X1', 0) -// -// Users can add their own names: -// -// pyb.Pin("LeftMotorDir", pyb.Pin.cpu.C12) -// g = pyb.gpio("LeftMotorDir", 0) -// -// and can query mappings -// -// pin = pyb.Pin("LeftMotorDir"); -// -// Users can also add their own mapping function: -// -// def MyMapper(pin_name): -// if pin_name == "LeftMotorDir": -// return pyb.Pin.cpu.A0 -// -// pyb.Pin.mapper(MyMapper) -// -// So, if you were to call: pyb.gpio("LeftMotorDir", 0) -// then "LeftMotorDir" is passed directly to the mapper function. -// -// To summarize, the following order determines how things get mapped into -// an ordinal pin number: -// -// 1 - Directly specify a pin object -// 2 - User supplied mapping function -// 3 - User supplied mapping (object must be usable as a dictionary key) -// 4 - Supply a string which matches a board pin -// 5 - Supply a string which matches a CPU port/pin -// -// You can set pyb.Pin.debug(True) to get some debug information about -// how a particular object gets mapped to a pin. - -static void pin_map_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { - (void)self_in; - print(env, ""); -} - -static mp_obj_t pin_map_call(mp_obj_t self_in, uint n_args, uint n_kw, const mp_obj_t *args) { - pin_map_obj_t *self = self_in; - mp_check_nargs(n_args, 1, 2, n_kw, false); - - if (n_args > 1) { - if (!self->map_dict) { - self->map_dict = mp_obj_new_dict(1); - } - mp_obj_dict_store(self->map_dict, args[0], args[1]); - return mp_const_none; - } - - // Run an argument through the mapper and return the result. - return (mp_obj_t)pin_map_user_obj(args[0]); -} - -static mp_obj_t pin_map_obj_mapper(uint n_args, mp_obj_t *args) { - pin_map_obj_t *self = args[0]; - if (n_args > 1) { - self->mapper = args[1]; - return mp_const_none; - } - return self->mapper; -} -static MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pin_map_obj_mapper_obj, 1, 2, pin_map_obj_mapper); - -static mp_obj_t pin_map_obj_debug(uint n_args, mp_obj_t *args) { - pin_map_obj_t *self = args[0]; - if (n_args > 1) { - self->debug = mp_obj_is_true(args[1]); - return mp_const_none; - } - return MP_BOOL(self->debug); -} -static MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pin_map_obj_debug_obj, 1, 2, pin_map_obj_debug); - -static void pin_map_load_attr(mp_obj_t self_in, qstr attr_qstr, mp_obj_t *dest) { - (void)self_in; - const char *attr = qstr_str(attr_qstr); - - if (strcmp(attr, "mapper") == 0) { - dest[0] = (mp_obj_t)&pin_map_obj_mapper_obj; - dest[1] = self_in; - } - if (strcmp(attr, "debug") == 0) { - dest[0] = (mp_obj_t)&pin_map_obj_debug_obj; - dest[1] = self_in; - } - if (strcmp(attr, pin_board_pins_obj.name) == 0) { - dest[0] = (mp_obj_t)&pin_board_pins_obj; - dest[1] = MP_OBJ_NULL; - } - if (strcmp(attr, pin_cpu_pins_obj.name) == 0) { - dest[0] = (mp_obj_t)&pin_cpu_pins_obj; - dest[1] = MP_OBJ_NULL; - } -} - -static const mp_obj_type_t pin_map_obj_type = { - { &mp_type_type }, - .name = MP_QSTR_PinMap, - .print = pin_map_obj_print, - .call = pin_map_call, - .load_attr = pin_map_load_attr, -}; - -static const pin_map_obj_t pin_map_obj_init = { - { &pin_map_obj_type }, - .mapper = MP_OBJ_NULL, - .map_dict = MP_OBJ_NULL, - .debug = false, -}; - -pin_map_obj_t pin_map_obj; - -void pin_map_init(void) { - pin_map_obj = pin_map_obj_init; -} - -// C API used to convert a user-supplied pin name into an ordinal pin number. -const pin_obj_t *pin_map_user_obj(mp_obj_t user_obj) { - const pin_obj_t *pin_obj; - - // If a pin was provided, then use it - if (MP_OBJ_IS_TYPE(user_obj, &pin_obj_type)) { - pin_obj = user_obj; - if (pin_map_obj.debug) { - printf("Pin map passed pin "); - mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); - printf("\n"); - } - return pin_obj; - } - - if (pin_map_obj.mapper) { - pin_obj = mp_call_function_1(pin_map_obj.mapper, user_obj); - if (pin_obj != mp_const_none) { - if (!MP_OBJ_IS_TYPE(pin_obj, &pin_obj_type)) { - nlr_raise(mp_obj_new_exception_msg(&mp_type_ValueError, "Pin.mapper didn't return a Pin object")); - } - if (pin_map_obj.debug) { - printf("Pin.mapper maps "); - mp_obj_print(user_obj, PRINT_REPR); - printf(" to "); - mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); - printf("\n"); - } - return pin_obj; - } - // The pin mapping function returned mp_const_none, fall through to - // other lookup methods. - } - - if (pin_map_obj.map_dict) { - mp_map_t *pin_map_map = mp_obj_dict_get_map(pin_map_obj.map_dict); - mp_map_elem_t *elem = mp_map_lookup(pin_map_map, user_obj, MP_MAP_LOOKUP); - if (elem != NULL && elem->value != NULL) { - pin_obj = elem->value; - if (pin_map_obj.debug) { - printf("Pin.map_dict maps "); - mp_obj_print(user_obj, PRINT_REPR); - printf(" to "); - mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); - printf("\n"); - } - return pin_obj; - } - } - - // See if the pin name matches a board pin - const char *pin_name = mp_obj_str_get_str(user_obj); - pin_obj = pin_find_named_pin(pin_board_pins, pin_name); - if (pin_obj) { - if (pin_map_obj.debug) { - printf("Pin.board maps "); - mp_obj_print(user_obj, PRINT_REPR); - printf(" to "); - mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); - printf("\n"); - } - return pin_obj; - } - - // See if the pin name matches a cpu pin - pin_obj = pin_find_named_pin(pin_cpu_pins, pin_name); - if (pin_obj) { - if (pin_map_obj.debug) { - printf("Pin.cpu maps "); - mp_obj_print(user_obj, PRINT_REPR); - printf(" to "); - mp_obj_print((mp_obj_t)pin_obj, PRINT_STR); - printf("\n"); - } - return pin_obj; - } - - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "pin '%s' not a valid pin identifier", pin_name)); -} diff --git a/stmhal/pin_named_pins.c b/stmhal/pin_named_pins.c index 48906ad800..6e81bb7424 100644 --- a/stmhal/pin_named_pins.c +++ b/stmhal/pin_named_pins.c @@ -1,22 +1,22 @@ #include #include #include -#include + +#include "stm32f4xx_hal.h" #include "misc.h" #include "mpconfig.h" #include "qstr.h" #include "obj.h" #include "runtime.h" - #include "pin.h" -static void pin_named_pins_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { +STATIC void pin_named_pins_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { pin_named_pins_obj_t *self = self_in; - print(env, "", self->name); + print(env, "", qstr_str(self->name)); } -static void pin_named_pins_obj_load_attr(mp_obj_t self_in, qstr attr_qstr, mp_obj_t *dest) { +STATIC void pin_named_pins_obj_load_attr(mp_obj_t self_in, qstr attr_qstr, mp_obj_t *dest) { pin_named_pins_obj_t *self = self_in; const char *attr = qstr_str(attr_qstr); const pin_obj_t *pin = pin_find_named_pin(self->named_pins, attr); @@ -35,13 +35,13 @@ static const mp_obj_type_t pin_named_pins_obj_type = { const pin_named_pins_obj_t pin_board_pins_obj = { { &pin_named_pins_obj_type }, - .name = "board", + .name = MP_QSTR_board, .named_pins = pin_board_pins, }; const pin_named_pins_obj_t pin_cpu_pins_obj = { { &pin_named_pins_obj_type }, - .name = "cpu", + .name = MP_QSTR_cpu, .named_pins = pin_cpu_pins, }; diff --git a/stmhal/qstrdefsport.h b/stmhal/qstrdefsport.h index d64b0c2ddb..f2ba3669ec 100644 --- a/stmhal/qstrdefsport.h +++ b/stmhal/qstrdefsport.h @@ -7,6 +7,8 @@ Q(sd_test) Q(present) Q(power) Q(wfi) +Q(disable_irq) +Q(enable_irq) Q(stop) Q(standby) Q(source_dir) @@ -38,19 +40,34 @@ Q(gpio_out) Q(FileIO) // Entries for sys.path Q(0:/) -Q(0:/src) Q(0:/lib) -Q(Pin) -Q(PinMap) -Q(PinAF) -Q(PinNamed) Q(rtc_info) Q(millis) + +// for Pin class +Q(Pin) +Q(PinAF) +Q(PinNamed) +Q(value) +Q(low) +Q(high) +Q(name) +Q(port) +Q(pin) +Q(mapper) +Q(dict) +Q(debug) +Q(board) +Q(cpu) +Q(IN) +Q(OUT_PP) +Q(OUT_OD) +Q(AF_PP) +Q(AF_OD) +Q(ANALOG) Q(PULL_NONE) Q(PULL_UP) Q(PULL_DOWN) -Q(PUSH_PULL) -Q(OPEN_DRAIN) // for Led object Q(Led) @@ -59,26 +76,26 @@ Q(off) Q(toggle) Q(intensity) -// for Usart object -Q(Usart) +// for USART object +Q(USART) Q(status) Q(recv_chr) Q(send_chr) Q(send) -// for exti object -Q(Exti) +// for ExtInt class +Q(ExtInt) Q(line) Q(enable) Q(disable) Q(swint) Q(regs) -Q(MODE_IRQ_RISING) -Q(MODE_IRQ_FALLING) -Q(MODE_IRQ_RISING_FALLING) -Q(MODE_EVT_RISING) -Q(MODE_EVT_FALLING) -Q(MODE_EVT_RISING_FALLING) +Q(IRQ_RISING) +Q(IRQ_FALLING) +Q(IRQ_RISING_FALLING) +Q(EVT_RISING) +Q(EVT_FALLING) +Q(EVT_RISING_FALLING) // for I2C object Q(I2C) @@ -97,7 +114,7 @@ Q(filtered_xyz) // for ADC object Q(ADC) -Q(ADC_all) +Q(ADCAll) Q(read_timed) Q(read_channel) Q(read_core_temp) @@ -137,12 +154,10 @@ Q(input) // for stm module Q(stm) -Q(read8) -Q(read16) -Q(read32) -Q(write8) -Q(write16) -Q(write32) +Q(mem) +Q(mem8) +Q(mem16) +Q(mem32) Q(GPIOA) Q(GPIOB) Q(GPIOC) diff --git a/stmhal/stm32f4xx_it.c b/stmhal/stm32f4xx_it.c index df69f52b8e..9b64f6165c 100644 --- a/stmhal/stm32f4xx_it.c +++ b/stmhal/stm32f4xx_it.c @@ -47,7 +47,7 @@ #include "mpconfig.h" #include "qstr.h" #include "obj.h" -#include "exti.h" +#include "extint.h" #include "timer.h" #include "storage.h" diff --git a/stmhal/usart.c b/stmhal/usart.c index cc0a6112e6..89770942be 100644 --- a/stmhal/usart.c +++ b/stmhal/usart.c @@ -165,13 +165,13 @@ void usart_tx_strn_cooked(pyb_usart_obj_t *usart_obj, const char *str, uint len) STATIC void usart_obj_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in, mp_print_kind_t kind) { pyb_usart_obj_t *self = self_in; - print(env, "", self->usart_id); + print(env, "", self->usart_id); } STATIC mp_obj_t usart_obj_make_new(mp_obj_t type_in, uint n_args, uint n_kw, const mp_obj_t *args) { // check arguments if (!(n_args == 2 && n_kw == 0)) { - nlr_raise(mp_obj_new_exception_msg(&mp_type_ValueError, "Usart accepts 2 arguments")); + nlr_raise(mp_obj_new_exception_msg(&mp_type_ValueError, "USART accepts 2 arguments")); } // create object @@ -194,7 +194,7 @@ STATIC mp_obj_t usart_obj_make_new(mp_obj_t type_in, uint n_args, uint n_kw, con o->usart_id = PYB_USART_YB; #endif } else { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Usart port %s does not exist", port)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "USART port %s does not exist", port)); } } else { o->usart_id = mp_obj_get_int(args[0]); @@ -202,7 +202,7 @@ STATIC mp_obj_t usart_obj_make_new(mp_obj_t type_in, uint n_args, uint n_kw, con // init USART (if it fails, it's because the port doesn't exist) if (!usart_init(o, mp_obj_get_int(args[1]))) { - nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "Usart port %d does not exist", o->usart_id)); + nlr_raise(mp_obj_new_exception_msg_varg(&mp_type_ValueError, "USART port %d does not exist", o->usart_id)); } o->is_enabled = true; @@ -267,7 +267,7 @@ STATIC MP_DEFINE_CONST_DICT(usart_locals_dict, usart_locals_dict_table); const mp_obj_type_t pyb_usart_type = { { &mp_type_type }, - .name = MP_QSTR_Usart, + .name = MP_QSTR_USART, .print = usart_obj_print, .make_new = usart_obj_make_new, .locals_dict = (mp_obj_t)&usart_locals_dict, diff --git a/stmhal/usrsw.c b/stmhal/usrsw.c index 0ab407cd96..6e73cf69b4 100644 --- a/stmhal/usrsw.c +++ b/stmhal/usrsw.c @@ -8,7 +8,7 @@ #include "runtime.h" #include "usrsw.h" -#include "exti.h" +#include "extint.h" #include "gpio.h" #include "pin.h" #include "genhdr/pins.h" @@ -70,12 +70,11 @@ static mp_obj_t pyb_switch(uint n_args, mp_obj_t *args) { // Init the EXTI each time this function is called, since the EXTI // may have been disabled by an exception in the interrupt, or the // user disabling the line explicitly. - exti_register((mp_obj_t)&MICROPY_HW_USRSW_PIN, - MP_OBJ_NEW_SMALL_INT(MICROPY_HW_USRSW_EXTI_MODE), - MP_OBJ_NEW_SMALL_INT(MICROPY_HW_USRSW_PULL), - switch_user_callback_obj == mp_const_none ? mp_const_none : (mp_obj_t)&switch_callback_obj, - true, - NULL); + extint_register((mp_obj_t)&MICROPY_HW_USRSW_PIN, + MP_OBJ_NEW_SMALL_INT(MICROPY_HW_USRSW_EXTI_MODE), + MP_OBJ_NEW_SMALL_INT(MICROPY_HW_USRSW_PULL), + switch_user_callback_obj == mp_const_none ? mp_const_none : (mp_obj_t)&switch_callback_obj, + true, NULL); return mp_const_none; } }