iommu/vt-d: Introduce is_downstream_to_pci_bridge helper

Several call sites are about to check whether a device belongs
to the PCI sub-hierarchy of a candidate PCI-PCI bridge.
Introduce an helper to perform that check.

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Lu Baolu <baolu.lu@linux.intel.com>
Signed-off-by: Joerg Roedel <jroedel@suse.de>
This commit is contained in:
Eric Auger 2019-06-03 08:53:32 +02:00 committed by Joerg Roedel
parent 5f64ce5411
commit b9a7f98164

View File

@ -729,12 +729,39 @@ static int iommu_dummy(struct device *dev)
return dev->archdata.iommu == DUMMY_DEVICE_DOMAIN_INFO; return dev->archdata.iommu == DUMMY_DEVICE_DOMAIN_INFO;
} }
/**
* is_downstream_to_pci_bridge - test if a device belongs to the PCI
* sub-hierarchy of a candidate PCI-PCI bridge
* @dev: candidate PCI device belonging to @bridge PCI sub-hierarchy
* @bridge: the candidate PCI-PCI bridge
*
* Return: true if @dev belongs to @bridge PCI sub-hierarchy, else false.
*/
static bool
is_downstream_to_pci_bridge(struct device *dev, struct device *bridge)
{
struct pci_dev *pdev, *pbridge;
if (!dev_is_pci(dev) || !dev_is_pci(bridge))
return false;
pdev = to_pci_dev(dev);
pbridge = to_pci_dev(bridge);
if (pbridge->subordinate &&
pbridge->subordinate->number <= pdev->bus->number &&
pbridge->subordinate->busn_res.end >= pdev->bus->number)
return true;
return false;
}
static struct intel_iommu *device_to_iommu(struct device *dev, u8 *bus, u8 *devfn) static struct intel_iommu *device_to_iommu(struct device *dev, u8 *bus, u8 *devfn)
{ {
struct dmar_drhd_unit *drhd = NULL; struct dmar_drhd_unit *drhd = NULL;
struct intel_iommu *iommu; struct intel_iommu *iommu;
struct device *tmp; struct device *tmp;
struct pci_dev *ptmp, *pdev = NULL; struct pci_dev *pdev = NULL;
u16 segment = 0; u16 segment = 0;
int i; int i;
@ -780,13 +807,7 @@ static struct intel_iommu *device_to_iommu(struct device *dev, u8 *bus, u8 *devf
goto out; goto out;
} }
if (!pdev || !dev_is_pci(tmp)) if (is_downstream_to_pci_bridge(dev, tmp))
continue;
ptmp = to_pci_dev(tmp);
if (ptmp->subordinate &&
ptmp->subordinate->number <= pdev->bus->number &&
ptmp->subordinate->busn_res.end >= pdev->bus->number)
goto got_pdev; goto got_pdev;
} }