✨ 1. EA 背景介绍
PCIe Enhanced Allocation (EA),增强分配,是一种由 PCIe 3.1 提出、PCIe 4.0 正式引入的一种可选配的 PCIe 能力。开启了 EA 能力的 PCIe 组件允许在其配置空间 BAR 范围外分配IO、Memory 及 Bus Number 资源。一言以蔽之,PCIe EA 机制就是 —— 原配置空间中的灵活可配的 BAR 弃而不用,改用固定值取而代之。
PCI 面世伊始即有现行的配置架构。得益于其即插即用用户友好型的特性,PCI 配置架构风风火火近三十载,到如今仍热力不减。PCI 配置结构能够久经考验,与其以下几个优点有关:
✔️ 能够简化并加速系统集成;
✔️ 缩减系统固件/软件开销及复杂度;
✔️ 提升系统 Debug 能力及鲁棒性,等等。
PCI/PCIe 配置架构中的 BAR 是可以灵活配置的(任意时间都可以重新配置),采用这种配置架构的 PCIe 系统,系统中各组件是基于物理共享总线及综合即插即用架构独立进行地址解码的。但这种灵活配置的 BAR 不太适用于 SoC 或多 Chip 模块,因为这些 SoC 或多 Chip 模块大部分不需要重复编程,SoC 中的很多既有 IP 也不支持灵活可配的 MMIO,在硬件及软件方面都没有灵活配置 BAR 的需求,这种灵活性反倒会增加成本及系统的复杂度。
为了适应这种情况,EA 机制横空出世!你不需要灵动的 BAR,OK,拿掉!你给我指定一个固定的范围,妥了!
✨ 2. EA 机制介绍
2.1 EA 适用范围
EA 能力仅限于在特定 Function 中使用。Function 能否使用 EA,取决于其在 PCIe 层级结构中的位置及其在 PCIe 平台环境中的体现形式。
1️⃣ 只有自设备上电启动开始便连接(直接或间接)在主桥上的 Function(我们称这种连接为永久连接),才能够使用 EA 机制。
2️⃣ 与主桥连接的 Bridge 中的 Function,若其下游 Function 永久连接在主桥上,则其上、下游端口(即 Primary Side 和 Secondary Side)均可使用 EA。
3️⃣ 与主桥连接的 Bridge 中的 Function,若其下游 Function 非永久连接在主桥上,则只有上游端口可使用 EA,下游端口不可使用 EA。
2.2 EA 使用规则
2.2.1 基本规则
对于下游 Function 非永久连接在主桥上的 Bridge Function,其下行端口只能采用非 EA 资源分配机制分配其 Type1 Header 中的 Bus Number 及 MMIO/IO 地址空间。
对于 Bridge 分配给其下游组件的 Bus Number 及 MMIO/IO 地址空间,系统软件需确保:① 分配的 Bus Number 在 EA 能力寄存器指定的固定 Secondary/Subordinate Bus Number范围之内;② 分配的 MMIO/IO 地址空间在 EA 能力指定的相关属性范围之内。对于多个 Bridge 的 Function,硬件指定的 Bus Number、MMIO/IO 地址空间允许存在重叠,但软件应确保实际使用的范围不存在交叠。
若某些 Function 只依赖于 EA 进行 IO 及内存地址分配,则该 Function 的 BAR 应硬连线为 0(设计者在文档中应特别注明这些 Function 依赖于 EA)。
若 Function 采用 EA 机制进行了资源分配并指明了其替代掉的 BAR,那该 Function 不能继续采用原配置空间对应 BAR。
若桥中某个 Function N 支持 EA,该 Function 可以采用 EA 机制指示该 Function 下游Bridge Function的资源范围,但非必须。系统软件应明白Function N 没有责任指明其下游Function 所用的资源,系统软件应完整遍历 Function N 的所有下游 Function 以搞清楚其采用的资源范围。
EA 机制不会改变命令寄存器中对 IO、内存范围解码等的开关使能作用。
除了 Bridge下游 Function 的 Bus Number或地址空间等资源允许存在交叠,EA 机制分配的所有资源不能存在重叠。
2.2.2 扩展 ROM 与 EA 机制
带有扩展 ROM 的 Function 可以采用扩展 ROM 基地址机制来指定 ROM 地址空间,也可以采用 EA 机制来指定,但不能同时启用。若 Function采用 EA 分配机制来指定扩展 ROM 的地址空间(EA Entry BEI = 8),则扩展 ROM 基地址寄存器(图1)中的扩展 ROM 使能及扩展 ROM 基地址字段的值不再有意义,需硬连线为 0,转而采用 EA Entry 使能位及 EA Entry 中指定的地址空间。
若 Function 仍然采用扩展 ROM 基地址寄存器来指定 ROM 地址空间, 则 EA Entry 的 BEI 不能为 8。若扩展 ROM 支持 ROM Validation,两种情况下扩展 ROM 基地址寄存器中的 ROM Validation Status 及 Details 字段值均有效。
图1 扩展 ROM 基地址寄存器
2.3 EA 能力结构
具备 EA 能力的组件需实现 EA 能力结构。所有组件的EA 能力结构都有 ① EA 扩展能力头标、② EA Entry,Type 1 类型的组件还有 ③ Fixed Bus Number。
EA 扩展能力头标(图2),用以指明当前组件具备 EA 能力、EA Entry数目,并指向下一能力的偏移地址。
Fixed Bus Number(图3),仅用于Type 1 类型的 Function,位置在 EA 扩展能力头标之后、第一个 EA Entry之前,2DW,用以指明该 Bridge Function 下接的 Fixed Secondary Bus Number 和 Fixed Subordinate Bus Number。若当前 Function 之后至少有一个 Function 开启了 EA 机制,Fixed Secondary Bus Number 字段用以指明该 Function Secondary 接口的 Bus Number, Fixed Subordinate Bus Number 字段用以指明该 Function 下游最大的 Bus Number。
若当前 Function 之后没有任何 Function 开启 EA 机制,则Fixed Secondary Bus Number 和 Fixed Subordinate Bus Number 字段应置零。
EA Entry(图4),作用与原 PCIe 配置空间的 BAR 类似,详见 2.3.1。由于Type 0 Function 的 EA 能力结构没有 Fixed Bus Number 寄存器,Type 0 与 Type 1 Function 对应的 EA Entry 起始地址偏移不同。
图2 EA扩展能力头标
图3 EA Fixed Bus Number 寄存器
图4 Type0 Function EA Entry 格式
2.3.1 EA Entry 格式
EA Entry 如上图(图4)所示,包括 Entry Enable、Writable、Properties、BAR Equivalent Indicator、Size、Base、MaxOffset 等字段。
Entry 控制寄存器
图5 EA Entry 控制寄存器
每个 EA Entry 的第一个 DW 对该Entry进行控制(图5),各字段意义如下:
● Entry Size (ES):用以指明当前 Entry 的大小(扣除了第一 DW)。0 表示该Entry只有第一 DW 数据。
● BAR Equivalent Indicator (BEI):用以指明当前 Entry 的等效 BAR,BEI 对应的 BAR 如表 1 所示。
● Primary Properties:指明该 Entry 对应资源的属性,详见表2。
● Secondary Properties:可选,是 Primary 属性的备选方案,用以指示一个跟 Primary 属性不同但兼容的属性,详见表2。
● Writeable (W):用以指明该 Entry 的 Base 及 MaxOffset 字段是否可写,1 为可写。只有 Entry 资源属性为预留的 Entry 才可写。
● Enable (E):用以指示是否启用当前 Entry。
Base 与 MaxOffset 字段
Base 字段用以指示该 Entry 分配地址空间的起始地址,Base[1:0] 不管为啥都采用 00b。Base + MaxOffset 为末端地址,MaxOffset[1:0] 不管为啥都采用 11b。Base 和 MaxOffset 的bit[1] 用以指示地址位宽,0 -> 32 bit,1 -> 64 bit。若 Base[1] 或 MaxOffset[1] 为 0,则其对应的 [63:32] 位在 Entry 中不存在,而非以 0 填充。
BEI 字段
BEI 用以指明当前 Entry 的等效 BAR,BEI 对应的 BAR 如表 1 所示。Type0 Function中,对于 BEI 为 0-5 的情况,虽然不要求地址对齐,但强烈建议在设置Base 及 MaxOffset 时采用对齐的地址,以避免软件使用过程中出现问题。
表1 BEI 与 BAR 对应关系
BEI 字段使用规则:
● Type 0 类型的 Function 可以采用 EA 机制对其自身进行资源分配,BEI 为 0-5,7 或 8
● 在支持 SR-IOV 的 Type 0 类型 Function 中,PF 可采用 EA 机制分配相关 VF 资源,BEI 为9-14
● Type 1 类型的 Function 可以采用 EA 机制对其自身进行资源分配,BEI 为0, 1 或 7
● Type 1 类型的 Function 可以(非强制)采用 EA 机制对其下游 Function 进行资源分配,BEI 为6
● 对于 64-bit 位宽的基地址寄存器,BEI 代表地址低 DW 对应的 BAR 位置
● Primary/Secondary Properties 为 00h 或 01h 时(即 Entry属 性为存储空间),Base + MaxOffset 小于 4GB 和大于 4GB 的两个 Entry 可以采用相同的 BEI,BEI 为 0-5
● Primary/Secondary Properties 为 03h 或 04h 时(即 Entry 属性为 PF 分配 VF 的存储空间),Base + MaxOffset 小于 4GB 和大于 4GB 的两个 Entry 可以采用相同的 BEI,BEI 为 9-14
● 对于两个 Entry BEI 相同的情况,在特定 Function中软件一次只能启用两段范围中的一个
● BEI 为 6 或 7 的 Entry 个数不受限,可以为任意多个
● 至多只能有一个 BEI 为 8 的 Entry,若存在 BEI = 8 的 Entry,
● 对于Type 1 类型的 Function,BEI = 2-5 为预留
Properties 字段
EA Entry Properties 字段用以指明该 Entry 对应资源的属性,详见表2。Primary是必选的属性,Secondary Properties是 Primary 属性的备选方案(可选),用以指示一个跟 Primary 属性不同但兼容的属性,以防软件不识别 Primary 属性。
举个例子,老的系统软件跑在新的硬件上,新硬件采用了新定义的 Primary 属性,老软件不认识新硬件的 Primary 属性,那么可以采用 Secondary 属性进行处理。Secondary 属性应为当时支持的属性,在此之后的硬件也是兼容该属性的。
表2 Properties 字段意义
✨ 3. EA 应用举例
举个 PCIe 系统使用 EA 机制的例子,如图6所示,Function 0-5, 7-8 永久连接在主桥上,Function 0-3 为 Si component A,Function 0-1 为 Type 0 类型,Bridge Function 2 通过 Bus J 连接非永久连接的 Function 6,Bridge Function 3 通过 Bus N 连接永久连接的 Function 4-5。绿色部分为支持 EA 机制,浅蓝色不支持。
图6 EA 应用举例
📚 参考
PCI Express Base Specification Revision 5.0 Version 1.0 (22 May 2019)
PCI Express Technology - Comprehensive Guide to Generation1.x, 2.x and 3.0. Mike Jacson, Ravi Budruk, MindShare, Inc.
PCIe® 3.1 & M-PCIe™ Protocol