* [PATCH v3 1/3] RDMA/usnic: Remove iommu_set_fault_handler()
2025-11-20 19:46 [PATCH v3 0/3] Cleanup around iommu_set_fault_handler() Jason Gunthorpe
@ 2025-11-20 19:46 ` Jason Gunthorpe
2025-11-23 9:29 ` Leon Romanovsky
2025-11-20 19:46 ` [PATCH v3 2/3] iommu/amd: Don't call report_iommu_fault() Jason Gunthorpe
2025-11-20 19:46 ` [PATCH v3 3/3] iommu: Allow drivers to say if they use report_iommu_fault() Jason Gunthorpe
2 siblings, 1 reply; 6+ messages in thread
From: Jason Gunthorpe @ 2025-11-20 19:46 UTC (permalink / raw)
To: AngeloGioacchino Del Regno, Christian Benvenuti, Heiko Stuebner,
iommu, Jernej Skrabec, Joerg Roedel, Leon Romanovsky,
linux-arm-kernel, linux-arm-msm, linux-mediatek, linux-rdma,
linux-rockchip, linux-sunxi, Matthias Brugger, Nelson Escobar,
Rob Clark, Robin Murphy, Samuel Holland, Suravee Suthikulpanit,
Chen-Yu Tsai, Will Deacon, Yong Wu
Cc: Lu Baolu, Kevin Tian, patches, Vasant Hegde
The handler in usnic just prints a fault report message, the iommu drivers
all do a better job of that these days. Just remove the use of this old
API.
Reviewed-by: Lu Baolu <baolu.lu@linux.intel.com>
Reviewed-by: Kevin Tian <kevin.tian@intel.com>
Acked-by: Jason Gunthorpe <jgg@nvidia.com>
Signed-off-by: Jason Gunthorpe <jgg@nvidia.com>
---
drivers/infiniband/hw/usnic/usnic_uiom.c | 13 -------------
1 file changed, 13 deletions(-)
diff --git a/drivers/infiniband/hw/usnic/usnic_uiom.c b/drivers/infiniband/hw/usnic/usnic_uiom.c
index 3fbf99757b1148..f7fb6246c83aba 100644
--- a/drivers/infiniband/hw/usnic/usnic_uiom.c
+++ b/drivers/infiniband/hw/usnic/usnic_uiom.c
@@ -51,17 +51,6 @@
((void *) &((struct usnic_uiom_chunk *) 0)->page_list[1] - \
(void *) &((struct usnic_uiom_chunk *) 0)->page_list[0]))
-static int usnic_uiom_dma_fault(struct iommu_domain *domain,
- struct device *dev,
- unsigned long iova, int flags,
- void *token)
-{
- usnic_err("Device %s iommu fault domain 0x%p va 0x%lx flags 0x%x\n",
- dev_name(dev),
- domain, iova, flags);
- return -ENOSYS;
-}
-
static void usnic_uiom_put_pages(struct list_head *chunk_list, int dirty)
{
struct usnic_uiom_chunk *chunk, *tmp;
@@ -450,8 +439,6 @@ struct usnic_uiom_pd *usnic_uiom_alloc_pd(struct device *dev)
return ERR_CAST(domain);
}
- iommu_set_fault_handler(pd->domain, usnic_uiom_dma_fault, NULL);
-
spin_lock_init(&pd->lock);
INIT_LIST_HEAD(&pd->devs);
--
2.43.0
^ permalink raw reply related [flat|nested] 6+ messages in thread* [PATCH v3 2/3] iommu/amd: Don't call report_iommu_fault()
2025-11-20 19:46 [PATCH v3 0/3] Cleanup around iommu_set_fault_handler() Jason Gunthorpe
2025-11-20 19:46 ` [PATCH v3 1/3] RDMA/usnic: Remove iommu_set_fault_handler() Jason Gunthorpe
@ 2025-11-20 19:46 ` Jason Gunthorpe
2025-11-21 7:24 ` Tian, Kevin
2025-11-20 19:46 ` [PATCH v3 3/3] iommu: Allow drivers to say if they use report_iommu_fault() Jason Gunthorpe
2 siblings, 1 reply; 6+ messages in thread
From: Jason Gunthorpe @ 2025-11-20 19:46 UTC (permalink / raw)
To: AngeloGioacchino Del Regno, Christian Benvenuti, Heiko Stuebner,
iommu, Jernej Skrabec, Joerg Roedel, Leon Romanovsky,
linux-arm-kernel, linux-arm-msm, linux-mediatek, linux-rdma,
linux-rockchip, linux-sunxi, Matthias Brugger, Nelson Escobar,
Rob Clark, Robin Murphy, Samuel Holland, Suravee Suthikulpanit,
Chen-Yu Tsai, Will Deacon, Yong Wu
Cc: Lu Baolu, Kevin Tian, patches, Vasant Hegde
This old style API is only used by drivers/gpu/drm/msm,
drivers/remoteproc/omap_remoteproc.c, and
drivers/remoteproc/qcom_q6v5_adsp.c none are used on x86 HW.
Remove the dead code to discourage new users.
Also remove the domain == NULL print because it was intended to protect
against a NULL deref inside report_iommu_fault() which is no longer
possible.
Just always print the fault in the same format if it could get a dev_data.
There is no value to be gained by also printing if the domain is NULL. In
today's kernel when the dev_data is populated the domain will be made
!NULL very quickly during iommu device probing.
Reviewed-by: Vasant Hegde <vasant.hegde@amd.com>
Signed-off-by: Jason Gunthorpe <jgg@nvidia.com>
---
drivers/iommu/amd/iommu.c | 24 ------------------------
1 file changed, 24 deletions(-)
diff --git a/drivers/iommu/amd/iommu.c b/drivers/iommu/amd/iommu.c
index 2e1865daa1cee8..072c80bb2c2b3a 100644
--- a/drivers/iommu/amd/iommu.c
+++ b/drivers/iommu/amd/iommu.c
@@ -840,29 +840,6 @@ static void amd_iommu_report_page_fault(struct amd_iommu *iommu,
dev_data = dev_iommu_priv_get(&pdev->dev);
if (dev_data) {
- /*
- * If this is a DMA fault (for which the I(nterrupt)
- * bit will be unset), allow report_iommu_fault() to
- * prevent logging it.
- */
- if (IS_IOMMU_MEM_TRANSACTION(flags)) {
- /* Device not attached to domain properly */
- if (dev_data->domain == NULL) {
- pr_err_ratelimited("Event logged [Device not attached to domain properly]\n");
- pr_err_ratelimited(" device=%04x:%02x:%02x.%x domain=0x%04x\n",
- iommu->pci_seg->id, PCI_BUS_NUM(devid), PCI_SLOT(devid),
- PCI_FUNC(devid), domain_id);
- goto out;
- }
-
- if (!report_iommu_fault(&dev_data->domain->domain,
- &pdev->dev, address,
- IS_WRITE_REQUEST(flags) ?
- IOMMU_FAULT_WRITE :
- IOMMU_FAULT_READ))
- goto out;
- }
-
if (__ratelimit(&dev_data->rs)) {
pci_err(pdev, "Event logged [IO_PAGE_FAULT domain=0x%04x address=0x%llx flags=0x%04x]\n",
domain_id, address, flags);
@@ -873,7 +850,6 @@ static void amd_iommu_report_page_fault(struct amd_iommu *iommu,
domain_id, address, flags);
}
-out:
if (pdev)
pci_dev_put(pdev);
}
--
2.43.0
^ permalink raw reply related [flat|nested] 6+ messages in thread* [PATCH v3 3/3] iommu: Allow drivers to say if they use report_iommu_fault()
2025-11-20 19:46 [PATCH v3 0/3] Cleanup around iommu_set_fault_handler() Jason Gunthorpe
2025-11-20 19:46 ` [PATCH v3 1/3] RDMA/usnic: Remove iommu_set_fault_handler() Jason Gunthorpe
2025-11-20 19:46 ` [PATCH v3 2/3] iommu/amd: Don't call report_iommu_fault() Jason Gunthorpe
@ 2025-11-20 19:46 ` Jason Gunthorpe
2 siblings, 0 replies; 6+ messages in thread
From: Jason Gunthorpe @ 2025-11-20 19:46 UTC (permalink / raw)
To: AngeloGioacchino Del Regno, Christian Benvenuti, Heiko Stuebner,
iommu, Jernej Skrabec, Joerg Roedel, Leon Romanovsky,
linux-arm-kernel, linux-arm-msm, linux-mediatek, linux-rdma,
linux-rockchip, linux-sunxi, Matthias Brugger, Nelson Escobar,
Rob Clark, Robin Murphy, Samuel Holland, Suravee Suthikulpanit,
Chen-Yu Tsai, Will Deacon, Yong Wu
Cc: Lu Baolu, Kevin Tian, patches, Vasant Hegde
report_iommu_fault() is an older API that has been superseded by
iommu_report_device_fault() which is capable to support PRI.
Only two external drivers consume this, drivers/remoteproc and
drivers/gpu/drm/msm. Ideally they would move over to the new APIs, but for
now protect against accidentally mix and matching the wrong components.
The iommu drivers support either the old iommu_set_fault_handler() via the
driver calling report_iommu_fault(), or they are newer server focused
drivers that call iommu_report_device_fault().
Include a flag in the iommu_ops if the driver calls report_iommu_fault()
and block iommu_set_fault_handler() for domain's of iommu drivers that
can't support it.
Reviewed-by: Lu Baolu <baolu.lu@linux.intel.com>
Reviewed-by: Kevin Tian <kevin.tian@intel.com>
Reviewed-by: Vasant Hegde <vasant.hegde@amd.com>
Signed-off-by: Jason Gunthorpe <jgg@nvidia.com>
---
drivers/iommu/arm/arm-smmu/arm-smmu.c | 1 +
drivers/iommu/arm/arm-smmu/qcom_iommu.c | 1 +
drivers/iommu/iommu.c | 6 +++++-
drivers/iommu/ipmmu-vmsa.c | 1 +
drivers/iommu/mtk_iommu.c | 1 +
drivers/iommu/mtk_iommu_v1.c | 1 +
drivers/iommu/omap-iommu.c | 1 +
drivers/iommu/rockchip-iommu.c | 1 +
drivers/iommu/sun50i-iommu.c | 1 +
include/linux/iommu.h | 3 +++
10 files changed, 16 insertions(+), 1 deletion(-)
diff --git a/drivers/iommu/arm/arm-smmu/arm-smmu.c b/drivers/iommu/arm/arm-smmu/arm-smmu.c
index 4ced4b5bee4df3..f68a0576b9a3a6 100644
--- a/drivers/iommu/arm/arm-smmu/arm-smmu.c
+++ b/drivers/iommu/arm/arm-smmu/arm-smmu.c
@@ -1643,6 +1643,7 @@ static const struct iommu_ops arm_smmu_ops = {
.get_resv_regions = arm_smmu_get_resv_regions,
.def_domain_type = arm_smmu_def_domain_type,
.owner = THIS_MODULE,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = arm_smmu_attach_dev,
.map_pages = arm_smmu_map_pages,
diff --git a/drivers/iommu/arm/arm-smmu/qcom_iommu.c b/drivers/iommu/arm/arm-smmu/qcom_iommu.c
index c5be95e560317e..173d5957796790 100644
--- a/drivers/iommu/arm/arm-smmu/qcom_iommu.c
+++ b/drivers/iommu/arm/arm-smmu/qcom_iommu.c
@@ -597,6 +597,7 @@ static const struct iommu_ops qcom_iommu_ops = {
.probe_device = qcom_iommu_probe_device,
.device_group = generic_device_group,
.of_xlate = qcom_iommu_of_xlate,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = qcom_iommu_attach_dev,
.map_pages = qcom_iommu_map,
diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 59244c744eabd2..8d9086a37671e1 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -2005,6 +2005,9 @@ EXPORT_SYMBOL_GPL(iommu_group_has_isolated_msi);
* This function should be used by IOMMU users which want to be notified
* whenever an IOMMU fault happens.
*
+ * This is a legacy API not supported by all drivers. New users should look
+ * to using domain->iopf_handler for the modern API.
+ *
* The fault handler itself should return 0 on success, and an appropriate
* error code otherwise.
*/
@@ -2012,7 +2015,8 @@ void iommu_set_fault_handler(struct iommu_domain *domain,
iommu_fault_handler_t handler,
void *token)
{
- if (WARN_ON(!domain || domain->cookie_type != IOMMU_COOKIE_NONE))
+ if (WARN_ON(!domain || domain->cookie_type != IOMMU_COOKIE_NONE ||
+ !domain->owner->report_iommu_fault_supported))
return;
domain->cookie_type = IOMMU_COOKIE_FAULT_HANDLER;
diff --git a/drivers/iommu/ipmmu-vmsa.c b/drivers/iommu/ipmmu-vmsa.c
index ffa892f6571406..04a5836bf36000 100644
--- a/drivers/iommu/ipmmu-vmsa.c
+++ b/drivers/iommu/ipmmu-vmsa.c
@@ -884,6 +884,7 @@ static const struct iommu_ops ipmmu_ops = {
.device_group = IS_ENABLED(CONFIG_ARM) && !IS_ENABLED(CONFIG_IOMMU_DMA)
? generic_device_group : generic_single_device_group,
.of_xlate = ipmmu_of_xlate,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = ipmmu_attach_device,
.map_pages = ipmmu_map,
diff --git a/drivers/iommu/mtk_iommu.c b/drivers/iommu/mtk_iommu.c
index 0e0285348d2b8e..ccf6fdeb64a261 100644
--- a/drivers/iommu/mtk_iommu.c
+++ b/drivers/iommu/mtk_iommu.c
@@ -1018,6 +1018,7 @@ static const struct iommu_ops mtk_iommu_ops = {
.of_xlate = mtk_iommu_of_xlate,
.get_resv_regions = mtk_iommu_get_resv_regions,
.owner = THIS_MODULE,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = mtk_iommu_attach_device,
.map_pages = mtk_iommu_map,
diff --git a/drivers/iommu/mtk_iommu_v1.c b/drivers/iommu/mtk_iommu_v1.c
index 10cc0b1197e801..3dd6222d210921 100644
--- a/drivers/iommu/mtk_iommu_v1.c
+++ b/drivers/iommu/mtk_iommu_v1.c
@@ -581,6 +581,7 @@ static const struct iommu_ops mtk_iommu_v1_ops = {
.release_device = mtk_iommu_v1_release_device,
.device_group = generic_device_group,
.owner = THIS_MODULE,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = mtk_iommu_v1_attach_device,
.map_pages = mtk_iommu_v1_map,
diff --git a/drivers/iommu/omap-iommu.c b/drivers/iommu/omap-iommu.c
index 5c6f5943f44b1f..7ba67600f32915 100644
--- a/drivers/iommu/omap-iommu.c
+++ b/drivers/iommu/omap-iommu.c
@@ -1723,6 +1723,7 @@ static const struct iommu_ops omap_iommu_ops = {
.release_device = omap_iommu_release_device,
.device_group = generic_single_device_group,
.of_xlate = omap_iommu_of_xlate,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = omap_iommu_attach_dev,
.map_pages = omap_iommu_map,
diff --git a/drivers/iommu/rockchip-iommu.c b/drivers/iommu/rockchip-iommu.c
index 0861dd469bd866..932b5a62bac572 100644
--- a/drivers/iommu/rockchip-iommu.c
+++ b/drivers/iommu/rockchip-iommu.c
@@ -1173,6 +1173,7 @@ static const struct iommu_ops rk_iommu_ops = {
.release_device = rk_iommu_release_device,
.device_group = generic_single_device_group,
.of_xlate = rk_iommu_of_xlate,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = rk_iommu_attach_device,
.map_pages = rk_iommu_map,
diff --git a/drivers/iommu/sun50i-iommu.c b/drivers/iommu/sun50i-iommu.c
index de10b569d9a940..13c37b1be481d7 100644
--- a/drivers/iommu/sun50i-iommu.c
+++ b/drivers/iommu/sun50i-iommu.c
@@ -848,6 +848,7 @@ static const struct iommu_ops sun50i_iommu_ops = {
.domain_alloc_paging = sun50i_iommu_domain_alloc_paging,
.of_xlate = sun50i_iommu_of_xlate,
.probe_device = sun50i_iommu_probe_device,
+ .report_iommu_fault_supported = true,
.default_domain_ops = &(const struct iommu_domain_ops) {
.attach_dev = sun50i_iommu_attach_device,
.flush_iotlb_all = sun50i_iommu_flush_iotlb_all,
diff --git a/include/linux/iommu.h b/include/linux/iommu.h
index c30d12e16473df..941e4971b05fd3 100644
--- a/include/linux/iommu.h
+++ b/include/linux/iommu.h
@@ -659,6 +659,8 @@ __iommu_copy_struct_to_user(const struct iommu_user_data *dst_data,
* no user domain for each PASID and the I/O page faults are
* forwarded through the user domain attached to the device
* RID.
+ * @report_iommu_fault_supported: True if the domain supports
+ * iommu_set_fault_handler()
*/
struct iommu_ops {
bool (*capable)(struct device *dev, enum iommu_cap);
@@ -710,6 +712,7 @@ struct iommu_ops {
struct iommu_domain *release_domain;
struct iommu_domain *default_domain;
u8 user_pasid_table:1;
+ u8 report_iommu_fault_supported:1;
};
/**
--
2.43.0
^ permalink raw reply related [flat|nested] 6+ messages in thread