GrabBag/Tools/MThings/ModbusTCP_Reference.md

214 lines
7.9 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Modbus TCP 协议参考文档
用于 MThings 调试工具配置参考
---
## 1. 地址划分
Modbus 协议定义了四种数据类型,每种类型有独立的地址空间:
| 类型 | 代码 | 地址范围 | 功能码 | 数据大小 | 访问 | MThings BLOCK |
|------|------|----------|--------|----------|------|---------------|
| Coils (线圈) | 0x | 00001-09999 | 01/05/15 | 1 bit | 读/写 | 0 |
| Discrete Inputs (离散输入) | 1x | 10001-19999 | 02 | 1 bit | 只读 | 1 |
| **Holding Registers (保持寄存器)** | 4x | 40001-49999 | 03/06/16 | 16 bit | 读/写 | **2** |
| Input Registers (输入寄存器) | 3x | 30001-39999 | 04 | 16 bit | 只读 | 3 |
> **注意**: 保持寄存器Holding Registers是最常用的类型MThings 中 BLOCK=2
---
## 2. 功能码说明
| 功能码 | 名称 | 说明 |
|--------|------|------|
| 01 | Read Coils | 读取线圈状态(位) |
| 02 | Read Discrete Inputs | 读取离散输入状态(位) |
| **03** | **Read Holding Registers** | **读取保持寄存器(最常用)** |
| 04 | Read Input Registers | 读取输入寄存器 |
| 05 | Write Single Coil | 写单个线圈 |
| **06** | **Write Single Register** | **写单个保持寄存器** |
| 15 | Write Multiple Coils | 写多个线圈 |
| **16** | **Write Multiple Registers** | **写多个保持寄存器** |
---
## 3. 错误码说明
当从站无法正常处理请求时返回异常响应功能码最高位置1
| 代码 | 名称 | 说明 | 原因 | 解决方案 |
|------|------|------|------|----------|
| 01 | ILLEGAL_FUNCTION | 非法功能码 | 从站不支持请求的功能码 | 检查功能码是否正确 |
| 02 | ILLEGAL_DATA_ADDRESS | 非法数据地址 | 请求的地址超出有效范围 | 检查起始地址和数量 |
| 03 | ILLEGAL_DATA_VALUE | 非法数据值 | 请求数据包中的值不合法 | 检查写入的数据值 |
| 04 | SLAVE_DEVICE_FAILURE | 从站设备故障 | 从站执行时发生错误 | 检查从站设备状态 |
| 05 | ACKNOWLEDGE | 确认 | 从站需要较长时间处理 | 稍后重新发送请求 |
| 06 | SLAVE_DEVICE_BUSY | 从站设备忙 | 从站正在处理其他命令 | 等待后重试 |
| 08 | MEMORY_PARITY_ERROR | 内存奇偶校验错误 | 从站内存错误 | 检查从站硬件 |
| 0A | GATEWAY_PATH_UNAVAILABLE | 网关路径不可用 | 网关配置错误 | 检查网关配置 |
| 0B | GATEWAY_TARGET_FAILED | 网关目标设备响应失败 | 目标设备未响应 | 检查目标设备是否在线 |
---
## 4. Modbus TCP 帧格式
Modbus TCP 在标准 Modbus 帧前添加 MBAP 头:
### MBAP 头 (7 字节)
| 字段 | 字节数 | 说明 |
|------|--------|------|
| Transaction ID | 2 | 事务标识符,用于匹配请求和响应 |
| Protocol ID | 2 | 协议标识符Modbus 固定为 0x0000 |
| Length | 2 | 后续字节数(单元标识符 + PDU |
| Unit ID | 1 | 单元标识符从站地址TCP 通常为 0 或 1 |
### 示例:读取保持寄存器
**请求**: 读取从站1的地址1000开始的3个寄存器
```
00 01 00 00 00 06 01 03 03 E8 00 03
│ │ │ │ │ │ │ │ │ │ │ │
│ │ │ │ │ │ │ │ │ │ └──┴── 寄存器数量 (3)
│ │ │ │ │ │ │ │ └──┴────── 起始地址 (1000 = 0x03E8)
│ │ │ │ │ │ │ └─────────── 功能码 (03 = 读保持寄存器)
│ │ │ │ │ │ └────────────── 单元ID (从站地址 1)
│ │ │ │ └──┴───────────────── 长度 (6字节)
│ │ └──┴─────────────────────── 协议ID (0x0000 = Modbus)
└──┴───────────────────────────── 事务ID (0x0001)
```
**响应**: 返回3个寄存器的值
```
00 01 00 00 00 09 01 03 06 00 01 00 00 00 00
│ │ │ │ │ │ │ │ │ │ │ │ │ │ │
│ │ │ │ │ │ │ │ │ │ │ │ │ └──┴── 寄存器3 (0)
│ │ │ │ │ │ │ │ │ │ │ └──┴────── 寄存器2 (0)
│ │ │ │ │ │ │ │ │ └──┴──────────── 寄存器1 (1)
│ │ │ │ │ │ │ │ └───────────────── 字节数 (6)
│ │ │ │ │ │ │ └──────────────────── 功能码 (03)
│ │ │ │ │ │ └─────────────────────── 单元ID (1)
│ │ │ │ └──┴────────────────────────── 长度 (9字节)
│ │ └──┴──────────────────────────────── 协议ID
└──┴────────────────────────────────────── 事务ID
```
---
## 5. 数据类型转换
Modbus 寄存器为 16 位,多字节数据需要多个寄存器:
| 类型 | 寄存器数 | 范围 | 说明 |
|------|----------|------|------|
| UINT16 | 1 | 0 ~ 65535 | 无符号16位整数 |
| INT16 | 1 | -32768 ~ 32767 | 有符号16位整数 |
| UINT32 | 2 | 0 ~ 4294967295 | 无符号32位整数 |
| INT32 | 2 | -2147483648 ~ 2147483647 | 有符号32位整数 |
| FLOAT32 | 2 | IEEE 754 | 单精度浮点数 |
### Float32 示例
`50.0` 的 IEEE 754 表示:
```
IEEE 754: 0x42480000
大端序 (Big Endian):
寄存器1 (高位): 0x4248
寄存器2 (低位): 0x0000
```
---
## 6. MThings 配置参数说明
### BLOCK (数据区域)
| 值 | 说明 |
|----|------|
| 0 | 线圈 Coils (功能码 01/05/15) |
| 1 | 离散输入 Discrete Inputs (功能码 02) |
| **2** | **保持寄存器 Holding Registers (功能码 03/06/16)** |
| 3 | 输入寄存器 Input Registers (功能码 04) |
### PrtcTYPE (数据类型)
| 值 | 说明 |
|----|------|
| 1 | UINT16 - 无符号16位整数 |
| **2** | **FLOAT32 - 32位浮点数** |
| 3 | INT16 - 有符号16位整数 |
| 4 | UINT32 - 无符号32位整数 |
| 5 | INT32 - 有符号32位整数 |
### Size (寄存器数量)
| 值 | 说明 |
|----|------|
| 1 | 1个寄存器 (16位) |
| 2 | 2个寄存器 (32位) |
| 4 | 4个寄存器 (64位) |
### ByteOder (字节序)
| 值 | 说明 |
|----|------|
| 0 | 大端序 Big Endian (高字节在前) - **常用** |
| 1 | 小端序 Little Endian (低字节在前) |
### WordOder (字序)
| 值 | 说明 |
|----|------|
| 0 | 高字在前 - **常用** |
| 1 | 低字在前 |
### ShowType (显示类型)
| 值 | 说明 |
|----|------|
| 0 | 浮点数显示 |
| 1 | 十六进制显示 |
| 2 | 十进制显示 |
| 3 | 二进制显示 |
### LinkMode (连接模式)
| 值 | 说明 |
|----|------|
| 0 | TCP Client 模式 |
| 1 | TCP Server 模式 |
---
## 7. 常见问题
### Q1: 为什么读取的数据全是0
**A**: 检查地址是否正确注意有些设备地址从0开始有些从1开始。
### Q2: 为什么连接超时?
**A**: 检查IP地址和端口是否正确防火墙是否放行502端口。
### Q3: 为什么浮点数显示不正确?
**A**: 检查字节序ByteOder和字序WordOder设置不同厂商可能使用不同的字节序。
### Q4: 返回异常码02是什么意思
**A**: 非法数据地址ILLEGAL_DATA_ADDRESS请求的地址超出设备有效范围。
### Q5: 如何区分功能码03和04
**A**:
- 功能码03读取保持寄存器Holding Registers可读写
- 功能码04读取输入寄存器Input Registers只读
---
## 8. 参考资料
- Modbus 官方规范: [modbus.org](https://modbus.org/specs.php)
- MThings 使用手册: `Tools/MThings/MThings使用手册.pdf`