Alright. So a little bit of progress has been made on this front.
It seems like its timing related between when the DMA and SAI are enabled.
On page 2291 of the reference manual, the steps for configuring the DMA/SAI interface are listed specifying that the DMA be enabled before the SAI.
In the HAL files (specifically around line 1705 of stm32h7xx_hal_sai.c) within the HAL_SAI_Receive_DMA function the SAI is enabled first, and then the DMA Is enabled.
Simply swapping the order doesn’t fix the channel swap, adding a very short delay (I used a
nop loop in the code snippet below) results in the channels going back in the correct order.
I have not tried this on something that has the correct input->output mapping in the first place, and I suspect that this would cause that to flip to the wrong channel.
Here’s the snippet in case its useful for anyone who just needs to hack something together for now.
HAL_SAI_Receive_DMA() Starting at line 1705:
/* Enable the interrupts for error handling */
__HAL_SAI_ENABLE_IT(hsai, SAI_InterruptFlag(hsai, SAI_MODE_DMA));
/* Enable SAI Rx DMA Request */
hsai->Instance->CR1 |= SAI_xCR1_DMAEN;
uint32_t foo = 0;
while(foo++ < 35000)
if((hsai->Instance->CR1 & SAI_xCR1_SAIEN) == 0U)
/* Enable SAI peripheral */
Also, for what its worth, I verified that the FSPOL bit in the FSCR wasn’t getting flipped or causing this.
I’ll keep updating this thread with anything new I find as well.