cancel
Showing results for 
Search instead for 
Did you mean: 

STM32Cube_FW_F0_V1.11.2 HAL I2C module has serious bug in NACK bit handling for I2C CR2 register, breaking fast successive I2C transfer in Slave-mode

MDednev
Associate

I suppose that NACK bit handling logic was inherited from F4 family, where ACK bit is used for address/data acknowledgement control and could be set/reset by software. Unlike F4 family, I2C controller of F0 uses CR2 NACK bit only for data bytes and denies software reset of NACK bit, software could only assert it for NACKing data transaction bytes. This leads to some race conditions in HAL I2C module.

There is the race conditions between NACK assertion in CR2 and hardware 'address matched' event in slave completion handler I2C_ITSlaveCplt() and other similar cases. This race condition leads to the invalid NACK for the first transmitted byte if address phase of second sequential I2C transaction ('address matched') arrives too early: there is a possibility of address

transaction will not reset NACK flag in I2C CR2 register, asserted by STOPF handler (I2C_ITSlaveCplt) or other function. So the first transmitted by master byte will be NACKed and Master=>Slave transaction will fail in this case.

HAL_I2C_Slave_Seq_Receive_IT and similar functions have the code to clear NACK

flag in CR2 in the beginning of transaction, but this doesn't help, because NACK flag in CR2 could be cleared only by the means of hardware (regarding to  the reference manual Note). So, if NACK was asserted by STOPF handler _after_  next address byte has arrived, this NACK will break first byte transfer.

At 100 kHz this is slightly possible, but at 400 kHz this possibility rises in many times, specially if MCU is under heavy load of other interrupt requests with higher priority, than I2C interrupt handler.

Proposed patch is attached.

0 REPLIES 0