cancel
Showing results for 
Search instead for 
Did you mean: 

i2c1 block with DMA is not working (STM32h743) - when the first transaction is sent from master board to slave board - > the i2c1_event interrupt is triggered and it is stuck in an endless loop.

VKats.1
Associate II

i've created 2 threads - i2c_tx_dma and i2c_rx_dma which use the HAL_I2C_Master_Transmit_DMA and HAL_I2C_Slave_Receive_DMA.

I am working with 2 boards of the STM32h74 family:

first board-> configured RX DMA on i2c1 block as a slave and activate HAL_I2C_Slave_Receive_DMA

second board-> configured TX DMA on i2c1 block as master and activate HAL_I2C_Master_Transmit_DMA.

the i2c1_event interrupt is triggered on the slave board and it is stuck in an endless loop.

# my DMA stream handler interrupt is not triggered at all

# my call back function is not triggered as well

# my i2c1_tx_buffer and i2c1_rx_buffer buffers are not fill up at all and remain empty

the attached picture with:

1) i2c1_rx_buffer and i2c1_tx_buffer declarations:

0693W00000Hno6oQAB.png2) flash ld file code with the buffers sections

0693W00000Hno7rQAB.png3) MX_DMA_Init()

0693W00000Hno81QAB.png4) HAL_I2C_MspInit() of I2C1:

0693W00000Hno8LQAR.png0693W00000Hno8QQAR.png5) i2c interrupts:

0693W00000Hno94QAB.png6) start of my main::

 0693W00000Hno9YQAR.png7) i2c call back functions:

0693W00000HnoARQAZ.pngI would love to get some guidance and understanding of what I am doing wrong

7 REPLIES 7

Stuck reentering interrupt handler? Check pending status have been cleared, or which ones aren't.​

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
TDK
Guru

Why is MX_I2C1_Init commented out?

If you feel a post has answered your question, please click "Accept as Solution".

Hi,

It's not really a commented out - it's called later in the main function, I just forgot to delete this line from the print screen attached

It's not called anywhere in the code you provided.

Consider attaching the source code file rather than providing screenshots of code which don't even tell the whole story.

If you feel a post has answered your question, please click "Accept as Solution".

Thanks for the advice. Since this is my first experience in the forum I thought the screenshots would be more accurate - next time I will attach all files

thanks - i will try it.

since I've developed only in ComPolling mode so far and everting worked perfectly I would like to learn and under stand the following:

In DMA mode, what is the correlation between I2C1_EV_IRQHandler() interrupt handler and my DMA1_Stream0_IRQHandler() interrupt handler ?

(in case that DMA1_Stream0 is the chosen one for I2C1 block Instance in the i2c1_rx dma init)

do i need to enable them both using HAL_NVIC_SetPriority and HAL_NVIC_EnableIRQ im my HAL_I2C_MspInit()?

TDK
Guru

I'm guessing based on this and based on your description that you've provided the code for the slave, not the master. It sounds like the issue is on the slave side, so that's good.

  HAL_I2C_Slave_Receive_DMA(hi2c, buffer, size);
  //HAL_I2C_Master_Transmit_DMA(hi2c, uint16_t DevAddress, uint8_t *pData, uint16_t Size);

Your code doesn't actually call these functions though, as the calls to the functions they're in are commented out:

//  RingBufferDmaU8_initI2cRx(&i2cRxRing, &hi2c1, i2c1_RxBuffer, I2C1_RX_BUFFER_SIZE);
//  RingBufferDmaU8_initI2cTx(&i2cTxRing, &hi2c1, i2c1_TxBuffer, I2C1_TX_BUFFER_SIZE);

Setting the address like this doesn't change anything (assuming it's not commented out). The address must be set when HAL_I2C_Init is called.

//  hi2c1.Init.OwnAddress1 = (I2C1_ADDRESS_1 << 1);
//  hi2c1.Init.OwnAddress2 = (I2C2_ADDRESS_2 << 1);

You have the slave address as 0 when they're initialized: 0 is a special address, which shouldn't be used as a specific slave address. Unsure if this is the source of the issue.

  hi2c1.Instance = I2C1;
  hi2c1.Init.Timing = 0x10103AFF;
  hi2c1.Init.OwnAddress1 = 0;
  hi2c1.Init.AddressingMode = I2C_ADDRESSINGMODE_7BIT;
  hi2c1.Init.DualAddressMode = I2C_DUALADDRESS_DISABLE;
  hi2c1.Init.OwnAddress2 = 0;
  hi2c1.Init.OwnAddress2Masks = I2C_OA2_NOMASK;
  hi2c1.Init.GeneralCallMode = I2C_GENERALCALL_DISABLE;
  hi2c1.Init.NoStretchMode = I2C_NOSTRETCH_DISABLE;

I would recommend making the program much simpler in order to debug, using CubeMX generated code where possible. Try to get HAL_I2C_IsDeviceReady to return HAL_OK on the master side first, then move on to sending/receiving in blocking mode, then move on to DMA mode.

I realize you've been debugging the problem with this code and it has changed over time. However, it makes it very difficult to debug when I have to guess at which lines should be uncommented and which should not.

If you feel a post has answered your question, please click "Accept as Solution".