MODBUS 是一个请求/应答协议,包括ASCII、RTU、TCP等,是1979年开发出的一种工业通信协议,并没有规定物理层。此协议定义了控制器能够认识和使用的消息结构,而不管它们是通过何种硬件方式进行通信的。所以硬件接口可以是RS-232、RS-422、RS-485和以太网等设备。TCP和RTU比ASCII常见,其中TCP的使用频率更高一些。
关于主站与从站:RTU模式下,一个主站可以连接多个从站,且主站有且只能有一个,从站至少一个;TCP模式下主要分为服务器与客户端,可认为客户端是主站。
1. Modbus协议相关术语及含义:
寄存器种类 | 数据类型 | 访问类型 | 功能码 |
---|---|---|---|
线圈 | 位 | 读写 | 01H 05H 0FH |
离散输入 | 位 | 读写(主站只读) | 02H |
保持寄存器 | 字 | 读写 | 04H |
输入寄存器 | 字 | 读写(主站只读) | 03H 06H 10H |
Memory Block
Coils:线圈、Discrete Inputs:离散输入、Holding Registers:保持寄存器、
Input Registers输入寄存器
Data Type
只有布尔型与无符号整型,即无法传输负数与浮点数,当然,我们可以通过其他方式实
现。
同许多规范一样,不同行业可能会有不同的称呼。如保持寄存器可以被称为输出寄存器,而线圈可以被称为数字或离散输出。
2. 常用功能码
Modbus中常用的功能码有 8个,可以分为位操作和字操作两类,如下表
功能码 | 描述 | PLC地址 | 寄存器地址 | 位/字操作 | 操作数量 |
---|---|---|---|---|---|
01H | 读线圈寄存器 | 00001-09999 | 0000H-FFFFH | 位 | 单个或多个 |
02H | 读离散输入寄存器 | 10001-19999 | 0000H-FFFFH | 位 | 单个或多个 |
03H | 读保持寄存器 | 40001-49999 | 0000H-FFFFH | 字 | 单个或多个 |
04H | 读输入寄存器 | 30001-39999 | 0000H-FFFFH | 字 | 单个或多个 |
05H | 写单个线圈寄存器 | 00001-09999 | 0000H-FFFFH | 位 | 单个 |
06H | 写单个保持寄存器 | 40001-49999 | 0000H-FFFFH | 字 | 单个 |
0FH | 写多个线圈寄存器 | 00001-09999 | 0000H-FFFFH | 位 | 多个 |
10H | 写多个保持寄存器 | 40001-49999 | 0000H-FFFFH | 字 | 多个 |
3. Modbus消息结构
接下来重点说下Modbus的消息结构,以功能码01(0x01)为例进行说明。
功能码01H读取Modbus从站中线圈寄存器的状态,可以是单个寄存器,或者是多个连续的寄存器。
发送:
假设从站地址为01H,读取线圈寄存器的起始地址为0017H,读取38(十进制)个寄存器,指令结构如下表:
从站地址 | 功能码 | 起始地址高位 | 起始地址低位 | 寄存器数量高位 | 寄存器数量低位 | CRC高位 | CRC低位 |
---|---|---|---|---|---|---|---|
01 | 01 | 00 | 17 | 00 | 26 | 0D | D4 |
响应:各线圈的状态与数据内容的每个bit对应,1代表ON,0代表OFF.若查询线圈的数量不是8的倍数,则在最后一个字节的高位补0.
读线圈结果举例:
从站地址 | 功能码 | 返回字节数 | 数据1 | 数据2 | 数据3 | 数据4 | 数据5 | CRC高位 | CRC低位 |
---|---|---|---|---|---|---|---|---|---|
01 | 01 | 05 | CD | 6B | B2 | 0E | 1B | 44 | EA |
第一个字节CDH对应线圈0017H到001E的状态,转为二进制是11001101,其中bit0对应0017H,bit7对应001E,如下表:
001EH | 001DH | 001CH | 001BH | 001AH | 0019H | 0018H | 0017H |
---|---|---|---|---|---|---|---|
1 | 1 | 0 | 0 | 1 | 1 | 0 | 1 |
ON | ON | OFF | OFF | ON | ON | OFF | ON |
对于刚接触的老铁们看到这里有点蒙圈吧?正常,我开始看到这里的时候也蒙圈。其实说白了就是规定了交换数据的方式,大家都按这个方式来,这就是“协议”啊,至于这个协议具体叫什么也不重要,重要的是大家都能明白我发的东西是什么意思就好了。就像以前谍战片里的电报一样,发过来的东西需要“协议”解读下,就是这个意思了。
下次和大家分享下Modbus调试助手的使用,那个更直观!