文章目录
寄存器及自定义变量
状态寄存器
USART_SR
主要关注该状态寄存器的以下两位:TC与RXNE。
TC:发送完成状态位。若置位,则代表串口发送完成
RXNE:读数据寄存器非空。若置位,则代表串口接收到数据
USART_RX_BUF[USART_REC_LEN]
定义该项为数组,用于接收缓存
u16 USART_RX_STA
该项为用户定义的变量,在本程序中将其视为寄存器,各个位定义如下:
bit15:接收完成标志位
bit14:接收到0x0D的标志位
bit13~0:数据位
串口初始化
uart_init(u32 bound)
void uart_init(u32 bound)
{
//GPIO端口设置
GPIO_InitTypeDef GPIO_InitStructure;
USART_InitTypeDef USART_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART1|RCC_APB2Periph_GPIOA, ENABLE); //使能USART1,GPIOA时钟
//USART1_TX GPIOA.9
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9; //PA.9
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP; //复用推挽输出
GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化GPIOA.9
//USART1_RX GPIOA.10初始化
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;//PA10
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;//浮空输入
GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化GPIOA.10
//Usart1 NVIC 配置
NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority=3 ;//抢占优先级3
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; //子优先级3
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道使能
NVIC_Init(&NVIC_InitStructure); //根据指定的参数初始化VIC寄存器
//USART 初始化设置
USART_InitStructure.USART_BaudRate = bound;//串口波特率
USART_InitStructure.USART_WordLength = USART_WordLength_8b;//字长为8位数据格式
USART_InitStructure.USART_StopBits = USART_StopBits_1;//一个停止位
USART_InitStructure.USART_Parity = USART_Parity_No;//无奇偶校验位
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//无硬件数据流控制
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; //收发模式
USART_Init(USART1, &USART_InitStructure); //初始化串口1
USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);//开启串口接受中断
USART_Cmd(USART1, ENABLE); //使能串口1
}
串口中断函数
USART1_IRQHandler(void)
void USART1_IRQHandler(void) //串口1中断服务程序
{
u8 Res;
if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET) //接收中断(接收到的数据必须是0x0d 0x0a结尾)
{
Res =USART_ReceiveData(USART1); //读取接收到的数据
if((USART_RX_STA&0x8000)==0)//接收未完成
{
if(USART_RX_STA&0x4000)//接收到了0x0d
{
if(Res!=0x0a)
{
USART_RX_STA=0;//接收错误,重新开始
}
else
{
USART_RX_STA|=0x8000; //接收完成了
}
}
else //还没收到0X0D
{
if(Res==0x0d)
{
USART_RX_STA|=0x4000;
}
else
{
USART_RX_BUF[USART_RX_STA&0X3FFF]=Res ;
USART_RX_STA++;
if(USART_RX_STA>(USART_REC_LEN-1))
{
USART_RX_STA=0;//接收数据错误,重新开始接收
}
}
}
}
}
}
代码运行逻辑:
首先判断状态寄存器USART_SR的RXNE状态,若置位,则代表接收到数据;
然后将接收到的数据放入Res中;
然后判断接收是否完成:根据自定义的变量USART_RX_STA的bit15和bit14位是否为1来判断是否接收到了回车键,若接收到了回车键,则接收完成,跳出中断函数。若没有接收完成,则将Res中的数据放入自定义数组USART_RX_BUF[]中,数组位数为USART_RX_STA&0X3FFF(USART_RX_STA的bit0~bit13位代表数据长度,bit14和bit15位为回车标志位)。
主函数
if(USART_RX_STA&0x8000)
{
len=USART_RX_STA&0x3fff;//得到此次接收到的数据长度
printf("\r\n您发送的消息为:\r\n\r\n");
for(t=0;t<len;t++)
{
USART_SendData(USART1, USART_RX_BUF[t]);//向串口1发送数据
while(USART_GetFlagStatus(USART1,USART_FLAG_TC)!=SET);//等待发送结束
}
printf("\r\n\r\n");//插入换行
USART_RX_STA=0;