Skip to content

Commit 2e9dc4d

Browse files
committed
Use interrupt mode for I2C transfers
Switch from polling mode to IT mode for I2C transfers. For example, this is needed if we want to use SPI and I2C in the same time.
1 parent 156ccfc commit 2e9dc4d

File tree

1 file changed

+23
-16
lines changed

1 file changed

+23
-16
lines changed

Diff for: cores/arduino/stm32/twi.c

+23-16
Original file line numberDiff line numberDiff line change
@@ -255,14 +255,12 @@ void i2c_custom_init(i2c_t *obj, i2c_timing_e timing, uint32_t addressingMode, u
255255

256256
handle->State = HAL_I2C_STATE_RESET;
257257

258-
if(master == 0) {
259-
HAL_NVIC_SetPriority(obj->irq, 0, 1);
260-
HAL_NVIC_EnableIRQ(obj->irq);
258+
HAL_NVIC_SetPriority(obj->irq, 0, 1);
259+
HAL_NVIC_EnableIRQ(obj->irq);
261260
#ifdef STM32F1xx
262-
HAL_NVIC_SetPriority(obj->irqER, 0, 1);
263-
HAL_NVIC_EnableIRQ(obj->irqER);
261+
HAL_NVIC_SetPriority(obj->irqER, 0, 1);
262+
HAL_NVIC_EnableIRQ(obj->irqER);
264263
#endif
265-
}
266264

267265
// Init the I2C
268266
HAL_I2C_Init(handle);
@@ -335,17 +333,18 @@ i2c_status_e i2c_master_write(i2c_t *obj, uint8_t dev_address,
335333

336334
{
337335
i2c_status_e ret = I2C_ERROR;
338-
HAL_StatusTypeDef status = HAL_OK;
339-
340-
// Check the communication status
341-
status = HAL_I2C_Master_Transmit(&(obj->handle), dev_address, data, size, I2C_TIMEOUT_TICK);
336+
uint32_t tickstart = HAL_GetTick();
342337

343-
if(status == HAL_OK)
338+
if(HAL_I2C_Master_Transmit_IT(&(obj->handle), dev_address, data, size) == HAL_OK){
344339
ret = I2C_OK;
345-
else if(status == HAL_TIMEOUT)
346-
ret = I2C_TIMEOUT;
347-
else
348-
ret = I2C_ERROR;
340+
// wait for transfer completion
341+
while((HAL_I2C_GetState(&(obj->handle)) != HAL_I2C_STATE_READY)
342+
&& (ret != I2C_TIMEOUT)){
343+
if((HAL_GetTick() - tickstart) > I2C_TIMEOUT_TICK) {
344+
ret = I2C_TIMEOUT;
345+
}
346+
}
347+
}
349348

350349
return ret;
351350
}
@@ -379,9 +378,17 @@ void i2c_slave_write_IT(i2c_t *obj, uint8_t *data, uint8_t size)
379378
i2c_status_e i2c_master_read(i2c_t *obj, uint8_t dev_address, uint8_t *data, uint8_t size)
380379
{
381380
i2c_status_e ret = I2C_ERROR;
381+
uint32_t tickstart = HAL_GetTick();
382382

383-
if(HAL_I2C_Master_Receive(&(obj->handle), dev_address, data, size, I2C_TIMEOUT_TICK) == HAL_OK) {
383+
if(HAL_I2C_Master_Receive_IT(&(obj->handle), dev_address, data, size) == HAL_OK) {
384384
ret = I2C_OK;
385+
// wait for transfer completion
386+
while((HAL_I2C_GetState(&(obj->handle)) != HAL_I2C_STATE_READY)
387+
&& (ret != I2C_TIMEOUT)){
388+
if((HAL_GetTick() - tickstart) > I2C_TIMEOUT_TICK) {
389+
ret = I2C_TIMEOUT;
390+
}
391+
}
385392
}
386393

387394
return ret;

0 commit comments

Comments
 (0)