主题 | 内容 | 教学目的/扩展视频 |
---|---|---|
串口通信重点课程 |
什么是USART串口,电路原理,单片机内部寄存器,固件库说明。加载相关文件,驱动程序分析,printf的使用。什么是中断,中断的程序设计,还有哪些中断。 | 熟悉串口的使用,熟练使用printf函数。介绍printf函数的高级使用方法,介绍各中断。 |
师从洋桃电子,杜洋老师
▲ 回顾上期USART串口发送三大方案详解:从单字节到格式化输出 | 零基础入门STM32第三十四步
寄存器名称 | 关键位 | 功能描述 |
---|---|---|
USART_SR | RXNE | 接收寄存器非空标志(数据就绪) |
USART_DR | DR[8:0] | 数据存储寄存器 |
USART_CR1 | RXNEIE | 接收中断使能位 |
STM32 CH340C
PA9(TX) ---> RX
PA10(RX) ---> TX
GND ---> GND
//USART 初始化设置
...
USART_ITConfig(USART1, USART_IT_RXNE, DISABLE);//开启ENABLE/关闭DISABLE中断
uint8_t received_data;
...
//主程序
#include "usart.h"
int main (void){//主程序
u8 a;
//初始化程序
RCC_Configuration(); //时钟设置
USART1_Init(115200); //串口初始化(参数是波特率)
//主循环
while(1){
//查询方式接收
if(USART_GetFlagStatus(USART1,USART_FLAG_RXNE) != RESET){ //查询串口待处理标志位
a =USART_ReceiveData(USART1);//读取接收到的数据
printf("%c",a); //把收到的数据发送回电脑
}
delay_ms(1000); //延时
}
}
运行效果:
USART_GetFlagStatus()
:检测RXNE标志位(第5位)USART_ReceiveData()
:读取DR寄存器并自动清除RXNE标志优势 | 缺陷 |
---|---|
实现简单无需中断配置 | 实时性差(最高响应延迟=主循环周期) |
资源占用少 | 高波特率易丢数据(>57600bps时风险高) |
调试方便 | CPU利用率低 |
//USART 初始化设置
...
USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);//开启ENABLE/关闭DISABLE中断
...
//串口1中断服务程序(固定的函数名不能修改)
void USART1_IRQHandler(void){
u8 a;
if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET){ //接收中断(接收到的数据必须是0x0d 0x0a结尾)
a =USART_ReceiveData(USART1);//读取接收到的数据
printf("%c",a); //把收到的数据发送回电脑
}
}
// 主函数配置
int main (void){//主程序
RCC_Configuration(); //时钟设置
USART1_Init(115200); //串口初始化(参数是波特率)
while(1) {
// 主循环可执行其他任务
delay_ms(500);
}
}
运行效果:
▲ 完整工程代码示例⏬USART串口接收程序
#define BUFFER_SIZE 128
uint8_t rx_buffer[BUFFER_SIZE];
uint16_t rx_index = 0;
void USART1_IRQHandler(void) {
if(USART_GetITStatus(USART1, USART_IT_RXNE)) {
rx_buffer[rx_index++] = USART_ReceiveData(USART1);
if(rx_index >= BUFFER_SIZE) rx_index = 0; // 防止溢出
}
}
// 在stm32f10x_it.c中增加抢占优先级配置
NVIC_InitTypeDef NVIC_InitStructure;
NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0; // 最高优先级
NVIC_Init(&NVIC_InitStructure);
// 在中断服务函数首尾添加临界区保护
__disable_irq(); // 进入临界区
// 数据处理代码
__enable_irq(); // 退出临界区
// 在USART初始化后添加
DMA_InitTypeDef DMA_InitStructure;
DMA_DeInit(DMA1_Channel5);
DMA_InitStructure.DMA_PeripheralBaseAddr = USART1_DR_Base;
DMA_InitStructure.DMA_MemoryBaseAddr = (uint32_t)rx_buffer;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralSRC;
DMA_InitStructure.DMA_BufferSize = BUFFER_SIZE;
DMA_Init(DMA1_Channel5, &DMA_InitStructure);
USART_DMACmd(USART1, USART_DMAReq_Rx, ENABLE);
评估指标 | 查询模式(115200bps) | 中断模式(115200bps) |
---|---|---|
最大接收速率 | 560字节/秒 | 11,520字节/秒 |
CPU占用率 | 20% | 5%(空闲时) |
最小响应延迟 | 10ms | 8.68μs(1字节时间) |
多任务兼容性 | 差 | 优 |
实验建议:使用信号发生器发送不同速率的数据包,通过逻辑分析仪捕获实际响应时间
[1] 洋桃电子B站课程-STM32入门100步
[2] STM32F103xx官方数据手册
[3] STM32F103X8-B数据手册(中文)
[4] STM32F103固件函数库用户手册(中文)
[5] USART串口接收程序
[6] ASCII码表和转义字符
[7] DYS串口助手 V1
下期预告:下一期将探讨USART控制程序
重点课程
,欢迎持续关注!
点击查阅往期【STM32专栏】文章
版权声明:本文采用[CC BY-NC-SA 4.0]协议,转载请注明来源
实测开发版:洋桃1号开发版(基于STM32F103C8T6)
更新日志:
- v1.0 初始版本(2025-02-27)