2. PCIe协议基础与Layerscape实现
PCIe 不是一条“更快的并行总线”,而是一套分层、带事务语义、可枚举、可热插拔的点对点串行互连协议。理解它,必须同时抓住两条线:一条是协议栈的分层与报文封装,另一条是 Layerscape 控制器如何把这些协议动作落到硬件寄存器与内存映射上。本节先建立协议骨架,再对照 Layerscape 的 PCIe 控制器特性,为后续配置空间访问、枚举和驱动调试打基础。
一、PCIe 的三层协议栈与报文封装
PCIe 协议栈自下而上分为物理层(PHY)、数据链路层(DLL)和事务层(TL)。物理层负责串行化、8b/10b 或 128b/130b 编码、链路训练与均衡;数据链路层负责链路级的可靠传输,用序列号、LCRC 和 ACK/NAK 保证相邻两个设备之间不丢包;事务层负责生成和解析 TLP(Transaction Layer Packet),承载内存读写、配置读写和消息事务。三层各司其职,上层报文对下层而言只是需要可靠搬运的负载。
TLP 是事务层的基本单位,典型字段包括:Header(含 Fmt、Type、Requester ID、Tag、地址或路由信息)、Data Payload(可选,最大由 Max_Payload_Size 决定)以及可选的 ECRC。DLLP(Data Link Layer Packet)不承载事务语义,只在链路两端之间传递 ACK/NAK、流控信用(Flow Control)和电源管理信息,因此它不会出现在配置空间或内存事务的路径上。理解 TLP 与 DLLP 的分工,是区分“事务问题”和“链路问题”的关键:配置读返回错误码,多半是 TLP 层或配置空间问题;链路反复重训、LCRC 错误,则更可能是 DLL/PHY 层问题。
二、配置空间:从 256 字节到 ECAM
PCIe 配置空间是枚举和驱动识别的入口。传统 PCI 配置空间为 256 字节,其中前 64 字节是标准头:Vendor ID、Device ID、Command、Status、Class Code、BAR0~BAR5、Capabilities Pointer 等。PCIe 在此基础上扩展为 4KB 配置空间,新增 PCI Express Capability、MSI/MSI-X Capability、Power Management 等结构。访问方式有两种:一是通过 CFG0/CFG1 的 I/O 端口间接访问(传统机制),二是通过 ECAM(Enhanced Configuration Access Mechanism)把配置空间直接映射到一段内存地址,用普通内存读写指令访问。
在 Layerscape 上,RC 模式通常使用 ECAM 映射,把总线号、设备号、功能号编码进地址偏移。例如某 Layerscape 平台将 ECAM 基址设为 0x3000_0000,则 Bus 1、Device 0、Function 0 的配置空间起始地址为 0x3000_0000 + (1<<20) + (0<<15) + (0<<12)。驱动或 U-Boot 通过读取该地址的 0x00 偏移即可拿到 Vendor ID 和 Device ID,从而判断设备是否存在。若读回 0xFFFF_FFFF,通常表示该位置无设备或链路未训练完成。
三、枚举过程与 Layerscape 的硬件配合
枚举是 RC 发现拓扑、分配总线号和资源的过程。典型流程是:RC 从 Bus 0 开始扫描,读取每个设备/功能的 Vendor ID;若有效,则读取 Header Type 判断是单功能还是多功能、是桥还是端点;对桥设备继续分配下游总线号并递归扫描;同时读取 BAR,确定所需内存或 I/O 空间大小,并写入分配后的基地址。枚举完成后,系统获得一棵完整的 PCIe 设备树,每个设备都有唯一的总线号、设备号和功能号。
Layerscape PCIe 控制器在枚举中承担几个关键角色。第一,它提供 Outbound 窗口,把 CPU 对本地地址的访问转换成 PCIe 配置或内存事务发往链路对端;第二,它提供 Inbound 窗口,把外部设备发来的内存读写映射到本地 DDR 或寄存器;第三,它通过 ATU(Address Translation Unit)完成地址转换,使 RC 侧地址与 PCIe 总线地址解耦。实际调试中,如果枚举不到设备,应优先检查 LTSSM 是否进入 L0、参考时钟是否稳定、PERST# 释放时序是否正确,再检查 ATU 窗口和 ECAM 基址配置。
四、Layerscape PCIe 控制器特性对照
Layerscape 系列(如 LS1046A、LS2088A、LX2160A)的 PCIe 控制器通常支持多个控制器实例,每个控制器可独立配置为 RC 或 EP。以 LS1046A 为例,它提供 3 个 PCIe 控制器,支持 Gen1/Gen2/Gen3,链路宽度可配置为 x1、x2、x4,部分控制器支持 x8。控制器内部集成 SerDes、LTSSM、ATU、MSI 控制器和配置空间访问逻辑。与通用 PCIe 规范相比,Layerscape 的差异主要体现在:地址转换窗口数量有限,需要合理规划 Outbound/Inbound 映射;MSI 中断需要经过 GIC 路由,配置时需同时设置 MSI Capability 和 GIC ITS/SPI 映射;部分控制器支持 SR-IOV,但需要确认 RC 和 EP 两侧的 PF/VF 配置。
五、一个可复用的枚举检查清单
| 检查项 | 观察位置/方法 | 正常判据 | 异常时优先排查 |
|---|---|---|---|
| LTSSM 状态 | 控制器状态寄存器 | 进入 L0 | 参考时钟、PERST#、SerDes 配置 |
| ECAM 可读性 | 读取 ECAM 基址 + 偏移 0x00 | Vendor ID ≠ 0xFFFF | ECAM 基址、总线号分配 |
| BAR 分配 | 读取 BAR0~BAR5,写全 1 再读回 | 得到有效空间大小 | ATU 窗口冲突、地址空间不足 |
| Outbound 映射 | 检查 ATU 窗口寄存器 | CPU 地址可命中目标总线地址 | 窗口基址、大小、目标地址 |
| MSI 中断 | 触发设备中断,观察 GIC | GIC 收到对应 SPI/LPI | MSI Capability、ITS 映射、使能位 |