AMD IOMMU与Linux (4) -- Domain, Group, Device

2023-05-16

1. domain的本质是一个页表,1对1的关系

2. IOMMU_DOMAIN_UNMANAGED vs. IOMMU_DOMAIN_DMA

        a. IOMMU_DOMAIN_UNMANAGED    - DMA mappings managed by IOMMU-API user, used for VMs
        b. IOMMU_DOMAIN_DMA    - Internally used for DMA-API implementations. This flag allows IOMMU drivers to implement certain optimizations for these domains

IOMMU_DOMAIN_DMA对应default_domain

IOMMU_DOMAIN_UNMANAGED对应VFIO, 或者GPU自行创建的domain

多个domain解决的问题: 用户态发起的DMA,它自己在分配iova,直接设置下来,要求iommu就用这个iova,内核对这个设备做dma_map,也要分配iova, 两者(两个iova)冲突产生。

解决办法 就是:

VFIO:默认情况下,iommu(应该是DMA设备,而不是IOMMU)上会绑定一个default_domain,它具有IOMMU_DOMAIN_DMA属性,原来怎么弄就怎么弄,这时你可以调用dma_map()。但如果你要用VFIO,你就要(DMA设备)先detach原来的驱动,改用VFIO的驱动,VFIO就给你换一个domain,这个domain的属性是IOMMU_DOMAIN_UNMANAGED,之后你爱用哪个iova就用那个iova,你自己保证不会冲突就好,VFIO通过iommu_map(domain, iova, pa)来执行这种映射。

等你从VFIO上detach,把你的domain删除了,这个iommu(同上,应该是DMA设备,而不是IOMMU)就会恢复原来的default_domain,这样你就可以继续用你的dma API了。

这种情况下,你必须给你的设备选一种应用模式,非此即彼

vfio-pci [1]

vfio-pci 驱动中,把这个设备的io空间和iommu_group直接暴露到用户态

vfio_group是vfio对iommu_group的表述

The Intel IOMMU driver allocates a virtual address per domain. Each PCIE device has its own domain (hence protection). Devices under p2p bridges share the virtual address with all devices under the p2p bridge due to transaction id aliasing for p2p bridges.[7]

IOVA generation is pretty generic. We used the same technique as vmalloc() but these are not global address spaces, but separate for each domain. Different DMA engines may support different number of domains.[7]

Interrupt ranges are not address translated, (0xfee00000 - 0xfeefffff). The same is true for peer to peer transactions. Hence we reserve the address from PCI MMIO ranges so they are not allocated for IOVA addresses【7】

IOVA是有domain的属性的

中断, P2P, MMIO不作remapping

3. 关于PASID

AMD IOMMU支持PASID, 由Device ID (BDF) + PASID (TLP Prefix) + GVA构成GVA到SPA的translate

 

4. IOMMU group

从struct device与struct iommu_group的结构上可以看出,DMA设备隶属于一个iommu group (PCIE 协议中由拓扑结构中ACS支持与否等因素决定设备的iommu group 【3】【4】【5】), 而一个iommu group可以处于default domain或者其它的domain

struct device {

        ...

struct fwnode_handle        *fwnode; /* firmware device node */ @fwnode:     Associated device node supplied by platform firmware.

struct iommu_group        *iommu_group;  * @iommu_group: IOMMU group the device belongs to.

struct dev_iommu        *iommu;  * @iommu:      Per device generic IOMMU runtime data

        ...

};

struct iommu_group {

        ...

        struct iommu_domain *default_domain;

        struct iommu_domain *domain;

        ...

};

iommu.c关于PCI设备group的分配 相关函数:pci_device_group/get_pci_alias_group/get_pci_function_alias_group

/* PCI device grouping function */
extern struct iommu_group *pci_device_group(struct device *dev);
/* Generic device grouping function */
extern struct iommu_group *generic_device_group(struct device *dev);
/* FSL-MC device grouping function */
struct iommu_group *fsl_mc_device_group(struct device *dev);

另外,一个DMA设备与一个IOMMU是通过struct dev_iommu作为纽带:

struct device {

        ...

        struct iommu_group        *iommu_group;  * @iommu_group: IOMMU group the device belongs to.

        struct dev_iommu        *iommu; * @iommu:      Per device generic IOMMU runtime data

        ...

}

struct dev_iommu {

        ...

        struct iommu_device                *iommu_dev;

        ...

};

struct iommu_device {

        struct list_head list;

        const struct iommu_ops *ops;

        struct fwnode_handle *fwnode;

        struct device *dev;

};

5. 关于struct iommu_fwspec

其中,固件(比如DTS或者ACPI)对Topo和smmu的描述,从软件管理的角度,称为(定义为)iommu_fwspec,属于device,在device发现的时候就可以生成(比如pcie扫描或者devicetree/ACPI扫描的时候)【1】

struct dev_iommu {

        ...

        struct iommu_fwspec                *fwspec;

        ...

};

struct iommu_fwspec {

        const struct iommu_ops        *ops;

        struct fwnode_handle        *iommu_fwnode;

        u32                        flags;

        unsigned int                num_ids;

        u32                        ids[];

};

AMD IOMMU driver没有使用, 因其直接扫描IVRS

6. 关于aux domain, 见【2】

Reference:

[1] Linux iommu和vfio概念空间解构 - 知乎 (zhihu.com)

[2] IOMMU的现状和发展 - 知乎 (zhihu.com) 

【3】 pci: Enable overrides for missing ACS capabilities - Patchwork (kernel.org)

【4】IOMMU是如何划分PCI device group的? - 知乎 (zhihu.com)

【5】IOMMU group and PCIe ACS问题 - 知乎 (zhihu.com)

[7] 14. Linux IOMMU Support — The Linux Kernel documentation

[8]dmar 与 IOMMU | Linux Performance

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

AMD IOMMU与Linux (4) -- Domain, Group, Device 的相关文章

随机推荐