蓝桥杯STM32G431RBT6学习——USART

蓝桥杯STM32G431RBT6学习——USART

前言

串口在蓝桥杯近几届中考频也相对较高(十三、十二届均考),因此必然也要学习一下。
在这里插入图片描述

作为后来之秀的开源项目DAP Link不仅支持SWD调试下载,同时还支持串口调试功能,国信长天开发板上使用的是一块STM32F103C8T6烧写的固件(奢侈),其串口连接的是STM32G431的PA9、PA10。

STM32CubeMX配置

在这里插入图片描述
将PA9、PA10设置为USART1使用引脚后,将USART1配置为异步通信即可,通信细节(波特率、停止位等)视情况自行调节,最后打勾NVIC中断

Keil代码编写

重新了解了一下HAL库的中断流程,以下做复习使用:
HAL库的初始化代码,都会由CubeMX自动生成于一组文件中,例如usart.c、usart.h等,在CubeMX中配置的外设参数,例如波特率、停止位等均在.c文件中以一个初始化函数进行实现。
对于其中断配置,HAL库提供一个中断函数(如:USART1_IRQHandler)对相关中断进行注册使能,此步骤由CubMX配置自动生成,我们需要做的只是将其回调函数进行重写即可。(HAL_xxx_Callback)回调函数由中断注册函数间接调用,以上中断配置于stm32g4xx_it.c中完成。

USART相关API:
常用中断回调函数
对于HAL_UART_IRQHandler存在一个问题,该函数每次执行结束以后,都会清除中断标志,并取消中断的使能

//串口中断注册函数,注册以后中断才会使能,CubeMX配置自动调用
void HAL_UART_IRQHandler(UART_HandleTypeDef *huart);
//数据发送中断触发的回调函数
void HAL_UART_TxCpltCallback(UART_HandleTypeDef *huart);
//数据接收中断触发的回调函数
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart);

参数:串口类型句柄,有CubeMX生成定义

串口发送、接收函数
这两个函数并不会触发中断,同时具备超时参数Timeout

HAL_StatusTypeDef HAL_UART_Transmit(UART_HandleTypeDef *huart, const uint8_t *pData, uint16_t Size, uint32_t Timeout);
HAL_StatusTypeDef HAL_UART_Receive(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size, uint32_t Timeout);

参数1:串口类型句柄,有CubeMX生成定义;
参数2:发送/接收的数据;
参数3:发送/接收的数据长度,通常使用string.h中的strlen获取;
参数4:超时时间,当发送/接收时间到仍未发送/接收到指定字符长度,则会取消此次发送/接收
串口发送、接收函数(中断式)
这两个函数会触发中断,
对于发送函数:该函数每发送一次数据就会触发一次中断,且无法连续调用,只有上次发送结束后才能进行下一次发送;
对于接收函数:该函数只有接收数据长度达到Size以后才会触发中断

HAL_StatusTypeDef HAL_UART_Transmit_IT(UART_HandleTypeDef *huart, const uint8_t *pData, uint16_t Size);
HAL_StatusTypeDef HAL_UART_Receive_IT(UART_HandleTypeDef *huart, uint8_t *pData, uint16_t Size);

参数1:串口类型句柄,有CubeMX生成定义;
参数2:发送/接收的数据;
参数3:发送/接收的数据长度,接收时常设为1用于接收不定长度的数据

串口发送示例
因为我们一般在串口发送的时候并不需要做中断处理,因此其实使用哪个发送函数均可。

  char txt[20];
  int num = 0;
  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
    /* USER CODE END WHILE */
	sprintf(txt,"hello -%d\r\n",num);
	HAL_UART_Transmit_IT(&huart1,(uint8_t *)txt,strlen(txt));
	num++;
	HAL_Delay(500);
    /* USER CODE BEGIN 3 */
  }

串口接收示例
为了不占用系统时间,我们在串口接收的时候一般使用中断进行处理接收到的数据,因此流程如下:
1、使用HAL_UART_Receive_IT函数开启中断;
2、重写接收回调函数HAL_UART_RxCpltCallback;
3、执行完回调函数后重新使用HAL_UART_Receive_IT函数开启中断

void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
	//将接收的数据写入数组
	buf[no] = data;
	//接收一个字节数据
	HAL_UART_Receive_IT(huart,&data,1);
	//数组元素移位
	no++;
	//接收到回车时候将接收的数据发送出去并重新接收
	if(data == '\n')
	{
		HAL_UART_Transmit(huart,(uint8_t *)buf,strlen(buf),50);
		no = 0;
	}
}

注意:由于系统初始并未开启中断,因此需要在死循环前使用HAL_UART_Receive_IT函数进行中断第一次开启,后续的中断开启在回调函数中完成。

后记

至此,终于捋清楚了所谓的阻塞式和非阻塞式,所谓阻塞式就是当前函数占用系统CPU完成当前任务,在当前任务完成之前都会卡在该函数,所谓非阻塞式就是使用中断来完成当前任务。此外,HAL库的中断注册函数会取消中断使能需要格外注意。

  • 1
    点赞
  • 17
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值