STM32 USART串口通信 综合练习

USART(通用同步/异步串行接收/发送器)串口通信具有以下特点:

  • 全双工操作:设备之间可以同时进行数据的发送和接收。
  • 异步通信:不需要共同的时钟信号,双方设备有各自的时钟。
  • 单端信号:使用一根线传输信号,通常需要地线作为参考。
  • 点对点通信:仅支持两个设备之间的直接通信。

USART串口通信的参数

  • 波特率:单位时间内传输的码元数量,决定了数据传输速率。
  • 起始位:标志数据帧的开始,通常为低电平。
  • 数据位:数据帧的有效载荷,常见为8位。
  • 校验位:用于数据验证,可以位于数据帧的最后一位。
  • 停止位:标志数据帧的结束,通常为高电平。

USART串口通信的优缺点

优点

  • 简单易用:不需要统一的时钟线,接线方便。
  • 广泛的应用:由于其简单性和灵活性,被广泛应用于各种嵌入式系统和物联网设备中。

缺点

  • 电气接口不统一:不同处理器使用的电平存在差异,直接相连可能会损伤器件。
  • 抗干扰能力差:TTL信号的抗干扰能力较差,数据在传输过程中容易出错。
  • 通信距离短:由于抗干扰能力差,通信距离通常限制在一个电路板上的两个芯片之间。

tim.c配置

#include "stm32f10x.h"

#include "led.h"

void Tim_init(u16 arr,u16 psc){

TIM_TimeBaseInitTypeDef Tim2;

NVIC_InitTypeDef NVIC_Initx;

//1、开启定时器2时钟

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2,ENABLE); //开启TIM2时钟

//2、定时器初始化

Tim2.TIM_Period = arr; //自动装载值 装载值10000-1

Tim2.TIM_CounterMode=TIM_CounterMode_Up; //计数模式 向上计数

Tim2.TIM_ClockDivision=TIM_CKD_DIV1; //时钟分割是输入捕获用的,故这里随便给

Tim2.TIM_Prescaler=psc; //预分频值 7200-1

TIM_TimeBaseInit(TIM2,&Tim2);

//3、打开更新中断

TIM_ITConfig(TIM2,TIM_IT_Update,ENABLE); //此处有中断

//4、优先级 有中断就有中断优先级

NVIC_Initx.NVIC_IRQChannel = TIM2_IRQn; //配置目标:中断线0

NVIC_Initx.NVIC_IRQChannelCmd = ENABLE;

NVIC_Initx.NVIC_IRQChannelPreemptionPriority = 1; //设置抢占优先级

NVIC_Initx.NVIC_IRQChannelSubPriority = 2; //设置响应优先级

NVIC_Init(&NVIC_Initx);

//5、启动定时器

TIM_Cmd(TIM2,ENABLE);

}

//构建中断服务函数,在.s启动文件中找

void TIM2_IRQHandler()

{

//交替闪烁

//如果B5输出为1 则B5输出为0 E5输出1

if(GPIO_ReadOutputDataBit(GPIOB,GPIO_Pin_5))

{

LED1_ON;

LED2_OFF;

}

else //如果B5输出为0 则B5输出为1 E5输出0

{

LED2_ON;

LED1_OFF;

}

// 否则B5输出为1 E5输出为0

//清除中断标记位 如何已经触发过来,再次使用不清除就一直是触发过后的高电平

TIM_ClearITPendingBit(TIM2,TIM_IT_Update);

}

tim.h配置

#ifndef __TIM_H

#define __TIM_H

#include "stm32f10x.h"

void Tim_init(u16 arr,u16 psc);

#endif

usart.c配置

#include "stm32f10x.h"

#include "usart.h"

void Usart_Init(int bsp)

{

GPIO_InitTypeDef Initx;

NVIC_InitTypeDef NVIC_Initx;

USART_InitTypeDef USART_Initx;

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_AFIO|RCC_APB2Periph_USART1,ENABLE);//开io时钟

//1、io设置 A9复用推挽和A10浮空 复用

//初始化 A9复用推挽 A10浮空 复用

Initx.GPIO_Mode = GPIO_Mode_AF_PP;

Initx.GPIO_Pin = GPIO_Pin_9;

Initx.GPIO_Speed = GPIO_Speed_50MHz;

GPIO_Init(GPIOA,&Initx);//A9复用推挽

Initx.GPIO_Mode = GPIO_Mode_IN_FLOATING;

Initx.GPIO_Pin = GPIO_Pin_10;

Initx.GPIO_Speed = GPIO_Speed_50MHz;

GPIO_Init(GPIOA,&Initx);//A10浮空 复用

//2、开串口1时钟

//3、设置串口1的工作方式

USART_Initx.USART_Mode = USART_Mode_Tx | USART_Mode_Rx;//输入和输出

USART_Initx.USART_Parity = USART_Parity_No;//无奇偶校验 Even偶校验 Odd奇校验

USART_Initx.USART_StopBits = USART_StopBits_1;//帧结尾传输一个停止位

USART_Initx.USART_WordLength = USART_WordLength_8b;//9位数据位

USART_Initx.USART_BaudRate = bsp;//波特率

USART_Initx.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//硬件流控制

USART_Init(USART1,&USART_Initx);

//4、打开串口的 "接收" 数据中断

USART_ITConfig(USART1,USART_IT_RXNE,ENABLE);//接收中断

//5、设置中断优先级

NVIC_Initx.NVIC_IRQChannel = USART1_IRQn;//配置目标USART1 全局中断

NVIC_Initx.NVIC_IRQChannelCmd = ENABLE;

NVIC_Initx.NVIC_IRQChannelPreemptionPriority = 2; //设置抢占优先级

NVIC_Initx.NVIC_IRQChannelSubPriority = 2; //设置响应优先级

NVIC_Init(&NVIC_Initx);

//6、启动串口

USART_Cmd(USART1,ENABLE);

}

void USART1_IRQHandler()

{

u16 data;

if(USART_GetITStatus(USART1,USART_IT_RXNE)) //是接收中断就触发此条件

{

data = USART_ReceiveData(USART1);//读数据

USART_SendData(USART1,data);//把data数据发出去

USART_ClearITPendingBit(USART1,USART_IT_RXNE);//清除中断标记位

}//可能有多个原因引起串口中断

//else if(xxx中断)

}

usart.h文件配置

#ifndef __USART_H

#define __USART_H

#include "stm32f10x.h"

void Usart_Init();

#endif

main.c配置

#include "stm32f10x.h"

#include "tim.h"

#include "usart.h"

int main()

{

u16 data;

u8 num[6],i = 0;

//中断分组

NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);

Tim_init(999,8999);

Usart_Init(115200);

//delay_init();

//编写程序功能

//BEEP_ON;

while(1){;

//读取定时器的当前值

data = TIM_GetCounter(TIM2);

i = 0;

//拆分当前值

while(data)

{

num[++i] = data %10;//把个位放入数组中保存

data = data / 10;//去掉当前数的个位

}

//发送当前值

for(;i>=1;i--)

{

USART_SendData(USART1,num[i]+'0');

while(USART_GetFlagStatus(USART1,USART_FLAG_TXE)==0);

}

//发完一组数据,换行

USART_SendData(USART1,'\r');

while(USART_GetFlagStatus(USART1,USART_FLAG_TXE)==0);

USART_SendData(USART1,'\n');

while(USART_GetFlagStatus(USART1,USART_FLAG_TXE)==0);

}

return 0;

}

运行结果:

总结

USART 是一种功能强大的串行通信接口,广泛应用于各种嵌入式系统和物联网设备中。通过合理配置 USART 参数,可以实现高效、稳定的数据传输。

相关推荐
wenchm9 小时前
细说STM32F407单片机SPI基础知识
stm32·单片机·嵌入式硬件
jikuaidi6yuan10 小时前
STM32 ADC 配置
stm32·单片机·嵌入式硬件
Be Legendary-CGK12 小时前
有源模拟滤波器的快速设计
嵌入式硬件·硬件工程
Anin蓝天(北京太速科技-陈)12 小时前
204-基于Xilinx Virtex-6 XC6VLX240T 和TI DSP TMS320C6678的信号处理板
嵌入式硬件·fpga开发·信号处理
Jack电子实验室12 小时前
STM32 出租车计价器系统设计(一) 江科大源码改写
c语言·stm32·单片机·嵌入式硬件·嵌入式
腾飞的信仰13 小时前
51单片机 串口UART
单片机·嵌入式硬件·51单片机
电子科技圈13 小时前
XMOS将在CES 2025上展出多款由边缘AI驱动的创新音效、音频、识别和处理解决方案
人工智能·科技·嵌入式硬件·mcu·物联网·音视频·iot
lantiandianzi14 小时前
基于单片机的输液速度监控系统设计
单片机·嵌入式硬件
紫阡星影14 小时前
【模块系列】STM32&PCF8563
c语言·stm32·单片机·嵌入式硬件
憧憬一下16 小时前
深入解析PCIe设备事务层与配置过程
arm开发·嵌入式硬件·嵌入式·pcie·linux驱动开发