Asymmetric_Reliable_Serial_.../非对称可靠串行传输技术规范.md

4068 lines
261 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

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

# 非对称可靠串行传输技术规范
**Asymmetric Reliable Serial Transport Technical Specification**
**版本:V1.0**<br>
**日期:2026-10-02**<br>
**作者:周爽**
---
## 修订记录
| 版本 | 日期 | 说明 |
|---|---|---|
| V1.0 | 2026-10-02 | 统一重新训练为UL校准、DL校准、双向同步确认及新会话建立的完整流程;取消DL单向重训和人为UL异常通知;明确训练失败与单点失败的区别;加入独立等价的1-bit串行CRC模块及32-bit自定义CRC参考函数,完善关键要求和验证索引。 |
| V0.9 | 2026-10-01 | 完善分层接口的确定性语义;补充诊断可观察性、接口时序、重新训练握手、验证验收与互操作声明要求。 |
| V0.8 | 2026-10-01 | 完善重传协议的确定性实现规则;统一协议层`link_up`接口,明确最大接收能力、窗口计时切换、`POLL_REQ`、业务接口契约、状态图说明及重传验证要求。 |
| V0.7 | 2026-10-01 | 完善链路训练和运行期监测的异常闭环;明确主端重启可见性、运行入口就绪时机、连续计数与超时优先级、可信方向帧边界切换、方向化重训、恢复候选帧丢弃、单个IDLE恢复、意外固定帧处理及运行期CRC错误门限。 |
| V0.6 | 2026-10-01 | 完善主从同步与重新训练状态机;明确重复`SYNC_RESET`、训练应答保护、同步确认和运行入口超时;补充`IDELAY`与`ODELAY`扫描状态机;统一200帧边界搜索与测量周期;修订完整UI环形窗口、`ALL_PASS`及最小通过窗口派生规则。 |
| V0.5 | 2026-09-30 | 明确链路重新训练期间的传输状态保持、恢复门控及主从状态机行为;统一`IDLE`和`CRC32`术语;修订数据协议边界、封装解析图、发送仲裁、`LEN`校验及帧内字计数规则;更新延迟配置就绪语义、`ODELAY`点间隔确认及运行入口`IDLE`握手。 |
| V0.4 | 2026-09-30 | 重构通信机制概述与总体架构,补充SEQ术语定义;明确规范核心覆盖数据链路层和传输协议层,将相位或延迟调节单元及其控制归入数据链路层的物理接口适配功能,并明确业务应用配置的可选属性。 |
| 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. 范围、目标与适用边界
本规范定义一种用于点对点、全双工、同源时钟串行链路的非对称可靠传输技术。规范覆盖线路帧编码、链路训练与同步、运行期边界监测、主端到从端方向的可靠传输与重传、从端到主端方向的无确认传输,以及数据链路层、传输协议层和业务应用层之间的接口契约。
本规范所定义通信机制的总体工作原理、分层架构和运行阶段见第4章。
本规范不限定具体物理承载、线路速率或内部串并转换结构。实现可以采用差分或单端物理通道,但通信双方必须具有兼容的外部电气接口、线路速率和同源时钟关系,并满足本规范的编码、状态行为、时序上界及层间接口语义。第7.3节以750 Mbps LVDS链路作为典型配置。
本规范面向RTL、ASIC、FPGA及功能等价的其他实现。互操作设备必须选择相互兼容的外部物理接口配置,并实现本规范中所有标记为“必须”的行为。
本规范明确以下边界:
- 本规范的核心实现规则覆盖数据链路层和传输协议层;
- 物理承载的内部实现不属于本规范的规定范围;本规范只约束其点对点串行通道、同源时钟条件、线路速率、电气特性和连续比特流;
- 数据链路层负责串行收发适配、相位或延迟调节单元及其扫描与配置、训练、同步、边界、加扰、CRC和线路帧封装;
- 传输协议层负责业务帧序号管理、接收窗口、确认与重传,并控制接收数据的提交和回滚;
- 业务应用层负责解释和处理有效载荷,其内部实现不属于基础传输规范的强制要求,但必须遵守与传输协议层之间的职责边界和接口语义;
- 基础传输规范不强制规定具体业务数据格式;可选业务应用配置另行明确其适用条件。
### 1.1 可靠性保证与适用前提
DL可靠传输保证的是:在同一会话中,按业务帧序号依次接受DATA,重复帧不重复提交,发送端通过累计确认得知协议接收已完成。ACK不表示业务应用层已经执行载荷所描述的操作。UL采用无确认传输,允许数据丢失和重复,发送完成不保证对端接收成功。
恢复传输进展以时钟和物理资源可用、对端遵守规范、接收资源最终可用且错误不会持续阻断所有有效交换为前提。连续失败达到门限或同步丢失时,协议终止会话并报告尚未完成的请求;本规范不保证跨会话自动重发或跨会话只执行一次。
CRC比较通过只表示满足本规范的完整性检查,不能证明不存在未检出的错误。安全、业务执行确认及跨会话重复操作保护由业务应用另行定义。
## 2. 规范性用语与一致性
“必须”表示互操作实现不可省略的要求;“不得”表示被禁止的行为;“应”表示正常情况下采用的要求,偏离时必须证明不影响互操作;“可以”表示允许的实现选择;“建议”表示不影响设备互操作性的实现指导。
当概述、示意图和字段表之间存在理解差异时,按以下顺序确定要求:
1. 精确字段表、状态转移条件和数学公式;
2. 逐项文字规则;
3. 时序图和状态图;
4. 说明性示例。
帧格式、码字、CRC和扰码的唯一权威定义位于第9章至第17章。同步状态机不得另行改变这些线路编码。传输重试机制的唯一权威定义位于第28章至第36章。第7章的典型LVDS配置只约束声明采用该配置的设备。
### 2.1 要求、指导与可选配置
| 内容类别 | 适用规则 |
|---|---|
| 基础规范要求 | 第9~36章的编码与运行行为,以及第37~48章的分层、接口和适用验证要求,按角色实现;不得通过采用示例配置改变固定规则 |
| 物理配置约束 | 第5~7章规定外部兼容条件及实现声明;具体器件内部结构不属于统一实现要求 |
| 可选配置 | 第7.3节典型物理配置仅适用于声明采用该配置的设备;第39.3节Transaction业务配置仅适用于声明支持该业务配置的设备 |
| 实现指导与示例 | 标明“建议”“示例”或“典型”的内容用于解释;不替代其引用的精确规则 |
实现可使用功能等价的内部接口、并行算法或状态编码,但必须保持规定的线路编码、事件顺序、接收提交条件及层间接口语义。示意图只展示所标明的路径;未画出的公共优先级和异常行为仍按正文执行。
### 2.2 关键要求编号与验证索引
本版为关键实现要求设置`REQ-`编号。编号定位要求所在章节,不另建一套行为定义;第48.5节给出编号、权威定义及验证项目之间的对应关系。没有编号的“必须”和“不得”要求同样有效。
## 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`帧 |
| 业务帧序号(`SEQ`) | `DATA`帧携带的16位模65536序号;每条物理链路的每个方向分别维护独立的序号空间。`DL`使用`SEQ`进行累计确认和重传控制,`UL`仅使用`SEQ`循环编号,不依据其执行确认或重传 |
| 控制帧 | `CTRL`帧,不占用业务`SEQ` |
| 固定帧 | `TRAIN`、`TRAIN_ACK`、`SYNC`、`SYNC_ACK`或`SYNC_RESET` |
| 逻辑帧 | 传输协议层交给数据链路层的完整帧内容,包括明文`SOF`、协议字段和载荷,不包含`CRC32`且未加扰 |
| 线路帧 | 数据链路层对逻辑帧追加`CRC32`(适用时)并按规定加扰后,实际在线路上传送的完整位串 |
| 线路侧(on-wire) | 指经过本规范规定的封装和扰码处理后,实际通过单个`DL`或`UL`物理通道传输的比特、码字或帧 |
| 采样通过窗口 | 延迟扫描中连续判定为通过的延迟档位范围 |
| 接收窗口 | 从端以`ACK_NEXT`为锚点公告并承诺的逻辑帧字节额度;不表示可以累加的增量信用 |
| 链路同步 | 完成训练、双向同步确认和帧边界建立,使链路可以传输普通协议帧 |
| 新会话初始化 | 同步恢复后,主端通过`POLL_REQ`确认控制帧通路可用、取得从端`WIN_BYTES`,并以响应中的`ACK_NEXT`初始化新会话发送序号的过程 |
| 回退N帧(Go-Back-N) | 发生错误后从最早未确认序号开始连续重传的机制 |
| 单位间隔(UI) | 一个线路位的持续时间 |
| 接收 | 线路数据进入帧解析器的过程;不表示该帧已经校验通过、被传输协议层接受或提交给上层 |
| CRC通过 | 完整接收普通线路帧后,计算CRC与收到的CRC字段一致;不表示协议已经接受 |
| 格式合法 | 帧满足适用的`SOF`、长度及方向相关控制字段规则;固定帧须完整匹配码型 |
| 接受 | 业务帧的`SEQ`和接收资源满足要求,传输协议层决定保留该帧 |
| 协议提交(commit) | 适用的CRC、格式、序号及资源检查完成后,将候选帧确认为可由业务接收接口读取的数据;不要求业务应用层已经读取或执行 |
| 回滚(rollback) | 丢弃候选帧,并保证该帧未产生任何上层可见副作用 |
| 确认 | 从端通过`ACK_NEXT`对此前已经接受的`DL DATA`业务帧进行累计确认 |
| 释放 | 主端根据有效累计确认移除未确认记账;仍被在途发送器使用的存储须延迟回收至不再使用 |
| 请求接受完成 | 业务发送接口末字握手完成,请求已被协议层保存 |
| 线路发送完成 | 一个线路帧的CRC最后一位已发送完毕,由`tx_frame_done`表示 |
| 业务发送结果形成 | DL请求已被累计确认,或UL请求已有效完成线路发送;结果形成与结果脉冲交付可以不在同一周期 |
### 3.3 通用缩写
| 缩写 | 中文名称 | 英文全称或说明 |
|---|---|---|
| `SOF` | 帧起始标记 | Start of Frame |
| `SEQ` | 业务帧序号 | Sequence Number |
| `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 |
## 4. 通信机制概述与总体架构
### 4.1 通信机制概述
本规范定义一种采用同源时钟的点对点全双工串行通信机制。系统由一个主端和一个或多个从端组成,每个从端分别通过独立的下行链路`DL`和上行链路`UL`与主端连接。链路采用连续传输方式:有协议帧时发送协议帧,没有其他内容时持续发送`IDLE`,线路上不出现未定义空洞。
主端承担可调延迟扫描、窗口判定、可靠发送和重传等复杂功能;从端使用固定收发时序和较简单的确定性状态机。链路启动时,主端先校准`UL`接收采样位置,再校准`DL`发送位置,随后完成双向同步确认。物理同步建立后,双方对齐传输状态并进入正常业务通信。
正常通信采用非对称传输策略:主端到从端的`DL`业务数据使用确认、接收窗口和错误重传保证可靠交付;从端到主端的`UL`业务数据采用无确认传输,主端丢弃校验失败的数据而不要求从端重传。运行期间,数据链路层持续维护帧边界并监测同步状态;发现同步丢失时,系统退出正常通信,并对该从端对应的UL和DL执行完整重新训练。
本章用于建立对完整通信机制的总体认识,不替代后续章节中的精确字段定义、状态转移条件、计数参数和接口时序。发生解释差异时,应按第2章规定的优先级采用后续详细规范。
### 4.2 分层架构
```mermaid
flowchart TB
APP["<b>业务应用层</b><br/>产生和解释有效载荷"] <--> TP["<b>传输协议层</b><br/>序号、窗口、确认与重传"]
TP <--> DLAYER["<b>数据链路层</b><br/>串并转换、相位或延迟调节、训练、同步、边界、CRC与扰码"]
DLAYER <--> PHY["<b>物理承载</b><br/>点对点连续串行通道与同源时钟条件"]
```
各层按照以下边界协同工作:
- 业务应用层产生和消费`DATA`有效载荷,不处理线路帧、业务序号或重传;
- 传输协议层将业务载荷组织为逻辑帧,维护业务`SEQ`、累计确认、接收窗口和重传状态;
- 数据链路层完成串行收发与串并转换适配、相位或延迟调节单元的实现和控制、线路帧封装与解析、`CRC32`、扰码、训练、同步及边界恢复;
- 物理承载提供独立的双向点对点串行通道、共同频率基准和满足信号完整性要求的连续比特流。本规范只约束这些外部条件,不规定其内部实现。
传输协议层交给数据链路层的内容称为逻辑帧。数据链路层追加适用的`CRC32`并执行规定的扰码后,形成实际通过物理通道发送的线路帧。三层功能和层间接口的完整要求见第37章至第46章。
### 4.3 链路建立流程
系统从上电或复位后的资源等待状态开始,按照下列顺序建立通信:
```mermaid
flowchart LR
READY["物理与时钟资源就绪"] --> ULTRAIN["UL训练<br/>主端扫描接收延迟"]
ULTRAIN --> DLTRAIN["DL训练<br/>主端扫描发送延迟"]
DLTRAIN --> SYNC["双向同步确认<br/>建立稳定帧边界"]
SYNC --> ALIGN["新会话初始化<br/>确认控制通路并取得接收窗口"]
ALIGN --> RUN["正常业务通信"]
```
资源就绪表示双方已经具备稳定参考时钟、可用收发路径以及完成初始化的延迟调节资源。`UL`训练期间,从端连续发送训练序列,主端扫描接收采样位置并选择通过窗口中心。`DL`训练期间,主端在不同发送延迟下发送定量训练序列,并根据从端返回的训练应答确定通过窗口中心。
延迟校准完成后,双方通过长同步序列和同步应答确认两个方向均能稳定识别帧边界。随后主端使用`POLL_REQ`确认控制帧通路可用、取得从端可用接收窗口,并以初始响应中的`ACK_NEXT`设置新会话发送起点;合规从端发送的起始值为0。各阶段的精确状态机、判定计数和等待间隔见第18章至第27章;新会话初始化规则见第28章至第36章。
### 4.4 运行期非对称传输
```mermaid
flowchart LR
M["主端"] -->|"DL:可靠DATA<br/>累计ACK、字节窗口、Go-Back-N重传"| S["从端"]
S -->|"UL:无确认DATA<br/>不要求重传"| M
S -->|"UL:CTRL<br/>报告ACK_NEXT与WIN_BYTES"| M
M -->|"DL:CTRL<br/>状态询问与控制请求"| S
```
在`DL`方向,主端只在公告窗口允许时首次发送新的业务帧,并保存所有尚未累计确认的业务帧。从端按期望序号接收,通过累计`ACK`报告下一期望序号,并使用`WIN_BYTES`公布可继续占用的接收容量。出现帧错误、序号不符合预期或确认超时时,主端按照回退N帧机制从最早未确认帧开始重传。
在`UL`方向,从端按循环序号发送业务帧,但不保存待确认副本,也不等待主端确认。主端对通过格式和`CRC32`检查的帧正常提交,对损坏帧直接丢弃;序号跳变或重复不触发`UL`重传。`UL`承载的`CTRL`用于支持`DL`可靠传输,不改变`UL DATA`自身的无确认属性。
`DATA`、`CTRL`和固定同步类帧均以完整帧为单位仲裁。一帧开始发送后必须连续发送至帧尾;当没有其他帧可发送时,发送端持续发送`IDLE`。线路帧格式及编码规则见第8章至第17章,可靠传输和重传的精确算法见第28章至第36章。
### 4.5 同步监测与异常恢复
正常通信期间,数据链路层在已知帧边界上识别`IDLE`或合法`SOF`。识别到带长度字段的帧后,先依据`LEN`得到暂定帧尾并完成整帧解析;到达暂定边界后,只有下一个位置仍无法识别`IDLE`或合法`SOF`时,才进入边界恢复。单帧`CRC32`失败表示该帧内容不可信,但不单独等同于链路失步。
空闲期间如果不能持续检测到合法`IDLE`,或者帧结束后的预期边界不能恢复,数据链路层按规定门限判定同步异常。任何需要启动新一轮重新训练的异常均从UL校准开始,依次重新校准UL和DL并完成双向同步确认,不跳过已校准方向;训练入口及对端通知按第26章执行。
任一方向同步丢失都会终止当前双向传输协议会话,并使双方传输协议层复位。重新训练一律执行完整UL→DL流程;可信方向仅用于在途帧排空及训练入口通知,不用于跳过校准。同步恢复后,主端通过`POLL_REQ`取得从端当前的`WIN_BYTES`并确认控制帧通路可用;从端必须在初始响应中发送`ACK_NEXT=0`,主端把实际收到的`ACK_NEXT`作为新会话起始序号,不将其解释为旧会话累计确认。完成新会话初始化后,传输协议层才允许对业务发送接口置位`app_tx_ready`。详细规则见第26.2节、第35章和第46章。
### 4.6 后续内容索引
| 内容 | 详细章节 |
|---|---|
| 物理拓扑、同源时钟和典型实现配置 | 第5章至第7章 |
| 公共编码、帧格式、CRC、扰码和解析 | 第8章至第17章 |
| 延迟训练、同步确认、运行期监测和重新训练 | 第18章至第27章 |
| 累计确认、接收窗口、重传和传输状态机 | 第28章至第36章 |
| 三层职责、处理流程及层间接口 | 第37章至第46章 |
| RTL诊断、验证与实现基线 | 第47章至第49章 |
本规范对重复出现的机制采用以下规则来源:第14章定义`CTRL`字段及适用检查;第25章定义运行期边界恢复;第26章定义会话终止与重新训练;第35章定义传输状态转移与并发动作;第43~46章定义层间接口时序。其他章节的图和流程用于解释或引用,不另行定义不同规则。概念事件不是额外的RTL端口,功能接口以第43~46章为准。
## 5. 物理承载的通用要求
物理承载必须提供相互独立的`DL`和`UL`连续串行通道。双方必须预先采用一致的线路速率、位序和时钟关系。本版不定义在线物理参数协商。
物理承载必须满足:
1. 两端串行线路速率相同且长期无频差;
2. 接收端能够连续观察串行流,帧间不得出现未定义空洞;
3. 电气实现满足所选介质的眼图、抖动、共模和耦合要求;
4. 数据链路层看到的比特流满足第9章规定的位序和字节序。
# 第二篇 物理承载、时钟与链路实现配置
## 6. 同源时钟与物理拓扑
`DL`和`UL`名称按系统拓扑固定,不随当前观察端点改变。多个从端场景中,每个从端均通过独立的一条`DL`和一条`UL`连接到主端,帧内不设置设备地址。
系统可以包含一个主端和一个或多个从端。每个从端拥有一条独立`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_LINE_FRAME_BYTES` | 派生常量1044 B:固定最大1032 B载荷加8 B逻辑头及4 B CRC,不允许按产品配置降低 |
| `MAX_LINE_FRAME_WORDS` | 派生常量261个32位字 |
| `TRAIN_TIMEOUT` | 按线路速率换算的训练超时参数 |
配置由硬件设计、寄存器或系统集成约束预先确定。本版不设置在线协商帧。
#### 7.1.1 参数分类
| 类别 | 代表参数 | 约束 |
|---|---|---|
| 规范固定值 | 最大载荷1032 B、编码位序、固定码字、CRC和扰码规则;第27章注明“固定为”的计数;连续无进展失败轮数3 | 所有适用实现必须一致,不允许产品自行修改 |
| 派生值 | UI、最大线路帧字节/字数、最小通过窗口时间和档位数、定时器周期数 | 按规定公式和配置输入计算,不独立配置 |
| 实现配置值 | 线路速率、电气接口、串并比、延迟映射、最小窗口比例、边界恢复上限及ACK/查询超时 | 必须声明确定值,并满足相应下限、时序预算及兼容条件 |
配置时间换算为计数周期时必须向上取整;实现声明必须同时记录实际时钟、计时起点和计算所得周期数。第27章和第33章的典型值不得误作所有物理配置的统一时间值。
### 7.2 数据链路层的相位与延迟能力
主端数据链路层的物理接口适配子模块必须能够改变`UL`采样相位或等效输入延迟,并能够改变`DL`发送相位或等效输出延迟。调节范围必须覆盖至少一个完整UI,或通过粗相位与细延迟组合达到等效覆盖。`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比特流。若实现配置采用第23.2节建议的`MIN_PASS_WINDOW_RATIO=0.4`,则派生的`MIN_PASS_WINDOW_TIME`约为533.3 ps;该数值仅属于本750 Mbps典型配置。
### 7.4 其他配置的适配规则
采用其他物理承载或速率时,不得修改帧格式、`SOF`、`LEN`、CRC、扰码、固定训练码型及传输状态语义。所有以帧数为单位的连续检测判据保持不变;以时间或时钟周期表示的等待和超时参数必须按实际线路速率重新计算。延迟扫描范围、延迟档位步进和最小通过窗口必须根据UI及目标时序裕量重新验证。
### 7.5 AC耦合与信号完整性
采用AC耦合时,发送端仍必须遵循第16章的扰码规则。固定训练帧和`IDLE`依靠其预定义码型获得均衡性质。扰码不能替代通道级基线漂移、最长连续同码、抖动和眼图验证;具体物理配置必须证明最坏业务数据、最大帧和连续控制流满足接收器要求。
### 7.6 时序预算与实现风险
#### 7.6.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 耦合基线漂移共同确定。
#### 7.6.2 主要实现风险
| 风险 | 后果 | 必须采取的措施 |
|---|---|---|
| 分频相位上电不确定 | 采样点落在数据边沿 | 每次上电执行完整双向校准 |
| 延迟范围不足 | 找不到完整窗口 | 增加粗相位搜索或调整时钟架构 |
| `TRAIN_ACK`无测试点标识 | 迟到应答污染下一点 | 严格测试时隙和最坏延迟保护间隔 |
| 只匹配`SOF` | 随机命中导致假事件 | 固定帧完整 160位匹配 |
| 在载荷内搜索`SOF` | 假失步和错误分帧 | 帧内按范围及对齐合法的`LEN`计数,CRC前不得提交 |
| CRC 错误立即重训 | 数据误码放大为链路中断 | CRC 错误与边界错误分开 |
| 流式输出立即产生副作用 | CRC 失败无法撤销 | 上层暂存,CRC 通过后提交 |
| 仅单端清空传输状态 | 两端会话不一致 | 任一同步丢失都使双方复位协议状态;从端初始响应固定发送`ACK_NEXT=0`,主端以实际收到的`ACK_NEXT`同时初始化`SND_UNA`和`SND_NXT`并取得`WIN_BYTES` |
| 多从端共用扫描状态 | 链路相互污染 | 每条链路独立状态、延迟和结果 |
# 第三篇 统一数据协议
## 8. 数据协议的接口边界
本规范定义帧标识、字段布局、位序、字节序、长度约束、固定训练码型、`CRC32`、扰码/解扰、发送封装、接收解析及格式错误报告。
`TRAIN`、`TRAIN_ACK`、`SYNC`、`SYNC_ACK`、`SYNC_RESET`虽由链路状态机处理,其线路表示仍由本规范统一定义。
本篇规定帧编码、封装、解析以及错误报告规则,不在本篇重复规定链路训练和可靠传输状态机。延迟扫描、同步握手顺序、固定帧重复发送次数及链路重新训练策略见第四篇;`SEQ`初始化、窗口调度、重传触发及超时参数见第五篇。接收解析器只报告格式和完整性检查结果,不自行决定该帧在当前链路状态或传输状态下是否可以执行。
适用链路为点对点全双工同源时钟串行链路;具体物理承载和线路速率由第7章的实现配置声明确定。每个方向独立形成一个连续串行流。多个从端分别使用独立链路,线路帧不含设备地址。逻辑序号不表示物理帧位置。
## 9. 公共编码规则
<a id="req-enc-001"></a>
### 9.1 位序、字节序与字序
关键要求编号:`REQ-ENC-001`。
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 字节整数倍。
- 在没有其他帧可发送时,连续发送`IDLE`。帧之间可以直接相接,不要求额外`IDLE`。
- 一帧开始后必须连续发送至结束。不得在帧内插入`IDLE`、控制帧、等待字或其他填充。
- 不使用字节转义、位填充、EOF、8b/10b 或 64b/66b 编码。
- `PAYLOAD`不自动补齐;提交给编码器的数据长度必须满足本规范。`DATA`和`CTRL`的逻辑帧不包含CRC;数据链路层追加4字节CRC后再执行等长扰码,因此其线路帧比对应逻辑帧增加4字节。
- 正常接收解析以已建立的32位字对齐为前提。训练期间按第21章及第24章建立对齐;运行期按第25.5节保持当前字相位恢复帧边界,恢复失败后重新训练。本规范不规定器件内部的对齐实现方法。
### 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结论;只有完成CRC和适用协议检查后才形成有效候选及接受事件。序号、资源及业务交付由传输协议层决定。`PAYLOAD`内部业务含义不在本规范中规定。
## 13. `DATA`载荷的业务定义边界
`DATA`是本规范唯一带业务`SEQ`的业务帧。其`PAYLOAD`是传输协议层不透明的字节序列,可以承载普通数据、设备寄存器配置、寄存器回读、命令、响应或其他用户业务内容。
### 13.1 本规范规定的内容
`DATA`必须遵守第12章规定的外层帧格式、长度范围、字节序、`CRC32`和扰码规则。主端到从端方向的`DATA`使用第28章至第36章规定的可靠传输机制;从端到主端方向的`DATA`使用无确认传输机制。
数据链路层和传输协议层只处理`DATA_SOF`、`SEQ`、`LEN`、`PAYLOAD`的完整性以及接收资源,不解释`PAYLOAD`内部字段。
### 13.2 由用户业务定义的内容
基础传输机制不解释`PAYLOAD`内部字段,也不强制规定统一的`PAYLOAD`格式。未采用本规范可选业务应用配置时,通信双方自行约定以下内容:
- 操作码、命令类型或事务类型;
- 寄存器地址、寄存器宽度、读写方向及连续访问格式;
- 请求和响应的关联方式;
- 业务状态码、权限检查和执行结果;
- 业务数据的版本、子协议或应用级校验。
通信双方自行定义的业务格式不得改变`DATA`逻辑帧格式,不得引入新的线路`SOF`,也不得改变本规范规定的确认、窗口和重传语义。声明采用第39.3节Transaction应用配置时,必须遵守该节规定;未声明采用时,第39.3节不构成基础传输规范的强制要求。
### 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`中具有接收状态语义;主端发送的`POLL_REQ`使用相同布局,但两个字段没有确认或窗口含义。没有`ACK_VALID`字段。接收端须按下表选择适用检查:
| 控制类别 | 合法方向和状态 | 接收端字段检查与动作 |
|---|---|---|
| `POLL_REQ` | 主端→从端 | 检查CRC、`FLAGS`、方向及当前会话状态;忽略`ACK_NEXT`和`WIN_BYTES`的数值,不检查其范围或对齐,不更新UL序号或窗口 |
| 运行期`ACK/UPDATE` | 从端→主端,已初始化会话 | `WIN_BYTES`须4字节对齐;`ACK_NEXT`须通过第31.6节累计ACK检查 |
| 运行期`RETRY_REQ` | 从端→主端,已初始化会话 | 与状态ACK执行相同检查,再按第32.3节及第35章处理重传请求 |
| 初始`ACK/UPDATE` | 从端→处于`M_WAIT_STATUS`的主端 | `WIN_BYTES`须4字节对齐;绕过运行期ACK区间检查,以`ACK_NEXT`初始化新会话序号 |
主端发送POLL_REQ时按第31.2节将两个占位字段置0;从端不得以占位字段非零或不对齐拒绝CRC及其他适用检查均合法的POLL_REQ。CRC始终覆盖实际收到的全部`CTRL`字段。
从端状态`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`帧的重传不得重复占用窗口额度。`AVAILABLE_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`就自动生成回复;触发动作由第35章的传输协议控制逻辑决定。`CTRL`不得被解释为`TRAIN_ACK`或`SYNC_ACK`。
## 15. `CRC32`
### 15.1 参数与覆盖范围
本规范的`CRC32`由本章参数、输入位序、状态递推及结果封装共同定义。每帧使用固定初值,按逻辑帧字节顺序、每字节位0先行计算;32位CRC寄存器向高位方向左移,以最高位与当前输入位形成反馈。输出不反转,不执行最终异或。
| 参数 | 数值或规则 |
|---|---|
| `Width` | 32 |
| `Poly` | `32'h04C11DB7`,包含隐含的最高次项x^32 |
| `Init` | `32'hFFFFFFFF`,每个普通帧开始前重新加载 |
| `RefIn` | `true`;每字节按位0、位1、…、位7计算 |
| `RefOut` | `false`;直接取本章定义的左移CRC寄存器数值 |
| `XorOut` | `32'h00000000` |
| 寄存器移位与反馈 | 左移;反馈取更新前的CRC位31与当前输入位的异或 |
| `Check`:ASCII `123456789` | `32'h9B63D02C` |
覆盖范围:
- `DATA`:`SOF`、`SEQ`、`LEN`、`PAYLOAD`。
- `CTRL`:`SOF`、`ACK_NEXT`、`FLAGS`、`RESERVED`、`WIN_BYTES`。
- 不包含`CRC32`字段自身,不包含相邻`IDLE`或其他帧。
- 固定同步类帧与`IDLE`不使用CRC。
<a id="req-crc-001"></a>
### 15.2 输入顺序、状态递推与结果封装
关键要求编号:`REQ-CRC-001`。
CRC按逻辑帧字节顺序处理:先处理`SOF`的第一个线路字节,再依次处理协议字段和载荷。每个输入字节内部必须按位0、位1、…、位7进入CRC运算。对于按第9.1节排列的一个32位逻辑字,依次处理该字的位0至位31;下一个字必须使用处理完前一个字后的CRC状态。此顺序与原始逻辑数据的串行发送顺序及扰码输入顺序一致,但CRC计算使用加扰前的位。
每个输入位采用以下确定性状态更新,所有反馈均取更新前的值:
1. 将旧CRC寄存器的位31与当前输入位异或,得到1位反馈。
2. 将旧CRC寄存器左移1位,低位补0,仅保留32位。
3. 反馈为1时,将移位结果与`32'h04C11DB7`异或;反馈为0时,保持移位结果。这就是处理该输入位后的新CRC状态。
开始处理每帧第一个被覆盖位前,将CRC状态置为`32'hFFFFFFFF`。最后一个被覆盖数据位处理完成后,不追加额外的32个0,不反转寄存器内容,也不执行最终异或;此时的32位寄存器数值就是`CRC32`字段值。输入位0先行不改变本章规定的寄存器左移方向及最高位反馈位置。并行处理多个位的实现必须等价于按上述位序连续执行状态更新。
`CRC32`字段按第9.1节小端规则封装:低字节先发送,每个字节位0先发送;一个32位CRC字段即按数值位0至位31序列化。发送端对该字段继续执行当前帧的扰码,但不将CRC字段重新输入本帧CRC计算。
接收端使用实际收到的原始`SOF`及解扰后的协议字段和载荷,按相同位序、初值和递推规则计算CRC。将收到的CRC字段解扰并按小端序重组为32位数值后,直接与本地计算结果比较。接收端不把CRC字段继续送入CRC计算,不通过整帧余数判断通过;不得计算加扰后的数据,也不得把另一帧CRC状态带入本帧。
上述参数、输入位序、移位方向、反馈位置及结果封装均属于互操作要求。仅匹配CRC位宽和多项式不足以保证实现兼容。
### 15.3 CRC计算参考代码
以下两段Verilog代码均实现第15.2节定义,独立使用且互不调用。1-bit版本为串行输入、串行CRC输出模块,内部仍保存32-bit CRC状态;32-bit版本为输入32-bit逻辑字、返回32-bit更新状态的函数。1-bit/32-bit描述数据处理及输出宽度,不改变本规范CRC字段固定为32 bit的要求。
#### 15.3.1 1-bit输入与1-bit输出参考模块
该模块每次输入握手只计算1个数据位。最后一个被覆盖位计算完成后,下一周期开始串行输出最终CRC,共32个位,按位0至位31输出。输出CRC期间不接受下一帧数据;本模块不输出原始数据、不执行扰码,也不代表完整线路发送器。
```verilog
module crc32_serial (
input wire clk,
input wire rst_n,
input wire data_bit,
input wire data_valid,
input wire frame_start,
input wire data_last,
output wire data_ready,
output wire crc_bit,
output wire crc_valid,
output wire crc_last
);
localparam [31:0] POLY = 32'h04C11DB7;
reg [31:0] crc_state;
reg [31:0] crc_output;
reg [4:0] output_index;
reg output_active;
wire [31:0] crc_base;
wire feedback;
wire [31:0] crc_next;
assign data_ready = !output_active;
assign crc_base = frame_start ? 32'hFFFFFFFF : crc_state;
assign feedback = crc_base[31] ^ data_bit;
assign crc_next = {crc_base[30:0], 1'b0}
^ (feedback ? POLY : 32'h00000000);
assign crc_bit = crc_output[0];
assign crc_valid = output_active;
assign crc_last = output_active && (output_index == 5'd31);
always @(posedge clk) begin
if (!rst_n) begin
crc_state <= 32'hFFFFFFFF;
crc_output <= 32'h00000000;
output_index <= 5'd0;
output_active <= 1'b0;
end else if (output_active) begin
crc_output <= {1'b0, crc_output[31:1]};
if (output_index == 5'd31) begin
output_active <= 1'b0;
output_index <= 5'd0;
end else begin
output_index <= output_index + 5'd1;
end
end else if (data_valid && data_ready) begin
crc_state <= crc_next;
if (data_last) begin
crc_output <= crc_next;
output_index <= 5'd0;
output_active <= 1'b1;
end
end
end
endmodule
```
接口与调用规则:
- `rst_n`为同步低有效复位,复位用于初始化本参考模块;复位期间不得使用输出。
- 每帧第一个被覆盖位在`data_valid && data_ready`时输入,并同时置`frame_start=1`;其他位`frame_start=0`。模块先选取FFFFFFFF初值,再计算首位,不会丢弃首位。不得在帧中途重新置位frame_start。
- 最后一个被覆盖位在输入握手时置`data_last=1`。模块将包含该末位计算结果的`crc_next`装入输出寄存器,不能装入尚未处理末位的旧状态。
- `data_valid=0`时不更新CRC;`data_ready=0`时不接受输入,调用方须保持未被接受的数据及帧标记,直到完成握手。
- 输出没有反压:`crc_valid=1`期间每周期输出1 bit,共连续32周期;`crc_last=1`仅对应最后的位31。输出接收者必须逐周期接收,crc_valid=0时crc_bit无意义。
- 输出第31位的周期data_ready仍为0;该位被采样后的下一周期data_ready恢复为1,新帧首位可带frame_start立即输入。
- 输入是被CRC覆盖的原始逻辑比特,包括SOF及全部协议字段和载荷,字节内位0先行。CRC字段和IDLE不作为输入;串行CRC输出是加扰前的字段位,线路封装器仍须执行本规范的扰码。
该模块采用串行计算和串行输出分阶段方式,供计算规则及位序参考。产品实现的缓存、并行化和流水线须另行满足连续线路吞吐要求,不得把本示例的data_ready直接当作串行物理线路可以停顿的许可。
#### 15.3.2 独立32-bit参考函数
```verilog
function [31:0] calc_crc32;
input [31:0] data;
input [31:0] crc;
reg [31:0] new_crc;
reg feedback;
integer i;
localparam [31:0] POLY = 32'h04C11DB7;
begin
new_crc = crc;
for (i = 0; i < 32; i = i + 1) begin
feedback = new_crc[31] ^ data[i];
new_crc = new_crc << 1;
if (feedback)
new_crc = new_crc ^ POLY;
end
calc_crc32 = new_crc;
end
endfunction
```
每次调用计算一个完整32-bit逻辑字,输入数据按位0至位31进入计算;返回值作为下一字的CRC状态。本函数不调用1-bit模块或其他CRC函数。每帧首字使用FFFFFFFF初值,末字处理完成后的32-bit返回值直接作为最终CRC字段。
#### 15.3.3 两种实现的一致性与逐帧使用
对同一帧,以FFFFFFFF为初始状态,将逻辑数据按字序输入32-bit函数,或按相同字序、每字位0至位31输入1-bit模块,得到的最终CRC数值必须完全一致。串行模块输出的第k个位等于32-bit计算结果的位k,k=0…31。
一致性也适用于任意相同中间状态:一个32-bit字更新等价于按第15.2节执行32次逐位递推。串行模块的公开接口固定逐帧初始化,任意中间状态等价性可在验证环境内检查内部递推,不要求增加产品端口。
两个版本均不追加零位、不反转输出、不执行最终异或。发送计算使用加扰前逻辑数据;接收计算使用实际收到的原始SOF及解扰后的协议字段和载荷,最终与解扰后的CRC字段比较。帧间IDLE及CRC字段本身不参与计算。
普通逻辑帧长度均为4字节整数倍,因此32-bit函数无须补零。第15.1节9字节ASCII检查值可用1-bit模块输入实际72个位后取32位串行结果,不得填充额外字节。两段代码的参考端口仅说明计算方法,不替代第43~46章层间接口定义。
## 16. 扰码与解扰
<a id="req-scr-001"></a>
### 16.1 作用范围与初始化规则
关键要求编号:`REQ-SCR-001`。
本规范采用以下自同步递推多项式:
```text
G(x) = 1 + x^39 + x^58
```
扰码作用范围和初始化规则如下:
- `DATA`、`CTRL`:`SOF`原样发送,`SOF`后所有位,包括`CRC32`,参与扰码。
- 每个上述帧在`SOF`结束后、主体第一个位之前,将58位状态重新加载为全1。
- 一帧主体内连续推进状态,不得在头部、载荷或CRC边界复位。
- `SOF`、`IDLE`、五种固定同步类帧期间绕过扰码器,不推进状态。
- 扰码状态不得跨帧延续;实现不得使用跨帧连续保持历史状态的扰码器配置。
### 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
LINE["连续串行线路"]
subgraph RX["接收端"]
CLASSIFY["在可信边界识别SOF或IDLE"]
CLASSIFY -->|"DATA或CTRL"| DESCR["解扰并按长度接收"]
DESCR --> CRC_RX["校验CRC32"]
CRC_RX --> PARSER["输出候选帧及校验结果"]
CLASSIFY -->|"固定同步类帧或IDLE"| FIX_RX["完整码型比较"]
end
MUX_TX --> LINE
LINE --> CLASSIFY
```
如上图所示,发送端首先根据帧类型形成逻辑帧。对于`DATA`和`CTRL`,发送端按第15章规定的逐字节位0先行输入及左移反馈规则,对明文`SOF`、字段及载荷计算`CRC32`,原样发送`SOF`,并对`SOF`后面的字段、载荷和`CRC32`进行逐帧加扰;固定同步类帧和`IDLE`则绕过 CRC 与扰码路径,按固定码型直接发送。各路径最终汇合为连续、32位对齐的串行数据流。
接收端执行发送端的逆过程。在已知 32位字边界处识别原始`SOF`或`IDLE`:`DATA`和`CTRL`按对应结构解扰、计数接收并校验`CRC32`;固定同步类帧和`IDLE`直接进行完整码型比较。候选逻辑帧可按第43章在CRC结论形成前流式输出,协议层必须暂存并保留回滚能力。只有完整检查通过后才能产生有效候选事件;普通帧的序号、控制字段和资源检查由传输协议层执行,固定帧状态切换由数据链路层执行,具体业务动作由业务应用层执行。
### 17.1 发送封装
发送端根据帧类型选择业务帧路径或固定模式旁路。业务帧依次完成字段检查、逻辑帧构造、`CRC32`计算和主体加扰;固定同步类帧及`IDLE`直接输出既定码型。所有路径最终在完整帧边界处进行仲裁和串接。
#### 17.1.1 `DATA`
1. 上层提交`SEQ`、`LEN`和载荷,编码器检查结构约束;不合法的发送请求不得开始上线。
2. 在承诺能够连续供给整帧后开始发送。可以预缓存整帧,或使用有确定供给保证的流水线。
3. 原样发送`DATA_SOF`;同时按第 15.2 节规定的字节顺序和每字节位0先行顺序,将`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;传输协议层必须按第14.2节检查方向及适用字段;POLL_REQ占位字段按发送规则置0。数据链路层将所有字段的实际值纳入CRC,不执行窗口或确认点合理性判断。
#### 17.1.3 固定同步帧和`IDLE`
固定同步帧直接输出对应`SOF`和四个固定 PRBS 字;`IDLE`直接输出一个码字。两者都不经过 CRC 和业务扰码路径。
本节只规定固定同步类帧和`IDLE`的线路生成方式。固定同步类帧的发送种类、次数和时机由第四篇的链路训练与同步状态机决定;`DATA`和`CTRL`的发送调度及优先级由第35章规定。数据链路层只在完整帧边界选择下一帧;没有固定同步类帧或传输协议层逻辑帧需要发送时,持续发送`IDLE`。
### 17.2 接收解析
接收端先在已知 32位边界处完成帧类型识别,再依据帧类型进入业务帧解扰与校验路径,或进入固定模式比较路径。解析器只在完整帧检查通过后输出有效事件。
#### 17.2.1 边界分类
在已知帧边界读取一个 32位原始字:
- `IDLE`:精确匹配后报告 idle_seen,下一字仍是边界。
- 五种固定`SOF`:接收后续四个原始字并执行完整模式比较。
- `DATA`/`CTRL` `SOF`:记录类型;将原始`SOF`输入 CRC;初始化解扰器,再接收主体。
- 其他值:报告`boundary_error`。由数据链路层按第25.5节恢复帧边界。
#### 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`不满足第12.1节规定的范围或4字节对齐要求,解析器必须立即报告`length_error`并终止当前候选帧。不得使用该非法`LEN`确定剩余接收长度、CRC位置或下一帧边界,随后必须进入第17.4节规定的边界恢复状态。
通过范围和对齐检查的`LEN`只表示其结构合法,不表示该字段未发生传输错误。例如,原始`LEN`可能因误码变成另一个仍在合法范围内的数值。由于帧头没有独立CRC,接收端必须暂时按照收到的合法`LEN`确定候选帧长度,但在整帧CRC通过前不得提交载荷或产生协议动作。CRC失败后的边界处理按照第17.5节执行。
#### 17.2.3 `CTRL`
`SOF`后解扰三个 32位字。第一字包含`ACK_NEXT`、`FLAGS`和`RESERVED`,第二字为`WIN_BYTES`,第三字为 CRC。数据链路层输出解扰后的候选字段,并在末字周期报告CRC比较结果。传输协议层忽略`RESERVED`,按第14.2节执行方向及适用字段检查后才产生概念事件`ctrl_valid`;此前不得更新确认或窗口状态。POLL_REQ的`ACK_NEXT`和`WIN_BYTES`不得参与语义或对齐检查。
#### 17.2.4 固定帧
收到固定`SOF`后,依次比较四个固定 PRBS 字,全部正确才产生对应有效事件。任一位置错误均报告`fixed_pattern_error`,不把部分匹配当成有效控制请求。
#### 17.2.5 帧内标记与缓存提交
- 解析器进入`DATA`或`CTRL`帧体后,必须按照已经确定的帧长持续接收至预期CRC位置。在到达预期帧尾前,任何与`SOF`或`IDLE`相同的32位数值都属于当前帧内容,不得被识别为新的帧边界或帧类型标记。
- 所有有效动作必须发生在完整校验之后。允许内部暂存载荷,但不得提前进行不可撤销的业务输出或其他业务动作。
- 可使用整帧缓存,或具有提交/回滚能力的暂存 FIFO;具体结构由实现决定。
- `LEN`合法后,接收端必须使用32位字计数器确定当前帧的CRC位置和结束位置。`DATA`线路帧总长度为`3 + LEN/4`个32位字;识别`SOF`后还需接收`2 + LEN/4`个32位字。`CTRL`线路帧固定为4个32位字,识别`SOF`后还需接收3个32位字。本规范不使用EOF标记或接收超时来确定正常帧尾。
### 17.3 解析结果契约
本节名称表示概念事件,不强制具体 RTL 端口名称、脉冲宽度或握手接口。一个候选帧必须以一个成功结果或一个失败结果结束,不得同时报告成功和失败。
| 解析结果 | 产生条件 | 可交付内容 | 必须禁止的动作 | 边界状态 |
|---|---|---|---|---|
| idle_seen | 完整匹配`IDLE` | `IDLE`事件 | 不得更新业务、窗口或控制状态 | 保持可信 |
| `fixed_valid(type)` | 固定帧`SOF`和全部 128位 PRBS 完整匹配 | 固定帧类型 | 不得仅凭`SOF`提前产生事件 | 保持可信 |
| `data_candidate_valid` | `DATA`的长度、CRC 和格式全部合法 | `SEQ`、`LEN`、完整`PAYLOAD` | 解析器不得自行判断窗口、重复或交付顺序 | 保持可信 |
| `ctrl_valid` | `CTRL`的CRC及第14.2节适用于其方向和类型的检查通过;`RESERVED`及POLL_REQ占位数值被忽略 | `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`不满足第14.2节适用字段或方向规则;POLL_REQ占位字段不触发此错误 | 错误类型及仅供诊断的字段 | 不得产生对应候选有效事件;`RESERVED`的任何取值均不得触发此错误 | 丢弃当前帧并保持下一边界可信 |
| `boundary_error` | 在预期帧边界未识别任何合法`IDLE`或`SOF` | 接收字仅供诊断 | 不得将该字解释为载荷或控制动作 | 进入恢复 |
成功结果只证明线路格式和完整性满足本规范。`DATA`的外层`SEQ`是否在窗口内、是否重复以及是否允许提交,仍由传输协议层决定。`CTRL`的`ctrl_valid`可以交给窗口/重传逻辑处理;固定帧事件可以交给链路状态机处理。
### 17.4 错误后的解析行为与边界恢复
解析错误的处理规则以第25章为准:CRC失败但帧长合法时,回滚当前候选并按第17.5节检查暂定边界;`CTRL`格式错误时丢弃该`CTRL`,仍按固定长度定位下一边界;`LEN`非法或帧边界无法识别时,进入`MON_RECOVERY`。
若当前候选已经通过第43章接口开始输出,但无法正常输出末字及CRC结论,必须先产生`rx_frame_abort`;`link_up`同时撤销时由会话复位统一回滚。恢复保持已有32位字相位,在后续每个32位字位置搜索;一个合法`IDLE`或一个完整验证通过的候选帧即可恢复。成功的普通恢复候选允许进入传输协议检查,未知字及失败候选不得产生业务提交。完整算法、搜索上限和固定帧状态动作见第25.5节,不另设`BOUNDARY_SEARCH`状态或不同恢复判据。
### 17.5 CRC错误后的暂定边界规则
当`DATA`的`LEN`合法,或者当前帧是固定长度的`CTRL`时,接收端必须先按照已确定的帧长到达预期CRC位置,并把CRC之后的下一个32位位置作为**暂定边界**。CRC失败只说明当前帧内容不可接受,不单独证明字边界已经丢失。
在暂定边界处:
1. 如果识别到`IDLE`或任一合法`SOF`,边界恢复为可信;当前错误帧按方向规则回滚;
2. 如果既不能识别`IDLE`,也不能识别任何合法`SOF`,才报告`BOUNDARY_ERROR`并按第25.5节进入固定32位字相位的边界恢复;
3. 外层`LEN`本身非法时,无法可靠定位CRC,必须立即中止候选帧并进入边界恢复;
4. 进入恢复前不得在当前帧体内部把与`SOF`相同的数据误认为新帧起点。
这一规则取代“任意CRC失败立即进入边界恢复”的旧行为。
# 第四篇 链路训练、同步与运行期监测
## 18. 总体同步流程
每条链路独立执行以下顺序,必须先校准`UL`,再校准`DL`。上电和每一轮重新训练均执行完整流程;重新训练前先按第26.2.2节完成旧会话终止、可信在途帧排空及对端训练入口通知。主端在UL扫描期间持续请求发送DL `IDLE`,不发送DL `TRAIN`,从端在`S_TRAIN`中持续发送UL `TRAIN`。
```mermaid
sequenceDiagram
participant M as 主端
participant S as 从端
Note over M,S: 时钟、串行及延迟资源就绪;完成可信在途排空
M->>S: DL可发送时,完整发送20个SYNC_RESET
S-->>M: 持续TRAIN
Note over M: UL扫描期间DL持续请求发送IDLE
Note over M: 每个IDELAY最多检测200帧<br/>连续50个TRAIN正确则该点通过
loop 每个DL ODELAY测试点
Note over M: 设置ODELAY并等待当前配置就绪
M->>S: 持续TRAIN,单点最多200帧时间
Note over S: 连续50个TRAIN正确后开始定量应答
S-->>M: 固定完整发送50个TRAIN_ACK
Note over M: 连续10个TRAIN_ACK则该点通过
M->>S: 保持当前ODELAY,完整发送400个IDLE
Note over M: 忽略点间隔内全部TRAIN_ACK
S-->>M: 50个TRAIN_ACK发送结束后恢复TRAIN
Note over M: 400个IDLE完整结束后切换ODELAY<br/>不需要确认TRAIN
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后<br/>UL连续发送20个IDLE
S-->>M: 20个IDLE
Note over M: 检测到首个完整IDLE后进入M_RUN
```
设计原则:
1. 从端的时钟和串行资源有效后自动发送`TRAIN`,不等待控制命令;
2. 主端设置每个`IDELAY`后必须等待当前延迟配置就绪,再清除历史并开始该点测量;
3. 每个`IDELAY`点最多检测200个固定帧时间;连续正确检测50个`TRAIN`则该点通过,否则超时失败;
4. `UL`窗口中心装载且配置就绪后,主端扫描`DL` `ODELAY`;
5. 主端设置每个`ODELAY`后必须等待当前延迟配置就绪,再清除ACK历史并开始发送该点的`TRAIN`;
6. 每个`ODELAY`点持续发送`TRAIN`,单点最多200个固定帧时间;
7. 从端连续正确检测50个`TRAIN`后固定发送50个`TRAIN_ACK`;应答期间不累计下一轮`TRAIN`;
8. 第50个`TRAIN_ACK`完整发送结束后,从端清除ACK活动标志及`TRAIN`计数,恢复持续发送`TRAIN`;不等待`IDLE`,不设置ACK活动超时;
9. 主端连续正确检测10个`TRAIN_ACK`则该`ODELAY`点立即通过,不必继续发送满200个`TRAIN`;
10. 每个`ODELAY`点结束后,主端保持当前ODELAY完整发送固定400个`IDLE`并忽略全部测试应答,继续监测UL可信性;
11. 第400个`IDLE`完整结束后允许切换ODELAY,不要求收到`TRAIN`;实现须满足第22.3节最坏残留应答时序上界;
12. 主端得到两个方向的窗口中心后持续发送固定160位`SYNC`;
13. 从端连续正确检测10000个`SYNC`后,连续发送20个`SYNC_ACK`,随后持续发送固定160位`SYNC`;
14. 主端连续正确检测10个`SYNC_ACK`后,忽略可能剩余的`SYNC_ACK`,检测到第一个`UL` `SYNC`后开始连续计数;
15. 主端连续正确检测10000个`UL` `SYNC`后停止发送`SYNC`并持续发送`IDLE`;
16. 从端检测到首个完整合法的`DL IDLE`后停止发送`SYNC`,使接收方向进入运行期边界监测,并在`UL`连续发送20个`IDLE`;20个`IDLE`完整发送结束前不提交普通协议帧;
17. 主端检测到首个完整合法的`UL IDLE`后进入`M_RUN`并置位`link_up`;剩余`IDLE`按正常空闲码字处理;
18. 主端随后通过`POLL_REQ`确认控制帧通路并取得`WIN_BYTES`;只有新会话初始化完成后才允许业务发送接口接受新帧;
19. `SYNC`采用“持续发送、条件终止、超时失败”;不需要额外的“进入业务状态”控制帧。
步骤12至17的同步确认和运行入口均受对应超时保护:正常情况下由对端状态变化终止;超过规定时间仍未观察到终止条件,则放弃本轮训练结果,按第26.2.2节重新进入完整UL→DL训练流程。长序列由连续重复固定160位`SYNC`帧构成,不改变单帧长度。
固定帧时间为`160/LINE_RATE`。连续帧数量判据与线路速率无关,具体时间必须按所选物理配置换算。采用第7.3节的750 Mbps典型配置时,一个固定帧为213.333 ns;50帧约10.667 μs,200帧约42.667 μs,10000帧`SYNC`约2.133 ms/方向,20帧`SYNC_ACK`约4.267 μs。400个32位`IDLE`为12800 bit,约17.067 μs;20个32位`IDLE`为640 bit,约0.853 μs。
### 18.1 连续计数、超时与帧切换公共规则
“连续N个目标固定帧”表示在同一已确认接收边界上,相邻N个160位帧位置全部完整匹配目标固定帧。任一位置出现目标帧不匹配、其他固定帧、`IDLE`、普通协议帧、未知内容、接收数据无效或边界改变时,连续计数立即清零。
所有训练和确认计数器统一遵循以下规则:
1. 计数包含第一个有效观察单位;
2. 计数达到终值的同周期立即产生完成事件;
3. 通过条件和超时条件在同一观察单位成立时,通过条件优先;
4. 资源失效或当前方向被实现判定为不可信时,资源或方向异常优先于通过和超时;
5. 状态离开后清零该状态专用计数器;
6. 计数器达到终值后饱和或立即转换,不允许回卷。
当重新训练仍需使用某个可信方向传递`TRAIN`、`SYNC_RESET`或其他固定帧时,该方向必须保持完整线路帧原子性。已经开始发送的普通帧必须完整结束,随后从下一个帧边界开始发送训练固定帧。若物理资源已经失效而无法完整结束当前帧,可以立即中止,但该方向必须被判为不可信,不得依赖它完成可信帧排空或训练入口通知。重新训练范围不因方向可信与否而改变。
## 19. 主端顶层状态机
### 19.1 状态图
外部硬件复位不作为同步状态。RTL复位只初始化状态寄存器、计数器和临时扫描结果,主端顶层状态初始化为`M_WAIT_RESOURCE`。同步模块不产生全局复位请求。
```mermaid
stateDiagram-v2
[*] --> M_WAIT_RESOURCE: power_on
M_WAIT_RESOURCE --> M_RETRAIN_PREP: resources_ready
M_RETRAIN_PREP --> M_SYNC_RESET_TX: DL发送资源可发送完整固定帧
M_RETRAIN_PREP --> M_RX_TRAIN: DL不可用,依靠对端监测进入训练
M_SYNC_RESET_TX --> M_RX_TRAIN: 20个完整SYNC_RESET发送结束
M_RX_TRAIN --> M_TX_TRAIN: UL窗口合格且中心配置就绪
M_RX_TRAIN --> M_RX_TRAIN: UL扫描无合格窗口,重新扫描
M_TX_TRAIN --> M_DL_CONFIRM: DL窗口合格且中心配置就绪
M_TX_TRAIN --> M_RETRAIN_PREP: DL整轮扫描失败或UL失效
M_DL_CONFIRM --> M_UL_CONFIRM: 10个连续SYNC_ACK
M_DL_CONFIRM --> M_RETRAIN_PREP: 完整TRAIN、确认超时或同步异常
M_UL_CONFIRM --> M_RUN_ENTRY: 10000个连续UL SYNC
M_UL_CONFIRM --> M_RETRAIN_PREP: 完整TRAIN、确认超时或同步异常
M_RUN_ENTRY --> M_RUN: 首个完整UL IDLE
M_RUN_ENTRY --> M_RETRAIN_PREP: 完整TRAIN、入口超时或同步异常
M_RUN --> M_RETRAIN_PREP: 同步异常、完整TRAIN或主动重训请求
M_RETRAIN_PREP --> M_WAIT_RESOURCE: 公共资源不可用
M_RUN --> M_WAIT_RESOURCE: 公共资源失效
```
任一状态公共资源失效时均进入`M_WAIT_RESOURCE`;图中只画出部分公共转移。资源恢复后仍经过统一入口执行完整训练。任何状态下资源异常优先于普通通过和超时;通过与超时同周期时通过优先。
### 19.2 状态行为
| 状态 | 主要动作 | 离开条件 |
|---|---|---|
| `M_WAIT_RESOURCE` | 等待公共资源可用;保持`link_up=0` | 资源就绪后进入`M_RETRAIN_PREP` |
| `M_RETRAIN_PREP` | 撤销链路可用状态,终止旧会话,清除本轮训练上下文;若可信方向已有在途帧,先完整排空;禁止新普通帧 | 准备及排空完成后,DL发送资源可用则进入`M_SYNC_RESET_TX`,否则按第26.2.2节依靠对端监测并进入`M_RX_TRAIN` |
| `M_SYNC_RESET_TX` | 连续完整发送20个`SYNC_RESET`;不因收到TRAIN提前停止;不发送普通协议帧 | 20个完整发送结束后无条件进入`M_RX_TRAIN` |
| `M_RX_TRAIN` | DL持续请求发送IDLE;执行UL延迟扫描、窗口分析和中心点装载;只以TRAIN作UL测量目标 | UL合格后进入`M_TX_TRAIN`;整轮无合格窗口时重新执行完整UL扫描 |
| `M_TX_TRAIN` | 执行DL延迟扫描、每点400个IDLE隔离、窗口分析和中心点装载 | DL合格后进入`M_DL_CONFIRM`;整轮失败或UL失效时进入统一重训练入口 |
| `M_DL_CONFIRM` | DL持续发送SYNC,等待从端返回SYNC_ACK | 连续10个正确SYNC_ACK;失败时进入统一重训练入口 |
| `M_UL_CONFIRM` | DL继续持续发送SYNC;忽略残余SYNC_ACK,从首个UL SYNC开始连续计数 | 连续10000个正确SYNC;失败时进入统一重训练入口 |
| `M_RUN_ENTRY` | DL持续发送IDLE;允许残余UL SYNC,等待首个完整UL IDLE | 首个完整UL IDLE通过;失败时进入统一重训练入口 |
| `M_RUN` | 发送IDLE或普通协议帧;运行期监测 | 需要重训练时进入统一入口;公共资源失效则等待资源 |
### 19.3 主端的确定性要求
- 每一轮重新训练必须从`M_RX_TRAIN`开始重新校准UL,随后执行DL校准、双向同步确认和运行入口;不得利用旧延迟配置跳过任一阶段。
- 所有重训练触发先按`M_RETRAIN_PREP`及第26.2.2节处理对端训练入口和可信在途帧排空;DL可发送完整固定帧时,主端先完整发送20个SYNC_RESET,包括上电统一入口,不因从端已经发送TRAIN而提前结束。
- 主端在UL扫描期间只请求发送DL IDLE,不发送DL TRAIN,避免从端产生TRAIN_ACK干扰UL测量。旧固定帧事件不得带入新点统计;只有连续50个正确UL TRAIN才能使当前点通过。
- 每个接收或发送延迟配置必须就绪后才可开始测量;具体就绪判断仍由物理实现提供。
- 单个扫描点失败只记录该点并继续扫描,不启动新一轮训练。UL整轮扫描无合格窗口时从首点重新扫描UL;DL整轮扫描无合格窗口、UL失效或确认/运行入口失败时,经统一入口重新开始UL校准。
- `M_DL_CONFIRM`、`M_UL_CONFIRM`和`M_RUN_ENTRY`收到完整TRAIN时放弃当前轮次,经统一入口重新开始UL校准。`M_RX_TRAIN`中的TRAIN是正常测量数据,`M_TX_TRAIN`及点间隔中的TRAIN是正常从端训练流,不作为重复重训请求。
- SYNC_ACK只在`M_DL_CONFIRM`统计,连续10个正确帧通过;进入`M_UL_CONFIRM`后允许忽略剩余SYNC_ACK,从首个完整SYNC开始连续累计10000个。
- `M_RUN_ENTRY`在已知边界匹配首个完整UL IDLE后立即进入`M_RUN`。入口超时不再依据UL是否仍收到SYNC选择不同恢复范围,一律重新执行完整训练。
- `M_RUN`收到完整TRAIN时撤销`link_up`并进入统一训练入口;该事件可来自从端DL异常、从端协议故障或从端重新启动,不需要区分具体来源。
- 延迟点隔离仍固定发送400个完整IDLE,期间忽略测试应答;UL失效则退出DL扫描,重新开始完整流程。
- 任一训练状态失败不使状态机永久停止;训练重试计数仅用于诊断。全局资源不可用时等待恢复,不把资源异常当作普通失败点。
- 任一重新训练均终止整个旧协议会话;可信在途帧按第26.2.3节排空,已提交接收数据及已形成发送结果按原接口契约保留。
- 完整训练和运行入口完成后,通过初始POLL_REQ/ACK建立新会话,才允许接受新的业务发送请求。
## 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_ENTRY_IDLE_TX: first complete DL IDLE
S_RUN_ENTRY_IDLE_TX --> S_RUN: 20 UL IDLE sent
S_SYNC_ACK_TX --> S_TRAIN: DL sync lost, TRAIN, or SYNC_RESET
S_UL_SYNC_TX --> S_TRAIN: 10500 frame timeout, DL sync lost, TRAIN, or SYNC_RESET
S_RUN_ENTRY_IDLE_TX --> S_TRAIN: sync_lost, TRAIN, or SYNC_RESET
S_RUN_ENTRY_IDLE_TX --> S_WAIT_RESOURCE: common resource lost
S_RUN --> S_TRAIN: sync_lost, unexpected fixed frame, or SYNC_RESET
S_RUN --> S_WAIT_RESOURCE: common resource lost
S_RUN --> S_TRAIN: 本地协议故障请求 / 排空可信在途帧后发送TRAIN
S_TRAIN --> S_TRAIN: SYNC_RESET / clear training history
```
### 20.2 状态行为
| 状态 | `DL`接收行为 | `UL`发送行为 | 离开条件 |
|---|---|---|---|
| `S_WAIT_RESOURCE` | 清空固定帧检测历史,禁止普通帧提交 | 等待资源稳定 | 资源就绪 |
| `S_TRAIN` | 分别累计连续`TRAIN`和连续`SYNC`;`TRAIN`达到50后固定发送50个`TRAIN_ACK`;应答期间不累计`TRAIN` | 默认连续`TRAIN`;应答结束清零计数并恢复`TRAIN` | 连续收到10000个有效`SYNC` |
| `S_SYNC_ACK_TX` | 继续检查`DL`是否保持`SYNC` | 连续发送20个`SYNC_ACK` | 20个完整发送结束;收到完整`TRAIN`或`SYNC_RESET`;或DL边界/资源失效 |
| `S_UL_SYNC_TX` | 继续接收主端`SYNC`,检测首个完整合法`IDLE`;从进入本状态起累计固定帧时间 | 持续发送`SYNC` | 收到首个完整运行入口`IDLE`;收到完整`TRAIN`或`SYNC_RESET`;达到10500个固定帧时间;或DL边界/资源失效 |
| `S_RUN_ENTRY_IDLE_TX` | 启用运行期边界监测但不向传输协议层提交普通帧;保持`link_up=0` | 连续发送20个`IDLE`,不得插入其他帧 | 完整发送20个`IDLE`后进入`S_RUN`并置位`link_up`;同步丢失;收到训练固定帧;或公共资源失效 |
| `S_RUN` | 解析普通帧并监测同步;处理固定帧状态事件 | 优先发送待响应`CTRL`;无帧时发送`IDLE` | 失步、资源失效、`SYNC_RESET`或意外固定帧 |
<a id="req-trn-001"></a>
从端因DL异常、本地协议故障或完整SYNC_RESET进入`S_TRAIN`时,均撤销`link_up`并终止旧会话。可信UL已开始的帧必须先排空,随后持续发送TRAIN;不再输出人为异常码流,也不等待主端先宣告UL失步。状态可先进入`S_TRAIN`,但TRAIN发送必须等待可信排空结束;资源不可用时等待资源。该公共入口规则也适用于训练、确认和运行入口状态中的重新训练事件。
### 20.3 `TRAIN_ACK`调度
关键要求编号:`REQ-TRN-001`。
从端在`S_TRAIN`中维护`TRAIN`连续计数、`train_ack_active`及`TRAIN_ACK`发送计数:
1. 默认在UL持续发送`TRAIN`。每完整接收一个正确DL `TRAIN`,连续计数加一;任一预期`TRAIN`不匹配使连续计数清零。
2. 连续计数达到50时,锁存`train_ack_active=1`。已经开始的UL `TRAIN`须完整结束,随后连续发送固定50个`TRAIN_ACK`。
3. 每个`TRAIN_ACK`完整发送结束才计数;第50个完整结束后立即清除活动标志和`TRAIN`连续计数,并从下一完整帧恢复持续发送`TRAIN`。
4. `TRAIN_ACK`发送期间不累计下一轮`TRAIN`;`IDLE`及后续`TRAIN`检测错误均不提前缩短本批50帧,不延长或重新启动本批应答。恢复`TRAIN`后从零重新累计,上一批计数不得沿用。
5. 进入同步确认状态时清除`TRAIN`相关计数;完整`SYNC_RESET`、同步异常或资源失效按第18.1节优先级处理。资源仍可用的可信发送方向须完整结束当前帧后切换;无法完成时将该方向判为不可信。
从端不需要知道ODELAY档位或主端测试点编号。固定50帧应答取代等待`IDLE`结束应答,不再设置ACK活动超时保护。主端按第22.3节固定发送400个`IDLE`隔离相邻测试点。
### 20.4 从端进入运行期
从端连续正确检测10000个`DL SYNC`后进入`S_SYNC_ACK_TX`,连续发送20个`SYNC_ACK`;随后进入`S_UL_SYNC_TX`并持续发送`SYNC`。主端确认10000个`UL SYNC`后停止发送`SYNC`并持续发送`DL IDLE`。
从端进入`S_UL_SYNC_TX`时启动`S_UL_SYNC_TIMEOUT_FRAMES`计时。该计时按160位固定帧时间累计,固定为10500;在计满前收到首个完整合法`DL IDLE`即正常结束。计满仍未收到`DL IDLE`,或者等待期间收到完整`TRAIN`或`SYNC_RESET`、DL边界失效或公共资源失效,均放弃本次确认并返回`S_TRAIN`。通过条件和超时在同一观察单位成立时,按第18.1节由通过条件优先。
从端在已知边界检测到首个完整合法`DL IDLE`后,使DL接收方向采用运行期边界监测规则并进入`S_RUN_ENTRY_IDLE_TX`,但保持本端`link_up=0`。已经开始发送的`UL SYNC`必须完整结束;随后从端连续发送20个32位`IDLE`。第20个`IDLE`完整发送结束后,从端进入`S_RUN`并置位本端`link_up`。这20个`IDLE`是运行入口响应,不用于重新验证链路质量。
从端发送20个`IDLE`期间不得向传输协议层提交普通`DATA`或`CTRL`;期间收到的`POLL_REQ`不锁存、不响应。主端如果尚未收到初始状态响应,必须按`T_POLL_INTERVAL`重新发送`POLL_REQ`。业务应用层的UL发送请求在运行入口序列完成前不得上线。该状态不设置普通流程超时,状态转换以完整发送20个`IDLE`为准;同步丢失、收到训练固定帧或`SYNC_RESET`时返回`S_TRAIN`,公共资源失效时进入`S_WAIT_RESOURCE`。
从端在`S_SYNC_ACK_TX`中必须完整发送20个`SYNC_ACK`,该状态不设置普通流程超时;若收到完整`TRAIN`或`SYNC_RESET`,或者DL边界或公共资源失效,则立即放弃本次确认并返回训练入口。进入`S_UL_SYNC_TX`后,若收到完整`TRAIN`或`SYNC_RESET`、DL边界或公共资源失效,或者达到10500个固定帧时间仍未收到完整合法`DL IDLE`,则放弃本次确认并返回训练入口。
## 21. 主端`UL` `IDELAY`扫描子状态机
### 21.1 目标
`UL`扫描在从端连续发送`TRAIN`时执行。主端改变对应接收链路的`IDELAY`,在每个延迟点搜索字边界并统计完整`TRAIN`匹配结果,得到采样通过窗口。
### 21.2 状态图与子状态
```mermaid
stateDiagram-v2
[*] --> RX_SET_DELAY
RX_SET_DELAY --> RX_WAIT_DELAY_READY: delay request accepted
RX_WAIT_DELAY_READY --> RX_CLEAR_HISTORY: rx_delay_ready
RX_CLEAR_HISTORY --> RX_SEARCH_AND_QUALIFY: start 200-frame timer
RX_SEARCH_AND_QUALIFY --> RX_RECORD: 50 consecutive TRAIN, pass
RX_SEARCH_AND_QUALIFY --> RX_RECORD: 200-frame timeout or point failure
RX_RECORD --> RX_NEXT_POINT: result recorded
RX_NEXT_POINT --> RX_SET_DELAY: more delay points
RX_NEXT_POINT --> RX_ANALYZE_WINDOW: scan complete
RX_ANALYZE_WINDOW --> RX_LOAD_CENTER: valid window found
RX_ANALYZE_WINDOW --> RX_SET_DELAY: no valid window, restart scan
RX_LOAD_CENTER --> [*]: center ready and boundary rebuilt
```
图中的结束节点表示`UL`扫描成功,控制权返回主端顶层状态机并进入`M_TX_TRAIN`。任一子状态下公共资源失效时,立即中止扫描并进入`M_WAIT_RESOURCE`;该全局异常转移未逐条画出。尚未记录的当前点不得写入扫描位图,已有扫描结果在重新训练时失效。
| 子状态 | 动作 | 转移条件 |
|---|---|---|
| `RX_SET_DELAY` | 请求设置当前`IDELAY`延迟档位 | 设置请求已被物理接口适配逻辑接受 |
| `RX_WAIT_DELAY_READY` | 等待当前延迟配置生效且接收路径可用于测量 | `rx_delay_ready=1` |
| `RX_CLEAR_HISTORY` | 清零比较历史、字对齐历史和当前点统计 | 下一拍启动200帧单点总计时 |
| `RX_SEARCH_AND_QUALIFY` | 在实现支持的全部接收对齐候选位置和32位字边界中持续搜索完整`TRAIN`,并在当前候选边界维护连续正确计数和200帧单点总计时 | 任一候选边界连续正确50个`TRAIN`,或达到200个固定帧时间 |
| `RX_RECORD` | 按第21.3节记录通过、失败和错误数 | 下一拍 |
| `RX_NEXT_POINT` | 选择下一个延迟档位 | 仍有测试点则继续,否则分析 |
| `RX_ANALYZE_WINDOW` | 找最长连续通过区间并选择中心 | 有合法窗口或失败 |
| `RX_LOAD_CENTER` | 请求装载中心延迟档位,等待`rx_delay_ready`并重新建立字边界 | 完成后进入`DL`扫描 |
`rx_delay_ready`是抽象就绪条件,表示当前请求的`IDELAY`配置已经生效且接收路径可以开始有效测量。本规范不规定它由器件状态信号、固定等待周期、配置回读还是其他机制产生。设置请求未被接受或就绪条件长期无效时,状态机可以保持在`RX_SET_DELAY`、`RX_WAIT_DELAY_READY`或`RX_LOAD_CENTER`,本规范不要求统一超时;挂起期间必须保持`link_up=0`和`session_ready=0`,不得启动200帧单点计时、搜索候选边界、累计`TRAIN`、更新扫描位图或发送普通协议帧。资源全局就绪状态撤销时进入`M_WAIT_RESOURCE`,不得把该事件记录为普通失败点。
### 21.3 测试点判定
`IDELAY`用于调整串行数据的采样相位,接收对齐搜索用于建立并行字及32位协议字的分组边界,两者属于相互独立的搜索维度。每个`IDELAY`测试点都必须清除旧边界历史,并在该点的200帧总计时内重新完成边界搜索和连续`TRAIN`判定。接收对齐候选位置的形成和切换方法属于物理接口适配实现,本规范不作限定。
每个`IDELAY`点的确定判据为:
- 请求改变`IDELAY`并确认`rx_delay_ready`后,清零该点的`TRAIN`连续计数、单点总计时、接收对齐搜索历史和旧边界历史;
- 历史清除完成后立即启动200个固定帧时间的单点总计时;边界搜索和连续`TRAIN`判定共用该计时,不另设边界搜索超时;
- 计时期间持续遍历实现支持的全部接收对齐候选位置和32位字边界候选位置;实现必须保证在200个固定帧时间内能够覆盖全部可能位置;
- 在某一候选位置完整匹配一个160位`TRAIN`时,将该位置作为当前候选边界并把连续计数置1;后续在同一候选边界每完整匹配一个`TRAIN`,连续计数加一;
- 当前候选边界上的预期`TRAIN`不匹配时,连续计数清零并继续执行边界搜索;旧候选不得阻止其他候选位置被检查;
- 任一候选边界的连续计数达到50时,该点立即判定通过,并将该边界作为当前点的有效接收边界;
- 单点总计时达到200个固定帧时间仍未出现连续50个正确`TRAIN`时,该点判定失败;
- 搜索和判定期间,如果实现报告当前接收边界或连续数据已经不可信,则清除当前候选历史并继续搜索;接收资源不可用时按下一段规定处理中止扫描。
公共资源失效不作为普通失败点记录,而是立即中止本轮扫描并使主端进入`M_WAIT_RESOURCE`。资源恢复后重新执行完整`UL`扫描。
50帧判据用于窗口扫描,不作为链路BER证明。最终选择的窗口中心还要通过双向各10000个连续`SYNC`完成同步确认。
## 22. 主端`DL` `ODELAY`扫描子状态机
### 22.1 目标
UL校准完成后,主端在每个ODELAY点最多发送200个固定帧时间的`TRAIN`;连续正确收到10个`TRAIN_ACK`即判定该点通过。从端每次检测通过只发送固定50个`TRAIN_ACK`。主端在每个测试点结束后保持当前ODELAY,完整发送固定400个`IDLE`并忽略应答,随后切换延迟;不以收到`TRAIN`为切换条件。
### 22.2 状态图与子状态
```mermaid
stateDiagram-v2
[*] --> TX_SET_DELAY
TX_SET_DELAY --> TX_WAIT_DELAY_READY: delay request accepted
TX_WAIT_DELAY_READY --> TX_CLEAR_ACK_COUNT: tx_delay_ready
TX_CLEAR_ACK_COUNT --> TX_SEND_TRAIN: ACK history cleared
TX_SEND_TRAIN --> TX_RECORD: 10 consecutive TRAIN_ACK
TX_SEND_TRAIN --> TX_RECORD: 200 frame timeout or point failure
TX_RECORD --> TX_POINT_GAP: result recorded
TX_POINT_GAP --> TX_NEXT_POINT: 400 complete IDLE sent
TX_POINT_GAP --> TX_TO_RX_TRAIN: UL no longer reliable
TX_NEXT_POINT --> TX_SET_DELAY: more delay points
TX_NEXT_POINT --> TX_ANALYZE_WINDOW: scan complete
TX_ANALYZE_WINDOW --> TX_LOAD_CENTER: valid window found
TX_ANALYZE_WINDOW --> TX_TO_RX_TRAIN: no valid window, restart full training
TX_LOAD_CENTER --> [*]: tx_delay_ready
state "统一入口后重新校准UL" as TX_TO_RX_TRAIN
```
图中的结束节点表示`DL`扫描成功,控制权返回主端顶层状态机并进入`M_DL_CONFIRM`。`TX_TO_RX_TRAIN`表示UL失效或本轮DL扫描无合格窗口,必须退出本子状态机,经`M_RETRAIN_PREP`及必要的SYNC_RESET发送后重新训练UL和DL;不得直接重新扫描DL。任一子状态下公共资源失效时,立即中止扫描并进入`M_WAIT_RESOURCE`;该全局异常转移未逐条画出。
| 子状态 | 动作 | 转移条件 |
|---|---|---|
| `TX_SET_DELAY` | 请求设置当前`ODELAY`延迟档位 | 设置请求已被物理接口适配逻辑接受 |
| `TX_WAIT_DELAY_READY` | 等待当前延迟配置生效且发送路径可用于测量 | `tx_delay_ready=1` |
| `TX_CLEAR_ACK_COUNT` | 清除当前点ACK计数和旧固定帧事件 | 下一拍 |
| `TX_SEND_TRAIN` | 持续发送`TRAIN`,维护ACK连续计数和200帧单点计时 | 连续10个ACK,或单点超时 |
| `TX_RECORD` | 按第22.3节记录通过或失败 | 下一拍 |
| `TX_POINT_GAP` | 保持当前ODELAY完整发送400个`IDLE`;忽略`TRAIN_ACK`和`TRAIN`测量事件,继续监测UL可信性 | 第400个`IDLE`完整结束;UL失效时退出扫描 |
| `TX_NEXT_POINT` | 选择下一个延迟档位 | 仍有点则继续,否则分析 |
| `TX_ANALYZE_WINDOW` | 找最长连续通过区间并选择中心 | 有合格窗口则装载中心;否则退出子状态机,经统一入口重新校准UL |
| `TX_LOAD_CENTER` | 请求装载中心延迟档位并等待`tx_delay_ready` | 就绪后进入双向`SYNC`确认 |
`tx_delay_ready`是抽象就绪条件,表示当前请求的`ODELAY`配置已经生效且发送路径可以开始有效测量。本规范不规定它由器件状态信号、固定等待周期、配置回读还是其他机制产生。设置请求未被接受或就绪条件长期无效时,状态机可以保持在`TX_SET_DELAY`、`TX_WAIT_DELAY_READY`或`TX_LOAD_CENTER`,本规范不要求统一超时;挂起期间必须保持`link_up=0`和`session_ready=0`,不得记录扫描结果或发送普通协议帧。延迟切换期间的线路输出不参与任何测试点判定;只有`tx_delay_ready=1`后才能清除旧ACK历史并开始新的`TRAIN`序列和200帧计时。资源全局就绪状态撤销时进入`M_WAIT_RESOURCE`。
<a id="req-trn-002"></a>
### 22.3 测试点判定与应答归属
关键要求编号:`REQ-TRN-002`。
每个ODELAY点采用以下判据:
1. 设置延迟并确认`tx_delay_ready`后,清除旧ACK历史,从第一个完整`TRAIN`开始累计200个固定帧时间。
2. 从端连续正确检测50个`TRAIN`后,按第20.3节固定完整发送50个`TRAIN_ACK`。
3. 主端在当前测试点连续完整匹配10个`TRAIN_ACK`时立即判定通过;任一预期ACK不匹配或非ACK内容使连续计数清零。达到200个固定帧时间仍未通过则该点失败;通过与超时同周期时通过优先。
4. 测试点结束后完整发送完当前`TRAIN`,保持当前ODELAY不变,连续发送固定`TX_POINT_GAP_IDLE_WORDS=400`个`IDLE`。仅完整发送的`IDLE`参与计数,不允许提前结束。
5. 400个`IDLE`期间忽略全部`TRAIN_ACK`及`TRAIN`测试事件,不要求收到`TRAIN`,不以`IDLE`是否被从端正确接收作为完成条件。第400个`IDLE`结束后才选择下一延迟点或分析窗口。
6. 请求切换或装载中心延迟时继续请求发送`IDLE`;切换期间的线路输出不参与测试判定。只有配置就绪后才能清除ACK历史,发送下一点`TRAIN`或进入`SYNC`确认。
7. UL失去可信接收时立即退出DL扫描,经统一训练入口重新校准UL和DL;公共资源失效进入资源等待。未收到`TRAIN`本身不构成点间隔故障。
该隔离方式必须满足下式,时间从主端最后一个`TRAIN`完整发送结束开始计算:
```text
400 × 32 / LINE_RATE >= 50 × 160 / LINE_RATE + T_ACK_TAIL_BOUND
```
`T_ACK_TAIL_BOUND`是实现声明的最坏附加延迟上界,至少包含最后一个DL `TRAIN`传播、从端检测处理、等待UL完整帧边界、UL传播、主端接收处理及裕量。从端在末批`TRAIN`到达后可能才完成检测,因此不得只从主端收到第10个ACK开始估算残留应答。
400个`IDLE`等于80个固定帧时间,允许上述附加延迟不超过30个固定帧时间。750 Mbps典型配置下,保护时间为17.067 μs,50个`TRAIN_ACK`为10.667 μs,附加延迟预算为6.400 μs。所有物理配置均须证明满足该上界;不能满足时,不符合本规范固定400个`IDLE`的训练配置,不得自行省略保护或将迟到ACK计入下一测试点。
## 23. 通过窗口与中心点选择
### 23.1 扫描位图
每个扫描点产生一个 `pass[i]`。主端:
1. 若全部扫描点均通过,按第23.2节的`ALL_PASS`规则处理,不执行基于失败边界的中心点计算;
2. 否则按照实现配置采用环形或线性窗口算法找出全部连续通过区间;环形算法必须先合并跨越最小和最大延迟档位的同一窗口;
3. 选择长度最大的区间;
4. 多个区间等长时,选择最接近标称延迟档位的区间;
5. 仍相同时选择延迟档位编号较小的区间;
6. 偶数点窗口有两个中心点时,选择更接近标称延迟档位者,仍相同则取较小延迟档位;
7. 装载所选点;`UL`所选点随后用于接收`TRAIN_ACK`和`UL` `SYNC`,`DL`所选点随后用于发送`TRAIN`和`DL` `SYNC`。
### 23.2 最小窗口判据
有效窗口必须同时满足:
- 对于`UL`窗口,连续通过点数不小于派生值`RX_MIN_PASS_TAPS`;对于`DL`窗口,连续通过点数不小于派生值`TX_MIN_PASS_TAPS`;
- 按实际延迟值换算的首尾通过采样点时间跨度不小于派生值`MIN_PASS_WINDOW_TIME`;
- 除`ALL_PASS`外,所选中心点到左右失败边界均留有实现配置规定的余量;
- 采用线性窗口算法时,窗口未在扫描范围边界被截断;采用环形窗口算法时,跨越最小和最大延迟档位的通过段已正确合并。
延迟扫描的实际有效范围必须覆盖至少一个完整UI。只有实现提供按模UI排列的一周相位候选、全部相邻间隔及首尾相邻间隔均已确定时,才允许采用环形窗口算法并合并跨数组边界的通过区间。实际扫描范围大于1 UI本身不证明首尾相邻;通过区间触及扫描边界本身不表示校准不完整。若采用线性窗口算法,则必须通过调整粗相位把完整窗口移入线性扫描范围;只有在线性扫描未观察到通过窗口两侧边界,或者实际有效扫描范围小于1 UI时,才需要调整粗相位、扩大扫描范围或判定校准不完整。
若全部扫描点均通过,则将该方向的扫描结果记录为`ALL_PASS`。`ALL_PASS`不表示扫描范围不足,但由于没有观察到失败边界,不能根据本次扫描推断真实眼图中心。实现必须按照实现配置选择确定的标称延迟点,继续执行双向10000帧`SYNC`确认,并通过时序预算证明所选点具有足够裕量;如果实现要求根据实测边界选择中心,则必须提高扫描分辨率或采用其他边界测量方法。
`MIN_PASS_WINDOW_RATIO`是由设备设计者在RTL集成前根据抖动、建立保持时间、PVT漂移和目标时序裕量确定的实现配置值,不属于运行期可任意修改的参数。建议基线为:
\[
MIN\_PASS\_WINDOW\_RATIO = 0.4
\]
该建议值是工程起点,不替代正式时序预算。最小窗口时间必须根据实际线路速率派生:
\[
UI=\frac{1}{LINE\_RATE}
\]
\[
MIN\_PASS\_WINDOW\_TIME=MIN\_PASS\_WINDOW\_RATIO\times UI
\]
`MIN_PASS_WINDOW_TIME`不得作为与比例无关的第二个配置值。若扫描步进均匀,连续通过点数要求分别派生为:
\[
RX\_MIN\_PASS\_TAPS=\left\lceil\frac{MIN\_PASS\_WINDOW\_TIME}{RX\_DELAY\_STEP\_TIME}\right\rceil+1
\]
\[
TX\_MIN\_PASS\_TAPS=\left\lceil\frac{MIN\_PASS\_WINDOW\_TIME}{TX\_DELAY\_STEP\_TIME}\right\rceil+1
\]
加1是因为连续通过`N`个等间隔采样点时,首尾采样点之间只有`N-1`个延迟间隔。若延迟步进不均匀,必须使用物理实现提供的实际延迟映射计算首尾通过点的时间跨度;上述等步进公式仅用于得到保守的点数下限。
### 23.3 跨延迟档位回卷
窗口分析须在实现配置中明确选择线性或环形方式。线性方式不连接首尾档位,并通过粗相位调整确定完整窗口及裕量;环形方式必须先将候选整理为按模UI排序的一周相位序列,声明实际相位映射、所有相邻间隔及首尾间隔,再合并跨边界通过区间。两种方式均须覆盖完整UI;无需要求所有物理延迟资源的原始首尾档位相邻。非均匀扫描和跨边界窗口须按展开后的实际相位间隔计算时间跨度,不得直接减原始首尾延迟值。
## 24. 帧边界建立与正常解析
### 24.1 固定帧搜索
训练期可以在实现支持的接收对齐候选位置搜索固定帧,但产生固定帧事件前必须完成160位全帧比较。候选位置的形成和切换方法属于物理接口适配实现,本规范不作限定。
- 初始字边界至少需要 `ALIGN_CONFIRM_FRAMES` 个连续完整固定帧;
- 任一候选帧不匹配使连续计数清零;
- 锁定后仅在确定的 32位边界检查`SOF`/`IDLE`;
- 进入普通帧后,直到该帧声明的结束位置都不得在载荷内重新搜索`SOF`。
`ALIGN_CONFIRM_FRAMES`用于确认固定帧候选边界,不增加训练通过门限。在同一延迟点、同一候选边界上,首个正确完整TRAIN计为第1个;用于边界确认的连续TRAIN也计入该点连续50个TRAIN的训练判定。边界确认后不得将这段计数清零再要求额外50帧。候选边界改变或连续性被破坏时,相关计数必须重新开始;200个固定帧时间的点测量上限仍覆盖整个搜索和验证过程。
### 24.2 普通帧正常解析条件
1. 在已知 32位边界匹配`DATA`或`CTRL` `SOF`;
2. 外层长度字段编码完整;
3. 长度满足协议规定的最小值、最大值和 4-字节对齐;
4. 按长度计数恰好到达 CRC 和帧结束位置;
5. 接收期间资源保持可用,且当前接收边界未被实现判定为不可信。
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_invalid
MON_RECOVERY --> MON_LOCKED_BOUNDARY: recovery_confirmed / resume at next boundary
MON_RECOVERY --> MON_SYNC_LOST: search_limit_reached / deassert link_up
MON_LOCKED_BOUNDARY --> MON_SYNC_LOST: receive resource unavailable
MON_IN_FRAME --> MON_SYNC_LOST: receive resource unavailable
```
### 25.2 边界状态定义
运行期边界分为三种可信度:
| 边界状态 | 含义 | 允许的动作 |
|---|---|---|
| 可信边界 | 当前32位位置已由`IDLE`、完整固定帧或上一完整帧长度确定 | 可以识别`IDLE`、`SOF`并开始新帧 |
| 暂定边界 | 位置由一个长度合法但CRC失败的帧推算得到,尚未由下一标志确认 | 只能检查下一`IDLE`或`SOF`,不得提交前一帧 |
| 边界丢失 | 无法确定下一个32位帧起点,或当前接收对齐位置不再可信 | 禁止业务提交,进入边界恢复 |
`MON_LOCKED_BOUNDARY` 内部应使用 `boundary_provisional` 标志区分可信边界和暂定边界。CRC失败且长度合法时置位该标志;下一位置匹配合法`IDLE`或`SOF`后清零;匹配失败则进入 `MON_RECOVERY`。暂定状态最多维持到下一预期边界,不允许跨越多个未确认帧。
边界确定必须遵循以下优先级:
1. 接收资源不可用时,当前数据和边界均不可信,必须撤销`link_up`并进入资源恢复或重新训练;
2. 实现明确报告当前接收边界不再可信时,必须丢弃当前未完成帧,对已输出但未完成的候选按第43章产生`rx_frame_abort`,清除解析历史并进入`MON_RECOVERY`;
3. 已经进入普通帧且未发生上述事件时,只能根据该帧已经通过范围和对齐检查的长度计算结束位置;
4. 仅在预期帧边界上识别`IDLE`和`SOF`;
5. `SOF`单独匹配只能建立候选起点,不能证明完整帧有效;
6. 固定训练类帧必须完整匹配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位字 | 原边界与线路内容不一致 | 无法计算下一边界 | 立即进入恢复 |
| 实现明确报告当前接收边界或连续数据不再可信 | 原有32位边界不再可信 | 不沿用任何旧长度或边界历史 | 对已输出未完成候选产生`rx_frame_abort`并回滚,清除解析历史后恢复 |
| 接收资源不可用 | 当前接收数据不可信 | 不执行边界搜索 | 立即撤销`link_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. 数据链路层暂存逻辑帧最后一个字;收到并比较随后的CRC字后,在输出该逻辑末字时同时置位`rx_data_last`、`rx_crc_valid`和`rx_crc_pass`;
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`造成的逻辑失步发现延迟有确定上界。接收资源可用状态和实现内部的边界有效性状态在帧内仍持续监测,不受帧长影响。
<a id="req-rcv-001"></a>
### 25.5 边界恢复搜索
关键要求编号:`REQ-RCV-001`。
进入`MON_RECOVERY`时清除失效候选的类型、剩余长度、CRC、解扰及匹配历史。若该候选已经向协议层开始输出、但不能形成正常末字及CRC结论,先产生一次`rx_frame_abort`;没有已输出候选时不产生abort。进入恢复本身不撤销`link_up`,不终止当前会话。
恢复保持已经建立的32位字相位,逐个完整32位字检测原始`IDLE`或`SOF`,不执行逐比特滑动对齐,也不切换底层接收对齐候选。未知字不输出给协议层。命中`SOF`后只建立候选,按以下条件判断:
| 候选 | 恢复条件及处理 |
|---|---|
| `IDLE` | 完整匹配1个合法`IDLE`,恢复可信边界 |
| 固定帧 | 完整匹配160位,并执行第25.6节及当前同步状态规定的动作;需要重新训练时不得保持运行状态 |
| `DATA` | `SOF`合法、`LEN`合法、整帧CRC正确;恢复后由协议层按方向检查序号和资源,再决定协议提交或丢弃 |
| `CTRL` | `SOF`合法、固定长度完整、CRC正确即可恢复线路边界;协议层仍按第14.2节执行方向和适用字段检查,非法`CTRL`不产生控制动作 |
普通恢复候选允许按第43章接口提前输出解扰后的候选流,由协议层暂存;只有末字及CRC结论形成后才允许协议检查和提交。CRC失败的候选回滚,`LEN`非法或无法完整完成的候选产生abort,随后继续搜索。候选不合法时不得产生业务副作用。CRC与结构验证通过的普通候选不再一律丢弃,也不需要先匹配下一帧标志才允许处理该候选。
恢复成功时,候选结束后的下一32位位置重新作为期望边界,按正常规则检测`IDLE`或`SOF`。不得吞掉下一帧`SOF`。搜索期间取得的完整候选仍须纳入第25.7节适用的CRC质量统计。
`RECOVERY_SEARCH_LIMIT_WORDS`从进入恢复并清除历史后的第一个32位字时间开始计数,包含候选验证时间;不得小于`2 × MAX_LINE_FRAME_WORDS`,当前基础下限为522个字时间。恢复与上限同周期成立时恢复优先。达到上限仍无法恢复,或实现已确认当前32位字相位失效时,撤销`link_up`并按第26章重新训练;字对齐重新建立由训练过程完成。
### 25.6 角色相关固定帧处理
| 接收端状态 | 完整固定帧 | 动作 |
|---|---|---|
| 主端 `M_RUN` | `TRAIN` | 从端已请求或进入训练;撤销link_up,经统一入口从UL开始完整训练,不区分异常来源 |
| 主端 `M_RUN` | `SYNC`、`TRAIN_ACK`、`SYNC_ACK`、`SYNC_RESET`或其他意外固定帧 | 认为双方状态不一致,立即撤销同步并重新训练`UL`和`DL` |
| 从端 `S_RUN` | `SYNC_RESET` | 立即撤销同步并进入 `S_TRAIN`,不触发全局复位 |
| 从端 `S_RUN` | `TRAIN`、`SYNC`、`TRAIN_ACK`、`SYNC_ACK`或其他意外固定帧 | 认为主端正在重建链路或双方状态不一致,立即撤销同步并进入`S_TRAIN` |
| 任一端训练期 | 与当前状态不一致的固定帧 | 不向上传递;清零对应连续计数,继续或超时恢复 |
### 25.7 运行期CRC错误门限
单个CRC错误只丢弃当前帧,不单独触发重新训练。每个接收方向同时维护连续错误计数和最近帧滑动窗口统计,只统计已经取得合法帧长并到达CRC位置的`DATA`和`CTRL`:
```text
CRC_CONSECUTIVE_RETRAIN_THRESHOLD = 4
CRC_WINDOW_FRAMES = 256
CRC_ERROR_RETRAIN_THRESHOLD = 8
```
连续4个CRC承载帧失败,或者最近256个CRC承载帧中累计8个CRC错误,任一条件满足即判定该方向链路质量失效。CRC正确使连续错误计数清零;长度非法和边界丢失按边界异常处理,不计入CRC错误统计。重新训练开始时清零两类统计。
主端检测到`UL`达到门限时重新训练`UL`和`DL`。从端检测到`DL`达到门限时撤销同步、进入`S_TRAIN`并通过可信`UL`持续发送`TRAIN`;主端收到完整TRAIN后经统一入口重新训练UL和DL。
### 25.8 运行期事件优先级
同一接收周期出现多个事件时,数据链路层按以下顺序处理:
1. 公共资源失效;
2. 当前方向被实现明确判定为不可信;
3. 完整`SYNC_RESET`;
4. 当前状态具有控制含义的完整固定帧;
5. 当前状态的通过条件;
6. 当前状态的超时条件;
7. 普通帧解析和计数更新。
完整固定帧引起的状态转换优先于普通协议帧。通过和超时同周期成立时通过优先。尚未完整接收的固定帧不得产生状态事件。
## 26. 重新训练与新会话建立
### 26.1 触发条件
下列事件启动完整重新训练,不触发主端或从端全局器件复位:
- UL或DL同步异常,且规定的边界恢复未能完成;
- 任一接收方向达到第25.7节CRC错误门限;
- 主端运行期收到完整TRAIN或其他规定的意外固定帧;
- DL整轮扫描不能得到合格窗口,或双向同步确认、运行入口超时/失败;
- 连续重传失败、缓存一致性故障或窗口承诺故障产生协议层重训请求;
- 主端主动重训练或从端收到完整SYNC_RESET;
- 公共资源失效后恢复,或任一端重启需要重建链路。
主端按第26.2.2节统一入口从UL校准开始;从端撤销link_up并进入S_TRAIN,可信UL在途帧排空后持续发送TRAIN。公共资源不可用时先等待资源恢复。
单个延迟点失败只记录并继续本轮扫描,不属于新一轮重新训练。UL扫描整轮无合格窗口时从首点重新扫描UL;DL整轮扫描失败不能只重扫DL,必须重新执行完整UL→DL流程。单个CRC错误、可恢复的边界错误及业务层错误不直接触发重新训练,仍按各自既定处理机制执行。
<a id="req-ses-001"></a>
### 26.2 同步丢失、重新训练与协议复位
关键要求编号:`REQ-SES-001`。
任何新一轮重新训练均重新校准UL和DL,不再根据异常方向选择恢复范围。只要任一方向同步丢失或协议故障要求重新训练,旧双向传输协议会话立即失效;检测端立即撤销link_up,对端获知训练事件后同样终止旧会话。
#### 26.2.1 协议层可见的链路状态
`link_up`是提供给传输协议层的聚合链路状态,只有同时满足以下条件时才允许为1:
```text
link_up = ul_sync_up && dl_sync_up && run_entry_complete
```
`ul_sync_up`和`dl_sync_up`可作为数据链路层内部状态或诊断输出;传输协议层不得因为其中一个方向仍可信而继续处理原会话业务。任一方向同步丢失时,检测端必须立即撤销`link_up`。另一端通过仍可信方向上的链路层训练序列或同步状态变化获知异常后,也必须撤销`link_up`。只有双方完成完整UL和DL重新训练及运行入口过程后,才能重新置位`link_up`。
<a id="req-trn-003"></a>
#### 26.2.2 完整重新训练与统一入口
关键要求编号:`REQ-TRN-003`。
每一轮重新训练均执行:
```text
撤销link_up并终止旧会话
→ 可信在途帧排空及对端训练入口通知
→ UL扫描、窗口选择和延迟装载
→ DL扫描、窗口选择和延迟装载
→ DL同步确认 → UL同步确认 → 运行入口
→ 初始POLL_REQ/ACK → 新会话业务传输
```
主端通过`M_RETRAIN_PREP`准备入口,清除训练上下文并禁止新普通帧。可信已开始帧按第26.2.3节完整排空;公共资源不可用时进入`M_WAIT_RESOURCE`。DL发送资源能够发送完整固定帧时,主端随后连续完整发送20个SYNC_RESET,再无条件进入`M_RX_TRAIN`;不能发送时依靠DL异常或资源不可用的对端可见性使从端进入S_TRAIN,资源具备UL测量条件后执行UL扫描。实现必须保证对端能够获知训练入口,不能一边在本地重训,一边持续输出会让对端保持运行状态的合法普通流。
从端因DL异常或本地协议故障启动训练时,先撤销link_up并终止旧会话;可信UL在途帧排空后,从下一完整帧边界直接持续发送TRAIN。主端运行期完整检测到TRAIN后进入统一入口,执行完整UL→DL训练。TRAIN在该处就是训练通知,不需要先人为制造UL边界丢失。UL资源失效时从端等待资源恢复,主端通过同步监测进入统一入口。
主端在UL扫描期间持续请求发送DL IDLE,不发送DL TRAIN。从端S_TRAIN中的IDLE不累计TRAIN资格,因此不会产生新的TRAIN_ACK;只有主端进入DL扫描并实际发送TRAIN后,才开始正常的50帧资格与应答机制。新轮次之前的TRAIN_ACK或SYNC事件不得用作新UL点通过证据。
只有当前轮次的UL和DL都完成校准并通过完整同步确认,才允许重新置位link_up。旧延迟值可供诊断保留,但不得据此跳过扫描或确认。可信方向不保留旧会话业务资格,仅允许在途排空及训练过程规定的固定帧。
#### 26.2.3 协议复位动作
任意传输状态下,只要`link_up`撤销或本地协议故障要求重新训练,传输协议层必须立即撤销`session_ready`,不得开始接受新的业务发送帧,并进入协议复位保持状态。已经完成首字握手但尚未完成末字握手的当前业务发送帧,按第45.1节继续接收到`app_tx_last`并报告中止。必须执行以下动作:
1. 停止并清除`T_ACK_WAIT`、`T_POLL_INTERVAL`、`T_PROGRESS_LIMIT`以及连续失败计数;
2. 立即终止旧会话语义,停止新普通帧请求。资源仍可用的可信发送方向须继续将已开始的普通帧完整发送至CRC末位;保留该帧读取数据及上下文至不再使用。该排空行为不推进旧会话序号、窗口或成功结果;方向不可用而无法完成时立即中止,并将该方向判为不可信;
3. 回滚所有尚未得到最终CRC结论的接收候选帧,不产生业务应用层可见提交;
4. 主端清零`SND_UNA`、`SND_NXT`、`OUTSTANDING_BYTES`和`PEER_WIN_BYTES`,逻辑上清空重传缓存、未发送描述符及控制请求快照;仍被可信在途发送器读取的存储延迟回收,不得复用;
5. 从端清零`RCV_NEXT`、UL发送`TX_SEQ`、`ACK_PENDING`和`RETRY_PENDING`,丢弃尚未提交的接收候选帧及控制响应快照;
6. 从端释放由未提交候选帧占用的传输协议接收资源,并根据复位后的实际可用接收容量重新计算`WIN_BYTES`,不得无条件把窗口设置为实现最大值;
7. 已协议提交的接收数据及其未交付部分不回滚;正在业务接收接口输出的帧须保留至末字握手。已形成但尚未输出的发送完成结果保持不变,结果队列继续按接受顺序输出。尚未形成最终结果的已接受发送请求形成一次中止结果,不得自动带入新会话。
上述协议复位不是主端或从端的全局器件复位,也不要求复位业务应用层。若业务应用层需要重新提交结果不确定的操作,必须由业务语义决定是否允许重复执行。
#### 26.2.4 重新训练期间的行为
传输协议层在`link_up=0`期间保持复位,不得开始新的普通`DATA`或`CTRL`,不得接受普通接收候选,不推进业务序号或协议超时。唯一发送例外是第26.2.3节可信方向在途帧的完整排空;排空结束后数据链路层只执行训练、同步及运行入口序列;从端本地协议故障按第46.2节在可信UL排空后持续发送TRAIN,主端据此启动完整训练。
从端持续发送UL TRAIN通知训练入口;主端在运行期收到完整TRAIN后从UL开始完整重新训练,不再判断故障属于UL、DL还是从端协议层。该通知属于数据链路层,不得解释为普通协议业务;已处于UL或DL扫描时按当前训练状态解释TRAIN。
#### 26.2.5 新会话初始化
完整UL和DL重新训练和运行入口过程完成后,按照以下顺序建立新会话:
1. 双方数据链路层重新置位各自的`link_up`;双方传输协议状态仍保持第26.2.3节规定的初始值,`session_ready`保持为0;
2. 主端进入`M_WAIT_STATUS`并置位`POLL_PENDING`;
3. 从端进入`S_EXPECT`。收到合法`POLL_REQ`后,以`ACK_NEXT=0`和当前实际`WIN_BYTES`形成状态`CTRL`;
4. 从端必须在该初始状态响应中发送`ACK_NEXT=0`。主端只接受格式和CRC合法的初始ACK/UPDATE,不使用`ACK_NEXT`的数值作为新会话准入条件;主端把收到的`ACK_NEXT`解释为新会话起始序号,原子设置`SND_UNA=ACK_NEXT`和`SND_NXT=ACK_NEXT`,保持`OUTSTANDING_BYTES=0`及重传缓存为空,并装载响应中的`WIN_BYTES`;
5. 主端收到合法初始ACK/UPDATE后进入`M_TRANSPORT_RUN`并置位内部`master_session_ready`;从端在初始状态`CTRL`完整发送后置位内部`slave_session_ready`;
6. 只有内部`session_ready=1`后,协议层才允许在新业务帧边界置位`app_tx_ready`。业务应用层不读取`session_ready`。合规新会话从`SEQ=0`开始;若收到非零初始`ACK_NEXT`,按第46.3节执行兼容对齐。
初始响应中的`ACK_NEXT`只定义新会话从哪个序号开始,不表示对旧会话帧的累计确认。该响应必须绕过正常运行期的ACK合理性检查,不得释放任何缓存;此时旧会话缓存已经清空。`POLL_REQ/ACK`同时用于确认控制帧通路可用并取得真实接收窗口。单端重启也按本节处理,不需要从该值推断重启前的会话状态。
### 26.3 `SYNC_RESET`
`SYNC_RESET`是主端主动请求从端返回训练状态的固定帧。它不触发从端全局器件复位;收到该帧会使链路同步状态撤销,并按第26.2节终止和复位当前传输协议会话。主端主动发起链路重新训练且`DL`仍具备传送完整固定帧的条件时,必须连续发送20个`SYNC_RESET`;发送期间收到的`TRAIN`不作为提前终止条件。逐帧重复发送是幂等操作:从端在任意非资源等待状态完整匹配其中任意一个160位`SYNC_RESET`后,清除`train_ack_active`及固定帧检测历史并进入或保持`S_TRAIN`。主端完整发送20帧后无条件进入M_RX_TRAIN,随后完成全部DL校准和同步确认。若`DL`已严重失步而无法识别全部`SYNC_RESET`,从端的运行期监测仍应检测到边界异常并自行进入`S_TRAIN`。从端因本地检测到`DL`失步而自行进入`S_TRAIN`时,不要求先收到`SYNC_RESET`。
### 26.4 复位可见性与训练入口
主端复位或重新初始化链路同步模块时,必须使`DL`退出合法运行期连续流,直至重新训练开始。该行为必须足以使从端撤销`DL`同步状态并进入`S_TRAIN`;不允许主端在本地同步状态已经丢失后继续输出会被从端解释为合法运行期`IDLE`或普通协议帧的连续流。满足此约束后,主端单独重启会使从端自动进入`S_TRAIN`并在`UL`持续发送`TRAIN`,主端经统一训练入口进入M_RX_TRAIN并完成整个UL→DL流程。
进入任一新训练轮次时,必须清除固定帧连续计数、固定帧匹配历史、候选边界、普通帧剩余长度、CRC和解扰状态、暂定边界标志、当前扫描点统计、已失效的窗口扫描结果以及运行期CRC错误统计。诊断计数和最近一次成功延迟值可以保留,但仅用于诊断;旧UL和DL窗口结果均不得作为新轮次跳过训练的依据。
当可信方向承担训练状态通知时,训练固定帧必须从该方向的完整帧边界开始。物理资源仍可用时,已经开始的普通帧先完整发送结束;物理资源失效导致无法完成时,必须中止该帧并把该方向一并判定为不可信。
## 27. 同步机制配置参数
所有参数必须在RTL集成前给出确定值并纳入版本控制。
| 参数 | 单位 | 约束/来源 |
|---|---:|---|
| `RX_DELAY_MIN/MAX/STEP` | 延迟档位 | `IDELAY`范围和分辨率 |
| `TX_DELAY_MIN/MAX/STEP` | 延迟档位 | `ODELAY`范围和分辨率 |
| `RX_DELAY_STEP_TIME` | ps/扫描步进 | 相邻`UL`扫描点的实际接收延迟差;由物理实现配置或校准数据给出 |
| `TX_DELAY_STEP_TIME` | ps/扫描步进 | 相邻`DL`扫描点的实际发送延迟差;由物理实现配置或校准数据给出 |
| `ALIGN_CONFIRM_FRAMES` | 帧 | 实现配置整数,范围1~50;固定帧候选边界的连续确认长度,计数关系见第24.1节 |
| `UL_TRAIN_PASS_COUNT` | 帧 | 固定为50个连续正确`TRAIN` |
| `UL_POINT_TIMEOUT_FRAMES` | 帧时间 | 固定为200;到期未通过则该`IDELAY`点失败 |
| `DL_TRAIN_QUALIFY_COUNT` | 帧 | 固定为50;达到后触发一批固定50个`TRAIN_ACK` |
| `DL_ACK_PASS_COUNT` | 帧 | 固定为10个连续正确`TRAIN_ACK` |
| `DL_POINT_TIMEOUT_FRAMES` | 帧时间 | 固定为200;到期未通过则该`ODELAY`点失败 |
| `TRAIN_ACK_TX_COUNT` | 帧 | 固定为50;应答期间不累计下一轮`TRAIN` |
| `TX_POINT_GAP_IDLE_WORDS` | 32位字 | 固定为400;完整发送后切换ODELAY,不要求`TRAIN`确认 |
| `T_ACK_TAIL_BOUND` | 时间 | 实现声明的最坏附加延迟及裕量;必须满足第22.3节400个`IDLE`保护上界 |
| `MIN_PASS_WINDOW_RATIO` | 无量纲(UI比例) | 实现配置值;建议基线为0.4,必须由目标时序预算确认,不允许运行期任意修改 |
| `MIN_PASS_WINDOW_TIME` | ps | 派生值:`MIN_PASS_WINDOW_RATIO × UI`,不得独立配置 |
| `RX_MIN_PASS_TAPS` | 延迟档位 | 派生值:均匀步进时为`ceil(MIN_PASS_WINDOW_TIME / RX_DELAY_STEP_TIME) + 1` |
| `TX_MIN_PASS_TAPS` | 延迟档位 | 派生值:均匀步进时为`ceil(MIN_PASS_WINDOW_TIME / TX_DELAY_STEP_TIME) + 1` |
| `DL_SYNC_PASS_COUNT` | 帧 | 固定为10000个连续正确`SYNC` |
| `SYNC_ACK_TX_COUNT` | 帧 | 固定为20;从端定量发送 |
| `SYNC_ACK_PASS_COUNT` | 帧 | 固定为10个连续正确`SYNC_ACK` |
| `UL_SYNC_PASS_COUNT` | 帧 | 固定为10000个连续正确`SYNC` |
| `M_DL_CONFIRM_TIMEOUT_FRAMES` | 固定帧时间 | 必须大于`DL_SYNC_PASS_COUNT + SYNC_ACK_PASS_COUNT`并覆盖往返及流水线余量 |
| `M_UL_CONFIRM_TIMEOUT_FRAMES` | 固定帧时间 | 必须大于`UL_SYNC_PASS_COUNT + (SYNC_ACK_TX_COUNT-SYNC_ACK_PASS_COUNT)`并覆盖流水线余量 |
| `S_UL_SYNC_TIMEOUT_FRAMES` | 固定帧时间 | 固定为10500;从端进入`S_UL_SYNC_TX`后等待首个完整合法`DL IDLE`的上限 |
| `SYNC_RESET_TX_COUNT` | 帧 | 固定为20;主端统一训练入口中,DL具备完整固定帧发送能力时连续发送 |
| `RUN_ENTRY_IDLE_TX_WORDS` | 32位字 | 固定为20;从端运行入口响应长度 |
| `RUN_ENTRY_IDLE_PASS_WORDS` | 32位字 | 固定为1;主端收到首个完整`UL IDLE`即通过 |
| `M_RUN_ENTRY_TIMEOUT_WORDS` | 32位字时间 | 主端进入`M_RUN_ENTRY`后等待首个完整`UL IDLE`的上限;必须大于`RUN_ENTRY_IDLE_TX_WORDS`并覆盖实现流水线余量 |
| `RECOVERY_IDLE_WORDS` | 32位字 | 固定为1;在候选边界匹配一个完整合法`IDLE`即可确认恢复 |
| `RECOVERY_CONFIRM_FRAMES` | 帧 | 固定为1;一个`SOF`、适用长度及CRC正确的普通帧即可确认线路边界,协议接受另行检查 |
| `RECOVERY_SEARCH_LIMIT_WORDS` | 32位字时间 | 实现配置值;不得小于2 × `MAX_LINE_FRAME_WORDS`;固定字相位搜索含候选验证,基础下限为522 |
| `CRC_CONSECUTIVE_RETRAIN_THRESHOLD` | CRC承载帧 | 固定为4;连续4个`DATA`或`CTRL` CRC失败触发完整UL和DL重新训练 |
| `CRC_WINDOW_FRAMES` | CRC承载帧 | 固定为256;滑动错误统计窗口 |
| `CRC_ERROR_RETRAIN_THRESHOLD` | CRC错误帧 | 固定为8;最近256个CRC承载帧中达到8个错误触发完整UL和DL重新训练 |
每次设置`IDELAY`或`ODELAY`后,数据链路层必须分别等待抽象条件`rx_delay_ready`或`tx_delay_ready`有效。本规范只约束“当前延迟配置就绪后才能开始测量”,不规定通过固定等待周期、器件状态信号、配置回读还是其他方法确认就绪。因此,通用参数表不规定统一的延迟稳定周期;具体物理实现可以在第7章配置声明中说明其就绪生成方法。
本表中的50、200、400、10、10000、10500、20、1、4、256和8为本规范固定基线。确认阶段、运行入口和边界恢复总超时必须按本表下限结合目标器件、线路速率、训练期接收对齐能力及实际流水线确定。
计数器按包含终值设计时,50计数至少6位,200计数至少8位,400计数至少9位,10计数至少4位,20计数至少5位,10000和10500计数至少14位。所有连续计数器达到终值后应饱和或立即触发状态转换,不允许回卷。
# 第五篇 非对称可靠传输与重传机制
## 28. 传输机制范围、目标与边界
### 28.1 适用范围
本规范定义链路同步完成后的业务确认、接收窗口、超时查询、Go-Back-N重传和连续失败后的重新训练触发机制。
本篇使用第三篇“统一数据协议”(第8章至第17章)定义的`DATA`、`CTRL`、`IDLE`和固定同步类帧,不重复定义帧格式、CRC、扰码或线路位序。其中,公共编码和线路位序见第9章,帧类型与标识见第10章,固定同步类帧见第11章,`DATA`和`CTRL`格式分别见第12章和第14章,CRC与扰码规则分别见第15章和第16章,封装与解析规则见第17章。
同步训练、延迟校准、运行期同步监测和重新训练机制由第四篇(第18章至第27章)规定;同步丢失后的传输协议会话复位见第26.2节,传输状态机及层间恢复接口分别见第35章和第46章。
### 28.2 设计目标
| 方向 | 机制 | 目标 |
|---|---|---|
| 主端 → 从端 | 累计ACK、字节窗口、Go-Back-N重传 | 可靠、有序、不重复向上层提交 |
| 从端 → 主端 | 无确认传输 | CRC与格式正确的帧直接输出;无ACK、无流控、无重传,允许丢帧和重复 |
本文中的“业务帧”仅指带`SEQ`的`DATA`。重传层不解释`DATA`载荷。`CTRL`、`IDLE`及固定同步类帧不属于业务序号空间,不进入重传缓存,也不消耗`WIN_BYTES`。
## 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
完成双向同步
↓
主端发送POLL_REQ
↓
从端返回初始ACK_NEXT和WIN_BYTES
↓
主端在窗口内连续发送DATA
↓
从端按SEQ接受并主动发送累计ACK
↓
主端释放重传缓存、更新窗口并继续发送
↓
发生错误:RETRY_REQ或超时触发Go-Back-N
↓
连续三轮重传无进展:报告可靠链路故障和会话中止,清空旧会话缓存并触发重新训练
```
### 29.3 总体数据流
```mermaid
flowchart LR
subgraph MASTER["Master"]
direction TB
MU[主端业务应用层发送]
MT[可靠发送控制]
MB[未确认业务帧重传缓存]
MC[确认、窗口与重传控制]
MR[无确认接收]
MO[主端业务应用层接收]
end
subgraph SLAVE["Slave"]
direction TB
SR[可靠接收与窗口管理]
SU[从端业务应用层接收]
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` | 主端 | 下一待重传位置 | 在完整帧边界按最新确认点推进 |
| `ACTIVE_TX_SEQ` | 主端 | 当前在途重传帧序号 | 帧开始时锁存,ACK不得修改 |
| `ROUND_ACK_PROGRESS` | 主端 | 当前重传发送阶段出现合法ACK推进 | 冻结范围时清零,ACK推进置位 |
| `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
```
推荐实现:
```text
帧RAM:保存完整逻辑帧
描述符FIFO:保存{RAM起始地址、FRAME_COST或LEN、SEQ}
```
重传不得重新分配`SEQ`。重传时,主端从`SOF`开始重新输出同一逻辑帧;数据链路层重新计算并追加CRC,再从规定初值重新执行逐帧扰码。
只有合法累计ACK才能将未确认帧作为成功传输而释放。超时、完成重传和无效`CTRL`不得释放未确认帧。进入重新训练时,必须按第26.2节中止当前会话并清空未确认帧、描述符和重传缓存,但不得将这些帧报告为成功。
### 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 主端
participant S as 从端
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`。初始化和运行期的所有`POLL_REQ`均使用以下固定字段;从端只根据`FLAGS=POLL_REQ`执行状态查询,`ACK_NEXT`和`WIN_BYTES`只参与实际字节的CRC计算,从端不解析或检查其数值,不作为主端对UL业务的确认或窗口公告:
```text
FLAGS = POLL_REQ
ACK_NEXT = 16'h0000
RESERVED = 8'h00
WIN_BYTES = 32'h00000000
```
从端响应:
```text
FLAGS = ACK/UPDATE
ACK_NEXT = 0
WIN_BYTES = 以当前ACK_NEXT为锚点、当前能够承诺的协议层逻辑帧接收总额度
```
主端收到合法初始响应前不得发送`DATA`。合法初始ACK/UPDATE到达后即完成主端会话初始化并进入`M_TRANSPORT_RUN`,即使`WIN_BYTES`为0也不继续留在`M_WAIT_STATUS`。存在队首待发送帧且窗口不足时,按第32.6.1节执行窗口查询;没有待发送请求时不必仅因窗口为0持续查询。
### 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 = 以当前ACK_NEXT为锚点、当前能够承诺的协议层逻辑帧接收总额度
```
开始发送状态`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`必须整体忽略。
<a id="req-win-001"></a>
### 31.7 从端接收窗口维护
关键要求编号:`REQ-WIN-001`。
从端接收资源要求分为静态能力和动态公告:
1. 静态能力:接收资源空闲时,必须能够提供至少1040 B的可公告窗口,接受一个最大`DATA`逻辑帧;CRC流水线和固定接收资源不得占用这份协议层容量。
2. 动态公告:每次形成状态`CTRL`快照时,以该快照`ACK_NEXT`为锚点,根据实际可承诺缓存及帧管理资源计算`WIN_BYTES`并向下对齐到4字节。运行时可以小于1040 B或为0,不要求每次公告达到能力下限。
采用独立帧描述符时,可使用以下保守的动态约束:
```text
WIN_BYTES <= free_logical_buffer_bytes
WIN_BYTES <= 12 × free_frame_descriptor_count
```
这里的free资源是该次快照可承诺给`ACK_NEXT`及后续未确认帧的资源,必须保留此前已授予且仍可能在途或重传的额度,不得因内部其他用途收回。公式不是只在上电检查的最大配置约束。
最低配置不能仅规定1040 B和一个描述符:1040 B额度可以合法容纳86个最短12 B逻辑帧。若采用上述保守公式,至少需要87个空闲描述符才能公告1040 B;也可使用其他等效管理结构,但须证明任意合法帧长度组合都不会耗尽已承诺资源。实际可公告窗口能力由字节缓存和帧管理能力共同决定,必须至少达到1040 B。
接受帧时按`FRAME_COST`占用资源,业务接收接口读取或其他明确的资源释放动作完成后归还对应容量。正常变化随下一次累计状态报告;`WIN_BYTES`从0恢复为非0时,即使无新帧也须置位`ACK_PENDING`并发送ACK/UPDATE。单纯窗口等待及主动查询按第32.6.1节执行。
### 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 主端
participant S as 从端
M->>S: DATA, SEQ=2(CRC校验失败)
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 = 以当前ACK_NEXT为锚点、当前能够承诺的协议层逻辑帧接收总额度
```
只有正确接受`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未推进时不释放缓存;
- 设置 `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不能截断当前帧;
- 若`ACK_NEXT`相对原`SND_UNA`发生推进,按正常前进ACK清零连续失败计数;若未推进,则不得把它计作ACK进展;
- 根据新窗口返回正常发送状态:有待发送帧且窗口足够时允许首次发送,否则等待窗口更新或上层业务。
3. 如果 `ACK_NEXT != SND_NXT`,主端必须先验证区间`[ACK_NEXT, SND_NXT)`中的每个`SEQ`均恰好存在一个重传描述符及其对应缓存内容。若任一项缺失、重复或无法读取,主端必须将其判定为本地传输协议状态损坏;不得继续重传,也不得将任何未确认帧报告为成功。主端必须报告当前会话中止,撤销`session_ready`,清空当前协议状态,置位`retrain_request`并进入`M_RETRAIN`,按第26.2节重新训练和建立新会话。
4. 上述一致性检查通过后,按当前状态处理:正常传输时停止首次发送并请求开始重传;已处于重传准备、发送或等待时,必须按本节下述重复请求规则合并,不直接重置指针或观察期。
5. 只有实际开始新轮次时,才在规定帧边界按最新确认点设置`RETX_PTR`并冻结`RETX_END`,具体见第32.8节和第35.2节。
6. 实际重传时按原`SEQ`顺序发送未确认帧。
7. 不增加`OUTSTANDING_BYTES`,不分配新`SEQ`,不建立新描述符。
8. 重传结束后等待从端主动累计ACK;`T_ACK_WAIT`无进展时发送`POLL_REQ`。
重传期间收到前进ACK时立即更新`SND_UNA`及未确认记账,但不得释放或覆盖仍被在途发送器读取的缓存。当前帧开始后锁存`ACTIVE_TX_SEQ`及读取上下文,不因ACK修改。完整结束当前帧后,在冻结区间内选择不早于新`SND_UNA`及`ACTIVE_TX_SEQ`+1的下一序号;模序号比较采用第30.2节,禁止直接对16位无符号数取大小。
再次收到RETRY_REQ时,先执行合法性、ACK和窗口更新;在重传准备阶段合并请求并以帧边界处最新确认点冻结范围;重传发送阶段不倒退指针、不打断当前帧、不增加待执行轮次;重传等待阶段,ACK未推进的请求仅合并,不提前开始下一轮,也不改变本轮观察期的起点或截止时间;ACK确有推进时本轮成功,若该RETRY_REQ仍要求重传未确认帧,则按最新确认点开始新的轮次。重复请求不算ACK进展,也不单独增加失败轮数。若全部已确认,等待可信当前帧排空后返回正常状态。
### 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 = 以当前ACK_NEXT为锚点、当前能够承诺的协议层逻辑帧接收总额度
```
主端无需判断是`POLL_REQ`丢失还是响应丢失;两者均按没有收到合法状态处理。
### 32.6 窗口不足
如果 `FRAME_COST > AVAILABLE_BYTES`,主端停止首次发送新帧并等待从端主动`ACK/UPDATE`。`T_POLL_INTERVAL`仍未取得足够窗口时发送`POLL_REQ`。
窗口不足不允许主端绕过限制发送新帧。`CTRL`不消耗窗口,因此任何窗口值下都可以发送`POLL_REQ`。
#### 32.6.1 单纯窗口不足的确定性问询流程
“单纯窗口不足”必须同时满足:
```text
存在等待首次发送的业务帧
OUTSTANDING_BYTES == 0
FRAME_COST > AVAILABLE_BYTES
link_up == 1
session_ready == 1
```
该状态只表示当前窗口不能容纳队首待发送业务帧,不表示ACK丢失、业务帧传输失败或链路同步异常。主端必须执行以下流程:
1. 保持在`M_TRANSPORT_RUN`,停止首次发送该业务帧;不得为其分配`SEQ`,不得写入重传缓存,也不得改变`SND_NXT`或`OUTSTANDING_BYTES`;
2. 进入单纯窗口等待的同周期清零并启动窗口问询计时器,计时间隔为`T_POLL_INTERVAL`;
3. 计时期间优先等待从端主动发送的`ACK/UPDATE`;从端在`WIN_BYTES`从0恢复为非0时仍必须按第31.7节主动报告;
4. 收到合法状态`CTRL`时,先装载最新`PEER_WIN_BYTES`并重新计算`AVAILABLE_BYTES`;
5. 若队首业务帧满足`FRAME_COST <= AVAILABLE_BYTES`,停止并清零窗口问询计时器,取消尚未开始发送的本次`POLL_REQ`,随后按第31.3节执行首次发送;已经开始发送的`POLL_REQ`必须完整结束;
6. 若收到合法状态后窗口仍不足,取消仅由本次窗口问询产生且尚未开始发送的`POLL_PENDING`,清零并重新启动完整的`T_POLL_INTERVAL`,不得在同一周期发送新的`POLL_REQ`;
7. 若计时达到`T_POLL_INTERVAL`且此前未取得足够窗口,置位一次`POLL_PENDING`并暂停该计时器;`POLL_PENDING`已经为1时不得重复累计新的请求;
8. `POLL_REQ`开始发送时清除本次已经覆盖的`POLL_PENDING`;该帧完整发送结束时清零、重新启动下一次`T_POLL_INTERVAL`。若请求或响应丢失,下一周期继续查询;
9. 如果当前已经没有待发送业务帧,停止并清零窗口问询计时器,取消尚未开始发送的窗口查询;
10. `link_up`撤销或进入`M_RETRAIN`时,立即停止并清零窗口问询计时器,后续按第26.2节处理。
单纯窗口不足期间不得启动`T_ACK_WAIT`、`T_PROGRESS_LIMIT`、Go-Back-N或连续重传失败计数,也不得仅因等待时间较长而触发重新训练。`POLL_REQ`和从端返回的状态`CTRL`不消耗业务窗口。
若`OUTSTANDING_BYTES != 0`,则不适用本节的独立窗口问询流程。主端必须继续使用针对最早未确认帧的ACK进度计时器:`T_ACK_WAIT`到期后发送第一次`POLL_REQ`,其后按`T_POLL_INTERVAL`查询,并按`T_PROGRESS_LIMIT`决定是否启动或判定一轮Go-Back-N。
两种计时模式必须按以下条件原子切换:合法前进ACK清除最后一个未确认帧后,如果仍有队首待发送帧且窗口不足,必须在该次ACK处理完成时停止ACK进度计时并启动单纯窗口问询计时;单纯窗口等待结束并完成首个新业务帧发送后,必须停止窗口问询计时,并在该帧`tx_frame_done`时启动ACK进度计时。任何时刻不得同时启用两种计时解释。
采用第7.3节的750 Mbps典型配置时,`T_POLL_INTERVAL=20 μs`,即187.5 MHz时钟的3750个周期。其他物理配置按第33.1节计算。
### 32.7 主端估算窗口与从端本地窗口不一致
主端的`AVAILABLE_BYTES`由最近一次合法窗口公告及本地未确认帧记账计算;从端内部的瞬时空闲资源还会受到已保留额度和上层释放时机影响,两者不要求每个时刻数值相等,但从端必须始终兑现已经公告的窗口承诺。
#### 32.7.1 主端低估窗口
主端低估只降低吞吐率。主端停止新帧并等待`ACK/UPDATE`,或在`T_POLL_INTERVAL`后`POLL_REQ`。收到最新状态后重新计算。
#### 32.7.2 主端高估窗口或窗口承诺不一致
`WIN_BYTES`是以对应`ACK_NEXT`为锚点的接收能力承诺,不是可以撤销的瞬时空闲空间。从端发布窗口后,必须为主端依据该窗口合法发送的业务帧保留足够的帧缓存和描述符资源,直至相应业务帧被累计确认或当前协议会话终止。
主端收到合法`CTRL`后,必须先按`ACK_NEXT`释放已经累计确认的前缀,再从剩余描述符重新计算:
```text
OUTSTANDING_BYTES
= [SND_UNA, SND_NXT)中全部未确认业务帧的FRAME_COST之和
PEER_WIN_BYTES
= 本CTRL中与ACK_NEXT对应的WIN_BYTES
AVAILABLE_BYTES
= PEER_WIN_BYTES - OUTSTANDING_BYTES
```
对于符合本规范的窗口公告,必须满足:
```text
OUTSTANDING_BYTES <= PEER_WIN_BYTES
```
`OUTSTANDING_BYTES`对应的接收能力已经由从端授予。同一`SEQ`的重传不产生新的窗口占用,因此即使`AVAILABLE_BYTES=0`,主端仍可以重传现有未确认帧;`AVAILABLE_BYTES=0`只禁止首次发送新的业务帧。
如果主端仅在:
```text
FRAME_COST <= AVAILABLE_BYTES
```
时首次发送业务帧,则从端不得因为本地帧缓存或描述符不足而拒绝该帧或其后续重传。新的窗口公告不得撤销已经由旧窗口合法授予并被主端占用的接收能力。
出现以下任一情况时,表示窗口承诺或本地协议状态已经不一致:
1. 主端处理合法`CTRL`并释放确认前缀后,得到`OUTSTANDING_BYTES > PEER_WIN_BYTES`;
2. 从端无法为主端依据已公告窗口合法首次发送的期望`SEQ`帧提供接收资源;
3. 从端无法接收已经占用窗口额度的未确认帧重传;
4. 主端的窗口记账、未确认描述符或重传缓存与`SND_UNA`、`SND_NXT`不一致。
上述情况不得通过缩小重传范围、等待窗口增大或重复发送`POLL_REQ`继续当前会话。检测端必须:
1. 停止首次发送和重传业务帧;
2. 报告窗口承诺或本地协议状态一致性故障;
3. 将全部未完成业务请求报告为会话中止,不得报告为成功;
4. 撤销`session_ready`并清空当前传输协议状态;
5. 触发重新训练,并按第26.2节建立新会话。
主端估算值与从端内部瞬时空闲资源可以在数值上不同,但只要双方仍满足已经公告的窗口承诺,这种差异不构成错误,也不需要专门的“窗口重新同步状态”。
<a id="req-arq-001"></a>
### 32.8 Go-Back-N轮次
关键要求编号:`REQ-ARQ-001`。
一次Go-Back-N轮次定义为:
1. 冻结 `RETX_END=SND_NXT`。
2. 从`SND_UNA`开始按`SEQ`顺序重传到`RETX_END-1`;重传不重复占用窗口额度,也不按当前`AVAILABLE_BYTES`缩小范围。
3. 重传期间不首次发送新业务帧。
4. 本轮重传发送期间维护`ROUND_ACK_PROGRESS`标志,任何合法ACK推进都置位;完成冻结范围后若有进展则本轮成功,返回正常状态;否则开始完整的`T_PROGRESS_LIMIT`观察期。
5. `T_ACK_WAIT`和`T_ACK_WAIT`+`T_POLL_INTERVAL`到期时发送`POLL_REQ`。
6. `T_PROGRESS_LIMIT`内`SND_UNA`向前推进:本轮成功,失败计数清零。
7. 发送阶段及其后观察期都无进展且观察期到期:本轮失败,计数加一;达到三轮失败门限则终止会话并请求完整训练,否则开始下一轮。等待阶段收到ACK未推进的合法RETRY_REQ时只合并请求,保持观察期计时,不提前开始下一轮,不增加失败计数。
8. 观察期内RETRY_REQ同时带来合法ACK推进时,本轮成功且失败计数清零;若仍有未确认帧需要重传,从最新确认点进入新的轮次。ACK推进优先于同周期超时。持续重复请求不得使无进展轮次无限重启。
### 32.9 连续失败与重新训练
连续三轮完整重传及完整观察期均无ACK推进时,主端必须:
1. 停止首次发送新业务帧;
2. 报告可靠链路故障,并把全部未确认业务请求报告为会话中止;
3. 触发链路重新训练;
4. 按第26.2节清空旧会话的未确认帧、描述符和重传缓存。
达到门限时不得把未确认帧当作成功帧。会话中止必须向业务应用层报告;同步恢复后从`SEQ=0`建立新会话,不继续重传旧会话帧。
## 33. 定时参数与失败门限
### 33.1 超时计算
ACK进度计时、重传观察期和单纯窗口查询可以复用计数器,但语义必须分开:
| 模式 | 起点及重新开始规则 | 到期动作 |
|---|---|---|
| 正常发送,有未确认帧 | 未确认集合首次非空时从最早帧`tx_frame_done`开始;同一正常阶段内只有合法ACK推进重启;有进展重传返回正常且仍有未确认帧时,从最后在途重传帧结束重新开始 | `T_ACK_WAIT`请求查询;`T_PROGRESS_LIMIT`启动重传 |
| 重传准备或发送 | 不按正常模式累积失败;锁存本轮ACK进展 | 完成当前冻结范围后判断`ROUND_ACK_PROGRESS` |
| 重传发送完成且本轮无进展 | 从冻结范围完整发送结束开始一个新的观察期;期间前进ACK使本轮成功 | 到`T_PROGRESS_LIMIT`仍无进展才增加一轮失败 |
| 初始化或单纯窗口等待 | 按第31.2节或第32.6.1节独立计时 | 查询状态,不按无进展业务重传判败 |
已形成的前进ACK结果优先于同周期超时。重复ACK、仅窗口变化及重复RETRY_REQ不重置ACK进度。重传发送期间记录的进展在帧边界及冻结范围结束处处理,不能因为等待阶段未再收到新ACK而把有进展轮次判为失败。
最大`DATA`线路帧为1044 B,`CTRL`为16 B:
```text
T_MAX_FRAME = 1044 × 8 / LINE_RATE
T_CTRL = 16 × 8 / LINE_RATE
```
查询响应预算必须覆盖两个方向,而不仅是UL阻塞:
```text
T_POLL_RESPONSE_BOUND = T_DL_BLOCK_MAX + T_CTRL(DL)
+ T_DL_PROP + T_SLAVE_PROCESS
+ T_UL_BLOCK_MAX + T_CTRL(UL)
+ T_UL_PROP + T_MASTER_PROCESS + T_CDC_MARGIN
```
若间隔从POLL_REQ完整发送结束起算,可去掉已完成的DL阻塞及DL `CTRL`序列化时间,但必须保留尚未完成的传播、处理及UL响应时间。`T_PROGRESS_LIMIT`须覆盖查询请求等待完整帧边界、实际发送及最坏返回时间,保证至少一次查询有机会完成。
750 Mbps时T_MAX_FRAME=11.136 μs、T_CTRL约0.171 μs。第33.2节20/20/60 μs仅适用于实现证明相应计时起点下的时序预算成立的典型配置;其他实现须依据实际阻塞、传播、处理及CDC向上取整,不得仅按线路速率比例忽略固定延迟。
### 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`完整发送结束时重新计时;存在未确认帧时,用作第一次`POLL_REQ`之后的重复查询间隔;
- `T_PROGRESS_LIMIT`:正常模式从最早未确认帧完成或最近ACK推进计时;重传无进展观察模式从冻结范围发送结束计时。达到上限启动重传或判定一轮失败;
- `MAX_GBN_FAILURE_ROUNDS`:连续无ACK推进的完整重传失败轮数门限。
必须满足 `T_PROGRESS_LIMIT > T_ACK_WAIT`,并保证在`T_PROGRESS_LIMIT`内至少可以发送一次`POLL_REQ`并接收一个最坏阻塞条件下的`CTRL`响应。
采用其他线路速率或时钟时,必须根据第33.1节重新计算并向上取整;实际时间不得短于最大阻塞帧、`CTRL`返回、处理、CDC、传播和抖动裕量之和。
表中三个时间参数属于实现配置值,20/20/60 μs仅为典型配置。`MAX_GBN_FAILURE_ROUNDS=3`为规范固定值,不随线路速率或业务负载改变。
### 33.3 无进展时间线
```text
0 μs: 开始或重新开始ACK进度计时
T_ACK_WAIT: ACK未推进,发送第一次POLL_REQ
第一次POLL_REQ完整结束后T_POLL_INTERVAL:ACK仍未推进,请求下一次POLL_REQ
T_PROGRESS_LIMIT: ACK仍未推进,启动或判定一轮Go-Back-N
```
同确认点ACK、旧ACK、无效`CTRL`以及只有`WIN_BYTES`变化都不算ACK进度。正常模式只有`SND_UNA`合法推进才重启;进入重传观察期的独立起点按第33.1节定义。
## 34. 事件—动作规范
### 34.1 主端事件表
本节为阅读索引,不重复定义寄存器动作或事件优先级。
| 事件 | 确定性规则来源 |
|---|---|
| 新会话初始响应 | 第26.2.5节、第31.2节及第35.2.3节 |
| 前进、同确认点、过时或越界ACK | 第31.6节;在途缓存保留按第35.2.3节 |
| RETRY_REQ及重传中重复请求 | 第32.3节及第35.2.3节 |
| 单纯窗口不足 | 第32.6.1节 |
| 计时、轮次进展及三轮失败 | 第32.8~32.9节、第33章 |
| 缓存或窗口承诺故障 | 第32.7.2节及第35.2.3节 |
| 同周期并发 | 第35.2.4节 |
| 会话终止与可信在途帧排空 | 第26.2.3节及第44章 |
### 34.2 从端事件表
| 事件 | 确定性规则来源 |
|---|---|
| 期望`DATA`、错误`DATA`、重复或未来序号 | 第31.4节、第32.2节及第35.4.2节 |
| POLL_REQ及零窗口恢复 | 第14.2节、第31.7节及第35.4节 |
| 状态快照和并发更新 | 第35.4.3~35.4.4节 |
| 窗口承诺故障及重新训练握手 | 第26章、第35.4节及第46.2节 |
从端接收和发送调度并行;状态机表和第35章的优先级为具体RTL实现的规则来源。
### 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. 普通从端→主端 DATA
```
已经开始发送的帧不得被`CTRL`中断。没有传输协议层帧需要发送时,本层不提出发送请求;`IDLE`等空闲码字由数据链路层连续生成,不属于本重传机制状态机。主端不得因为从端业务接收缓存已满而丢弃合法`CTRL`,建议为`CTRL`设置独立的小型接收通路。
## 35. 传输状态机
### 35.1 实现划分与并行关系
本章状态机是规范性控制模型。链路运行状态保留`M_RUN`;主端传输协议运行状态统一为`M_TRANSPORT_RUN`,两者属于独立并行状态机,诊断不得混用。具体RTL可以合并或拆分状态,但外部行为、事件优先级和寄存器更新必须等价。
全双工接收、发送调度和定时统计必须并行运行。不得用一个互斥状态机表示整个端点,否则发送`CTRL`期间可能错误地停止接收。推荐划分如下:
| 端点 | 并行控制单元 |
|---|---|
| 主端 | 可靠传输控制器、主端→从端发送调度器、`CTRL`接收处理器、定时器 |
| 从端 | 业务帧接收控制器、状态报告生成逻辑、从端→主端发送调度器 |
发送调度器只在完整帧边界接受新请求。任何帧一旦开始发送,必须连续发送到结束。重传控制器只产生协议帧请求,不负责生成`IDLE`;无协议帧请求时由数据链路层维持连续线路输出。
### 35.2 主端可靠传输控制器
#### 35.2.1 状态定义
| 状态 | 含义 | 允许的主要动作 |
|---|---|---|
| `M_WAIT_STATUS` | 等待从端合法状态报告 | 发送或重发`POLL_REQ`;禁止首次发送新业务帧 |
| `M_TRANSPORT_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` | 链路失步、数据链路层正在重新训练、达到连续失败门限,或检测到缓存/窗口承诺一致性故障 | 清除当前协议会话状态和缓存,停止协议帧请求;由协议层故障进入时置位`retrain_request`;等待链路重新同步 |
`M_TRANSPORT_RUN`同时覆盖有未确认帧、等待窗口和暂时没有上层发送请求的情况。这些情况由`OUTSTANDING_BYTES`、窗口比较和请求有效信号区分,不需要建立互斥的等待状态。主端内部会话状态必须满足:`M_WAIT_STATUS`和`M_RETRAIN`时`master_session_ready=0`;`M_TRANSPORT_RUN`、`M_RETX_PREP`、`M_RETX_SEND`和`M_RETX_WAIT`属于同一个有效会话,保持`master_session_ready=1`。重传期间是否接受新的业务发送帧由`app_tx_ready`单独控制,不得通过撤销`master_session_ready`表示普通反压。
`M_RETX_PREP`按以下规则冻结本轮重传范围:
```text
RETX_END = 当前SND_NXT
RETX_PTR = 当前SND_UNA
```
只要`RETX_PTR != RETX_END`,主端就从`RETX_PTR`开始依次重传,直至`RETX_END-1`。这些帧已经占用窗口额度,重传时不得再次扣减窗口,也不得根据当前`AVAILABLE_BYTES`缩小重传范围。进入本状态后若发现`OUTSTANDING_BYTES > PEER_WIN_BYTES`,必须按第32.7.2节作为窗口承诺一致性故障处理。
#### 35.2.2 状态图
```mermaid
stateDiagram-v2
[*] --> M_WAIT_STATUS
M_WAIT_STATUS --> M_TRANSPORT_RUN: 收到格式和CRC合法的初始ACK/UPDATE
M_WAIT_STATUS --> M_WAIT_STATUS: T_POLL_INTERVAL无合法状态 / 请求POLL
M_TRANSPORT_RUN --> M_TRANSPORT_RUN: 新业务帧完成或合法ACK更新
M_TRANSPORT_RUN --> M_TRANSPORT_RUN: OUTSTANDING_BYTES=0且窗口不足 / 启动T_POLL_INTERVAL
M_TRANSPORT_RUN --> M_TRANSPORT_RUN: T_POLL_INTERVAL到期 / POLL_PENDING=1
M_TRANSPORT_RUN --> M_TRANSPORT_RUN: POLL_REQ发送完成且窗口仍不足 / 重启T_POLL_INTERVAL
M_TRANSPORT_RUN --> M_TRANSPORT_RUN: 合法状态但窗口仍不足 / 重启T_POLL_INTERVAL
M_TRANSPORT_RUN --> M_TRANSPORT_RUN: 合法状态且窗口足够 / 停止问询并恢复首次发送
M_TRANSPORT_RUN --> M_RETX_PREP: 合法RETRY_REQ且仍有未确认帧
M_TRANSPORT_RUN --> M_RETX_PREP: 未确认帧T_PROGRESS_LIMIT无进展
M_RETX_PREP --> M_RETX_SEND: 已锁存非空重传范围
M_RETX_PREP --> M_TRANSPORT_RUN: ACK已确认全部发送帧
M_RETX_PREP --> M_RETRAIN: 重传缓存一致性检查失败
M_RETX_SEND --> M_RETX_SEND: 重传帧完成且冻结范围仍有帧
M_RETX_SEND --> M_RETX_WAIT: 范围结束且本轮无ACK进展
M_RETX_SEND --> M_TRANSPORT_RUN: 在途帧结束且全部确认或本轮有进展
M_RETX_SEND --> M_RETRAIN: 重传缓存读取失败
M_RETX_WAIT --> M_TRANSPORT_RUN: ACK推进且不需新重传轮次
M_RETX_WAIT --> M_RETX_WAIT: RETRY_REQ但ACK未推进 / 合并且保持计时
M_RETX_WAIT --> M_RETX_PREP: RETRY_REQ且ACK推进仍有未确认帧 / 新轮次
M_RETX_WAIT --> M_RETX_PREP: T_PROGRESS_LIMIT无进展且失败次数小于3
M_RETX_WAIT --> M_RETRAIN: T_PROGRESS_LIMIT无进展且形成第3次连续失败
M_WAIT_STATUS --> M_RETRAIN: link_up撤销
M_TRANSPORT_RUN --> M_RETRAIN: link_up撤销或窗口承诺故障
M_RETX_PREP --> M_RETRAIN: link_up撤销或窗口承诺故障
M_RETX_SEND --> M_RETRAIN: link_up撤销或窗口承诺故障
M_RETX_WAIT --> M_RETRAIN: link_up撤销或窗口承诺故障
M_RETRAIN --> M_WAIT_STATUS: 已观察link_up=0后再次置位 / 请求POLL
```
本状态图用于表示主要控制路径;窗口与ACK计时模式切换、同周期事件优先级及全部寄存器动作以第35.2.3节和第35.2.4节为准。
#### 35.2.3 规范性转移与动作
| 当前状态 | 事件和条件 | 寄存器及控制动作 | 下一状态 |
|---|---|---|---|
| 任意非`M_RETRAIN`状态 | `link_up=0` | 按第26.2节中止当前会话;清零序号、窗口和协议计时,清空描述符及重传缓存,撤销`session_ready`,并对每个已接受但尚未形成最终结果的业务请求报告一次中止;所有清空动作遵守第26.2.3节在途存储延迟回收及结果保留规则 | `M_RETRAIN` |
| 已初始化的非`M_RETRAIN`状态 | 收到合法状态`CTRL` | 按第14.2节及第31.6节检查ACK和窗口后解释`FLAGS`;`M_WAIT_STATUS`不执行此通用分支 | 按下列事件判断 |
| `M_WAIT_STATUS` | 收到格式和CRC合法的初始ACK/UPDATE | 绕过运行期ACK合理性检查;原子设置`SND_UNA=ACK_NEXT`和`SND_NXT=ACK_NEXT`,保持`OUTSTANDING_BYTES=0`及重传缓存为空;装载`PEER_WIN_BYTES`并清除本次`POLL_REQ`等待 | `M_TRANSPORT_RUN`,即使`WIN_BYTES`为0 |
| `M_WAIT_STATUS` | `T_POLL_INTERVAL`无合法状态 | 置位`POLL_PENDING`;保持当前新会话初始状态不变 | `M_WAIT_STATUS` |
| `M_TRANSPORT_RUN` | `OUTSTANDING_BYTES==0`且队首待发送帧`FRAME_COST > AVAILABLE_BYTES` | 保持该请求未分配`SEQ`且不写重传缓存;按第32.6.1节启动单纯窗口问询计时 | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 单纯窗口问询达到`T_POLL_INTERVAL`且窗口仍不足 | 置位一次`POLL_PENDING`并暂停窗口问询计时;不得启动重传相关计时或失败计数 | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 单纯窗口等待中收到合法状态`CTRL` | 更新窗口并重新计算`AVAILABLE_BYTES`;足够时停止问询并恢复首次发送;不足时取消尚未上线的窗口查询并重新开始完整`T_POLL_INTERVAL` | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 新业务帧完成首次发送 | `OUTSTANDING_BYTES += FRAME_COST`;`SND_NXT++`;若未确认集合由空变为非空则启动进度计时 | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 合法前进ACK | 释放确认前缀,更新`SND_UNA`和窗口,清零失败计数并重新开始或停止进度计时 | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 同确认点`ACK/UPDATE` | 仅更新同一确认点的窗口;不得释放缓存或重置进度计时 | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 合法`RETRY_REQ`且 `ACK_NEXT==SND_NXT` | 执行第32.3节的无重传目标分支,不启动Go-Back-N | `M_TRANSPORT_RUN` |
| `M_TRANSPORT_RUN` | 合法`RETRY_REQ`且仍有未确认帧 | 置位重传启动请求,停止接受新的首次发送请求;若有新业务帧正在发送,等待其完成 | `M_RETX_PREP` |
| `M_TRANSPORT_RUN` | `T_PROGRESS_LIMIT`无ACK进展且存在未确认帧 | 置位重传启动请求,停止接受新的首次发送请求;若有新业务帧正在发送,等待其完成 | `M_RETX_PREP` |
| `M_RETX_PREP` | `ACK_NEXT==SND_NXT` | 不建立重传请求,停止进度计时 | `M_TRANSPORT_RUN` |
| `M_RETX_PREP` | 主端→从端帧仍在发送 | 等待该帧完整结束;若它是首次发送的新业务帧,先完成`SND_NXT`和`OUTSTANDING_BYTES`记账 | `M_RETX_PREP` |
| 任意非`M_RETRAIN`状态 | 合法`CTRL`处理后得到`OUTSTANDING_BYTES > PEER_WIN_BYTES`,或检测到窗口承诺无法兑现 | 报告窗口承诺一致性故障和会话中止;撤销`session_ready`;清空当前协议状态;置位`retrain_request` | `M_RETRAIN` |
| `M_RETX_PREP`或`M_RETX_SEND` | 合法未确认区间内存在描述符或缓存缺失、重复或不可读 | 报告本地传输协议状态损坏和会话中止;撤销`session_ready`;清空当前协议状态;置位`retrain_request` | `M_RETRAIN` |
| `M_RETX_PREP` | 发送器已到帧边界且仍有未确认帧 | 使用此时的`SND_UNA`和`SND_NXT`锁存`RETX_PTR`和`RETX_END`,并清零`ROUND_ACK_PROGRESS`;重传不再次检查或扣减窗口额度 | `M_RETX_SEND` |
| `M_RETX_SEND` | 当前重传帧完整结束 | 释放该帧读取占用;按第30.2节模序号规则,以`ACTIVE_TX_SEQ`+1及最新`SND_UNA`确定下一未确认位置,不重复分配`SEQ`或窗口 | 范围未结束则继续;全部确认则`M_TRANSPORT_RUN`;范围结束且`ROUND_ACK_PROGRESS`则`M_TRANSPORT_RUN`,否则`M_RETX_WAIT`并启动观察期 |
| `M_RETX_SEND` | 收到合法前进ACK | 更新未确认集合、窗口并置`ROUND_ACK_PROGRESS`,清零失败计数;当前帧及`ACTIVE_TX_SEQ`不变,所用缓存延迟回收 | 保持至当前帧结束,再选择下一位置或返回`M_TRANSPORT_RUN` |
| `M_RETX_WAIT` | `T_ACK_WAIT`及随后一个`T_POLL_INTERVAL`到期且无进展 | 置位`POLL_PENDING`;不增加失败计数 | `M_RETX_WAIT` |
| `M_RETX_WAIT` | 合法前进ACK且非仍有未确认帧的RETRY_REQ | 清零失败计数;剩余未确认帧重新按正常计时处理 | `M_TRANSPORT_RUN` |
| `M_RETX_WAIT` | 合法RETRY_REQ且ACK未推进,仍有未确认帧 | 仅合并请求,保持本轮观察期起点和截止时间;不增加失败计数 | `M_RETX_WAIT` |
| `M_RETX_WAIT` | 合法RETRY_REQ且ACK推进,仍有未确认帧 | 本轮成功,清零失败计数,按最新确认点准备新轮次 | `M_RETX_PREP` |
| `M_RETX_WAIT` | `T_PROGRESS_LIMIT`无进展 | 当前轮失败计数加一;小于3时令`RETX_PTR=SND_UNA`开始下一轮;形成第3次连续失败时置位`retrain_request` | 小于3时进入`M_RETX_PREP`,否则进入`M_RETRAIN` |
| `M_RETRAIN` | 本轮已观察到`link_up=0`,随后`link_up`重新置位 | 保持第31.2节规定的初始协议状态;保持`session_ready=0`;置位`POLL_PENDING` | `M_WAIT_STATUS` |
正常状态切换只在完整帧边界改变发送上下文。同步丢失或协议故障时立即终止旧会话,但可信方向的在途帧仍按第26.2.3节排空;其缓存及上下文不能提前复用,排空不产生旧会话成功记账。
重传准备或发送时的重复RETRY_REQ只合并状态,不倒退当前在途帧或增加轮次。`M_RETX_WAIT`收到ACK未推进的合法RETRY_REQ时保持等待,不重启、不暂停、不延长本轮观察期。观察期到期且仍无进展,必须按本轮失败处理,即使同周期收到重复请求。若RETRY_REQ带来合法ACK推进,本轮成功并清零失败计数;仍需重传时按最新确认点进入新轮次,否则返回正常状态。同周期ACK推进抑制失败判定;同一轮最多判败一次。
因此,`RETRY_REQ`或`T_PROGRESS_LIMIT`超时到达时不得立即用旧`SND_NXT`冻结`RETX_END`。若当时正在首次发送新业务帧,必须先等待 `tx_frame_done`,完成该帧的`SND_NXT`和`OUTSTANDING_BYTES`更新,再以更新后的`SND_NXT`冻结重传范围。这样能够保证已经上线的最后一帧不会遗漏在Go-Back-N范围之外。
#### 35.2.4 主端事件优先级
同一时钟周期出现多个事件时,必须按以下顺序处理:
1. `link_up`撤销或本地协议故障引起的会话终止和协议复位;该事件抑制本周期所有较低优先级协议动作;
2. 已经有效的`tx_frame_done`及其发送记账;
3. 合法接收`CTRL`:先做累计ACK和窗口更新,再解释`FLAGS`;
4. `T_ACK_WAIT`、后续`T_POLL_INTERVAL`及`T_PROGRESS_LIMIT`定时事件;
5. 新上层业务请求。
前进ACK与`T_PROGRESS_LIMIT`超时同周期发生时,以前进ACK为准,重置进度计时并抑制本周期的失败判定。合法`RETRY_REQ`中的`ACK_NEXT`必须先释放确认前缀;只有仍有未确认帧且当前状态允许启动新轮次时才进入重传。等待阶段ACK未推进的请求保持原观察期,按第32.8节处理。
ACK进度计时独立于`M_TRANSPORT_RUN`的发送活动。只要存在未确认帧,即使主端仍在窗口内连续发送新帧,也必须继续统计最早未确认帧的无进展时间。初始化等待、没有未确认帧但窗口不足以及ACK进度等待可以复用同一个物理计数器,但必须按第32.6.1节和第33章分别产生事件;不同模式不得同时解释同一个超时事件。进入`M_RETRAIN`时所有协议计时停止并清零,重新训练期间不产生超时事件;恢复后的计时按照第26.2.4节重新启动。
#### 35.2.5 重传期间前进ACK与读取占用
```mermaid
sequenceDiagram
participant P as 主端传输协议层
participant L as 主端数据链路层
participant S as 从端
P->>L: 开始重传,锁存ACTIVE_TX_SEQ
Note over P,L: 当前帧的读取数据保持有效
S->>P: 合法累计ACK向前推进
Note over P: 更新确认点并记录本轮进展<br/>当前帧读取占用暂不释放
P->>L: 继续提供当前帧剩余逻辑字
L->>S: 完整发送当前线路帧和CRC
L->>P: tx_frame_done=1
Note over P: 释放读取占用;按最新确认点<br/>与已发送位置确定后续重传指针
```
ACK释放的是协议上的未确认资格;缓存仍被发送器读取时必须延后回收。不得用新确认点改写当前`ACTIVE_TX_SEQ`,也不得因此跳过尚未发送且未确认的帧。
### 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_TRANSPORT_RUN`提供且满足窗口条件的新业务帧请求。
`POLL_PENDING`允许合并,不能因为同一请求等待多个周期而排队多个`POLL_REQ`。开始发送`POLL_REQ`时清除本次已经覆盖的`POLL_PENDING`;同周期产生的新`POLL_REQ`事件必须继续保留。单纯窗口等待时,窗口问询计时器在该`POLL_REQ`完整发送结束后按第32.6.1节重新启动。下层没有收到本层完整帧请求时如何发送`IDLE`,不属于本状态机。
### 35.4 从端业务接收控制器
从端接收控制器与从端发送调度器并行工作。发送`CTRL`或从端业务帧期间,接收控制器必须继续解析和处理主端→从端帧。
#### 35.4.1 状态定义与状态图
| 状态 | 含义 |
|---|---|
| `S_EXPECT` | 等待`SEQ`等于`RCV_NEXT`的合法业务帧 |
| `S_RETRY_WAIT` | 已发现错误,仍等待同一个`RCV_NEXT`对应的正确业务帧 |
| `S_LINK_HOLD` | 链路不可用或正在重新训练;协议状态保持复位,不处理普通协议帧 |
```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
S_EXPECT --> S_LINK_HOLD: 已公告窗口承诺无法兑现 / retrain_request
S_RETRY_WAIT --> S_LINK_HOLD: 已公告窗口承诺无法兑现 / retrain_request
S_EXPECT --> S_LINK_HOLD: link_up撤销
S_RETRY_WAIT --> S_LINK_HOLD: link_up撤销
S_LINK_HOLD --> S_EXPECT: 本轮已观察link_up为0后重新置位 / 等待POLL_REQ
```
`S_LINK_HOLD`期间不得接受普通`DATA`或`CTRL`。重新训练完成后,保持`RCV_NEXT=0`进入`S_EXPECT`,但在收到合法`POLL_REQ`前不恢复普通业务传输。收到合法`POLL_REQ`只置位`ACK_PENDING`,不改变上述接收状态。`WIN_BYTES`从0恢复为非0时同样只置位`ACK_PENDING`。无效`CTRL`直接丢弃,不改变`RCV_NEXT`、`ACK_PENDING`或`RETRY_PENDING`。
#### 35.4.2 从端事件—动作表
| 当前状态 | 事件和条件 | 必须动作 | 下一状态 |
|---|---|---|---|
| 任意非`S_LINK_HOLD`接收状态 | `link_up=0` | 回滚未完成候选帧;清零`RCV_NEXT`、`ACK_PENDING`和`RETRY_PENDING`,释放未提交接收资源并重新计算`WIN_BYTES`;撤销`session_ready` | `S_LINK_HOLD` |
| 任意非`S_LINK_HOLD`接收状态 | 无法为依据已公告窗口合法发送的期望`SEQ`帧或其重传提供已承诺资源 | 报告窗口承诺一致性故障和会话中止;回滚当前候选帧;撤销`session_ready`;复位当前协议状态并置位`retrain_request` | `S_LINK_HOLD` |
| `S_LINK_HOLD` | 本轮已观察`link_up`=0,随后`link_up`=1 | 保持`RCV_NEXT=0`,根据真实资源重新计算`WIN_BYTES`,等待`POLL_REQ` | `S_EXPECT` |
| `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` |
| 任意非`S_LINK_HOLD`接收状态 | 收到合法`POLL_REQ` | `ACK_PENDING=1` | 状态不变 |
| 任意非`S_LINK_HOLD`接收状态 | `WIN_BYTES`从0恢复为非0 | `ACK_PENDING=1` | 状态不变 |
| 任意非`S_LINK_HOLD`接收状态 | `CTRL`校验或格式失败 | 丢弃`CTRL`,不产生状态更新 | 状态不变 |
#### 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`对应业务帧才能清除它;同步丢失时按第26.2节直接复位该状态。
#### 35.4.4 从端事件优先级
同一时钟周期出现多个事件时,必须按以下顺序形成下一状态:
1. `link_up`撤销或本地协议故障引起的会话终止和协议复位;该事件抑制本周期所有较低优先级协议动作;
2. 本轮已经观察`link_up`=0后,`link_up`重新置位才允许退出保持状态;
3. `DATA`候选帧完成事件,按成功接受或失败丢弃更新`RCV_NEXT`和`RETRY_PENDING`;
4. 合法`POLL_REQ`及`WIN_BYTES`从0恢复事件;
5. 状态`CTRL`开始发送产生的旧快照清除事件;
6. 从端上层无确认业务发送请求。
同一个候选业务帧不得同时报告成功和失败。如果业务帧事件、`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节接收控制器。
会话终止后不开始新的普通`CTRL`或UL `DATA`。可信UL的在途帧仍完整排空,所用数据和快照仅保留至排空结束,不再成为新会话请求;排空产生的`tx_frame_done`不得形成旧会话成功结果。方向不可用时中止并判为不可信。尚未形成最终发送结果的完整业务请求按第45.2节报告中止。
### 35.6 RTL接口事件契约
状态机可以使用不同端口名称,但至少需要等价的内部事件:
| 事件 | 产生位置 | 语义 |
|---|---|---|
| `business_candidate_valid` | `DATA`解析器 | CRC和格式已经通过,字段可供序号与资源检查 |
| `business_candidate_error` | `DATA`解析器或接收控制器 | 第32.2节定义的错误,候选帧不得提交 |
| `ctrl_valid` | 传输协议层`CTRL`检查逻辑 | CRC及第14.2节适用的方向、状态和字段检查通过;POLL占位值被忽略 |
| `frame_tx_start` | 发送调度器 | 完整帧字段已经锁存,本帧不可被抢占 |
| `tx_frame_done` | 发送器 | 单周期脉冲;完整线路帧最后一位已经发送,并关联发送开始时锁存的帧类别及业务`SEQ` |
| `ack_progress` | 主端`CTRL`处理器 | 合法`ACK_NEXT`使`SND_UNA`向前推进 |
| `status_launch` | 从端发送调度器 | 最新状态快照已经锁存并开始发送 |
| `link_up_rise` | 数据链路层接口 | `link_up`从0变为1;传输协议层进入新会话状态查询,但尚不得恢复业务 |
解析器不得在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. 合法`CTRL`处理后若`OUTSTANDING_BYTES > PEER_WIN_BYTES`,或者任一端无法兑现已经公告的窗口承诺,必须按第32.7.2节中止当前会话并触发重新训练。
### 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轮重传无进展时必须报告可靠链路故障及会话中止,并触发重新训练;旧会话缓存按第26.2节清除,不得把未确认帧报告为成功。
2. `RETRY_REQ`的`ACK_NEXT`位于合法未确认区间但对应描述符或缓存缺失、重复或不可读时,必须报告本地传输协议状态损坏和会话中止,并进入`M_RETRAIN`;不得尝试跳过缺失项继续重传。
3. 合法`CTRL`处理后若`OUTSTANDING_BYTES > PEER_WIN_BYTES`,或者任一端无法兑现已经公告的窗口承诺,必须报告一致性故障和会话中止并进入重新训练;不得通过分批重传或等待窗口增大继续旧会话。
4. 从端→主端业务不得进入链路重传或窗口控制状态机。
5. 主端业务缓存满时可以丢弃从端业务帧,但必须继续解析线路并保证`CTRL`接收。
6. 任一方向同步丢失都必须使双方复位传输协议状态;合规从端在新会话初始响应中发送`ACK_NEXT=0`,主端按第46.3节以实际收到的初始值执行防御性对齐。
# 第六篇 分层架构与层间接口
## 37. 数据链路层
### 37.1 负责功能
数据链路层必须负责:
1. 实现与物理承载对接的串行收发、串并转换及相关时钟接口;
2. 实现并控制FPGA SERDES、ASIC串行收发适配电路或功能等价的物理接口;
3. 实现并控制`IDELAY`、`ODELAY`或功能等价的相位或延迟调节单元,使调节范围覆盖至少一个完整`UI`,并完成`UL`采样位置和`DL`发送位置的扫描、判定与配置;
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`相同码字都不得被识别为新边界。
数据链路层必须暂存逻辑帧最后一个字,直到随后线路CRC字已经接收并完成比较;输出该逻辑末字时,必须同时置位`rx_data_last`及`rx_crc_valid`,并输出`rx_crc_pass`的比较结果:通过为1、失败为0。
#### 37.4.4 RX_CRC
CRC字段必须解扰,但不得通过`rx_data`输出。数据链路层比较收到的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
在可信边界或第25.5节恢复候选位置检测到合法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`按第14.2节检查方向、当前状态和适用字段;POLL占位值不检查,其他适用条件合法才执行控制动作。
#### 38.4.2 CRC失败
CRC失败时必须回滚全部候选数据:
| 接收端及方向 | 处理 |
|---|---|
| 从端接收`DL` `DATA` | 不推进`RCV_NEXT`,置`RETRY_PENDING`和`ACK_PENDING` |
| 主端接收`UL` `DATA` | 直接丢弃,不请求重传 |
| 任意端接收`CTRL` | 丢弃`CTRL`,不更新ACK、窗口或重传状态 |
#### 38.4.3 未完成候选帧中止
数据链路层以`rx_frame_abort`报告已经识别`SOF`、但因`LEN`非法或帧中途边界失效等原因无法正常完成的候选帧。传输协议层必须根据已经锁存的候选帧类型和接收方向执行:
| 接收端及候选类型 | 处理 |
|---|---|
| 从端接收`DL DATA` | 回滚候选帧,不推进`RCV_NEXT`,置位`RETRY_PENDING`和`ACK_PENDING` |
| 主端接收`UL DATA` | 回滚并丢弃,不发送确认且不请求重传 |
| 任意端接收`CTRL` | 回滚并丢弃,不更新ACK、窗口或重传状态 |
`rx_frame_abort`只描述当前候选帧不能完成,不单独终止协议会话。数据链路层随后按第25章执行边界恢复;只有恢复失败并撤销`link_up`时,传输协议层才复位整个会话。
### 38.5 `DATA`载荷处理边界
传输协议层不得解析`PAYLOAD`内部的业务字段。`DATA`通过`CRC32`、外层`LEN`、方向相关的`SEQ`和接收资源检查后,即可按第38.7节决定提交或回滚。
业务应用层判定的命令非法、地址越界、权限不足或执行失败,不属于传输协议错误,不得触发`RETRY_REQ`、回滚已提交帧或改变`RCV_NEXT`。需要业务响应时,由业务应用层生成新的`DATA`载荷。
### 38.6 `CTRL`检查
`CTRL`检查的唯一字段及方向定义见第14.2节。数据链路层只提供候选流和CRC结论;传输协议层在CRC通过后执行适用检查,`RESERVED`始终忽略,POLL_REQ的`ACK_NEXT`和`WIN_BYTES`不进行数值或对齐检查。
`M_WAIT_STATUS`只接受初始ACK/UPDATE,并先于运行期通用`CTRL`分支处理;初始响应不使用运行期已发送区间检查。合法初始响应完成会话初始化,即使窗口为0也进入正常传输控制状态,`DATA`等待则按第32.6.1节执行。
### 38.7 协议接受条件
`DL DATA`的接受条件为:
```text
DL_ACCEPT = CRC通过
AND 外层格式合法
AND SEQ == RCV_NEXT
AND 从端接收资源足够
```
`UL DATA`向业务应用层提交的条件为:
```text
UL_DELIVER = CRC通过
AND 外层格式合法
AND 主端业务接收资源足够
```
`UL`采用无确认接收。主端不得因`SEQ`跳变或重复拒绝CRC和格式正确的帧;主端业务接收资源不足时,可以丢弃该完整候选帧,但必须继续消费线路数据、维持帧边界,不发送确认且不请求重传。
`CTRL`必须按第38.6节根据`FLAGS`、方向和当前状态分别判定,不得使用一个统一的`ACK_NEXT`合理性条件处理全部`CTRL`。
### 38.8 接收暂存和提交
数据链路层不缓存完整帧,因此传输协议层必须提供:
- 整帧暂存RAM/FIFO;或者
- 行为等价的提交/回滚缓存。
候选帧处理顺序为:
```text
rx_data_valid → 写候选暂存区
rx_data_last && rx_crc_valid && rx_crc_pass → 候选数据接收完成并取得CRC通过结论
rx_data_last && rx_crc_valid && !rx_crc_pass → 回滚CRC失败候选帧
协议检查 → 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
从端数据链路层:
SOF → 解扰 → 外层LEN → 流式输出 → CRC通过
↓
从端传输协议层:
候选暂存 → SEQ==RCV_NEXT → 资源检查 → commit
↓
从端业务应用层:
接收DATA载荷并按用户业务定义处理
```
### 40.2 `DL` CRC失败
```text
从端数据链路层:rx_crc_valid=1,rx_crc_pass=0
↓
从端传输协议层:rollback,不推进RCV_NEXT
↓
置RETRY_PENDING和ACK_PENDING
↓
通过UL发送RETRY_REQ
```
### 40.3 `UL` CRC失败
```text
主端数据链路层:rx_crc_valid=1,rx_crc_pass=0
↓
主端传输协议层:rollback并直接丢弃
↓
不发送ACK,不请求重传
```
### 40.4 外层`LEN`错误
```text
数据链路层:检测OUTER_LENGTH_ERROR并产生rx_frame_abort
↓
传输协议层:回滚当前候选帧
├─ 从端接收DL DATA:RETRY_PENDING=1,ACK_PENDING=1
├─ 主端接收UL DATA:丢弃,不请求重传
└─ CTRL:丢弃,不更新协议状态
↓
数据链路层进入边界恢复;恢复失败时撤销link_up
```
### 40.5 `DATA`载荷的业务处理
```text
数据链路层:外层LEN合法且CRC通过
↓
传输协议层:完成SEQ与资源检查并提交DATA载荷
↓
业务应用层:按用户定义解释和执行载荷
```
业务应用层发现载荷语义错误或执行失败时,由用户业务自行处理。该结果不得使传输协议层撤销已经完成的累计确认,也不得触发链路重传或重新训练。
## 41. 分层实现一致性要求
1. 数据链路层必须独立解析外层`LEN`,以确定帧结束和CRC位置。
2. 数据链路层不得要求传输协议层返回帧结束位置。
3. `rx_data_valid`期间的数据必须被视为候选数据,CRC通过前不得提交。
4. 每个正常结束的候选帧必须在逻辑末字周期产生一次且仅一次`rx_crc_valid`,并使`rx_data_last`与`rx_crc_valid`同周期有效。
5. 外层`LEN`非法而无法定位CRC时,必须产生`rx_frame_abort`;该候选帧不再产生`rx_data_last`或`rx_crc_valid`。
6. 接收接口不得使用能够暂停物理数据流的反压。
7. 发送接口必须具有帧开始前及帧间反压能力。
8. 一帧开始后不得在帧内暂停tx_data流。
9. 数据链路层必须生成CRC和扰码;传输协议层不得重复实现CRC。
10. `DATA`载荷的全部业务语义和执行结果必须由业务应用层处理。
11. 主端重传缓存必须保存CRC生成前、加扰前的协议帧内容。
12. `FRAME_COST`必须按不含CRC的逻辑帧长度计算,不得按重传RAM实际存储字节数计算。
13. `DL`和`UL`名称必须按第3章固定方向使用,不得相对当前端点反转含义。
14. 任一方向同步丢失都必须终止当前会话并清除传输协议状态;合规从端在新会话初始响应中发送`ACK_NEXT=0`。主端仍按第46.3节以实际收到的初始`ACK_NEXT`执行防御性对齐。
## 42. 层间接口阅读与实现规则
第37~41章定义分层职责和处理契约,第43~46章定义具体接口。接收候选流、最终CRC结果和协议提交是不同阶段;发送请求接受、线路发送完成和业务结果形成也是不同阶段。具体信号时序以第43~46章为准,不从概念流程图推导额外端口。
物理实现的眼图预算及实现风险集中见第7.6节;第26.2.3节定义会话终止、可信在途排空和结果保留,接口章节引用这些规则而不改变它们。典型业务应用仍在第39.3节,其载荷语义不增加基础传输层义务。
## 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_data[31:0]` | 数据链路层→传输协议层 | 解扰后的候选帧字,包含`SOF`和协议字段,不包含CRC |
| `rx_data_valid` | 数据链路层→传输协议层 | 当前`rx_data`属于候选帧 |
| `rx_data_last` | 数据链路层→传输协议层 | 当前字是逻辑帧的最后一个字;正常结束时必须与`rx_crc_valid`同周期有效 |
| `rx_crc_valid` | 数据链路层→传输协议层 | 当前候选帧的CRC结果有效;必须与该候选帧的`rx_data_last`同周期有效 |
| `rx_crc_pass` | 数据链路层→传输协议层 | 在`rx_crc_valid`有效时表示CRC比较结果 |
| `rx_frame_abort` | 数据链路层→传输协议层 | 已经开始输出的候选帧无法正常完成;包括`LEN`非法或帧中途进入边界恢复,协议层必须立即回滚该候选帧 |
链路可用状态使用第46.1节定义的`link_up`电平表示。`link_up=0`时,协议层必须回滚所有未完成候选帧并复位当前会话,因此链路层不需要再用`rx_frame_abort`重复报告同步丢失。
### 43.3 错误表示规则
接收错误必须按以下方式唯一表示:
| 情况 | 接口表示 | 协议层动作 |
|---|---|---|
| 外层`LEN`非法 | `rx_frame_abort=1` | 立即回滚且不再等待`rx_data_last`或`rx_crc_valid`;从端的`DL DATA`按业务帧错误置位`RETRY_PENDING`和`ACK_PENDING`,主端的`UL DATA`及任意`CTRL`直接丢弃 |
| CRC校验失败 | `rx_crc_valid=1`且`rx_crc_pass=0` | 丢弃已完整输出的候选帧;是否产生`RETRY_REQ`由传输协议状态决定 |
| 边界异常但恢复成功 | `link_up`保持为1;若打断已输出候选则产生一次`rx_frame_abort`,否则无候选中止事件 | 回滚被打断候选,不复位会话;恢复候选可按正常协议检查处理 |
| 边界恢复失败、同步丢失或链路资源不可用 | `link_up=0` | 回滚所有未完成候选帧并按第26.2节复位当前会话 |
`rx_frame_abort`只终止当前候选帧,不表示链路失步。边界错误类型、同步丢失原因及资源故障原因可以保存在链路层诊断寄存器或计数器中,但不得作为传输协议状态机的额外控制输入。
<a id="req-if-001"></a>
### 43.4 接口时序
关键要求编号:`REQ-IF-001`。
普通`DATA`或`CTRL`候选帧(包括恢复搜索命中的普通候选)使用以下接口时序:
```text
接口周期: 0 1 2 ... N
rx_data: SOF 协议字段 PAYLOAD/字段末字
rx_data_valid: 1 1 1
rx_data_last: 0 0 1
rx_crc_valid: 0 0 1
rx_crc_pass: X X PASS/FAIL
```
线路上的CRC字位于逻辑末字之后。为了形成上述接口时序,数据链路层必须暂存逻辑末字,在收到并比较CRC字后,同时输出该末字、`rx_data_last`、`rx_crc_valid`和`rx_crc_pass`。`rx_crc_pass`仅在`rx_crc_valid=1`时有效。
这一对齐只需要末字及相关CRC状态的流水暂存,不要求数据链路层缓存完整帧。CRC字所在的线路周期不向协议层输出`rx_data`,因此可以用于输出暂存末字;实现必须同时支持CRC后立即到来的下一帧`SOF`或`IDLE`,不得降低连续线路帧的吞吐率。
协议层必须在末字周期原子处理结果:`rx_crc_pass=1`时才允许继续进行`SEQ`、资源和控制字段检查;`rx_crc_pass=0`时回滚整个候选帧。外层`LEN`非法或已输出候选中途无法完成时,必须产生一次`rx_frame_abort`;该候选不再产生`rx_data_last`或`rx_crc_valid`。`rx_frame_abort`与末字CRC结论互斥。正常末字必须同时满足`rx_data_valid`=1。
#### 43.4.1 接收完成与中止时序示意
```mermaid
sequenceDiagram
participant L as 数据链路层
participant P as 传输协议层
L->>P: SOF及逻辑字段,rx_data_valid=1
Note over P: 候选暂存;尚未提交
alt 候选完整接收
L->>P: 同周期输出末字、valid=1、last=1、crc_valid=1
alt crc_pass=1
Note over P: 执行协议检查;全部通过才提交
else crc_pass=0
Note over P: 回滚候选;不输出业务载荷
end
else 已输出候选但无法完成
L->>P: rx_frame_abort=1,单次事件
Note over P: 回滚候选;该候选无last或CRC结论
end
```
图中的valid、last和CRC信号均为`rx_`接收接口信号;帧内可提前输出的字仅属于候选流。候选CRC通过不等于协议接受,最终接受事件必须等待全部协议条件通过。
### 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_valid && tx_data_ready && tx_data_last`只表示数据链路层已经接受逻辑帧的最后一个字。数据链路层仍须生成、追加、扰码并发送CRC;只有CRC最后一位完成线路发送后,才能产生`tx_frame_done`。
`tx_frame_done`必须是发送接口时钟域中的单周期脉冲,并满足:
1. 正常发送及可信方向在途排空时,每个完整发送的`DATA`或`CTRL`产生一次且仅一次`tx_frame_done`;`link_up`=0排空期间该事件仅释放读取占用,不形成协议成功;
2. `tx_frame_done`必须晚于对应帧的`tx_data_last`握手,不得与尚未接受完整逻辑帧的请求关联;
3. 每个方向只允许存在一个已经由数据链路层接受、但尚未产生`tx_frame_done`的普通逻辑帧;传输协议层必须从该帧`SOF`握手起保存帧类别、业务`SEQ`及请求上下文,直至收到按序返回的`tx_frame_done`;会话中止但可信方向仍在排空时须继续保留读取上下文,资源失效中止则释放该上下文;数据链路层无需接收或返回帧标识;
4. 未完成CRC发送的帧、被中止的帧以及仅完成`tx_data_last`握手的帧不得产生有效完成事件;
5. 新帧可以在`tx_frame_done`同周期或后续周期开始,但新帧的锁存信息不得覆盖本周期完成事件对应的信息;
6. `link_up`撤销与`tx_frame_done`同周期发生时,会话终止具有最高优先级,该完成脉冲不得推进旧会话序号或产生业务成功结果,但必须允许结束发送上下文并回收不再使用的存储。
确定性时序示例如下:
```text
周期: N N+1或更晚
tx_data_valid: 1 0
tx_data_ready: 1 X
tx_data_last: 1 0
tx_frame_done: 0 1
事件: 逻辑末字握手 CRC最后一位完成发送
```
重传计时、首次发送记账、重传指针推进、状态`CTRL`上线确认、`POLL_REQ`间隔重启,以及无确认方向的线路发送完成通知,均必须以有效的`tx_frame_done`脉冲为边界。`tx_data_ready`只表示逻辑字接受能力,不得代替`tx_frame_done`。
### 44.5 会话终止时的可信在途帧排空
```mermaid
sequenceDiagram
participant P as 传输协议层
participant L as 数据链路层
participant R as 对端
P->>L: 当前普通帧已开始发送
L->>P: link_up=0
Note over P: 立即终止旧会话;禁止新业务帧<br/>保留发送器仍在读取的存储
alt 当前发送方向仍可信且资源可用
P->>L: 仅提供当前帧尚未接受的逻辑字
L->>R: 发送到完整CRC边界
L->>P: tx_frame_done=1
Note over P: 仅清理读取占用;不产生旧会话成功
else 当前发送方向资源失效
Note over P,L: 中止发送并结束读取上下文<br/>不要求继续发送,不产生tx_frame_done
end
```
会话终止、可信排空与资源失效的权威规则见第26.2节;该图不授权在`link_up=0`期间启动新的普通帧。
## 45. 传输协议层与业务应用层接口
业务应用层与传输协议层之间使用两组独立的32位流式数据接口:一组用于业务发送,一组用于业务接收。接口只传输`DATA PAYLOAD`,不传输`SOF`、`SEQ`、`LEN`、CRC或扰码后的内容。
### 45.1 业务发送流接口
```text
app_tx_data[31:0]
app_tx_valid
app_tx_ready
app_tx_last
```
| 信号 | 方向 | 定义 |
|---|---|---|
| `app_tx_data[31:0]` | 业务应用层→传输协议层 | 当前32位有效载荷字 |
| `app_tx_valid` | 业务应用层→传输协议层 | 当前`app_tx_data`有效 |
| `app_tx_ready` | 传输协议层→业务应用层 | 传输协议层能够接受当前有效载荷字 |
| `app_tx_last` | 业务应用层→传输协议层 | 当前字是本业务帧有效载荷的最后一个字 |
一次数据传输在`app_tx_valid && app_tx_ready`时发生。业务应用层必须提供1~258个完整32位字,并在最后一个字上置位`app_tx_last`,因此协议层计数得到的`LEN`自然满足`4 <= LEN <= 1032`且为4字节整数倍。接口不支持不足32位的末字。
传输协议层根据成功握手的字数生成`LEN`。在业务帧起始位置,只有同时满足以下条件时才允许置位`app_tx_ready`:
1. `session_ready=1`;
2. 当前没有正在接收的业务发送帧;
3. 本地请求缓存至少能够保存一个最大1032 B有效载荷及其内部描述信息。
一旦业务帧第一个字完成握手,传输协议层必须为该帧保留最大载荷缓存,并保持`app_tx_ready=1`直至最后一个字完成握手;即使内部`session_ready`在帧中途撤销,也必须继续接收该帧。允许业务应用层在帧内暂时撤销`app_tx_valid`;传输协议层不得把数据间隙解释为帧结束。
最后一个字完成握手表示完整业务请求已经被传输协议层接受并保存。此前不得为该请求分配业务`SEQ`、建立重传描述符或产生发送完成结果。如果内部`session_ready`在首字握手后、末字握手前曾经撤销,协议层必须锁存本帧的中止标志;末字握手后不得为该帧分配`SEQ`或发送到新会话,而应按接受顺序产生一次`app_tx_aborted`。`session_ready`撤销与末字握手同周期发生时同样按中止处理。
窗口不足只阻止协议层把已经接受的业务请求首次发送到链路,不得破坏已经完成接口握手并保存的请求。协议层可以在本地请求缓存允许的范围内继续接受后续业务帧;缓存不足时在下一帧开始前拉低`app_tx_ready`。
<a id="req-if-002"></a>
### 45.2 发送结果接口
关键要求编号:`REQ-IF-002`。
业务发送流接口的最后一个字握手只表示请求已经被协议层完整接受,不表示该请求已经达到传输完成条件。发送结果使用两个独立事件信号:
```text
app_tx_completed
app_tx_aborted
```
| 信号 | 方向 | 定义 |
|---|---|---|
| `app_tx_completed` | 传输协议层→业务应用层 | 单周期脉冲;最早一个尚未报告结果的已接受业务请求达到完成条件 |
| `app_tx_aborted` | 传输协议层→业务应用层 | 单周期脉冲;最早一个尚未报告结果的已接受业务请求因会话终止而中止 |
结果接口必须满足:
1. `app_tx_completed`和`app_tx_aborted`均为业务接口时钟域中的单周期脉冲,同一周期不得同时置位;
2. 每个已经完整接受的业务请求必须产生一次且仅产生一次结果,同一请求不得同时报告完成和中止;
3. 结果严格按照完整业务帧在发送流接口上的接受顺序输出,因此不需要请求标签;
4. `DL`业务帧在对应`SEQ`被累计ACK确认后形成完成结果;`UL`业务帧在产生有效`tx_frame_done`后形成完成结果,该结果不保证主端接收成功;
5. 已接受请求在完成结果形成前遇到会话终止时形成中止结果;已形成并排队等待输出的完成结果不可改为中止;业务应用层依据自身语义决定是否在新会话中重新提交;
6. 业务应用层必须在每个周期接收结果,本接口不提供反压;
7. 如果一次累计ACK或会话终止同时形成多个结果,传输协议层必须暂存尚未输出的结果,并按接受顺序每周期最多输出一个,不得覆盖或丢失;结果队列不因协议会话复位而清空,只有全局硬件复位可初始化;
8. 接口跨时钟域时,实现必须增加可靠的事件同步或异步队列,不得直接跨时钟传递单周期脉冲。
#### 45.2.1 结果排队与会话终止
```mermaid
sequenceDiagram
participant A as 业务应用层
participant P as 传输协议层
Note over P: 请求A的成功结果已形成并排队<br/>请求B已接受但尚未完成
Note over P: link_up撤销,旧会话终止
P->>A: app_tx_completed=1:请求A
P->>A: 后续周期app_tx_aborted=1:请求B
Note over A,P: 按接受顺序,每周期最多一个结果<br/>协议会话复位不清空结果队列
```
只有会话终止前已经形成的成功结果能够继续输出。会话终止与ACK或线路完成同周期时,按会话终止优先级处理,不为未完成请求形成新的成功结果。
<a id="req-if-003"></a>
### 45.3 业务接收流接口
关键要求编号:`REQ-IF-003`。
```text
app_rx_data[31:0]
app_rx_valid
app_rx_ready
app_rx_last
```
| 信号 | 方向 | 定义 |
|---|---|---|
| `app_rx_data[31:0]` | 传输协议层→业务应用层 | 当前32位有效载荷字 |
| `app_rx_valid` | 传输协议层→业务应用层 | 当前`app_rx_data`有效 |
| `app_rx_ready` | 业务应用层→传输协议层 | 业务应用层能够接受当前有效载荷字 |
| `app_rx_last` | 传输协议层→业务应用层 | 当前字是本业务帧有效载荷的最后一个字 |
一次数据传输在`app_rx_valid && app_rx_ready`时发生。该接口只输出已经通过CRC、格式、序号及资源检查并完成协议提交的`PAYLOAD`,不得输出候选帧、协议头或CRC字段。
业务应用层可以通过`app_rx_ready`实施反压。反压期间传输协议层必须保持`app_rx_valid`和`app_rx_data`稳定,并保留尚未输出的完整业务帧;从端据此维护并公告`WIN_BYTES`。一帧开始输出后允许在任意字处暂停,帧边界仅由`app_rx_last`确定。协议会话终止不能丢弃已提交数据或截断正在交付的帧;输出及反压保持规则持续到末字握手,保留的数据占用必须计入新会话实际可用资源。
#### 45.3.1 已提交接收数据的反压与会话终止
```mermaid
sequenceDiagram
participant P as 传输协议层
participant A as 业务应用层
P->>A: 已提交载荷,app_rx_valid=1
A->>P: app_rx_ready=0
Note over P,A: 保持valid、data和last稳定
Note over P: link_up撤销;候选流回滚<br/>已提交载荷继续保留
A->>P: app_rx_ready=1
P->>A: 继续交付载荷,直至末字握手
Note over P: 释放对应存储;新会话窗口<br/>按仍保留的数据占用计算
```
该保留规则适用于协议会话复位,不改变全局硬件复位的初始化语义。
## 46. 链路状态与恢复接口
### 46.1 数据链路层向传输协议层
协议控制只依赖以下功能信号:
```text
link_up
```
| 信号 | 含义 |
|---|---|
| `link_up` | 电平为1表示`UL`、`DL`及运行入口过程均已完成,数据链路层能够正常收发普通协议帧;电平为0表示数据链路层未就绪,传输协议层必须保持会话复位状态 |
`link_up`必须是协议层可见的聚合电平:
```text
link_up = ul_sync_up && dl_sync_up && run_entry_complete
```
普通帧因发送资源失效而无法完成CRC末位时,不产生`tx_frame_done`,并撤销`link_up`、将该方向判为不可信。若`link_up`因另一方向异常或协议故障已撤销,而当前方向仍可信,则继续排空当前线路帧;排空完成仍可产生`tx_frame_done`用于释放发送上下文,但不能推进旧会话记账或形成成功结果。
`link_up`从1变为0时,传输协议层必须立即按第26.2.3节终止并复位当前会话;`link_up`=0期间不得开始新普通帧或接受普通接收候选,可信在途发送仅按第26.2.3节排空,不运行协议定时器。`link_up`重新变为1后,主端进入`M_WAIT_STATUS`并发起初始`POLL_REQ`,从端进入`S_EXPECT`并等待该请求。`ul_sync_up`、`dl_sync_up`、`sync_lost`、`retrain_busy`和`retrain_done`可以作为数据链路层内部状态或诊断输出,但不得作为传输协议状态机的独立控制输入。
### 46.2 传输协议层向数据链路层
```text
retrain_request
```
`retrain_request`是保持型请求,采用以下确定性握手:
1. 传输协议层因连续重传失败、缓存一致性故障或窗口承诺故障要求重新训练时,置位`retrain_request`并进入`M_RETRAIN`或`S_LINK_HOLD`;
2. 数据链路层接受请求后必须先撤销`link_up`,锁存本次重新训练请求,并按第26.2.2节执行统一的完整训练入口;保持为1的请求不得重复启动新的训练轮次;
3. 传输协议层观察到`link_up=0`后才允许撤销`retrain_request`,并记录本次重新训练已经经过链路不可用阶段;
4. 数据链路层完成规定的重新训练和运行入口过程后重新置位`link_up`;
5. 协议层只有在已经观察到本次`link_up=0`、随后又观察到`link_up=1`时,才能退出重新训练保持状态并开始新会话初始化。
主端数据链路层处理retrain_request时,经统一入口终止旧会话并排空可信在途帧;DL具备完整固定帧发送条件时先连续完整发送20个SYNC_RESET,随后从M_RX_TRAIN开始完整UL→DL训练,资源异常时按第26.2.2节处理。从端处理本地retrain_request时,撤销link_up、终止旧会话并排空可信UL在途帧,然后直接持续发送TRAIN;主端运行期收到完整TRAIN即执行完整重训练,不需要人为异常码流或额外CTRL通知。从端不得在重新训练期间开始旧会话新普通帧。上述通知不触发全局复位,也不需要增加协议层请求接口。
### 46.3 新会话恢复门控
传输协议层内部维护`session_ready`,用于表示业务序号、窗口及控制帧通路已经完成新会话初始化。该状态不是层间端口,也不要求输出给业务应用层;业务发送能力必须统一反映到`app_tx_ready`。
进入重新训练时,传输协议层必须停止新普通协议帧请求及接收接受并执行第26.2.3节的协议复位,同时清零内部`session_ready`。任一重新训练均执行完整UL→DL流程;仍可信的发送方向仅允许按第26.2.3节排空旧在途帧,之后只承载训练过程规定的固定帧,不能开始原会话普通帧。
`link_up`重新置位后,主端进入`M_WAIT_STATUS`并发送`POLL_REQ`;从端必须以`ACK_NEXT=0`和当前真实接收容量返回初始状态。主端必须确认响应为CRC和格式合法的初始`ACK/UPDATE`,但不以`ACK_NEXT`的具体取值决定是否进入`M_TRANSPORT_RUN`;主端把收到的值作为新会话起始序号,同时设置`SND_UNA`和`SND_NXT`,不得把它按运行期累计ACK处理。
主端内部状态按以下规则维护:
```text
M_WAIT_STATUS、M_RETRAIN:
master_session_ready = 0
M_TRANSPORT_RUN、M_RETX_PREP、M_RETX_SEND、M_RETX_WAIT:
master_session_ready = link_up
```
进入普通重传状态不终止当前会话,因此不得清零`master_session_ready`。重传期间如果暂时禁止接受新的业务发送帧,只拉低`app_tx_ready`。
从端在`link_up`重新置位后保持`slave_session_ready=0`并等待初始`POLL_REQ`。针对该请求的初始状态`CTRL`产生有效`tx_frame_done`后,置位`slave_session_ready`;进入`S_RETRY_WAIT`不终止会话,因此保持该状态。进入`S_LINK_HOLD`、检测到协议一致性故障或`link_up=0`时清零。
在新业务帧边界,协议层只能在内部`session_ready=1`且本地请求缓存满足第45.1节要求时置位`app_tx_ready`。业务应用层不需要也不得依赖`session_ready`;它只根据`app_tx_valid/app_tx_ready`握手提交数据,并通过`app_tx_completed`或`app_tx_aborted`获得最终结果。
从端发送非零初始`ACK_NEXT`属于不符合本规范的行为,主端可以记录诊断信息;但为避免序号冲突,只要响应帧本身合法,主端仍必须把该值作为新会话起始序号,并使用其中的`WIN_BYTES`完成初始化。这一赋值不恢复任何旧会话状态。
### 46.4 层间接口通用时序规则
1. 每组层间接口必须在具体实现中声明所属时钟域和复位极性;跨时钟域时必须使用可靠的同步器、握手或异步队列,不得直接跨域传递单周期事件。
2. `link_up`和`retrain_request`为保持型电平;`rx_frame_abort`、`rx_crc_valid`、`tx_frame_done`、`app_tx_completed`和`app_tx_aborted`为各自接口时钟域中的单周期事件。
3. 对带`valid/ready`握手的发送接口,发送方在`valid=1 && ready=0`期间必须保持`data`和`last`稳定;一次传输只在`valid && ready`同周期有效时发生。
4. 全局硬件复位期间valid、所有结果事件及`link_up`为0,并初始化接口队列。协议会话复位不同于全局复位:`session_ready`为0,不接受新请求;已开始的业务输入继续接至末字,已提交接收数据继续交付,已形成结果和新形成中止结果仍按顺序输出,可信方向在途帧继续排空。恢复普通新请求须完成训练和会话初始化。
5. `link_up`撤销或本地协议故障与`tx_frame_done`、接收完成、ACK或定时器到期同周期时,会话终止优先,不形成新的旧会话成功结果。此前已经形成的完成结果不撤销;`tx_frame_done`仍可用于结束可信排空和回收所用存储。
# 第七篇 实现、诊断与验证
## 47. RTL实现输出与诊断契约
### 47.1 强制功能状态
每个端点必须向其传输协议层提供第46章定义的`link_up`。如果业务应用层或系统管理逻辑需要判断整个传输通路是否可提交新业务,应使用`app_tx_ready`或实现提供的等价业务就绪状态,不得把`link_up`单独解释为新会话已经初始化完成。
### 47.2 诊断可观察性
除`link_up`功能接口外,表中项目不要求全部实现为RTL顶层端口。实现可以通过状态寄存器、调试总线、片上逻辑分析、仿真层次信号或功能等价的方式提供,但必须在实现声明中说明读取方式、位宽、时钟域及编码。
| 诊断项目 | 适用角色 | 含义 |
|---|---|---|
| `retrain_busy` | 主端、从端 | 当前正在执行训练、重新训练或运行入口过程 |
| `master_link_state / master_transport_state` | 主端 | 分别报告链路状态及传输协议状态,编码与映射独立 |
| `slave_link_state / slave_transport_state` | 从端 | 分别报告链路状态及传输协议状态,编码与映射独立 |
| `monitor_state` | 主端、从端 | 本端接收方向的运行期监测状态 |
| `rx_delay_selected` | 具有UL可调接收延迟的主端 | 最终选择的UL接收延迟点 |
| `tx_delay_selected` | 具有DL可调发送延迟的主端 | 最终选择的DL发送延迟点 |
| `rx_pass_first/last` | 具有UL扫描能力的主端 | UL所选通过窗口边界;`ALL_PASS`时同时报告对应状态 |
| `tx_pass_first/last` | 具有DL扫描能力的主端 | DL所选通过窗口边界;`ALL_PASS`时同时报告对应状态 |
| `rx_pass_bitmap / tx_pass_bitmap` | 具有对应扫描能力的主端 | 最近一次完整扫描结果 |
| `fixed_frame_error_count` | 主端、从端 | 在要求完整匹配固定帧的状态中发生的固定帧比较失败数 |
| `crc_error_count` | 主端、从端 | 本端接收方向到达预期CRC位置但CRC比较失败的普通帧数 |
| `length_error_count` | 主端、从端 | 本端接收方向的外层`LEN`非法数 |
| `boundary_recovery_count` | 主端、从端 | 进入`MON_RECOVERY`的次数 |
| `retrain_count` | 主端、从端 | 实际开始的新训练或重新训练轮次 |
| `last_retrain_reason` | 主端、从端 | 最近一次训练入口原因 |
| `resource_fault` | 按实现适用 | 时钟、延迟调节或串并转换资源不可用的诊断状态 |
固定采样结构且没有对应可调资源的从端不需要伪造延迟点、窗口边界或扫描位图。状态编码和`last_retrain_reason`数值编码可以由实现定义,但必须提供符号映射;最近训练原因至少应能够区分上电初始化、外部请求、协议层`retrain_request`、UL同步异常、DL同步异常、CRC错误门限、边界恢复失败和物理资源异常。
诊断计数器必须饱和或提供溢出指示,不得无提示回卷。除非实现声明提供显式诊断清零操作,以上累计计数从全局复位开始统计,普通会话复位和重新训练不得清零。跨时钟域读取多位状态、计数器和延迟值时必须使用可靠CDC或一致性快照。
## 48. 验证与验收要求
### 48.1 RTL仿真
#### 48.1.1 训练、扫描与同步
至少覆盖:
1. 所有固定帧均完成160位比较后才产生匹配事件,任一位错误均不得被接受;
2. `PRBS7`多项式、初值、位序、终止位置和128位序列的64/64平衡;
3. 扫描位图、最长窗口、并列窗口、偶数点中心及标称延迟点的确定性选择;
4. 环形扫描先证明一周相位排序及首尾间隔合法,再正确合并跨边界窗口;线性扫描发现窗口被边界截断时不得直接完成;`ALL_PASS`按第23.2节选择标称点并继续同步确认;
5. 通过窗口分别满足和不满足`RX_MIN_PASS_TAPS`、`TX_MIN_PASS_TAPS`及`MIN_PASS_WINDOW_TIME`时的判定;
6. `IDELAY`点连续49个`TRAIN`后出现错误时计数清零,连续50个时立即通过,200帧到期时失败;
7. 从端检测50个DL `TRAIN`后精确发送50个`TRAIN_ACK`;应答期间不累计`TRAIN`,`IDLE`或`TRAIN`错误不缩短应答;第50个结束后清零并恢复`TRAIN`;
8. `ODELAY`点连续9个`TRAIN_ACK`后出现非ACK固定帧时计数清零,连续10个时立即通过,200帧到期时失败;
9. 每个ODELAY点通过或失败后固定完整发送400个`IDLE`;忽略残余ACK,不要求`TRAIN`且不得提前切换;在声明的最坏延迟内验证迟到ACK不会污染下一点,UL失效仍退出扫描;
10. 从端的`DL SYNC`计数在9999后出现错误时清零,连续10000个时通过;
11. 从端精确发送20个`SYNC_ACK`,主端连续正确检测10个时通过;
12. 主端进入UL确认后忽略剩余`SYNC_ACK`,并从第一个完整`SYNC`开始累计10000个连续`SYNC`;
13. 主端和从端的`SYNC`均由规定状态条件终止,并能由各自超时路径退出;
14. 主端以`DL IDLE`结束同步;从端收到首个完整`DL IDLE`后连续发送20个`UL IDLE`,只在全部发送完成后置位本端`link_up`;主端收到首个完整`UL IDLE`后进入`M_RUN`并置位本端`link_up`;
15. 所有训练通过条件与超时条件同周期成立时,通过条件优先;
16. 延迟配置未就绪时状态机保持等待且不开始测量;就绪丢失时进入资源恢复,不把该点记录为普通失败点;
17. M_DL_CONFIRM、M_UL_CONFIRM和M_RUN_ENTRY收到完整TRAIN时,经统一入口从UL校准开始;M_RX_TRAIN和M_TX_TRAIN中的正常TRAIN不得触发重复重训;
18. M_RUN_ENTRY超时后无论UL是否仍收到SYNC,都经统一入口重新执行UL及DL校准;DL整轮扫描失败也不得只重新扫描DL;
19. 主端单独复位时,DL退出合法运行流并使从端确定进入`S_TRAIN`;
20. 可信方向从普通帧切换到训练固定帧时保持完整帧边界;
21. 从端协议故障请求在可信UL在途帧排空后直接持续发送TRAIN,主端据此终止旧会话并执行完整UL→DL训练;不依赖人为UL异常通知;
22. 多从端处于不同训练和运行状态时,各自的状态、延迟配置、计数和结果互不影响;
23. 单个延迟点失败继续扫描,不重新训练;DL整轮扫描无合格窗口时退出扫描,从UL重新开始;
24. 主端触发完整训练时,DL可用则完整发送20个SYNC_RESET,不能因提前收到TRAIN缩短;资源异常时等待资源,恢复后仍执行完整流程;
25. UL扫描期间DL只发送IDLE,不触发新的TRAIN_ACK;残余TRAIN_ACK不计作UL TRAIN通过证据。
#### 48.1.2 普通帧、边界及层间接口
至少覆盖:
1. 载荷中出现全部`SOF`、`IDLE`及固定帧相同图样时不误分帧;
2. `DATA`和`CTRL`无`IDLE`背靠背发送时,只在计算得到的下一边界识别新`SOF`;
3. CRC错误且长度合法时,按声明长度得到暂定边界;下一位置为合法`IDLE`或`SOF`时丢弃当前帧并恢复可信边界,下一位置非法时进入`MON_RECOVERY`;
4. `LEN`越界、低两位非零或无法完整取得时,不使用该值继续计数,产生`rx_frame_abort`并立即进入边界恢复;
5. `LEN`误码后仍处于合法范围时,接收等待不超过该值对应且受最大帧限制的长度,随后由CRC或下一边界发现异常;
6. `MON_RECOVERY`保持当前32位相位,逐字搜索;一个`IDLE`、一个完整合法固定帧或一个结构及CRC正确的普通帧能够恢复。搜索失败或已确认字相位失效时重新训练;
7. 恢复期间仅匹配`SOF`而完整结构或CRC失败时不得恢复;成功普通候选允许进入协议检查,重复DL帧不得再次提交;失败及被打断候选必须回滚;
8. 连续4个CRC承载帧错误或最近256个CRC承载帧中达到8个错误时,触发完整UL→DL重新训练;单个CRC错误不得直接撤销`link_up`;
9. 正常候选帧的逻辑末字与`rx_data_last`、`rx_crc_valid`和`rx_crc_pass`同周期输出,CRC字不得出现在`rx_data`中;
10. 从端收到`DL DATA`的`rx_frame_abort`时回滚并置位`RETRY_PENDING`和`ACK_PENDING`;主端收到`UL DATA`时只丢弃;任意`CTRL`中止时不更新协议状态;
11. `tx_data_valid && !tx_data_ready`期间数据和末字标志保持稳定;一帧`SOF`被接受后链路层持续接受到`tx_data_last`,帧内不得反压;
12. `tx_data_last`握手后只有CRC最后一位完成线路发送才产生一个`tx_frame_done`;每个方向最多存在一个尚未完成的普通逻辑帧;会话终止后可信在途帧保持读取上下文直至排空,所用存储不复用;
13. 已接受的普通逻辑帧未能完整发送时不产生`tx_frame_done`并撤销`link_up`,协议层不得对该帧记账或报告完成;
14. `link_up`撤销与`tx_frame_done`、接收完成、合法ACK或定时器到期同周期发生时,会话终止优先;
15. 对每个跨时钟域接口分别验证单周期事件不丢失、不重复,多位状态读取一致,且不会产生非法握手。
#### 48.1.3 传输协议与业务接口
至少覆盖:
1. 连续发送多个`DATA`并由一个累计ACK释放多个重传项,`OUTSTANDING_BYTES`始终等于未确认描述符`FRAME_COST`之和;
2. 同确认点ACK只更新同锚点窗口,旧ACK和越界ACK不改变任何可靠传输状态;
3. `SEQ`跨越`16'hFFFF`回绕时,累计ACK合理性判断、缓存释放和Go-Back-N范围均正确;
4. 分别丢弃或破坏`ACK/UPDATE`、`RETRY_REQ`、`POLL_REQ`及其响应,验证累计确认、周期查询和超时重传能够恢复;
5. 从端收到`POLL_REQ`时只依据CRC、`FLAGS`、方向和当前状态处理,不解析或检查其中的`ACK_NEXT`和`WIN_BYTES`,也不以其更新任何状态;
6. 新会话初始`ACK/UPDATE`绕过运行期ACK区间检查;合规从端以`ACK_NEXT=0`初始化,另注入非零初始值并验证主端以该值同时初始化`SND_UNA`和`SND_NXT`且不恢复旧状态;
7. 验证零窗口、非零但不足以容纳队首帧、窗口恢复及单纯窗口长期不足;单纯窗口等待不得启动Go-Back-N或重新训练;
8. ACK进度计时与单纯窗口问询计时在最后一个未确认帧被确认和首个新帧完成发送时原子切换,任一时刻只有一种计时解释有效;
9. 重传帧中途收到部分或全部前进ACK时更新确认记账但不释放所用存储,当前帧完整结束后正确选择下一序号且不跳过帧;重传中重复RETRY_REQ按状态合并,本轮发送阶段的ACK进展不被误判为失败;
10. 连续三轮完整重传无进展时只产生一次会话中止,所有已接受且尚未形成完成结果的请求各产生一次`app_tx_aborted`;已形成的完成结果保留且不改写;
11. 注入重传描述符缺失、重复、缓存不可读及`OUTSTANDING_BYTES > PEER_WIN_BYTES`,验证旧会话中止且不得跳过错误继续传输;
12. 模拟从端无法兑现已公告窗口,验证双方终止旧会话并进入重新训练;
13. 协议层置位`retrain_request`后保持请求,数据链路层只接受一次并撤销`link_up`;协议层观察到低电平后撤销请求,且只有随后观察到`link_up`重新置位才能退出重新训练保持状态;
14. `link_up`重新置位后只通过初始`POLL_REQ/ACK`建立新会话,旧会话的序号、窗口、控制快照和重传缓存均不得恢复;
15. 从端空闲时实际可公告至少1040 B;既能接收一个最大逻辑帧,也能承接额度允许的连续最短帧组合而不耗尽帧管理资源;采用保守描述符公式时验证87个描述符配置;
16. 主端UL业务接收资源不足时完整消费并丢弃CRC和格式正确的`UL DATA`,保持边界且不产生ACK、`RETRY_REQ`或重新训练;
17. 业务发送接口分别验证1字和258字有效载荷、帧间反压及帧内`app_tx_valid`间隙;`app_tx_valid && !app_tx_ready`期间数据与末字标志保持稳定;
18. 首字握手后、末字握手前发生会话终止时,协议层继续接收到`app_tx_last`,不向新会话发送该帧,并按接受顺序产生一次`app_tx_aborted`;
19. 一个累计ACK或一次会话终止同时形成多个业务结果时,结果按业务帧接受顺序每周期最多输出一个,不丢失、不重复,`app_tx_completed`和`app_tx_aborted`不得同周期有效;
20. 会话终止不改写已形成且排队的完成结果;协议会话复位期间继续交付结果,保持全局复位与会话复位的区别。业务接收接口被反压时保持`app_rx_valid`、`app_rx_data`和`app_rx_last`稳定,并保留尚未输出的完整业务帧。协议会话复位不截断已提交业务接收流。
### 48.2 门级、时序与板级验证
- 对所选物理配置的串行收发时钟、采样时钟、并行时钟和全部CDC路径完成静态时序检查;第7.3节典型配置还必须验证主端375 MHz DDR、187.5 MHz四位并行接口和从端750 MHz SDR之间的关系;
- 验证每次设置接收或发送延迟后,只有对应延迟配置就绪条件有效才开始测量;验证就绪丢失时进入资源恢复而不记录普通失败点;
- 在工艺、电压、温度角落记录窗口宽度、所选延迟点及中心漂移;
- 在最长线路、最差连接器和最大同时翻转条件下验证;
- 验证AC耦合基线漂移、终端匹配和目标误码环境;
- 注入位错误、CRC错误、长度错误、边界丢失、接收资源不可用和固定帧丢失;
- 验证任一同步丢失都会使双方协议状态复位;所有重新训练均须依次完成UL校准、DL校准、双向确认、运行入口及初始POLL_REQ/ACK,不得复用旧窗口跳过训练。合规从端以`ACK_NEXT=0`建立新会话,主端还必须通过非零初始值的防御性对齐测试。
### 48.3 运行准入条件
一条链路只有同时满足以下条件才可进入系统可用状态:
- `UL`和`DL`均按第23章得到合格结果;正常窗口装载所选中心点,`ALL_PASS`装载实现声明的确定标称点;
- 从端连续正确检测10000个`DL SYNC`,主端连续正确检测10个`SYNC_ACK`;
- 从端精确发送20个`SYNC_ACK`后持续发送`SYNC`,主端连续正确检测10000个`UL SYNC`;
- 从端识别首个完整`DL IDLE`后精确发送20个`UL IDLE`,主端识别首个完整`UL IDLE`后进入`M_RUN`;
- 双方`link_up=1`;
- 主端发送初始`POLL_REQ`并收到CRC、格式和类型合法的初始`ACK/UPDATE`,双方内部`session_ready`均已建立;
- 业务发送能力已按第45章正确反映到`app_tx_ready`。
`link_up`只表示UL、DL及运行入口过程均已就绪;系统业务可用还要求初始`POLL_REQ/ACK`完成。实现不得用未定义的固定保持时间代替这些确定条件。
### 48.4 实现验收条件
运行准入只说明当前链路完成训练和会话建立,不能替代实现验收。面向交付的实现必须完成第48.1节按角色适用的RTL验证,以及第48.2节按物理配置适用的时序和实测验证,并提供可复核结果。验收记录至少包含规范修订基线、实现配置、验证环境、输入条件、预期行为、实际结果和未覆盖项目。
必须验证:重复且ACK不推进的RETRY_REQ持续到来时,本轮观察期仍在原截止时间到期,连续三轮无进展最终终止会话;ACK推进与超时同周期时按进展处理。正常路径通过不能替代该异常活性验证。
CRC验证必须分别检查位序、初值、逐位反馈、逐字状态继承及结果封装,并对并行更新逻辑与第15.2节递推做等价比较。第15.3节32-bit函数必须与1-bit模块的逐位计算等价,串行输出按位0至位31重组后必须等于逐字计算的最终CRC;还须验证末位结果装载、32周期输出、输出末位标记、输入间隙及输出期间的输入保持;验证应覆盖任意初始状态、全0/全1输入、每个位置的单独置位、连续多字及最大长度逻辑帧。接口验证必须覆盖第43~45章时序图,包括候选末字与CRC同周期、中途abort、累计ACK期间读取占用、会话终止排空、结果排队和已提交接收数据的反压保留。
### 48.5 关键要求与验证索引
| 要求编号 | 权威定义 | 验证重点 |
|---|---|---|
| `REQ-ENC-001` | [第9.1节](#req-enc-001) | 小端字节序、字节内位0先行、32位字序一致 |
| `REQ-CRC-001` | [第15.2节](#req-crc-001) | CRC逐位递推、每帧初值、覆盖范围和结果封装 |
| `REQ-SCR-001` | [第16.1节](#req-scr-001) | 逐帧初始化、SOF绕过、帧体与CRC连续加扰 |
| `REQ-TRN-001` | [第20.3节](#req-trn-001) | 50个TRAIN资格与固定50个TRAIN_ACK |
| `REQ-TRN-002` | [第22.3节](#req-trn-002) | 固定400个IDLE隔离、残留应答时序上界 |
| `REQ-TRN-003` | [第26.2.2节](#req-trn-003) | 全部重训从UL开始、对端入口通知、扫描失败及正常TRAIN解释 |
| `REQ-RCV-001` | [第25.5节](#req-rcv-001) | 固定字相位搜索、单个IDLE恢复、候选接受契约 |
| `REQ-SES-001` | [第26.2节](#req-ses-001) | 会话立即终止、可信排空与存储延后回收 |
| `REQ-WIN-001` | [第31.7节](#req-win-001) | 最大容量与动态窗口区别、字节和描述符承诺 |
| `REQ-ARQ-001` | [第32.8节](#req-arq-001) | 重复请求不延长观察期、三轮失败闭环 |
| `REQ-IF-001` | [第43.4节](#req-if-001) | CRC末字同周期、候选abort与最终接受时机 |
| `REQ-IF-002` | [第45.2节](#req-if-002) | 每请求单次有序结果、复位保留已形成结果 |
| `REQ-IF-003` | [第45.3节](#req-if-003) | 接收反压保持、跨会话保留已提交数据 |
验收记录应引用相应要求编号;本索引不替代第48.1~48.2节完整验证清单。
## 49. 实现基线结论
本规范将主要校准和可靠传输复杂性集中在主端。主端负责两个方向的延迟扫描、窗口分析、最终延迟点选择、同步确认、累计确认、窗口控制和Go-Back-N;从端负责固定帧比较、`TRAIN_ACK`/`SYNC_ACK`生成、DL错误检测、状态`CTRL`生成、普通帧解析和同步异常上报。双方共同执行运行期边界监测和规定的重新训练状态转换。第7.3节给出的750 Mbps LVDS配置只是一种典型物理实现。
上电及重新训练先完成统一入口准备;主端DL可发送时完整发送20个SYNC_RESET,随后顺序固定为“从端连续`TRAIN` → 主端校准UL → 从端固定50个`TRAIN_ACK`,主端以固定400个`IDLE`隔离相邻发送延迟点并校准DL → 主端持续`SYNC` → 从端定量发送`SYNC_ACK`并持续发送`SYNC` → 主端持续发送`DL IDLE` → 从端发送20个`UL IDLE` → 主端收到首个`UL IDLE`后进入`M_RUN`”。运行期通过确定边界上的`IDLE`或`SOF`、帧内长度计数和帧尾CRC完成持续监测;内容错误与边界失步分别处理。
任一方向同步丢失都终止当前双向传输协议会话。重新训练始终从UL校准开始并完成DL校准和全部同步确认,双方协议状态均复位;恢复后通过初始`POLL_REQ/ACK`建立新会话。合规从端发送`ACK_NEXT=0`,主端仍按实际收到的初始值执行防御性序号对齐。
## 附录A:互操作实现声明清单
每个符合本规范的设备或IP至少应提供以下声明:
1. 本规范版本:V1.0;
2. 主端或从端角色;
3. 物理承载类型、电气接口、线路速率、同源时钟关系、线路位序和连续比特流接口约束;
4. 确认支持本规范固定的1032 B最大`DATA PAYLOAD`、帧格式、固定码字、CRC和扰码规则;
5. 按角色适用的接收窗口容量、帧描述符数量、主端重传缓存容量及主端`MAX_INFLIGHT_FRAMES`;
6. 按角色适用的延迟调节范围、实际延迟映射、扫描步进、环形或线性窗口算法、标称延迟点及最小通过窗口;
7. 确认采用第27章和第33章规定的固定计数与门限,声明400个`IDLE`保护的最坏残留应答预算,并声明各计时起点、阻塞/传播/流水线/CDC预算及超时周期数;
8. `SYNC_RESET`、完整UL→DL重新训练、`retrain_request`握手及同步丢失后协议复位的实现方式;
9. 第43章至第46章层间接口的位宽、时钟域、复位极性和CDC映射;
10. 第47章诊断信息的访问方式、位宽、编码和清零规则;
11. 第48章运行准入条件、实现验收要求及关键要求验证索引的完成情况。
互操作要求两端的外部物理接口、电气特性、线路速率、位序、同源时钟关系、线路编码和方向行为相互兼容,不要求两端使用相同的内部串并转换结构、并行宽度、工作时钟、延迟资源或状态编码。实现可以采用不同的流水线、RAM组织和时钟域结构,但不得改变线路比特序列、接收接受条件、确认语义、状态转换或错误恢复行为。