]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
driver core: Replace dev->dma_iommu with dev_dma_iommu()
authorDouglas Anderson <dianders@chromium.org>
Mon, 6 Apr 2026 23:22:56 +0000 (16:22 -0700)
committerDanilo Krummrich <dakr@kernel.org>
Sun, 26 Apr 2026 21:38:35 +0000 (23:38 +0200)
In C, bitfields are not necessarily safe to modify from multiple
threads without locking. Switch "dma_iommu" over to the "flags" field
so modifications are safe.

Cc: Leon Romanovsky <leon@kernel.org>
Cc: Robin Murphy <robin.murphy@arm.com>
Cc: Christoph Hellwig <hch@lst.de>
Reviewed-by: Rafael J. Wysocki (Intel) <rafael@kernel.org>
Reviewed-by: Danilo Krummrich <dakr@kernel.org>
Acked-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Acked-by: Marek Szyprowski <m.szyprowski@samsung.com>
Signed-off-by: Douglas Anderson <dianders@chromium.org>
Link: https://patch.msgid.link/20260406162231.v5.3.Id20d5973cbff542fea290e13177e9423f5d81342@changeid
Signed-off-by: Danilo Krummrich <dakr@kernel.org>
drivers/iommu/dma-iommu.c
drivers/iommu/iommu.c
include/linux/device.h
include/linux/iommu-dma.h

index 54d96e847f161b7f4707232d8c21394bde31eaaf..3fdcbbf273fa2072c38f484dacec334d704f795e 100644 (file)
@@ -2142,18 +2142,21 @@ EXPORT_SYMBOL_GPL(dma_iova_destroy);
 
 void iommu_setup_dma_ops(struct device *dev, struct iommu_domain *domain)
 {
+       bool dma_iommu;
+
        if (dev_is_pci(dev))
                dev->iommu->pci_32bit_workaround = !iommu_dma_forcedac;
 
-       dev->dma_iommu = iommu_is_dma_domain(domain);
-       if (dev->dma_iommu && iommu_dma_init_domain(domain, dev))
+       dma_iommu = iommu_is_dma_domain(domain);
+       dev_assign_dma_iommu(dev, dma_iommu);
+       if (dma_iommu && iommu_dma_init_domain(domain, dev))
                goto out_err;
 
        return;
 out_err:
        pr_warn("Failed to set up IOMMU for device %s; retaining platform DMA ops\n",
                dev_name(dev));
-       dev->dma_iommu = false;
+       dev_clear_dma_iommu(dev);
 }
 
 static bool has_msi_cookie(const struct iommu_domain *domain)
index 61c12ba782066adcb597f1188b848ff734c9fc48..fccdbaf6dbd573ca366c80a927c5299efca6430c 100644 (file)
@@ -590,9 +590,8 @@ static void iommu_deinit_device(struct device *dev)
        dev->iommu_group = NULL;
        module_put(ops->owner);
        dev_iommu_free(dev);
-#ifdef CONFIG_IOMMU_DMA
-       dev->dma_iommu = false;
-#endif
+       if (IS_ENABLED(CONFIG_IOMMU_DMA))
+               dev_clear_dma_iommu(dev);
 }
 
 static struct iommu_domain *pasid_array_entry_to_domain(void *entry)
index 00113821ebe9b114b18e01c69512324064d4d4c5..bb02afb00f05ef4d8fd65f43e7ff052fba885ef4 100644 (file)
@@ -515,11 +515,14 @@ struct device_physical_location {
  * @DEV_FLAG_CAN_MATCH: The device has matched with a driver at least once or it
  *             is in a bus (like AMBA) which can't check for matching drivers
  *             until other devices probe successfully.
+ * @DEV_FLAG_DMA_IOMMU: Device is using default IOMMU implementation for DMA and
+ *             doesn't rely on dma_ops structure.
  * @DEV_FLAG_COUNT: Number of defined struct_device_flags.
  */
 enum struct_device_flags {
        DEV_FLAG_READY_TO_PROBE = 0,
        DEV_FLAG_CAN_MATCH = 1,
+       DEV_FLAG_DMA_IOMMU = 2,
 
        DEV_FLAG_COUNT
 };
@@ -614,8 +617,6 @@ enum struct_device_flags {
  *             for dma allocations.  This flag is managed by the dma ops
  *             instance from ->dma_supported.
  * @dma_skip_sync: DMA sync operations can be skipped for coherent buffers.
- * @dma_iommu: Device is using default IOMMU implementation for DMA and
- *             doesn't rely on dma_ops structure.
  * @flags:     DEV_FLAG_XXX flags. Use atomic bitfield operations to modify.
  *
  * At the lowest level, every device in a Linux system is represented by an
@@ -735,9 +736,6 @@ struct device {
 #ifdef CONFIG_DMA_NEED_SYNC
        bool                    dma_skip_sync:1;
 #endif
-#ifdef CONFIG_IOMMU_DMA
-       bool                    dma_iommu:1;
-#endif
 
        DECLARE_BITMAP(flags, DEV_FLAG_COUNT);
 };
@@ -766,6 +764,7 @@ static inline bool dev_test_and_set_##accessor_name(struct device *dev) \
 
 __create_dev_flag_accessors(ready_to_probe, DEV_FLAG_READY_TO_PROBE);
 __create_dev_flag_accessors(can_match, DEV_FLAG_CAN_MATCH);
+__create_dev_flag_accessors(dma_iommu, DEV_FLAG_DMA_IOMMU);
 
 #undef __create_dev_flag_accessors
 
index a92b3ff9b93436be49e3c3c9f10ae3a614352909..060f6e23ab3c83b7659adad9988aa49c1ddaafb3 100644 (file)
@@ -7,12 +7,13 @@
 #ifndef _LINUX_IOMMU_DMA_H
 #define _LINUX_IOMMU_DMA_H
 
+#include <linux/device.h>
 #include <linux/dma-direction.h>
 
 #ifdef CONFIG_IOMMU_DMA
 static inline bool use_dma_iommu(struct device *dev)
 {
-       return dev->dma_iommu;
+       return dev_dma_iommu(dev);
 }
 #else
 static inline bool use_dma_iommu(struct device *dev)