Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

Merge tag 'dma-mapping-6.17-2025-09-09' into HEAD

dma-mapping fix for Linux 6.17

- one more fix for DMA API debugging infrastructure (Baochen Qiang)

+86 -11
+12 -4
drivers/of/of_reserved_mem.c
··· 25 25 #include <linux/memblock.h> 26 26 #include <linux/kmemleak.h> 27 27 #include <linux/cma.h> 28 + #include <linux/dma-map-ops.h> 28 29 29 30 #include "of_private.h" 30 31 ··· 176 175 base = dt_mem_next_cell(dt_root_addr_cells, &prop); 177 176 size = dt_mem_next_cell(dt_root_size_cells, &prop); 178 177 179 - if (size && 180 - early_init_dt_reserve_memory(base, size, nomap) == 0) 178 + if (size && early_init_dt_reserve_memory(base, size, nomap) == 0) { 179 + /* Architecture specific contiguous memory fixup. */ 180 + if (of_flat_dt_is_compatible(node, "shared-dma-pool") && 181 + of_get_flat_dt_prop(node, "reusable", NULL)) 182 + dma_contiguous_early_fixup(base, size); 181 183 pr_debug("Reserved memory: reserved region for node '%s': base %pa, size %lu MiB\n", 182 184 uname, &base, (unsigned long)(size / SZ_1M)); 183 - else 185 + } else { 184 186 pr_err("Reserved memory: failed to reserve memory for node '%s': base %pa, size %lu MiB\n", 185 187 uname, &base, (unsigned long)(size / SZ_1M)); 188 + } 186 189 187 190 len -= t_len; 188 191 } ··· 477 472 uname, (unsigned long)(size / SZ_1M)); 478 473 return -ENOMEM; 479 474 } 480 - 475 + /* Architecture specific contiguous memory fixup. */ 476 + if (of_flat_dt_is_compatible(node, "shared-dma-pool") && 477 + of_get_flat_dt_prop(node, "reusable", NULL)) 478 + dma_contiguous_early_fixup(base, size); 481 479 /* Save region in the reserved_mem array */ 482 480 fdt_reserved_mem_save_node(node, uname, base, size); 483 481 return 0;
+3
include/linux/dma-map-ops.h
··· 153 153 { 154 154 __free_pages(page, get_order(size)); 155 155 } 156 + static inline void dma_contiguous_early_fixup(phys_addr_t base, unsigned long size) 157 + { 158 + } 156 159 #endif /* CONFIG_DMA_CMA*/ 157 160 158 161 #ifdef CONFIG_DMA_DECLARE_COHERENT
-2
kernel/dma/contiguous.c
··· 483 483 pr_err("Reserved memory: unable to setup CMA region\n"); 484 484 return err; 485 485 } 486 - /* Architecture specific contiguous memory fixup. */ 487 - dma_contiguous_early_fixup(rmem->base, rmem->size); 488 486 489 487 if (default_cma) 490 488 dma_contiguous_default_area = cma;
+47 -1
kernel/dma/debug.c
··· 39 39 dma_debug_sg, 40 40 dma_debug_coherent, 41 41 dma_debug_resource, 42 + dma_debug_noncoherent, 42 43 }; 43 44 44 45 enum map_err_types { ··· 142 141 [dma_debug_sg] = "scatter-gather", 143 142 [dma_debug_coherent] = "coherent", 144 143 [dma_debug_resource] = "resource", 144 + [dma_debug_noncoherent] = "noncoherent", 145 145 }; 146 146 147 147 static const char *dir2name[] = { ··· 995 993 "[mapped as %s] [unmapped as %s]\n", 996 994 ref->dev_addr, ref->size, 997 995 type2name[entry->type], type2name[ref->type]); 998 - } else if (entry->type == dma_debug_coherent && 996 + } else if ((entry->type == dma_debug_coherent || 997 + entry->type == dma_debug_noncoherent) && 999 998 ref->paddr != entry->paddr) { 1000 999 err_printk(ref->dev, entry, "device driver frees " 1001 1000 "DMA memory with different CPU address " ··· 1582 1579 1583 1580 check_sync(dev, &ref, false); 1584 1581 } 1582 + } 1583 + 1584 + void debug_dma_alloc_pages(struct device *dev, struct page *page, 1585 + size_t size, int direction, 1586 + dma_addr_t dma_addr, 1587 + unsigned long attrs) 1588 + { 1589 + struct dma_debug_entry *entry; 1590 + 1591 + if (unlikely(dma_debug_disabled())) 1592 + return; 1593 + 1594 + entry = dma_entry_alloc(); 1595 + if (!entry) 1596 + return; 1597 + 1598 + entry->type = dma_debug_noncoherent; 1599 + entry->dev = dev; 1600 + entry->paddr = page_to_phys(page); 1601 + entry->size = size; 1602 + entry->dev_addr = dma_addr; 1603 + entry->direction = direction; 1604 + 1605 + add_dma_entry(entry, attrs); 1606 + } 1607 + 1608 + void debug_dma_free_pages(struct device *dev, struct page *page, 1609 + size_t size, int direction, 1610 + dma_addr_t dma_addr) 1611 + { 1612 + struct dma_debug_entry ref = { 1613 + .type = dma_debug_noncoherent, 1614 + .dev = dev, 1615 + .paddr = page_to_phys(page), 1616 + .dev_addr = dma_addr, 1617 + .size = size, 1618 + .direction = direction, 1619 + }; 1620 + 1621 + if (unlikely(dma_debug_disabled())) 1622 + return; 1623 + 1624 + check_unmap(&ref); 1585 1625 } 1586 1626 1587 1627 static int __init dma_debug_driver_setup(char *str)
+20
kernel/dma/debug.h
··· 54 54 extern void debug_dma_sync_sg_for_device(struct device *dev, 55 55 struct scatterlist *sg, 56 56 int nelems, int direction); 57 + extern void debug_dma_alloc_pages(struct device *dev, struct page *page, 58 + size_t size, int direction, 59 + dma_addr_t dma_addr, 60 + unsigned long attrs); 61 + extern void debug_dma_free_pages(struct device *dev, struct page *page, 62 + size_t size, int direction, 63 + dma_addr_t dma_addr); 57 64 #else /* CONFIG_DMA_API_DEBUG */ 58 65 static inline void debug_dma_map_page(struct device *dev, struct page *page, 59 66 size_t offset, size_t size, ··· 131 124 static inline void debug_dma_sync_sg_for_device(struct device *dev, 132 125 struct scatterlist *sg, 133 126 int nelems, int direction) 127 + { 128 + } 129 + 130 + static inline void debug_dma_alloc_pages(struct device *dev, struct page *page, 131 + size_t size, int direction, 132 + dma_addr_t dma_addr, 133 + unsigned long attrs) 134 + { 135 + } 136 + 137 + static inline void debug_dma_free_pages(struct device *dev, struct page *page, 138 + size_t size, int direction, 139 + dma_addr_t dma_addr) 134 140 { 135 141 } 136 142 #endif /* CONFIG_DMA_API_DEBUG */
+2 -2
kernel/dma/mapping.c
··· 712 712 if (page) { 713 713 trace_dma_alloc_pages(dev, page_to_virt(page), *dma_handle, 714 714 size, dir, gfp, 0); 715 - debug_dma_map_page(dev, page, 0, size, dir, *dma_handle, 0); 715 + debug_dma_alloc_pages(dev, page, size, dir, *dma_handle, 0); 716 716 } else { 717 717 trace_dma_alloc_pages(dev, NULL, 0, size, dir, gfp, 0); 718 718 } ··· 738 738 dma_addr_t dma_handle, enum dma_data_direction dir) 739 739 { 740 740 trace_dma_free_pages(dev, page_to_virt(page), dma_handle, size, dir, 0); 741 - debug_dma_unmap_page(dev, dma_handle, size, dir); 741 + debug_dma_free_pages(dev, page, size, dir, dma_handle); 742 742 __dma_free_pages(dev, size, page, dma_handle, dir); 743 743 } 744 744 EXPORT_SYMBOL_GPL(dma_free_pages);
+2 -2
kernel/dma/pool.c
··· 102 102 103 103 #ifdef CONFIG_DMA_DIRECT_REMAP 104 104 addr = dma_common_contiguous_remap(page, pool_size, 105 - pgprot_dmacoherent(PAGE_KERNEL), 106 - __builtin_return_address(0)); 105 + pgprot_decrypted(pgprot_dmacoherent(PAGE_KERNEL)), 106 + __builtin_return_address(0)); 107 107 if (!addr) 108 108 goto free_page; 109 109 #else