From: Yi Liu <yi.l....@intel.com>

Introduce pci_device_iommu_get_attr() to get vIOMMU attributes
from the PCI device.

This is in preparation to ask if vIOMMU has dma translation enabled
and also to get IOVA boundaries.

Signed-off-by: Yi Liu <yi.l....@intel.com>
[joao: Massage commit message; add one more argument in
 pci_device_get_iommu_bus_devfn(); rename to pci_device_iommu_get_attr()
 to align with the other already namespaced function. ]
Signed-off-by: Joao Martins <joao.m.mart...@oracle.com>
---
follow-up version from:
https://lore.kernel.org/all/20210302203827.437645-6-yi.l....@intel.com/
---
 include/hw/pci/pci.h |  4 ++++
 hw/pci/pci.c         | 16 ++++++++++++++++
 2 files changed, 20 insertions(+)

diff --git a/include/hw/pci/pci.h b/include/hw/pci/pci.h
index f59aef5a329a..10c81287b6b3 100644
--- a/include/hw/pci/pci.h
+++ b/include/hw/pci/pci.h
@@ -372,8 +372,12 @@ typedef struct PCIIOMMUOps PCIIOMMUOps;
 struct PCIIOMMUOps {
     AddressSpace * (*get_address_space)(PCIBus *bus,
                                 void *opaque, int32_t devfn);
+    int (*get_iommu_attr)(PCIBus *bus, void *opaque, int32_t devfn,
+                          enum IOMMUMemoryRegionAttr attr, void *data);
 };
 void pci_setup_iommu_ops(PCIBus *bus, const PCIIOMMUOps *iommu_ops, void 
*opaque);
+int pci_device_iommu_get_attr(PCIDevice *dev, enum IOMMUMemoryRegionAttr attr,
+                              void *data);
 
 pcibus_t pci_bar_address(PCIDevice *d,
                          int reg, uint8_t type, pcibus_t size);
diff --git a/hw/pci/pci.c b/hw/pci/pci.c
index 90ae92a43d85..91ba6f0927a4 100644
--- a/hw/pci/pci.c
+++ b/hw/pci/pci.c
@@ -2710,6 +2710,22 @@ AddressSpace *pci_device_iommu_address_space(PCIDevice 
*dev)
     return &address_space_memory;
 }
 
+int pci_device_iommu_get_attr(PCIDevice *dev, enum IOMMUMemoryRegionAttr attr,
+                              void *data)
+{
+    PCIBus *bus, *iommu_bus;
+    uint8_t devfn;
+
+    pci_device_get_iommu_bus_devfn(dev, &bus, &iommu_bus, &devfn);
+    if (!pci_bus_bypass_iommu(bus) && iommu_bus &&
+        iommu_bus->iommu_ops && iommu_bus->iommu_ops->get_iommu_attr) {
+        return iommu_bus->iommu_ops->get_iommu_attr(bus, 
iommu_bus->iommu_opaque,
+                                                    devfn, attr, data);
+    }
+
+    return -ENOENT;
+}
+
 void pci_setup_iommu(PCIBus *bus, PCIIOMMUFunc fn, void *opaque)
 {
     bus->iommu_fn = fn;
-- 
2.17.2


Reply via email to