Skip to main content
Visitor II
June 23, 2026
Question

Nucleo H753ZI: SPI DMA generates no TX Interrupt

  • June 23, 2026
  • 2 replies
  • 51 views

I have a Nucleo-H753ZI board for testing purposes. I used CubeMX to configure SPI4 as a slave. You can see the configuration code below. SPI4_TX is assigned to DMA1 Stream 3, Medium priority, SPI4_RX is assigned to DMA1 Stream 0, medium priority.

I have a SPI master attached to the SPI4 which works as intended, i checked that on the oscilloscope. The Master transmits 1 Byte, wait for 50µs, reads another 4 bytes and based on the content of that 4 bytes, continues to clock more bytes in or out. The clock frequency is 12,5 MHz and 680ns pause between each byte. In my testcode below, the globaldata[4] = 10; defines that 10 more bytes will be clocked by the master. So the entire frame will contain 15 bytes.

I am now executing three different variations of code leading to surprising results. When calling HAL_SPI_Receive_DMA, the function HAL_SPI_RxCpltCallback is called as expected. When calling HAL_SPI_TransmitReceive_DMA, the function HAL_SPI_TxRxCpltCallback is called as expected. But when I call HAL_SPI_Transmit_DMA, the corresponding callback HAL_SPI_TxCpltCallback is not called. And I wonder why.

If I debug the code and set breakpoints to the corresponding SPI_DMAReceiveCplt, SPI_DMATransmitReceiveCplt and SPI_DMATransmitCplt in stm32h7xx_hal_spi.c are called and call themselves __HAL_SPI_ENABLE_IT(hspi, SPI_IT_EOT). But in case of SPI_DMATransmitCplt, nothing else happens. Why is the TX Complete Interrupt not fired?

uint8_t globaldata[15];
uint8_t globalrec[15];

void main()
{
globaldata[0] = 0;
globaldata[1] = 0;
globaldata[2] = 10;
globaldata[3] = 0;
globaldata[4] = 10;
globaldata[5] = 1;
globaldata[6] = 2;
globaldata[7] = 3;
globaldata[8] = 4;
globaldata[9] = 5;
globaldata[10] = 6;
globaldata[11] = 7;
globaldata[12] = 8;
globaldata[13] = 9;
globaldata[14] = 10;

HAL_StatusTypeDef status;
status = HAL_SPI_Transmit_DMA(&hspi4, globaldata, 15);
status = HAL_SPI_Receive_DMA(&hspi4, globaldata, 15);
status = HAL_SPI_TransmitReceive_DMA(&hspi4, globaldata, globalrec, 15);

while(1)
{

}
}

Config code for SPI4:

/**
* @brief SPI4 Initialization Function
* @param None
* @retval None
*/
static void MX_SPI4_Init(void)
{

/* USER CODE BEGIN SPI4_Init 0 */

/* USER CODE END SPI4_Init 0 */

/* USER CODE BEGIN SPI4_Init 1 */

/* USER CODE END SPI4_Init 1 */
/* SPI4 parameter configuration*/
hspi4.Instance = SPI4;
hspi4.Init.Mode = SPI_MODE_SLAVE;
hspi4.Init.Direction = SPI_DIRECTION_2LINES;
hspi4.Init.DataSize = SPI_DATASIZE_8BIT;
hspi4.Init.CLKPolarity = SPI_POLARITY_LOW;
hspi4.Init.CLKPhase = SPI_PHASE_1EDGE;
hspi4.Init.NSS = SPI_NSS_SOFT;
hspi4.Init.FirstBit = SPI_FIRSTBIT_MSB;
hspi4.Init.TIMode = SPI_TIMODE_DISABLE;
hspi4.Init.CRCCalculation = SPI_CRCCALCULATION_DISABLE;
hspi4.Init.CRCPolynomial = 0x0;
hspi4.Init.NSSPMode = SPI_NSS_PULSE_DISABLE;
hspi4.Init.NSSPolarity = SPI_NSS_POLARITY_LOW;
hspi4.Init.FifoThreshold = SPI_FIFO_THRESHOLD_01DATA;
hspi4.Init.TxCRCInitializationPattern = SPI_CRC_INITIALIZATION_ALL_ZERO_PATTERN;
hspi4.Init.RxCRCInitializationPattern = SPI_CRC_INITIALIZATION_ALL_ZERO_PATTERN;
hspi4.Init.MasterSSIdleness = SPI_MASTER_SS_IDLENESS_00CYCLE;
hspi4.Init.MasterInterDataIdleness = SPI_MASTER_INTERDATA_IDLENESS_00CYCLE;
hspi4.Init.MasterReceiverAutoSusp = SPI_MASTER_RX_AUTOSUSP_DISABLE;
hspi4.Init.MasterKeepIOState = SPI_MASTER_KEEP_IO_STATE_ENABLE;
hspi4.Init.IOSwap = SPI_IO_SWAP_DISABLE;
if (HAL_SPI_Init(&hspi4) != HAL_OK)
{
Error_Handler();
}
/* USER CODE BEGIN SPI4_Init 2 */

/* USER CODE END SPI4_Init 2 */

}

Config code for DMA

/**
* Enable DMA controller clock
*/
static void MX_DMA_Init(void)
{

/* DMA controller clock enable */
__HAL_RCC_DMA1_CLK_ENABLE();

/* DMA interrupt init */
/* DMA1_Stream0_IRQn interrupt configuration */
HAL_NVIC_SetPriority(DMA1_Stream0_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(DMA1_Stream0_IRQn);
/* DMA1_Stream1_IRQn interrupt configuration */
HAL_NVIC_SetPriority(DMA1_Stream1_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(DMA1_Stream1_IRQn);
/* DMA1_Stream2_IRQn interrupt configuration */
HAL_NVIC_SetPriority(DMA1_Stream2_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(DMA1_Stream2_IRQn);
/* DMA1_Stream3_IRQn interrupt configuration */
HAL_NVIC_SetPriority(DMA1_Stream3_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(DMA1_Stream3_IRQn);

}

 

 

2 replies

ST Technical Moderator
June 23, 2026

Hello ​@LBsbs 

Does the TC flag get set? Did you check what happens on the bus using a logic analyzer?

In order to give better visibility on the answered topics, please click on 'Best answer' on the reply which solved your issue or answered your question. Saket_Om
Billy OWEN
ST Employee
June 23, 2026

Hi ​@LBsbs 

 

This post has been escalated to the ST Online Support Team for additional assistance.  We'll contact you directly.

 

Regards,

Billy