- twin_layout_blob_sized generalized: multi-entry TwinCAT line format (1 real @240bit + N continuation + remainder entry); 1024B path kept byte-identical; 800B = 27 entries verified on hardware - 800B constants (PAYLOAD/SM 800), deployed as el6695_rt_800b - 10-min + 5h stability runs: 18M cycles, zero errors, zero mismatches, PLC nMismatch frozen over the whole run (monitor_5h.csv evidence) - docs: 800B plan/design/verification/test-report chapters, jitter analysis (NFS rootfs stall primary cause), D2000 dev plan - scripts: 800B deploy/relink/verify, mismatch-delta, 5h monitor
198 lines
7.7 KiB
Markdown
198 lines
7.7 KiB
Markdown
# EL6695 8B 双向通讯 — 验证说明文档
|
||
|
||
> **版本**: 1.1(新增 §7 800B 验证)
|
||
> **日期**: 2026-07-27
|
||
> **配套文档**: `8b-bridge-design.md`(设计)、`8b-test-report.md`(测试记录)
|
||
|
||
---
|
||
|
||
## 1. 验证目标
|
||
|
||
证明 TwinCAT PC 与 J1900 之间经 EL6695 桥接的 **8 字节过程数据通道**满足:
|
||
|
||
1. **双向连通**: TwinCAT → J1900、J1900 → TwinCAT 两个方向都通;
|
||
2. **每字节有效**: 8 个字节中的**每一个**都真实参与传输,而非只有个别字节(如计数器低位)在动;
|
||
3. **经过软件处理**: 回传数据确实经过 J1900 用户态程序的读-算-写,不是硬件环回或透传;
|
||
4. **持续稳定**: 连续运行无失配、无陈旧数据、无传输错误。
|
||
|
||
---
|
||
|
||
## 2. 为什么朴素方案不足以证明
|
||
|
||
### 2.1 失败案例: ULINT 计数器(8B 初版)
|
||
|
||
最初的 8B 设计直接把 `nCycles`(ULINT, 小端)拷入 `aOut1[0..7]`,J1900 计算 `f(x)=x*7+3` 写回。该方案的问题:
|
||
|
||
| 字节 | 内容 | 变化频率 |
|
||
|---|---|---|
|
||
| 0 | nCycles 低字节 | 每周期 |
|
||
| 1 | | 每 256 周期 |
|
||
| 2 | | 每 65536 周期 |
|
||
| 3 | | 每 1677 万周期(≈4.6 小时) |
|
||
| 4–7 | 恒为 0 | **从不变化** |
|
||
|
||
结论:这种证据只能证明低 2~3 字节在传输,**无法排除"高字节根本没被映射"的可能**。用户指出的"不要只改变一个字节就说成功了"正是针对此类证据。
|
||
|
||
### 2.2 验证设计必须满足的性质
|
||
|
||
- 8 个字节**互不相同**(避免字节间串扰被掩盖);
|
||
- 8 个字节**每周期全部变化**(任何一字节断传都会立即表现为失配);
|
||
- 回传是**逐字节独立**的非平凡变换(证明每字节都被对端软件读取并处理);
|
||
- 校验**容忍桥接管线延迟**(不能假设固定的往返周期数)。
|
||
|
||
---
|
||
|
||
## 3. 验证协议原理
|
||
|
||
### 3.1 发送图案(TwinCAT 侧, 1 kHz)
|
||
|
||
```
|
||
aOut1[i] = (nCycles + i·32) mod 256, i = 0..7
|
||
```
|
||
|
||
性质:
|
||
- 步进 32、模 256:8 个值在同一周期内互不重叠;
|
||
- 每周期整体 +1:8 字节全部随周期变化;
|
||
- 以 256 为周期循环:任意 16 个连续 PLC 周期的 8 字节组**两两不同**(因为 16 < 256),这保证了历史环匹配不会出现跨周期误判。
|
||
|
||
### 3.2 J1900 变换
|
||
|
||
```
|
||
tx[i] = rx[i] XOR 0x5A, i = 0..7
|
||
```
|
||
|
||
- **逐字节独立**: 第 i 字节的输出只依赖第 i 字节的输入 → 每个字节单独构成一条可检验的证据链;
|
||
- **软件才能产生**: XOR 0x5A 不是硬件环回会出现的结果,证明数据进入了 J1900 用户态程序并被改写;
|
||
- **可逆**: TwinCAT 侧用同一常数 XOR 即可还原比较。
|
||
|
||
### 3.3 历史环匹配(TwinCAT 侧)
|
||
|
||
桥接存在约 4 个 PLC 周期的管线延迟(TwinCAT 输出帧 → J1900 处理 → TwinCAT 输入帧)。因此不能用"aIn1 对应当前周期 aOut1"校验。
|
||
|
||
PLC 每周期把刚发送的 8 字节存入 16 槽历史环:
|
||
|
||
```
|
||
hW = nCycles mod 16
|
||
aHist[hW, 0..7] = aOut1[0..7]
|
||
```
|
||
|
||
校验时与全部 16 个历史槽做整组比较:
|
||
|
||
```
|
||
bSync = TRUE ⟺ ∃h: ∀i∈[0,7]: (aIn1[i] XOR 0x5A) = aHist[h, i]
|
||
nMatchLag = (hW − h + 16) mod 16
|
||
```
|
||
|
||
- **整组匹配**: 只有 8 个字节**同时**等于某一历史周期发送值时才判真 — 任何一个字节出错都会导致失配;
|
||
- **延迟自测量**: 匹配槽位直接给出往返延迟 `nMatchLag`,无需预设。
|
||
|
||
### 3.4 判读标准
|
||
|
||
| 判据 | 通过条件 | 实测 |
|
||
|---|---|---|
|
||
| `bSync` | 持续 TRUE | ✅ |
|
||
| `nMatchLag` | 稳定小值(< 16) | ✅ 恒为 4 |
|
||
| `nMismatch` | 数据流建立后**零增长** | ✅ 24s 窗口内不变 |
|
||
| J1900 `stale` | 0% | ✅ |
|
||
| J1900 `tx_err/rx_err` | 0 | ✅ |
|
||
|
||
---
|
||
|
||
## 4. 观测方法与时差说明
|
||
|
||
### 4.1 权威判据 vs 采样展示
|
||
|
||
- **权威判据**: PLC 内部 1 kHz 实时执行的 `bSync` / `nMismatch`,数据在同一任务周期内一致采样;
|
||
- **采样展示**: ADS 读 `aOut1` / `aIn1` / `nCycles` 是**分多次请求**完成的,彼此相差可达数毫秒。
|
||
|
||
因此 ADS 采样中 `aIn1 XOR 0x5A` 的 **byte0 偶尔差 ±1**(byte0 每周期变化,而 aOut1 与 aIn1 的快照时刻不同),例如:
|
||
|
||
```
|
||
aOut1(sent) = 3B-5B-7B-9B-BB-DB-FB-1B
|
||
aIn1^5A = 3A-5A-7A-9A-BA-DA-FA-1A ← byte0 差 1,其余 7 字节全等
|
||
```
|
||
|
||
这是**观测时差**,不是传输错误。当 ADS 两次读落在同一毫秒时,8 字节完全一致:
|
||
|
||
```
|
||
aOut1(sent) = 98-B8-D8-F8-18-38-58-78
|
||
aIn1^5A = 98-B8-D8-F8-18-38-58-78 ← 8/8 全等
|
||
```
|
||
|
||
### 4.2 逐字节验证示例(实测样本)
|
||
|
||
| 字节 i | 设计公式 | 发送 aOut1 | 接收 aIn1 | aIn1^0x5A | 判定 |
|
||
|---|---|---|---|---|---|
|
||
| 0 | (n+0)·1 | `98` | `C2` | `98` | ✓ |
|
||
| 1 | n+32 | `B8` | `E2` | `B8` | ✓ |
|
||
| 2 | n+64 | `D8` | `82` | `D8` | ✓ |
|
||
| 3 | n+96 | `F8` | `A2` | `F8` | ✓ |
|
||
| 4 | n+128 | `18` | `42` | `18` | ✓ |
|
||
| 5 | n+160 | `38` | `62` | `38` | ✓ |
|
||
| 6 | n+192 | `58` | `02` | `58` | ✓ |
|
||
| 7 | n+224 | `78` | `22` | `78` | ✓ |
|
||
|
||
---
|
||
|
||
## 5. 验证覆盖矩阵
|
||
|
||
| 验证点 | 方法 | 覆盖 |
|
||
|---|---|---|
|
||
| TwinCAT→J1900 方向 | J1900 rx_buf 非零统计 + PLC 图案被 J1900 正确还原(能 XOR 回去) | ✅ |
|
||
| J1900→TwinCAT 方向 | aIn1 与历史环整组匹配 | ✅ |
|
||
| 字节 0..7 逐一 | 每字节独立图案 + 独立 XOR | ✅ |
|
||
| 软件处理证明 | XOR 0x5A 仅 J1900 用户态可产生 | ✅ |
|
||
| 桥接延迟 | nMatchLag 自测量(4 周期) | ✅ |
|
||
| 稳定性 | nMismatch 零增长、stale=0%、err=0 | ✅ |
|
||
| TwinCAT 配置持久性 | 激活后 _Boot tszip 中 SM2/SM3 记录检查 | ✅ |
|
||
|
||
## 6. 已知局限
|
||
|
||
1. 验证图案为周期性确定图案,未做随机负载压力测试;
|
||
2. `lag=4` 为当前拓扑/周期下的实测值,未验证不同任务周期下的行为;
|
||
3. 8B 配置不含诊断 PDO,"对端是否在线"需以数据流本身判断(失配即掉线)。
|
||
|
||
---
|
||
|
||
## 7. 800B 变体的验证方法
|
||
|
||
800B 工程采用**序列号 + 图案 + 反推校验**协议(类 1KB),与 8B 的 XOR 历史环不同,原因是 800B 要同时验证"大载荷每个字节"与"序号处理"两个维度。
|
||
|
||
### 7.1 协议与验证链
|
||
|
||
```
|
||
TwinCAT 发送: aOut1[0..7] = nCycles; aOut1[i] = (nCycles+i) mod 256
|
||
(i ∈ [16..263] ∪ [280..799], 避开 [264..279] 统计字段)
|
||
J1900 处理: tx[0..7] = rx_seq*7+3; tx[8..15] = 本地周期号;
|
||
tx[264..279] = 抖动/失配/原始 seq; 其余字节原样回显
|
||
TwinCAT 校验: nProcessedSeq = aIn1[0..7]
|
||
nReturnedSeq = (nProcessedSeq - 3) / 7 (MOD 7 = 0 才有效)
|
||
逐字节比对 aIn1[i] == (nReturnedSeq + i) mod 256
|
||
```
|
||
|
||
- **反推校验**:J1900 的 f(x)=x·7+3 可逆,PLC 从回传值反推原始发送周期,无需预设管线延迟(实测 lag=4);
|
||
- **J1900 侧自检**:ticker 对图案区 [16..255] 做 `(tc_seq+i) mod 256` 独立校验(`mism` 计数),与 PLC 侧校验互为对侧证据。
|
||
|
||
### 7.2 与 8B 方法的取舍
|
||
|
||
| 维度 | 8B(XOR 历史环) | 800B(seq+图案反推) |
|
||
|---|---|---|
|
||
| 每字节独立性 | 强(每字节独立 XOR) | 中(图案含周期序号,错位立现) |
|
||
| 延迟测量 | 直接(nMatchLag) | 直接(nCycles − nReturnedSeq) |
|
||
| 大载荷成本 | 历史环 16×8B 比对/周期 | 768 字节比对/周期 |
|
||
| 适合 | 小载荷通路证明 | 应用级带宽验证 |
|
||
|
||
### 7.3 ADS 快照判读(800B 特有)
|
||
|
||
外部 ADS 校验脚本用 `nReturnedSeq` 重建预期图案时,因 `nCycles/nReturnedSeq/aIn1` 分次读取,可能出现 `nReturnedSeq > nCycles`(显示 lag 为负)与全图案"失配"的假象——**以 PLC 内部 1kHz 实时计算的 `bSync` 为唯一权威判据**;ADS 全数组读取仅用于非零覆盖率统计(800B 时应 ≈770+/800)。
|
||
|
||
### 7.4 800B 稳定性判据
|
||
|
||
| 判据 | 通过条件 | 实测 |
|
||
|---|---|---|
|
||
| J1900 周期完整 | 周期数 = 时长 × 频率 | 600000 / 600.0s ✅ |
|
||
| J1900 `mism` | 0 | ✅ |
|
||
| PLC `nMismatch` | 运行窗口内零增长 | 295s 窗口 delta=0;90s 确认 delta=0 ✅ |
|
||
| 传输错误 | tx/rx = 0 | ✅ |
|
||
| 非零覆盖率 | ≈770/800 | 775–776 ✅ |
|