SPI 32-Bit Wide DMA Transmission Failure Issue

SPI 32-Bit Wide DMA Transmission Failure Issue

Someone is usingthe STM32H563 development productand has enabledDMA mode forSPI communication. They discovered an issue where, when theSPI data width is configured to16 bits or32 bits, using theSTM32 HAL library’sSPI DMA API start function results in no data transmission.

SPI 32-Bit Wide DMA Transmission Failure Issue

However, if theSPI data width is configured to8 bits, the transmission works normally.

SPI 32-Bit Wide DMA Transmission Failure Issue

What could be the reason? After repeatedly checking,DMA configuration did not reveal any issues. Since8 bit data width works, it stands to reason that theSPI andDMA configurations should not have major problems, unless there was an operational error during configuration, but repeated checks found no issues.

Later, after tracking and debugging, a small bug was found in the code. An error occurred during parameter checking at the following code location, causing it to exit. The following code is located in theSPI DMA API function mentioned earlier.

SPI 32-Bit Wide DMA Transmission Failure Issue

This code is not the functional code of theSPI orDMA module, but is specifically for checking the validity of the data width of theDMA source and destination during transmission when theSPI communication data width is set to16 bits or32 bits and DMA transmission is enabled.

Specifically, if theSPI data width is set to32 bits, theDMA source and destination widths must be32 bits; if theSPI data width is greater than8 bits, then the destination or source data width of theDMA cannot be configured to8 bits. Otherwise, it exits directly and returns an error.

From the content and logic of this code, there seems to be no issue, but why does the parameter validity check fail every time? As mentioned earlier, if theSPI data width is configured to8 bits, everything works normally. However, this code does not check when theSPI data width equals8 bits, so it naturally does not return an error here.

Later, through code debugging, it was found that all member variables in thehspi.hdmarx->Init andhspi.hdmatx->Init structures were0 values, meaning that theInit structures’ members were not initialized, leading to failures when checking the data width of theDMA source and destination.

SPI 32-Bit Wide DMA Transmission Failure Issue

This is strange.hspi.hdmarx->Init andhspi.hdmatx->Init structures’ members are directly related toDMA transmission, how could they not be initialized? It doesn’t make sense!

Later, after reading the code, it was found that in the STM32H5 series, eachDMA configuration is considered a transmission node, and we can see the configuration forSPI RX/TX DMA nodes in theHAL_SPI_MspInit() function.

SPI 32-Bit Wide DMA Transmission Failure Issue

Here we can also see a temporary variable calledNodeConfig, which is also a structure variable that stores the initialization parameters for eachDMA channel node, and its members are basically the same as those inhspi.hdmarx->Init andhspi.hdmatx->Init structures. Let’s refer to the code screenshot below:

SPI 32-Bit Wide DMA Transmission Failure Issue

After making the corresponding initialization configuration based onNodeConfig, the relevantDMA control registers are further written. In other words, the current library code indeed does not initialize thehspi.hdmarx->Init andhspi.hdmatx->Init structures; to be precise, it has bypassed them and used another initialization method. This led to failures and error returns when checking the members of thehspi.hdmarx->Init andhspi.hdmatx->Init structures.

In this case, to solve the current problem, the most direct and simple method is to disable this check code in theAPI code.

SPI 32-Bit Wide DMA Transmission Failure Issue

After disabling this check code, theDMA mode forSPI 16 bit and32 bit data communication works normally.

SPI 32-Bit Wide DMA Transmission Failure Issue

Of course, there is another way, which is to not disable this validity check code, but in theHAL_SPI_MspInit() function, after completing the initialization of theNodeConfig structure variable and configuring the relevantDMA nodes, use some variable content from theNodeConfig structure to assign to the corresponding members ofhspi.hdmarx->Init andhspi.hdmatx->Init structures for subsequent validity checks, for example like this: 【The following is part of the configuration forSPI DMA receiving node】

SPI 32-Bit Wide DMA Transmission Failure Issue

After verification, this method also works.

Here, I would like to remind you that when assigning values in the above manner, pay attention to the position of the assignment operation. If the assignment statement is placed at the position indicated by the red box, it may encounter aHardfault fault, while placing it at the green box position will be fine.

SPI 32-Bit Wide DMA Transmission Failure IssueSPI 32-Bit Wide DMA Transmission Failure Issue

If you are interested, you can analyze the specific code to understand why aHardfault occurs. Today’s sharing mainly aims to remind about this smallbug in the current HAL library routine, and we hope for improvements in the future. Now, the new STM32 chips are being released rapidly with many new features, functions, and applications, which also pose significant challenges to the STM32 ecosystem, such as various technical materials and application examples, and it is inevitable that bugs will appear. As long as we can continue to improve, that is sufficient.

*****************************************Previous topic reading links:1、Why is there an exception in one of the multi-channel DMA transmissions?2、Application example of synchronized output using different TIMERS3、Using EXIT0 to synchronize triggering SPI DMA transmission4、Using GPIO+DMA+TIM to simulate SPI communication demonstration5、STM32U5 ADC+TIM+DMA loop transmission demonstrationSPI 32-Bit Wide DMA Transmission Failure Issue

Leave a Comment