Loading drivers/iommu/intel-iommu.c +36 −39 Original line number Original line Diff line number Diff line Loading @@ -2207,31 +2207,32 @@ static struct dmar_domain *dmar_insert_dev_info(struct intel_iommu *iommu, } } /* domain is initialized */ /* domain is initialized */ static struct dmar_domain *get_domain_for_dev(struct pci_dev *pdev, int gaw) static struct dmar_domain *get_domain_for_dev(struct device *dev, int gaw) { { struct dmar_domain *domain, *free = NULL; struct dmar_domain *domain, *free = NULL; struct intel_iommu *iommu = NULL; struct intel_iommu *iommu = NULL; struct device_domain_info *info; struct device_domain_info *info; struct dmar_drhd_unit *drhd; struct pci_dev *dev_tmp = NULL; struct pci_dev *dev_tmp; unsigned long flags; unsigned long flags; int bus = 0, devfn = 0; u8 bus, devfn, bridge_bus, bridge_devfn; int segment; domain = find_domain(&pdev->dev); domain = find_domain(dev); if (domain) if (domain) return domain; return domain; segment = pci_domain_nr(pdev->bus); if (dev_is_pci(dev)) { struct pci_dev *pdev = to_pci_dev(dev); u16 segment; segment = pci_domain_nr(pdev->bus); dev_tmp = pci_find_upstream_pcie_bridge(pdev); dev_tmp = pci_find_upstream_pcie_bridge(pdev); if (dev_tmp) { if (dev_tmp) { if (pci_is_pcie(dev_tmp)) { if (pci_is_pcie(dev_tmp)) { bus = dev_tmp->subordinate->number; bridge_bus = dev_tmp->subordinate->number; devfn = 0; bridge_devfn = 0; } else { } else { bus = dev_tmp->bus->number; bridge_bus = dev_tmp->bus->number; devfn = dev_tmp->devfn; bridge_devfn = dev_tmp->devfn; } } spin_lock_irqsave(&device_domain_lock, flags); spin_lock_irqsave(&device_domain_lock, flags); info = dmar_search_domain_by_dev_info(segment, bus, devfn); info = dmar_search_domain_by_dev_info(segment, bus, devfn); Loading @@ -2240,19 +2241,17 @@ static struct dmar_domain *get_domain_for_dev(struct pci_dev *pdev, int gaw) domain = info->domain; domain = info->domain; } } spin_unlock_irqrestore(&device_domain_lock, flags); spin_unlock_irqrestore(&device_domain_lock, flags); /* pcie-pci bridge already has a domain, uses it */ if (info) if (info) goto found_domain; goto found_domain; } } drhd = dmar_find_matched_drhd_unit(pdev); if (!drhd) { printk(KERN_ERR "IOMMU: can't find DMAR for device %s\n", pci_name(pdev)); return NULL; } } iommu = drhd->iommu; /* Allocate and intialize new domain for the device */ iommu = device_to_iommu(dev, &bus, &devfn); if (!iommu) goto error; /* Allocate and initialize new domain for the device */ domain = alloc_domain(false); domain = alloc_domain(false); if (!domain) if (!domain) goto error; goto error; Loading @@ -2266,15 +2265,14 @@ static struct dmar_domain *get_domain_for_dev(struct pci_dev *pdev, int gaw) /* register pcie-to-pci device */ /* register pcie-to-pci device */ if (dev_tmp) { if (dev_tmp) { domain = dmar_insert_dev_info(iommu, bus, devfn, NULL, domain = dmar_insert_dev_info(iommu, bridge_bus, bridge_devfn, domain); NULL, domain); if (!domain) if (!domain) goto error; goto error; } } found_domain: found_domain: domain = dmar_insert_dev_info(iommu, pdev->bus->number, domain = dmar_insert_dev_info(iommu, bus, devfn, dev, domain); pdev->devfn, &pdev->dev, domain); error: error: if (free != domain) if (free != domain) domain_exit(free); domain_exit(free); Loading Loading @@ -2320,7 +2318,7 @@ static int iommu_prepare_identity_map(struct pci_dev *pdev, struct dmar_domain *domain; struct dmar_domain *domain; int ret; int ret; domain = get_domain_for_dev(pdev, DEFAULT_DOMAIN_ADDRESS_WIDTH); domain = get_domain_for_dev(&pdev->dev, DEFAULT_DOMAIN_ADDRESS_WIDTH); if (!domain) if (!domain) return -ENOMEM; return -ENOMEM; Loading Loading @@ -2864,8 +2862,7 @@ static struct dmar_domain *__get_valid_domain_for_dev(struct pci_dev *pdev) struct dmar_domain *domain; struct dmar_domain *domain; int ret; int ret; domain = get_domain_for_dev(pdev, domain = get_domain_for_dev(&pdev->dev, DEFAULT_DOMAIN_ADDRESS_WIDTH); DEFAULT_DOMAIN_ADDRESS_WIDTH); if (!domain) { if (!domain) { printk(KERN_ERR printk(KERN_ERR "Allocating domain for %s failed", pci_name(pdev)); "Allocating domain for %s failed", pci_name(pdev)); Loading Loading
drivers/iommu/intel-iommu.c +36 −39 Original line number Original line Diff line number Diff line Loading @@ -2207,31 +2207,32 @@ static struct dmar_domain *dmar_insert_dev_info(struct intel_iommu *iommu, } } /* domain is initialized */ /* domain is initialized */ static struct dmar_domain *get_domain_for_dev(struct pci_dev *pdev, int gaw) static struct dmar_domain *get_domain_for_dev(struct device *dev, int gaw) { { struct dmar_domain *domain, *free = NULL; struct dmar_domain *domain, *free = NULL; struct intel_iommu *iommu = NULL; struct intel_iommu *iommu = NULL; struct device_domain_info *info; struct device_domain_info *info; struct dmar_drhd_unit *drhd; struct pci_dev *dev_tmp = NULL; struct pci_dev *dev_tmp; unsigned long flags; unsigned long flags; int bus = 0, devfn = 0; u8 bus, devfn, bridge_bus, bridge_devfn; int segment; domain = find_domain(&pdev->dev); domain = find_domain(dev); if (domain) if (domain) return domain; return domain; segment = pci_domain_nr(pdev->bus); if (dev_is_pci(dev)) { struct pci_dev *pdev = to_pci_dev(dev); u16 segment; segment = pci_domain_nr(pdev->bus); dev_tmp = pci_find_upstream_pcie_bridge(pdev); dev_tmp = pci_find_upstream_pcie_bridge(pdev); if (dev_tmp) { if (dev_tmp) { if (pci_is_pcie(dev_tmp)) { if (pci_is_pcie(dev_tmp)) { bus = dev_tmp->subordinate->number; bridge_bus = dev_tmp->subordinate->number; devfn = 0; bridge_devfn = 0; } else { } else { bus = dev_tmp->bus->number; bridge_bus = dev_tmp->bus->number; devfn = dev_tmp->devfn; bridge_devfn = dev_tmp->devfn; } } spin_lock_irqsave(&device_domain_lock, flags); spin_lock_irqsave(&device_domain_lock, flags); info = dmar_search_domain_by_dev_info(segment, bus, devfn); info = dmar_search_domain_by_dev_info(segment, bus, devfn); Loading @@ -2240,19 +2241,17 @@ static struct dmar_domain *get_domain_for_dev(struct pci_dev *pdev, int gaw) domain = info->domain; domain = info->domain; } } spin_unlock_irqrestore(&device_domain_lock, flags); spin_unlock_irqrestore(&device_domain_lock, flags); /* pcie-pci bridge already has a domain, uses it */ if (info) if (info) goto found_domain; goto found_domain; } } drhd = dmar_find_matched_drhd_unit(pdev); if (!drhd) { printk(KERN_ERR "IOMMU: can't find DMAR for device %s\n", pci_name(pdev)); return NULL; } } iommu = drhd->iommu; /* Allocate and intialize new domain for the device */ iommu = device_to_iommu(dev, &bus, &devfn); if (!iommu) goto error; /* Allocate and initialize new domain for the device */ domain = alloc_domain(false); domain = alloc_domain(false); if (!domain) if (!domain) goto error; goto error; Loading @@ -2266,15 +2265,14 @@ static struct dmar_domain *get_domain_for_dev(struct pci_dev *pdev, int gaw) /* register pcie-to-pci device */ /* register pcie-to-pci device */ if (dev_tmp) { if (dev_tmp) { domain = dmar_insert_dev_info(iommu, bus, devfn, NULL, domain = dmar_insert_dev_info(iommu, bridge_bus, bridge_devfn, domain); NULL, domain); if (!domain) if (!domain) goto error; goto error; } } found_domain: found_domain: domain = dmar_insert_dev_info(iommu, pdev->bus->number, domain = dmar_insert_dev_info(iommu, bus, devfn, dev, domain); pdev->devfn, &pdev->dev, domain); error: error: if (free != domain) if (free != domain) domain_exit(free); domain_exit(free); Loading Loading @@ -2320,7 +2318,7 @@ static int iommu_prepare_identity_map(struct pci_dev *pdev, struct dmar_domain *domain; struct dmar_domain *domain; int ret; int ret; domain = get_domain_for_dev(pdev, DEFAULT_DOMAIN_ADDRESS_WIDTH); domain = get_domain_for_dev(&pdev->dev, DEFAULT_DOMAIN_ADDRESS_WIDTH); if (!domain) if (!domain) return -ENOMEM; return -ENOMEM; Loading Loading @@ -2864,8 +2862,7 @@ static struct dmar_domain *__get_valid_domain_for_dev(struct pci_dev *pdev) struct dmar_domain *domain; struct dmar_domain *domain; int ret; int ret; domain = get_domain_for_dev(pdev, domain = get_domain_for_dev(&pdev->dev, DEFAULT_DOMAIN_ADDRESS_WIDTH); DEFAULT_DOMAIN_ADDRESS_WIDTH); if (!domain) { if (!domain) { printk(KERN_ERR printk(KERN_ERR "Allocating domain for %s failed", pci_name(pdev)); "Allocating domain for %s failed", pci_name(pdev)); Loading