[NXP Rapid IoT Review] Touch button does not respond - I2C deadlock release method[Copy link]
NXP Rapid IoT uses I2C1 to connect many peripherals, I2C1: Sensors + Touch: FXOS8700, FXAS21002, MPL3115, ENS210, TSL25711, CCS811 (behind I2C switch), SX9500 I2C2: after I2C switch (...NTAG_I2C_EN): NT3H2211, A1006, A71 And in the development process, the inevitable reset and restart of Rapid IoT causes confusion in the I2C timing. At the same time, due to battery power supply, not all settings on I2C can be powered off or hardware copied. Phenomenon manifested Touch button does not respond, sensor has no data, signal phenomenon SCL is high, SDA is always low The reasons for the deadlock are analyzed as follows: Under normal circumstances, the I2C bus protocol can ensure the normal read and write operations of the bus. However, when the I2C master device is abnormally reset (watchdog action, abnormal power supply on the board causes the reset chip to act, manual button reset, etc.), it may cause the I2C bus deadlock. The following is a detailed explanation of the causes of bus deadlock. During the I2C master device's read and write operations, the master device controls SCL to generate 8 clock pulses after the start signal, and then pulls the SCL signal to a low level. At this time, the slave device outputs a response signal and pulls the SDA signal to a low level. If the master device is abnormally reset at this time, SCL will be released to a high level. At this time, if the slave device is not reset, it will continue the I2C response and pull SDA to a low level until SCL becomes a low level, and then the response signal will end. As for the I2C master device, after resetting, it detects the SCL and SDA signals. If it finds that the SDA signal is at a low level, it will think that the I2C bus is occupied and will wait for the SCL and SDA signals to become high. In this way, the I2C master device waits for the slave device to release the SDA signal, while the I2C slave device is waiting for the master device to pull the SCL signal low to release the response signal. The two are waiting for each other, and the I2C bus enters a deadlock state. Similarly, when I2C performs a read operation, the I2C slave device responds and outputs data. If the I2C master device is abnormally reset at this moment and the data bit output by the I2C slave device is exactly 0, the I2C bus will also enter a deadlock state. The unlocking method is as follows: (1) Try to use an I2C slave device with a reset input. (2) Connect the power supplies of all slave I2C devices together and connect them to the main power supply through a MOS tube. The on and off of the MOS tube is realized by the I2C master device. (3) Design a watchdog function in the I2C slave device. (4) Add an I2C bus recovery program to the I2C master device. Each time the I2C master device is reset, if it detects that the SDA data line is pulled low, it controls the SCL clock line in the I2C to generate 9 clock pulses (for 8-bit data). In this way, the I2C slave device can complete the suspended read operation and recover from the deadlock state. (5) Add an additional bus recovery device to the I2C bus. (6) Connect an I2C buffer with deadlock recovery function to the I2C bus, such as Linear's LTC4307. The hardware is also set up, and not every device meets the above conditions, so we can only choose method (4). The specific code is as follows:
static void i2c_release_bus_delay(void) { #if 0 #define I2C1_RELEASE_BUS_COUNT 200U uint32_t i = 0; for (i = 0; i < I2C1_RELEASE_BUS_COUNT; i++) { __NOP(); } #else App_WaitUsec(100); #endif } void BOARD_I2C1_ConfigurePins(void) { /* Port C Clock Gate Control: Clock enabled */ CLOCK_EnableClock(kCLOCK_PortC); const port_pin_config_t portc10_pinC7_config = {/* Internal pull-up resistor is enabled */ kPORT_PullUp, /* Fast slew rate is configured */ kPORT_FastSlewRate, /* Passive filter is disabled */ kPORT_PassiveFilterDisable, /* Open drain is enabled */ kPORT_OpenDrainEnable, /* Low drive strength is configured */ kPORT_LowDriveStrength,/* Pin is configured as I2C1_SCL */
kPORT_MuxAlt2,
/* Pin Control Register fields [15:0] are not locked */
After the initial clock is on, you can call the above code. Complete code,
board.rar(6.03 KB, downloads: 7)
2019-3-10 17:28 上传
点击文件名下载附件
Replace the project file\RapidIot_Base\board\board.c This content is provided by EEWORLD forum user dvd1478[/size ]Original, if you want to reprint or use it for commercial purposes, you must obtain the author's consent and indicate the source
Well, the I2C deadlock problem does exist. If it is not solved properly, it is really troublesome. Thank you for sharing!
Details
Published on 2019-3-12 13:33