Showing results for 
Search instead for 
Did you mean: 

How to access multiple I2C devices on the same I2C line?

Associate II


I am using STM32F091VC based custom board. and our application is Multi thread with the FreeRTOS. On I2C1 line three device are connected. all the device are accessed from the different thread. to prevent the simultaneous access we have used Mutex. so, at a time only one device can be accessed. also we have configured I2C communication with the DMA(interrupt based). but some time application execution stuck in HAL layer's I2C ISR relted Api. this might be because of simultaneous access.

For your refer i am attaching my I2C code, Please suggest that Is our implementation is correct or not. also give some light to implement code to access multiple device on same I2C line.

Chief II
	/* Create Mutex, if not created */
	if(osMutexId_I2C1 == NULL)
		  osMutexId_I2C1 = osMutexCreate(&osMutex_I2C1);

You can't do that form a threads, which lock on that mutex! It creates race condition at start. One solution is to create those mutexes before starting kernel.

And why do You implement the same functions for each peripheral instance? Implement one set of functions with a corresponding handle parameter.

Associate III

One issue that comes to mind is that you're releasing the mutex right after initiating a DMA transaction. You never wait for the DMA/I2C transaction to complete before allowing the caller to initiate the next DMA transaction. This would be my first suspect in your situation.

I would solve this problem with a semaphore that gets taken right before the I2C/DMA transaction is initiated and released in the DMA transaction finished callback function.  The reason you need semaphores and not mutexes is that the DMA finished callback is called from the interrupt context, in which case a semaphore must be used to signal the thread that it's free to continue on with allowing the next transaction to proceed.

Several slaves on I2C but with 3V3 and 10K pull-ups?
Sound too "weak" to me:
I use 2K2 on 3V3 with just a single device.

The more slave devices you connect ("capacitors") - the lower you have to go with pull-ups.
10K and three slaves - even 100Kbps does not seem reliable to me.

ST Employee

Hello @ssath.7

For a better analysis, could you please provide the following information:

  • The version of the STM32Cube firmware you are using.
  • The values of XferCount and XferSize when the application execution gets stuck.
  • The contents of the ISR, CR1, and CR2 registers when the application execution gets stuck.
If your question is answered, please close this topic by clicking "Accept as Solution".