Skip to main content
Visitor II
July 18, 2025
Question

UART with DMA RX/TX

  • July 18, 2025
  • 3 replies
  • 280 views

Dear ST's experts,

I want to send/receive data through UART between STM32 and PC. The data must be sent to PC every 500ms and then STM32 receive data from PC. I have configured UART2 with DMA in circular mode. I am using the function HAL_UART_TxCpltCallback to pause the UART (HAL_UART_DMAPause(&huart2);) to send data every 500ms. My problem is that when I use the above function, receiving data does not work properly.
How I can solve the problem?
Should I use DMA in normal mode for TX? 

    This topic has been closed for replies.

    3 replies

    Technical Moderator
    July 18, 2025
    Graduate II
    July 18, 2025

    USART Rx/Tx DMA can occur concurrently.

    Don't pause or block in interrupt handlers, or callbacks generated from interrupts, ie within interrupt context.

    Blocking in interrupt context is very bad form.

    If you want to initiate transfers on a periodic basis, start them in TIM callbacks, or count off time related to SysTick, ie initiate every 500 calls to SysTick_Handler()

    Or pace within your main() loop

    uint32_t start = HAL_GetTick();
    
    while(1)
    {
     if ((HAL_GetTick() - start) >= 500)
     {
     // Do 500ms Task
     start += 500;
     }
    }
    Graduate II
    July 18, 2025

    My problem is that when I use the above function, receiving data does not work properly.


    You have to be more specific about "receiving data does not work properly".

    Not interrupting? Data not what you expect or out of sync? 

    Show your code. 

     

    You can also look at this project https://github.com/karlyamashita/Nucleo-G071RB_UART_DMA_Idle_Circular/wiki

    Or this one that shows how to use a more configurable data structure for multiple UART instances. https://github.com/karlyamashita/Nucleo-G071RB_UART_DMA_Idle_Circular_Multi_Instances

    The UART_DMA_Idle_Circular_Drv_STM32 driver is universal so it can be used on any STM32 unless if it doesn't have HAL_UARTEx_ReceiveToIdle_DMA