[PATCH v4 05/21] iommu: Document MSI mapping during domain replacement

From: Andrew Jones

Date: Thu Aug 20 2026 - 17:42:18 EST


Interrupt-remapping drivers may need to prepare software MSI mappings
for an incoming domain from their attach_dev() callback. At that point
the device is not yet attached to the supplied domain and, for an
iommufd replacement, the current attach handle still describes the old
domain.

Document that iommu_dma_map_msi() supports this use. Clarify the DMA
backend only requires a compatible device and that the iommufd backend
intentionally combines context from the current handle with the
explicitly supplied destination HWPT.

Signed-off-by: Andrew Jones <andrew.jones@xxxxxxxxxxxxxxxx>
---
drivers/iommu/dma-iommu.c | 7 ++++---
drivers/iommu/iommu.c | 5 +++++
drivers/iommu/iommufd/driver.c | 8 +++++---
3 files changed, 14 insertions(+), 6 deletions(-)

diff --git a/drivers/iommu/dma-iommu.c b/drivers/iommu/dma-iommu.c
index 39ee5f0b1da9..030948a7e6b9 100644
--- a/drivers/iommu/dma-iommu.c
+++ b/drivers/iommu/dma-iommu.c
@@ -2252,9 +2252,10 @@ static struct iommu_dma_msi_page *iommu_dma_get_msi_page(struct device *dev,
* mapping granule. Used for pre-mapping MSI targets before any MSI
* descriptor has been set.
*
- * The caller must pass a device attached to @domain and hold @dev's IOMMU
- * group mutex. If @required_size is non-zero then it must exactly match the
- * domain's MSI mapping granule. @msi_iova and @msi_shift must be non-NULL.
+ * The caller must pass a device compatible with @domain and hold @dev's IOMMU
+ * group mutex. @domain may be the incoming domain of an attach_dev() callback.
+ * If @required_size is non-zero then it must exactly match the domain's MSI
+ * mapping granule. @msi_iova and @msi_shift must be non-NULL.
*/
int iommu_dma_sw_map_msi(struct iommu_domain *domain,
struct device *dev, phys_addr_t msi_addr,
diff --git a/drivers/iommu/iommu.c b/drivers/iommu/iommu.c
index 84b60d0f8c23..389d67c4bda3 100644
--- a/drivers/iommu/iommu.c
+++ b/drivers/iommu/iommu.c
@@ -4272,6 +4272,11 @@ EXPORT_SYMBOL_GPL(pci_dev_reset_iommu_done);
* stop the domain from changing between iterations, leaving the table
* inconsistent. The caller locks once around the whole loop instead.
*
+ * @domain may be the incoming domain of an attach_dev() callback. In that
+ * case, @dev need not be attached to @domain yet, but it must be compatible
+ * with @domain and the caller must keep the current group attachment stable
+ * until the callback completes.
+ *
* Return: 0 on success or negative error code if the mapping failed.
*/
int iommu_dma_map_msi(struct iommu_domain *domain,
diff --git a/drivers/iommu/iommufd/driver.c b/drivers/iommu/iommufd/driver.c
index b39796bc7251..358cc6d87941 100644
--- a/drivers/iommu/iommufd/driver.c
+++ b/drivers/iommu/iommufd/driver.c
@@ -281,9 +281,11 @@ int iommufd_sw_map_msi(struct iommu_domain *domain, struct device *dev,
return -EOPNOTSUPP;

/*
- * It is safe to call iommu_attach_handle_get() here because the iommu
- * core code invokes this under the group mutex which also prevents any
- * change of the attach handle for the duration of this function.
+ * During a domain replacement this returns the current handle, not the
+ * handle for @domain. That is intentional: the current handle supplies
+ * the stable iommufd context and group MSI window, while @domain selects
+ * the HWPT where the mapping is installed. The group mutex prevents the
+ * current handle from changing for the duration of this function.
*/
iommu_group_mutex_assert(dev);

--
2.43.0