VT-d: split domid map cleanup check into a function

This logic will want invoking from elsewhere.

No functional change intended.

Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Reviewed-by: Kevin Tian <kevin.tian@intel.com>
master commit: 9fdc10abe9
master date: 2021-11-24 11:06:20 +0100
This commit is contained in:
Jan Beulich committed 2022-01-07 08:51:05 +01:00
1 parent a51f2df5dc
commit 992ba6df20
1 file changed
+47 -42
+47 -42
View File
@@ -153,6 +153,51 @@ static void cleanup_domid_map(struct domain *domain, struct vtd_iommu *iommu)
}
}
static bool any_pdev_behind_iommu(const struct domain *d,
const struct pci_dev *exclude,
const struct vtd_iommu *iommu)
{
const struct pci_dev *pdev;
for_each_pdev ( d, pdev )
{
const struct acpi_drhd_unit *drhd;
if ( pdev == exclude )
continue;
drhd = acpi_find_matched_drhd_unit(pdev);
if ( drhd && drhd->iommu == iommu )
return true;
}
return false;
}
/*
* If no other devices under the same iommu owned by this domain,
* clear iommu in iommu_bitmap and clear domain_id in domid_bitmap.
*/
static void check_cleanup_domid_map(struct domain *d,
const struct pci_dev *exclude,
struct vtd_iommu *iommu)
{
bool found = any_pdev_behind_iommu(d, exclude, iommu);
/*
* Hidden devices are associated with DomXEN but usable by the hardware
* domain. Hence they need considering here as well.
*/
if ( !found && is_hardware_domain(d) )
found = any_pdev_behind_iommu(dom_xen, exclude, iommu);
if ( !found )
{
clear_bit(iommu->index, &dom_iommu(d)->arch.iommu_bitmap);
cleanup_domid_map(d, iommu);
}
}
static int iommus_incoherent;
static void sync_cache(const void *addr, unsigned int size)
@@ -1674,27 +1719,6 @@ int domain_context_unmap_one(
return rc;
}
static bool any_pdev_behind_iommu(const struct domain *d,
const struct pci_dev *exclude,
const struct vtd_iommu *iommu)
{
const struct pci_dev *pdev;
for_each_pdev ( d, pdev )
{
const struct acpi_drhd_unit *drhd;
if ( pdev == exclude )
continue;
drhd = acpi_find_matched_drhd_unit(pdev);
if ( drhd && drhd->iommu == iommu )
return true;
}
return false;
}
static int domain_context_unmap(struct domain *domain, u8 devfn,
struct pci_dev *pdev)
{
@@ -1703,7 +1727,6 @@ static int domain_context_unmap(struct domain *domain, u8 devfn,
int ret = 0;
uint16_t seg = pdev->seg;
uint8_t bus = pdev->bus, tmp_bus, tmp_devfn, secbus;
bool found;
drhd = acpi_find_matched_drhd_unit(pdev);
if ( !drhd )
@@ -1784,26 +1807,8 @@ static int domain_context_unmap(struct domain *domain, u8 devfn,
goto out;
}
if ( ret )
goto out;
/*
* If no other devices under the same iommu owned by this domain,
* clear iommu in iommu_bitmap and clear domain_id in domid_bitmap.
*/
found = any_pdev_behind_iommu(domain, pdev, iommu);
/*
* Hidden devices are associated with DomXEN but usable by the hardware
* domain. Hence they need considering here as well.
*/
if ( !found && is_hardware_domain(domain) )
found = any_pdev_behind_iommu(dom_xen, pdev, iommu);
if ( !found )
{
clear_bit(iommu->index, &dom_iommu(domain)->arch.iommu_bitmap);
cleanup_domid_map(domain, iommu);
}
if ( !ret )
check_cleanup_domid_map(domain, pdev, iommu);
out:
return ret;
Reference in new issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.