提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档
MODBUS RTU 是一种工业通信协议,广泛应用于工业自动化领域,用于连接各种电子设备;
为什么要用MODBUS RTU
- MODBUS协议简单、可靠、易于实现的特点
- 标准化的需求:
在工业自动化领域,标准化的通信协议对于提高系统的互操作性、降低开发成本、加快项目进度具有重要意义。MODBUS RTU协议作为一种广泛采用的工业标准,为不同厂商的设备之间的互连互通提供了有力的支持。
整体格式
- 起始位:消息开始前的静默期(至少3.5个字符时间)。
- 地址域:1字节,表示目标设备的地址(0x01到0xFF)。
- 功能码:1字节,表示要执行的操作(例如0x03表示读取保持寄存器)。
- 数据域:可变长度,包含实际的数据。
- 校验域:2字节,使用CRC(循环冗余校验)。
- 停止位:消息结束后的静默期(至少3.5个字符时间)。
常用几个指令如 MODBUS调试助手 exe 所示

详细格式
1.起始位:
在消息开始之前,必须有一个至少3.5个字符时间的静默期。这是为了确保接收方能够正确识别消息的开始。
2.地址域:
- 广播消息不接收响应:广播消息不会收到任何响应,因此不适用于需要应答的请求。
- 设备地址唯一性:在同一个网络中,每个从设备的地址必须是唯一的,以避免地址冲突。
- 地址0xFF:虽然0xFF在某些实现中可能被用作特殊用途,但根据MODBUS标准,它不是合法的设备地址
单播地址(Unicast Addresses)
- 地址域:0x01(目标设备地址)
- 功能码:0x03(读保持寄存器)
- 数据域:0x00 0x01(起始地址0x0001),0x00 0x02(读取2个寄存器)
- 校验域:0x1C 0x0F(CRC校验值)
广播地址(Broadcast Address)
- 地址域:0x00(广播地址)
- 功能码:0x06(假设用于复位)
- 数据域:0x00 0x00(寄存器地址),0x00 0x00(寄存器值)
- 校验域:0xXX 0XX(CRC校验值)
3.功能码:
常用的功能码
- 0x01 - 读线圈状态 (Read Coils)
描述: 从设备读取一组线圈(离散输出)的状态。
数据域:起始地址(2字节)、线圈数量(2字节)。
响应:线圈状态(1位/线圈,按字节对齐)。 - 0x02 - 读离散输入状态 (Read Discrete Inputs)
描述:从设备读取一组离散输入的状态。
数据域:起始地址(2字节)、输入数量(2字节)。
响应:输入状态(1位/输入,按字节对齐)。 - 0x03 - 读保持寄存器 (Read Holding Registers)
描述:从设备读取一组保持寄存器的值。
数据域:起始地址(2字节)、寄存器数量(2字节)。
响应:寄存器值(2字节/寄存器)。 - 0x04 - 读输入寄存器 (Read Input Registers)
描述:从设备读取一组输入寄存器的值。
数据域:起始地址(2字节)、寄存器数量(2字节)。
响应:寄存器值(2字节/寄存器)。 - 0x05 - 写单个线圈 (Write Single Coil)
描述:向设备写入单个线圈的状态。
数据域:线圈地址(2字节)、线圈状态(2字节,0x0000表示OFF,0xFF00表示ON)。
响应:线圈地址(2字节)、线圈状态(2字节)。 - 0x06 - 写单个保持寄存器 (Write Single Register)
描述:向设备写入单个保持寄存器的值。
数据域:寄存器地址(2字节)、寄存器值(2字节)。
响应:寄存器地址(2字节)、寄存器值(2字节)。 - 0x0F - 写多个线圈 (Write Multiple Coils)
描述:向设备写入多个线圈的状态。
数据域:起始地址(2字节)、线圈数量(2字节)、字节数(1字节)、线圈状态(N字节,1位/线圈)。
响应:起始地址(2字节)、线圈数量(2字节)。 - 0x10 - 写多个保持寄存器 (Write Multiple Registers)
描述:向设备写入多个保持寄存器的值。
数据域:起始地址(2字节)、寄存器数量(2字节)、字节数(1字节)、寄存器值(N字节,2字节/寄存器)。
响应:起始地址(2字节)、寄存器数量(2字节)。
其他功能码
错误码
如果从设备无法执行请求的操作,它会返回一个异常响应,其中包含一个错误码。常见的错误码包括:
0x01 - 非法功能码 (Illegal Function)
0x02 - 非法数据地址 (Illegal Data Address)
0x03 - 非法数据值 (Illegal Data Value)
0x04 - 从设备故障 (Slave Device Failure)
0x05 - 从设备忙 (Acknowledge)
0x06 - 从设备内存区满 (Slave Device Busy)
0x07 - 负载设备故障 (Negative Acknowledge)
0x08 - 存储区检验失败 (Memory Parity Error)
0x0A - 闸道路径不可用 (Gateway Path Unavailable)
0x0B - 闸道目标设备未响应 (Gateway Target Device Failed to Respond)
4.数据域:
可变长度,包含实际的数据。数据的具体格式和长度取决于功能码。例如,读保持寄存器的功能码0x03可能包含起始地址和寄存器数量。
5.校验域:
- 提取数据部分:从接收到的报文中提取地址域、功能码和数据域,形成一个字节数组。
- 计算CRC:使用相同的CRC-16算法计算该字节数组的校验值。
- 比较校验值:将计算得到的CRC校验值与报文中的校验域进行比较。如果两者一致,则认为数据传输无误;否则,认为数据传输有误。
计算步骤
1.提取数据部分
假设接收到的报文如下:
提取的数据部分为:
2.计算CRC
使用CRC-16算法计算提取的数据部分的校验值。
3. 比较校验值
6.停止位:
在消息结束之后,必须有一个至少3.5个字符时间的静默期。这是为了确保接收方能够正确识别消息的结束。
到此这篇modbus报文解析实例(modbus rtu 报文)的文章就介绍到这了,更多相关内容请继续浏览下面的相关推荐文章,希望大家都能在编程的领域有一番成就!版权声明:
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若内容造成侵权、违法违规、事实不符,请将相关资料发送至xkadmin@xkablog.com进行投诉反馈,一经查实,立即处理!
转载请注明出处,原文链接:https://www.xkablog.com/rfx/47516.html