mirror of
https://github.com/AuxXxilium/linux_dsm_epyc7002.git
synced 2024-12-15 23:56:45 +07:00
iommu/arm-smmu-v3: Unregister IOMMU and bus ops on device removal
When removing the SMMUv3 driver, we need to clear any state that we registered during probe. This includes our bus ops, sysfs entries and the IOMMU device registered for early firmware probing of masters. Signed-off-by: Will Deacon <will@kernel.org> Tested-by: John Garry <john.garry@huawei.com> # smmu v3 Reviewed-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> Signed-off-by: Joerg Roedel <jroedel@suse.de>
This commit is contained in:
parent
34debdca68
commit
ab24677471
@ -3565,6 +3565,45 @@ static unsigned long arm_smmu_resource_size(struct arm_smmu_device *smmu)
|
||||
return SZ_128K;
|
||||
}
|
||||
|
||||
static int arm_smmu_set_bus_ops(struct iommu_ops *ops)
|
||||
{
|
||||
int err;
|
||||
|
||||
#ifdef CONFIG_PCI
|
||||
if (pci_bus_type.iommu_ops != ops) {
|
||||
if (ops)
|
||||
pci_request_acs();
|
||||
err = bus_set_iommu(&pci_bus_type, ops);
|
||||
if (err)
|
||||
return err;
|
||||
}
|
||||
#endif
|
||||
#ifdef CONFIG_ARM_AMBA
|
||||
if (amba_bustype.iommu_ops != ops) {
|
||||
err = bus_set_iommu(&amba_bustype, ops);
|
||||
if (err)
|
||||
goto err_reset_pci_ops;
|
||||
}
|
||||
#endif
|
||||
if (platform_bus_type.iommu_ops != ops) {
|
||||
err = bus_set_iommu(&platform_bus_type, ops);
|
||||
if (err)
|
||||
goto err_reset_amba_ops;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
||||
err_reset_amba_ops:
|
||||
#ifdef CONFIG_ARM_AMBA
|
||||
bus_set_iommu(&amba_bustype, NULL);
|
||||
#endif
|
||||
err_reset_pci_ops: __maybe_unused;
|
||||
#ifdef CONFIG_PCI
|
||||
bus_set_iommu(&pci_bus_type, NULL);
|
||||
#endif
|
||||
return err;
|
||||
}
|
||||
|
||||
static int arm_smmu_device_probe(struct platform_device *pdev)
|
||||
{
|
||||
int irq, ret;
|
||||
@ -3655,33 +3694,16 @@ static int arm_smmu_device_probe(struct platform_device *pdev)
|
||||
return ret;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_PCI
|
||||
if (pci_bus_type.iommu_ops != &arm_smmu_ops) {
|
||||
pci_request_acs();
|
||||
ret = bus_set_iommu(&pci_bus_type, &arm_smmu_ops);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
#endif
|
||||
#ifdef CONFIG_ARM_AMBA
|
||||
if (amba_bustype.iommu_ops != &arm_smmu_ops) {
|
||||
ret = bus_set_iommu(&amba_bustype, &arm_smmu_ops);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
#endif
|
||||
if (platform_bus_type.iommu_ops != &arm_smmu_ops) {
|
||||
ret = bus_set_iommu(&platform_bus_type, &arm_smmu_ops);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
return 0;
|
||||
return arm_smmu_set_bus_ops(&arm_smmu_ops);
|
||||
}
|
||||
|
||||
static int arm_smmu_device_remove(struct platform_device *pdev)
|
||||
{
|
||||
struct arm_smmu_device *smmu = platform_get_drvdata(pdev);
|
||||
|
||||
arm_smmu_set_bus_ops(NULL);
|
||||
iommu_device_unregister(&smmu->iommu);
|
||||
iommu_device_sysfs_remove(&smmu->iommu);
|
||||
arm_smmu_device_disable(smmu);
|
||||
|
||||
return 0;
|
||||
|
Loading…
Reference in New Issue
Block a user