I was trying USART
using a STM32F407VGT6
and CubeMX
.
I am able to send and receive data using Interrupts. But I am getting a problem which I am not able to understand:
I am using HAL_UART_Transmit_IT
to send the data.
I have enabled __HAL_UART_ENABLE_IT(&huart3,UART_IT_TC);
.
Here is my code:
int main(void)
{
HAL_Init();
MX_GPIO_Init();
MX_USART3_UART_Init();
Green_Blink(100);
Orange_Blink(100);
Blue_Blink(100);
Red_Blink(100);
HAL_Delay(100);
__HAL_UART_ENABLE_IT(&huart3,UART_IT_TC);
char buff[] = {'2','4','.','0','0'};
while (1)
{
HAL_UART_Transmit_IT(&huart3,(uint8_t*)"OK\r\n ",5);
HAL_UART_Transmit_IT(&huart3,(uint8_t*)buff,5);
HAL_UART_Transmit_IT(&huart3,(uint8_t*)"OK\r\n ",5);
HAL_UART_Transmit_IT(&huart3,(uint8_t*)buff,5);
HAL_UART_Transmit_IT(&huart3,(uint8_t*)"OK\r\n ",5);
HAL_UART_Transmit_IT(&huart3,(uint8_t*)buff,5);
HAL_Delay(1000);
Blue_Blink(100);
}
}
So I am sending this kind of data. First, I am sending OK
and then I am sending the buffer data as you can see.
But in terminal(tera term in my case) I can't see the buffer data.
I can see OK
.
I don't know why this is happening. And how to resolve it?
Any suggestions?
You need to wait for the callback, which indicates the end of transmission . It is the interrupt function which is executed asynchronously. It does not have a chance to send even a single byte.
You just override the buffer and start the transmission over.
For this kind of messages, use blocking functions. Use DMA or interrupt ones when your main program is doing something during the communication, and you want the communication to be done in the background.
Edit
Some explanation. HAL interrupt functions do not wait until the transmission is completed. They return immediately to the caller and the communication is completed in the background. The main program can execute in parallel doing another tasks. When all bytes are sent (or on error) HAL library invokes the appropriate callback. For end of transmission it is:
void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart)
Because of the asynchronous execution if you want to start another transmission you need to know if the previous one has already completed.
Edit 2
In this case it does not make any sense to send asynchronously. You need to wait for the end of the previous transmissions:
and in main function: