dma-mapping: Add helpers for dma_range_map bounds
authorRobin Murphy <robin.murphy@arm.com>
Fri, 19 Apr 2024 16:54:43 +0000 (17:54 +0100)
committerJoerg Roedel <jroedel@suse.de>
Fri, 26 Apr 2024 10:07:24 +0000 (12:07 +0200)
Several places want to compute the lower and/or upper bounds of a
dma_range_map, so let's factor that out into reusable helpers.

Acked-by: Rob Herring <robh@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
Reviewed-by: Hanjun Guo <guohanjun@huawei.com> # For arm64
Reviewed-by: Jason Gunthorpe <jgg@nvidia.com>
Tested-by: Hanjun Guo <guohanjun@huawei.com>
Signed-off-by: Robin Murphy <robin.murphy@arm.com>
Link: https://lore.kernel.org/r/45ec52f033ec4dfb364e23f48abaf787f612fa53.1713523152.git.robin.murphy@arm.com
Signed-off-by: Joerg Roedel <jroedel@suse.de>
arch/loongarch/kernel/dma.c
drivers/acpi/arm64/dma.c
drivers/of/device.c
include/linux/dma-direct.h

index 7a9c6a9dd2d01fb429b67aea02deada5e5b1f3be..429555fb4e13896a19abb83f6b1f11063e6f61a7 100644 (file)
@@ -8,17 +8,12 @@
 void acpi_arch_dma_setup(struct device *dev)
 {
        int ret;
-       u64 mask, end = 0;
+       u64 mask, end;
        const struct bus_dma_region *map = NULL;
 
        ret = acpi_dma_get_range(dev, &map);
        if (!ret && map) {
-               const struct bus_dma_region *r = map;
-
-               for (end = 0; r->size; r++) {
-                       if (r->dma_start + r->size - 1 > end)
-                               end = r->dma_start + r->size - 1;
-               }
+               end = dma_range_map_max(map);
 
                mask = DMA_BIT_MASK(ilog2(end) + 1);
                dev->bus_dma_limit = end;
index b98a149f8d509f75c07c869a71953ffd80b657da..52b2abf88689824bad7d08ae83515cb5b2ee1502 100644 (file)
@@ -28,13 +28,7 @@ void acpi_arch_dma_setup(struct device *dev)
 
        ret = acpi_dma_get_range(dev, &map);
        if (!ret && map) {
-               const struct bus_dma_region *r = map;
-
-               for (end = 0; r->size; r++) {
-                       if (r->dma_start + r->size - 1 > end)
-                               end = r->dma_start + r->size - 1;
-               }
-
+               end = dma_range_map_max(map);
                dev->dma_range_map = map;
        }
 
index 841ccd3a19d1eac10fef7b9fccf2d699bd295e2c..9e7963972fa7503ed7b343cebd4b9af3c4d3528a 100644 (file)
@@ -117,16 +117,9 @@ int of_dma_configure_id(struct device *dev, struct device_node *np,
                if (!force_dma)
                        return ret == -ENODEV ? 0 : ret;
        } else {
-               const struct bus_dma_region *r = map;
-
                /* Determine the overall bounds of all DMA regions */
-               for (dma_start = ~0; r->size; r++) {
-                       /* Take lower and upper limits */
-                       if (r->dma_start < dma_start)
-                               dma_start = r->dma_start;
-                       if (r->dma_start + r->size > end)
-                               end = r->dma_start + r->size;
-               }
+               dma_start = dma_range_map_min(map);
+               end = dma_range_map_max(map);
        }
 
        /*
index 3eb3589ff43e9320d65f84a7ac0e22a73efd4118..edbe13d007762b7850886ad1ad6a9a812aec7176 100644 (file)
@@ -54,6 +54,24 @@ static inline phys_addr_t translate_dma_to_phys(struct device *dev,
        return (phys_addr_t)-1;
 }
 
+static inline dma_addr_t dma_range_map_min(const struct bus_dma_region *map)
+{
+       dma_addr_t ret = (dma_addr_t)U64_MAX;
+
+       for (; map->size; map++)
+               ret = min(ret, map->dma_start);
+       return ret;
+}
+
+static inline dma_addr_t dma_range_map_max(const struct bus_dma_region *map)
+{
+       dma_addr_t ret = 0;
+
+       for (; map->size; map++)
+               ret = max(ret, map->dma_start + map->size - 1);
+       return ret;
+}
+
 #ifdef CONFIG_ARCH_HAS_PHYS_TO_DMA
 #include <asm/dma-direct.h>
 #ifndef phys_to_dma_unencrypted