PCI,PCIE之基础

PCIE之前接触过,但是总是感觉理解的很肤浅,这里针对之前模糊的地方重新梳理一些概念,不是很系统讲PCIE,如果想系统的理解,请参考文末的连接。
1)PCIE空间概念:
PCIE空间分为配置空间,IO空间,Memory空间,这些空间属于系统空间的一部分(PCI配置空间是通过两个端口CFCh和CF8h访问的,CFCh端口存放Bus/Device/Function + registerd地址,CF8h存放要设置的值)。配置空间的访问主要是在PCIE系统总线枚举和设备发现过程中进行,主要是按照PCIE配置规范来,设备的驱动不会访问配置空间,IO/Memory空间是设备驱动访问的空间,用于配置访问设备,如设备的控制寄存器的配置,状态寄存器的查询等。
在这里插入图片描述
2)PCI配置头
由于PCI/PCIe设备分为Bridge和Agent两种,所以配置空间也有两种类型,其中Agent的配置空间类型称为Type 00h:
在这里插入图片描述
Vendor Identification 唯一的数字,描述这个 PCI 设备的发明者。 Digital 的 PCI Vendor Identification 是 0x1011 而 Intel 是 0x8086 。
Device Identification 描述设备自身的唯一数字。例如 Digital 的 21141 快速以太网设备的设备标识符是 0x0009
Status 此域给除了设备的状态,它的位的含义由 PCI Local Bus 规范规定。
Command 系统通过写这个域控制这个设备。例如:允许设备访问 PCI I/O 内存。
Class Code 标识了设备的类型。对于每一种设备都有标准分类:显示、 SCSI 等等。对于 SCSI 的类型编码是 0x0100 。
Base Address Registers 这些寄存器用于确定和分配设备可以使用的 PCI I/O 和 PCI 内存的类型、大小和位置。 Interrupt Pin PCI 卡的物理管脚中的 4 个用于向 PCI 总线传递中断。标准中把它们标记为 A 、 B 、 C 和 D 。 Interrupt Pin 域描述了这个 PCI 设备使用那个管脚。通常对于一个设备来说这是硬件决定的。就是说每一次系统启动的时候,这个设备都使用同一个中断管脚。这些信息允许中断处理子系统管理这些设备的中断。
Interrupt Line PCI 配置头中的 Interrupt Line 域用于在 PCI 初始化代码、设备驱动程序和 Linux 的中断处理子系统之间传递中断控制。写在这里的数字对于设备驱动程序来讲是没有意义的,但是它可以让中断处理程序正确地把一个中断从 PCI 设备发送到 Linux 操作系统中正确的设备驱动程序的中断处理代码处。
在这里插入图片描述
在这里插入图片描述
关于PCI IO/Memory空间多说一句
这两种地址空间用于设备和 CPU 上运行的设备驱动程序通讯。例如: DECchip 21141 快速以太网设备把它的内部寄存器映射到了 PCI I/O 空间。然后它的 Linux 设备驱动程序通过读写这些寄存器来控制设备。显示卡驱动程序通常使用大量的 PCI 内存空间来放置显示卡的信息。
直到 PCI 系统建立起来并使用 PCI 配置头中的 Command 域打开了设备对于这些地址空间的访问为止,设备都无法访问这些空间。应该注意的是只有 PCI 配置代码读写 PCI 配置地址, Linux 的设备驱动程序只是读写 PCI I/O 和 PCI 内存地址。
下面是Bridge的配置空间,它的类型被称为Type 01h:
在这里插入图片描述
Type 01h中也有Vendor ID,Device ID,Status,Command等寄存器。
另外需要注意的是这里的BAR计算得到的系统空间是该桥下挂的所有设备的系统空间的总和。
另外Subordinate Bus Number、Secondary Bus Number和Primary Bus Number,这些寄存器共同确定了该桥上行和下行的所有Bus号,详见后面的枚举过程。
PCI发现设备过程中,Bridge和Agent区分是通过配置空间的class code,pci bridge的class code是0x060400。
PCIe配置空间
PCIe是在PCI基础上发展的协议,PCIe也有上述的PCI配置空间,并且在此基础之上进行了扩展,其扩展形式是通过一种称为Capability的寄存器块来完成的。
PCI配置空间的大小是256个字节,即0x00-0xFF,而PCIe的配置空间扩大到了0x00-0xFFF,下图是具体的布局。
在这里插入图片描述
在原来的配置空间中,有一个寄存器指定了第一个Capability的位置,而第一个Capability又指定下一个Capability,构成了一串Capability,具体如下图所示:
在这里插入图片描述
各个不同的Capability的作用不同,且不同的设备有不同的Capability,在这里不一一介绍了。
3) 配置空间配置方法
在这里插入图片描述
软件可以定位不在主 PCI 总线上的设备,必须有一种机制使得桥可以决定是否把配置 cycle 从它的主接口(桥上距离CPU较近的一侧)传递到次接口(桥上距离CPU较远的一侧)上。一个 cycle 就是它显示在 PCI 总线上的地址。 PCI 规范定义了两种 PCI 地址配置格式:类型 0 和类型 1 ,如上图显示。类型 0 的 PCI 配置 cycle 不包含总线号,被这个 PCI 总线上的所有的 PCI 设备解释用于 PCI 地址配置。配置 cycle 的位 32 : 11 看作是设备选择域。设计系统的一个方法是让每一个位选择一个不同的设备。这种情况下为 11 可能选择槽位 0 的 PCI 设备,位 12 选择槽位 1 的 PCI 设备,依此类推。另一种方法是把设备的槽位号直接写到位 31 : 11 中。一个系统使用哪一种机制依赖于系统的 PCI 内存控制器。
类型 1 的 PCI 配置 cycle 包括一个 PCI 总线号,这种配置循环被除了 PCI-PCI 桥之外的所有 PCI 设备忽略。所有看到了类型 1 的 PCI 配置 cycle 的 PCI-PCI 桥都可以把这些信息向它们的下游传送。一个 PCI-PCI 桥是否忽略 PCI 配置循环或者向它的下游传递,依赖于这个桥是如何配置的。每一个 PCI-PCI 桥都有一个主总线接口号和一个次总线接口号。主总线接口离 CPU 最近而次总线接口是离 CPU 最远的。每一个 PCI-PCI 桥都还有一个附属总线编号,这是在第二个总线接口之外可以桥接的最大的 PCI 总线数目。或者说,附属总线编号是 PCI-PCI 桥下游的最大的 PCI 总线编号。当 PCI-PCI 桥看到一个类型 1 的 PCI 配置 cycle 的时候,它做以下事情:
如果指定的总线编号不在桥的次总线编号和总线的附属编号之间就忽略它。
如果指定的总线编号和桥的次总线编号符合就把它转变成为类型 0 的配置命令
如果指定的总线编号大于次要总线编号而小于或等于附属总线编号,就不改变地传递到次要总线接口上。
每一个独立的操作系统负责在 PCI 配置阶段分配总线编号,但是不管使用哪一种编码方案,对于系统中所有的 PCI-PCI 桥,以下陈述都必须是正确的:
所有位于一个 PCI-PCI 桥后面的 PCI 总线的编码都必须在次总线编号和附属总线编号之间(包含)
如果违背了这条规则,则 PCI-PCI 桥将无法正确地传递和转换类型 1 的 PCI 配置 cycle ,系统无法成功地找到并初始化系统中的 PCI 设备。为了完成编码方案, Linux 按照特定的顺序配置这些特殊设备。
由上述可见,软件发起的肯定是类型1配置cycle,类型0的配置cycle软件不可见。
参考:PCI基础
PCI

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值