docs: Modbus 协议 V1.1 — 修正位宽+输出模式+融合模式
- CAPVD/Origin/Variation → 32-bit (各占2个寄存器) - Output Mode 删除脉冲模式(单继电器仅存在输出) - 新增 Fusion Mode (0x0001): direction_mode低4位, 0=仅地感 ~ 6=ETC - direction_mode 字段重构: bit[7:4]=function_mode, bit[3:0]=fusion_mode - Fusion Mode 仅在光耦配置为雷达输入时有效
This commit is contained in:
+107
-67
@@ -1,6 +1,6 @@
|
||||
# DLD154Pro RS485 Modbus RTU 协议
|
||||
|
||||
> 版本: V1.0 | 日期: 2026-07-22 | 状态: 草案(待评审,未实现)
|
||||
> 版本: V1.1 | 日期: 2026-07-22 | 状态: 草案(待评审,未实现)
|
||||
>
|
||||
> 适用产品: DLD154Pro (CH591R, 单路线圈车检器)
|
||||
>
|
||||
@@ -61,43 +61,50 @@
|
||||
| 0x0002 | Loop Stable | 线圈基线已稳定 | 0=收敛中, 1=稳定 |
|
||||
| 0x0003 | Opto Input | 光耦输入状态 (PB10) | 0=低, 1=高 |
|
||||
| 0x0004 | Power Up State | 上电初始化中 | 0=正常, 1=初始化 |
|
||||
| 0x0005 | Reserved | — | — |
|
||||
| 0x0005 | Relay Output | 继电器当前输出状态 | 0=释放, 1=吸合 |
|
||||
|
||||
### 3.2 输入寄存器 (Input Registers) — 功能码 0x04
|
||||
|
||||
| 地址 | 名称 | 类型 | 说明 |
|
||||
|------|------|------|------|
|
||||
| 0x0000 | Loop Freq Hi | uint16 | 线圈振荡频率,高 16 位 (Hz) |
|
||||
| 0x0001 | Loop Freq Lo | uint16 | 线圈振荡频率,低 16 位 (Hz) |
|
||||
| 0x0002 | CAPVD | uint16 | 归一化周期值(算法内部) |
|
||||
| 0x0003 | Origin | uint16 | 基线值(无车时基准) |
|
||||
| 0x0004 | Variation | int16 | 当前相对于基线的变化量 |
|
||||
| 0x0005 | FW Version | uint16 | 固件版本,高字节=主版本,低字节=子版本。例 `0x0300` = v3.00 |
|
||||
| 0x0006 | HW Version | uint16 | 硬件版本。例 `0x0301` = v3.01 |
|
||||
| 0x0007 | Freq Sens | uint16 | 当前灵敏度等级 (0=低, 1=中, 2=高) |
|
||||
| 0x0008 | Condition | uint16 | 环境活跃度 (0=安静, 1-100=嘈杂) |
|
||||
| 地址 | 名称 | 类型 | 宽度 | 说明 |
|
||||
|------|------|------|------|------|
|
||||
| 0x0000 | Loop Freq Hi | uint16 | 2 寄存器 | 线圈振荡频率,高 16 位 (Hz) |
|
||||
| 0x0001 | Loop Freq Lo | uint16 | | 线圈振荡频率,低 16 位 (Hz) |
|
||||
| 0x0002 | CAPVD Hi | uint16 | **2 寄存器** | 归一化周期值 (32-bit),高 16 位 |
|
||||
| 0x0003 | CAPVD Lo | uint16 | | 归一化周期值,低 16 位 |
|
||||
| 0x0004 | Origin Hi | uint16 | **2 寄存器** | 基线值 (32-bit),高 16 位 |
|
||||
| 0x0005 | Origin Lo | uint16 | | 基线值,低 16 位 |
|
||||
| 0x0006 | Variation Hi | int16 | **2 寄存器** | 变化量 = CAPVD − Origin (32-bit 有符号),高 16 位 |
|
||||
| 0x0007 | Variation Lo | int16 | | 变化量,低 16 位 |
|
||||
| 0x0008 | FW Version | uint16 | 1 寄存器 | 固件版本,高字节=主版本,低字节=子版本。例 `0x0300` = v3.00 |
|
||||
| 0x0009 | HW Version | uint16 | 1 寄存器 | 硬件版本。例 `0x0301` = v3.01 |
|
||||
| 0x000A | Freq Sens | uint16 | 1 寄存器 | 当前灵敏度等级 (0=低, 1=中, 2=高) |
|
||||
| 0x000B | Condition | uint16 | 1 寄存器 | 环境活跃度 (0=安静, 1–100=嘈杂) |
|
||||
|
||||
> **频率换算**:`freq_hz = (reg[0] << 16) | reg[1]`,单位 Hz。典型空线圈 50–120kHz,有车时下降。
|
||||
> **32-bit 值换算**:
|
||||
> - 频率:`freq_hz = (reg[0x0000] << 16) | reg[0x0001]`,单位 Hz。典型空线圈 50–120kHz。
|
||||
> - CAPVD:`capvd = (reg[0x0002] << 16) | reg[0x0003]`,归一化到 `MEASUREMENT_BASE = 131072`。
|
||||
> - Origin:`origin = (reg[0x0004] << 16) | reg[0x0005]`,100 次滑动平均累加值。
|
||||
> - Variation:`var = (int32_t)((reg[0x0006] << 16) | reg[0x0007])`,正值=频率降低(可能有车),负值=频率升高。
|
||||
|
||||
### 3.3 保持寄存器 (Holding Registers) — 功能码 0x03 / 0x06 / 0x10
|
||||
|
||||
| 地址 | 名称 | 范围 | 默认 | R/W | 说明 |
|
||||
|------|------|------|------|-----|------|
|
||||
| 0x0000 | Sensitivity | 0–2 | 2 | R/W | 灵敏度: 0=低(0.330%ΔL/L), 1=中(0.165%), 2=高(0.085%) |
|
||||
| 0x0001 | Output Mode | 0–2 | 0 | R/W | 0=存在输出, 1=进入脉冲(500ms), 2=离开脉冲(500ms) |
|
||||
| 0x0002 | Hold Time | 0–255 | 0 | R/W | 有限存在时间 (×5s), 0=永久存在。例 12=60s 后强制释放 |
|
||||
| 0x0003 | Output Delay | 0–255 | 10 | R/W | 离开延时 (×50ms), 例 10=500ms。0=无延时 |
|
||||
| 0x0000 | Sensitivity | 0–2 | 2 | R/W | 灵敏度等级 (0=低, 1=中, 2=高) |
|
||||
| 0x0001 | Fusion Mode | 0–6 | 0 | R/W | 输出组合模式(见 §6.5) |
|
||||
| 0x0002 | Hold Time | 0–255 | 0 | R/W | 有限存在时间 (×5s), 0=永久存在 |
|
||||
| 0x0003 | Output Delay | 0–255 | 10 | R/W | 离开延时 (×50ms), 例 10=500ms |
|
||||
| 0x0004 | Freq Level | 0–1 | 0 | R/W | 线圈频率档: 0=高频, 1=低频 |
|
||||
| 0x0005 | RS485 Baud | uint32 | 9600 | **R** | RS485 波特率,只读(通过 BLE 修改) |
|
||||
| 0x0006 | (Baud Lo) | — | — | **R** | 波特率低 16 位 |
|
||||
| 0x0007 | RS485 Addr | 1–247 | 1 | **R** | RS485 从机地址,只读(通过 BLE 修改) |
|
||||
| 0x0008 | Protocol | 0–1 | 0 | **R** | 当前协议: 0=700BS, 1=Modbus,只读 |
|
||||
| 0x0009 | BT Timeout | 0–255 | 0 | R/W | 蓝牙空闲超时关闭 (分钟), 0=不关闭 |
|
||||
| 0x000A | Safe Timeout | 0–255 | 0 | R/W | 线圈安全模式超时 (×10s), 0=关闭 |
|
||||
| 0x000B | Opto Func | 0–1 | 0 | **R** | 光耦功能: 0=雷达输入, 1=复位,只读(通过 BLE 修改) |
|
||||
| 0x0005 | RS485 Baud Hi | — | — | **R** | RS485 波特率高 16 位(只读) |
|
||||
| 0x0006 | RS485 Baud Lo | — | — | **R** | RS485 波特率低 16 位(只读) |
|
||||
| 0x0007 | RS485 Addr | 1–247 | 1 | **R** | RS485 从机地址(只读) |
|
||||
| 0x0008 | Protocol | 0–1 | 0 | **R** | 当前 RS485 协议: 0=700BS, 1=Modbus |
|
||||
| 0x0009 | BT Timeout | 0–255 | 0 | R/W | 蓝牙空闲关闭超时 (分钟), 0=不关闭 |
|
||||
| 0x000A | Safe Timeout | 0–255 | 0 | R/W | 安全模式超时 (×10s), 0=关闭 |
|
||||
| 0x000B | Opto Func | 0–1 | 0 | **R** | 光耦功能: 0=雷达输入, 1=复位 |
|
||||
|
||||
> **只读寄存器 (0x0005–0x0008, 0x000B)**:对这些地址写 0x06 返回异常 0x02(Illegal Data Address)。
|
||||
> 这些参数只能通过 BLE 小程序修改,避免 RS485 改错后设备失联。
|
||||
> **只读寄存器 (0x0005–0x0008, 0x000B)**:写操作返回异常 0x02(Illegal Data Address)。
|
||||
> 这些参数只能通过 BLE 小程序修改。RS485 地址/波特率通过 Modbus 误改会立即失联。
|
||||
|
||||
---
|
||||
|
||||
@@ -114,24 +121,26 @@
|
||||
|
||||
### 4.2 读输入寄存器 — 功能码 0x04
|
||||
|
||||
读取频率 + CAPVD:
|
||||
读取频率 + CAPVD + Origin + Variation(共 8 个寄存器,16 字节):
|
||||
|
||||
```
|
||||
>>> 01 04 00 00 00 03 30 1F (读3个: 频率Hi/Lo + CAPVD)
|
||||
<<< 01 04 06 00 01 86 A0 11 BB 22 xx xx
|
||||
地址 功能 字节数 FreqHi FreqLo CAPVD CRC
|
||||
→ freq = 0x000186A0 = 100000 Hz
|
||||
→ CAPVD = 0x11BB
|
||||
>>> 01 04 00 00 00 08 70 1F (读 0x0000 起 8 个寄存器)
|
||||
<<< 01 04 10
|
||||
00 01 86 A0 ← Freq = 0x000186A0 = 100000 Hz
|
||||
00 02 00 7C ← CAPVD = 0x0002007C = 131196
|
||||
00 01 FF F3 ← Origin = 0x0001FFF3 = 131059
|
||||
FF FF 00 99 ← Var = 0xFFFF0099 = −65383 (频率降低)
|
||||
XX XX
|
||||
```
|
||||
|
||||
### 4.3 读保持寄存器 — 功能码 0x03
|
||||
|
||||
读取全部检测参数:
|
||||
读取全部可读写参数:
|
||||
|
||||
```
|
||||
>>> 01 03 00 00 00 05 84 09 (读5个: 灵敏度/输出模式/存在时间/延时/频率档)
|
||||
<<< 01 03 0A 00 02 00 00 00 00 00 0A 00 00 xx xx
|
||||
→ 灵敏度=2(高), 存在输出, 永久存在, 延时=500ms, 高频
|
||||
>>> 01 03 00 00 00 05 84 09 (读 5 个: 灵敏度/融合模式/存在时间/延时/频率档)
|
||||
<<< 01 03 0A 00 02 00 00 00 00 00 0A 00 00 XX XX
|
||||
→ 灵敏度=2(高), 融合模式=0(仅地感), 永久存在, 延时=500ms, 高频
|
||||
```
|
||||
|
||||
### 4.4 写单个寄存器 — 功能码 0x06
|
||||
@@ -139,25 +148,34 @@
|
||||
修改灵敏度为"中":
|
||||
|
||||
```
|
||||
>>> 01 06 00 00 00 01 49 F3 (写地址0x0000=1, 中灵敏度)
|
||||
<<< 01 06 00 00 00 01 49 F3 (回显)
|
||||
>>> 01 06 00 00 00 01 49 F3 (写 0x0000=1)
|
||||
<<< 01 06 00 00 00 01 49 F3
|
||||
```
|
||||
|
||||
修改输出模式为"进入脉冲":
|
||||
修改融合模式为"地感或雷达":
|
||||
|
||||
```
|
||||
>>> 01 06 00 01 00 01 18 33 (写地址0x0001=1, 进入脉冲)
|
||||
<<< 01 06 00 01 00 01 18 33
|
||||
>>> 01 06 00 01 00 03 99 F5 (写 0x0001=3, 地感或雷达)
|
||||
<<< 01 06 00 01 00 03 99 F5
|
||||
```
|
||||
|
||||
### 4.5 批量写寄存器 — 功能码 0x10
|
||||
|
||||
一次写入灵敏度 + 输出模式 + 存在时间(60s) + 延时(200ms):
|
||||
一次写入灵敏度和存在时间(60s):
|
||||
|
||||
```
|
||||
>>> 01 10 00 00 00 03 06 00 02 00 01 00 0C 00 04 xx xx
|
||||
地址 功能 起始 数量 字节 灵敏度=2 模式=1 时间=12 延时=4 CRC
|
||||
<<< 01 10 00 00 00 03 41 F3 (写入成功)
|
||||
>>> 01 10 00 00 00 02 04 00 02 00 0C XX XX
|
||||
地址 功能 起始 数量 字节 灵敏度=2 时间=12 CRC
|
||||
<<< 01 10 00 00 00 02 40 31 (写入成功)
|
||||
```
|
||||
|
||||
### 4.6 异常响应示例
|
||||
|
||||
写入超出范围的灵敏度值:
|
||||
|
||||
```
|
||||
>>> 01 06 00 00 00 05 88 32 (写 0x0000=5, 超出 0–2)
|
||||
<<< 01 86 03 02 63 (异常: 功能码 0x86, 异常码 0x03=Illegal Data Value)
|
||||
```
|
||||
|
||||
---
|
||||
@@ -167,33 +185,36 @@
|
||||
| 功能码 | 名称 | 支持 | 说明 |
|
||||
|--------|------|------|------|
|
||||
| 0x01 | Read Coils | ✗ | 不使用 |
|
||||
| 0x02 | Read Discrete Inputs | ✓ | 车辆状态、故障、光耦 |
|
||||
| 0x02 | Read Discrete Inputs | ✓ | 车辆状态、故障、继电器、光耦 |
|
||||
| 0x03 | Read Holding Registers | ✓ | 读所有配置参数 |
|
||||
| 0x04 | Read Input Registers | ✓ | 读传感器数据 |
|
||||
| 0x04 | Read Input Registers | ✓ | 读传感器数据 (32-bit 跨双寄存器) |
|
||||
| 0x05 | Write Single Coil | ✗ | 不使用 |
|
||||
| 0x06 | Write Single Register | ✓ | 写单个参数(安全:只写 R/W 寄存器) |
|
||||
| 0x06 | Write Single Register | ✓ | 写单个参数 |
|
||||
| 0x0F | Write Multiple Coils | ✗ | 不使用 |
|
||||
| 0x10 | Write Multiple Registers | ✓ | 批量写参数 |
|
||||
| 0x11 | Report Slave ID | ✓ | 返回设备型号 + 运行状态 |
|
||||
|
||||
---
|
||||
|
||||
## 6. 设计决策与注意事项
|
||||
## 6. 设计说明
|
||||
|
||||
### 6.1 为什么不通过 Modbus 修改 RS485 地址/波特率?
|
||||
### 6.1 为什么 CAPVD/Origin/Variation 用 2 个寄存器?
|
||||
|
||||
DLD154V4B 算法移植后,`MEASUREMENT_BASE = 131072 (2^17)`,IIR 滤波后的 CAPVD 和 Origin 是 `uint32_t` 类型,典型值在 10 万级,远超 16 位(65535)。Variation 是差值且可能为负,需要完整 32-bit 有符号表示。因此各占 2 个 Modbus 寄存器(寄存器对,大端序)。
|
||||
|
||||
### 6.2 为什么不通过 Modbus 修改 RS485 地址/波特率?
|
||||
|
||||
如果在 Modbus 通信中写入错误的地址或波特率,设备将**立即失联**且无法通过同一条总线恢复。
|
||||
正确的做法:
|
||||
- 通过 **BLE 小程序** 修改 RS485 地址和波特率(带外管理通道)
|
||||
- Modbus 侧只读查询当前值,防止误操作
|
||||
|
||||
### 6.2 参数持久化
|
||||
### 6.3 参数持久化
|
||||
|
||||
- `0x06` 或 `0x10` 写入 Holding Register → 立即更新 RAM → 写入 DataFlash → 返回响应
|
||||
- Flash 写入失败 → 返回异常码 `0x04` (Slave Device Failure)
|
||||
- 灵敏度写入 0–2 范围之外的值 → 返回异常码 `0x03` (Illegal Data Value)
|
||||
- 值超出范围(如灵敏度写 5)→ 返回异常码 `0x03` (Illegal Data Value)
|
||||
|
||||
### 6.3 灵敏度与 ΔL/L 对应关系
|
||||
### 6.4 灵敏度与 ΔL/L 对应关系
|
||||
|
||||
| 灵敏度值 | SensTable 进入 | ΔL/L 进入 | SensTable1 离开 | ΔL/L 离开 |
|
||||
|---------|---------------|-----------|----------------|-----------|
|
||||
@@ -203,31 +224,49 @@
|
||||
|
||||
ΔL/L 越大越不灵敏。高灵敏度 (2) 适合安静环境,低灵敏度 (0) 适合强干扰环境。
|
||||
|
||||
### 6.4 输出模式详解
|
||||
### 6.5 输出组合模式 (Fusion Mode)
|
||||
|
||||
| 模式 | 值 | 行为 |
|
||||
|------|-----|------|
|
||||
| 存在输出 | 0 | 有车时继电器吸合,车走释放(+离开延时) |
|
||||
| 进入脉冲 | 1 | 车进入时继电器吸合 500ms 后释放 |
|
||||
| 离开脉冲 | 2 | 车离开时继电器吸合 500ms 后释放 |
|
||||
`direction_mode` 字段重构:
|
||||
|
||||
### 6.5 实现要点(待编码时参考)
|
||||
| 位段 | 名称 | 说明 |
|
||||
|------|------|------|
|
||||
| bit [7:4] | `function_mode` | 功能代码。bit0=RS485 协议选择(0=700BS, 1=Modbus), bit1=光耦功能(0=雷达输入, 1=复位) |
|
||||
| bit [3:0] | `fusion_mode` | 输出组合模式 — **仅当光耦配置为"雷达输入"时有效** |
|
||||
|
||||
> DLD154Pro 为单路线圈、单刀双掷继电器,**仅支持存在输出**。继电器输出信号由线圈检测结果与雷达输入(光耦 PB10)按 `fusion_mode` 组合后驱动。
|
||||
|
||||
| 值 | 模式 | 继电器吸合条件 | 适用场景 |
|
||||
|----|------|--------------|---------|
|
||||
| 0 | 默认 (仅地感) | 线圈有车 | 纯线圈场景(光耦未接雷达时也用此模式) |
|
||||
| 1 | 仅地感 | 线圈有车 | 同 0,显式指定忽略雷达 |
|
||||
| 2 | 仅雷达 | 光耦输入有效(雷达有车) | 纯雷达,地感只做背景监控 |
|
||||
| 3 | 地感 **或** 雷达 | 线圈 OR 雷达 | 互补冗余,任一触发即吸合 |
|
||||
| 4 | 地感 **且** 雷达 | 线圈 AND 雷达 | 双确认,防地感误触(如行人/拖车) |
|
||||
| 5 | 混行模式 | 待定义 | 混合交通流场景 |
|
||||
| 6 | ETC 模式 | 待定义 | ETC 专用逻辑 |
|
||||
|
||||
> **注意**:当 `g_fm_radar_input_disable = 1`(光耦配置为复位功能)时,`fusion_mode` 无效,继电器仅由线圈检测结果驱动。
|
||||
|
||||
### 6.6 实现要点(待编码时参考)
|
||||
|
||||
```c
|
||||
// RS485 方向控制 (PA13)
|
||||
#define RS485_RE_TX() GPIOA_SetBits(GPIO_Pin_13) // 发送
|
||||
#define RS485_RE_RX() GPIOA_ResetBits(GPIO_Pin_13) // 接收
|
||||
|
||||
// UART0 中断接收,3.5 字符超时判定帧结束
|
||||
// 32-bit 值拆分为 2 个 Modbus 寄存器(大端序)
|
||||
// CAPVD = 131196 → reg[0]=0x0002, reg[1]=0x007C
|
||||
reg[0] = (uint16_t)(capvd >> 16);
|
||||
reg[1] = (uint16_t)(capvd & 0xFFFF);
|
||||
|
||||
// CRC16 查表法:poly=0xA001, init=0xFFFF
|
||||
// 帧间隔: t3.5 = 3.5 × 11 / baud (秒)
|
||||
// @9600 = 4.0ms
|
||||
// @19200 = 2.0ms
|
||||
// @115200= 0.33ms
|
||||
```
|
||||
|
||||
RS485 半双工时序关键:发送最后一字节后等待 **1 字节时间** 再切换为接收,
|
||||
避免 RE 切换过早导致最后一个字节被截断。
|
||||
RS485 半双工时序:发送最后一字节后等待 **1 字节时间** 再切换 RE 为接收,
|
||||
避免 RE 过早翻转导致最后一个字节被截断。
|
||||
|
||||
---
|
||||
|
||||
@@ -235,4 +274,5 @@ RS485 半双工时序关键:发送最后一字节后等待 **1 字节时间**
|
||||
|
||||
| 版本 | 日期 | 作者 | 变更 |
|
||||
|------|------|------|------|
|
||||
| V1.0 | 2026-07-22 | wangfq | 初版草案:寄存器映射 + 命令示例 + 设计决策 |
|
||||
| V1.1 | 2026-07-22 | wangfq | 修正: CAPVD/Origin/Variation 扩展为 32-bit (×2 寄存器); Output Mode 删除脉冲模式(仅存在输出); 新增 Fusion Mode(输出组合模式 0-6); direction_mode 字段重构说明 |
|
||||
| V1.0 | 2026-07-22 | wangfq | 初版草案 |
|
||||
|
||||
Reference in New Issue
Block a user