3235 lines
155 KiB
Markdown
3235 lines
155 KiB
Markdown
# 非对称可靠串行传输技术规范
|
||
|
||
**Asymmetric Reliable Serial Transport Technical Specification**
|
||
|
||
**版本:V0.3**<br>
|
||
**日期:2026-09-30**<br>
|
||
**作者:周爽**
|
||
|
||
---
|
||
|
||
## 修订记录
|
||
|
||
| 版本 | 日期 | 说明 |
|
||
|---|---|---|
|
||
| V0.3 | 2026-09-30 | 新增基于Transaction帧结构的典型业务应用配置,明确请求与响应封装、设备与通道路由、字节序及分片规则,并增加读写分片示意图。 |
|
||
| V0.2 | 2026-09-29 | 删除专用配置帧,将寄存器配置等业务统一纳入DATA载荷;统一术语和分层边界,完善拓扑、同步、重传、解析及帧布局图。 |
|
||
| V0.1 | 2026-09-29 | 整合数据协议、链路同步、非对称可靠传输机制和三层接口,形成首个统一规范基线。 |
|
||
|
||
## 目录
|
||
|
||
- 第一篇 总则与系统模型
|
||
- 第1章 范围、目标与适用边界
|
||
- 第2章 规范性用语与一致性
|
||
- 第3章 术语、角色与方向
|
||
- 第4章 总体架构与工作阶段
|
||
- 第5章 物理承载的通用要求
|
||
- 第二篇 物理承载与时钟配置
|
||
- 第6章 同源时钟与物理拓扑
|
||
- 第7章 物理承载与时钟配置
|
||
- 第三篇 统一数据协议
|
||
- 第8章 数据协议的接口边界
|
||
- 第9章 公共编码规则
|
||
- 第10章 帧类型与标识
|
||
- 第11章 固定训练与同步类帧
|
||
- 第12章 DATA业务数据帧
|
||
- 第13章 DATA载荷的业务定义边界
|
||
- 第14章 CTRL统一控制帧
|
||
- 第15章 CRC32
|
||
- 第16章 扰码与解扰
|
||
- 第17章 封装、解析与边界恢复
|
||
- 第四篇 链路训练、同步与运行期监测
|
||
- 第18章 总体同步流程
|
||
- 第19章 主端顶层状态机
|
||
- 第20章 从端顶层状态机
|
||
- 第21章 主端UL输入延迟扫描
|
||
- 第22章 主端DL输出延迟扫描
|
||
- 第23章 通过窗口与中心点选择
|
||
- 第24章 帧边界建立与正常解析
|
||
- 第25章 运行期持续同步监测
|
||
- 第26章 重新训练与传输状态恢复
|
||
- 第27章 同步机制配置参数
|
||
- 第五篇 非对称可靠传输与重传机制
|
||
- 第28章 传输机制范围、目标与边界
|
||
- 第29章 机制总览
|
||
- 第30章 状态、序号与资源模型
|
||
- 第31章 正常传输流程
|
||
- 第32章 异常处理与恢复流程
|
||
- 第33章 定时参数与失败门限
|
||
- 第34章 事件—动作规范
|
||
- 第35章 传输状态机
|
||
- 第36章 重传机制一致性要求
|
||
- 第六篇 分层架构与层间接口
|
||
- 第37章 数据链路层
|
||
- 第38章 传输协议层
|
||
- 第39章 业务应用层
|
||
- 第40章 层间处理流程
|
||
- 第41章 分层实现一致性要求
|
||
- 第42章 时序预算与实现风险
|
||
- 第43章 数据链路层与传输协议层接收接口
|
||
- 第44章 传输协议层与数据链路层发送接口
|
||
- 第45章 传输协议层与业务应用层接口
|
||
- 第46章 链路状态与恢复接口
|
||
- 第七篇 实现、诊断与验证
|
||
- 第47章 RTL实现输出与诊断契约
|
||
- 第48章 验证与验收要求
|
||
- 第49章 实现基线结论
|
||
|
||
---
|
||
|
||
# 第一篇 总则与系统模型
|
||
|
||
## 1. 范围、目标与适用边界
|
||
|
||
本规范定义一种用于点对点、全双工、同源时钟串行链路的非对称可靠传输技术。规范覆盖线路帧编码、链路训练与同步、运行期边界监测、主端到从端方向的可靠传输与重传、从端到主端方向的无确认传输,以及数据链路层、传输协议层和业务应用层之间的接口契约。
|
||
|
||
本规范不限定必须使用LVDS,也不限定线路速率必须为750 Mbps。LVDS和750 Mbps配置是第7章规定的一种典型物理实现配置。采用其他差分或单端物理承载、其他线路速率或不同的串并转换结构时,只要满足本规范的公共编码、时钟关系、状态行为和层间接口语义,即可形成兼容实现。
|
||
|
||
本规范面向RTL、ASIC、FPGA及功能等价的其他实现。互操作设备必须选择相同的物理实现配置,并实现本规范中所有标记为“必须”的行为。
|
||
|
||
本规范明确以下边界:
|
||
|
||
- 物理承载负责可靠地提供连续串行比特流及所需的相位调节能力;
|
||
- 数据链路层负责训练、同步、边界、加扰、CRC和线路帧封装;
|
||
- 传输协议层负责SEQ、窗口、确认、重传、接收提交和回滚;
|
||
- 业务应用层负责解释和处理有效载荷;
|
||
- 本规范不定义具体业务数据格式,也不规定寄存器映射表。
|
||
|
||
## 2. 规范性用语与一致性
|
||
|
||
“必须”表示互操作实现不可省略的要求;“不得”表示被禁止的行为;“应”表示正常情况下采用的要求,偏离时必须证明不影响互操作;“可以”表示允许的实现选择;“建议”表示不影响设备互操作性的实现指导。
|
||
|
||
当概述、示意图和字段表之间存在理解差异时,按以下顺序确定要求:
|
||
|
||
1. 精确字段表、状态转移条件和数学公式;
|
||
2. 逐项文字规则;
|
||
3. 时序图和状态图;
|
||
4. 说明性示例。
|
||
|
||
帧格式、码字、CRC和扰码的唯一权威定义位于第9章至第17章。同步状态机不得另行改变这些线路编码。传输重试机制的唯一权威定义位于第28章至第36章。第7章的典型LVDS配置只约束声明采用该配置的设备。
|
||
|
||
## 3. 术语、角色与方向
|
||
|
||
### 3.1 术语书写规则
|
||
|
||
本规范采用“中文叙述、英文标识”的统一方式:
|
||
|
||
1. 角色、动作、机制、状态含义和计量单位使用中文;
|
||
2. 协议帧类型、字段名、状态常量、参数名及RTL信号名保留英文标识,并使用代码格式;
|
||
3. 行业通用缩写首次出现时给出中文名称和英文全称,后续使用缩写;
|
||
4. 同一概念不得交替使用中文、英文单词和不同缩写;
|
||
5. `DL`仅表示下行链路,不作为“数据链路层”的缩写;数据链路层在正文中不使用缩写。
|
||
|
||
例如,正文应写为“主端进入接收训练状态`M_RX_TRAIN`”,不得写为“Master进入RX training state”。
|
||
|
||
### 3.2 基本术语
|
||
|
||
| 术语 | 定义 |
|
||
|---|---|
|
||
| 主端(Master) | 负责扫描接收和发送延迟、决定校准结果,并实现`DL`复杂重传控制的一端 |
|
||
| 从端(Slave) | 使用固定采样和发送结构,并实现确定性接收及简化应答的一端 |
|
||
| 下行链路(Downlink,`DL`) | 主端到从端方向 |
|
||
| 上行链路(Uplink,`UL`) | 从端到主端方向 |
|
||
| 业务帧 | 带业务`SEQ`的`DATA`帧 |
|
||
| 控制帧 | `CTRL`帧,不占用业务`SEQ` |
|
||
| 固定帧 | `TRAIN`、`TRAIN_ACK`、`SYNC`、`SYNC_ACK`或`SYNC_RESET` |
|
||
| 逻辑帧 | 传输协议层交给数据链路层的完整帧内容,包括明文`SOF`、协议字段和载荷,不包含`CRC32`且未加扰 |
|
||
| 线路帧 | 数据链路层对逻辑帧追加`CRC32`(适用时)并按规定加扰后,实际在线路上传送的完整位串 |
|
||
| 线路侧(on-wire) | 指经过本规范规定的封装和扰码处理后,实际通过单个`DL`或`UL`物理通道传输的比特、码字或帧 |
|
||
| 采样通过窗口 | 延迟扫描中连续判定为通过的延迟档位范围 |
|
||
| 接收窗口 | `WIN_BYTES`表示的传输协议层可用接收容量 |
|
||
| 链路同步 | 完成训练、双向同步确认和帧边界建立,使链路可以传输普通协议帧 |
|
||
| 传输状态对齐 | 通过`POLL_REQ`和状态控制帧取得`ACK_NEXT`及`WIN_BYTES`的过程 |
|
||
| 回退N帧(Go-Back-N) | 发生错误后从最早未确认序号开始连续重传的机制 |
|
||
| 单位间隔(UI) | 一个线路位的持续时间 |
|
||
| 提交(commit) | `CRC32`、格式、序号及资源检查完成后,将候选帧正式提交给上层 |
|
||
| 回滚(rollback) | 丢弃候选帧,并保证该帧未产生任何上层可见副作用 |
|
||
|
||
### 3.3 通用缩写
|
||
|
||
| 缩写 | 中文名称 | 英文全称或说明 |
|
||
|---|---|---|
|
||
| `SOF` | 帧起始标记 | Start of Frame |
|
||
| `CRC32` | 32位循环冗余校验 | 32-bit Cyclic Redundancy Check |
|
||
| `PRBS7` | 7阶伪随机二进制序列 | Pseudo-Random Binary Sequence 7 |
|
||
| `ACK` | 确认 | Acknowledgement |
|
||
| `ARQ` | 自动重传请求 | Automatic Repeat Request |
|
||
| `LVDS` | 低电压差分信号 | Low-Voltage Differential Signaling |
|
||
| `FPGA` | 现场可编程门阵列 | Field-Programmable Gate Array |
|
||
| `ASIC` | 专用集成电路 | Application-Specific Integrated Circuit |
|
||
| `RTL` | 寄存器传输级 | Register-Transfer Level |
|
||
| `SERDES` | 串并转换器 | Serializer/Deserializer |
|
||
| `SDR` | 单倍数据速率 | Single Data Rate |
|
||
| `DDR` | 双倍数据速率 | Double Data Rate |
|
||
| `PLL` | 锁相环 | Phase-Locked Loop |
|
||
| `MMCM` | 混合模式时钟管理器 | Mixed-Mode Clock Manager |
|
||
| `CDC` | 时钟域交叉 | Clock Domain Crossing |
|
||
| `FIFO` | 先进先出队列 | First In, First Out |
|
||
| `TX` | 发送路径 | Transmit |
|
||
| `RX` | 接收路径 | Receive |
|
||
| `RAM` | 随机存取存储器 | Random-Access Memory |
|
||
| `DMA` | 直接存储器访问 | Direct Memory Access |
|
||
| `PCB` | 印制电路板 | Printed Circuit Board |
|
||
| `BER` | 误码率 | Bit Error Rate |
|
||
| `UI` | 单位间隔 | Unit Interval |
|
||
| `PVT` | 工艺、电压和温度 | Process, Voltage and Temperature |
|
||
| `DNL` | 微分非线性 | Differential Nonlinearity |
|
||
| `INL` | 积分非线性 | Integral Nonlinearity |
|
||
|
||
`DL`和`UL`名称按系统拓扑固定,不随当前观察端点改变。多个从端场景中,每个从端均通过独立的一条`DL`和一条`UL`连接到主端,帧内不设置设备地址。
|
||
|
||
## 4. 总体架构与工作阶段
|
||
|
||
```mermaid
|
||
flowchart TB
|
||
APP[业务应用层] <--> TP[传输协议层]
|
||
TP <--> DL[数据链路层]
|
||
DL <--> PHY[物理承载]
|
||
```
|
||
|
||
系统依次经历资源就绪、`UL`训练、`DL`训练、双向同步确认和运行期通信。运行期中,数据链路层持续维护帧边界并监测同步;传输协议层在`DL`执行累计确认、字节窗口和Go-Back-N重传,在`UL`执行无确认发送和无确认接收。
|
||
|
||
同步丢失时,数据链路层进入对应训练流程。按照本规范的简化策略,`UL`失效触发`UL`与`DL`完整重训。物理重新训练不自动清除传输协议状态;只有完成明确的会话复位流程后,业务`SEQ`和重传状态才重新初始化。
|
||
|
||
## 5. 物理承载的通用要求
|
||
|
||
物理实现必须提供相互独立的`DL`和`UL`连续串行通道。双方必须预先采用一致的线路速率、位序、时钟关系和训练参数。本版不定义在线物理参数协商。
|
||
|
||
物理承载必须满足:
|
||
|
||
1. 两端串行线路速率相同且长期无频差;
|
||
2. 主端能够遍历`UL`采样相位,并能够调节`DL`发送相位或实现等效功能;
|
||
3. 相位调节范围覆盖至少一个完整UI,或通过粗相位与细延迟组合达到等效覆盖;
|
||
4. 接收端能够连续观察串行流,帧间不得出现未定义空洞;
|
||
5. 电气实现满足所选介质的眼图、抖动、共模和耦合要求;
|
||
6. 数据链路层看到的比特流满足第9章规定的位序和字节序。
|
||
|
||
# 第二篇物理承载与时钟配置
|
||
|
||
## 6. 同源时钟与物理拓扑
|
||
|
||
系统可以包含一个主端和一个或多个从端。每个从端拥有一条独立`DL`和一条独立`UL`,不与其他从端复用串行数据线。各链路可以共享同一参考时钟体系,但每条链路独立训练、独立维护延迟和独立判断同步状态。
|
||
|
||
```mermaid
|
||
flowchart TB
|
||
CLK["同源参考时钟"]
|
||
|
||
subgraph LINKS["一个主端与多个从端的独立双向串行链路"]
|
||
direction LR
|
||
M["主端<br/>每个从端配置独立TX和RX"]
|
||
S1["从端1<br/>1个RX和1个TX"]
|
||
S2["从端2<br/>1个RX和1个TX"]
|
||
OMIT["…<br/>省略若干从端"]
|
||
SN["从端N<br/>1个RX和1个TX"]
|
||
|
||
M ~~~ S1
|
||
S1 ~~~ S2
|
||
S2 ~~~ OMIT
|
||
OMIT ~~~ SN
|
||
|
||
M -->|"DL1:主端TX到从端1 RX"| S1
|
||
S1 -->|"UL1:从端1 TX到主端RX"| M
|
||
M -->|"DL2:主端TX到从端2 RX"| S2
|
||
S2 -->|"UL2:从端2 TX到主端RX"| M
|
||
M -->|"DLN:主端TX到从端N RX"| SN
|
||
SN -->|"ULN:从端N TX到主端RX"| M
|
||
end
|
||
|
||
CLK -.->|"派生工作时钟"| M
|
||
CLK -.->|"派生工作时钟"| S1
|
||
CLK -.->|"派生工作时钟"| S2
|
||
CLK -.->|"派生工作时钟"| SN
|
||
```
|
||
|
||
主端和从端的工作时钟必须来自同一参考源,或者来自频率严格同源的派生时钟,因此双方不存在长期频偏。固定相位差、分频启动相位不确定、封装和PCB路径差异、时钟树偏差及PVT漂移仍然存在,必须通过第18章至第27章规定的训练过程确定可靠采样窗口。
|
||
|
||
对任一实现,线路速率必须同时满足两端串并转换关系:
|
||
|
||
\[
|
||
R_{line}=N_M f_{M,parallel}=N_S f_{S,parallel}
|
||
\]
|
||
|
||
其中,\(N_M\)和\(N_S\)分别为两端每个并行时钟周期对应的线路位数。
|
||
|
||
## 7. 物理承载与时钟配置
|
||
|
||
### 7.1 配置声明
|
||
|
||
每一种具体产品或互操作配置必须在配套实现声明中明确:
|
||
|
||
| 参数 | 含义 |
|
||
|---|---|
|
||
| `PHY_TYPE` | 电气接口类型 |
|
||
| `LINE_RATE` | 每条通道的线路比特率 |
|
||
| `REF_CLK_FREQ` | 公共参考时钟频率 |
|
||
| `MASTER_SERDES_RATIO` | 主端串并转换比例 |
|
||
| `SLAVE_SERDES_RATIO` | 从端串并转换比例 |
|
||
| `BIT_ORDER` | 字节及串行位发送顺序;必须与第9章一致 |
|
||
| `DELAY_STEP` | 延迟单元的标称步进 |
|
||
| `DELAY_TAP_COUNT` | 可扫描延迟档位数量 |
|
||
| `AC_COUPLED` | 是否使用AC耦合 |
|
||
| `MAX_FRAME_SIZE` | 所选配置允许的最大线路帧长度 |
|
||
| `TRAIN_TIMEOUT` | 按线路速率换算的训练超时参数 |
|
||
|
||
配置由硬件设计、寄存器或系统集成约束预先确定。本版不设置在线协商帧。
|
||
|
||
### 7.2 相位与延迟能力
|
||
|
||
主端`UL`接收路径必须能够改变采样相位或等效输入延迟;主端`DL`发送路径必须能够改变发送相位或等效输出延迟。`IDELAY`和`ODELAY`是典型FPGA实现名称,并非强制要求。使用PLL相移、相位插值器、可调时钟树或其他等效方法均可。
|
||
|
||
从端可以采用固定采样相位和固定发送相位。训练扫描、窗口判定和中心点选择集中在主端,以降低从端实现复杂度。
|
||
|
||
### 7.3 典型配置:750 Mbps LVDS同源时钟链路
|
||
|
||
本节是说明性的标准实现配置。只有设备声明采用“750 Mbps LVDS典型配置”时,本节参数才成为该设备的互操作要求。
|
||
|
||
| 项目 | 主端 FPGA | 从端 ASIC |
|
||
|---|---:|---:|
|
||
| 物理接口 | LVDS | LVDS |
|
||
| 线路速率 | 750 Mbps/通道 | 750 Mbps/通道 |
|
||
| 公共参考源 | 12 GHz派生 | 12 GHz派生 |
|
||
| 串行处理方式 | 375 MHz DDR | 750 MHz SDR |
|
||
| 并行处理方式 | 4位 @ 187.5 MHz | 1位 @ 750 MHz |
|
||
| 接收延迟调节 | 每通道输入延迟 | 固定采样 |
|
||
| 发送延迟调节 | 每通道输出延迟 | 固定发送 |
|
||
|
||
\[
|
||
12\text{ GHz}/16=750\text{ MHz}
|
||
\]
|
||
|
||
\[
|
||
375\text{ MHz}\times2=750\text{ Mbps}
|
||
\]
|
||
|
||
\[
|
||
187.5\text{ MHz}\times4=750\text{ Mbps}
|
||
\]
|
||
|
||
该配置中,一个UI约为1.333 ns。主端内部每个187.5 MHz周期处理4位,从端每个750 MHz周期处理1位,二者在线路上产生完全相同的750 Mbps比特流。
|
||
|
||
### 7.4 其他配置的适配规则
|
||
|
||
采用其他物理承载或速率时,不得修改帧格式、`SOF`、`LEN`、CRC、扰码、固定训练码型及传输状态语义。所有以帧数为单位的连续检测判据保持不变;以时间或时钟周期表示的等待和超时参数必须按实际线路速率重新计算。延迟扫描范围、延迟档位步进和最小通过窗口必须根据UI及目标时序裕量重新验证。
|
||
|
||
### 7.5 AC耦合与信号完整性
|
||
|
||
采用AC耦合时,发送端仍必须遵循第16章的扰码规则。固定训练帧和`IDLE`依靠其预定义码型获得均衡性质。扰码不能替代通道级基线漂移、最长连续同码、抖动和眼图验证;具体物理配置必须证明最坏业务数据、最大帧和连续控制流满足接收器要求。
|
||
|
||
# 第三篇统一数据协议
|
||
|
||
## 8. 数据协议的接口边界
|
||
|
||
本规范定义帧标识、字段布局、位序、字节序、长度约束、固定训练码型、`CRC32`、扰码/解扰、发送封装、接收解析及格式错误报告。
|
||
|
||
`TRAIN`、`TRAIN_ACK`、`SYNC`、`SYNC_ACK`、`SYNC_RESET`虽由链路状态机处理,其线路表示仍由本规范统一定义。
|
||
|
||
本规范不定义延迟扫描、同步握手顺序、重复发送次数、`SEQ`初始化时机、窗口调度、重传触发、超时参数或链路重新训练策略。这些由工作机制/架构规范定义。本规范只规定解析错误发生后,帧解析器必须满足的安全行为和重新取得可信帧边界的条件。接收解析器报告格式有效事件,并不自行决定该帧在当前状态下是否可以执行。
|
||
|
||
适用链路为点对点全双工同源时钟串行链路;具体物理承载和线路速率由第7章的实现配置声明确定。每个方向独立形成一个连续串行流。多个从端分别使用独立链路,线路帧不含设备地址。逻辑序号不表示物理帧位置。
|
||
|
||
## 9. 公共编码规则
|
||
|
||
### 9.1 位序、字节序与字序
|
||
|
||
1. 每个字节按位0、位1、…、位7 顺序发送。
|
||
2. 16位、32位数值字段均为小端序:低字节先发送。
|
||
3. 每个32位字内部按低字节先行、每字节位0先行的顺序发送;多字帧先发送`W0`,再发送`W1`,依次类推。
|
||
4. 本文`SOF`的 32位数值与其字节列表是同一码字的两种表示。例如 `32'h6A45E574` 对应线路字节 `74 E5 45 6A`。
|
||
|
||
|
||
### 9.2 连续传输与对齐
|
||
|
||
- 所有帧均以 32位字为单位,长度为 4 字节整数倍。
|
||
- 在没有其他帧可发送时,连续发送`IDLE32`。帧之间可以直接相接,不要求额外`IDLE`。
|
||
- 一帧开始后必须连续发送至结束。不得在帧内插入`IDLE`、控制帧、等待字或其他填充。
|
||
- 不使用字节转义、位填充、EOF、8b/10b 或 64b/66b 编码。
|
||
- `PAYLOAD`不自动补齐;提交给编码器的数据长度必须满足本规范。`DATA`和`CTRL`的逻辑帧不包含CRC;数据链路层追加4字节CRC后再执行等长扰码,因此其线路帧比对应逻辑帧增加4字节。
|
||
- 接收解析以已有的 32位字对齐为前提。寻找或恢复这种对齐的方法不属于本规范。
|
||
|
||
### 9.3 逻辑帧与线路帧
|
||
|
||
“逻辑帧”指传输协议层提交给数据链路层的完整帧内容,包括明文`SOF`、协议字段和载荷,不包含CRC且未加扰。“线路帧”指数据链路层对逻辑帧追加CRC(适用时)并按规定加扰后,实际在线路上传送的完整位串。
|
||
|
||
对于`DATA`和`CTRL`,数据链路层以逻辑帧全部字节作为CRC输入,追加CRC字段后保持`SOF`原样,并对`SOF`之后的字段、载荷和CRC逐帧加扰。固定同步类帧和`IDLE`由数据链路层直接生成,整体保持原样,不属于传输协议层提交的逻辑帧。
|
||
|
||
## 10. 帧类型与标识
|
||
|
||
| 类型 | `SOF`/码字的 32位数值 | 发送字节顺序 | 线路帧总长度 | 主体校验 | 主体加扰 |
|
||
|---|---|---|---:|---|---|
|
||
| `TRAIN` | `C4A4E74B` | `4B E7 A4 C4` | 20 B | 固定模式比较 | 否 |
|
||
| `TRAIN_ACK` | `B94D2C66` | `66 2C 4D B9` | 20 B | 固定模式比较 | 否 |
|
||
| `SYNC` | `468EEE32` | `32 EE 8E 46` | 20 B | 固定模式比较 | 否 |
|
||
| `SYNC_ACK` | `3846A67B` | `7B A6 46 38` | 20 B | 固定模式比较 | 否 |
|
||
| `SYNC_RESET` | `871257AE` | `AE 57 12 87` | 20 B | 固定模式比较 | 否 |
|
||
| `DATA` | `6A45E574` | `74 E5 45 6A` | 16~1044 B | `CRC32` | 是 |
|
||
| `CTRL` | `49D523B9` | `B9 23 D5 49` | 16 B | `CRC32` | 是 |
|
||
| `IDLE` | `C4F0B966` | `66 B9 F0 C4` | 4 B | 整字精确匹配 | 否 |
|
||
|
||
所有`SOF`均不加扰。接收端必须精确比较完整 32位,不采用单字节前缀匹配或近似匹配。
|
||
|
||
八种标记均具有 16 个 0 和 16 个 1。标记均衡不等同于任意业务载荷或加扰输出具有严格的连续同码上界。
|
||
|
||
## 11. 固定训练与同步类帧
|
||
|
||
### 11.1 布局
|
||
|
||
五种固定帧共用同一主体:
|
||
|
||
```text
|
||
| SOF:32 bit | PRBS7:128 bit |
|
||
```
|
||
|
||
```mermaid
|
||
flowchart LR
|
||
FSOF["SOF<br/>4字节<br/>偏移0~3"]
|
||
FPRBS["PRBS7<br/>16字节<br/>偏移4~19"]
|
||
FSOF --> FPRBS
|
||
|
||
classDef header fill:#e9effb,stroke:#6d84ba,color:#244475;
|
||
classDef body fill:#fff0e3,stroke:#d7722d,color:#84502d;
|
||
|
||
class FSOF header;
|
||
class FPRBS body;
|
||
```
|
||
|
||
| 字索引 | 内容 |
|
||
|---:|---|
|
||
| `W0` | 对应帧类型的`SOF` |
|
||
| `W1` | `32'h57F020C2` |
|
||
| `W2` | `32'hF634BB99` |
|
||
| `W3` | `32'hE87126D6` |
|
||
| `W4` | `32'h47916753` |
|
||
|
||
这些帧不含`SEQ`、`LEN`、`PAD`、CRC 或任何业务字段;不经过业务扰码器。完整帧为160位,发送时间为 `160/LINE_RATE`;采用第7.3节的750 Mbps典型配置时约为213.333 ns。
|
||
|
||
### 11.2 `PRBS7`精确定义
|
||
|
||
| 项目 | 定义 |
|
||
|---|---|
|
||
| 多项式 | P(x)=x^7+x^6+1 |
|
||
| 状态 | q[6:0] |
|
||
| 每帧初值 | `7'h42`,即 `7'b1000010` |
|
||
| 当前输出 | 旧状态 q[0] |
|
||
| 下一状态 | `{q[6] ^ q[0], q[6:1]}` |
|
||
| 每帧输出数 | 128位 |
|
||
| 下一帧 | 重新加载 7'h42 |
|
||
|
||
多项式的不同实现可能采用不同移位方向。本规范以本节状态更新式及固定字节序列为互操作依据。
|
||
|
||
```systemverilog
|
||
// 每个 PRBS bit 的参考更新;右侧全部取更新前的状态。
|
||
prbs_bit = q[0];
|
||
q_next = {q[6] ^ q[0], q[6:1]};
|
||
```
|
||
|
||
输出字节为:
|
||
|
||
```text
|
||
C2 20 F0 57 99 BB 34 F6 D6 26 71 E8 53 67 91 47
|
||
```
|
||
|
||
本实现的周期是 127位。128位主体包含完整周期和下一周期的首位,恰好有 64 个 0、64 个 1;第 128位是 PRBS 输出,不是填充。结合均衡`SOF`,完整帧恰好有 80 个 0、80 个 1。
|
||
|
||
这五种完整固定帧自身及有序两两拼接的最长连续同码不超过 7位。该结论只针对这些固定码型,不是任意线路流的保证。
|
||
|
||
### 11.3 完整固定帧字节
|
||
|
||
```text
|
||
TRAIN:
|
||
4B E7 A4 C4 C2 20 F0 57 99 BB 34 F6 D6 26 71 E8 53 67 91 47
|
||
|
||
TRAIN_ACK:
|
||
66 2C 4D B9 C2 20 F0 57 99 BB 34 F6 D6 26 71 E8 53 67 91 47
|
||
|
||
SYNC:
|
||
32 EE 8E 46 C2 20 F0 57 99 BB 34 F6 D6 26 71 E8 53 67 91 47
|
||
|
||
SYNC_ACK:
|
||
7B A6 46 38 C2 20 F0 57 99 BB 34 F6 D6 26 71 E8 53 67 91 47
|
||
|
||
SYNC_RESET:
|
||
AE 57 12 87 C2 20 F0 57 99 BB 34 F6 D6 26 71 E8 53 67 91 47
|
||
```
|
||
|
||
### 11.4 类型语义与解析输出
|
||
|
||
| 类型 | 描述性语义 | 解析器输出 |
|
||
|---|---|---|
|
||
| `TRAIN` | 已知训练模式 | 完整训练帧匹配事件 |
|
||
| `TRAIN_ACK` | 训练检测应答 | 完整训练应答匹配事件 |
|
||
| `SYNC` | 同步确认序列 | 完整同步序列匹配事件 |
|
||
| `SYNC_ACK` | 同步确认应答 | 完整同步应答匹配事件 |
|
||
| `SYNC_RESET` | 主端发给从端的链路同步复位请求 | 完整同步复位请求匹配事件 |
|
||
|
||
解析器必须比较全部 160位。`SOF`命中仅用于选择格式,不能单独产生有效事件。是否需要多帧连续正确、重复请求如何处理、何时执行状态切换,均由外部链路状态机决定。
|
||
|
||
## 12. `DATA`业务数据帧
|
||
|
||
### 12.1 线路帧与逻辑帧布局
|
||
|
||
`DATA`线路帧格式如下。逻辑帧由`DATA_SOF`、`SEQ`、`LEN`和`PAYLOAD`组成,即下列格式去除`CRC32`字段后的部分。
|
||
|
||
```text
|
||
| DATA_SOF:4 B | SEQ:2 B | LEN:2 B | PAYLOAD:LEN B | CRC32:4 B |
|
||
```
|
||
|
||
```mermaid
|
||
flowchart LR
|
||
subgraph DATA_LOGICAL["DATA逻辑帧:8 + LEN字节"]
|
||
direction LR
|
||
DSOF["DATA_SOF<br/>4字节<br/>偏移0~3"]
|
||
DSEQ["SEQ<br/>2字节<br/>偏移4~5"]
|
||
DLEN["LEN<br/>2字节<br/>偏移6~7"]
|
||
DPAYLOAD["PAYLOAD<br/>LEN字节<br/>偏移8~8+LEN-1"]
|
||
|
||
DSOF --> DSEQ --> DLEN --> DPAYLOAD
|
||
end
|
||
|
||
DPAYLOAD --> DCRC["CRC32<br/>4字节<br/>偏移8+LEN~11+LEN"]
|
||
|
||
classDef header fill:#e9effb,stroke:#6d84ba,color:#244475;
|
||
classDef payload fill:#fff0e3,stroke:#d7722d,color:#84502d;
|
||
classDef crc fill:#e6f4f4,stroke:#087f8c,color:#175660;
|
||
|
||
class DSOF,DSEQ,DLEN header;
|
||
class DPAYLOAD payload;
|
||
class DCRC crc;
|
||
```
|
||
|
||
| 字节偏移 | 长度 | 字段 | 定义 |
|
||
|---:|---:|---|---|
|
||
| 0 | 4 B | `DATA_SOF` | 第 10 章定义的码字,原样发送 |
|
||
| 4 | 2 B | `SEQ` | 16位无符号业务序号 |
|
||
| 6 | 2 B | `LEN` | 载荷字节数,不包含头部和 CRC |
|
||
| 8 | `LEN` B | `PAYLOAD` | 按原始字节顺序传输的业务数据 |
|
||
| 8+`LEN` | 4 B | `CRC32` | 第 15 章定义的校验值 |
|
||
|
||
`DATA`线路帧解扰后的32位字布局:
|
||
|
||
```text
|
||
W0 = DATA_SOF
|
||
W1[15:0] = SEQ
|
||
W1[31:16] = LEN
|
||
W2 ... = PAYLOAD,按低字节、低 bit 先发送
|
||
W(2+LEN/4) = CRC32
|
||
总字数 = 3 + LEN/4
|
||
```
|
||
|
||
`LEN`必须满足 `4 <= LEN <= 1032` 且 `LEN[1:0] == 0`。本版不支持零长度`DATA`。`DATA`线路帧总长度为16~1044 B;对应逻辑帧长度为12~1040 B。
|
||
|
||
### 12.2 `SEQ`与业务语义边界
|
||
|
||
`SEQ`为模 65536 序号。每条物理链路的每个方向分别维护独立的`DATA`序号空间。
|
||
|
||
格式解析器只报告 CRC/格式通过的`SEQ`和载荷。序号是否在当前窗口、是否重复、是否为期望值,以及数据能否交付应用,由外部接收控制逻辑决定。`PAYLOAD`内部业务含义不在本规范中规定。
|
||
|
||
## 13. `DATA`载荷的业务定义边界
|
||
|
||
`DATA`是本规范唯一带业务`SEQ`的业务帧。其`PAYLOAD`是传输层不透明的字节序列,可以承载普通数据、设备寄存器配置、寄存器回读、命令、响应或其他用户业务内容。
|
||
|
||
### 13.1 本规范规定的内容
|
||
|
||
`DATA`必须遵守第12章规定的外层帧格式、长度范围、字节序、`CRC32`和扰码规则。主端到从端方向的`DATA`使用第28章至第36章规定的可靠传输机制;从端到主端方向的`DATA`使用无确认传输机制。
|
||
|
||
数据链路层和传输协议层只处理`DATA_SOF`、`SEQ`、`LEN`、`PAYLOAD`的完整性以及接收资源,不解释`PAYLOAD`内部字段。
|
||
|
||
### 13.2 由用户业务定义的内容
|
||
|
||
`PAYLOAD`的内部格式完全由业务应用定义,本规范不规定:
|
||
|
||
- 操作码、命令类型或事务类型;
|
||
- 寄存器地址、寄存器宽度、读写方向及连续访问格式;
|
||
- 请求和响应的关联方式;
|
||
- 业务状态码、权限检查和执行结果;
|
||
- 业务数据的版本、子协议或应用级校验。
|
||
|
||
如果使用`DATA`实现从端寄存器配置,主端和从端必须在本规范之外约定相同的载荷格式。该业务定义不得改变`DATA`外层格式,不得引入新的线路`SOF`,也不得改变本规范规定的确认、窗口和重传语义。
|
||
|
||
### 13.3 传输成功与业务执行的边界
|
||
|
||
从端对`DATA`的累计确认只表示该帧已通过线路完整性检查、序号检查和接收资源检查,并已被传输协议层可靠提交。确认不表示载荷中的命令已经执行,也不表示寄存器或其他业务状态已经按发送方预期改变。
|
||
|
||
载荷语义非法、地址越界、访问权限不足或业务执行失败均属于业务应用层结果,不得作为传输协议层的`format_error`、`RETRY_REQ`或重新训练条件。需要业务执行确认时,用户业务应在`DATA`载荷中自行定义响应或回读机制。
|
||
|
||
## 14. `CTRL`统一业务控制帧
|
||
|
||
### 14.1 线路帧与逻辑帧布局
|
||
|
||
`CTRL`逻辑帧固定为12 B,由`CTRL_SOF`、`ACK_NEXT`、`FLAGS`、`RESERVED`和`WIN_BYTES`组成;数据链路层追加4 B `CRC32`后形成16 B线路帧。
|
||
|
||
```text
|
||
| CTRL_SOF:4 B |
|
||
| ACK_NEXT:2 B | FLAGS:1 B | RESERVED:1 B |
|
||
| WIN_BYTES:4 B |
|
||
| CRC32:4 B |
|
||
```
|
||
|
||
```mermaid
|
||
flowchart LR
|
||
subgraph CTRL_LOGICAL["CTRL逻辑帧:12字节"]
|
||
direction LR
|
||
CSOF["CTRL_SOF<br/>4字节<br/>偏移0~3"]
|
||
CACK["ACK_NEXT<br/>2字节<br/>偏移4~5"]
|
||
CFLAGS["FLAGS<br/>1字节<br/>偏移6"]
|
||
CRES["RESERVED<br/>1字节<br/>偏移7"]
|
||
CWIN["WIN_BYTES<br/>4字节<br/>偏移8~11"]
|
||
|
||
CSOF --> CACK --> CFLAGS --> CRES --> CWIN
|
||
end
|
||
|
||
CWIN --> CCRC["CRC32<br/>4字节<br/>偏移12~15"]
|
||
|
||
classDef header fill:#e9effb,stroke:#6d84ba,color:#244475;
|
||
classDef control fill:#fff0e3,stroke:#d7722d,color:#84502d;
|
||
classDef crc fill:#e6f4f4,stroke:#087f8c,color:#175660;
|
||
|
||
class CSOF header;
|
||
class CACK,CFLAGS,CRES,CWIN control;
|
||
class CCRC crc;
|
||
```
|
||
|
||
固定 16 B、4 个 32位字:
|
||
|
||
```text
|
||
W0 = CTRL_SOF
|
||
W1[15:0] = ACK_NEXT
|
||
W1[23:16] = FLAGS
|
||
W1[31:24] = RESERVED
|
||
W2[31:0] = WIN_BYTES
|
||
W3 = CRC32
|
||
```
|
||
|
||
### 14.2 字段语义
|
||
|
||
| 字段 | 定义 |
|
||
|---|---|
|
||
| `ACK_NEXT` | 发送此`CTRL`的端点下一帧期望接收的业务序号;之前的数据已累计接收 |
|
||
| `FLAGS` | 控制请求类别;详见下表 |
|
||
| `RESERVED` | 发送端建议置 0;接收端必须忽略其数值,不参与帧结构合法性判断 |
|
||
| `WIN_BYTES` | 从`ACK_NEXT`开始,接收端允许对方继续占用的传输协议层接收窗口额度,单位为逻辑帧字节 |
|
||
|
||
`RESERVED`虽不参与结构判断,但CRC必须覆盖其实际值。
|
||
|
||
`ACK_NEXT`、`WIN_BYTES`在所有合法`CTRL`中都有效;没有`ACK_VALID`字段。它们描述的是本`CTRL`发送方的接收状态,并非其自身的发送序号。
|
||
|
||
`WIN_BYTES`是以`ACK_NEXT`为锚点的接收窗口公告,不是每次收到控制帧都可累加的新额度。其数值必须为 4 的整数倍,即 `WIN_BYTES[1:0] == 0`;合法范围为 0~`32'hFFFFFFFC`。
|
||
|
||
接收端发布`WIN_BYTES`即承诺保留相应接收能力。新的窗口公告不得撤销发送端依据较早公告已经合法占用的在途额度;已经授予但尚未累计确认的额度,必须继续能够接收对应帧或其重传,直至`ACK_NEXT`推进或链路重新初始化。
|
||
|
||
`DATA`按不含CRC的逻辑帧长度消耗窗口:
|
||
|
||
```text
|
||
FRAME_COST = 8 + LEN,单位为字节
|
||
```
|
||
|
||
这里的8 B包括`SOF`和`SEQ`/`LEN`;`PAYLOAD`为`LEN` B。数据链路层追加的4 B `CRC32`不进入传输协议层缓存,因此不消耗`WIN_BYTES`。`CTRL`、`IDLE`及固定同步类帧也不消耗`WIN_BYTES`。对应线路帧长度仍为`LINE_FRAME_BYTES = FRAME_COST + 4 = 12 + LEN`。
|
||
|
||
发送端收到新的`CTRL`后,先根据`ACK_NEXT`释放已经累计确认的发送帧,再统计从`ACK_NEXT`开始已经发送但尚未确认的不同业务帧所占用的`FRAME_COST`。可供新帧使用的容量为:
|
||
|
||
```text
|
||
AVAILABLE_BYTES = max(WIN_BYTES - OUTSTANDING_BYTES, 0)
|
||
```
|
||
|
||
只有待发送帧的`FRAME_COST`不大于`AVAILABLE_BYTES`时,才允许首次发送该帧。同一`SEQ`帧的重传不得重复占用窗口额度。`WIN_BYTES`=0 时不得首次发送新的`DATA`,但仍可发送重传帧、`CTRL`、`IDLE`和固定同步类帧。缓存释放后,接收端应通过新的`ACK/UPDATE`公告更新后的`WIN_BYTES`;`POLL_REQ`可用于请求对端重新报告当前状态。
|
||
|
||
| `FLAGS` | 名称 | 字段含义 |
|
||
|---:|---|---|
|
||
| 8'h00 | `ACK/UPDATE` | 累计确认及窗口更新 |
|
||
| 8'h01 | `RETRY_REQ` | 同时请求对端从`ACK_NEXT`开始回退重传 |
|
||
| 8'h02 | `POLL_REQ` | 同时请求对端返回其当前接收状态 |
|
||
|
||
位0 表示`RETRY_REQ`,位1 表示`POLL_REQ`。位[7:2] 必须为 0;本版也禁止位[1:0] 同时为 1,因此只有 00、01、02 三个数值合法。
|
||
|
||
`CTRL`不含自己的业务`SEQ`、`LEN`或载荷。解析器不得因收到`CTRL`就自动生成回复;触发动作由外部控制逻辑决定。`CTRL`不得被解释为`TRAIN_ACK`或`SYNC_ACK`。
|
||
|
||
## 15. `CRC32`
|
||
|
||
### 15.1 参数与覆盖范围
|
||
|
||
采用 CRC-32/MPEG-2 参数集。多项式和初始值保持为 32'h04C11DB7 和 32'hFFFFFFFF;输入不反转、输出不反转,最终结果不异或。
|
||
|
||
| 参数 | 数值 |
|
||
|---|---|
|
||
| `Width` | 32 |
|
||
| `Poly` | 32'h04C11DB7 |
|
||
| `Init` | 32'hFFFFFFFF |
|
||
| `RefIn` | `false` |
|
||
| `RefOut` | `false` |
|
||
| `XorOut` | 32'h00000000 |
|
||
| `Check`:ASCII `123456789` | 32'h0376E6E7 |
|
||
| `Residue` | 32'h00000000 |
|
||
|
||
表中的`Residue`是 CRC-32/MPEG-2 参数集的目录值。本协议接收端按第 15.2 节直接比较计算结果和收到的`CRC32`字段,不使用“把线路序列化后的 CRC 字段继续送入 CRC 后检查`Residue`”的方法;后者会受到本协议小端字段封装顺序的影响。
|
||
|
||
覆盖范围:
|
||
|
||
- `DATA`:`SOF`、`SEQ`、`LEN`、`PAYLOAD`。
|
||
- `CTRL`:`SOF`、`ACK_NEXT`、`FLAGS`、`RESERVED`、`WIN_BYTES`。
|
||
- 不包含`CRC32`字段自身,不包含相邻`IDLE`或其他帧。
|
||
- 固定同步类帧与`IDLE`不使用 CRC。
|
||
|
||
### 15.2 输入顺序与结果封装
|
||
|
||
CRC 按逻辑帧的字节顺序处理:先处理`SOF`的第一个线路字节,再依次处理后续字段和载荷字节。由于`RefIn`=`false`,每个输入字节内部必须按位7、位6、…、位0 的顺序进入 CRC 运算。不得把串行器输出的位0 先行物理位流直接作为 CRC 的逐位输入顺序。
|
||
|
||
CRC 使用正常形式多项式 32'h04C11DB7,以寄存器最高位一侧进行非反射运算。开始处理每帧前将 CRC 状态置为 32'hFFFFFFFF;最后一个被覆盖数据位处理完成后,不追加额外的 32 个 0,不反转寄存器内容,也不执行最终异或。此时的 32位 CRC 状态数值就是`CRC32`字段值。
|
||
|
||
`CRC32`字段作为普通 32位数值,仍按第 9.1 节的小端规则封装:低字节先发送,每个字节在线路上位0 先发送。字段的线路序列化规则不改变`RefOut`=`false`的定义。接收端对解扰后的同一逻辑帧字节序列执行相同计算,并将计算得到的 32位数值与收到并按小端序重组的`CRC32`字段直接比较。
|
||
|
||
上述`Width`、`Poly`、`Init`、`RefIn`、`RefOut`、`XorOut`和`Check`值共同构成本协议的 CRC 一致性参数;仅使用“`CRC32`”名称或只匹配多项式,不足以证明实现兼容。
|
||
|
||
接收端使用实际收到的原始`SOF`和解扰后的字段计算 CRC,随后与解扰得到的`CRC32`字段比较。不得把加扰后的字节直接送入此校验,也不得将另一帧的 CRC 状态带入本帧。
|
||
|
||
## 16. 扰码与解扰
|
||
|
||
### 16.1 作用范围及与 10GBASE-R 的关系
|
||
|
||
采用 10GBASE-R 的自同步递推多项式:
|
||
|
||
```text
|
||
G(x) = 1 + x^39 + x^58
|
||
```
|
||
|
||
本协议的作用范围和初始化规则是自定义的:
|
||
|
||
- `DATA`、`CTRL`:`SOF`原样发送,`SOF`后所有位,包括`CRC32`,参与扰码。
|
||
- 每个上述帧在`SOF`结束后、主体第一个位之前,将 58位状态重新加载为全 1。
|
||
- 一帧主体内连续推进状态,不得在头部、载荷或 CRC 边界复位。
|
||
- `SOF`、`IDLE`、五种固定同步类帧期间绕过扰码器,不推进状态。
|
||
- 本协议不引入 64b/66b,也不采用标准以太网的跨块连续状态管理。不能直接使用保持跨帧历史的 IP 默认配置而不检查兼容性。
|
||
|
||
### 16.2 逐位参考算法
|
||
|
||
TX 和 RX 分别维护独立的 58位状态,均初始化为 `{58{1'b1}}`。
|
||
|
||
```systemverilog
|
||
// 加扰:所有右侧状态均为当前 bit 处理前的值。
|
||
wire_bit = plain_bit ^ tx_state[38] ^ tx_state[57];
|
||
tx_state_next = {tx_state[56:0], wire_bit};
|
||
|
||
// 解扰:移入收到的扰码 bit,而不是解扰结果。
|
||
plain_bit = wire_bit ^ rx_state[38] ^ rx_state[57];
|
||
rx_state_next = {rx_state[56:0], wire_bit};
|
||
```
|
||
|
||
若一个时钟处理多个位,必须按低位先行顺序逐次展开,后一个位使用前一个位更新后的状态。不能让一个 32位字的全部位都使用同一个未经推进的旧状态。
|
||
|
||
发送与接收在正确`SOF`后使用相同初值,因此本协议不设置 58位无效区,也不增加额外的解扰预热字段。
|
||
|
||
### 16.3 编码约束
|
||
|
||
扰码是等长处理,不改变`LEN`或帧长,不保证任意输入的严格 DC 均衡或最大连续同码长度。相同明文帧使用相同初值时会得到相同线路帧。固定同步帧和`IDLE`的均衡性质由其码型本身保证。
|
||
|
||
## 17. 封装、解析与边界恢复
|
||
|
||
```mermaid
|
||
flowchart LR
|
||
subgraph TX["发送端"]
|
||
APP_TX["业务应用层提供DATA载荷"] --> TP_TX["传输协议层形成逻辑帧"]
|
||
CTRL_TX["传输协议层形成CTRL逻辑帧"] --> DL_TX["数据链路层计算CRC32"]
|
||
TP_TX --> DL_TX
|
||
DL_TX --> SCR["保持SOF原样<br/>扰码SOF后的字段、载荷和CRC32"]
|
||
FIX_TX["固定同步类帧或IDLE"] --> MUX_TX["完整帧边界仲裁"]
|
||
SCR --> MUX_TX
|
||
end
|
||
|
||
MUX_TX --> LINE["连续串行线路"]
|
||
|
||
subgraph RX["接收端"]
|
||
LINE --> CLASSIFY["在可信边界识别SOF或IDLE"]
|
||
CLASSIFY -->|"DATA或CTRL"| DESCR["解扰并按长度接收"]
|
||
DESCR --> CRC_RX["校验CRC32"]
|
||
CRC_RX --> PARSER["输出候选帧及校验结果"]
|
||
CLASSIFY -->|"固定同步类帧或IDLE"| FIX_RX["完整码型比较"]
|
||
end
|
||
```
|
||
|
||
如上图所示,发送端首先根据帧类型形成逻辑帧。对于`DATA`和`CTRL`,发送端按第 15 章规定的非反射字节输入规则,对明文`SOF`、字段及载荷计算`CRC32`,原样发送`SOF`,并对`SOF`后面的字段、载荷和`CRC32`进行逐帧加扰;固定同步类帧和`IDLE`则绕过 CRC 与扰码路径,按固定码型直接发送。各路径最终汇合为连续、32位对齐的串行数据流。
|
||
|
||
接收端执行发送端的逆过程。在已知 32位字边界处识别原始`SOF`或`IDLE`:`DATA`和`CTRL`按对应结构解扰、计数接收并校验`CRC32`;固定同步类帧和`IDLE`直接进行完整码型比较。只有完整性及字段格式检查全部通过后,解析器才输出有效帧或字段事件;序号接受、同步状态切换、重传及具体业务动作由外部控制逻辑决定。
|
||
|
||
### 17.1 发送封装
|
||
|
||
发送端根据帧类型选择业务帧路径或固定模式旁路。业务帧依次完成字段检查、逻辑帧构造、`CRC32`计算和主体加扰;固定同步类帧及`IDLE`直接输出既定码型。所有路径最终在完整帧边界处进行仲裁和串接。
|
||
|
||
#### 17.1.1 `DATA`
|
||
|
||
1. 上层提交`SEQ`、`LEN`和载荷,编码器检查结构约束;不合法的发送请求不得开始上线。
|
||
2. 在承诺能够连续供给整帧后开始发送。可以预缓存整帧,或使用有确定供给保证的流水线。
|
||
3. 原样发送`DATA_SOF`;同时按第 15.2 节规定的字节顺序和每字节位7 先行顺序,将`SOF`输入本帧 CRC 计算。
|
||
4. 初始化本帧扰码状态为 58 个 1。
|
||
5. 依次生成`SEQ`、`LEN`、`PAYLOAD`;明文同时送入 CRC 计算,经过扰码的位送往线路。
|
||
6. 根据最终 CRC 状态形成`CRC32`字段;该字段不再输入本帧 CRC 累加,但必须继续通过当前扰码状态发送。
|
||
7. 结束本帧,下一字可直接为`IDLE`或下一个完整帧的`SOF`。
|
||
|
||
#### 17.1.2 `CTRL`
|
||
|
||
流程与`DATA`相同,但逻辑主体只有 `ACK_NEXT、FLAGS、RESERVED、WIN_BYTES`,长度固定。发送端建议将`RESERVED`置 0;编码器必须检查`WIN_BYTES`和`FLAGS`的范围,并将`RESERVED`的实际值纳入 CRC。
|
||
|
||
#### 17.1.3 固定同步帧和`IDLE`
|
||
|
||
固定同步帧直接输出对应`SOF`和四个固定 PRBS 字;`IDLE`直接输出一个码字。两者都不经过 CRC 和业务扰码路径。
|
||
|
||
如何仲裁这些发送请求、某种帧发送几次,以及何时允许发送,属于外部工作机制。
|
||
|
||
### 17.2 接收解析
|
||
|
||
接收端先在已知 32位边界处完成帧类型识别,再依据帧类型进入业务帧解扰与校验路径,或进入固定模式比较路径。解析器只在完整帧检查通过后输出有效事件。
|
||
|
||
#### 17.2.1 边界分类
|
||
|
||
在已知帧边界读取一个 32位原始字:
|
||
|
||
- `IDLE`:精确匹配后报告 idle_seen,下一字仍是边界。
|
||
- 五种固定`SOF`:接收后续四个原始字并执行完整模式比较。
|
||
- `DATA`/`CTRL` `SOF`:记录类型;将原始`SOF`输入 CRC;初始化解扰器,再接收主体。
|
||
- 其他值:报告`boundary_error`。寻找下一个可信边界的算法由外部恢复逻辑实现。
|
||
|
||
#### 17.2.2 `DATA`
|
||
|
||
1. 解扰`W1`,按位段提取`SEQ`和`LEN`。
|
||
2. 检查`DATA`长度上限、下限和4字节对齐;必须满足第12.1节。传输层不检查载荷内部格式。
|
||
3. 按该长度接收并解扰载荷,再接收并解扰最后一个 CRC 字。
|
||
4. CRC 计算包含已收到的`SOF`、解扰后的`W1`和全部载荷,不包含 CRC 字自身。
|
||
5. `DATA`通过CRC和外层格式检查后报告完整候选帧。
|
||
6. 接收控制逻辑再决定序号接受和应用交付;解析器不擅自推进外部协议状态。
|
||
|
||
`LEN`不合法时不得将未经限制的数值用于缓存地址、DMA 长度或接收计数。解析器必须报告`length_error`、终止当前候选帧并进入第 17.4 节定义的边界恢复状态。
|
||
|
||
合法范围内的`LEN`也可能已经损坏;无独立头部 CRC 时,错误可能直到帧尾 CRC 或下一边界才暴露。实现不得把“长度范围合法”当成“长度已校验正确”。
|
||
|
||
#### 17.2.3 `CTRL`
|
||
|
||
`SOF`后解扰三个 32位字。第一字包含`ACK_NEXT`、`FLAGS`和`RESERVED`,第二字为`WIN_BYTES`,第三字为 CRC。接收端忽略`RESERVED`的数值;只有 CRC 通过且`WIN_BYTES`、`FLAGS`合法,才产生`ctrl_valid`;此前不得更新任何发送确认或窗口状态。
|
||
|
||
#### 17.2.4 固定帧
|
||
|
||
收到固定`SOF`后,依次比较四个固定 PRBS 字,全部正确才产生对应有效事件。任一位置错误均报告`fixed_pattern_error`,不把部分匹配当成有效控制请求。
|
||
|
||
#### 17.2.5 帧内标记与缓存提交
|
||
|
||
- 接收帧体期间不得把与`SOF`/`IDLE`相同的内容识别为新标记,无论相同模式出现在加扰前还是加扰后。
|
||
- 所有有效动作必须发生在完整校验之后。允许内部暂存载荷,但不得提前进行不可撤销的业务输出或其他业务动作。
|
||
- 可使用整帧缓存,或具有提交/回滚能力的暂存 FIFO;具体结构由实现决定。
|
||
- 在连续流模型下,合法长度由确定的位/32位字数计数接收。本规范不引入额外的帧接收超时字段或计时规则。
|
||
|
||
### 17.3 解析结果契约
|
||
|
||
本节名称表示概念事件,不强制具体 RTL 端口名称、脉冲宽度或握手接口。一个候选帧必须以一个成功结果或一个失败结果结束,不得同时报告成功和失败。
|
||
|
||
| 解析结果 | 产生条件 | 可交付内容 | 必须禁止的动作 | 边界状态 |
|
||
|---|---|---|---|---|
|
||
| idle_seen | 完整匹配`IDLE32` | `IDLE`事件 | 不得更新业务、窗口或控制状态 | 保持可信 |
|
||
| `fixed_valid(type)` | 固定帧`SOF`和全部 128位 PRBS 完整匹配 | 固定帧类型 | 不得仅凭`SOF`提前产生事件 | 保持可信 |
|
||
| `data_candidate_valid` | `DATA`的长度、CRC 和格式全部合法 | `SEQ`、`LEN`、完整`PAYLOAD` | 解析器不得自行判断窗口、重复或交付顺序 | 保持可信 |
|
||
| `ctrl_valid` | `CTRL`的 CRC、`WIN_BYTES`和`FLAGS`全部合法;`RESERVED`被忽略 | `ACK_NEXT`、`WIN_BYTES`、`FLAGS` | 校验完成前不得更新确认、窗口或重传状态 | 保持可信 |
|
||
| `fixed_pattern_error` | 固定`SOF`已识别,但后续 PRBS 不完整匹配 | 错误类型和错误计数信息 | 不得产生任何固定帧有效事件 | 在固定长度后的暂定边界验证下一标记 |
|
||
| `crc_error` | 候选`DATA`或`CTRL`的 CRC 不匹配 | 错误类型;可提供仅供诊断的接收字段 | 不得提交载荷或控制状态 | 按第17.5节验证暂定边界 |
|
||
| `length_error` | `LEN`不满足对应帧约束 | 错误类型;`LEN`仅供诊断 | 不得按非法`LEN`分配缓存或继续无界计数 | 进入恢复 |
|
||
| `format_error` | CRC可以正确,但`CTRL`的`WIN_BYTES`、`FLAGS`等字段非法 | 错误类型及仅供诊断的字段 | 不得产生对应候选有效事件;`RESERVED`的任何取值均不得触发此错误 | 丢弃当前帧并保持下一边界可信 |
|
||
| `boundary_error` | 在预期帧边界未识别任何合法`IDLE`或`SOF` | 接收字仅供诊断 | 不得将该字解释为载荷或控制动作 | 进入恢复 |
|
||
|
||
成功结果只证明线路格式和完整性满足本规范。`DATA`的外层`SEQ`是否在窗口内、是否重复以及是否允许提交,仍由外部接收控制逻辑决定。`CTRL`的`ctrl_valid`可以交给窗口/重传逻辑处理;固定帧事件可以交给链路状态机处理。
|
||
|
||
|
||
### 17.4 错误后的解析行为与边界恢复
|
||
|
||
解析错误必须按是否仍能确定下一帧位置分类处理:
|
||
|
||
| 错误 | 当前候选帧 | 下一边界处理 |
|
||
|---|---|---|
|
||
| `format_error` | 回滚,不产生协议动作 | 帧长已经确定,下一位置仍是可信边界 |
|
||
| `crc_error` | 回滚,按`DL`或`UL`规则报告 | 按第17.5节进入暂定边界验证 |
|
||
| `fixed_pattern_error` | 丢弃固定帧事件 | 固定帧长度已知,下一位置按暂定边界验证 |
|
||
| `length_error` | 立即中止并回滚 | CRC位置不可确定,进入`BOUNDARY_SEARCH` |
|
||
| `boundary_error` | 不建立候选帧 | 进入`BOUNDARY_SEARCH` |
|
||
|
||
`BOUNDARY_SEARCH`执行以下确定性流程:
|
||
|
||
1. 保持已建立的32位字相位,每次移动一个完整32位字检查原始线路数据;
|
||
2. 搜索期间不运行普通帧体解扰,不把未知字交付上层;
|
||
3. 完整匹配一个固定帧,或者连续匹配至少两个`IDLE32`,可重新建立可信边界;
|
||
4. 命中`DATA`或`CTRL` `SOF`时,只建立重新锁定候选;必须完成对应长度、解扰和CRC检查后才恢复可信边界并提交候选;
|
||
5. 候选失败时继续搜索,不得输出候选内容;
|
||
6. 持续无法恢复、32位字相位本身失效或错误达到门限时,由链路同步状态机触发重新训练。
|
||
|
||
所有合法帧均为32位整数倍,因此上述搜索恢复帧边界而不主动改变底层字相位;位相位失效由第25章的滑动搜索和重训机制处理。
|
||
|
||
### 17.5 CRC错误后的暂定边界规则
|
||
|
||
当`DATA`的`LEN`合法,或者当前帧是固定长度的`CTRL`时,接收端必须先按照已确定的帧长到达预期CRC位置,并把CRC之后的下一个32位位置作为**暂定边界**。CRC失败只说明当前帧内容不可接受,不单独证明字边界已经丢失。
|
||
|
||
在暂定边界处:
|
||
|
||
1. 如果识别到`IDLE`或任一合法`SOF`,边界恢复为可信;当前错误帧按方向规则回滚;
|
||
2. 如果既不能识别`IDLE`,也不能识别任何合法`SOF`,才报告`BOUNDARY_ERROR`并进入滑动边界恢复;
|
||
3. 外层`LEN`本身非法时,无法可靠定位CRC,必须立即中止候选帧并进入边界恢复;
|
||
4. 进入恢复前不得在当前帧体内部把与`SOF`相同的数据误认为新帧起点。
|
||
|
||
这一规则取代“任意CRC失败立即进入边界恢复”的旧行为。
|
||
|
||
# 第四篇链路训练、同步与运行期监测
|
||
|
||
## 18. 总体同步流程
|
||
|
||
每条链路独立执行以下顺序,必须先校准`UL`,再校准`DL`:
|
||
|
||
```mermaid
|
||
sequenceDiagram
|
||
participant M as Master
|
||
participant S as Slave
|
||
Note over M,S: 时钟、PLL/MMCM、delay 控制器就绪
|
||
S-->>M: 连续 TRAIN
|
||
Note over M: 每个 IDELAY 最多检测 200 帧<br/>连续 50 个 TRAIN 正确则该点通过
|
||
loop 每个 DL ODELAY 测试点
|
||
M->>S: 持续 TRAIN,单点最多 200 帧时间
|
||
Note over S: 连续 50 个 TRAIN 正确后进入 ACK_ACTIVE
|
||
S-->>M: ACK_ACTIVE 期间持续 TRAIN_ACK
|
||
Note over M: 连续 10 个 TRAIN_ACK 则该点通过
|
||
M->>S: 4 帧时间 IDLE,终止 TRAIN_ACK
|
||
Note over M,S: 再排空 4 帧时间,随后切换 ODELAY
|
||
end
|
||
Note over M: 选择并装载 DL 窗口中心
|
||
M->>S: 持续发送 SYNC
|
||
Note over S: 连续正确检测 10000 个 SYNC
|
||
S-->>M: 连续发送 20 个 SYNC_ACK
|
||
S-->>M: 随后持续发送 SYNC
|
||
Note over M: 连续 10 个 SYNC_ACK 后等待第一个 SYNC<br/>再连续正确检测 10000 个 SYNC
|
||
M->>S: 停止 SYNC,持续发送 IDLE
|
||
Note over S: 检测到合法 IDLE,停止 SYNC并进入 RUN
|
||
S-->>M: IDLE 或合法 UL 协议帧
|
||
Note over M: 确认 Slave进入 RUN,Master进入 RUN
|
||
```
|
||
|
||
设计原则:
|
||
|
||
1. 从端的时钟和串行资源有效后自动发送`TRAIN`,不等待控制命令;
|
||
2. 每个`IDELAY`点最多检测200个固定帧时间;连续正确检测50个`TRAIN`则该点通过,否则超时失败;
|
||
3. `UL`窗口中心装载后,主端扫描`DL` `ODELAY`;
|
||
4. 每个`ODELAY`点持续发送`TRAIN`,单点最多200个固定帧时间;
|
||
5. 从端连续正确检测50个`TRAIN`后锁存 `train_ack_active` 并持续发送`TRAIN_ACK`;本测试点内不再因后续`TRAIN`错误撤销,直到检测到主端发送的`IDLE`间隔;
|
||
6. 主端连续正确检测10个`TRAIN_ACK`则该`ODELAY`点立即通过,不必继续发送满200个`TRAIN`;
|
||
7. 每个`ODELAY`点结束后,主端保持当前`ODELAY`发送4个固定帧时间的`IDLE`,再用4个固定帧时间排空残余`TRAIN_ACK`;确认从端已停止ACK并恢复`TRAIN`后才切换`ODELAY`。异常时可延长,但总点间隔以16个固定帧时间为上限;
|
||
8. 主端得到两个方向的窗口中心后持续发送固定160位`SYNC`;
|
||
9. 从端连续正确检测10000个`SYNC`后,连续发送20个`SYNC_ACK`;
|
||
10. 从端发完20个`SYNC_ACK`后持续发送固定160位`SYNC`;
|
||
11. 主端连续正确检测10个`SYNC_ACK`后,忽略可能剩余的`SYNC_ACK`,检测到第一个`UL` `SYNC`后开始连续计数;
|
||
12. 主端连续正确检测10000个`UL` `SYNC`后停止发送`SYNC`并持续发送`IDLE`;
|
||
13. 从端检测到合法`IDLE`后停止发送`SYNC`、进入运行期,并发送`IDLE`或合法`UL`协议帧;
|
||
14. 主端检测到从端已经进入运行期后进入 `M_RUN`;
|
||
15. `SYNC`采用“持续发送、条件终止、超时失败”;不需要额外的“进入业务状态”控制命令。
|
||
|
||
步骤8和步骤10的`SYNC`持续发送均受超时保护:正常情况下由对端状态变化终止;超过规定时间仍未观察到终止条件,则本次同步失败并进入重新训练。长序列由连续重复固定160位`SYNC`帧构成,不改变单帧长度。
|
||
|
||
固定帧时间为 `160/LINE_RATE`。连续帧数量判据与线路速率无关,具体时间必须按所选物理配置换算。采用第7.3节的750 Mbps典型配置时,一个固定帧为213.333 ns;50帧约10.667 μs,200帧约42.667 μs,8帧点间隔约1.707 μs,10000帧`SYNC`约2.133 ms/方向,20帧`SYNC_ACK`约4.267 μs。
|
||
|
||
## 19. 主端顶层状态机
|
||
|
||
### 19.1 状态图
|
||
|
||
外部硬件复位不作为同步状态。RTL复位只负责初始化状态寄存器、计数器和临时扫描结果,其中主端顶层状态初始化为 `M_WAIT_RESOURCE`。同步模块不产生全局复位请求。
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> M_WAIT_RESOURCE: power_on
|
||
M_WAIT_RESOURCE --> M_RX_TRAIN: resources_ready
|
||
|
||
M_RX_TRAIN --> M_TX_TRAIN: RX window found
|
||
M_RX_TRAIN --> M_RX_TRAIN: RX training failed
|
||
|
||
M_TX_TRAIN --> M_DL_CONFIRM: TX window found
|
||
M_TX_TRAIN --> M_TX_TRAIN: TX training failed and RX healthy
|
||
M_TX_TRAIN --> M_RX_TRAIN: RX lost during TX training
|
||
|
||
M_DL_CONFIRM --> M_UL_CONFIRM: SYNC_ACK confirmed
|
||
M_DL_CONFIRM --> M_TX_TRAIN: ACK timeout and RX healthy
|
||
M_DL_CONFIRM --> M_RX_TRAIN: RX no longer reliable
|
||
|
||
M_UL_CONFIRM --> M_RUN_ENTRY: UL SYNC confirmed
|
||
M_UL_CONFIRM --> M_RX_TRAIN: UL SYNC timeout
|
||
|
||
M_RUN_ENTRY --> M_RUN: peer_run_confirmed
|
||
M_RUN_ENTRY --> M_DL_CONFIRM: run_entry_timeout
|
||
|
||
M_RUN --> M_RX_TRAIN: UL synchronization lost
|
||
M_RUN --> M_TX_TRAIN: Slave reports DL loss
|
||
M_RUN --> M_WAIT_RESOURCE: common resource lost
|
||
```
|
||
|
||
### 19.2 状态行为
|
||
|
||
| 状态 | 主要动作 | 离开条件 |
|
||
|---|---|---|
|
||
| `M_WAIT_RESOURCE` | 等待时钟、MMCM/PLL和延迟控制器可用;撤销 `link_sync_up` | 资源就绪 |
|
||
| `M_RX_TRAIN` | 执行第 21 章`IDELAY`扫描、`UL`窗口分析和中心点装载 | 找到合法窗口;失败时持续重试 |
|
||
| `M_TX_TRAIN` | 执行第 22 章`ODELAY`扫描、`DL`窗口分析和中心点装载 | 找到合法窗口;失败时持续重试 |
|
||
| `M_DL_CONFIRM` | `DL`持续发送`SYNC`;等待从端完成10000个`DL` `SYNC`检测并返回`SYNC_ACK` | 连续收到10个`SYNC_ACK`或超时 |
|
||
| `M_UL_CONFIRM` | `DL`继续持续发送`SYNC`;先忽略剩余`SYNC_ACK`,检测到首个`UL` `SYNC`后连续计数 | 连续收到10000个`SYNC`或超时 |
|
||
| `M_RUN_ENTRY` | 停止发送`SYNC`,持续发送`IDLE`;等待从端返回`IDLE`或合法`UL`帧 | 确认对端进入运行期或超时 |
|
||
| `M_RUN` | 发送`IDLE`/协议帧;执行第 25 章同步监测 | 失步、资源失效或从端返回`TRAIN` |
|
||
|
||
### 19.3 主端的确定性要求
|
||
|
||
- `UL`和`DL`扫描得到合法窗口后装载所选中心点,并直接进入下一同步阶段;
|
||
- 上电后先执行 `M_RX_TRAIN`,RX窗口建立后无条件进入 `M_TX_TRAIN`;
|
||
- 任何`UL`失效都返回 `M_RX_TRAIN`;RX重新训练成功后仍无条件执行完整TX训练;
|
||
- `M_DL_CONFIRM` 和 `M_UL_CONFIRM` 期间,主端均持续发送`SYNC`;
|
||
- `SYNC_ACK`只在 `M_DL_CONFIRM` 统计,必须连续正确收到10个;任一非`SYNC_ACK`固定帧使计数清零;
|
||
- 进入 `M_UL_CONFIRM` 后,主端允许继续收到从端尚未发送完的`SYNC_ACK`;这些剩余ACK不计为错误;
|
||
- `M_UL_CONFIRM` 检测到第一个完整`SYNC`时将`UL` `SYNC`连续计数置1;此后任一非`SYNC`固定帧使计数清零,重新等待下一个完整`SYNC`作为新序列起点;
|
||
- `M_RUN_ENTRY` 期间`DL`持续发送`IDLE`,不允许发送协议帧;
|
||
- `link_sync_up` 只在 `M_RUN` 有效;
|
||
- `UL`失步返回 `M_RX_TRAIN`,随后依次重新训练`UL`和`DL`;能够明确判断为`DL`单向异常时,直接返回 `M_TX_TRAIN`;
|
||
- 从运行期进入定向训练时,如果`DL`仍能发送固定帧,主端先发送完整`SYNC_RESET`,使从端进入 `S_TRAIN`;随后再开始`IDELAY`或`ODELAY`扫描;
|
||
- 公共时钟、MMCM/PLL或公共延迟资源异常时返回 `M_WAIT_RESOURCE`,资源恢复后依次重新训练`UL`和`DL`;
|
||
- 训练失败时停留在对应训练状态持续重试,重试计数仅用于诊断,不使状态机停止;
|
||
- 定向训练和双向确认期间保留传输协议层序号、累计 ACK状态和未确认帧缓存;
|
||
- 主端在 `M_RUN` 收到完整`TRAIN`,表示从端已因`DL`异常返回训练状态;若`UL`接收仍可靠,则直接进入 `M_TX_TRAIN`。
|
||
|
||
## 20. 从端顶层状态机
|
||
|
||
### 20.1 状态图
|
||
|
||
与主端相同,从端外部硬件复位不作为同步状态。RTL复位后将从端同步状态初始化为 `S_WAIT_RESOURCE`;同步模块自身只能在等待资源、训练、确认和运行状态之间转换。
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> S_WAIT_RESOURCE: power_on
|
||
S_WAIT_RESOURCE --> S_TRAIN: resources_ready
|
||
S_TRAIN --> S_SYNC_ACK_TX: 10000 DL SYNC received
|
||
S_SYNC_ACK_TX --> S_UL_SYNC_TX: 20 SYNC_ACK sent
|
||
S_UL_SYNC_TX --> S_RUN: legal run IDLE
|
||
S_SYNC_ACK_TX --> S_TRAIN: sync timeout
|
||
S_UL_SYNC_TX --> S_TRAIN: sync timeout
|
||
S_RUN --> S_TRAIN: sync_lost or sync_reset
|
||
S_RUN --> S_WAIT_RESOURCE: common resource lost
|
||
```
|
||
|
||
### 20.2 状态行为
|
||
|
||
| 状态 | `DL`接收行为 | `UL`发送行为 | 离开条件 |
|
||
|---|---|---|---|
|
||
| `S_WAIT_RESOURCE` | 清空固定帧检测历史,禁止普通帧提交 | 等待资源稳定 | 资源就绪 |
|
||
| `S_TRAIN` | 分别累计连续`TRAIN`和连续`SYNC`;`TRAIN`达到50后等待`IDLE`结束当前测试点 | 默认连续`TRAIN`;`train_ack_active` 有效时持续发送`TRAIN_ACK` | 连续收到10000个有效`SYNC` |
|
||
| `S_SYNC_ACK_TX` | 继续检查`DL`是否保持`SYNC` | 连续发送20个`SYNC_ACK` | 20个发送完成或超时 |
|
||
| `S_UL_SYNC_TX` | 继续接收主端`SYNC`,检测合法`IDLE` | 持续发送`SYNC` | 收到合法运行入口`IDLE`或超时 |
|
||
| `S_RUN` | 解析普通帧并监测同步;处理`SYNC_RESET` | 无协议帧时发送`IDLE` | 失步、资源失效或`SYNC_RESET` |
|
||
|
||
### 20.3 `TRAIN_ACK`调度
|
||
|
||
从端在 `S_TRAIN` 中使用 `train_run_count` 和 `train_ack_active`:
|
||
|
||
1. 默认在`UL`持续发送`TRAIN`;
|
||
2. 每完整接收一个正确`DL` `TRAIN`,`train_run_count` 加一;
|
||
3. `train_ack_active=0` 时,任一预期`TRAIN`不匹配使 `train_run_count` 清零;
|
||
4. `train_run_count` 达到50时置位 `train_ack_active`;
|
||
5. `train_ack_active=1` 时,`UL`在固定帧边界持续发送`TRAIN_ACK`;
|
||
6. `train_ack_active=1` 后,本测试点不再根据后续`TRAIN`正确与否撤销该标志;
|
||
7. 检测到主端在当前`ODELAY`下发送的合法`IDLE`间隔时,清除 `train_ack_active` 和 `train_run_count`,`UL`恢复发送`TRAIN`;
|
||
8. 从识别合法`IDLE`到最后一个残余`TRAIN_ACK`离开从端发送端的延迟必须有确定上界,并由点间排空时间覆盖;
|
||
9. 进入 `S_SYNC_ACK_TX`、`S_UL_SYNC_TX`、`S_RUN` 或重新开始训练时,清零`TRAIN`相关计数和活动标志。
|
||
|
||
从端不需要知道主端当前使用的`ODELAY`值。每个测试点都必须重新累计50个连续正确`TRAIN`,上一点的累计结果不得沿用。
|
||
|
||
### 20.4 从端进入运行期
|
||
|
||
从端不依靠额外控制命令切换到运行期。它连续正确检测10000个`DL` `SYNC`后进入 `S_SYNC_ACK_TX`,连续发送20个`SYNC_ACK`;随后进入 `S_UL_SYNC_TX` 并持续发送`SYNC`。主端确认10000个`UL` `SYNC`后停止发送`SYNC`并持续发送`IDLE`;从端检测到规定数量的连续合法`IDLE`后进入 `S_RUN`,停止发送`SYNC`并发送`IDLE`或合法`UL`协议帧。
|
||
|
||
从端在 `S_SYNC_ACK_TX` 和 `S_UL_SYNC_TX` 中都要求`DL`继续出现合法`SYNC`;若在`IDLE`到来前连续异常达到规定门限,或阶段超时,则放弃本次确认并返回训练流程。
|
||
|
||
## 21. 主端`UL` `IDELAY`扫描子状态机
|
||
|
||
### 21.1 目标
|
||
|
||
`UL`扫描在从端连续发送`TRAIN`时执行。主端改变对应接收链路的`IDELAY`,在每个延迟点搜索字边界并统计完整`TRAIN`匹配结果,得到采样通过窗口。
|
||
|
||
### 21.2 子状态
|
||
|
||
| 子状态 | 动作 | 转移条件 |
|
||
|---|---|---|
|
||
| `RX_SET_DELAY` | 写入当前`IDELAY`延迟档位 | 写命令接受后 |
|
||
| `RX_WAIT_SETTLE` | 等待延迟和接收流水线稳定 | `RX_DELAY_SETTLE_CYCLES` 到期 |
|
||
| `RX_CLEAR_HISTORY` | 清零比较历史、字对齐历史和当前点统计 | 下一拍 |
|
||
| `RX_SEARCH_ALIGNMENT` | 在允许的位滑移范围内搜索完整`TRAIN` | 找到候选边界或搜索超时 |
|
||
| `RX_MEASURE` | 在固定边界上连续检测`TRAIN`;维护连续正确计数和单点总计时 | 连续50个正确,或达到200个帧时间 |
|
||
| `RX_RECORD` | 按第 21.3 节记录通过/失败和错误数 | 下一拍 |
|
||
| `RX_NEXT_POINT` | 选择下一个延迟档位 | 仍有测试点则继续,否则分析 |
|
||
| `RX_ANALYZE_WINDOW` | 找最长连续通过区间并选择中心 | 有合法窗口或失败 |
|
||
| `RX_LOAD_CENTER` | 装载中心延迟档位,等待稳定并重新建立字边界 | 完成后进入`DL`扫描 |
|
||
|
||
### 21.3 测试点判定
|
||
|
||
每个`IDELAY`点的确定判据为:
|
||
|
||
- 改变`IDELAY`并等待稳定后,清零该点的`TRAIN`连续计数、200帧总计时和旧比较历史;
|
||
- 每完整匹配一个160位`TRAIN`,连续计数加一;
|
||
- 任一预期`TRAIN`不匹配,连续计数清零;
|
||
- 连续计数达到50时,该点立即判定通过;
|
||
- 从测量开始达到200个固定帧时间仍未出现连续50个正确`TRAIN`,该点判定失败;
|
||
- 测量期间发生字边界重新搜索、接收溢出或资源失效时,该点失败;
|
||
- 无法在 `RX_ALIGNMENT_SEARCH_LIMIT` 内找到候选边界时,该点失败。
|
||
|
||
50帧判据用于窗口扫描,不作为链路BER证明。最终选择的窗口中心还要通过双向各10000个连续`SYNC`完成同步确认。
|
||
|
||
### 21.4 字边界与延迟的关系
|
||
|
||
`IDELAY`调整位采样相位,位滑移/齿轮箱调整 4位并行字的分组边界。每次改变`IDELAY`后都必须清除旧比较历史。若器件特性可能使跨延迟档位的采样产生位滑移,应在每个点重新允许有限范围的字边界搜索。
|
||
|
||
## 22. 主端`DL` `ODELAY`扫描子状态机
|
||
|
||
### 22.1 目标
|
||
|
||
`UL`校准完成后,主端已能可靠接收`TRAIN_ACK`。每个`ODELAY`点持续发送`TRAIN`,最多测试200个固定帧时间;主端连续正确收到10个`TRAIN_ACK`时立即判定该点通过。`TRAIN_ACK`不携带延迟档位或轮次,因此相邻测试点之间必须使用明确的`TRAIN`中断和ACK排空间隔。
|
||
|
||
### 22.2 子状态
|
||
|
||
| 子状态 | 动作 | 转移条件 |
|
||
|---|---|---|
|
||
| `TX_SET_DELAY` | 写入当前`ODELAY`延迟档位 | 写命令接受后 |
|
||
| `TX_WAIT_SETTLE` | 等待延迟和发送流水线稳定 | `TX_DELAY_SETTLE_CYCLES` 到期 |
|
||
| `TX_CLEAR_ACK_COUNT` | 清除当前点 ACK 计数和旧固定帧事件 | 下一拍 |
|
||
| `TX_SEND_TRAIN` | 持续发送`TRAIN`,同时维护ACK连续计数和200帧单点计时 | 连续10个ACK,或单点超时 |
|
||
| `TX_RECORD` | 按第 22.3 节记录通过/失败 | 下一拍 |
|
||
| `TX_BREAK_TRAIN` | 保持当前`ODELAY`并连续发送`IDLE`,使从端退出ACK_ACTIVE | 4个固定帧时间到期 |
|
||
| `TX_DRAIN_ACK` | 继续发送`IDLE`并忽略全部`UL` `TRAIN_ACK`,排空残余响应 | 4个固定帧时间到期 |
|
||
| `TX_NEXT_POINT` | 选择下一个延迟档位 | 仍有点则继续,否则分析 |
|
||
| `TX_ANALYZE_WINDOW` | 找最长连续通过区间并选择中心 | 有合法窗口或失败 |
|
||
| `TX_LOAD_CENTER` | 装载中心延迟档位并等待稳定 | 完成后进入双向`SYNC`确认 |
|
||
|
||
### 22.3 测试点判定与应答归属
|
||
|
||
每个`ODELAY`点的确定判据为:
|
||
|
||
- 主端设置`ODELAY`、等待稳定并清除本地ACK检测历史;
|
||
- 主端持续发送`TRAIN`,并从第一个`TRAIN`开始计时;
|
||
- 从端连续正确检测50个`TRAIN`后进入 `train_ack_active`,持续发送`TRAIN_ACK`;
|
||
- 主端每完整匹配一个160位`TRAIN_ACK`,ACK连续计数加一;
|
||
- 任一非`TRAIN_ACK`固定帧使ACK连续计数清零;
|
||
- 主端连续正确收到10个`TRAIN_ACK`时,该点立即通过并停止发送`TRAIN`;
|
||
- 达到200个固定帧时间仍未得到连续10个`TRAIN_ACK`时,该点失败;
|
||
- `UL`失锁、接收溢出或物理资源失效时,该点失败。
|
||
|
||
点结束后必须按以下顺序隔离:
|
||
|
||
1. 保持当前`ODELAY`,连续发送4个固定帧时间的`IDLE`,即20个32位`IDLE`字;
|
||
2. 从端检测到当前`ODELAY`下的合法`IDLE`后清除 `train_ack_active`;
|
||
3. 主端继续发送4个固定帧时间的`IDLE`,即另外20个`IDLE`字,并忽略此期间全部`TRAIN_ACK`;
|
||
4. 点间隔为8个固定帧时间,即 `1280/LINE_RATE`;采用第7.3节的750 Mbps典型配置时为320个187.5 MHz周期,约1.707 μs;
|
||
5. 基线排空结束时,主端应已停止收到`TRAIN_ACK`,并至少检测到一个从端恢复发送的完整`TRAIN`;
|
||
6. 若仍收到`TRAIN_ACK`或尚未检测到`TRAIN`,则继续发送`IDLE`并排空,但点间隔总长度不得超过16个固定帧时间;
|
||
7. 达到16个固定帧时间仍未确认ACK停止,判定点间隔失败,不得把后续ACK归入下一`ODELAY`点;
|
||
8. 点间隔确认成功后设置下一个`ODELAY`,并额外等待 `TX_DELAY_SETTLE_CYCLES`;
|
||
9. 清除ACK历史后才开始下一点`TRAIN`。
|
||
|
||
上述4+4帧是正常基线,总上限16帧用于处理额外流水线延迟。从端从识别`IDLE`到最后一个残余`TRAIN_ACK`离开发送端的延迟必须有确定上界。若实现后的最坏延迟超过16帧预算,必须修改 `TX_POINT_GAP_MAX_FRAMES` 并重新验证,不能让主端带着未清除的ACK历史进入下一测试点。
|
||
|
||
## 23. 通过窗口与中心点选择
|
||
|
||
### 23.1 扫描位图
|
||
|
||
每个扫描点产生一个 `pass[i]`。主端:
|
||
|
||
1. 找出所有连续的通过区间;
|
||
2. 选择长度最大的区间;
|
||
3. 多个区间等长时,选择最接近标称延迟档位的区间;
|
||
4. 仍相同时选择延迟档位编号较小的区间;
|
||
5. 偶数点窗口有两个中心点时,选择更接近标称延迟档位者,仍相同则取较小延迟档位;
|
||
6. 装载中心点;`UL`中心点随后用于接收`TRAIN_ACK`和`UL` `SYNC`,`DL`中心点随后用于发送`TRAIN`和`DL` `SYNC`。
|
||
|
||
### 23.2 最小窗口判据
|
||
|
||
有效窗口必须同时满足:
|
||
|
||
- 连续通过点数不小于 `MIN_PASS_TAPS`;
|
||
- 换算时间宽度不小于 `MIN_PASS_WINDOW_TIME`;
|
||
- 中心点到左右失败边界均留有规定余量;
|
||
- 窗口未在扫描范围边界被截断。
|
||
|
||
通过区间触及最小或最大延迟档位表示可能未观察到真实眼图边界。必须扩大粗相位/扫描范围后重扫,或判定校准不完整。
|
||
|
||
项目初始目标可取:
|
||
|
||
\[
|
||
MIN\_PASS\_WINDOW\_TIME \ge 0.4UI \approx 533.3\ \text{ps}
|
||
\]
|
||
|
||
该值是工程起点,不替代正式时序预算。
|
||
|
||
### 23.3 跨延迟档位回卷
|
||
|
||
若延迟形成周期性相位空间,RTL 必须明确选择环形位图算法,或先用粗相位把眼图移到线性扫描范围内部。两种方法只能选择一种并写入集成参数。
|
||
|
||
## 24. 帧边界建立与正常解析
|
||
|
||
### 24.1 固定帧搜索
|
||
|
||
训练期可以在允许的位滑移候选位置搜索固定帧,但产生固定帧事件前必须完成 160位全帧比较。
|
||
|
||
- 初始字边界至少需要 `ALIGN_CONFIRM_FRAMES` 个连续完整固定帧;
|
||
- 任一候选帧不匹配使连续计数清零;
|
||
- 锁定后仅在确定的 32位边界检查`SOF`/`IDLE`;
|
||
- 进入普通帧后,直到该帧声明的结束位置都不得在载荷内重新搜索`SOF`。
|
||
|
||
### 24.2 普通帧正常解析条件
|
||
|
||
1. 在已知 32位边界匹配`DATA`或`CTRL` `SOF`;
|
||
2. 外层长度字段编码完整;
|
||
3. 长度满足协议规定的最小值、最大值和 4-字节对齐;
|
||
4. 按长度计数恰好到达 CRC 和帧结束位置;
|
||
5. 接收期间没有资源失效、位滑移或本地 FIFO 溢出。
|
||
|
||
CRC失败但长度合法时,当前帧内容不可交付;根据声明长度计算得到的下一位置作为暂定边界。若该位置出现合法`IDLE`或`SOF`,边界恢复为可信并继续解析;否则进入恢复。长度非法、提前结束、超出实现上限或计数无法到达合法边界时,边界直接判定为不可信。
|
||
|
||
## 25. 运行期持续同步监测
|
||
|
||
### 25.1 监测状态机
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> MON_LOCKED_BOUNDARY
|
||
MON_LOCKED_BOUNDARY --> MON_LOCKED_BOUNDARY: valid IDLE
|
||
MON_LOCKED_BOUNDARY --> MON_IN_FRAME: valid SOF and legal length
|
||
MON_IN_FRAME --> MON_LOCKED_BOUNDARY: frame end and legal length
|
||
MON_LOCKED_BOUNDARY --> MON_RECOVERY: unknown word or illegal length
|
||
MON_IN_FRAME --> MON_RECOVERY: boundary or overflow error
|
||
MON_RECOVERY --> MON_LOCKED_BOUNDARY: recovery_confirmed
|
||
MON_RECOVERY --> MON_SYNC_LOST: search_limit_reached
|
||
MON_LOCKED_BOUNDARY --> MON_SYNC_LOST: physical resource lost
|
||
MON_IN_FRAME --> MON_SYNC_LOST: physical resource lost
|
||
```
|
||
|
||
### 25.2 边界状态定义
|
||
|
||
运行期边界分为三种可信度:
|
||
|
||
| 边界状态 | 含义 | 允许的动作 |
|
||
|---|---|---|
|
||
| 可信边界 | 当前32位位置已由`IDLE`、完整固定帧或上一完整帧长度确定 | 可以识别`IDLE`、`SOF`并开始新帧 |
|
||
| 暂定边界 | 位置由一个长度合法但CRC失败的帧推算得到,尚未由下一标志确认 | 只能检查下一`IDLE`或`SOF`,不得提交前一帧 |
|
||
| 边界丢失 | 无法确定下一个32位帧起点,或位/字相位已经变化 | 禁止业务提交,进入边界恢复 |
|
||
|
||
`MON_LOCKED_BOUNDARY` 内部应使用 `boundary_provisional` 标志区分可信边界和暂定边界。CRC失败且长度合法时置位该标志;下一位置匹配合法`IDLE`或`SOF`后清零;匹配失败则进入 `MON_RECOVERY`。暂定状态最多维持到下一预期边界,不允许跨越多个未确认帧。
|
||
|
||
边界确定必须遵循以下优先级:
|
||
|
||
1. 物理资源失效、明确位滑移或接收溢出优先级最高,直接判定边界丢失;
|
||
2. 已经进入普通帧时,只能根据该帧已验证的长度计算结束位置;
|
||
3. 仅在预期帧边界上识别`IDLE`和`SOF`;
|
||
4. `SOF`单独匹配只能建立候选起点,不能证明完整帧有效;
|
||
5. 固定训练类帧必须完整匹配160位后才能确认其边界和类型。
|
||
|
||
### 25.3 不同情况下的边界确定方法
|
||
|
||
| 当前情况 | 当前边界如何确定 | 下一边界如何确定 | 失败处理 |
|
||
|---|---|---|---|
|
||
| 训练完成后进入运行期 | 由连续完整`SYNC`及随后连续`IDLE`建立32位相位 | 每个`IDLE`后移动1个32位字 | `IDLE`确认不足时不得进入`RUN` |
|
||
| 正常`IDLE` | 在可信32位边界完整匹配 `32'hC4F0B966` | 当前边界加1个32位字 | 不匹配任何合法`SOF`时进入恢复 |
|
||
| 固定160位帧 | 在候选起点完整匹配`SOF`和128位`PRBS7` | 当前边界加5个32位字 | 只匹配`SOF`或PRBS错误不得产生固定帧事件 |
|
||
| `DATA` | 在可信边界匹配`DATA` `SOF`,并取得合法`LEN` | 当前边界加 `3 + LEN/4` 个32位字 | `LEN`非法立即进入恢复 |
|
||
| `CTRL` | 在可信边界匹配`CTRL` `SOF` | `CTRL`固定4个32位字,下一边界为当前边界加4 | 固定长度未完整接收、溢出或物理错误时进入恢复 |
|
||
| `DATA`/`CTRL` CRC正确 | 起点和帧长均已确认,CRC证明帧内容完整 | 按对应帧长得到的下一边界转为可信边界 | 下一位置仍必须出现`IDLE`或合法`SOF` |
|
||
| CRC错误但帧长可确定 | 起点和已确定的帧长仍可用于推算位置,但内容不可交付 | 按帧长得到暂定边界,并检查该位置的`IDLE`或合法`SOF` | 下一标志合法则恢复为可信;否则进入恢复 |
|
||
| `CTRL`格式错误 | `CTRL`固定长度已知,CRC位置仍可确定 | 当前边界加4个32位字 | 丢弃该`CTRL`,不更新确认或窗口状态 |
|
||
| `LEN`越界、低2位非零或无法完整取得`LEN` | 无法安全确定帧总长度 | 不使用收到的`LEN`继续计数 | 立即进入恢复 |
|
||
| `LEN`被误码改变但仍落在合法范围 | 接收端暂时无法识别该错误,按收到的`LEN`计数 | 在计算位置校验CRC和下一标志 | CRC或下一标志通常失败,随后进入恢复;等待时间受最大帧长限制 |
|
||
| 预期边界出现未知32位字 | 原边界与线路内容不一致 | 无法计算下一边界 | 立即进入恢复 |
|
||
| 已确认位滑移、齿轮箱位滑移或FIFO溢出 | 原有32位相位不再可信 | 不沿用任何旧长度或边界历史 | 清除解析历史并进入恢复 |
|
||
| MMCM/PLL失锁、延迟控制器失效或时钟异常 | 物理采样本身不可信 | 不执行边界搜索 | 立即撤销 `link_sync_up` 并返回训练流程 |
|
||
| 普通帧无缝背靠背发送 | 前一帧长度确定后一帧起点 | 前一帧下一边界直接匹配后一帧`SOF` | 不要求两帧之间插入`IDLE` |
|
||
|
||
`DATA`的线路帧总长度为 `LINE_FRAME_BYTES = 12 + LEN` 字节;`CTRL`固定为16字节;固定训练类帧固定为20字节;`IDLE`固定为4字节。因此,在已知帧起点和合法`LEN`时,RTL应使用字计数直接生成 `expected_next_boundary`,不得通过搜索载荷中的`SOF`推测帧尾。
|
||
|
||
### 25.4 普通帧内的边界维护
|
||
|
||
进入 `MON_IN_FRAME` 后:
|
||
|
||
1. 锁存帧类型、起始位置和合法`LEN`;
|
||
2. `DATA`将剩余字数装载为 `2 + LEN/4`,对应`SOF`之后的`SEQ`/`LEN`字、载荷和CRC;`CTRL`将剩余字数装载为3;
|
||
3. 每接收一个32位字递减剩余字数;
|
||
4. 计数未归零前,任何`IDLE`、`SOF`或固定帧图样都只作为帧内容,不执行同步判断;
|
||
5. 逻辑帧最后一个字输出时置位 `rx_data_last`;随后接收CRC字并在校验结果有效时置位 `rx_crc_valid` 和 `rx_crc_pass`。若实现使用流水线对齐这些信号,仍必须保持“帧数据结束在前、CRC最终结论在后”的接口语义;
|
||
6. 计数归零后的下一个32位位置就是 `expected_next_boundary`;
|
||
7. CRC正确时该位置为可信边界;CRC错误时该位置为暂定边界;
|
||
8. 在该位置完整匹配`IDLE`或合法`SOF`后,边界转为可信;若匹配失败则进入 `MON_RECOVERY`。
|
||
|
||
最大`DATA`帧为1044字节,即261个32位字,线路时间约11.136 μs;`CTRL`为16字节,即4个32位字,约170.667 ns。因此,帧内不搜索`SOF`造成的逻辑失步发现延迟有确定上界。参考时钟、PLL、延迟资源和FIFO溢出监测在帧内仍持续工作,不受帧长影响。
|
||
|
||
### 25.5 边界恢复搜索
|
||
|
||
进入 `MON_RECOVERY` 时,必须清除当前帧类型、剩余长度、解扰状态、CRC状态和此前的`SOF`匹配历史,并禁止向协议层提交数据。
|
||
|
||
当4位并行节拍仍可信、只有32位字起点未知时:
|
||
|
||
1. 每接收4位更新一次32位滑动窗口;
|
||
2. 依次检查一个32位字包含的8种4位偏移;
|
||
3. 在候选位置只匹配未加扰的`IDLE`或各类`SOF`;
|
||
4. 匹配`SOF`后必须继续验证对应完整结构,不能仅凭`SOF`恢复。
|
||
|
||
候选边界通过以下任一方式确认:
|
||
|
||
- 在同一32位相位连续匹配 `RECOVERY_IDLE_WORDS` 个`IDLE`;
|
||
- 完整匹配一个与当前角色允许状态一致的160位固定帧;若该帧为`TRAIN`、`SYNC`或`SYNC_RESET`,还必须执行相应顶层状态转换;
|
||
- 从候选`DATA` `SOF`开始取得合法`LEN`,按长度完成解扰和CRC,并连续得到 `RECOVERY_CONFIRM_FRAMES` 个CRC及边界均正确的普通帧;
|
||
- 从候选`CTRL` `SOF`开始完整接收固定16字节,CRC正确,并满足`CTRL`格式约束。
|
||
|
||
若4位节拍内部的位相位也不可信,接收端必须遍历SERDES/齿轮箱支持的全部位滑移位置;每次改变位滑移后清除滑动窗口和候选历史,再执行上述搜索。只在旧32位相位上寻找`SOF`不能恢复位滑移。
|
||
|
||
恢复成功后,将确认候选的起始位置设为新的可信边界,重新初始化对应帧的解扰和CRC状态。达到 `RECOVERY_SEARCH_LIMIT` 仍不能确认,则置位 `sync_lost`,撤销 `link_sync_up` 并返回训练流程。
|
||
|
||
### 25.6 角色相关固定帧处理
|
||
|
||
| 接收端状态 | 完整固定帧 | 动作 |
|
||
|---|---|---|
|
||
| 主端 `M_RUN` | `TRAIN` | 从端已因`DL`异常退回训练;若`UL`仍可靠则进入 `M_TX_TRAIN` |
|
||
| 主端 `M_RUN` | 其他意外固定帧 | 记录异常;连续达到门限后重训 |
|
||
| 从端 `S_RUN` | `SYNC_RESET` | 立即撤销同步并进入 `S_TRAIN`,不触发全局复位 |
|
||
| 从端 `S_RUN` | 连续`TRAIN`或`SYNC` | 认为主端正在重建链路,进入 `S_TRAIN` 并按训练流程响应 |
|
||
| 任一端训练期 | 与当前状态不一致的固定帧 | 不向上传递;清零对应连续计数,继续或超时恢复 |
|
||
|
||
## 26. 重新训练与传输状态恢复
|
||
|
||
### 26.1 触发条件
|
||
|
||
异常恢复不触发主端或从端的全局复位,而是返回对应训练状态:
|
||
|
||
- `UL`采样或字边界失步:主端进入 `M_RX_TRAIN`;RX恢复后无条件继续执行 `M_TX_TRAIN`;
|
||
- 从端通过`TRAIN`报告`DL`失步,或`DL`确认超时且`UL`仍可靠:主端直接进入 `M_TX_TRAIN`;
|
||
- TX训练期间`UL`也失去可靠接收:返回 `M_RX_TRAIN`,随后重新训练RX和TX;
|
||
- 参考时钟异常、MMCM/PLL失锁或公共延迟资源异常:进入 `M_WAIT_RESOURCE`,资源恢复后重新训练RX和TX;
|
||
- 从端收到完整`SYNC_RESET`:进入 `S_TRAIN`,持续发送`TRAIN`;
|
||
- 双向确认阶段失败:根据仍然可靠的方向返回 `M_RX_TRAIN`、`M_TX_TRAIN`,或者只重新执行确认阶段。
|
||
|
||
训练失败时状态机持续执行相应训练,不因重试次数达到某个值而停止。重试计数只用于诊断。单个 CRC错误、合法帧的内容错误或上层丢包不触发物理重训。
|
||
|
||
### 26.2 物理重训练与会话复位
|
||
|
||
- **物理重训练**只重新建立采样相位和帧边界,保留发送序号、接收期望序号、窗口状态和未确认缓存;
|
||
- **会话复位**清除传输协议状态和缓存,从初始序号开始。会话复位必须由独立系统条件触发,不能由普通失步隐式触发。
|
||
|
||
物理重训练步骤:
|
||
|
||
1. 链路层撤销 `link_sync_up` 并置位 `link_retraining`;
|
||
2. 传输协议层停止提交新帧,并冻结计时器或进入链路不可用状态;
|
||
3. 接收端丢弃尚未得到最终 CRC 结论的半帧;
|
||
4. 完成双向校准、`DL` `SYNC`/`SYNC_ACK`以及`UL` `SYNC`确认后,链路层恢复`IDLE`;
|
||
5. 主端通过`POLL_REQ`获取从端当前累计 ACK 和接收窗口;
|
||
6. 主端依据返回状态继续发送或重传未确认帧。
|
||
|
||
### 26.3 `SYNC_RESET`
|
||
|
||
`SYNC_RESET`是主端请求从端返回训练状态的固定帧。它不触发从端全局复位,也不清除传输状态。从端必须完整匹配160位后进入 `S_TRAIN`。若`DL`已严重失步而无法识别`SYNC_RESET`,从端的运行期监测仍应检测到边界异常并自行进入 `S_TRAIN`。
|
||
|
||
## 27. 同步机制配置参数
|
||
|
||
所有参数必须在 RTL 集成前给出确定值并纳入版本控制。
|
||
|
||
| 参数 | 单位 | 约束/来源 |
|
||
|---|---:|---|
|
||
| `RX_DELAY_MIN/MAX/STEP` | 延迟档位 | `IDELAY`范围和分辨率 |
|
||
| `TX_DELAY_MIN/MAX/STEP` | 延迟档位 | `ODELAY`范围和分辨率 |
|
||
| `RX_DELAY_SETTLE_CYCLES` | 时钟周期 | 器件稳定时间 + RX 流水线清空 |
|
||
| `TX_DELAY_SETTLE_CYCLES` | 时钟周期 | 器件稳定时间 + TX 流水线清空 |
|
||
| `RX_ALIGNMENT_SEARCH_LIMIT` | 候选位置 | 覆盖所有位滑移相位 |
|
||
| `ALIGN_CONFIRM_FRAMES` | 帧 | 按假锁概率确定 |
|
||
| `UL_TRAIN_PASS_COUNT` | 帧 | 固定为50个连续正确`TRAIN` |
|
||
| `UL_POINT_TIMEOUT_FRAMES` | 帧时间 | 固定为200;到期未通过则该`IDELAY`点失败 |
|
||
| `DL_TRAIN_QUALIFY_COUNT` | 帧 | 固定为50;从端达到后持续发送`TRAIN_ACK` |
|
||
| `DL_ACK_PASS_COUNT` | 帧 | 固定为10个连续正确`TRAIN_ACK` |
|
||
| `DL_POINT_TIMEOUT_FRAMES` | 帧时间 | 固定为200;到期未通过则该`ODELAY`点失败 |
|
||
| `TX_TRAIN_BREAK_FRAMES` | 固定帧时间 | 固定为4;保持当前`ODELAY`发送`IDLE`并终止`TRAIN_ACK` |
|
||
| `TX_ACK_DRAIN_FRAMES` | 固定帧时间 | 基线值为4;必须覆盖残余`TRAIN_ACK`最坏延迟 |
|
||
| `TX_POINT_GAP_MAX_FRAMES` | 固定帧时间 | 固定基线为16;超过仍未确认ACK停止则点间隔失败 |
|
||
| `MIN_PASS_TAPS` | 延迟档位 | 由最小眼宽和延迟档位步进推导 |
|
||
| `MIN_PASS_WINDOW_TIME` | ps | 由时序预算确定 |
|
||
| `DL_SYNC_PASS_COUNT` | 帧 | 固定为10000个连续正确`SYNC` |
|
||
| `SYNC_ACK_TX_COUNT` | 帧 | 固定为20;从端定量发送 |
|
||
| `SYNC_ACK_PASS_COUNT` | 帧 | 固定为10个连续正确`SYNC_ACK` |
|
||
| `UL_SYNC_PASS_COUNT` | 帧 | 固定为10000个连续正确`SYNC` |
|
||
| `SYNC_PHASE_TIMEOUT_FRAMES` | 帧时间 | 必须大于10000并覆盖检测、切换和流水线余量 |
|
||
| `RUN_ENTRY_DL_IDLE_WORDS` | 32位字 | 从端进入`RUN`所需的连续`DL` `IDLE`数 |
|
||
| `RUN_ENTRY_UL_IDLE_WORDS` | 32位字 | 主端确认从端进入`RUN`所需的连续`UL` `IDLE`数 |
|
||
| `RUN_ENTRY_TIMEOUT` | 时钟周期 | 主端和从端完成`RUN`入口握手的最长时间 |
|
||
| `RECOVERY_IDLE_WORDS` | 32位字 | 边界恢复所需连续`IDLE`数 |
|
||
| `RECOVERY_CONFIRM_FRAMES` | 帧 | 普通帧恢复确认数 |
|
||
| `RECOVERY_SEARCH_LIMIT` | 位/时钟周期 | 超过后触发重训 |
|
||
|
||
本表中的50、200、10、10000和20为本规范固定基线。延迟稳定周期、ACK排空时间和各阶段总超时仍须依据目标器件及实际流水线验证;若实测最坏延迟超过基线排空预算,必须增大相应时间参数。
|
||
|
||
计数器按包含终值设计时,50计数至少6位,200计数至少8位,10计数至少4位,20计数至少5位,10000计数至少14位,16帧点间隔计数至少5位。所有连续计数器达到终值后应饱和或立即触发状态转换,不允许回卷。
|
||
|
||
# 第五篇非对称可靠传输与重传机制
|
||
|
||
## 28. 传输机制范围、目标与边界
|
||
|
||
### 28.1 适用范围
|
||
|
||
本规范定义链路同步完成后的业务确认、接收窗口、超时查询、Go-Back-N重传和连续失败后的重新训练触发机制。
|
||
|
||
本规范使用《数据协议标准》中定义的`DATA`、`CTRL`、`IDLE`和固定同步类帧,不重新定义帧格式、CRC、扰码或线路位序。同步训练、延迟校准和完整协议复位流程由链路同步规范定义。
|
||
|
||
### 28.2 设计目标
|
||
|
||
| 方向 | 机制 | 目标 |
|
||
|---|---|---|
|
||
| 主端 → 从端 | 累计ACK、字节窗口、Go-Back-N重传 | 可靠、有序、不重复向上层提交 |
|
||
| 从端 → 主端 | 无确认传输 | CRC与格式正确的帧直接输出;无ACK、无流控、无重传,允许丢帧和重复 |
|
||
|
||
本文中的“业务帧”仅指带`SEQ`的`DATA`。重传层不解释`DATA`载荷。`CTRL`、`IDLE`及固定同步类帧不属于业务序号空间,不进入重传缓存,也不消耗`WIN_BYTES`。
|
||
|
||
### 28.3 规范性用语
|
||
|
||
- **必须、不得**:实现兼容所需的强制行为。
|
||
- **建议**:推荐行为,允许在不影响线路互操作和可靠性的前提下采用等效实现。
|
||
- **可以**:可选实现方式。
|
||
|
||
### 28.4 术语边界
|
||
|
||
| 术语 | 本文中的固定含义 |
|
||
|---|---|
|
||
| 接收 | 线路数据进入帧解析器 |
|
||
| 校验通过 | CRC和数据协议格式全部正确 |
|
||
| 接受 | `SEQ`正确、资源充足,传输层决定保留该帧 |
|
||
| 提交 | 完整帧通过接收缓冲或提交接口交给上层 |
|
||
| 确认 | 从端通过`ACK_NEXT`累计确认业务序号 |
|
||
| 释放 | 主端删除已确认帧的重传缓存和描述符 |
|
||
|
||
## 29. 机制总览
|
||
|
||
本章用于建立整体运行模型;第 30 章以后给出规范性实现细节。
|
||
|
||
### 29.1 主端与从端职责
|
||
|
||
主端负责:
|
||
|
||
- 为主端→从端业务帧分配`SEQ`;
|
||
- 保存所有未确认业务帧;
|
||
- 根据从端报告的`WIN_BYTES`控制首次发送;
|
||
- 检查累计ACK的合理性并释放缓存;
|
||
- 在ACK无进展时发送`POLL_REQ`;
|
||
- 根据`RETRY_REQ`或超时执行Go-Back-N;
|
||
- 连续三轮重传无进展时触发重新训练。
|
||
|
||
从端负责:
|
||
|
||
- 只接受`SEQ`等于`RCV_NEXT`的主端业务帧;
|
||
- 每接受一个业务帧都触发累计ACK;
|
||
- 合并尚未上线的累计ACK;
|
||
- 发现CRC、格式或`SEQ`错误时发送`RETRY_REQ`;
|
||
- 响应主端的`POLL_REQ`;
|
||
- 维护并报告可承诺的接收窗口。
|
||
|
||
### 29.2 运行阶段
|
||
|
||
```text
|
||
完成双向同步
|
||
↓
|
||
Master发送POLL_REQ
|
||
↓
|
||
Slave返回初始ACK_NEXT和WIN_BYTES
|
||
↓
|
||
Master在窗口内连续发送DATA
|
||
↓
|
||
Slave按SEQ接受并主动发送累计ACK
|
||
↓
|
||
Master释放重传缓存、更新窗口并继续发送
|
||
↓
|
||
发生错误:RETRY_REQ或超时触发Go-Back-N
|
||
↓
|
||
连续三轮重传无进展:保留缓存并触发retrain
|
||
```
|
||
|
||
### 29.3 总体数据流
|
||
|
||
```mermaid
|
||
flowchart RL
|
||
subgraph MASTER["Master"]
|
||
direction TB
|
||
MU[Master上层发送]
|
||
MT[可靠发送控制]
|
||
MB[未确认业务帧重传缓存]
|
||
MC[确认、窗口与重传控制]
|
||
MR[无确认接收]
|
||
MO[Master上层接收]
|
||
end
|
||
|
||
subgraph SLAVE["Slave"]
|
||
direction TB
|
||
SR[可靠接收与窗口管理]
|
||
SU[Slave上层接收]
|
||
SX[无确认发送]
|
||
end
|
||
|
||
MU --> MT
|
||
MT <--> MB
|
||
MC --> MT
|
||
MR --> MO
|
||
SR --> SU
|
||
|
||
MT -->|DATA + SEQ| SR
|
||
SR -->|累计ACK / RETRY_REQ / WIN_BYTES| MC
|
||
MC -->|POLL_REQ| SR
|
||
SX -->|DATA,自由递增SEQ| MR
|
||
```
|
||
|
||
### 29.4 核心原理
|
||
|
||
主端为每个新`SEQ`帧只预留一次接收窗口并保存一次重传副本。重传同一`SEQ`只再次占用线路带宽,不增加窗口占用。从端只向上层提交`SEQ`等于`RCV_NEXT`的合法帧,因此主端重复发送已经被接受的帧不会导致重复提交。
|
||
|
||
从端主动累计ACK是正常确认路径。`POLL_REQ`是ACK丢失、零窗口停滞或状态未知时的恢复路径。`RETRY_REQ`是快速错误通知,但主端的本地超时保证即使`RETRY_REQ`丢失也能恢复。
|
||
|
||
## 30. 状态、序号与资源模型
|
||
|
||
### 30.1 状态变量归属
|
||
|
||
| 变量 | 维护端 | 含义 | 主要更新事件 |
|
||
|---|---|---|---|
|
||
| `SND_UNA` | 主端 | 最早尚未累计确认的`SEQ` | 合法前进ACK |
|
||
| `SND_NXT` | 主端 | 下一帧新业务使用的`SEQ` | 新`SEQ`帧首次传输 |
|
||
| RETX_PTR | 主端 | 当前重传位置 | 开始或推进Go-Back-N |
|
||
| `OUTSTANDING_BYTES` | 主端 | 未确认不同`SEQ`帧的总`FRAME_COST` | 新帧、ACK、协议复位 |
|
||
| `PEER_WIN_BYTES` | 主端 | 从端最近合法报告的`WIN_BYTES` | 合法ACK/RETRY响应 |
|
||
| `RCV_NEXT` | 从端 | 下一帧期望接收的`SEQ` | 接受一个合法期望帧 |
|
||
| `ACK_PENDING` | 从端 | 存在尚未上线的状态报告 | 接受帧、窗口恢复、错误或`POLL_REQ` |
|
||
| `RETRY_PENDING` | 从端 | 正在等待`RCV_NEXT`对应帧 | 错误置位,接受期望帧清除 |
|
||
| `WIN_BYTES` | 从端 | 当前可承诺给主端的协议层逻辑帧接收窗口 | 接受帧、上层释放缓存 |
|
||
|
||
### 30.2 模序号
|
||
|
||
16位业务`SEQ`按模65536运算:
|
||
|
||
```text
|
||
SEQ_DISTANCE(A, B) = (B - A) mod 65536
|
||
```
|
||
|
||
为避免回绕比较歧义,任一时刻主端未确认业务帧数量必须小于32768。实现应设置更小的 `MAX_INFLIGHT_FRAMES`,达到该值时停止首次发送新帧。
|
||
|
||
从端接收端不需要判断一个错误`SEQ`是旧帧还是未来帧,只需要判断:
|
||
|
||
```text
|
||
SEQ == RCV_NEXT
|
||
```
|
||
|
||
### 30.3 `FRAME_COST`
|
||
|
||
`FRAME_COST`是一个`DATA`逻辑帧占用的传输协议层窗口字节数,不包括数据链路层追加的CRC:
|
||
|
||
```text
|
||
FRAME_COST = SOF 4 B + SEQ/LEN 4 B + PAYLOAD LEN B
|
||
= 8 + LEN
|
||
|
||
LINE_FRAME_BYTES = FRAME_COST + CRC32 4 B
|
||
= 12 + LEN
|
||
```
|
||
|
||
| 示例 | `LEN` | `FRAME_COST` |
|
||
|---|---:|---:|
|
||
| 最短`DATA` | 4 B | 12 B |
|
||
| 最长`DATA` | 1032 B | 1040 B |
|
||
|
||
### 30.4 `OUTSTANDING_BYTES`与可用窗口
|
||
|
||
```text
|
||
OUTSTANDING_BYTES = Σ FRAME_COST(SEQ)
|
||
SEQ ∈ [SND_UNA, SND_NXT)
|
||
|
||
AVAILABLE_BYTES = max(PEER_WIN_BYTES - OUTSTANDING_BYTES, 0)
|
||
```
|
||
|
||
记账规则:
|
||
|
||
- 新`SEQ`帧首次传输:增加一次`FRAME_COST`。
|
||
- 同一`SEQ`重传:不增加。
|
||
- `ACK_NEXT`向前推进:减去被确认帧的`FRAME_COST`。
|
||
- 完整协议复位:清零。
|
||
|
||
`PEER_WIN_BYTES`是以对应`ACK_NEXT`为锚点的窗口快照,不是增量信用。多个窗口报告不得相加。
|
||
|
||
### 30.5 主端重传缓存
|
||
|
||
主端必须保存每个未确认`DATA`的不含CRC、未加扰逻辑帧:
|
||
|
||
```text
|
||
SOF + SEQ + LEN + PAYLOAD + CRC32
|
||
```
|
||
|
||
推荐实现:
|
||
|
||
```text
|
||
帧RAM:保存完整逻辑帧
|
||
描述符FIFO:保存{RAM起始地址、FRAME_COST或LEN、SEQ}
|
||
```
|
||
|
||
重传不得重新分配`SEQ`。重传时,主端从`SOF`开始重新输出同一逻辑帧;数据链路层重新计算并追加CRC,再从规定初值重新执行逐帧扰码。
|
||
|
||
只有合法累计ACK才能释放缓存。超时、完成重传、无效`CTRL`和物理重新训练均不得直接释放未确认帧。
|
||
|
||
### 30.6 必须保持的不变量
|
||
|
||
```text
|
||
SND_UNA到SND_NXT之间的每个不同SEQ恰好对应一个重传描述符
|
||
|
||
OUTSTANDING_BYTES
|
||
== 所有未确认描述符FRAME_COST之和
|
||
|
||
Master首次发送的新帧总额度不得超过Slave已授予窗口
|
||
|
||
Slave只向上层提交SEQ等于RCV_NEXT的帧
|
||
|
||
同一SEQ重传不产生新的缓存项或窗口费用
|
||
```
|
||
|
||
## 31. 正常传输流程
|
||
|
||
### 31.1 正常流程时序图
|
||
|
||
```mermaid
|
||
sequenceDiagram
|
||
participant M as Master
|
||
participant S as Slave
|
||
|
||
M->>S: POLL_REQ
|
||
S-->>M: ACK/UPDATE, ACK_NEXT=0, WIN_BYTES=W0
|
||
M->>S: DATA, SEQ=0
|
||
S->>S: 校验、提交、RCV_NEXT=1、ACK_PENDING=1
|
||
M->>S: DATA, SEQ=1
|
||
S->>S: 校验、提交、RCV_NEXT=2、合并待发送ACK
|
||
S-->>M: ACK/UPDATE, ACK_NEXT=2, WIN_BYTES=W1
|
||
M->>M: 释放SEQ 0和1,更新窗口
|
||
M->>S: 后续DATA
|
||
```
|
||
|
||
### 31.2 初始化与初始窗口
|
||
|
||
完成新的协议会话同步后:
|
||
|
||
```text
|
||
Master:
|
||
SND_UNA = 0
|
||
SND_NXT = 0
|
||
OUTSTANDING_BYTES = 0
|
||
PEER_WIN_BYTES = 0
|
||
retransmit_fail_count = 0
|
||
清空重传缓存
|
||
|
||
Slave:
|
||
RCV_NEXT = 0
|
||
ACK_PENDING = 0
|
||
RETRY_PENDING = 0
|
||
```
|
||
|
||
主端主动发送`POLL_REQ`。为使其字段确定,规定:
|
||
|
||
```text
|
||
FLAGS = POLL_REQ
|
||
ACK_NEXT = 16'h0000
|
||
RESERVED = 8'h00
|
||
WIN_BYTES = 32'h00000000
|
||
```
|
||
|
||
从端响应:
|
||
|
||
```text
|
||
FLAGS = ACK/UPDATE
|
||
ACK_NEXT = 0
|
||
WIN_BYTES = 当前可用的协议层逻辑帧接收窗口
|
||
```
|
||
|
||
主端收到合法初始响应前不得发送`DATA`。若`WIN_BYTES`为0,主端保持等待并按T_POLL_INTERVAL间隔重新`POLL_REQ`。
|
||
|
||
### 31.3 新`SEQ`帧的首次传输
|
||
|
||
“首次传输”指某个新`SEQ`业务帧区别于其后续重传的第一次上线,不是主端运行后的第一帧。
|
||
|
||
主端按以下顺序处理:
|
||
|
||
1. 使用`SND_NXT`作为新帧`SEQ`。
|
||
2. 形成完整逻辑帧并计算 `FRAME_COST=8+LEN`。
|
||
3. 检查:
|
||
|
||
```text
|
||
FRAME_COST <= AVAILABLE_BYTES
|
||
未确认帧数量 < MAX_INFLIGHT_FRAMES
|
||
当前不处于重传阶段
|
||
```
|
||
|
||
4. 将逻辑帧和描述符写入重传缓存。
|
||
5. 完整发送该帧。
|
||
6. 更新:
|
||
|
||
```text
|
||
OUTSTANDING_BYTES += FRAME_COST
|
||
SND_NXT = SND_NXT + 1 mod 65536
|
||
```
|
||
|
||
7. 如果未确认集合从空变为非空,在该帧最后一位发送完成后启动ACK进度计时。
|
||
|
||
一帧开始后必须连续发送至结束。窗口不足时停止首次发送新业务帧,但`CTRL`仍可发送。
|
||
|
||
### 31.4 从端接受并提交业务帧
|
||
|
||
从端只接受同时满足以下条件的`DATA`业务帧:
|
||
|
||
```text
|
||
CRC和数据协议格式正确
|
||
SEQ == RCV_NEXT
|
||
接收资源足以提交完整帧
|
||
```
|
||
|
||
从端必须先把完整帧提交到传输层接收缓冲或具有提交能力的FIFO,然后执行:
|
||
|
||
```text
|
||
RCV_NEXT = RCV_NEXT + 1 mod 65536
|
||
ACK_PENDING = 1
|
||
```
|
||
|
||
传输层向上层输出`DATA`载荷;载荷解释及业务动作由上层决定。ACK仅表示完整业务帧已经被传输层可靠接收。
|
||
|
||
### 31.5 累计ACK触发与合并
|
||
|
||
每正确接受一个业务帧都必须触发`ACK_PENDING`,但尚未上线的多个ACK允许合并:
|
||
|
||
- 从端只保存一个待发送状态快照。
|
||
- 新帧被接受时,用最新`RCV_NEXT`和`WIN_BYTES`覆盖尚未上线的旧状态。
|
||
- 不为每个未上线ACK建立独立`CTRL`队列。
|
||
- `CTRL`开始发送后字段保持不变。
|
||
- `CTRL`发送期间若又接受新业务帧,必须再次置位`ACK_PENDING`。
|
||
|
||
从端在当前从端→主端帧结束后的下一个帧边界优先发送:
|
||
|
||
```text
|
||
FLAGS = ACK/UPDATE
|
||
ACK_NEXT = RCV_NEXT
|
||
WIN_BYTES = 当前可用的协议层逻辑帧接收窗口
|
||
```
|
||
|
||
开始发送状态`CTRL`时,从端锁存字段并清除本次快照已经覆盖的`ACK_PENDING`。随后发生的新事件具有更高时序优先级,必须重新置位`ACK_PENDING`。
|
||
|
||
### 31.6 主端处理正常累计ACK
|
||
|
||
主端先完成`CTRL`的CRC、格式和合理性检查。定义:
|
||
|
||
```text
|
||
sent_distance = SEQ_DISTANCE(SND_UNA, SND_NXT)
|
||
ack_distance = SEQ_DISTANCE(SND_UNA, ACK_NEXT)
|
||
```
|
||
|
||
必须满足:
|
||
|
||
```text
|
||
ack_distance <= sent_distance
|
||
```
|
||
|
||
| 条件 | 含义与处理 |
|
||
|---|---|
|
||
| `ACK_NEXT` == `SND_UNA` | 同确认点、无进展ACK;不释放帧,可以更新同一确认点的`WIN_BYTES` |
|
||
| 0 < ack_distance <= sent_distance | 合法前进ACK |
|
||
| ack_distance > sent_distance | ACK确认了未发送帧;丢弃整个`CTRL`并记录错误 |
|
||
|
||
合法前进ACK按以下顺序处理:
|
||
|
||
1. 释放 `[SND_UNA, ACK_NEXT)` 的重传缓存项。
|
||
2. 减去这些帧的`FRAME_COST`。
|
||
3. 设置 `SND_UNA=ACK_NEXT`。
|
||
4. 使用本`CTRL`的`WIN_BYTES`替换`PEER_WIN_BYTES`。
|
||
5. 从剩余描述符重新核对`OUTSTANDING_BYTES`。
|
||
6. 清零连续失败计数。
|
||
7. 若仍有未确认帧,重新启动进度计时;否则停止计时。
|
||
|
||
同确认点ACK可能是重复状态、窗口更新或`RETRY_REQ`,不能仅凭 `ACK_NEXT==SND_UNA` 判定线路重复。已经被较新ACK越过的旧确认点及其`WIN_BYTES`必须整体忽略。
|
||
|
||
### 31.7 从端接收窗口维护
|
||
|
||
`WIN_BYTES`是从端当前能够承诺给后续主端业务帧的传输协议层接收窗口额度,以不含CRC的逻辑帧字节数计量,并向下对齐到4字节。数据链路层必须独立配置足够的CRC流水线和固定接收资源,不得占用或减少已经公告的`WIN_BYTES`。
|
||
|
||
从端还必须保证帧描述符数量能够支持所公告的窗口。最短`DATA`逻辑帧的`FRAME_COST`为12 B,因此可以采用以下保守约束:
|
||
|
||
```text
|
||
WIN_BYTES <= free_logical_buffer_bytes
|
||
WIN_BYTES <= 12 × free_frame_descriptor_count
|
||
```
|
||
|
||
最终公告值取上述约束的较小值并向下对齐到4字节。等效的、更保守的资源计算也可以使用,但不得出现主端按已公告`WIN_BYTES`合法发送后从端因描述符不足而拒绝帧的情况。
|
||
|
||
一个帧被接受时按`FRAME_COST`占用资源;对应接收缓冲被上层释放时归还相同额度。从端必须保证已经公布的窗口不会被其他内部用途占用。
|
||
|
||
正常窗口变化随下一次累计ACK报告。为避免零窗口死锁,`WIN_BYTES`从0恢复为非0时,即使没有新业务帧被接受,从端也必须主动置位`ACK_PENDING`并发送`ACK/UPDATE`。
|
||
|
||
### 31.8 正常窗口示例
|
||
|
||
从端报告:
|
||
|
||
```text
|
||
ACK_NEXT=10
|
||
WIN_BYTES=2048
|
||
```
|
||
|
||
主端首次发送三个帧:
|
||
|
||
| `SEQ` | `FRAME_COST` |
|
||
|---:|---:|
|
||
| 10 | 400 B |
|
||
| 11 | 600 B |
|
||
| 12 | 300 B |
|
||
|
||
此时:
|
||
|
||
```text
|
||
OUTSTANDING_BYTES = 1300 B
|
||
AVAILABLE_BYTES = 2048 - 1300 = 748 B
|
||
```
|
||
|
||
重传其中任意帧不会再次增加`OUTSTANDING_BYTES`。从端返回`ACK_NEXT`=12后,主端释放`SEQ` 10和11,再使用该`CTRL`中的新`WIN_BYTES`重新计算可用窗口。
|
||
|
||
### 31.9 从端→主端正常业务
|
||
|
||
从端→主端业务不使用重传、ACK或`WIN_BYTES`流控。从端每发送一个`DATA`,仅执行:
|
||
|
||
```text
|
||
使用当前TX_SEQ
|
||
TX_SEQ = TX_SEQ + 1 mod 65536
|
||
```
|
||
|
||
主端对CRC和格式正确的帧直接解析输出,不因`SEQ`连续、跳变或重复改变处理。CRC或格式错误的帧直接丢弃。若主端本地业务缓存已满,可以丢弃完整业务帧,但必须继续消费线路数据并保持解析边界。
|
||
|
||
## 32. 异常处理与恢复流程
|
||
|
||
### 32.1 异常流程时序图
|
||
|
||
```mermaid
|
||
sequenceDiagram
|
||
participant M as Master
|
||
participant S as Slave
|
||
|
||
M->>S: DATA, SEQ=2,线路损坏
|
||
S->>S: 丢弃,RCV_NEXT保持2
|
||
M->>S: DATA, SEQ=3
|
||
S->>S: SEQ不等于RCV_NEXT,丢弃
|
||
S-->>M: RETRY_REQ, ACK_NEXT=2, WIN_BYTES=W
|
||
M->>M: 暂停新帧,从SEQ=2开始
|
||
M->>S: 重传SEQ=2
|
||
M->>S: 重传SEQ=3
|
||
S-->>M: ACK/UPDATE, ACK_NEXT=4
|
||
M->>M: 释放SEQ=2和3
|
||
```
|
||
|
||
### 32.2 从端检测业务帧错误
|
||
|
||
以下任一情况发生时,从端不得接受或提交候选帧,也不得推进`RCV_NEXT`:
|
||
|
||
- CRC错误;
|
||
- `DATA`的`LEN`不满足下述确定性范围或对齐判据;
|
||
- `SEQ`不等于`RCV_NEXT`;
|
||
- 帧边界恢复后候选帧校验失败;
|
||
- 发送端违反已授予窗口,导致本地资源不足。
|
||
|
||
本节中的长度和字段格式检查只针对主端→从端方向的`DATA`业务帧。候选帧在识别出对应`SOF`并解扰`W1`后,必须按下表检查:
|
||
|
||
| 帧类型 | 必须满足的全部条件 |
|
||
|---|---|
|
||
| `DATA` | `4 <= LEN <= 1032`,且 `LEN[1:0] == 0` |
|
||
|
||
`DATA`载荷内容没有协议层格式限制。载荷语义、地址、权限和业务执行结果由业务应用层处理,不构成传输帧格式错误。`SEQ`是否等于`RCV_NEXT`按本节单独判断,不属于格式检查。
|
||
|
||
`CTRL`、`IDLE`和固定同步类帧不属于本节的业务帧错误判定范围。`CTRL`校验失败时丢弃该`CTRL`且不得更新ACK或窗口状态,不因此发送业务帧`RETRY_REQ`。
|
||
|
||
从端不需要区分`SEQ`是旧值、重复值还是未来值。错误处理统一为:
|
||
|
||
```text
|
||
丢弃候选帧
|
||
RETRY_PENDING = 1
|
||
ACK_PENDING = 1
|
||
```
|
||
|
||
待发送`CTRL`为:
|
||
|
||
```text
|
||
FLAGS = RETRY_REQ
|
||
ACK_NEXT = RCV_NEXT
|
||
WIN_BYTES = 当前实际可用的协议层逻辑帧接收窗口
|
||
```
|
||
|
||
只有正确接受`RCV_NEXT`对应帧才能清除`RETRY_PENDING`。发送一次`RETRY_REQ`不得清除`RETRY_PENDING`。
|
||
|
||
### 32.3 主端处理`RETRY_REQ`
|
||
|
||
主端收到合法`RETRY_REQ`后:
|
||
|
||
1. 按第31.6节检查和处理其中的`ACK_NEXT`与`WIN_BYTES`。
|
||
2. 如果处理后的 `ACK_NEXT == SND_NXT`,表示该`CTRL`没有指向任何已经发送但尚未确认的业务帧。主端必须执行以下动作,然后结束本次`RETRY_REQ`处理:
|
||
|
||
- 按累计ACK结果释放 `[原SND_UNA, ACK_NEXT)` 的全部重传缓存;若`ACK_NEXT`没有推进,则不释放任何缓存;
|
||
- 设置 `SND_UNA=ACK_NEXT`,并从剩余描述符重新核对`OUTSTANDING_BYTES`;此时必须为0;
|
||
- 使用本`CTRL`中的`WIN_BYTES`替换`PEER_WIN_BYTES`,并令 `AVAILABLE_BYTES=PEER_WIN_BYTES`;
|
||
- 不设置RETX_PTR,不启动Go-Back-N,也不增加重传失败计数;
|
||
- 停止ACK进度计时器并退出当前重传状态;
|
||
- 若`ACK_NEXT`相对原`SND_UNA`发生推进,按正常前进ACK清零连续失败计数;若未推进,则不得把它计作ACK进展;
|
||
- 根据新窗口返回正常发送状态:有待发送帧且窗口足够时允许首次发送,否则等待窗口更新或上层业务。
|
||
|
||
3. 如果 `ACK_NEXT != SND_NXT`,停止首次发送新业务帧。
|
||
4. 设置 `RETX_PTR=ACK_NEXT`。
|
||
5. 按原`SEQ`顺序重传未确认帧。
|
||
6. 不增加`OUTSTANDING_BYTES`,不分配新`SEQ`,不建立新描述符。
|
||
7. 重传结束后等待从端主动累计ACK;T_ACK_WAIT无进展时发送`POLL_REQ`。
|
||
|
||
若重传期间收到更大的合法`ACK_NEXT`,主端立即释放已确认前缀,并从新的`SND_UNA`继续,不得重传已经累计确认的帧。
|
||
|
||
### 32.4 ACK或`RETRY_REQ`丢失
|
||
|
||
ACK使用累计确认。某个ACK丢失时,后续更大的`ACK_NEXT`覆盖它。最后一个ACK丢失且没有后续状态时,主端通过T_ACK_WAIT到期及随后一个T_POLL_INTERVAL到期时的`POLL_REQ`恢复。
|
||
|
||
主端不直接检测某个`RETRY_REQ`是否丢失。`RETRY_REQ`丢失表现为`SND_UNA`长期不推进,最终由`POLL_REQ`和T_PROGRESS_LIMIT无进展超时触发Go-Back-N。
|
||
|
||
从端处于`RETRY_PENDING`期间,如果再次收到错误或非期望帧,可以再次置位`ACK_PENDING`;尚未上线的重复`RETRY_REQ`仍合并为最新状态。
|
||
|
||
### 32.5 主端主动`POLL_REQ`
|
||
|
||
从端主动累计ACK是正常路径,`POLL_REQ`仅用于恢复和状态查询。主端在以下情况发送`POLL_REQ`:
|
||
|
||
- 初始化时取得初始`ACK_NEXT`和`WIN_BYTES`;
|
||
- 存在未确认帧且T_ACK_WAIT无ACK推进;
|
||
- 可用窗口不足并持续等待更新;
|
||
- `WIN_BYTES`为0并持续等待恢复;
|
||
- 重传结束后T_ACK_WAIT仍无ACK推进;
|
||
- 上一次`POLL_REQ`没有得到合法响应。
|
||
|
||
从端收到`POLL_REQ`后,在下一个可用帧边界响应:
|
||
|
||
```text
|
||
若RETRY_PENDING=1:FLAGS=RETRY_REQ
|
||
否则: FLAGS=ACK/UPDATE
|
||
|
||
ACK_NEXT = RCV_NEXT
|
||
WIN_BYTES = 当前实际可用的协议层逻辑帧接收窗口
|
||
```
|
||
|
||
主端无需判断是`POLL_REQ`丢失还是响应丢失;两者均按没有收到合法状态处理。
|
||
|
||
### 32.6 窗口不足
|
||
|
||
如果 `FRAME_COST > AVAILABLE_BYTES`,主端停止首次发送新帧并等待从端主动`ACK/UPDATE`。T_POLL_INTERVAL仍未取得足够窗口时发送`POLL_REQ`。
|
||
|
||
窗口不足不允许主端绕过限制发送新帧。`CTRL`不消耗窗口,因此任何窗口值下都可以发送`POLL_REQ`。
|
||
|
||
### 32.7 主端估算窗口与从端本地窗口不一致
|
||
|
||
主端的`AVAILABLE_BYTES`是最近状态快照基础上的保守估计,从端的`WIN_BYTES`是实时本地状态,两者不要求每个时刻数值相等。
|
||
|
||
#### 32.7.1 主端低估窗口
|
||
|
||
主端低估只降低吞吐率。主端停止新帧并等待`ACK/UPDATE`,或在T_POLL_INTERVAL后`POLL_REQ`。收到最新状态后重新计算。
|
||
|
||
#### 32.7.2 主端高估窗口
|
||
|
||
从端必须在接受每帧前独立检查本地资源。如果空间不足:
|
||
|
||
1. 丢弃该帧;
|
||
2. 不推进`RCV_NEXT`;
|
||
3. 发送 `RETRY_REQ + 当前ACK_NEXT + 实际WIN_BYTES`。
|
||
|
||
主端收到状态后从描述符FIFO重新求和,不得只相信增量计数:
|
||
|
||
```text
|
||
OUTSTANDING_BYTES = 当前全部未确认描述符FRAME_COST之和
|
||
```
|
||
|
||
若:
|
||
|
||
```text
|
||
OUTSTANDING_BYTES <= PEER_WIN_BYTES
|
||
```
|
||
|
||
可以按正常Go-Back-N重传。若不满足,主端进入窗口重新同步状态:
|
||
|
||
1. 停止首次发送新帧;
|
||
2. 保留全部未确认缓存;
|
||
3. 从`SND_UNA`开始,只重传累计`FRAME_COST`不超过当前`WIN_BYTES`的最长连续前缀;
|
||
4. 若第一个未确认帧也无法容纳,则等待窗口更新并`POLL_REQ`;
|
||
5. 收到前进ACK后重新计算,再发送下一批。
|
||
|
||
### 32.8 Go-Back-N轮次
|
||
|
||
一次Go-Back-N轮次定义为:
|
||
|
||
1. 冻结 `RETX_END=SND_NXT`。
|
||
2. 从`SND_UNA`开始按`SEQ`顺序重传到 `RETX_END-1`;窗口重新同步状态下按第32.7节分批。
|
||
3. 重传期间不首次发送新业务帧。
|
||
4. 重传完成后重新开始T_PROGRESS_LIMIT进度计时。
|
||
5. T_ACK_WAIT和T_ACK_WAIT+T_POLL_INTERVAL到期时发送`POLL_REQ`。
|
||
6. T_PROGRESS_LIMIT内`SND_UNA`向前推进:本轮成功,失败计数清零。
|
||
7. T_PROGRESS_LIMIT内`SND_UNA`没有推进:本轮失败,失败计数加一并开始下一轮。
|
||
|
||
### 32.9 连续失败与重新训练
|
||
|
||
连续三轮完整重传和查询均无ACK推进时,主端必须:
|
||
|
||
1. 停止首次发送新业务帧;
|
||
2. 保留全部未确认帧和描述符;
|
||
3. 报告可靠链路故障;
|
||
4. 触发链路重新训练。
|
||
|
||
达到门限时不得把未确认帧当作成功帧释放或静默丢弃。
|
||
|
||
纯物理重新训练不自动清除协议状态。若双方仍保留`SEQ`,主端在重新训练后`POLL_REQ`并继续重传。若从端协议状态已经复位,双方必须执行完整协议复位;不得由单端自行改变`SEQ`基准。
|
||
|
||
## 33. 定时参数与失败门限
|
||
|
||
### 33.1 超时计算
|
||
|
||
主端只维护一个针对最早未确认帧的ACK进度定时器。未确认集合从空变为非空时,在最早未确认帧最后一位发送完成后开始计时;此后只有`SND_UNA`合法向前推进才重新开始计时。
|
||
|
||
从端可能正在发送一个不可中断的最大从端→主端业务帧。最大`DATA`帧为1044 B:
|
||
|
||
```text
|
||
T_MAX_FRAME = 1044 × 8 / LINE_RATE
|
||
|
||
750 Mbps典型配置:T_MAX_FRAME = 11.136 μs
|
||
```
|
||
|
||
`CTRL`为16 B:
|
||
|
||
```text
|
||
T_CTRL = 16 × 8 / LINE_RATE
|
||
|
||
750 Mbps典型配置:T_CTRL ≈ 0.171 μs
|
||
```
|
||
|
||
ACK响应上界需要覆盖:
|
||
|
||
```text
|
||
T_MAX_FRAME + T_CTRL + Slave处理延迟 + CDC/传播/抖动裕量
|
||
```
|
||
|
||
实现必须据此确定不短于上述上界的查询间隔。第7.3节的750 Mbps典型配置采用 `T_POLL_INTERVAL=20 μs`。
|
||
|
||
### 33.2 固定参数
|
||
|
||
| 参数 | 750 Mbps典型配置数值 | 典型配置的187.5 MHz时钟周期数 |
|
||
|---|---:|---:|
|
||
| T_ACK_WAIT | 20 μs | 3750 |
|
||
| T_POLL_INTERVAL | 20 μs | 3750 |
|
||
| T_PROGRESS_LIMIT | 60 μs | 11250 |
|
||
| MAX_GBN_FAILURE_ROUNDS | 3 | — |
|
||
|
||
其中:
|
||
|
||
- `T_ACK_WAIT`:最早未确认帧开始计时后,允许等待累计ACK自然到达的时间;到期时发送第一次`POLL_REQ`;
|
||
- `T_POLL_INTERVAL`:第一次`POLL_REQ`之后,相邻`POLL_REQ`之间的间隔;
|
||
- `T_PROGRESS_LIMIT`:自最近一次ACK推进以来允许无进展的总时间;达到该值时启动Go-Back-N或判定当前重传轮失败;
|
||
- `MAX_GBN_FAILURE_ROUNDS`:连续无ACK推进的完整重传失败轮数门限。
|
||
|
||
必须满足 `T_PROGRESS_LIMIT > T_ACK_WAIT`,并保证在T_PROGRESS_LIMIT内至少可以发送一次`POLL_REQ`并接收一个最坏阻塞条件下的`CTRL`响应。
|
||
|
||
采用其他线路速率或时钟时,必须根据第33.1节重新计算并向上取整;实际时间不得短于最大阻塞帧、`CTRL`返回、处理、CDC、传播和抖动裕量之和。
|
||
|
||
### 33.3 无进展时间线
|
||
|
||
```text
|
||
0 μs: 开始或重新开始ACK进度计时
|
||
T_ACK_WAIT: ACK未推进,发送第一次POLL_REQ
|
||
T_ACK_WAIT+T_POLL_INTERVAL: ACK仍未推进,发送第二次POLL_REQ
|
||
T_PROGRESS_LIMIT: ACK仍未推进,启动或判定一轮Go-Back-N
|
||
```
|
||
|
||
同确认点ACK、旧ACK、无效`CTRL`以及只有`WIN_BYTES`变化都不算ACK进度。只有`SND_UNA`合法向前推进才重新开始进度计时。
|
||
|
||
## 34. 事件—动作规范
|
||
|
||
### 34.1 主端事件表
|
||
|
||
| 事件 | 条件 | 必须动作 |
|
||
|---|---|---|
|
||
| 同步完成 | 新协议会话 | 初始化状态并发送`POLL_REQ` |
|
||
| 新业务请求 | 窗口和描述符均足够 | 分配`SND_NXT`、缓存、首次发送、增加`OUTSTANDING_BYTES` |
|
||
| 新业务请求 | 窗口不足 | 保持请求,停止首次发送,等待ACK或`POLL_REQ` |
|
||
| 合法前进ACK | `ACK_NEXT`在已发送区间 | 释放前缀、更新`SND_UNA`和`WIN_BYTES`、重算窗口 |
|
||
| 同确认点ACK | `ACK_NEXT`等于`SND_UNA` | 不释放缓存;可以更新同锚点`WIN_BYTES` |
|
||
| 旧或越界ACK | 不满足合理性检查 | 丢弃整个`CTRL`并记录错误 |
|
||
| `RETRY_REQ` | `ACK_NEXT`合法且存在未确认帧 | 暂停新帧,从`ACK_NEXT`开始Go-Back-N |
|
||
| T_ACK_WAIT无进展 | 存在未确认帧 | 发送第一次`POLL_REQ` |
|
||
| T_ACK_WAIT+T_POLL_INTERVAL无进展 | 仍无进展 | 再次发送`POLL_REQ` |
|
||
| T_PROGRESS_LIMIT无进展 | 存在未确认帧 | 开始重传或判定当前轮失败 |
|
||
| 连续3轮失败 | `SND_UNA`未推进 | 保留缓存,报告故障并重新训练 |
|
||
|
||
### 34.2 从端事件表
|
||
|
||
| 事件 | 条件 | 必须动作 |
|
||
|---|---|---|
|
||
| 收到业务帧 | CRC/格式正确、`SEQ`等于`RCV_NEXT`、资源足够 | 提交一次、`RCV_NEXT`++、`ACK_PENDING`=1 |
|
||
| 收到业务帧 | CRC、格式、`SEQ`或资源任一不满足 | 丢弃、不推进`RCV_NEXT`、置`RETRY_PENDING`和`ACK_PENDING` |
|
||
| 收到重复或未来`SEQ` | `SEQ`不等于`RCV_NEXT` | 与其他错误相同,不分类处理 |
|
||
| 收到`POLL_REQ` | `CTRL`合法 | 优先返回当前`ACK_NEXT`和`WIN_BYTES` |
|
||
| `ACK_PENDING` | 到达发送帧边界 | 发送最新累计状态并清除已覆盖的`ACK_PENDING` |
|
||
| `RETRY_PENDING` | 需要发送状态 | `FLAGS`使用`RETRY_REQ` |
|
||
| 正确接受期望帧 | `RETRY_PENDING`为1 | 清除`RETRY_PENDING`,并报告新累计状态 |
|
||
| `WIN_BYTES`从0恢复 | 没有新业务帧也可能发生 | `ACK_PENDING`=1,主动发送窗口更新 |
|
||
|
||
### 34.3 `CTRL`调度优先级
|
||
|
||
从端→主端方向在完整帧边界按以下顺序仲裁:
|
||
|
||
```text
|
||
1. ACK_PENDING对应的状态CTRL
|
||
- RETRY_PENDING=1:FLAGS=RETRY_REQ
|
||
- RETRY_PENDING=0:FLAGS=ACK/UPDATE
|
||
- POLL_REQ响应与尚未上线的普通累计ACK允许合并为同一个最新状态CTRL
|
||
2. 普通Slave→Master DATA
|
||
```
|
||
|
||
已经开始发送的帧不得被`CTRL`中断。没有重传协议层帧需要发送时,本层不提出发送请求;`IDLE`等空闲码字由下层链路层连续生成,不属于本重传机制状态机。主端不得因为从端业务接收缓存已满而丢弃合法`CTRL`,建议为`CTRL`设置独立的小型接收通路。
|
||
|
||
## 35. 传输状态机
|
||
|
||
### 35.1 实现划分与并行关系
|
||
|
||
本章状态机是规范性控制模型。具体RTL可以合并或拆分状态,但外部行为、事件优先级和寄存器更新必须等价。
|
||
|
||
全双工接收、发送调度和定时统计必须并行运行。不得用一个互斥状态机表示整个端点,否则发送`CTRL`期间可能错误地停止接收。推荐划分如下:
|
||
|
||
| 端点 | 并行控制单元 |
|
||
|---|---|
|
||
| 主端 | 可靠传输控制器、主端→从端发送调度器、`CTRL`接收处理器、定时器 |
|
||
| 从端 | 业务帧接收控制器、状态报告生成逻辑、从端→主端发送调度器 |
|
||
|
||
发送调度器只在完整帧边界接受新请求。任何帧一旦开始发送,必须连续发送到结束。重传控制器只产生协议帧请求,不负责生成`IDLE`;无协议帧请求时由下层链路层维持连续线路输出。
|
||
|
||
### 35.2 主端可靠传输控制器
|
||
|
||
#### 35.2.1 状态定义
|
||
|
||
| 状态 | 含义 | 允许的主要动作 |
|
||
|---|---|---|
|
||
| `M_WAIT_STATUS` | 等待从端合法状态报告 | 发送或重发`POLL_REQ`;禁止首次发送新业务帧 |
|
||
| `M_RUN` | 正常可靠传输 | 在窗口内连续提交新业务帧;并行处理ACK、窗口和超时 |
|
||
| `M_RETX_PREP` | 准备一个Go-Back-N重传批次 | 等待当前在途帧结束,再锁存范围、设置RETX_PTR并确定本批终点 |
|
||
| `M_RETX_SEND` | 顺序提交重传帧 | 禁止首次发送新业务帧;按描述符顺序推进RETX_PTR |
|
||
| `M_RETX_WAIT` | 本批重传结束后等待ACK进展 | 在T_ACK_WAIT及随后一个T_POLL_INTERVAL到期时请求状态;在T_PROGRESS_LIMIT判定本轮成功或失败 |
|
||
| `M_RETRAIN` | 已达到连续失败门限 | 保留未确认缓存,停止业务帧请求并请求链路重新训练 |
|
||
|
||
`M_RUN`同时覆盖有未确认帧、等待窗口和暂时没有上层发送请求的情况。这些情况由 `OUTSTANDING_BYTES`、窗口比较和请求有效信号区分,不需要建立互斥的等待状态。
|
||
|
||
`M_RETX_PREP`按以下规则确定重传批次:
|
||
|
||
```text
|
||
RETX_END = 当前SND_NXT
|
||
RETX_PTR = 当前SND_UNA
|
||
|
||
若 OUTSTANDING_BYTES <= PEER_WIN_BYTES:
|
||
RETX_BATCH_END = RETX_END
|
||
若 OUTSTANDING_BYTES > PEER_WIN_BYTES:
|
||
RETX_BATCH_END = 从SND_UNA开始,累计FRAME_COST不超过PEER_WIN_BYTES的最长连续前缀终点
|
||
```
|
||
|
||
第一种情况属于正常Go-Back-N,重传已经占用过窗口的帧,不再次扣减窗口。第二种情况只用于第32.7节的窗口重新同步。如果第二种情况下第一个未确认帧也无法容纳,则本批为空,进入 `M_RETX_WAIT` 并通过`POLL_REQ`等待新状态。
|
||
|
||
#### 35.2.2 状态图
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> M_WAIT_STATUS
|
||
M_WAIT_STATUS --> M_RUN: 收到合法状态且无待恢复帧
|
||
M_WAIT_STATUS --> M_RETX_PREP: 收到合法状态且保留未确认帧
|
||
M_WAIT_STATUS --> M_WAIT_STATUS: T_POLL_INTERVAL无合法状态 / 请求POLL
|
||
|
||
M_RUN --> M_RUN: 新帧完成、合法ACK或窗口更新
|
||
M_RUN --> M_RETX_PREP: 合法RETRY_REQ且仍有未确认帧
|
||
M_RUN --> M_RETX_PREP: 未确认帧T_PROGRESS_LIMIT无进展
|
||
|
||
M_RETX_PREP --> M_RETX_SEND: 已锁存非空重传批次
|
||
M_RETX_PREP --> M_RETX_WAIT: 窗口重同步时第一个未确认帧也无法容纳
|
||
M_RETX_PREP --> M_RUN: ACK已确认全部发送帧
|
||
|
||
M_RETX_SEND --> M_RETX_SEND: 重传帧完成且本批仍有帧
|
||
M_RETX_SEND --> M_RETX_WAIT: 本批最后一帧完成
|
||
M_RETX_SEND --> M_RUN: ACK已确认全部发送帧
|
||
|
||
M_RETX_WAIT --> M_RETX_PREP: ACK推进且窗口重同步批次尚未完成
|
||
M_RETX_WAIT --> M_RUN: ACK推进且本轮已经完整发送
|
||
M_RETX_WAIT --> M_RETX_PREP: T_PROGRESS_LIMIT无进展且失败次数小于3
|
||
M_RETX_WAIT --> M_RETRAIN: T_PROGRESS_LIMIT无进展且形成第3次连续失败
|
||
|
||
M_RETRAIN --> M_WAIT_STATUS: retrain完成 / 请求POLL
|
||
```
|
||
|
||
#### 35.2.3 规范性转移与动作
|
||
|
||
| 当前状态 | 事件和条件 | 寄存器及控制动作 | 下一状态 |
|
||
|---|---|---|---|
|
||
| 任意非`M_RETRAIN`状态 | 收到合法`CTRL` | 先按第31.6节处理`ACK_NEXT`和`WIN_BYTES`;无效`CTRL`不改变任何可靠传输状态 | 按下列事件继续判断 |
|
||
| `M_WAIT_STATUS` | 收到合法状态,且无保留的未确认帧 | 更新确认点和窗口;清除本次`POLL_REQ`等待 | `M_RUN`,即使`WIN_BYTES`为0 |
|
||
| `M_WAIT_STATUS` | 重新训练后收到合法状态,且仍有未确认帧 | 保留描述符;设置 `RETX_END=SND_NXT` | `M_RETX_PREP` |
|
||
| `M_WAIT_STATUS` | T_POLL_INTERVAL无合法状态 | 置位 `POLL_PENDING`;不得初始化或清除`SEQ` | `M_WAIT_STATUS` |
|
||
| `M_RUN` | 新业务帧完成首次发送 | `OUTSTANDING_BYTES += FRAME_COST`;`SND_NXT++`;若未确认集合由空变为非空则启动进度计时 | `M_RUN` |
|
||
| `M_RUN` | 合法前进ACK | 释放确认前缀,更新`SND_UNA`和窗口,清零失败计数并重新开始或停止进度计时 | `M_RUN` |
|
||
| `M_RUN` | 同确认点`ACK/UPDATE` | 仅更新同一确认点的窗口;不得释放缓存或重置进度计时 | `M_RUN` |
|
||
| `M_RUN` | 合法`RETRY_REQ`且 `ACK_NEXT==SND_NXT` | 执行第32.3节的无重传目标分支,不建立重传批次 | `M_RUN` |
|
||
| `M_RUN` | 合法`RETRY_REQ`且仍有未确认帧 | 置位重传启动请求,停止接受新的首次发送请求;若有新业务帧正在发送,等待其完成 | `M_RETX_PREP` |
|
||
| `M_RUN` | T_PROGRESS_LIMIT无ACK进展且存在未确认帧 | 置位重传启动请求,停止接受新的首次发送请求;若有新业务帧正在发送,等待其完成 | `M_RETX_PREP` |
|
||
| `M_RETX_PREP` | `ACK_NEXT==SND_NXT` | 不建立重传请求,停止进度计时 | `M_RUN` |
|
||
| `M_RETX_PREP` | 主端→从端帧仍在发送 | 等待该帧完整结束;若它是首次发送的新业务帧,先完成`SND_NXT`和`OUTSTANDING_BYTES`记账 | `M_RETX_PREP` |
|
||
| `M_RETX_PREP` | 发送器已到帧边界且仍有未确认帧 | 使用此时的`SND_UNA`、`SND_NXT`和描述符锁存RETX_END、RETX_PTR及RETX_BATCH_END | 批次非空则`M_RETX_SEND`,否则`M_RETX_WAIT` |
|
||
| `M_RETX_PREP` | 第一个未确认帧也无法容纳 | 置位`POLL_PENDING`,启动本轮进度等待 | `M_RETX_WAIT` |
|
||
| `M_RETX_SEND` | 一个重传帧发送完成 | `RETX_PTR++`;不得增加`OUTSTANDING_BYTES`或分配`SEQ` | 本批未结束则保持,否则转`M_RETX_WAIT` |
|
||
| `M_RETX_SEND` | 收到合法前进ACK | 立即释放确认前缀;若RETX_PTR落后于新`SND_UNA`则令 `RETX_PTR=SND_UNA`;清零失败计数 | 全部确认则`M_RUN`,否则继续当前批次 |
|
||
| `M_RETX_WAIT` | T_ACK_WAIT及随后一个T_POLL_INTERVAL到期且无进展 | 置位`POLL_PENDING`;不增加失败计数 | `M_RETX_WAIT` |
|
||
| `M_RETX_WAIT` | ACK推进且 `RETX_PTR < RETX_END` | 清零失败计数,从新`SND_UNA`重新计算窗口允许的剩余前缀 | `M_RETX_PREP` |
|
||
| `M_RETX_WAIT` | ACK推进且本轮冻结范围已经全部发送 | 清零失败计数;剩余未确认帧重新按正常计时处理 | `M_RUN` |
|
||
| `M_RETX_WAIT` | T_PROGRESS_LIMIT无进展 | 当前轮失败计数加一;小于3时令 `RETX_PTR=SND_UNA` 开始下一轮 | `M_RETX_PREP`或`M_RETRAIN` |
|
||
| `M_RETRAIN` | 物理重新训练完成且协议状态保留 | 保留`SEQ`、缓存和描述符,置位`POLL_PENDING` | `M_WAIT_STATUS` |
|
||
| 任意状态 | 双方完整协议复位 | 清空可靠传输状态并按第31.2节初始化 | `M_WAIT_STATUS` |
|
||
|
||
如果状态转移发生时主端→从端发送器正在发送一个完整帧,当前帧必须先发送结束。状态机可以立即禁止新的首次发送请求,但重传帧或`POLL_REQ`只能在下一帧边界被调度。
|
||
|
||
因此,`RETRY_REQ`或T_PROGRESS_LIMIT超时到达时不得立即用旧`SND_NXT`冻结RETX_END。若当时正在首次发送新业务帧,必须先等待 `frame_tx_done`,完成该帧的`SND_NXT`和`OUTSTANDING_BYTES`更新,再以更新后的`SND_NXT`冻结重传范围。这样能够保证已经上线的最后一帧不会遗漏在Go-Back-N范围之外。
|
||
|
||
#### 35.2.4 主端事件优先级
|
||
|
||
同一时钟周期出现多个事件时,必须按以下顺序处理:
|
||
|
||
1. 双方完整协议复位或重新训练进入事件;
|
||
2. 合法接收`CTRL`:先做累计ACK和窗口更新,再解释`FLAGS`;
|
||
3. 当前发送帧完成事件;
|
||
4. T_ACK_WAIT、后续T_POLL_INTERVAL及T_PROGRESS_LIMIT定时事件;
|
||
5. 新上层业务请求。
|
||
|
||
前进ACK与T_PROGRESS_LIMIT超时同周期发生时,以前进ACK为准,重置进度计时并抑制本周期的失败判定。合法`RETRY_REQ`中的`ACK_NEXT`必须先释放确认前缀;仅当处理后仍有未确认帧时才进入重传。
|
||
|
||
ACK进度计时独立于 `M_RUN` 的发送活动。只要存在未确认帧,即使主端仍在窗口内连续发送新帧,也必须继续统计最早未确认帧的无进展时间。初始化等待或没有未确认帧但窗口不足时,可以复用同一个计数器作为T_POLL_INTERVAL `POLL_REQ`间隔计时;两种模式不得同时解释同一个超时事件。
|
||
|
||
### 35.3 主端发送调度器
|
||
|
||
主端发送调度器只描述重传协议层向下层提交完整帧的行为:
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> M_TX_BOUNDARY
|
||
M_TX_BOUNDARY --> M_TX_FRAME: 在帧边界选中一个完整帧请求
|
||
M_TX_FRAME --> M_TX_BOUNDARY: frame_done
|
||
M_TX_FRAME --> M_TX_FRAME: frame_done之前保持当前帧
|
||
```
|
||
|
||
在 `M_TX_BOUNDARY` 按以下顺序选择请求:
|
||
|
||
1. 已经置位的`POLL_REQ`;
|
||
2. `M_RETX_SEND`提供的下一帧重传请求;
|
||
3. `M_RUN`提供且满足窗口条件的新业务帧请求。
|
||
|
||
`POLL_PENDING`允许合并,不能因为同一请求等待多个周期而排队多个`POLL_REQ`。开始发送`POLL_REQ`时清除本次已经覆盖的`POLL_PENDING`;同周期产生的新`POLL_REQ`事件必须继续保留。下层没有收到本层完整帧请求时如何发送`IDLE`,不属于本状态机。
|
||
|
||
### 35.4 从端业务接收控制器
|
||
|
||
从端接收控制器与从端发送调度器并行工作。发送`CTRL`或从端业务帧期间,接收控制器必须继续解析和处理主端→从端帧。
|
||
|
||
#### 35.4.1 状态定义与状态图
|
||
|
||
| 状态 | 含义 |
|
||
|---|---|
|
||
| `S_EXPECT` | 等待`SEQ`等于`RCV_NEXT`的合法业务帧 |
|
||
| `S_RETRY_WAIT` | 已发现错误,仍等待同一个`RCV_NEXT`对应的正确业务帧 |
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> S_EXPECT
|
||
S_EXPECT --> S_EXPECT: 正确期望帧 / 提交、RCV_NEXT++、ACK_PENDING=1
|
||
S_EXPECT --> S_RETRY_WAIT: 业务帧错误 / 丢弃、RETRY_PENDING=1、ACK_PENDING=1
|
||
S_RETRY_WAIT --> S_RETRY_WAIT: 非期望或错误帧 / 丢弃、ACK_PENDING=1
|
||
S_RETRY_WAIT --> S_EXPECT: 正确期望帧 / 提交、RCV_NEXT++、RETRY_PENDING=0、ACK_PENDING=1
|
||
```
|
||
|
||
收到合法`POLL_REQ`只置位`ACK_PENDING`,不改变上述接收状态。`WIN_BYTES`从0恢复为非0时同样只置位`ACK_PENDING`。无效`CTRL`直接丢弃,不改变`RCV_NEXT`、`ACK_PENDING`或`RETRY_PENDING`。
|
||
|
||
#### 35.4.2 从端事件—动作表
|
||
|
||
| 当前状态 | 事件和条件 | 必须动作 | 下一状态 |
|
||
|---|---|---|---|
|
||
| `S_EXPECT` | `DATA`的CRC和格式正确、`SEQ==RCV_NEXT`且资源足够 | 提交一次;`RCV_NEXT++`;`ACK_PENDING=1` | `S_EXPECT` |
|
||
| `S_EXPECT` | `DATA`发生第32.2节任一错误 | 丢弃;`RCV_NEXT`不变;`RETRY_PENDING=1`;`ACK_PENDING=1` | `S_RETRY_WAIT` |
|
||
| `S_RETRY_WAIT` | 正确收到当前`RCV_NEXT`对应业务帧且资源足够 | 提交一次;`RCV_NEXT++`;`RETRY_PENDING=0`;`ACK_PENDING=1` | `S_EXPECT` |
|
||
| `S_RETRY_WAIT` | 再次收到错误帧或非期望`SEQ` | 丢弃;`RCV_NEXT`不变;保持`RETRY_PENDING`;`ACK_PENDING=1` | `S_RETRY_WAIT` |
|
||
| 任意接收状态 | 收到合法`POLL_REQ` | `ACK_PENDING=1` | 状态不变 |
|
||
| 任意接收状态 | `WIN_BYTES`从0恢复为非0 | `ACK_PENDING=1` | 状态不变 |
|
||
| 任意接收状态 | `CTRL`校验或格式失败 | 丢弃`CTRL`,不产生状态更新 | 状态不变 |
|
||
| 任意接收状态 | 双方完整协议复位 | `RCV_NEXT=0`,清除待发送状态 | `S_EXPECT` |
|
||
|
||
#### 35.4.3 待发送状态的并发更新
|
||
|
||
`ACK_PENDING`表示存在一个尚未开始发送的最新状态快照,不表示独立ACK队列。状态`CTRL`开始发送时锁存:
|
||
|
||
```text
|
||
TX_ACK_NEXT = RCV_NEXT
|
||
TX_WIN_BYTES = 当前WIN_BYTES
|
||
TX_FLAGS = (RETRY_PENDING == 1) ? RETRY_REQ : ACK/UPDATE
|
||
```
|
||
|
||
状态`CTRL`一旦开始发送,以上字段保持到帧结束。开始发送时可以清除本次快照覆盖的`ACK_PENDING`,但同周期或发送期间发生的新事件必须重新置位。RTL更新必须采用“新事件置位优先于旧快照清除”的规则,等价于:
|
||
|
||
```text
|
||
ACK_PENDING_next = NEW_STATUS_EVENT
|
||
OR (ACK_PENDING AND NOT STATUS_LAUNCH)
|
||
```
|
||
|
||
其中 `NEW_STATUS_EVENT` 包括接受业务帧、检测业务帧错误、收到合法`POLL_REQ`以及`WIN_BYTES`从0恢复。发送`RETRY_REQ`不得清除`RETRY_PENDING`;只有正确接受当前`RCV_NEXT`对应业务帧或完整协议复位才能清除它。
|
||
|
||
#### 35.4.4 从端事件优先级
|
||
|
||
同一时钟周期出现多个事件时,必须按以下顺序形成下一状态:
|
||
|
||
1. 双方完整协议复位;
|
||
2. `DATA`候选帧完成事件,按成功接受或失败丢弃更新`RCV_NEXT`和`RETRY_PENDING`;
|
||
3. 合法`POLL_REQ`及`WIN_BYTES`从0恢复事件;
|
||
4. 状态`CTRL`开始发送产生的旧快照清除事件;
|
||
5. 从端上层无确认业务发送请求。
|
||
|
||
同一个候选业务帧不得同时报告成功和失败。如果业务帧事件、`POLL_REQ`或窗口恢复与 `STATUS_LAUNCH` 同周期发生,新状态事件必须使`ACK_PENDING`在周期结束后保持为1。从端发送调度事件不得改变接收状态,也不得阻止接收控制器在同周期处理业务帧。
|
||
|
||
### 35.5 从端发送调度器
|
||
|
||
```mermaid
|
||
stateDiagram-v2
|
||
[*] --> S_TX_BOUNDARY
|
||
S_TX_BOUNDARY --> S_TX_FRAME: 在帧边界选中一个完整帧请求
|
||
S_TX_FRAME --> S_TX_BOUNDARY: frame_done
|
||
S_TX_FRAME --> S_TX_FRAME: frame_done之前保持当前帧
|
||
```
|
||
|
||
在 `S_TX_BOUNDARY` 按以下顺序选择请求:
|
||
|
||
1. `ACK_PENDING`对应的状态`CTRL`;
|
||
2. 从端上层提供的无确认`DATA`。
|
||
|
||
选择状态`CTRL`时按第35.4.3节锁存字段。当前正在发送的从端业务帧不得被新到达的ACK、`RETRY_REQ`状态或`POLL_REQ`响应中断;这些事件只置位`ACK_PENDING`,并在下一个完整帧边界参与仲裁。发送调度状态不得阻塞第35.4节接收控制器。
|
||
|
||
### 35.6 RTL接口事件契约
|
||
|
||
状态机可以使用不同端口名称,但至少需要等价的内部事件:
|
||
|
||
| 事件 | 产生位置 | 语义 |
|
||
|---|---|---|
|
||
| `business_candidate_valid` | `DATA`解析器 | CRC和格式已经通过,字段可供序号与资源检查 |
|
||
| `business_candidate_error` | `DATA`解析器或接收控制器 | 第32.2节定义的错误,候选帧不得提交 |
|
||
| `ctrl_valid` | `CTRL`解析器 | CRC、`FLAGS`和`WIN_BYTES`均合法 |
|
||
| `frame_tx_start` | 发送调度器 | 完整帧字段已经锁存,本帧不可被抢占 |
|
||
| `frame_tx_done` | 发送器 | 完整帧最后一位已经发送,并同时报告帧类别及业务`SEQ` |
|
||
| `ack_progress` | 主端`CTRL`处理器 | 合法`ACK_NEXT`使`SND_UNA`向前推进 |
|
||
| `status_launch` | 从端发送调度器 | 最新状态快照已经锁存并开始发送 |
|
||
| `retrain_done` | 链路同步层 | 物理同步恢复;是否保留协议状态由链路恢复结果同时给出 |
|
||
|
||
解析器不得在CRC和格式检查完成前产生 `business_candidate_valid` 或 `ctrl_valid`。状态机不得把仅识别到`SOF`当作有效帧事件。
|
||
|
||
## 36. 重传机制一致性要求
|
||
|
||
### 36.1 序号与提交
|
||
|
||
1. `DATA`在主端→从端方向必须共用同一`SEQ`空间、ACK和重传窗口。
|
||
2. 从端不得接受或提交 `SEQ != RCV_NEXT` 的业务帧。
|
||
3. 从端每接受一个业务帧都必须触发`ACK_PENDING`。
|
||
4. 尚未上线的累计ACK必须允许合并为最新`ACK_NEXT`和`WIN_BYTES`。
|
||
5. 从端→主端业务`SEQ`只循环递增;主端不得因`SEQ`跳变或重复拒绝CRC和格式正确的帧。
|
||
|
||
### 36.2 窗口与缓存
|
||
|
||
1. 主端不得在合法累计ACK到达前释放可靠方向的重传帧。
|
||
2. 同一`SEQ`重传不得再次增加`OUTSTANDING_BYTES`。
|
||
3. `OUTSTANDING_BYTES`必须等于未确认描述符`FRAME_COST`之和。
|
||
4. 从端必须独立检查本地接收资源,不得因主端已发送就假定空间足够。
|
||
5. `WIN_BYTES`不得作为增量累加,旧确认点的窗口不得覆盖新确认点状态。
|
||
6. 窗口不一致时不得丢弃主端重传缓存,必须按第32.7节重新同步。
|
||
|
||
### 36.3 `CTRL`与超时
|
||
|
||
1. 从端`CTRL`必须在帧边界优先于普通从端业务帧发送。
|
||
2. `CTRL`、`IDLE`及固定同步类帧不得占用业务窗口或改变业务`SEQ`。
|
||
3. 主端必须实现T_ACK_WAIT后的首次`POLL_REQ`、按T_POLL_INTERVAL重复`POLL_REQ`,以及T_PROGRESS_LIMIT无进展重传规则。
|
||
4. CRC、格式或ACK合理性检查失败的`CTRL`不得改变发送状态。
|
||
5. 同确认点ACK不得重复释放缓存,也不得重置进度超时。
|
||
|
||
### 36.4 失败与方向差异
|
||
|
||
1. 连续3轮重传无进展时必须保留缓存并触发重新训练,不得静默丢帧。
|
||
2. 从端→主端业务不得进入链路重传或窗口控制状态机。
|
||
3. 主端业务缓存满时可以丢弃从端业务帧,但必须继续解析线路并保证`CTRL`接收。
|
||
4. 重新训练不得由单端擅自重置业务`SEQ`;完整复位必须由双方一致执行。
|
||
|
||
# 第六篇分层架构与层间接口
|
||
|
||
## 37. 数据链路层
|
||
|
||
### 37.1 负责功能
|
||
|
||
数据链路层必须负责:
|
||
|
||
1. 物理串行收发、串并转换及相关时钟接口;
|
||
2. FPGA SERDES或ASIC串行接收发送适配;
|
||
3. `IDELAY`、`ODELAY`等链路校准;
|
||
4. 训练、同步建立、同步确认及`SYNC_RESET`处理;
|
||
5. 32位字边界建立;
|
||
6. `IDLE`、固定同步帧及`DATA`、`CTRL` `SOF`检测;
|
||
7. 运行期同步监测及边界恢复;
|
||
8. `DATA`和`CTRL`帧体的加扰与解扰;
|
||
9. `DATA`外层`LEN`提取及接收字数统计;
|
||
10. `CRC32`生成和校验;
|
||
11. 向传输协议层流式输出不含CRC的解扰候选帧;
|
||
12. 无上层发送帧时持续产生`IDLE`;
|
||
13. 根据传输协议层请求执行重新训练。
|
||
|
||
### 37.2 不负责功能
|
||
|
||
数据链路层不得负责:
|
||
|
||
- `CTRL`的`FLAGS`、`WIN_BYTES`及`ACK_NEXT`合理性判断;
|
||
- `DATA`的`SEQ`接受判断;
|
||
- ACK、窗口、`POLL_REQ`和Go-Back-N状态维护;
|
||
- 主端重传缓存;
|
||
- `DATA`载荷解释;
|
||
- `DATA`载荷对应的任何具体业务操作。
|
||
|
||
### 37.3 发送路径
|
||
|
||
传输协议层向数据链路层提供:
|
||
|
||
```text
|
||
SOF + SEQ/LEN + PAYLOAD
|
||
```
|
||
|
||
或者`CTRL`的:
|
||
|
||
```text
|
||
SOF + ACK_NEXT/FLAGS/RESERVED + WIN_BYTES
|
||
```
|
||
|
||
以上数据未加扰且不包含CRC。数据链路层必须:
|
||
|
||
1. 检查输入帧的外层类型和长度是否可编码;
|
||
2. 将`SOF`原样发送并送入CRC计算;
|
||
3. 对`SOF`之后的字段和载荷进行逐帧加扰;
|
||
4. 在接收逻辑帧最后一个字时完成CRC计算;
|
||
5. 自动追加CRC字段;
|
||
6. 使用当前扰码状态发送CRC字段;
|
||
7. CRC最后一位上线后产生发送完成事件。
|
||
|
||
CRC计算与输入数据接收并行进行,不需要专门的CRC计算停顿,但CRC字段在线路上占用一个32位字的发送时间。
|
||
|
||
### 37.4 接收路径
|
||
|
||
接收状态概念上划分为:
|
||
|
||
```text
|
||
WAIT_BOUNDARY
|
||
↓
|
||
RX_HEADER
|
||
↓
|
||
RX_BODY
|
||
↓
|
||
RX_CRC
|
||
↓
|
||
WAIT_BOUNDARY
|
||
```
|
||
|
||
#### 37.4.1 WAIT_BOUNDARY
|
||
|
||
在可信32位边界读取一个未解扰字:
|
||
|
||
- `IDLE`:报告或统计`IDLE`,保持边界可信;
|
||
- 固定同步类`SOF`:由数据链路层继续比较完整固定码型;
|
||
- `DATA`或`CTRL` `SOF`:开始普通候选帧;
|
||
- 其他数值:报告BOUNDARY_ERROR并进入边界恢复。
|
||
|
||
普通`SOF`作为候选帧第一个字通过接收流接口输出。`SOF`保持原样,不经过解扰。
|
||
|
||
#### 37.4.2 RX_HEADER
|
||
|
||
`DATA`在`SOF`后解扰`SEQ`/`LEN`字。数据链路层必须同时:
|
||
|
||
- 把解扰后的`SEQ`/`LEN`字输出给传输协议层;
|
||
- 提取外层`LEN`用于本层帧计数;
|
||
- 检查外层`LEN`是否合法。
|
||
|
||
`CTRL`长度固定,数据链路层按固定字数接收,无需`LEN`字段。
|
||
|
||
#### 37.4.3 RX_BODY
|
||
|
||
外层`LEN`合法后,数据链路层按确定字数持续解扰并输出字段和载荷。帧体中的任何`SOF`或`IDLE`相同码字都不得被识别为新边界。
|
||
|
||
逻辑帧最后一个字输出时,必须同时置位 `rx_data_last`。
|
||
|
||
#### 37.4.4 RX_CRC
|
||
|
||
CRC字段必须解扰,但不得通过 `rx_data` 输出。数据链路层比较收到的CRC与本帧计算结果,并产生一次CRC结果事件。
|
||
|
||
CRC处理完成后,下一个32位线路字重新作为预期帧边界进行检查。
|
||
|
||
### 37.5 外层长度检查
|
||
|
||
数据链路层只检查确定帧结束位置所必需的外层`LEN`:
|
||
|
||
| 帧类型 | 外层长度要求 |
|
||
|---|---|
|
||
| `DATA` | `4 <= LEN <= 1032`,且 `LEN[1:0] == 0` |
|
||
| `CTRL` | 总长度固定为16 B,不含`LEN`字段 |
|
||
|
||
外层`LEN`非法时,数据链路层不能使用该`LEN`继续无界计数,也不能假定CRC位置。必须终止当前候选帧、产生帧中止事件并进入边界恢复。
|
||
|
||
### 37.6 链路完整帧判据
|
||
|
||
数据链路层只在以下条件全部满足时报告CRC通过:
|
||
|
||
```text
|
||
在可信边界检测到合法DATA/CTRL SOF
|
||
AND 外层LEN合法,或者CTRL固定长度正确
|
||
AND 按预期字数接收到完整帧体
|
||
AND CRC字段位于预期位置
|
||
AND 收到的CRC等于计算CRC
|
||
```
|
||
|
||
CRC通过只证明链路封装完整,不证明`CTRL`内部字段合法,也不证明业务`SEQ`可以接受。
|
||
|
||
### 37.7 CRC错误与同步状态
|
||
|
||
外层`LEN`合法且按照该`LEN`到达预期CRC位置时,单次CRC错误不得直接判定链路失步。数据链路层应报告CRC失败,并在下一预期边界继续检测`IDLE`或`SOF`。
|
||
|
||
如果下一预期边界没有任何合法标记,则报告BOUNDARY_ERROR并进入边界恢复。
|
||
|
||
## 38. 传输协议层
|
||
|
||
### 38.1 负责功能
|
||
|
||
传输协议层必须负责:
|
||
|
||
1. 接收候选帧的暂存和提交/回滚;
|
||
2. 根据`SOF`解析`DATA`或`CTRL`类型;
|
||
3. 提取业务`SEQ`、`LEN`、`CTRL`字段;
|
||
4. `CTRL`字段及ACK合理性检查;
|
||
5. 维护`DATA`业务`SEQ`空间;
|
||
6. `DL`的窗口、累计ACK、`POLL_REQ`、`RETRY_REQ`和Go-Back-N;
|
||
7. 主端重传缓存和描述符;
|
||
8. `UL`无确认发送及无确认接收;
|
||
9. 决定候选业务帧是否允许提交;
|
||
10. 多轮重传失败后向数据链路层请求重新训练。
|
||
|
||
### 38.2 不负责功能
|
||
|
||
传输协议层不得负责:
|
||
|
||
- 具体物理电气接口和SERDES;
|
||
- 延迟校准及训练码型检测;
|
||
- 线路`SOF`搜索;
|
||
- 加扰和解扰;
|
||
- 根据外层`LEN`定位CRC;
|
||
- `CRC32`计算;
|
||
- `IDLE`生成;
|
||
- 具体`DATA`载荷语义;
|
||
- `DATA`载荷对应的任何具体业务操作。
|
||
|
||
### 38.3 候选帧上下文
|
||
|
||
传输协议层接收候选帧时,必须维护等价于以下内容的上下文:
|
||
|
||
```text
|
||
candidate_active
|
||
candidate_type
|
||
candidate_seq
|
||
candidate_len
|
||
candidate_format_ok
|
||
candidate_buffer
|
||
```
|
||
|
||
在最终CRC结果到达前,候选帧不得向业务应用层提交,也不得推进`RCV_NEXT`或执行`CTRL`动作。
|
||
|
||
### 38.4 CRC结果处理
|
||
|
||
#### 38.4.1 CRC通过
|
||
|
||
收到CRC通过事件后,传输协议层按帧类型继续处理:
|
||
|
||
- 对`DATA`检查方向相关的业务`SEQ`和接收资源,然后决定提交或回滚;
|
||
- 对`CTRL`检查`FLAGS`、`WIN_BYTES`、`ACK_NEXT`及当前状态,合法时执行控制动作,否则丢弃。
|
||
|
||
#### 38.4.2 CRC失败
|
||
|
||
CRC失败时必须回滚全部候选数据:
|
||
|
||
| 接收端及方向 | 处理 |
|
||
|---|---|
|
||
| 从端接收`DL` `DATA` | 不推进`RCV_NEXT`,置`RETRY_PENDING`和`ACK_PENDING` |
|
||
| 主端接收`UL` `DATA` | 直接丢弃,不请求重传 |
|
||
| 任意端接收`CTRL` | 丢弃`CTRL`,不更新ACK、窗口或重传状态 |
|
||
|
||
### 38.5 `DATA`载荷处理边界
|
||
|
||
传输协议层不得解析`PAYLOAD`内部的业务字段。`DATA`通过`CRC32`、外层`LEN`、方向相关的`SEQ`和接收资源检查后,即可按第38.7节决定提交或回滚。
|
||
|
||
业务应用层判定的命令非法、地址越界、权限不足或执行失败,不属于传输协议错误,不得触发`RETRY_REQ`、回滚已提交帧或改变`RCV_NEXT`。需要业务响应时,由业务应用层生成新的`DATA`载荷。
|
||
|
||
### 38.6 `CTRL`检查
|
||
|
||
传输协议层在CRC通过后检查:
|
||
|
||
- `FLAGS`是否为`ACK/UPDATE`、`RETRY_REQ`或`POLL_REQ`;
|
||
- `WIN_BYTES`是否为4字节整数倍;
|
||
- `ACK_NEXT`是否位于当前合理序号区间;
|
||
- `CTRL`方向和当前端点状态是否允许执行对应动作。
|
||
|
||
任一项不满足时必须丢弃整个`CTRL`,不得部分更新窗口、确认点或重传状态。
|
||
|
||
### 38.7 协议接受条件
|
||
|
||
`DL` `DATA`的接受条件为:
|
||
|
||
```text
|
||
DL_ACCEPT = CRC通过
|
||
AND 外层格式合法
|
||
AND SEQ == RCV_NEXT
|
||
AND 接收资源足够
|
||
```
|
||
|
||
`UL` `DATA`的接受条件为:
|
||
|
||
```text
|
||
UL_ACCEPT = CRC通过
|
||
AND 外层格式合法
|
||
```
|
||
|
||
`UL`采用无确认接收,主端不得因`SEQ`跳变或重复拒绝CRC和格式正确的帧。
|
||
|
||
`CTRL`的执行条件为:
|
||
|
||
```text
|
||
CTRL_ACCEPT = CRC通过
|
||
AND CTRL字段合法
|
||
AND ACK_NEXT合理
|
||
```
|
||
|
||
### 38.8 接收暂存和提交
|
||
|
||
数据链路层不缓存完整帧,因此传输协议层必须提供:
|
||
|
||
- 整帧暂存RAM/FIFO;或者
|
||
- 行为等价的提交/回滚缓存。
|
||
|
||
候选帧处理顺序为:
|
||
|
||
```text
|
||
rx_data_valid → 写候选暂存区
|
||
rx_data_last → 候选数据接收完成,但仍不提交
|
||
rx_crc_valid → 获取最终CRC结果
|
||
协议检查 → 检查SEQ和资源
|
||
commit → 向业务应用层提交
|
||
rollback → 丢弃候选暂存内容
|
||
```
|
||
|
||
业务应用层不得观察到回滚帧产生的载荷或其他业务动作。
|
||
|
||
### 38.9 主端重传缓存
|
||
|
||
由于CRC和扰码由数据链路层生成,主端传输协议层的重传缓存建议保存:
|
||
|
||
```text
|
||
SEQ
|
||
LEN
|
||
PAYLOAD_RAM_ADDRESS
|
||
FRAME_COST
|
||
PAYLOAD
|
||
```
|
||
|
||
重传缓存不需要保存:
|
||
|
||
- CRC字段;
|
||
- 加扰后的数据;
|
||
- 固定`SOF`的重复副本。
|
||
|
||
重传时,传输协议层重新生成固定的`DATA_SOF`,并把同一`SEQ`、`LEN`和`PAYLOAD`重新提交给数据链路层。数据链路层重新计算CRC并从固定初值开始加扰。
|
||
|
||
重传缓存实际存储字节数与窗口计费必须区分。窗口中的`FRAME_COST`仍为:
|
||
|
||
```text
|
||
FRAME_COST = SOF 4 B + SEQ/LEN 4 B + PAYLOAD LEN B
|
||
= 8 + LEN
|
||
|
||
LINE_FRAME_BYTES = FRAME_COST + CRC32 4 B
|
||
= 12 + LEN
|
||
```
|
||
|
||
同一`SEQ`重传不得重复增加`FRAME_COST`。
|
||
|
||
## 39. 业务应用层
|
||
|
||
### 39.1 负责功能
|
||
|
||
业务应用层负责:
|
||
|
||
- 产生和消费`DATA`有效载荷;
|
||
- 定义并解释`DATA`载荷内部的业务格式;
|
||
- 在需要时使用`DATA`载荷定义寄存器读写、命令、响应及其关联方式;
|
||
- 执行实际业务操作并处理地址、权限和执行结果;
|
||
- 维护用户业务缓存和业务调度;
|
||
- 接收可靠方向的发送完成通知。
|
||
|
||
### 39.2 不负责功能
|
||
|
||
业务应用层不得负责:
|
||
|
||
- `SOF`和线路帧格式;
|
||
- `CRC32`和扰码;
|
||
- 业务`SEQ`分配;
|
||
- ACK、窗口、`POLL_REQ`和重传;
|
||
- 链路同步和重新训练。
|
||
|
||
业务应用层只接收传输协议层已经提交的`DATA`载荷。业务应用层对载荷内容的接受或拒绝不得反向改变已经完成的传输确认。
|
||
|
||
### 39.3 典型业务应用:基于Transaction帧结构的业务应用层处理
|
||
|
||
本节定义一种可选的典型业务应用配置,不属于基础传输规范的强制要求。只有声明支持本Transaction应用配置的设备才必须遵守本节。在本应用场景中,主端为FPGA,从端为用于SPI扇出的ASIC。
|
||
|
||
Transaction是业务应用层的数据单元。一个完整Transaction作为`PAYLOAD`,由传输协议层封装进第12章定义的`DATA`逻辑帧;数据链路层随后追加`CRC32`并执行扰码,形成在线路上传输的`DATA`线路帧。为避免与传输协议层的`DATA`逻辑帧混淆,本节将Transaction内部的数据区统一称为`T_DATA`。
|
||
|
||
#### 39.3.1 Transaction帧结构
|
||
|
||
一个Transaction帧由8字节命令字段`CMD`和可选的Transaction数据区`T_DATA`组成。`CMD`包含读写标志`W/R`、主动回读标志`ARD FLAG`、芯片标识`CID`、地址`ADDR`、扩展地址`EXADDR`和数据长度`LENGTH`。
|
||
|
||
| 组成 | 字段 | 长度 | 位位置 | 功能描述 | 备注 |
|
||
|---|---|---:|:---:|---|---|
|
||
| `CMD` | `W/R` | 1 bit | `[63]` | 读写标识,0表示写,1表示读 | — |
|
||
| `CMD` | `ARD FLAG` | 1 bit | `[62]` | 主动回读数据标志 | 主动回读模块根据读出芯片的读请求读出实验数据 |
|
||
| `CMD` | `CID` | 5 bits | `[61:57]` | 芯片组中每个芯片的ID标识 | 包括量子测控芯片组及其他需要配置的芯片组 |
|
||
| `CMD` | `ADDR` | 25 bits | `[56:32]` | 目标设备中的字节地址 | 必须4字节对齐,即`ADDR[1:0] == 2'b00` |
|
||
| `CMD` | `EXADDR` | 12 bits | `[31:20]` | 设备及通道路由字段 | `[11:8]`预留,`[7:3]`选择设备,`[2:0]`选择从端通道 |
|
||
| `CMD` | `LENGTH` | 20 bits | `[19:0]` | `T_DATA`的长度,单位为字节 | 必须是4字节的整数倍,最大支持1 MByte |
|
||
| 数据区 | `T_DATA` | `N*4` bytes | — | 写入数据或读响应数据 | 读请求不包含该字段 |
|
||
|
||
`LENGTH`始终表示`T_DATA`字段的字节数,不包括8字节`CMD`。`CMD`按64位小端序封装,先发送`CMD[7:0]`,最后发送`CMD[63:56]`。`T_DATA`中的每个32位字同样按小端序传输,即低字节先发送;多个32位字按照业务提供的先后顺序传输。
|
||
|
||
#### 39.3.2 请求和响应封装
|
||
|
||
承载Transaction的`DATA`逻辑帧,其`LEN`与Transaction字段之间必须满足以下关系:
|
||
|
||
| Transaction类型 | 传输方向 | `DATA`逻辑帧的`LEN` | Transaction `LENGTH` | Transaction数据区 |
|
||
|---|---|---:|---:|---|
|
||
| 写请求 | `DL` | `8 + LENGTH` | 写入数据的字节数 | 包含`LENGTH`字节`T_DATA` |
|
||
| 读请求 | `DL` | `8` | 期望读取的字节数 | 不包含`T_DATA` |
|
||
| 读响应 | `UL` | `8 + LENGTH` | 返回数据的字节数 | 包含`LENGTH`字节`T_DATA` |
|
||
|
||
读响应的`CMD`必须与对应读请求的`CMD`逐位完全一致,并返回该命令指定的全部`LENGTH`字节数据,不支持部分响应。`DL`中的`W/R=1`表示读请求,`UL`中的`W/R=1`表示读响应。
|
||
|
||
本应用配置不增加事务编号,也不要求多个读请求的响应按请求顺序返回。多个完全相同的读请求同时在途时不进行特殊区分,其读响应允许按任意顺序返回。读响应仍遵守本规范规定的`UL`无确认传输机制,本节不为其增加确认或重传能力。
|
||
|
||
#### 39.3.3 设备与通道路由
|
||
|
||
`EXADDR[7:3]`用于设备路由:`5'd0`代表主端,`5'd1`~`5'd31`代表从端。因此,本应用配置最多表示31个从端。
|
||
|
||
基础传输规范中的各从端分别使用独立的点对点物理链路。主端业务应用层根据`EXADDR[7:3]`选择对应的物理链路;Transaction进入选定链路后,不依靠`EXADDR`完成线路层寻址。读响应保持请求CMD不变,因此其`EXADDR`仍保留被访问从端的编号。
|
||
|
||
`EXADDR[2:0]`用于从端内部的通道路由,具体定义如下:
|
||
|
||
| `EXADDR[2:0]` | 目的通道 |
|
||
|:---:|:---:|
|
||
| `3'b000` | 从端内部 |
|
||
| `3'b001` | A-SPI0 |
|
||
| `3'b010` | A-SPI1 |
|
||
| `3'b011` | A-SPI2 |
|
||
| `3'b100` | A-SPI3 |
|
||
| `3'b101` | A-SPI4 |
|
||
| `3'b110` | A-SPI5 |
|
||
| `3'b111` | B-SPI[1:0] |
|
||
|
||
一个确定的`EXADDR`值只映射到一个确定设备的一个确定通道。一次Transaction及其全部分片不得跨设备、跨SPI通道或跨地址空间边界。
|
||
|
||
#### 39.3.4 Transaction分片
|
||
|
||
Transaction的`LENGTH`最大支持1 MByte,可能超过`DATA`逻辑帧允许的最大载荷。`DATA`逻辑帧允许的最大`PAYLOAD`长度为1032字节,因此每个Transaction分片最多包含8字节`CMD`和1024字节`T_DATA`。
|
||
|
||
以下示意图以4200字节`T_DATA`为例,展示主端业务应用层的分片结果:
|
||
|
||
```mermaid
|
||
flowchart TB
|
||
O["原始Transaction<br/>ADDR = A,LENGTH = 4200<br/>T_DATA = 4200 B"]
|
||
S{"按T_DATA每片最多1024 B分片"}
|
||
F0["分片0<br/>ADDR = A,LENGTH = 1024<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
F1["分片1<br/>ADDR = A + 1024,LENGTH = 1024<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
F2["分片2<br/>ADDR = A + 2048,LENGTH = 1024<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
F3["分片3<br/>ADDR = A + 3072,LENGTH = 1024<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
F4["分片4<br/>ADDR = A + 4096,LENGTH = 104<br/>T_DATA = 104 B<br/>DATA逻辑帧 LEN = 112"]
|
||
|
||
O --> S
|
||
S --> F0
|
||
S --> F1
|
||
S --> F2
|
||
S --> F3
|
||
S --> F4
|
||
```
|
||
|
||
图中的每个分片都包含独立的8字节`CMD`。`ADDR`只按此前已经分片的`T_DATA`累计字节数递增,`CMD`长度不参与地址计算。
|
||
|
||
对于写请求,当原始Transaction的`T_DATA`超过1024字节时,主端业务应用层必须将其拆分为多个写请求,每个分片的`LENGTH`不得大于1024。例如,一个包含8字节`CMD`和4200字节`T_DATA`的Transaction,应拆分为4个包含1024字节`T_DATA`的分片和1个包含104字节`T_DATA`的分片;承载这些分片的`DATA`逻辑帧,其`LEN`依次为1032、1032、1032、1032和112字节。
|
||
|
||
对于读请求,其自身只携带8字节`CMD`。当`LENGTH`大于1024时,主端业务应用层必须将其拆分为多条读请求,每条读请求的`LENGTH`不得大于1024,以保证承载对应读响应的`DATA`逻辑帧之`LEN`不超过1032字节。
|
||
|
||
以下示意图以从地址`A`开始读取4200字节为例。五条分片读请求均只携带8字节`CMD`,所以承载请求的`DATA`逻辑帧之`LEN`均为8;每条读响应回显对应请求的`CMD`,并携带该分片指定长度的`T_DATA`:
|
||
|
||
```mermaid
|
||
flowchart TB
|
||
O["原始读请求<br/>ADDR = A,LENGTH = 4200<br/>不携带T_DATA"]
|
||
S{"按每条响应最多1024 B T_DATA拆分读请求"}
|
||
R0["读请求0<br/>ADDR = A,LENGTH = 1024<br/>DATA逻辑帧 LEN = 8"]
|
||
P0["读响应0<br/>CMD与读请求0完全一致<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
R1["读请求1<br/>ADDR = A + 1024,LENGTH = 1024<br/>DATA逻辑帧 LEN = 8"]
|
||
P1["读响应1<br/>CMD与读请求1完全一致<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
R2["读请求2<br/>ADDR = A + 2048,LENGTH = 1024<br/>DATA逻辑帧 LEN = 8"]
|
||
P2["读响应2<br/>CMD与读请求2完全一致<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
R3["读请求3<br/>ADDR = A + 3072,LENGTH = 1024<br/>DATA逻辑帧 LEN = 8"]
|
||
P3["读响应3<br/>CMD与读请求3完全一致<br/>T_DATA = 1024 B<br/>DATA逻辑帧 LEN = 1032"]
|
||
R4["读请求4<br/>ADDR = A + 4096,LENGTH = 104<br/>DATA逻辑帧 LEN = 8"]
|
||
P4["读响应4<br/>CMD与读请求4完全一致<br/>T_DATA = 104 B<br/>DATA逻辑帧 LEN = 112"]
|
||
|
||
O --> S
|
||
S --> R0 --> P0
|
||
S --> R1 --> P1
|
||
S --> R2 --> P2
|
||
S --> R3 --> P3
|
||
S --> R4 --> P4
|
||
```
|
||
|
||
图中的五组请求与响应相互独立。图示连线只表示对应关系,不表示各读响应必须按照请求编号顺序返回。
|
||
|
||
除`ADDR`和`LENGTH`外,每个分片的`W/R`、`ARD FLAG`、`CID`和`EXADDR`均复制原始Transaction。第`i`个分片的地址按此前各分片`T_DATA`的累计字节数计算:
|
||
|
||
```text
|
||
fragment_ADDR[i] = original_ADDR + sum(fragment_LENGTH[0 .. i-1])
|
||
```
|
||
|
||
8字节`CMD`不参与地址递增。发起方必须保证地址计算不会发生25位`ADDR`溢出;地址溢出不进入`EXADDR`,本应用配置不定义溢出后的处理。
|
||
|
||
接收端将每个分片作为独立Transaction分别执行,不重组原始长Transaction,也不保证全部分片构成一个原子操作。
|
||
|
||
## 40. 层间处理流程
|
||
|
||
### 40.1 `DL`正常接收
|
||
|
||
```text
|
||
Slave数据链路层:
|
||
SOF → 解扰 → 外层LEN → 流式输出 → CRC通过
|
||
↓
|
||
Slave传输协议层:
|
||
候选暂存 → SEQ==RCV_NEXT → 资源检查 → commit
|
||
↓
|
||
Slave业务应用层:
|
||
接收DATA载荷并按用户业务定义处理
|
||
```
|
||
|
||
### 40.2 `DL` CRC失败
|
||
|
||
```text
|
||
Slave数据链路层:rx_crc_valid=1,rx_crc_pass=0
|
||
↓
|
||
Slave传输协议层:rollback,不推进RCV_NEXT
|
||
↓
|
||
置RETRY_PENDING和ACK_PENDING
|
||
↓
|
||
通过UL发送RETRY_REQ
|
||
```
|
||
|
||
### 40.3 `UL` CRC失败
|
||
|
||
```text
|
||
Master数据链路层:rx_crc_valid=1,rx_crc_pass=0
|
||
↓
|
||
Master传输协议层:rollback并直接丢弃
|
||
↓
|
||
不发送ACK,不请求重传
|
||
```
|
||
|
||
### 40.4 外层`LEN`错误
|
||
|
||
```text
|
||
数据链路层:
|
||
检测OUTER_LENGTH_ERROR
|
||
↓
|
||
rx_frame_abort=1
|
||
↓
|
||
传输协议层rollback
|
||
↓
|
||
数据链路层进入边界恢复
|
||
```
|
||
|
||
### 40.5 `DATA`载荷的业务处理
|
||
|
||
```text
|
||
数据链路层:外层LEN合法且CRC通过
|
||
↓
|
||
传输协议层:完成SEQ与资源检查并提交DATA载荷
|
||
↓
|
||
业务应用层:按用户定义解释和执行载荷
|
||
```
|
||
|
||
业务应用层发现载荷语义错误或执行失败时,由用户业务自行处理。该结果不得使传输协议层撤销已经完成的累计确认,也不得触发链路重传或重新训练。
|
||
|
||
## 41. 分层实现一致性要求
|
||
|
||
1. 数据链路层必须独立解析外层`LEN`,以确定帧结束和CRC位置。
|
||
2. 数据链路层不得要求传输协议层返回帧结束位置。
|
||
3. rx_data_valid期间的数据必须被视为候选数据,CRC通过前不得提交。
|
||
4. 每个正常结束的候选帧必须产生一次且仅一次rx_crc_valid。
|
||
5. 外层`LEN`非法而无法定位CRC时,必须产生rx_frame_abort,不得让协议层无限等待CRC结果。
|
||
6. 接收接口不得使用能够暂停物理数据流的反压。
|
||
7. 发送接口必须具有帧开始前及帧间反压能力。
|
||
8. 一帧开始后不得在帧内暂停tx_data流。
|
||
9. 数据链路层必须生成CRC和扰码;传输协议层不得重复实现CRC。
|
||
10. `DATA`载荷的全部业务语义和执行结果必须由业务应用层处理。
|
||
11. 主端重传缓存必须保存CRC生成前、加扰前的协议帧内容。
|
||
12. `FRAME_COST`必须按不含CRC的逻辑帧长度计算,不得按重传RAM实际存储字节数计算。
|
||
13. `DL`和`UL`名称必须按第3章固定方向使用,不得相对当前端点反转含义。
|
||
14. 重新训练不得自动清除传输协议状态;只有双方完成session reset后才能重新初始化业务`SEQ`。
|
||
|
||
## 42. 时序预算与实现风险
|
||
|
||
### 42.1 接收眼图预算
|
||
|
||
\[
|
||
T_{有效}=UI-T_{tx\_jitter}-T_{rx\_jitter}-T_{channel\_ISI}-T_{skew}-T_{setup/hold}-T_{margin}
|
||
\]
|
||
|
||
\[
|
||
T_{margin,side}\approx\frac{T_{有效}}{2}
|
||
\]
|
||
|
||
最终最小窗口、中心保护量和重训阈值必须由发送/接收抖动、PCB/连接器损耗、差分偏斜、电源噪声、延迟 DNL/INL、PVT、ASIC 建立保持时间和 AC 耦合基线漂移共同确定。
|
||
|
||
### 42.2 主要实现风险
|
||
|
||
| 风险 | 后果 | 必须采取的措施 |
|
||
|---|---|---|
|
||
| 分频相位上电不确定 | 采样点落在数据边沿 | 每次上电执行完整双向校准 |
|
||
| 延迟范围不足 | 找不到完整窗口 | 增加粗相位搜索或调整时钟架构 |
|
||
| `TRAIN_ACK`无测试点标识 | 迟到应答污染下一点 | 严格测试时隙和最坏延迟保护间隔 |
|
||
| 只匹配`SOF` | 随机命中导致假事件 | 固定帧完整 160位匹配 |
|
||
| 在载荷内搜索`SOF` | 假失步和错误分帧 | 帧内按已验证长度计数 |
|
||
| CRC 错误立即重训 | 数据误码放大为链路中断 | CRC 错误与边界错误分开 |
|
||
| 流式输出立即产生副作用 | CRC 失败无法撤销 | 上层暂存,CRC 通过后提交 |
|
||
| 重训清空传输状态 | 两端状态不一致 | 物理重训保留传输状态,恢复后`POLL_REQ` |
|
||
| 多从端共用扫描状态 | 链路相互污染 | 每条链路独立状态、延迟和结果 |
|
||
|
||
## 43. 数据链路层与传输协议层接收接口
|
||
|
||
### 43.1 方向实例
|
||
|
||
| 端点 | 接收方向 | 建议前缀 |
|
||
|---|---|---|
|
||
| 从端 | `DL`接收 | `dl_rx_*` |
|
||
| 主端 | `UL`接收 | `ul_rx_*` |
|
||
|
||
以下使用通用名称 `rx_*` 描述,实际RTL按方向替换前缀。
|
||
|
||
### 43.2 接口信号
|
||
|
||
```text
|
||
rx_data[31:0]
|
||
rx_data_valid
|
||
rx_data_last
|
||
|
||
rx_crc_valid
|
||
rx_crc_pass
|
||
|
||
rx_frame_abort
|
||
rx_error_code
|
||
```
|
||
|
||
| 信号 | 方向 | 定义 |
|
||
|---|---|---|
|
||
| `rx_data[31:0]` | 链路层→协议层 | 解扰后的候选帧字,包含`SOF`和协议字段,不包含CRC |
|
||
| `rx_data_valid` | 链路层→协议层 | 当前rx_data属于候选帧 |
|
||
| `rx_data_last` | 链路层→协议层 | 当前字是逻辑帧的最后一个字 |
|
||
| `rx_crc_valid` | 链路层→协议层 | 当前候选帧的CRC结果有效 |
|
||
| `rx_crc_pass` | 链路层→协议层 | 在rx_crc_valid有效时表示CRC比较结果 |
|
||
| `rx_frame_abort` | 链路层→协议层 | 当前候选帧无法正常完成,协议层必须立即回滚 |
|
||
| `rx_error_code` | 链路层→协议层 | 帧中止或边界错误原因 |
|
||
|
||
### 43.3 错误码
|
||
|
||
建议至少支持:
|
||
|
||
```text
|
||
OUTER_LENGTH_ERROR
|
||
BOUNDARY_ERROR
|
||
SYNC_LOST
|
||
```
|
||
|
||
CRC失败使用 `rx_crc_valid=1` 且 `rx_crc_pass=0` 表示,不要求再使用rx_error_code重复报告。
|
||
|
||
### 43.4 接口时序
|
||
|
||
正常`DATA`:
|
||
|
||
```text
|
||
周期: 0 1 2 ... N N+1
|
||
rx_data: SOF SEQ/LEN PAYLOAD -
|
||
rx_data_valid: 1 1 1 0
|
||
rx_data_last: 0 0 最后字=1 0
|
||
rx_crc_valid: 0 0 0 1
|
||
rx_crc_pass: X X X PASS/FAIL
|
||
```
|
||
|
||
CRC结果对应此前最近一个已经产生 `rx_data_last` 的候选帧。
|
||
|
||
外层`LEN`非法时,数据链路层可能已经输出`SOF`及`SEQ`/`LEN`字。随后必须产生 `rx_frame_abort`,传输协议层不得继续等待rx_data_last或rx_crc_valid。
|
||
|
||
### 43.5 无接收反压
|
||
|
||
该接口不得依赖接收反压。数据链路层开始输出候选帧后,传输协议层必须能够连续消费整帧数据。
|
||
|
||
实现可以不提供 `rx_ready`。如果为了通用接口保留rx_ready,则必须保证一帧开始后始终为1,不得用于暂停物理接收流。
|
||
|
||
传输协议层资源不足时仍必须消费线路数据,可以停止写入候选缓存并标记资源错误,但不得阻塞数据链路层。
|
||
|
||
## 44. 传输协议层与数据链路层发送接口
|
||
|
||
### 44.1 方向实例
|
||
|
||
| 端点 | 发送方向 | 建议前缀 |
|
||
|---|---|---|
|
||
| 主端 | `DL`发送 | `dl_tx_*` |
|
||
| 从端 | `UL`发送 | `ul_tx_*` |
|
||
|
||
以下使用通用名称 `tx_*` 描述。
|
||
|
||
### 44.2 接口信号
|
||
|
||
```text
|
||
tx_data[31:0]
|
||
tx_data_valid
|
||
tx_data_ready
|
||
tx_data_last
|
||
tx_frame_done
|
||
```
|
||
|
||
| 信号 | 方向 | 定义 |
|
||
|---|---|---|
|
||
| `tx_data[31:0]` | 协议层→链路层 | 未加扰且不含CRC的逻辑帧字 |
|
||
| `tx_data_valid` | 协议层→链路层 | 当前tx_data有效 |
|
||
| `tx_data_ready` | 链路层→协议层 | 数据链路层当前能够接收逻辑帧字 |
|
||
| `tx_data_last` | 协议层→链路层 | 当前字是逻辑帧的最后一个字 |
|
||
| `tx_frame_done` | 链路层→协议层 | 自动追加的CRC最后一位已经发送到线路 |
|
||
|
||
### 44.3 反压规则
|
||
|
||
数据链路层可以在以下情况拉低tx_data_ready:
|
||
|
||
- 链路尚未同步;
|
||
- 正在训练或重新训练;
|
||
- 正在发送固定链路管理帧;
|
||
- 前一帧尚未完成;
|
||
- 正在为前一帧插入和发送CRC;
|
||
- 当前不在可接受新`SOF`的帧边界。
|
||
|
||
为了避免物理帧中断,必须满足:
|
||
|
||
1. 数据链路层可以在`SOF`握手前反压;
|
||
2. 一旦接受一帧`SOF`,数据链路层必须保持tx_data_ready有效直到接受tx_data_last;
|
||
3. 传输协议层一旦开始一帧,必须连续提供逻辑帧的全部字;
|
||
4. 数据链路层可以在接受tx_data_last后拉低就绪,用于发送CRC字段;
|
||
5. 下一帧`SOF`只能在数据链路层重新置位就绪后握手。
|
||
|
||
传输协议层在提交`SOF`前必须保证完整逻辑帧已经可连续读取,不得在帧中途因业务应用层断流而撤销有效。
|
||
|
||
### 44.4 发送完成语义
|
||
|
||
`tx_data_last`握手只表示数据链路层已经接受逻辑帧的最后一个字。只有 `tx_frame_done` 才表示:
|
||
|
||
- CRC已经生成;
|
||
- CRC已经完成加扰;
|
||
- 完整线路帧已经发送结束。
|
||
|
||
重传计时、发送描述符推进及无确认方向的线路发送完成通知应以tx_frame_done为边界。
|
||
|
||
## 45. 传输协议层与业务应用层接口
|
||
|
||
### 45.1 业务发送接口
|
||
|
||
建议接口包含:
|
||
|
||
```text
|
||
app_tx_valid
|
||
app_tx_ready
|
||
app_tx_len
|
||
app_tx_data
|
||
app_tx_data_valid
|
||
app_tx_data_ready
|
||
app_tx_data_last
|
||
app_tx_tag
|
||
```
|
||
|
||
业务应用层只提供`DATA`及其有效载荷,不提供`SOF`、`SEQ`、CRC或扰码数据。传输协议层负责分配`SEQ`、缓存可靠方向帧并生成发送逻辑帧。
|
||
|
||
### 45.2 业务发送结果
|
||
|
||
建议区分:
|
||
|
||
```text
|
||
app_tx_accepted
|
||
app_tx_completed
|
||
```
|
||
|
||
| 事件 | 含义 |
|
||
|---|---|
|
||
| `app_tx_accepted` | 传输协议层已经接收并保存业务请求 |
|
||
| `app_tx_completed` | 该方向规定的完成条件已经满足 |
|
||
|
||
`DL`的 `app_tx_completed` 表示对应`SEQ`已经被累计ACK确认。`UL`的 `app_tx_completed` 只表示完整线路帧已经发送,不保证主端接收成功。
|
||
|
||
### 45.3 业务接收接口
|
||
|
||
建议接口包含:
|
||
|
||
```text
|
||
app_rx_valid
|
||
app_rx_ready
|
||
app_rx_len
|
||
app_rx_data
|
||
app_rx_data_valid
|
||
app_rx_data_ready
|
||
app_rx_data_last
|
||
```
|
||
|
||
业务应用层接口可以使用反压,因为传输协议层负责接收缓存和窗口管理。只有协议接受帧才能出现在该接口。
|
||
|
||
对于`DL`,从端只有在完整帧已经可靠写入接收缓存后才能推进`RCV_NEXT`并触发累计ACK。
|
||
|
||
## 46. 链路状态与恢复接口
|
||
|
||
### 46.1 数据链路层向传输协议层
|
||
|
||
```text
|
||
link_up
|
||
sync_lost
|
||
retrain_busy
|
||
retrain_done
|
||
session_reset
|
||
```
|
||
|
||
| 信号 | 含义 |
|
||
|---|---|
|
||
| `link_up` | 普通协议帧可以发送和接收 |
|
||
| `sync_lost` | 当前字或帧边界不再可信 |
|
||
| `retrain_busy` | 数据链路层正在执行训练和同步恢复 |
|
||
| `retrain_done` | 物理同步已经重新建立 |
|
||
| `session_reset` | 双方已经完成完整协议会话复位,传输`SEQ`必须重新初始化 |
|
||
|
||
### 46.2 传输协议层向数据链路层
|
||
|
||
```text
|
||
retrain_request
|
||
sync_reset_request
|
||
```
|
||
|
||
| 请求 | 数据链路层动作 | 传输协议层状态 |
|
||
|---|---|---|
|
||
| `retrain_request` | 重新执行物理训练和同步 | 保留`SEQ`、窗口状态和未确认重传缓存 |
|
||
| `sync_reset_request` | 执行双方完整会话复位流程 | 完成session_reset后清空并重新初始化 |
|
||
|
||
物理重新训练完成后,主端传输协议层应发送`POLL_REQ`重新取得从端的`ACK_NEXT`和`WIN_BYTES`,再恢复`DL`发送或重传。
|
||
|
||
# 第七篇实现、诊断与验证
|
||
|
||
## 47. RTL 实现输出与诊断契约
|
||
|
||
每条链路至少提供:
|
||
|
||
| 输出 | 含义 |
|
||
|---|---|
|
||
| `link_sync_up` | 当前链路允许传输协议层工作 |
|
||
| `link_retraining` | 当前处于训练/重训 |
|
||
| `master_state / slave_state` | 顶层状态 |
|
||
| `monitor_state` | 运行期监测状态 |
|
||
| `rx_delay_selected` | `UL`最终`IDELAY` |
|
||
| `tx_delay_selected` | `DL`最终`ODELAY` |
|
||
| `rx_pass_first/last` | `UL`选中窗口边界 |
|
||
| `tx_pass_first/last` | `DL`选中窗口边界 |
|
||
| `rx_pass_bitmap / tx_pass_bitmap` | 扫描结果 |
|
||
| `fixed_frame_error_count` | 固定帧比较错误数 |
|
||
| `crc_error_count` | 普通帧 CRC 错误数 |
|
||
| `length_error_count` | 外层长度非法数 |
|
||
| `boundary_recovery_count` | 边界恢复次数 |
|
||
| `retrain_count` | 重训次数 |
|
||
| `last_retrain_reason` | 最近重训原因 |
|
||
| `resource_fault` | 时钟、延迟或串并转换故障 |
|
||
|
||
计数器可饱和,不应无提示回卷。跨时钟域读取状态和延迟值时必须使用可靠 CDC。
|
||
|
||
## 48. 验证与验收要求
|
||
|
||
### 48.1 RTL 仿真
|
||
|
||
至少覆盖:
|
||
|
||
1. 所有固定帧的 160位正确匹配及单位错误拒绝;
|
||
2. `PRBS7`初值、位序、终止位置和 64/64 平衡;
|
||
3. 扫描位图、最长窗口、并列窗口和偶数中心选择;
|
||
4. 窗口触及扫描边界时不误判完成;
|
||
5. `IDELAY`点连续49个`TRAIN`后出现错误时计数清零,连续50个时立即通过,200帧到期时失败;
|
||
6. 从端在连续50个`DL` `TRAIN`后锁存`TRAIN_ACK`发送状态,并只由合法`IDLE`点间隔解除;
|
||
7. `ODELAY`点连续9个`TRAIN_ACK`后出现非ACK固定帧时计数清零,连续10个时立即通过,200帧到期时失败;
|
||
8. 4帧`TRAIN`中断、4帧ACK排空以及最多16帧点间隔能够隔离迟到`TRAIN_ACK`;
|
||
9. 从端的`DL` `SYNC`连续计数在9999后出现错误时清零,连续10000个时通过;
|
||
10. 从端精确发送20个`SYNC_ACK`,主端连续10个时通过;
|
||
11. 主端进入`UL`确认后忽略剩余`SYNC_ACK`,并从第一个完整`SYNC`开始累计10000个连续`SYNC`;
|
||
12. 主端和从端的`SYNC`均由状态条件终止,并能由超时退出;
|
||
13. 主端以`IDLE`结束同步,从端停止`SYNC`并返回`IDLE`,双方自动进入`RUN`;
|
||
14. 载荷中出现全部`SOF`/`IDLE`图样时不误分帧;
|
||
15. CRC错误且长度合法时保持边界;
|
||
16. 长度非法、位滑移、FIFO溢出时进入恢复;
|
||
17. 恢复成功和搜索超时重训;
|
||
18. 物理重训前后传输状态保持;
|
||
19. 多从端处于不同状态且互不影响;
|
||
20. power_on初始化、PLL失锁和延迟就绪丢失发生在各主要状态时的行为。
|
||
21. `DATA`和`CTRL`无`IDLE`背靠背发送时,下一`SOF`只在计算得到的边界被识别;
|
||
22. 帧长可确定但CRC错误、下一边界为合法`IDLE`或`SOF`时,丢弃当前帧但保持同步;
|
||
23. 帧长可确定但CRC错误、下一边界也非法时,进入边界恢复;
|
||
24. `LEN`越界或未按4字节对齐时,不使用该`LEN`继续计数并立即进入恢复;
|
||
25. `LEN`误码后仍为合法值时,接收等待不超过对应最大帧长度,随后由CRC或下一边界发现异常;
|
||
26. 依次注入8种4位字偏移以及实现支持的全部位滑移位置,验证滑动搜索和重新锁定;
|
||
27. 恢复期间出现仅`SOF`匹配但完整固定帧、长度或CRC失败时,不得错误恢复边界。
|
||
|
||
### 48.2 门级、时序与板级验证
|
||
|
||
- 对所选物理配置的SERDES时钟、串行采样时钟、并行时钟和所有CDC路径完成静态时序检查;第7.3节典型配置对应375 MHz DDR与750 MHz SDR;
|
||
- 验证延迟控制时序;
|
||
- 在工艺、电压、温度角落记录窗口宽度和中心漂移;
|
||
- 在最长线、最差连接器和最大同时翻转条件下测量;
|
||
- 验证 AC 耦合基线漂移和终端匹配;
|
||
- 注入位错误、CRC错误、长度错误、位滑移、时钟失锁和固定帧丢失;
|
||
- 验证重训后传输层通过`POLL_REQ`恢复且不丢失已确认状态。
|
||
|
||
### 48.3 链路验收条件
|
||
|
||
一条链路只有同时满足以下条件才可进入系统可用状态:
|
||
|
||
- `UL`和`DL`均找到不小于规定宽度的有效窗口;
|
||
- `UL`和`DL`窗口中心均已装载;
|
||
- 从端连续正确检测10000个`DL` `SYNC`,主端连续正确检测10个`SYNC_ACK`;
|
||
- 从端精确发送20个`SYNC_ACK`后持续发送`SYNC`,主端连续正确检测10000个`UL` `SYNC`;
|
||
- 运行入口的`DL`和`UL` `IDLE`被双方正确识别;
|
||
- `link_sync_up` 稳定;
|
||
- 初始协议`POLL_REQ`/ACK 完成后,传输协议层声明 `transport_ready`。
|
||
|
||
`link_sync_up` 表示物理和帧边界可靠;`transport_ready` 表示可靠传输状态已经对齐。业务应用层只能在 `transport_ready` 后启动需要可靠`DL`的业务。
|
||
|
||
## 49. 实现基线结论
|
||
|
||
本方案将复杂性集中在主端:主端负责两个方向的延迟扫描、窗口分析、中心选择、同步确认和运行期恢复;从端只需使用所选物理配置规定的固定收发结构,并完成固定帧比较、`TRAIN_ACK`/`SYNC_ACK`生成、普通帧解析和同步监测;第7.3节典型配置使用750 MHz SDR。
|
||
|
||
正常上电顺序固定为“从端连续`TRAIN` → 主端校准`UL` → 主端校准`DL` → 主端持续`SYNC` → 从端定量`SYNC_ACK`并持续`SYNC` → 主端持续`IDLE` → 双方`RUN`”。运行期通过确定边界上的`IDLE`/`SOF`、帧内长度计数和帧尾 CRC完成持续监测;内容错误与边界失步分开处理。发生物理失步时执行重训并保留传输协议状态。
|
||
|
||
## 附录A:互操作实现声明清单
|
||
|
||
每个符合本规范的设备或IP至少应提供以下声明:
|
||
|
||
1. 本规范版本:V0.3;
|
||
2. 主端或从端角色;
|
||
3. 采用的物理实现配置及第7章全部参数;
|
||
4. 最大`DATA`载荷;
|
||
5. 接收窗口容量及重传缓存容量;
|
||
6. 延迟范围、步进和最小通过窗口;
|
||
7. 第27章规定的训练计数、超时和间隔参数;
|
||
8. 是否支持`SYNC_RESET`及会话复位;
|
||
9. 对外层间接口的位宽和时钟域映射;
|
||
10. 第48章验证项目的完成情况。
|
||
|
||
两端只有在线路编码、物理实现配置和方向行为一致时才能互操作。实现可以在内部采用不同流水线、RAM组织、状态编码和时钟域结构,但不得改变线路比特序列、接收接受条件、确认语义或错误恢复行为。
|