0%

riscv iommu board 移植

问题1:

boston 使用的 pcie 总线 xinlinx_pcie_root_realize 在调用 pci_bridge_initfn 后, qemu系统中查询 pci_bus 失败

object_resolve_path_type(“”, TYPE_PCI_BUS, NULL)

导致qemu 模拟的iommu 设备无法正常注册

riscv_iommu_sys_realize 函数中不能找到 pci_bus,没有走 riscv_iommu_pci_setup_iommu 函数。

bus->iommu_fn 为 空

问题2:

正常情况下 board 注册完时,会通过 notify 调用 pci_done

最终, 会调用 bus->iommu_fn 函数

riscv_iommu_find_as->riscv_iommu_space->memory_region_init_iommu(as->iova_mr, TYPE_RISCV_IOMMU_MEMORY_REGION)

address_space_init(&as->iova_as, MEMORY_REGION(&as->iova_mr), TYPE_RISCV_IOMMU_PCI)

而 boston board 没有走这条链路。
这个链路是 qemu guest 起来之前走的,因此与 dts 配置无关。

问题 3:

boston 上添加 gpex 总线
原来的 xinlinx 总线还是会影响到 pci_bus,导致不能正常初始化 iommu 设备
需要删除 xinlinx 总线的创建。

问题 4:

e1000e 网卡没有与 iommu 进行交互

gpex 总线的 dts 配置中需要设置 iommu-map
第一项代表 rid-base,对应 pcie 设备的总线号 15-8 位
第二项表示 iommu 的 phandle
第四项代表 length, match rid-base:rid-base+length 范围内的 pcie 设备
e1000e 网卡的总线号 0000 在该范围内,系统起来后,会将 e1000e 网卡加到 iommu group 中。

问题 5:

复制 virt 的 pcie dts 配置后, e1000e 网卡中断不正常。
调研后发现是 interrupt-map 配置有问题。

interrupt-map
<child-address , child-id parent-phandle, 中断号>

virt 的中断控制器 plic 配置的 interrupt-cells 为 1, 即只有 <中断号>

到了 boston 上, parent aplic_s 的 interrupt-cells 为 2,代表 <中断号,中断类型>
所以 interrupt-map 应该配置为
<child-address , child-id parent-phandle, 中断号,中断类型>
第一项占位取决与 address-cells

问题 6:

vfio 配置,VFIO_SET_IOMMU 需要打开 allow_unsafe_interrupts 选项,否则 group 会 attach 不上 container

问题 7

在 close(group_fd) 或 VFIO_IOMMU_UNMAP_DMA 时会包 folio 的 panic
原因为 unmap_dma 时会调用 riscv_iommu_iova_to_phys 接口翻译 iova->phys
在该函数中,翻译时取页内偏移时调用了 iova & PAGE_MASK,而 PAGE_MASK 是 ~(1<<12 -1), 这个地方应该 & ~PAGE_MASK, 才是取页内偏移。由于计算物理地址有误,导致了后续的物理地址 unpin 错误。