Merge pull request #5422 from Neradoc/nera-secondary-I2C
Allow multiple board buses
This commit is contained in:
commit
9a353a4f56
4
main.c
4
main.c
|
@ -290,10 +290,10 @@ STATIC void cleanup_after_vm(supervisor_allocation *heap, mp_obj_t exception) {
|
|||
keypad_reset();
|
||||
#endif
|
||||
|
||||
// reset_board_busses() first because it may release pins from the never_reset state, so that
|
||||
// reset_board_buses() first because it may release pins from the never_reset state, so that
|
||||
// reset_port() can reset them.
|
||||
#if CIRCUITPY_BOARD
|
||||
reset_board_busses();
|
||||
reset_board_buses();
|
||||
#endif
|
||||
reset_port();
|
||||
reset_board();
|
||||
|
|
|
@ -71,7 +71,7 @@ uint8_t display_init_sequence[] = {
|
|||
void board_init(void) {
|
||||
displayio_fourwire_obj_t *bus = &displays[0].fourwire_bus;
|
||||
bus->base.type = &displayio_fourwire_type;
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi();
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi(0);
|
||||
common_hal_busio_spi_never_reset(spi);
|
||||
common_hal_displayio_fourwire_construct(bus,
|
||||
spi,
|
||||
|
|
|
@ -72,7 +72,7 @@ uint8_t display_init_sequence[] = {
|
|||
void board_init(void) {
|
||||
displayio_fourwire_obj_t *bus = &displays[0].fourwire_bus;
|
||||
bus->base.type = &displayio_fourwire_type;
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi();
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi(0);
|
||||
common_hal_displayio_fourwire_construct(bus,
|
||||
spi,
|
||||
&pin_PA09, // Command or data
|
||||
|
|
|
@ -51,7 +51,7 @@ uint8_t display_init_sequence[] = {
|
|||
};
|
||||
|
||||
void board_init(void) {
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi();
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi(0);
|
||||
displayio_fourwire_obj_t *bus = &displays[0].fourwire_bus;
|
||||
bus->base.type = &displayio_fourwire_type;
|
||||
common_hal_displayio_fourwire_construct(bus,
|
||||
|
|
|
@ -78,7 +78,7 @@ void board_init(void) {
|
|||
gpio_set_direction(21, GPIO_MODE_DEF_OUTPUT);
|
||||
gpio_set_level(21, true);
|
||||
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi();
|
||||
busio_spi_obj_t *spi = common_hal_board_create_spi(0);
|
||||
displayio_fourwire_obj_t *bus = &displays[0].fourwire_bus;
|
||||
bus->base.type = &displayio_fourwire_type;
|
||||
|
||||
|
|
|
@ -4,12 +4,12 @@
|
|||
#define MICROPY_HW_NEOPIXEL (&pin_GPIO12)
|
||||
#define CIRCUITPY_STATUS_LED_POWER (&pin_GPIO11)
|
||||
|
||||
#define DEFAULT_I2C_BUS_SCL (&pin_GPIO25)
|
||||
#define DEFAULT_I2C_BUS_SDA (&pin_GPIO24)
|
||||
#define CIRCUITPY_BOARD_I2C (2)
|
||||
#define CIRCUITPY_BOARD_I2C_PIN {{.scl = &pin_GPIO25, .sda = &pin_GPIO24}, \
|
||||
{.scl = &pin_GPIO23, .sda = &pin_GPIO22}}
|
||||
|
||||
#define DEFAULT_SPI_BUS_SCK (&pin_GPIO6)
|
||||
#define DEFAULT_SPI_BUS_MOSI (&pin_GPIO3)
|
||||
#define DEFAULT_SPI_BUS_MISO (&pin_GPIO4)
|
||||
#define CIRCUITPY_BOARD_SPI (1)
|
||||
#define CIRCUITPY_BOARD_SPI_PIN {{.clock = &pin_GPIO6, .mosi = &pin_GPIO3, .miso = &pin_GPIO4}}
|
||||
|
||||
#define DEFAULT_UART_BUS_RX (&pin_GPIO5)
|
||||
#define DEFAULT_UART_BUS_TX (&pin_GPIO20)
|
||||
#define CIRCUITPY_BOARD_UART (1)
|
||||
#define CIRCUITPY_BOARD_UART_PIN {{.tx = &pin_GPIO20, .rx = &pin_GPIO5}}
|
||||
|
|
|
@ -1,5 +1,7 @@
|
|||
#include "shared-bindings/board/__init__.h"
|
||||
|
||||
CIRCUITPY_BOARD_BUS_SINGLETON(stemma_i2c, i2c, 1)
|
||||
|
||||
STATIC const mp_rom_map_elem_t board_module_globals_table[] = {
|
||||
CIRCUITPYTHON_BOARD_DICT_STANDARD_ITEMS
|
||||
|
||||
|
@ -47,5 +49,7 @@ STATIC const mp_rom_map_elem_t board_module_globals_table[] = {
|
|||
{ MP_ROM_QSTR(MP_QSTR_I2C), MP_ROM_PTR(&board_i2c_obj) },
|
||||
{ MP_ROM_QSTR(MP_QSTR_SPI), MP_ROM_PTR(&board_spi_obj) },
|
||||
{ MP_ROM_QSTR(MP_QSTR_UART), MP_ROM_PTR(&board_uart_obj) },
|
||||
|
||||
{ MP_ROM_QSTR(MP_QSTR_STEMMA_I2C), MP_ROM_PTR(&board_stemma_i2c_obj) },
|
||||
};
|
||||
MP_DEFINE_CONST_DICT(board_module_globals, board_module_globals_table);
|
||||
|
|
|
@ -259,23 +259,42 @@ typedef long mp_off_t;
|
|||
#error No *_FLASH_FILESYSTEM set!
|
||||
#endif
|
||||
|
||||
// Default board buses.
|
||||
|
||||
#ifndef CIRCUITPY_BOARD_I2C
|
||||
#if defined(DEFAULT_I2C_BUS_SCL) && defined(DEFAULT_I2C_BUS_SDA)
|
||||
#define CIRCUITPY_BOARD_I2C (1)
|
||||
#define CIRCUITPY_BOARD_I2C_PIN {{.scl = DEFAULT_I2C_BUS_SCL, .sda = DEFAULT_I2C_BUS_SDA}}
|
||||
#else
|
||||
#define CIRCUITPY_BOARD_I2C (0)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef CIRCUITPY_BOARD_SPI
|
||||
#if defined(DEFAULT_SPI_BUS_SCK) && defined(DEFAULT_SPI_BUS_MOSI) && defined(DEFAULT_SPI_BUS_MISO)
|
||||
#define CIRCUITPY_BOARD_SPI (1)
|
||||
#define CIRCUITPY_BOARD_SPI_PIN {{.clock = DEFAULT_SPI_BUS_SCK, .mosi = DEFAULT_SPI_BUS_MOSI, .miso = DEFAULT_SPI_BUS_MISO}}
|
||||
#else
|
||||
#define CIRCUITPY_BOARD_SPI (0)
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#ifndef CIRCUITPY_BOARD_UART
|
||||
#if defined(DEFAULT_UART_BUS_TX) && defined(DEFAULT_UART_BUS_RX)
|
||||
#define CIRCUITPY_BOARD_UART (1)
|
||||
#define CIRCUITPY_BOARD_UART_PIN {{.tx = DEFAULT_UART_BUS_TX, .rx = DEFAULT_UART_BUS_RX}}
|
||||
#define BOARD_UART_ROOT_POINTER mp_obj_t board_uart_bus;
|
||||
#else
|
||||
#define CIRCUITPY_BOARD_UART (0)
|
||||
#define BOARD_UART_ROOT_POINTER
|
||||
#endif
|
||||
#else
|
||||
#define BOARD_UART_ROOT_POINTER mp_obj_t board_uart_bus;
|
||||
#endif
|
||||
|
||||
// These CIRCUITPY_xxx values should all be defined in the *.mk files as being on or off.
|
||||
// So if any are not defined in *.mk, they'll throw an error here.
|
||||
|
||||
#if CIRCUITPY_BOARD
|
||||
#define BOARD_I2C (defined(DEFAULT_I2C_BUS_SDA) && defined(DEFAULT_I2C_BUS_SCL))
|
||||
#define BOARD_SPI (defined(DEFAULT_SPI_BUS_SCK) && defined(DEFAULT_SPI_BUS_MISO) && defined(DEFAULT_SPI_BUS_MOSI))
|
||||
#define BOARD_UART (defined(DEFAULT_UART_BUS_RX) && defined(DEFAULT_UART_BUS_TX))
|
||||
// I2C and SPI are always allocated off the heap.
|
||||
#if BOARD_UART
|
||||
#define BOARD_UART_ROOT_POINTER mp_obj_t shared_uart_bus;
|
||||
#else
|
||||
#define BOARD_UART_ROOT_POINTER
|
||||
#endif
|
||||
#else
|
||||
#define BOARD_UART_ROOT_POINTER
|
||||
#endif
|
||||
|
||||
#if CIRCUITPY_DISPLAYIO
|
||||
#ifndef CIRCUITPY_DISPLAY_LIMIT
|
||||
#define CIRCUITPY_DISPLAY_LIMIT (1)
|
||||
|
|
|
@ -28,12 +28,15 @@
|
|||
#include "py/runtime.h"
|
||||
|
||||
#include "shared-bindings/board/__init__.h"
|
||||
#if BOARD_I2C
|
||||
#if CIRCUITPY_BOARD_I2C
|
||||
#include "shared-bindings/busio/I2C.h"
|
||||
#endif
|
||||
#if BOARD_SPI
|
||||
#if CIRCUITPY_BOARD_SPI
|
||||
#include "shared-bindings/busio/SPI.h"
|
||||
#endif
|
||||
#if CIRCUITPY_BOARD_UART
|
||||
#include "shared-bindings/busio/UART.h"
|
||||
#endif
|
||||
|
||||
//| """Board specific pin names
|
||||
//|
|
||||
|
@ -47,84 +50,57 @@
|
|||
//| """Board ID string. The unique identifier for the board model in
|
||||
//| circuitpython, as well as on circuitpython.org.
|
||||
//| Example: "hallowing_m0_express"."""
|
||||
//|
|
||||
|
||||
//| def I2C() -> busio.I2C:
|
||||
//| """Returns the `busio.I2C` object for the board designated SDA and SCL pins. It is a singleton."""
|
||||
//| """Returns the `busio.I2C` object for the board's designated I2C bus(es).
|
||||
//| The object created is a singleton, and uses the default parameter values for `busio.I2C`."""
|
||||
//| ...
|
||||
//|
|
||||
|
||||
#if BOARD_I2C
|
||||
mp_obj_t board_i2c(void) {
|
||||
mp_obj_t singleton = common_hal_board_get_i2c();
|
||||
if (singleton != NULL && !common_hal_busio_i2c_deinited(singleton)) {
|
||||
return singleton;
|
||||
}
|
||||
assert_pin_free(DEFAULT_I2C_BUS_SDA);
|
||||
assert_pin_free(DEFAULT_I2C_BUS_SCL);
|
||||
return common_hal_board_create_i2c();
|
||||
#if CIRCUITPY_BOARD_I2C
|
||||
STATIC mp_obj_t board_i2c_0(void) {
|
||||
return common_hal_board_create_i2c(0);
|
||||
}
|
||||
#else
|
||||
mp_obj_t board_i2c(void) {
|
||||
STATIC mp_obj_t board_i2c_0(void) {
|
||||
mp_raise_NotImplementedError_varg(translate("No default %q bus"), MP_QSTR_I2C);
|
||||
return MP_ROM_NONE;
|
||||
}
|
||||
#endif
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_i2c_obj, board_i2c);
|
||||
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_i2c_obj, board_i2c_0);
|
||||
|
||||
//| def SPI() -> busio.SPI:
|
||||
//| """Returns the `busio.SPI` object for the board designated SCK, MOSI and MISO pins. It is a
|
||||
//| singleton."""
|
||||
//| """Returns the `busio.SPI` object for the board's designated SPI bus(es).
|
||||
//| The object created is a singleton, and uses the default parameter values for `busio.SPI`."""
|
||||
//| ...
|
||||
//|
|
||||
#if BOARD_SPI
|
||||
mp_obj_t board_spi(void) {
|
||||
mp_obj_t singleton = common_hal_board_get_spi();
|
||||
if (singleton != NULL && !common_hal_busio_spi_deinited(singleton)) {
|
||||
return singleton;
|
||||
}
|
||||
assert_pin_free(DEFAULT_SPI_BUS_SCK);
|
||||
assert_pin_free(DEFAULT_SPI_BUS_MOSI);
|
||||
assert_pin_free(DEFAULT_SPI_BUS_MISO);
|
||||
return common_hal_board_create_spi();
|
||||
#if CIRCUITPY_BOARD_SPI
|
||||
STATIC mp_obj_t board_spi_0(void) {
|
||||
return common_hal_board_create_spi(0);
|
||||
}
|
||||
#else
|
||||
mp_obj_t board_spi(void) {
|
||||
STATIC mp_obj_t board_spi_0(void) {
|
||||
mp_raise_NotImplementedError_varg(translate("No default %q bus"), MP_QSTR_SPI);
|
||||
return MP_ROM_NONE;
|
||||
}
|
||||
#endif
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_spi_obj, board_spi);
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_spi_obj, board_spi_0);
|
||||
|
||||
//| def UART() -> busio.UART:
|
||||
//| """Returns the `busio.UART` object for the board designated TX and RX pins. It is a singleton.
|
||||
//|
|
||||
//| The object created uses the default parameter values for `busio.UART`. If you need to set
|
||||
//| parameters that are not changeable after creation, such as ``receiver_buffer_size``,
|
||||
//| do not use `board.UART()`; instead create a `busio.UART` object explicitly with the
|
||||
//| desired parameters."""
|
||||
//| """Returns the `busio.UART` object for the board's designated UART bus(es).
|
||||
//| The object created is a singleton, and uses the default parameter values for `busio.UART`."""
|
||||
//| ...
|
||||
//|
|
||||
#if BOARD_UART
|
||||
mp_obj_t board_uart(void) {
|
||||
mp_obj_t singleton = common_hal_board_get_uart();
|
||||
if (singleton != NULL) {
|
||||
return singleton;
|
||||
}
|
||||
|
||||
assert_pin_free(DEFAULT_UART_BUS_RX);
|
||||
assert_pin_free(DEFAULT_UART_BUS_TX);
|
||||
|
||||
return common_hal_board_create_uart();
|
||||
#if CIRCUITPY_BOARD_UART
|
||||
STATIC mp_obj_t board_uart_0(void) {
|
||||
return common_hal_board_create_uart(0);
|
||||
}
|
||||
#else
|
||||
mp_obj_t board_uart(void) {
|
||||
STATIC mp_obj_t board_uart_0(void) {
|
||||
mp_raise_NotImplementedError_varg(translate("No default %q bus"), MP_QSTR_UART);
|
||||
return MP_ROM_NONE;
|
||||
}
|
||||
#endif
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_uart_obj, board_uart);
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_uart_obj, board_uart_0);
|
||||
|
||||
const mp_obj_module_t board_module = {
|
||||
.base = { &mp_type_module },
|
||||
|
|
|
@ -35,21 +35,29 @@
|
|||
extern const mp_obj_dict_t board_module_globals;
|
||||
STATIC const MP_DEFINE_STR_OBJ(board_module_id_obj, CIRCUITPY_BOARD_ID);
|
||||
|
||||
mp_obj_t common_hal_board_get_i2c(void);
|
||||
mp_obj_t common_hal_board_create_i2c(void);
|
||||
bool common_hal_board_is_i2c(mp_obj_t obj);
|
||||
mp_obj_t common_hal_board_get_i2c(const mp_int_t instance);
|
||||
mp_obj_t common_hal_board_create_i2c(const mp_int_t instance);
|
||||
mp_obj_t board_i2c(size_t n_args, const mp_obj_t *args);
|
||||
MP_DECLARE_CONST_FUN_OBJ_0(board_i2c_obj);
|
||||
|
||||
mp_obj_t common_hal_board_get_spi(void);
|
||||
mp_obj_t common_hal_board_create_spi(void);
|
||||
bool common_hal_board_is_spi(mp_obj_t obj);
|
||||
mp_obj_t common_hal_board_get_spi(const mp_int_t instance);
|
||||
mp_obj_t common_hal_board_create_spi(const mp_int_t instance);
|
||||
mp_obj_t board_spi(size_t n_args, const mp_obj_t *args);
|
||||
MP_DECLARE_CONST_FUN_OBJ_0(board_spi_obj);
|
||||
|
||||
mp_obj_t common_hal_board_get_uart(void);
|
||||
mp_obj_t common_hal_board_create_uart(void);
|
||||
bool common_hal_board_is_uart(mp_obj_t obj);
|
||||
mp_obj_t common_hal_board_get_uart(const mp_int_t instance);
|
||||
mp_obj_t common_hal_board_create_uart(const mp_int_t instance);
|
||||
mp_obj_t board_uart(size_t n_args, const mp_obj_t *args);
|
||||
MP_DECLARE_CONST_FUN_OBJ_0(board_uart_obj);
|
||||
|
||||
mp_obj_t board_i2c(void);
|
||||
mp_obj_t board_spi(void);
|
||||
mp_obj_t board_uart(void);
|
||||
#define CIRCUITPY_BOARD_BUS_SINGLETON(name, bus, instance) \
|
||||
STATIC mp_obj_t board_##name(void) { \
|
||||
return common_hal_board_create_##bus(instance); \
|
||||
} \
|
||||
MP_DEFINE_CONST_FUN_OBJ_0(board_##name##_obj, board_##name);
|
||||
|
||||
#define CIRCUITPYTHON_BOARD_DICT_STANDARD_ITEMS \
|
||||
{ MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR_board) }, \
|
||||
|
|
|
@ -46,141 +46,189 @@
|
|||
#include "shared-module/sharpdisplay/SharpMemoryFramebuffer.h"
|
||||
#endif
|
||||
|
||||
#if BOARD_I2C
|
||||
#if CIRCUITPY_BOARD_I2C
|
||||
// Statically allocate the I2C object so it can live past the end of the heap and into the next VM.
|
||||
// That way it can be used by built-in I2CDisplay displays and be accessible through board.I2C().
|
||||
STATIC busio_i2c_obj_t i2c_obj;
|
||||
STATIC mp_obj_t i2c_singleton = NULL;
|
||||
|
||||
mp_obj_t common_hal_board_get_i2c(void) {
|
||||
return i2c_singleton;
|
||||
typedef struct {
|
||||
const mcu_pin_obj_t *scl;
|
||||
const mcu_pin_obj_t *sda;
|
||||
} board_i2c_pin_t;
|
||||
|
||||
static const board_i2c_pin_t i2c_pin[CIRCUITPY_BOARD_I2C] = CIRCUITPY_BOARD_I2C_PIN;
|
||||
static busio_i2c_obj_t i2c_obj[CIRCUITPY_BOARD_I2C];
|
||||
|
||||
bool common_hal_board_is_i2c(mp_obj_t obj) {
|
||||
for (uint8_t instance = 0; instance < CIRCUITPY_BOARD_I2C; instance++) {
|
||||
if (obj == &i2c_obj[instance]) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
mp_obj_t common_hal_board_create_i2c(void) {
|
||||
// All callers have either already verified this or come so early that it can't be otherwise.
|
||||
assert(i2c_singleton == NULL || common_hal_busio_i2c_deinited(i2c_singleton));
|
||||
busio_i2c_obj_t *self = &i2c_obj;
|
||||
mp_obj_t common_hal_board_get_i2c(const mp_int_t instance) {
|
||||
return &i2c_obj[instance];
|
||||
}
|
||||
|
||||
mp_obj_t common_hal_board_create_i2c(const mp_int_t instance) {
|
||||
const mp_obj_t singleton = common_hal_board_get_i2c(instance);
|
||||
if (singleton != NULL && !common_hal_busio_i2c_deinited(singleton)) {
|
||||
return singleton;
|
||||
}
|
||||
|
||||
busio_i2c_obj_t *self = &i2c_obj[instance];
|
||||
self->base.type = &busio_i2c_type;
|
||||
|
||||
common_hal_busio_i2c_construct(self, DEFAULT_I2C_BUS_SCL, DEFAULT_I2C_BUS_SDA, 100000, 255);
|
||||
i2c_singleton = (mp_obj_t)self;
|
||||
return i2c_singleton;
|
||||
assert_pin_free(i2c_pin[instance].scl);
|
||||
assert_pin_free(i2c_pin[instance].sda);
|
||||
|
||||
common_hal_busio_i2c_construct(self, i2c_pin[instance].scl, i2c_pin[instance].sda, 100000, 255);
|
||||
|
||||
return &i2c_obj[instance];
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#if BOARD_SPI
|
||||
#if CIRCUITPY_BOARD_SPI
|
||||
// Statically allocate the SPI object so it can live past the end of the heap and into the next VM.
|
||||
// That way it can be used by built-in FourWire displays and be accessible through board.SPI().
|
||||
STATIC busio_spi_obj_t spi_obj;
|
||||
STATIC mp_obj_t spi_singleton = NULL;
|
||||
|
||||
mp_obj_t common_hal_board_get_spi(void) {
|
||||
return spi_singleton;
|
||||
typedef struct {
|
||||
const mcu_pin_obj_t *clock;
|
||||
const mcu_pin_obj_t *mosi;
|
||||
const mcu_pin_obj_t *miso;
|
||||
} board_spi_pin_t;
|
||||
|
||||
static const board_spi_pin_t spi_pin[CIRCUITPY_BOARD_SPI] = CIRCUITPY_BOARD_SPI_PIN;
|
||||
static busio_spi_obj_t spi_obj[CIRCUITPY_BOARD_SPI];
|
||||
|
||||
bool common_hal_board_is_spi(mp_obj_t obj) {
|
||||
for (uint8_t instance = 0; instance < CIRCUITPY_BOARD_SPI; instance++) {
|
||||
if (obj == &spi_obj[instance]) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
mp_obj_t common_hal_board_create_spi(void) {
|
||||
// All callers have either already verified this or come so early that it can't be otherwise.
|
||||
assert(spi_singleton == NULL || common_hal_busio_spi_deinited(spi_singleton));
|
||||
busio_spi_obj_t *self = &spi_obj;
|
||||
mp_obj_t common_hal_board_get_spi(const mp_int_t instance) {
|
||||
return &spi_obj[instance];
|
||||
}
|
||||
|
||||
mp_obj_t common_hal_board_create_spi(const mp_int_t instance) {
|
||||
const mp_obj_t singleton = common_hal_board_get_spi(instance);
|
||||
if (singleton != NULL && !common_hal_busio_spi_deinited(singleton)) {
|
||||
return singleton;
|
||||
}
|
||||
|
||||
busio_spi_obj_t *self = &spi_obj[instance];
|
||||
self->base.type = &busio_spi_type;
|
||||
|
||||
const mcu_pin_obj_t *clock = MP_OBJ_TO_PTR(DEFAULT_SPI_BUS_SCK);
|
||||
const mcu_pin_obj_t *mosi = MP_OBJ_TO_PTR(DEFAULT_SPI_BUS_MOSI);
|
||||
const mcu_pin_obj_t *miso = MP_OBJ_TO_PTR(DEFAULT_SPI_BUS_MISO);
|
||||
common_hal_busio_spi_construct(self, clock, mosi, miso);
|
||||
spi_singleton = (mp_obj_t)self;
|
||||
return spi_singleton;
|
||||
assert_pin_free(spi_pin[instance].clock);
|
||||
assert_pin_free(spi_pin[instance].mosi);
|
||||
assert_pin_free(spi_pin[instance].miso);
|
||||
|
||||
common_hal_busio_spi_construct(self, spi_pin[instance].clock, spi_pin[instance].mosi, spi_pin[instance].miso);
|
||||
|
||||
return &spi_obj[instance];
|
||||
}
|
||||
#endif
|
||||
|
||||
#if BOARD_UART
|
||||
mp_obj_t common_hal_board_get_uart(void) {
|
||||
return MP_STATE_VM(shared_uart_bus);
|
||||
#if CIRCUITPY_BOARD_UART
|
||||
|
||||
typedef struct {
|
||||
const mcu_pin_obj_t *tx;
|
||||
const mcu_pin_obj_t *rx;
|
||||
} board_uart_pin_t;
|
||||
|
||||
static const board_uart_pin_t uart_pin[CIRCUITPY_BOARD_UART] = CIRCUITPY_BOARD_UART_PIN;
|
||||
static busio_uart_obj_t uart_obj[CIRCUITPY_BOARD_UART];
|
||||
|
||||
bool common_hal_board_is_uart(mp_obj_t obj) {
|
||||
for (uint8_t instance = 0; instance < CIRCUITPY_BOARD_UART; instance++) {
|
||||
if (obj == &uart_obj[instance]) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
mp_obj_t common_hal_board_create_uart(void) {
|
||||
busio_uart_obj_t *self = m_new_ll_obj(busio_uart_obj_t);
|
||||
mp_obj_t common_hal_board_get_uart(const mp_int_t instance) {
|
||||
return &uart_obj[instance];
|
||||
}
|
||||
|
||||
mp_obj_t common_hal_board_create_uart(const mp_int_t instance) {
|
||||
const mp_obj_t singleton = common_hal_board_get_uart(instance);
|
||||
if (singleton != NULL && !common_hal_busio_uart_deinited(singleton)) {
|
||||
return singleton;
|
||||
}
|
||||
|
||||
busio_uart_obj_t *self = &uart_obj[instance];
|
||||
self->base.type = &busio_uart_type;
|
||||
|
||||
const mcu_pin_obj_t *rx = MP_OBJ_TO_PTR(DEFAULT_UART_BUS_RX);
|
||||
const mcu_pin_obj_t *tx = MP_OBJ_TO_PTR(DEFAULT_UART_BUS_TX);
|
||||
#ifdef DEFAULT_UART_BUS_RTS
|
||||
const mcu_pin_obj_t *rts = MP_OBJ_TO_PTR(DEFAULT_UART_BUS_RTS);
|
||||
#else
|
||||
const mcu_pin_obj_t *rts = NULL;
|
||||
#endif
|
||||
#ifdef DEFAULT_UART_BUS_CTS
|
||||
const mcu_pin_obj_t *cts = MP_OBJ_TO_PTR(DEFAULT_UART_BUS_CTS);
|
||||
#else
|
||||
const mcu_pin_obj_t *cts = NULL;
|
||||
#endif
|
||||
#ifdef DEFAULT_UART_IS_RS485
|
||||
const mcu_pin_obj_t *rs485_dir = MP_OBJ_TO_PTR(DEFAULT_UART_BUS_RS485DIR);
|
||||
#ifdef DEFAULT_UART_RS485_INVERT
|
||||
const bool rs485_invert = true;
|
||||
#else
|
||||
const bool rs485_invert = false;
|
||||
#endif
|
||||
#else
|
||||
const mcu_pin_obj_t *rs485_dir = NULL;
|
||||
const bool rs485_invert = false;
|
||||
#endif
|
||||
MP_STATE_VM(board_uart_bus) = &uart_obj;
|
||||
|
||||
common_hal_busio_uart_construct(self, tx, rx, rts, cts, rs485_dir, rs485_invert,
|
||||
9600, 8, BUSIO_UART_PARITY_NONE, 1, 1.0f, 64, NULL, false);
|
||||
MP_STATE_VM(shared_uart_bus) = MP_OBJ_FROM_PTR(self);
|
||||
return MP_STATE_VM(shared_uart_bus);
|
||||
assert_pin_free(uart_pin[instance].tx);
|
||||
assert_pin_free(uart_pin[instance].rx);
|
||||
|
||||
common_hal_busio_uart_construct(self, uart_pin[instance].tx, uart_pin[instance].rx,
|
||||
NULL, NULL, NULL, false, 9600, 8, BUSIO_UART_PARITY_NONE, 1, 1.0f, 64, NULL, false);
|
||||
|
||||
return &uart_obj[instance];
|
||||
}
|
||||
#endif
|
||||
|
||||
void reset_board_busses(void) {
|
||||
#if BOARD_I2C
|
||||
void reset_board_buses(void) {
|
||||
#if CIRCUITPY_BOARD_I2C
|
||||
for (uint8_t instance = 0; instance < CIRCUITPY_BOARD_I2C; instance++) {
|
||||
bool display_using_i2c = false;
|
||||
#if CIRCUITPY_DISPLAYIO
|
||||
for (uint8_t i = 0; i < CIRCUITPY_DISPLAY_LIMIT; i++) {
|
||||
if (displays[i].bus_base.type == &displayio_i2cdisplay_type && displays[i].i2cdisplay_bus.bus == i2c_singleton) {
|
||||
if (displays[i].bus_base.type == &displayio_i2cdisplay_type && displays[i].i2cdisplay_bus.bus == &i2c_obj[instance]) {
|
||||
display_using_i2c = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
if (!common_hal_busio_i2c_deinited(&i2c_obj[instance])) {
|
||||
// make sure I2C lock is not held over a soft reset
|
||||
if (i2c_singleton != NULL) {
|
||||
common_hal_busio_i2c_unlock(i2c_singleton);
|
||||
common_hal_busio_i2c_unlock(&i2c_obj[instance]);
|
||||
if (!display_using_i2c) {
|
||||
common_hal_busio_i2c_deinit(i2c_singleton);
|
||||
i2c_singleton = NULL;
|
||||
common_hal_busio_i2c_deinit(&i2c_obj[instance]);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#if BOARD_SPI
|
||||
#if CIRCUITPY_BOARD_SPI
|
||||
for (uint8_t instance = 0; instance < CIRCUITPY_BOARD_SPI; instance++) {
|
||||
bool display_using_spi = false;
|
||||
#if CIRCUITPY_DISPLAYIO
|
||||
for (uint8_t i = 0; i < CIRCUITPY_DISPLAY_LIMIT; i++) {
|
||||
mp_const_obj_t bus_type = displays[i].bus_base.type;
|
||||
if (bus_type == &displayio_fourwire_type && displays[i].fourwire_bus.bus == spi_singleton) {
|
||||
if (bus_type == &displayio_fourwire_type && displays[i].fourwire_bus.bus == &spi_obj[instance]) {
|
||||
display_using_spi = true;
|
||||
break;
|
||||
}
|
||||
#if CIRCUITPY_SHARPDISPLAY
|
||||
if (displays[i].bus_base.type == &sharpdisplay_framebuffer_type && displays[i].sharpdisplay.bus == spi_singleton) {
|
||||
if (displays[i].bus_base.type == &sharpdisplay_framebuffer_type && displays[i].sharpdisplay.bus == &spi_obj[instance]) {
|
||||
display_using_spi = true;
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
if (!common_hal_busio_spi_deinited(&spi_obj[instance])) {
|
||||
// make sure SPI lock is not held over a soft reset
|
||||
if (spi_singleton != NULL) {
|
||||
common_hal_busio_spi_unlock(spi_singleton);
|
||||
common_hal_busio_spi_unlock(&spi_obj[instance]);
|
||||
if (!display_using_spi) {
|
||||
common_hal_busio_spi_deinit(spi_singleton);
|
||||
spi_singleton = NULL;
|
||||
common_hal_busio_spi_deinit(&spi_obj[instance]);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#if BOARD_UART
|
||||
MP_STATE_VM(shared_uart_bus) = NULL;
|
||||
#if CIRCUITPY_BOARD_UART
|
||||
for (uint8_t instance = 0; instance < CIRCUITPY_BOARD_UART; instance++) {
|
||||
common_hal_busio_uart_deinit(&uart_obj[instance]);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
|
|
@ -27,6 +27,6 @@
|
|||
#ifndef MICROPY_INCLUDED_SHARED_MODULE_BOARD__INIT__H
|
||||
#define MICROPY_INCLUDED_SHARED_MODULE_BOARD__INIT__H
|
||||
|
||||
void reset_board_busses(void);
|
||||
void reset_board_buses(void);
|
||||
|
||||
#endif // MICROPY_INCLUDED_SHARED_MODULE_BOARD__INIT__H
|
||||
|
|
|
@ -24,7 +24,6 @@
|
|||
* THE SOFTWARE.
|
||||
*/
|
||||
|
||||
|
||||
#include <string.h>
|
||||
|
||||
#include "shared-module/displayio/__init__.h"
|
||||
|
@ -169,11 +168,11 @@ void reset_displays(void) {
|
|||
if (((size_t)fourwire->bus) < ((size_t)&displays) ||
|
||||
((size_t)fourwire->bus) > ((size_t)&displays + CIRCUITPY_DISPLAY_LIMIT)) {
|
||||
busio_spi_obj_t *original_spi = fourwire->bus;
|
||||
#if BOARD_SPI
|
||||
// We don't need to move original_spi if it is the board.SPI object because it is
|
||||
#if CIRCUITPY_BOARD_SPI
|
||||
// We don't need to move original_spi if it is a board.SPI object because it is
|
||||
// statically allocated already. (Doing so would also make it impossible to reference in
|
||||
// a subsequent VM run.)
|
||||
if (original_spi == common_hal_board_get_spi()) {
|
||||
if (common_hal_board_is_spi(original_spi)) {
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
@ -197,11 +196,11 @@ void reset_displays(void) {
|
|||
if (((size_t)i2c->bus) < ((size_t)&displays) ||
|
||||
((size_t)i2c->bus) > ((size_t)&displays + CIRCUITPY_DISPLAY_LIMIT)) {
|
||||
busio_i2c_obj_t *original_i2c = i2c->bus;
|
||||
#if BOARD_I2C
|
||||
// We don't need to move original_i2c if it is the board.I2C object because it is
|
||||
#if CIRCUITPY_BOARD_I2C
|
||||
// We don't need to move original_i2c if it is a board.I2C object because it is
|
||||
// statically allocated already. (Doing so would also make it impossible to reference in
|
||||
// a subsequent VM run.)
|
||||
if (original_i2c == common_hal_board_get_i2c()) {
|
||||
if (common_hal_board_is_i2c(original_i2c)) {
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
@ -230,11 +229,11 @@ void reset_displays(void) {
|
|||
if (((uint32_t)is31->i2c) < ((uint32_t)&displays) ||
|
||||
((uint32_t)is31->i2c) > ((uint32_t)&displays + CIRCUITPY_DISPLAY_LIMIT)) {
|
||||
busio_i2c_obj_t *original_i2c = is31->i2c;
|
||||
#if BOARD_I2C
|
||||
#if CIRCUITPY_BOARD_I2C
|
||||
// We don't need to move original_i2c if it is the board.I2C object because it is
|
||||
// statically allocated already. (Doing so would also make it impossible to reference in
|
||||
// a subsequent VM run.)
|
||||
if (original_i2c == common_hal_board_get_i2c()) {
|
||||
if (common_hal_board_is_i2c(original_i2c)) {
|
||||
continue;
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -71,8 +71,8 @@ STATIC bool common_hal_sharpdisplay_framebuffer_get_pixels_in_byte_share_row(sha
|
|||
|
||||
void common_hal_sharpdisplay_framebuffer_reset(sharpdisplay_framebuffer_obj_t *self) {
|
||||
if (self->bus != &self->inline_bus
|
||||
#if BOARD_SPI
|
||||
&& self->bus != common_hal_board_get_spi()
|
||||
#if CIRCUITPY_BOARD_SPI
|
||||
&& !common_hal_board_is_spi(self->bus)
|
||||
#endif
|
||||
) {
|
||||
memcpy(&self->inline_bus, self->bus, sizeof(busio_spi_obj_t));
|
||||
|
|
Loading…
Reference in New Issue