Skip to main content
CJans.1
Associate III
Nov 4, 2022 1:29 PM UTC
Solved

DMA transfer error but CFSR does not indicate bus error

I'm using a STM32H743.

I used STM32CubeMx to configure the DCMI. It uses DMA to transfer to memory.

When calling HAL_DCMI_Start_DMA(), the DCMI_DMAError() function is called.

I found out that there is a transfer error. And according the documentation a bus error is the reason.

But the CFSR register of the MCU is zero, indicating no bus error.

What could be wrong?

Things I did:

  • use STM32CubeMX to set up DCMI and enable DMA
  • Disabled caching
  • created a buffer in SRAM1 using
    • __attribute__ ((section(".buffer"), used)) uint32_t bigbuf[30000];
    • checked that it is present in region RAM_D2
  • called HAL_DCMI_Start_DMA(&hdcmi, DCMI_MODE_CONTINUOUS, (uint32_t)bigbuf, ((752*480)/4)/4);
    • HAL_OK is returned
    • sensor is 752*480, I use 8 bit DCMI (thus 4 in a word) and I use half the number of pixels and half the number of lines
  • checked with oscilloscope that DCMI is working (clock, sync and data signals present)

Any idea why I can get this transfer error?

This topic has been closed for replies.
CJans.1
CJans.1Best answer
Associate III
Nov 6, 2022 11:22 AM UTC

I found the problem! It is a bug of STM32CubeMx.

STM32CubeMx generates this code to initalize all peripherals:

 /* Initialize all configured peripherals */
 MX_GPIO_Init();
 MX_DCMI_Init();
 MX_I2C1_Init();
 MX_I2C2_Init();
 MX_UART5_Init();
 MX_USART1_UART_Init();
 MX_DMA_Init();
 MX_USB_DEVICE_Init();

The problem is that MX_DCMI_Init() initializes the DMA. But the DMA clock is not enabled yet! It is enabled by MX_DMA_Init().

I did not want to change the initialization order, so I enabled the DMA clock just before all the inits:

 /* USER CODE BEGIN SysInit */
 
 __HAL_RCC_DMA2_CLK_ENABLE();
 
 /* USER CODE END SysInit */
 
 /* Initialize all configured peripherals */
 MX_GPIO_Init();
 MX_DCMI_Init();
 MX_I2C1_Init();
 MX_I2C2_Init();
 MX_UART5_Init();
 MX_USART1_UART_Init();
 MX_DMA_Init();
 MX_USB_DEVICE_Init();

And now it works!

3 replies

Tesla DeLorean
Guru
Nov 4, 2022 1:37 PM UTC

>>But the CFSR register of the MCU is zero, indicating no bus error.

The MCU doesn't do the DMA, or have visibility, as to what the DMA Controller is doing / using.

Look at the Bus Matrix, and how that relates to the DMA Unit, and the Memory you're acting on.

Some memories are not visible / usable. Be sure of where your buffer is situated.

Check alignment.

Tips, Buy me a coffee, or three.. PayPal Venmo (See Profile) Up vote any posts that you find helpful, it shows what's working..
CJans.1
CJans.1Author
Associate III
Nov 4, 2022 1:42 PM UTC

Thx Tesla DeLoran

I'm using SRAM1 which should be accesable by the DMA. It starts at 0x30000000.

You say 'Look at the Bus Matrix': Do you mean to find out what the bus error is? Or do you mean that I have to program the Bus Matrix? (I assumed STM32CubeMx does that).

CJans.1
CJans.1AuthorBest answer
Associate III
Nov 6, 2022 11:22 AM UTC

I found the problem! It is a bug of STM32CubeMx.

STM32CubeMx generates this code to initalize all peripherals:

 /* Initialize all configured peripherals */
 MX_GPIO_Init();
 MX_DCMI_Init();
 MX_I2C1_Init();
 MX_I2C2_Init();
 MX_UART5_Init();
 MX_USART1_UART_Init();
 MX_DMA_Init();
 MX_USB_DEVICE_Init();

The problem is that MX_DCMI_Init() initializes the DMA. But the DMA clock is not enabled yet! It is enabled by MX_DMA_Init().

I did not want to change the initialization order, so I enabled the DMA clock just before all the inits:

 /* USER CODE BEGIN SysInit */
 
 __HAL_RCC_DMA2_CLK_ENABLE();
 
 /* USER CODE END SysInit */
 
 /* Initialize all configured peripherals */
 MX_GPIO_Init();
 MX_DCMI_Init();
 MX_I2C1_Init();
 MX_I2C2_Init();
 MX_UART5_Init();
 MX_USART1_UART_Init();
 MX_DMA_Init();
 MX_USB_DEVICE_Init();

And now it works!