Modbus 异常响应
前面 Modbus 功能码 中提到,对于广播模式以外的查询报文,如果一切正常,从站设备会返回一个正常响应报文。但是,如果出现差错,会怎么办呢?—— 没错,从站设备会返回异常响应报文。
异常响应
通常来说,在 Modbus 主设备(客户端)和从设备(服务器)的通信过程中,存在以下 4 种处理反馈:
- 正常接收,正常处理,返回正常响应报文。
- 因为通信错误等原因,造成从站设备没有接收到查询报文,主站设备将按超时处理。
- 从站设备接收到查询报文,但报文存在错误(例如 LRC、CRC 错误等),从站设备将丢弃报文不响应,主站设备将按超时处理。
- 从站设备接收到正确的报文,但是超过处理范围(例如不存在的功能码或者寄存器等),从站设备将按返回包含异常码(Exception Code)的响应报文。
下图大致展示了 Modbus 的查询报文、正常响应报文和异常响应报文的帧格式。
异常功能码
异常响应报文由从站地址、功能码以及异常码构成。其中,功能码与正常响应报文不同,在异常响应报文中,功能码最高位(即 MSB)被设置为 1。
因为 Modbus 协议中功能码占用一个字节,因此可以用如下表达式描述正常功能码和异常功能码的关系:
异常功能码 = 正常功能码 + 0x80
异常帧
与正常报文类似,从设备给主设备回复的异常报文 也包含 4 个域:
域 | 定义 | 大小(RTU 格式) | 描述 |
---|---|---|---|
1 | 从设备号(地址) | 1 个字节 | 从设备的唯一地址,1-247 |
2 | 异常功能码 | 1 个字节 | 请求功能码 + 128(0x80) |
3 | 异常数据 | n 个字节 | 异常码(看下面说明) |
4 | 校验和 | 2 个字节 | CRC 校验和(ASCII 为 LRC) |
异常数据域通常存放异常码,至于返回什么异常码则依赖于此次通信发生了何种错误。
下表列出了 Modbus 协议中常见的异常码。
异常码 | 名称 | 描述 |
---|---|---|
01 (0x01) | 非法功能码 | 从站设备不支持此功能码。 |
02 (0x02) | 非法数据地址 | 指定的数据地址在从站设备中不存在。 |
03 (0x03) | 非法数据值 | 指定的数据超过范围或者不允许使用。 |
04 (0x04) | 从站设备故障 | 从站设备处理响应的过程中,出现未知错误等。 |
05 (0x05) | 确认 | 从站设备已经接受请求, 并且正在处理这个请求,但是需要长持续时间进行这些操作,返回这个响应防止在客户机(或主站)中发生超时错误,客户机(或主机)可以继续发送轮询程序完成报文来确认是否完成处理。 |
06 (0x06) | 从站设备忙 | 从站设备正在处理长持续时间的程序命令。 |
07 (0x07) | 否定确认 | 从站设备无法执行主站设备发送的请求。 |
08 (0x08) | 存储奇偶性差错 | 指示扩展文件区不能通过一致性校验。 |
10 (0x0A) | 不可用的网关路径 | 与网关一起使用,指示网关不能为处理请求分配输入端口值输出端口的内部通信路径。通常意味着网关是错误配置的或过载的。 |
11 (0x0B) | 网关目标设备响应失败 | 与网关一起使用,指示没有从目标设备中获得响应,通常意味着设备未在网络中。 |