PCI桥支持32/64 pref / no pref:
pci_bus 0000:00: root bus resource [bus 00-ff]
pci_bus 0000:00: root bus resource [io 0x0000-0xffff]
pci_bus 0000:00: root bus resource [mem 0x1000000000-0x10ffffffff] (bus address [0x00000000-0xffffffff])
pci_bus 0000:00: root bus resource [mem 0x1100000000-0x11ffffffff pref] (bus address [0x00000000-0xffffffff])
pci_bus 0000:00: root bus resource [mem 0x2000000000-0x2fffffffff] (bus address [0x00000000-0xfffffffff])
pci_bus 0000:00: root bus resource [mem 0x3000000000-0x3fffffffff pref] (bus address [0x00000000-0xfffffffff])
用2个BAR扫描端点:
pci 0000:01:00.0: BAR 2: assigned [mem 0x2100000000-0x211fffffff 64bit pref]
pci 0000:01:00.0: BAR 0: assigned [mem 0x1000000000-0x100007ffff]
桥显示窗口:
pci 0000:00:00.0: PCI bridge to [bus 01]
pci 0000:00:00.0: bridge window [mem 0x1000000000-0x10000fffff]
pci 0000:00:00.0: bridge window [mem 0x2100000000-0x211fffffff 64bit pref]
端点总结了BAR:
endpoint: BAR 0 addr = 0x1000000000, size = 524287
endpoint: BAR 1 addr = 0x2100000000, size = 536870911
BAR1的高32位被编程为什么?我期望0x21,但找到0x1。
这是因为pcibios_bus_to_resource / pcibios_resource_to_bus。 它识别3个窗口偏移:
window->res->start = 1000000000 window->offset = 1000000000 window->res->end = 10FFFFFFFF
window->res->start = 1100000000 window->offset = 1100000000 window->res->end = 11FFFFFFFF
window->res->start = 2000000000 window->offset = 2000000000 window->res->end = 2FFFFFFFFF
在显示上述地址时添加偏移量,但在编程BAR时减去它们 在端点中注册。所以0x2100000000变成0x100000000。
64位地址和32位BAR可能有意义,但为什么64位BAR会这样正确?
答案 0 :(得分:1)
据此(摘自问题):
pci_bus 0000:00: root bus resource [mem 0x1000000000-0x10ffffffff] (bus address [0x00000000-0xffffffff])
pci_bus 0000:00: root bus resource [mem 0x1100000000-0x11ffffffff pref] (bus address [0x00000000-0xffffffff])
pci_bus 0000:00: root bus resource [mem 0x2000000000-0x2fffffffff] (bus address [0x00000000-0xfffffffff])
pci_bus 0000:00: root bus resource [mem 0x3000000000-0x3fffffffff pref] (bus address [0x00000000-0xfffffffff])
存储器地址0x20&00; 0000&00; 0000对应于总线地址0。
因此,如果要使用存储器地址0x21&00; 0000&00; 0000来访问设备中的BAR,则需要将其编程为0x1&00; 0000&00; 0000。
类似地,存储器地址0x10&00; 0000&00; 0000对应于总线地址0.因此,设备中的BAR被编程为0以使用存储器地址0x10&00; 0000&00; 0000来访问。