3. UART工作原理:帧格式、波特率与收发时序

UART(Universal Asynchronous Receiver/Transmitter,通用异步收发器)是嵌入式系统中最基础、最广泛使用的串行通信协议之一。它的核心价值在于:仅需两根信号线(TX、RX)即可实现全双工通信,且不需要独立的时钟线。这种“异步”特性意味着收发双方必须事先约定好通信速率(波特率)和数据帧结构,否则无法正确解析数据。本章将深入拆解UART帧格式的每一位含义、波特率的计算与误差容忍度,以及发送与接收的完整时序逻辑,帮助读者建立从物理层到协议层的完整认知。

UART 异步帧结构与收发时序 帧结构(8N1格式示例) 起始位 0 (低电平) D0 LSB D1 D2 D3 D4 D5 D6 D7 MSB 校验位 停止位 (1/1.5/2) 空闲态: 高电平 波特率与位时间 波特率 = 每秒传输的码元数 (bps) 位时间 T_bit = 1 / 波特率 例: 9600bps → T_bit ≈ 104.17μs 例: 115200bps → T_bit ≈ 8.68μs 发送/接收时序逻辑(发送0x55 = 01010101b) TX RX 起始 D0=1 D1=0 D2=1 D3=0 D4=1 D5=0 D6=1 D7=0 停止 接收方在每个位时间的中心点采样(如箭头↓所示),确保避开信号跳变沿

上图展示了UART通信中最核心的帧结构与时序关系。左侧为8N1格式(8个数据位、无校验、1个停止位)的帧布局,右侧为波特率与位时间的换算关系,下方则给出了发送0x55(二进制01010101)时TX与RX线上的实际电平跳变。可以看到,UART的每一帧都以一个下降沿(高电平跳变到低电平)作为起始标志,随后依次传输数据位(LSB在前),最后以高电平的停止位结束。接收方通过检测下降沿来同步时钟,并在每个位时间的中心点进行采样,从而保证数据解析的可靠性。

3.1 UART帧格式:每一位都有明确职责

核心原理:帧是UART传输的最小完整单元

UART协议将数据封装为固定格式的“帧”(Frame),每一帧由起始位、数据位、校验位(可选)和停止位组成。这种设计使得接收方无需外部时钟即可从数据流中提取同步信息。帧格式的每一位都有其特定作用:

  • 起始位(Start Bit):始终为逻辑0(低电平),占用1个位时间。当TX线从空闲态(高电平)跳变为低电平时,接收方即认定一帧数据开始。起始位的下降沿是接收方进行时钟同步的关键触发点。
  • 数据位(Data Bits):通常为5~8位,常见配置为8位。数据位紧跟在起始位之后,按照最低有效位(LSB)先行的顺序逐位发送。例如发送字节0x55(01010101b),先发送D0(1),最后发送D7(0)。
  • 校验位(Parity Bit):可选字段,用于简单的错误检测。偶校验(Even Parity)保证包括校验位在内的“1”的个数为偶数;奇校验(Odd Parity)则保证为奇数。无校验(None)时该位被省略,帧长度相应缩短。
  • 停止位(Stop Bit):始终为逻辑1(高电平),长度可为1、1.5或2个位时间。停止位不仅标志一帧结束,还保证了帧与帧之间至少有一个高电平的间隔,为下一帧的起始位下降沿提供明确的电平跳变基础。
帧字段电平状态位宽作用常见配置
起始位低电平 (0)1 bit同步信号,触发接收固定为1位
数据位0/1 可变5~8 bit承载有效数据8位最常用
校验位0/1 可变0 或 1 bit错误检测无/奇/偶校验
停止位高电平 (1)1/1.5/2 bit帧结束标志1位最常用

判断方法:如何根据需求选择帧格式

在实际工程中,帧格式的选择需要综合考虑数据量、错误检测需求和兼容性。判断流程如下:

  1. 确定数据位宽度:传输标准ASCII字符选7位,传输二进制数据或汉字编码选8位。8位是绝大多数场景的默认选择。
  2. 决定是否需要校验:如果通信环境电磁干扰较小、数据可靠性要求一般,可省略校验位(N);如果链路较长或干扰明显,建议启用偶校验(E),因为偶校验便于硬件实现且能检测出奇数个位错误。
  3. 选择停止位长度:默认选1位。若接收端时钟精度较差或波特率较高,可选用2位停止位以增加容错时间。
经验提醒:在Modbus RTU等工业协议中,帧格式通常固定为8N1(8数据位、无校验、1停止位)或8E1(8数据位、偶校验、1停止位)。与设备通信前,务必查阅其数据手册确认帧格式,否则即使波特率正确也无法解析数据。

案例拆解:解析一帧实际数据

假设某传感器以9600bps、8N1格式发送数据0x3A(二进制00111010)。我们分析其帧结构:

  • 起始位:1位低电平(0)
  • 数据位:8位,LSB先行,依次为 D0=0, D1=1, D2=0, D3=1, D4=1, D5=1, D6=0, D7=0
  • 校验位:无(N)
  • 停止位:1位高电平(1)

因此,TX线上实际电平序列为:0 0 1 0 1 1 1 0 0 1(从左到右依次为起始位、D0~D7、停止位)。接收方在检测到下降沿后,等待1.5个位时间(即起始位中心点)开始采样,之后每隔1个位时间采样一次,共采样8次得到数据位,再采样1次确认停止位为高电平,从而完成一帧的接收。

常见误区与总结

风险提示:初学者常误以为数据位是MSB先行,导致解析出的字节高低位颠倒。UART协议明确规定LSB先行,例如发送0x01时,线上先出现的是D0=1,而非D7=1。此外,停止位不是“空闲位”,它属于帧的一部分,接收方必须检测到停止位为高电平才认为帧有效;若停止位为低电平,则产生“帧错误”(Framing Error)。

3.2 波特率:通信速率的约定与计算

核心原理:波特率决定位时间

波特率(Baud Rate)定义为每秒传输的码元(符号)数量,单位是bps(bits per second)。在UART中,每个码元携带1比特信息,因此波特率等于比特率。波特率的倒数即位时间(Bit Time),即传输1位所需的时间:

位时间 T_bit = 1 / 波特率
示例:
波特率 9600 bps → T_bit = 1/9600 ≈ 104.17 μs
波特率 115200 bps → T_bit = 1/115200 ≈ 8.68 μs

收发双方必须使用相同的波特率。实际系统中,波特率由UART外设的时钟分频产生。例如STM32的USART模块,其波特率寄存器BRR的值由公式 BRR = fck / (16 × 波特率) 计算得出,其中fck为外设时钟频率。

判断方法:波特率误差的容忍范围

由于收发双方的时钟源存在误差,实际波特率不可能完全一致。UART接收方在每个位时间的中心点采样,只要误差不超过半个位时间,就能正确采样。工程上要求收发双方的波特率误差控制在±2%以内,对于高速通信(如921600bps以上),建议误差小于±1%。误差来源包括:

  • 晶振本身的频率误差(通常为±20ppm~±50ppm)
  • 分频系数取整带来的量化误差
  • 温度漂移导致的频率变化

计算实际波特率的方法:假设系统时钟为16MHz,目标波特率9600bps,则BRR = 16e6 / (16 × 9600) = 104.17,取整为104,实际波特率 = 16e6 / (16 × 104) = 9615.38bps,误差 = (9615.38 - 9600) / 9600 ≈ 0.16%,在允许范围内。

实战要点:在调试串口通信时,如果出现乱码但帧格式正确,优先检查波特率是否匹配。使用逻辑分析仪测量实际位时间,与理论值对比,可快速定位波特率偏差问题。

案例拆解:跨平台波特率匹配

某项目需要将MCU(系统时钟8MHz)与PC(USB转串口芯片)通信,目标波特率115200bps。MCU端计算BRR = 8e6 / (16 × 115200) = 4.34,取整为4,实际波特率 = 8e6 / (16 × 4) = 125000bps,误差高达8.5%,远超容忍范围。此时应调整系统时钟或使用非标准分频。解决方案:将MCU系统时钟改为7.3728MHz(该频率可精确分频出常用波特率),BRR = 7.3728e6 / (16 × 115200) = 4,实际波特率恰好为115200bps,误差为0%。

常见误区与总结

风险提示:不要盲目追求高波特率。波特率越高,位时间越短,对线路质量、电平转换芯片的压摆率、接收端采样时钟精度的要求越高。在长线传输或强干扰环境下,过高的波特率会导致误码率急剧上升。建议根据通信距离和线缆质量选择:1米以内可尝试1Mbps以上,10米级建议不超过115200bps,更长距离则应考虑RS-485并降低波特率。

3.3 发送与接收的时序逻辑

核心原理:发送与接收的完整流程

发送时序:发送端在TX线空闲时保持高电平。当CPU将数据写入UART发送寄存器(TDR)后,发送移位寄存器(TSR)在波特率时钟驱动下逐位移出数据。首先输出起始位(低电平),然后依次输出数据位(LSB先行),接着输出校验位(若启用),最后输出停止位(高电平)。发送完成后,TX线恢复空闲高电平,并置位发送完成标志(TC)。

接收时序:接收端持续监测RX线电平。当检测到下降沿(高→低跳变)时,启动接收过程。为避免噪声干扰,接收方通常在起始位的中心点(即1.5个位时间后)再次确认电平仍为低,才认定是有效起始位。随后,在每个数据位的中心点采样,共采样8次(或5~7次,取决于数据位宽度),得到数据字节。最后采样停止位,若为高电平则帧有效,数据被移入接收数据寄存器(RDR),并置位接收完成标志(RXNE)。

阶段发送端动作接收端动作关键标志
空闲TX保持高电平RX等待下降沿—
起始位TX拉低1个位时间检测下降沿,1.5位后确认检测到起始位
数据位逐位输出D0~D7每位中心点采样移位寄存器工作
校验位输出校验值(可选)采样并校验校验错误标志PE
停止位TX拉高1个位时间采样确认高电平帧错误标志FE
完成置位TC置位RXNE,数据可读TC / RXNE

判断方法:如何诊断时序异常

当通信异常时,可通过以下步骤定位时序问题:

  1. 检查空闲电平:用示波器测量TX/RX线,空闲时应为高电平。若空闲为低电平,说明线路接反或芯片配置错误。
  2. 观察起始位:发送数据时,应能看到明显的下降沿。若无下降沿,说明数据未写入发送寄存器或波特率配置错误。
  3. 测量位时间:用示波器测量连续两个下降沿之间的时间间隔,与理论位时间对比。若偏差超过5%,检查时钟配置。
  4. 验证停止位:停止位应为高电平。若停止位为低,接收端会报帧错误(FE),检查波特率误差或线路干扰。

案例拆解:一次典型的乱码排障

背景:某物联网网关通过UART与4G模块通信,波特率115200,8N1。设备上电后,网关收到的数据全部为乱码。

排查过程:

  • 第一步:用逻辑分析仪抓取TX线波形,发现帧格式正确(起始位、8个数据位、停止位),但测量位时间约为9.2μs,理论值应为8.68μs,误差约6%。
  • 第二步:检查网关MCU的系统时钟配置,发现外部晶振为12MHz,但软件中误配置为11.0592MHz,导致波特率分频计算错误。
  • 第三步:修正时钟配置后,位时间恢复为8.68μs,通信恢复正常。

复盘经验:乱码问题90%以上源于波特率不匹配或时钟配置错误。排查时应先验证物理层波形,再检查软件配置,避免盲目修改协议。

常见误区与总结

风险提示:接收方在起始位检测时,仅凭一个下降沿就启动接收是不可靠的。若线路存在毛刺干扰,可能导致误触发。成熟的UART外设(如STM32的USART)会在起始位中心点再次采样确认,若此时电平不为低,则取消本次接收。在软件模拟UART时,务必实现此“二次确认”逻辑,否则抗干扰能力极差。
本章核心要点回顾:① UART帧由起始位(低电平)、数据位(LSB先行)、可选校验位和停止位(高电平)组成;② 波特率决定位时间,收发双方误差需控制在±2%以内;③ 发送时序以TX线拉低为起点,接收时序以检测下降沿为起点,并在位中心采样;④ 排障时优先检查空闲电平、起始位下降沿、位时间和停止位电平。