Search code examples
stm32i2chal

Resetting I2C state using HAL in STM32L0 MCU


I use I2C-tools to test firmware (HAL-based), I2C, STM32L0 MCU. When I send command to MCU (via i2cset utility), it sends an answer (received in i2cget). It works fine. If I call i2cget twice after single i2cset, it fails (which is expected behaviour). But if I execute i2cset after that error, then it also fails. So, the receive-transfer becomes broken (no callback is activated). How can it be fixed?

At the moment, HAL_I2C_Slave_Receive_IT() is called in HAL_I2C_SlaveTxCpltCallback(). HAL_I2C_SlaveRxCpltCallback() calls HAL_I2C_Slave_Transmit_IT(). Should I put HAL_I2C_Slave_Receive_IT() in two callbacks (receive/transmit related)?


Solution

  • I don't know if you've solved this question. However, it is more accurate to define a flag that states that the HAL_I2C_SlaveTxCpltCallback, HAL_I2C_SlaveRxCpltCallback, and HAL_I2C_ErrorCallback functions have completed transfers or an error occurred.

    maybe the following codes may be useful. You can reinit after making deinit.

    /**
      * @brief  Initialize and setup GPIO and I2C peripheral
      * @param  obj : pointer to i2c_t structure
      * @retval none
      */
    void i2c_deinit(i2c_t *obj)
    {
      HAL_NVIC_DisableIRQ(obj->irq);
    #if !defined(STM32F0xx) && !defined(STM32L0xx)
      HAL_NVIC_DisableIRQ(obj->irqER);
    #endif // !defined(STM32F0xx) && !defined(STM32L0xx)
      HAL_I2C_DeInit(&(obj->handle));
    }
    
    
    void LDC_I2C_ReInit(void)
        {
        HAL_I2C_Init(&hi2c1);
        }
    

    and it has a fine example in these links.

    https://github.com/stm32duino/Arduino_Core_STM32/blob/c392140415b3cf29100062ecb083adfa0f59f8b1/cores/arduino/stm32/twi.h

    https://github.com/stm32duino/Arduino_Core_STM32/blob/c392140415b3cf29100062ecb083adfa0f59f8b1/cores/arduino/stm32/twi.c