首页 > 其他分享 >STM32学习(USART通信协议)

STM32学习(USART通信协议)

时间:2024-06-05 17:32:39浏览次数:18  
标签:USART 通信协议 通信 STM32 包尾 串口 波特率 数据

        本文章时本人根据江科大视频所记录的笔记,希望对大家的学习能提供帮助。

1.通信接口

通信的目的:将一个设备的数据传送到另一个设备,扩展硬件系统(stm32内部芯片无法得到的数据,需要连接外部芯片获取)
通信协议:制定通信的规则,通信双方按照协议规则进行数据收发

USART:TX(数据发送脚)、RX(数据接收脚)

I2C:SCL(时钟)、SDA(数据)

SPI:SCLK(时钟)、MOSI(主机输出数据脚)、MISO(主机输入数据脚)、CS(片选,指定通信的对象)

CAN:CAN_H、CAN_L(差分数据脚,用两个引脚表示一个差分数据)

USB:DP、DM(一对差分数据脚)

双工特性:全双工就是指通信双方能够同时进行双向通信,一般来说,全双工的通信都有两根通信线,发送线路和接收线路互补影响;半双工只用一根数据线;单工是指数据只能从一个设备到另一个设备,而不能反着来。

时钟特性:I2C和SPI有单独的时钟线,所以它们是同步的,接收方可以在时钟信号的指引下进行采样;剩下的串口、CAN、USB没有时钟线,所以双方约定一个采样频率,就是异步通信,并且还要加一些帧头帧尾等,进行采样位置的对齐。

电平特性:上面3个都是单端信号,就是它们的引脚的高低电平都是对GND的电压差,所以单端信号通信的双方必须要共地,就是把GND、接在一起,所以说这里通信的引脚,前三个还应该加一个GND引脚,不接GND无法通信;后面的CAN和USB是差分信号,它是靠两个差分引脚的电压差来传输信号的是差分信号,在通信时可以不需要GND(不过USB协议里面也有一些地方需要单端信号,所以USB、还需要共地),使用差分信号可以极大地提高抗干扰能力,所以差分信号一般传输速度和距离都会非常高。

设备特性:点对点通信就直接传输数据就可以了;多设备通信需要有一个寻址的过程,以确定通信的对象。

2.串口的通信协议

2.1 串口通信

        串口是一种应用十分广泛的通讯接口,串口成本低、容易使用、通信线路简单,可实现两个设备的互相通信
        单片机的串口可以使单片机与单片机、单片机与电脑、单片机与各式各样的模块互相通信,极大地扩展了单片机的应用范围,增强了单片机系统的硬件实力

2.2 硬件电路

        下面的三根线必须连接(TX接RX、RX接TX、GND接GND,TX与RX要交叉连接),上方的VCC如果有单独供电可以不用连接,但没有供电时需要单独连接。当只需单向的数据传输时,可以只接一根通信线,当电平标准不一致时,需要加电平转换芯片。

电平标准:

电平标准是数据1和数据0的表达方式,是传输线缆中人为规定的电压与数据的对应关系,串口常用的电平标准有如下三种:

TTL电平:+3.3V或+5V表示1,0V表示0
RS232电平:-3~-15V表示1,+3~+15V表示0
RS485电平:两线压差+2~+6V表示1,-2~-6V表示0(差分信号)

2.3 串口参数及时序

波特率:串口通信的速率
起始位:标志一个数据帧的开始,固定为低电平
数据位:数据帧的有效载荷,1为高电平,0为低电平,低位先行
校验位:用于数据验证,根据数据位计算得来
停止位:用于数据帧间隔,固定为高电平

3.USART串口通信

3.1 串口简介

USART是STM32内部集成的硬件外设,可根据数据寄存器的一个字节数据自动生成数据帧时序,从TX引脚发送出去,也可自动接收RX引脚的数据帧时序,拼接为一个字节数据,存放在数据寄存器里
自带波特率发生器,最高达4.5Mbits/s
可配置数据位长度(8/9)、停止位长度(0.5/1/1.5/2)
可选校验位(无校验/奇校验/偶校验)
支持同步模式、硬件流控制、DMA、智能卡、IrDA、LIN

3.2 USART基本结构

        最左边的是波特率发生器,用于产生约定的通信速率,时钟来源是PCLK2或1,经过波特率发生器分频后,产生的时钟通向发送控制器和接收控制器,发送控制器和接收控制器,用来控制发送移位和接受移位,之后,由发送数据寄存器和发送移位寄存器这两个寄存器的配合,将数据一位移位地移出去,通过GPIO地复用输出,输出到TX引脚残生串口协议规定地波形(右移的符号就是表示这个移位寄存器是往右移的,是低位先行),当数据由数据巨蠢器移位到移位寄存器时,会置一个TXE的标志位,通过判断这个标志位就可以知道是不是可以写下一个数据了。然后接受部分也是类似的,RX引脚的波形,通过GPIO输入,在接收控制器的控制下,一位一位地移入接收移位寄存器(也是右移),因为时地位先行,所以要从左边开始移进来,移完一帧数据后,数据就会统一运到接受数据寄存器,在转移的同时,置一个RXNE标志位,通过检查这个标志位就知道是否接收到数据,同时这个标志位可以申请标志位,在接收到数据时,直接进入中断函数,然后快速地读取和保存数据。

3.3 波特率发生器

发送器和接收器的波特率由波特率寄存器BRR里的DIV确定
计算公式:波特率 = fPCLK2/1 / (16 * DIV)     (因为内部有一个16倍波特率地采样时钟,所以输入时钟/DIV要等于16倍地波特率)

DIV(分频系数),分为整数部分和小数部分,可以实现更细腻地分频
 

3.4 USART配置

1.开启时钟,把需要用的USART和GPIO的时钟打开

2.GPIO初始化,把TX配置成复用输出,RX配置成输入

3.配置USART

USART_InitTypeDef USART_InitStructure;                  
USART_InitStructure.USART_BaudRate              //波特率USART_InitStructure.USART_HardwareFlowControl    //硬件流控制,不需要
USART_InitStructure.USART_Mode   //模式,发送模式和接收模式
USART_InitStructure.USART_Parity      //奇偶校验
USART_InitStructure.USART_StopBits   //停止位
USART_InitStructure.USART_WordLength;        //字长

USART_Init(USART1, &USART_InitStructure);

4.配置中断(如果只有发送就不需要配置)

3.5 USART串口文本

数据包的作用:将一个个单独的数据给打包起来,方便我们进行多字节的数据通信,把属于同一批的数据进行打包和分割,方便接收方识别

串口数据包,通常使用的是额外添加包头包尾的方式

HEX数据包:优点是传输最直接,解析数据非常简单,比较适合一些模块发送原始的数据;缺点灵活性不足、载荷和包头包尾重复

文本数据包:优点是数据直观理解,非常灵活,比较适合一些输入指令进行人机交互的场合:缺点是解析效率低

问题1:包头包尾和数据载荷重复

解决办法:

1.如果可以的话,我们可以在发送的时候,对数据进行限幅

2.如果无法避免载荷数据和包头包尾重复,那我们就经量使用固定长度的数据包

3.增加包头包尾的数量,并且让它尽量呈现出载荷数据出现不了的状态

问题2:包头包尾并不完全需要

但是有了包尾,无论数据怎么变化,都可以分辨出包头包尾的

问题3:固定包长和可变包场选择的问题

 如果载荷会出现和包头包尾重复的情况,最好使用固定包长,避免接收错误

如果载荷不会出现和包头包尾重复,可以选择可变包长

问题4:各种数据转换为字节流的问题

用Uin8_t的指针指向它,把它们当作一个字节数组发送

数据包接收:

        每收到一个字节,程序都会进一遍中断,在中断函数里,可以拿到一个字节,拿到后退出中断,所以每拿到一个数据都是一个独立的过程,而对于数据包来说,它具有前后关联性,包头之后是数据,数据之后是包尾,对于包头数据包尾三种状态,需要不同的处理逻辑,在程序中设计一个能记住不同状态的机制,在不同状态执行不同状态的操作,同时话要进行状态的合理转移,这种程序思维,就叫做“状态机”。

4.附加

pintf函数移植

1.

int fputc(int ch, FILE *f)
{
    Serial_SendByte(ch);            //将printf的底层重定向到自己的发送字节函数
    return ch;
}

然后就可以在主函数中直接调用,但这样只能在一个串口使用。

2.

#include <stdarg.h>

void Serial_Printf(char *format, ...)
{
    char String[100];                //定义字符数组
    va_list arg;                    //定义可变参数列表数据类型的变量arg
    va_start(arg, format);            //从format开始,接收参数列表到arg变量
    vsprintf(String, format, arg);    //使用vsprintf打印格式化字符串和参数列表到字符数组中
    va_end(arg);                    //结束变量arg
    Serial_SendString(String);        //串口发送字符数组(字符串)
}

封装Sprintf函数

显示汉字:

1.

keil软件选择UTF-8编码,串口也要选择UTF-8编码

打开工程选项,C/C++,杂项控制栏写上 --no-multibyte-chars

2.

切换为GB2312编码

标签:USART,通信协议,通信,STM32,包尾,串口,波特率,数据
From: https://blog.csdn.net/2401_83265518/article/details/139423033

相关文章

  • stm32系列--同一定时器双通道捕获
     voidTIM3_Cap_Init(u16arr,u16psc)//定时器3通道2输入捕获配置{TIM_ICInitTypeDefTIM_ICInitStructure;TIM_TimeBaseInitTypeDefTIM_TimeBaseStructure;NVIC_InitTypeDefNVIC_InitStructure;GPIO_InitTypeDefGPIO_InitStructure;R......
  • stm32系列--低电平时间的测量
     TIM_ICInitTypeDefTIM2_ICInitStructure;voidTIM2_CH1_Cap_Init(u16arr,u16psc){GPIO_InitTypeDefGPIO_InitStructure;TIM_TimeBaseInitTypeDefTIM_TimeBaseStructure;NVIC_InitTypeDefNVIC_InitStructure;RCC_APB1Peri......
  • STM32H743 ADC+DMA
    1.**STM32CubeMX配置如下:**ADC:配置通道配置ADC的工作模式,这里用到了DMA使用ADC中断DMA2的通道4对应ADC2GPIO的配置,没有配置上下拉DMA配置:用STM32H743用DMA传输ADC的数据会有一个需要注意的点,需要将传输数据的buf配置在固定的某一段RAM中。#defineADC_CONVE......
  • USART串口协议
    一、通信接口1、通信的目的:将一个设备的数据传送到另一个设备,扩展硬件系统2、通信协议:制定通信的规则,通信双方按照协议规则进行数据收发二、串口通信1、串口是一种应用十分广泛的通讯接口,串口成本低、容易使用、通信线路简单,可实现两个设备的互相通信2、单片机的串口可以......
  • stm32系列--PWM捕获功能
      Capture_Init(59999,120-1);//可捕获最小频率72M/(120*60000)=17*0.6=10HzPA1//TIM2_CH2PA7做为捕获通道//输入捕获能捕获到的最小的频率为72M/{(ARR+1)*(PSC+1)}voidCapture_Init(u16arr,u16psc){GPIO_InitTypeDefGPIO_InitStructure;......
  • STM32F407 hal库FFT
    简介:本文所用开发板为立创天空星,主控芯片为STM32F407VET6,F407系列应该都能使用本文的方法。也推荐大家可以买一块立创天空星玩玩,很好用。1.设置调试模式为SWD调试2.将低速和高速时钟设置为外部时钟源3.时钟设置(按下图即可)4.设置ADC,可以和中断部分一起看注意DMA设定时......
  • 网络编程介绍(二)(端口、通信协议)
    端口标记正在计算机设备上运行的应用程序的,被规定为一个16位的二进制,范围是0~65535。分类周知端口:0~1023,被预先定义的知名应用占用(如:HTTP占用80,FTP占用21)注册端口:1024~49151,分配给用户进程或某些应用程序。动态端口:49152到65535,之所以称......
  • STM32:第一次写底层代码心得体会
    初次手敲stm32代码的心得体会在最开始的时候,是很迷茫的,不知道从何下手,寄存器的地址怎么找?总线地址在哪里?外设挂在那条总线上?等等问题。在参考了一篇博客(https://blog.csdn.net/k666499436/article/details/123800095?spm=1001.2014.3001.5501)后慢慢熟悉之后便清晰很多。......
  • STM32 - 串口通信(HAL库)
    为什么要用HAL库?使用方便,可以完全使用GUI配置、支持更多的芯片型号和开发板、良好的封装与抽象、Easy上手和开发有什么缺点?封装层次较高,造成稍微的性能损失STM32cubemx部分以使用stm32系列的NUCLEO-F03RB为例1.配置时钟选择STM32F103RCTx系列芯片,配置时钟的同时会......
  • STM32——ADC篇(ADC的使用)
    一、ADC的介绍 1.1什么是ADC        ADC(Analogto-DigitalConverter)模拟数字转换器,是将模拟信号转换成数字信号的一种外设。比如某一个电阻两端的是一个模拟信号,单片机无法直接采集,此时需要ADC先将短租两端的电压这个模拟信号转化成数字信号,单片机才能够进行处理。......