diff --git a/src/omv/boards/NANO33/omv_boardconfig.h b/src/omv/boards/NANO33/omv_boardconfig.h index 8fcdeb2be..d2f13a5de 100644 --- a/src/omv/boards/NANO33/omv_boardconfig.h +++ b/src/omv/boards/NANO33/omv_boardconfig.h @@ -102,6 +102,18 @@ #define FIR_I2C_SDA_PIN (31) #define FIR_I2C_SPEED (CAMBUS_SPEED_FULL) +// I2C0 +#define TWI0_ID (0) +#define TWI0_SCL_PIN (2) +#define TWI0_SDA_PIN (31) +#define TWI0_SPEED (CAMBUS_SPEED_FULL) + +// I2C1 +#define TWI1_ID (1) +#define TWI1_SCL_PIN (15) +#define TWI1_SDA_PIN (14) +#define TWI1_SPEED (CAMBUS_SPEED_FULL) + // PDM/MIC #define PDM_DIN_PIN (25) #define PDM_CLK_PIN (26) diff --git a/src/omv/ports/nrf/cambus.c b/src/omv/ports/nrf/cambus.c index a19beffdf..eeacd0242 100644 --- a/src/omv/ports/nrf/cambus.c +++ b/src/omv/ports/nrf/cambus.c @@ -23,17 +23,19 @@ int cambus_init(cambus_t *bus, uint32_t bus_id, uint32_t speed) { bus->id = bus_id; bus->speed = speed; - bus->scl_pin = FIR_I2C_SCL_PIN; - bus->sda_pin = FIR_I2C_SDA_PIN; bus->initialized = false; switch (bus_id) { case 0: { + bus->scl_pin = TWI0_SCL_PIN; + bus->sda_pin = TWI0_SDA_PIN; nrfx_twi_t _twi = NRFX_TWI_INSTANCE(0); memcpy(&bus->twi, &_twi, sizeof(nrfx_twi_t)); break; } case 1: { + bus->scl_pin = TWI1_SCL_PIN; + bus->sda_pin = TWI1_SDA_PIN; nrfx_twi_t _twi = NRFX_TWI_INSTANCE(1); memcpy(&bus->twi, &_twi, sizeof(nrfx_twi_t)); break; @@ -43,8 +45,8 @@ int cambus_init(cambus_t *bus, uint32_t bus_id, uint32_t speed) } nrfx_twi_config_t config = { - .scl = FIR_I2C_SCL_PIN, - .sda = FIR_I2C_SDA_PIN, + .scl = bus->scl_pin, + .sda = bus->sda_pin, .frequency = speed, .interrupt_priority = 4, .hold_bus_uninit = false diff --git a/src/omv/ports/stm32/cambus.c b/src/omv/ports/stm32/cambus.c index 41e4b6e6f..79e13d7d9 100644 --- a/src/omv/ports/stm32/cambus.c +++ b/src/omv/ports/stm32/cambus.c @@ -92,6 +92,21 @@ int cambus_init(cambus_t *bus, uint32_t bus_id, uint32_t speed) return -1; } + // Our code only knows about these two I2Cs instances. + if (bus->i2c->Instance == FIR_I2C) { + bus->port = FIR_I2C_PORT; + bus->scl_pin = FIR_I2C_SCL_PIN; + bus->sda_pin = FIR_I2C_SDA_PIN; + } else if (bus->i2c->Instance == ISC_I2C) { + bus->port = ISC_I2C_PORT; + bus->scl_pin = ISC_I2C_SCL_PIN; + bus->sda_pin = ISC_I2C_SDA_PIN; + } else { + bus->port = NULL; + bus->scl_pin = 0; + bus->sda_pin = 0; + } + // Configure the I2C handle bus->i2c->Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT; #if !defined(STM32F4) @@ -111,7 +126,8 @@ int cambus_init(cambus_t *bus, uint32_t bus_id, uint32_t speed) HAL_I2C_DeInit(bus->i2c); if (HAL_I2C_Init(bus->i2c) != HAL_OK) { - /* Initialization Error */ + bus->i2c = NULL; + bus->port = NULL; return -1; } @@ -197,6 +213,7 @@ int cambus_deinit(cambus_t *bus) bus->i2c->Instance = NULL; } bus->i2c = NULL; + bus->port = NULL; return 0; } @@ -390,29 +407,28 @@ i2c_error: return ret; } -// TODO this is only used by the FIR code, hard-code pin/port for now. int cambus_pulse_scl(cambus_t *bus) { - #if defined(FIR_I2C_SCL_PIN) - // Configure SCL as GPIO - GPIO_InitTypeDef GPIO_InitStructure; - GPIO_InitStructure.Pull = GPIO_NOPULL; - GPIO_InitStructure.Speed = GPIO_SPEED_HIGH; - GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_PP; - GPIO_InitStructure.Pin = FIR_I2C_SCL_PIN; - HAL_GPIO_Init(FIR_I2C_PORT, &GPIO_InitStructure); + if (bus->port) { + // Configure SCL as GPIO + GPIO_InitTypeDef GPIO_InitStructure; + GPIO_InitStructure.Pull = GPIO_NOPULL; + GPIO_InitStructure.Speed = GPIO_SPEED_HIGH; + GPIO_InitStructure.Mode = GPIO_MODE_OUTPUT_PP; + GPIO_InitStructure.Pin = bus->scl_pin; + HAL_GPIO_Init(bus->port, &GPIO_InitStructure); - // Pulse SCL to recover stuck device. - for (int i=0; i<10000; i++) { - HAL_GPIO_WritePin(FIR_I2C_PORT, FIR_I2C_SCL_PIN, GPIO_PIN_SET); - mp_hal_delay_us(10); - HAL_GPIO_WritePin(FIR_I2C_PORT, FIR_I2C_SCL_PIN, GPIO_PIN_RESET); - mp_hal_delay_us(10); + // Pulse SCL to recover stuck device. + for (int i=0; i<10000; i++) { + HAL_GPIO_WritePin(bus->port, bus->scl_pin, GPIO_PIN_SET); + mp_hal_delay_us(10); + HAL_GPIO_WritePin(bus->port, bus->scl_pin, GPIO_PIN_RESET); + mp_hal_delay_us(10); + } + + // Clear ARLO flag if it's set. + __HAL_I2C_CLEAR_FLAG(bus->i2c, I2C_FLAG_ARLO); + debug_printf("reset stuck i2c device\n"); } - - // Clear ARLO flag if it's set. - __HAL_I2C_CLEAR_FLAG(bus->i2c, I2C_FLAG_ARLO); - debug_printf("reset stuck i2c device\n"); - #endif return 0; } diff --git a/src/omv/ports/stm32/cambus_struct.h b/src/omv/ports/stm32/cambus_struct.h index 91f69087b..4b81600f7 100644 --- a/src/omv/ports/stm32/cambus_struct.h +++ b/src/omv/ports/stm32/cambus_struct.h @@ -36,6 +36,9 @@ typedef enum _cambus_speed { typedef struct _cambus { uint32_t id; uint32_t speed; + uint32_t scl_pin; + uint32_t sda_pin; + GPIO_TypeDef *port; // This pointer will be set to its respective I2C handle defined in MicroPython // because all I2C IRQs are defined in stm32_it.c and handled by MicroPython. I2C_HandleTypeDef *i2c;