STM32-RS485
一、先理清几个容易混淆的概念
学习 RS485 前,最容易混在一起的几个词是:串口、UART、TTL/CMOS、RS232、RS422、RS485。
串口是一个比较泛的说法。UART、RS232、RS422、RS485 都遵循类似的串行通信时序,因此平时经常被统称为“串口通信”。
UART 是 STM32 内部的串口外设,它负责产生串行通信时序,例如:
-
起始位
-
有效数据位
-
校验位
-
停止位
TTL/CMOS、RS232、RS422、RS485 则更偏向“接口电气标准”,也就是逻辑 1 和逻辑 0 在物理线路上怎么表示。

可以这样理解:
| 名称 | 重点 | 简单理解 |
|---|---|---|
| UART | 通信时序 | STM32 内部外设,产生 TX/RX 串口帧 |
| TTL/CMOS | 单端逻辑电平 | MCU 引脚直接输出的逻辑电平 |
| RS232 | 单端接口标准 | 常用于传统串口设备,电平范围和 MCU 不同 |
| RS422 | 差分接口标准 | 抗干扰能力强,常见一发多收结构 |
| RS485 | 差分接口标准 | 支持多节点总线,常用于工业控制 |
所以,STM32 想使用 RS485 通信时,并不是直接把 UART_TX、UART_RX 接到总线上,而是需要经过 RS485 收发器完成电平和信号形式转换。
二、RS485 是什么
RS485 是一种串行通信接口标准,使用差分信号进行传输。它常用于工业控制、仪表采集、楼宇控制、远距离设备互联等场景。
RS485 的主要特点:
-
差分信号传输,抗干扰能力强
-
接口电平较低,不容易损坏芯片
-
传输速率较高
-
传输距离远
-
支持多个节点挂接在同一条总线上
-
常和 Modbus 等上层协议配合使用
RS485 的强项不是“协议复杂”,而是“物理层可靠”。在噪声较多、线缆较长、设备较分散的环境里,RS485 比普通 TTL 串口更适合。
三、差分信号为什么抗干扰
普通 TTL 串口是单端信号,接收端判断某一根线相对地的电平高低。线缆较长或现场干扰较强时,地电位差、共模噪声都可能影响判断。
RS485 使用 A、B 两根线传输一对相反的差分信号。接收端关心的不是某一根线对地电压,而是 A、B 两线之间的电压差。
逻辑关系可以概括为:
| 逻辑状态 | 差分电压含义 |
|---|---|
| 逻辑 1 | 差分电压为正,约 +(2~6)V |
| 逻辑 0 | 差分电压为负,约 -(2~6)V |
实际学习时,不必死记某个芯片在所有条件下的精确电压值,先抓住核心:接收器看的是两根线的差值,因此同向叠加到两根线上的干扰会被很大程度抵消。
四、RS485 总线结构
RS485 通常通过收发器芯片把 STM32 的 UART 信号转换为 A/B 差分总线信号。常见结构如下:

图中可以看到:
-
STM32 侧仍然使用 UART 的 TX、RX
-
中间的 TP8485/SP3485 等芯片负责电平转换和总线驱动
-
总线侧使用 A、B 两根差分线
-
多个节点可以挂在同一条 A/B 总线上
-
总线两端通常需要终端匹配电阻
RS485 总线连接时要特别关注匹配电阻。匹配电阻的作用是提高总线稳定性、抑制反射和噪声。线缆较长、通信速率较高、节点较多时,这一点尤其重要。
实际布线还要注意:
-
A/B 极性要统一,不能一端接反
-
总线拓扑尽量使用一条主干线,减少过长分支
-
线缆建议使用双绞线
-
远距离通信要考虑共地、隔离和浪涌保护
-
多节点通信时,上层协议要解决地址和总线仲裁问题
五、RS485 与 Modbus 的关系
RS485 只规定物理接口和电气传输方式,它本身不规定“谁发给谁”“数据是什么意思”“从机地址是多少”。
Modbus 是常见的上层通信协议,可以运行在 RS485 总线上。很多工业设备说“支持 RS485”,实际使用时往往还会说“支持 Modbus RTU”。
二者关系可以这样分:
| 层次 | 作用 |
|---|---|
| RS485 | 解决电气传输:差分信号、长距离、多节点 |
| UART | 提供串行时序:起始位、数据位、校验位、停止位 |
| Modbus RTU | 定义数据帧:地址、功能码、寄存器、CRC 校验 |
也就是说,RS485 让数据能可靠地在总线上传输,Modbus RTU 决定这些数据应该如何组织和解释。
六、TP8485 收发器引脚说明
STM32 使用 RS485 时,常见做法是外接 485 电平转换芯片,例如 TP8485、SP3485 等。
TP8485 常见引脚含义如下:
| 引脚 | 含义 | 说明 |
|---|---|---|
| RO | Receiver Output | 接收器输出端,通常接 STM32 的 UART_RX |
| RE | Receiver Enable | 接收器输出使能,低电平有效 |
| DE | Driver Enable | 驱动器输出使能,高电平有效 |
| DI | Driver Input | 驱动器输入端,通常接 STM32 的 UART_TX |
| A | Bus A | 接收器输入端 / 驱动器输出端 |
| B | Bus B | 接收器输入端 / 驱动器输出端 |

其中最关键的是 RE 和 DE。
RS485 常见半双工通信中,发送和接收共用 A/B 两根线。为了避免多个节点同时驱动总线,需要通过 DE、RE 控制当前节点处于发送状态还是接收状态。
常见控制方式:
| 工作模式 | DE | RE | 状态说明 |
|---|---|---|---|
| 接收模式 | 0 | 0 | 驱动器关闭,接收器打开,监听总线 |
| 发送模式 | 1 | 通常关闭接收 | 驱动器打开,向 A/B 总线发送数据 |
很多开发板会把 RE 和 DE 接到同一个 GPIO 上:
-
GPIO 输出低电平:进入接收模式
-
GPIO 输出高电平:进入发送模式
这样控制简单,但要注意发送完成后及时切回接收模式,否则可能错过其他节点返回的数据。
七、STM32 HAL 库中常用接口
RS485 的底层收发依然依赖 UART,所以 HAL 层主要使用 UART 相关接口。
| HAL 接口或宏 | 作用 |
|---|---|
__HAL_RCC_USARTx_CLK_ENABLE |
使能串口外设时钟 |
HAL_UART_Init |
初始化串口工作参数 |
__HAL_UART_ENABLE_IT |
使能串口相关中断 |
HAL_UART_Transmit |
串口发送数据 |
HAL_UART_Receive |
串口接收数据 |
__HAL_UART_GET_FLAG |
查询当前串口状态 |
这里要注意一个点:HAL UART 接口只负责“串口收发”,不会自动替你处理 RS485 的收发方向。
因此在半双工 RS485 中,发送流程通常要包含:
-
拉高方向控制引脚,进入发送模式
-
调用 UART 发送接口
-
等待数据真正发送完成
-
拉低方向控制引脚,回到接收模式
如果只等发送函数返回,但移位寄存器里最后一位还没完全发出去,就立刻切回接收模式,可能导致最后的数据位被截断。工程中通常要关注发送完成标志,例如 TC 标志。
八、RS485 配置步骤
STM32 上配置 RS485,可以按下面的顺序理解:

1. 配置串口工作参数
先确定 UART 的基本通信参数:
-
波特率
-
数据位
-
停止位
-
校验方式
-
收发模式
通信双方必须保持一致,否则会出现乱码、接收失败或校验错误。
2. 完成串口底层初始化
底层初始化一般包括:
-
配置 UART TX/RX 对应 GPIO
-
使能 GPIO 时钟
-
使能 USART 外设时钟
-
配置中断控制器 NVIC
-
配置 RS485 方向控制 GPIO
RS485 方向控制引脚建议在初始化后默认置为接收模式,因为总线大部分时间应该处于监听状态。
3. 开启串口异步接收中断
RS485 总线通信通常不知道对方什么时候发数据,因此接收端常用中断方式。
开启接收中断后,收到数据时可以及时进入中断处理流程,避免主循环轮询不及时造成数据丢失。
4. 设置中断优先级并使能中断
需要配置 USART 对应的中断优先级,并使能对应 IRQ。优先级要根据项目中其他外设的重要程度合理安排。
如果系统中还有定时器、DMA、RTOS 或其他实时任务,就要避免 UART 接收中断被长时间阻塞。
5. 编写串口中断服务逻辑
中断服务函数中一般会调用 HAL 接收相关处理,完成数据读取、缓冲和状态更新。
这里不展开源码,只强调思路:中断里不要做太重的业务逻辑,建议把数据放入缓冲区,再由主循环或任务层解析。
6. 发送数据前后控制方向
半双工 RS485 最容易出问题的地方就是方向切换。
推荐思路:
-
平时保持接收模式
-
发送前切到发送模式
-
发送完成后等待最后一位真正发完
-
再切回接收模式
这样可以减少总线冲突,也能及时接收对端回复。
更多推荐

所有评论(0)