目录
一、工程配置
二、使用USART中断收发前必知的两个函数的作用
2.1 HAL_UART_Transmit_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)
2.2 HAL_UART_Receive_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size)
三、代码详解
3.1 main()函数
3.2 两个回调函数
四、总结
硬件条件:带有两个usart外设(引脚空闲)的STM32开发板/工控板,用杜邦线把它俩正确的连起来。
实现功能:
本文默认读者已经有了如下的基本知识和技能:
下面直接开始工程(工程中只讲述与usart有关的地方)。
本文以STM32F103C8T6芯片为例。
图形化界面中,usart1和usart2的配置如图1-1、图1-2所示。它们的中断优先级配置如图1-3所示。
到此,两个usart的配置全部结束了(代码中不再添加多余的配置代码)。
/* USER CODE BEGIN PV */
uint8_t RxData1 = 0x00U; // usart1接收到的信息待存入的空间
uint8_t RxData2 = 0x00U; // usart2接收到的信息待存入的空间
uint8_t TxData1 = 0x01U; // usart1待发送的信息
uint8_t TxData2 = 0xFFU; // usart1待发送的信息
/* USER CODE END PV */
int main(void)
{
/* USER CODE BEGIN 1 */
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_USART1_UART_Init();
MX_USART2_UART_Init();
/* USER CODE BEGIN 2 */
HAL_UART_Receive_IT(&huart1, &RxData1, sizeof(RxData1)); // 指定usart1存储接收信息所用的空间,并使能usart1的相关接收中断
HAL_UART_Receive_IT(&huart2, &RxData2, sizeof(RxData2)); // 指定usart2存储接收信息所用的空间,并使能usart2的相关接收中断
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
if(HAL_UART_Transmit_IT(&huart1, &TxData1, (uint16_t) sizeof(TxData1)) != HAL_OK) // usart1发送信息,发完信息立即进入中断,执行用户自定义的回调函数使得TxData1的内容加1
{
Error_Handler();
}
if(HAL_UART_Transmit_IT(&huart2, &TxData2, (uint16_t) sizeof(TxData2)) != HAL_OK) // usart2发送信息,发完信息立即进入中断,执行用户自定义的回调函数使得TxData2的内容减1
{
Error_Handler();
}
}
/* USER CODE END 3 */
}
/*
* 该函数是在HAL_UART_Transmit_IT()函数执行完之后立即自动调用的回调函数
*
*/
void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart)
{
if(huart->Instance == USART1)
{
// 产生usart1下一次发送的信息
if(TxData1 == 0xFFU)
{
TxData1 = 0x01U;
}
else
{
TxData1++;
}
}
if(huart->Instance == USART2)
{
// 产生usart2下一次发送的信息
if(TxData2 == 0x01U)
{
TxData2 = 0xFFU;
}
else
{
TxData2--;
}
}
}
/*
* 该函数是在“接收寄存器非空”中断里自动调用的回调函数
* 进入该函数前,usart1已经将接收到的信息存储在了RxData1中;usart2已经将接收到的信息存储在了RxData2中
* 并且,两个usart相关的接收中断是处于失能的状态
*/
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
if(huart->Instance == USART1)
{
HAL_UART_Receive_IT(&huart1, &RxData1, sizeof(RxData1)); // 指定usart1存储下一次接收信息所用的空间,并再次使能usart1的相关接收中断
// 用户代码begin
// 用户代码end
}
if(huart->Instance == USART2)
{
HAL_UART_Receive_IT(&huart2, &RxData2, sizeof(RxData2)); // 指定usart2存储下一次接收信息所用的空间,并再次使能usart2的相关接收中断
// 用户代码begin
// 用户代码end
}
}
stm32的usart配置和使用流程在stm32cubeide软件中是这样的:
我遇到的错误点总结:
所有与usart相关的函数,它们的功能,传递参数的含义、类型、取值,返回值等;所有与usart相关的结构体,它们的定义,成员变量的含义、类型、取值等,或是其它更多的信息。这些请自行在工程里的这两个文件中进行查阅: