cancel
Showing results for 
Search instead for 
Did you mean: 

I2C blocks on STM32F4 HAL_I2C_IsDeviceReady HAL v1.6

Chr. Fahrni
Associate II
Posted on January 09, 2017 at 13:49

My software checks the I2C state of a device by calling if( HAL_I2C_IsDeviceReady(hi2c, addr, 2, 15)!= HAL_OK).

There are several changes in the new Version of HAL V1.6.

The problem is the expired Delay tickstart within the do..while loop: If the loop is the 2nd run, the Function I2C_WaitOnFlagUntilTimeout does not wait until the Start is done. Then the code breaks with HAL_TIMEOUT and the bus lanes SDA and SCL are both low.

A workaround could be to renew the tickstart in the following part of the code:

      /* Generate Start */

      hi2c->Instance->CR1 |= I2C_CR1_START;

      /* Wait until SB flag is set */

      tickstart = HAL_GetTick();   // line 3266 added by C. Fahrni

      if(I2C_WaitOnFlagUntilTimeout(hi2c, I2C_FLAG_SB, RESET, Timeout, tickstart) != HAL_OK)

      {

        return HAL_TIMEOUT;

      }

Maybe there is another workaround. I hope for a bugfix in the next version...

#i2c #hal #hal_i2c_isdeviceready #i2c-bus-locked #hal-v1.6 #stm32f4
2 REPLIES 2
Amel NASRI
ST Employee
Posted on January 09, 2017 at 17:21

Hi @C Fahrni,

Could you please provide more details on your case:

  1. what do you mean by '2nd run?
  2. could you please share minimum code that may help to reproduce issue?
  3. what HW are you using?
  4. do you have same issue using the I2C examples provided within the Cube package?

-Amel-

To give better visibility on the answered topics, please click on Accept as Solution on the reply which solved your issue or answered your question.

Chr. Fahrni
Associate II
Posted on January 20, 2017 at 10:51

Hi Amel

Thank you for replying…

Cube is generation the following file:

  * @file    stm32f4xx_hal_i2c.c

  * @author  MCD Application Team

  * @version V1.6.0

  * @date    04-November-2016

I use the STM32F427. I did not try out other I2C examples – I first want to describe you the issue:

The controller finds out if a I2C slave is connected to the bus. This is done with 2 Trials:

if( HAL_I2C_IsDeviceReady(hi2c, DevAddress, 2, 5)!= HAL_OK)

So within

IsDeviceReady

there is a do..while loop that counts the Trials.

First iteration:

  • The tickstart ist set directy before and has not expired (15ms).

  • if(I2C_WaitOnFlagUntilTimeout(hi2c, I2C_FLAG_SB, RESET, Timeout, tickstart) != HAL_OK)

    has not timeout.

  • while((tmp1 == RESET) && (tmp2 == RESET) && (tmp3 != HAL_I2C_STATE_TIMEOUT))

    is waiting until Timeout

Second iteration

  • After generation of Start,

    HAL_I2C_IsDeviceReady

    terminates with

    HAL_TIMEOUT

    , the Bus lanes are low…

        do

        {

          /* Generate Start */

          hi2c->Instance->CR1 |= I2C_CR1_START;

          /* Wait until SB flag is set */

          if(I2C_WaitOnFlagUntilTimeout(hi2c, I2C_FLAG_SB, RESET, Timeout, tickstart) != HAL_OK)

          {

            return HAL_TIMEOUT;

          }

This function

HAL_I2C_IsDeviceReady

in V1.6 has several modification compared to the last HAL version.

As workaround I reduced the Trials to 1. Other workaround could be to make a Stop before leaving.

Best Regards,

Christoph Fahrni