2025-02-06 09:23 PM - last edited on 2025-02-07 03:12 AM by Andrew Neil
Hi guys, I was trying to implement HAL_UART_Transmit_DMA() since I am using freeRTOS. It auto trigger a reset for my stm32f427.
Tried HAL_UART_Transmit(), everything works well. Only HAL_UART_Transmit_DMA() causing the reset, Did I missed anything?
for (uint8_t j=1; j!=CPH_MAX_N_PORTS; ++j) // can change to +1 after disabling drone troubleshoot port
{
if(byte_1 == j)
{
if ((ports_handle[j-1])->hdmatx == NULL)
{
USER_LOG_ERROR("TX DMA not linked for UART!");
}
HAL_UART_DMAStop(ports_handle[j-1]); // Stop RX DMA before TX
ports_handle[j-1]->gState = HAL_UART_STATE_READY;
__HAL_DMA_ENABLE_IT(ports_handle[j-1]->hdmatx, DMA_IT_TC); // TX Complete Interrupt
__HAL_DMA_ENABLE_IT(ports_handle[j-1]->hdmatx, DMA_IT_TE); // TX Error Interrupt
if (ports_handle[j-1]->hdmatx == NULL) {
USER_LOG_ERROR("TX DMA not linked for UART!");
}
if (ports_handle[j-1]->gState != HAL_UART_STATE_READY) {
USER_LOG_ERROR("UART TX is busy (State: %d)", ports_handle[j-1]->gState);
}
if (!(ports_handle[j-1]->hdmatx->Instance->CR & DMA_SxCR_TCIE)) {
USER_LOG_WARN("TX DMA Interrupts not enabled! Enabling now...");
__HAL_DMA_ENABLE_IT(ports_handle[j-1]->hdmatx, DMA_IT_TC);
__HAL_DMA_ENABLE_IT(ports_handle[j-1]->hdmatx, DMA_IT_TE);
}
USER_LOG_INFO("UART TX State: %d", HAL_UART_GetState(ports_handle[j-1]));
if (HAL_UART_GetState(ports_handle[j-1]) == HAL_UART_STATE_READY)
{
if(HAL_UART_Transmit(ports_handle[j-1], USB_recv_buf+cur_msg_pos+MSD_HEADER, totalBufLen-MSD_HEADER,10) != HAL_OK) // forward the buffer
{
USER_LOG_ERROR("UART transmission failed for port %d!", j);
}
}
else
{
USER_LOG_ERROR("UART transmission busy for port %d!", j);
USER_LOG_ERROR("UART state -> %d!", HAL_UART_GetState(ports_handle[j-1]));
}
HAL_UARTEx_ReceiveToIdle_DMA(ports_handle[j-1], DMARxBuf[j], BUFFER_SIZE); // restart the DMA
__HAL_DMA_DISABLE_IT(DMAs_handle[j-1],DMA_IT_HT); // disable the interrupt as we don’t need the Half Transfer interrupt
valid_port_found = true;
break;
}
}
* none of the error log was triggered. Initially, I tried without the non-essential code as below and I got the state value of 0x22 which is HAL_UART_STATE_BUSY_RX and that is why I am adding those extra lines of code.
if (HAL_UART_GetState(ports_handle[j-1]) == HAL_UART_STATE_READY)
{
if(HAL_UART_Transmit(ports_handle[j-1], USB_recv_buf+cur_msg_pos+MSD_HEADER, totalBufLen-MSD_HEADER,10) != HAL_OK) // forward the buffer
{
USER_LOG_ERROR("UART transmission failed for port %d!", j);
}
}
else
{
USER_LOG_ERROR("UART transmission busy for port %d!", j);
USER_LOG_ERROR("UART state -> %d!", HAL_UART_GetState(ports_handle[j-1]));
}
From my perspective, DMA for RX works fine, which I do receive what I want. Only calling the following will cause the HAL_UART_Transmit_DMA() reset:
HAL_UART_DMAStop(ports_handle[j-1]);
The line of code when calling HAL_UART_Transmit_DMA:
if(HAL_UART_Transmit_DMA(ports_handle[j-1], USB_recv_buf+cur_msg_pos+MSD_HEADER, totalBufLen-MSD_HEADER) != HAL_OK)
OR should I ask what is the correct way to do this if we detect HAL_UART_STATE_BUSY_RX.