devicetree.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v5 0/8] kdump: reduce vmcore size and capture time
@ 2026-08-06  9:35 ` Wandun Chen
  2026-08-06  9:35   ` [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag Wandun Chen
                     ` (8 more replies)
  0 siblings, 9 replies; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

On SoCs that carve out large firmware-owned reserved memory (GPU,
camera ISP, ...), kdump currently dumps those carveouts as part of
system RAM even though their contents are firmware state that is not
useful for kernel crash analysis.

This series introduces a 'dumpable' flag on struct reserved_mem and a
MEMBLOCK_NODUMP flag in memblock to filter vmcore ELF header on DT-based
architectures (arm64, riscv, loongarch). Reserved regions default to
non-dumpable and are marked MEMBLOCK_NODUMP so kdump omits them;
reusable CMA regions are explicitly marked dumpable in rmem_cma_setup()
because their pages are handed back to the buddy allocator and may carry
crash-relevant data.

Since the reserved memory regions are filtered out, the vmcore is
smaller in size and faster to produce. ACPI systems already filter
reserved memory out of the vmcore through their existing path; only
DT-based systems currently fail to filter these regions, which is what
this series addresses. The flag lives in memblock itself rather than
in a DT-only structure, so the mechanism is generic and both ACPI and
DT systems can benefit from it (suggested by Rob, thanks).

The series is based on linux-next and is organized as follows:
  Patches 1-2: Introduce MEMBLOCK_NODUMP in memblock and the dumpable
               flag on struct reserved_mem.
  Patches 3-4: Mark non-dumpable /reserved-memory and /memreserve/
               entries with MEMBLOCK_NODUMP.
  Patch 5:     Switch riscv to memblock so the NODUMP flag is visible
               to the vmcore ELF header builder; add (KEXEC_FILE &&
               CRASH_DUMP) to riscv's ARCH_KEEP_MEMBLOCK condition.
  Patches 6-8: Fold the duplicated per-arch memblock walks into the
               weak defaults in crash_core, switch to
               for_each_mem_region(), and exclude MEMBLOCK_NODUMP
               regions from the vmcore ELF header.

v4 --> v5:
1. Rework the mechanism around a memblock-level MEMBLOCK_NODUMP flag
   (suggested by Rob) instead of the v4 opt-in 'dumpable' flag on
   DT-only struct reserved_mem.

2. Switch the riscv vmcore elf header preparation to use memblock
   instead of the resource tree, aligning it with arm64 and loongarch,
   so riscv also can exclude reserved memory from vmcore.

3. Deduplicate the vmcore elf header preparation: arm64, riscv and
   loongarch open-coded the same logic, so fold it into shared
    __weak defaults in crash_core.

4.  Drop the v4 patch that saved /memreserve/ entries into the
    reserved_mem array; /memreserve/ is now marked MEMBLOCK_NODUMP
    directly.

v3 --> v4:
1. Rebase this series on v7.2-rc1.
2. Add two cleanup patches (patch 02/03).
3. Simplify patch 03 to avoid checking whether initial_boot_params is
   NULL multiple times, suggested by Rob.

v2 --> v3:
1. Fix out-of-bounds issue if device tree lacks /reserved-memory node.[2]
2. Fix UAF issue when alloc_reserved_mem_array() fails.
3. Add some prepare patches.

v1 --> v2:
1. v1 added an opt-out DT property ('linux,no-dump'). Per Rob's
   feedback [1], v2 drop that property and exclude reserve memory
   by default.
2. Split some prepared patches from the original patches.
3. Address coding-style comments on patch 5 from Rob.

[1] https://lore.kernel.org/lkml/20260506144542.GA2072596-robh@kernel.org/
[2] https://sashiko.dev/#/patchset/20260520091844.592753-1-chenwandun%40lixiang.com?part=4

Wandun Chen (8):
  memblock: introduce MEMBLOCK_NODUMP flag
  of: reserved_mem: add dumpable flag to opt-in vmcore
  of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP
  of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP
  riscv: build crash_mem ranges from memblock instead of resource tree
  crash_core: fold duplicated memblock arch hooks into the weak default
  crash_core: replace for_each_mem_range() with for_each_mem_region()
  crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF
    header

 arch/arm64/kernel/machine_kexec_file.c     | 29 ------------------
 arch/loongarch/kernel/machine_kexec_file.c | 27 -----------------
 arch/riscv/Kconfig                         |  2 +-
 arch/riscv/kernel/machine_kexec_file.c     | 33 --------------------
 drivers/of/fdt.c                           |  2 ++
 drivers/of/of_private.h                    |  1 +
 drivers/of/of_reserved_mem.c               | 35 ++++++++++++++++++++++
 include/linux/memblock.h                   |  9 ++++++
 include/linux/of_reserved_mem.h            |  1 +
 kernel/crash_core.c                        | 34 +++++++++++++++++++--
 kernel/dma/contiguous.c                    |  1 +
 mm/memblock.c                              | 16 ++++++++++
 12 files changed, 98 insertions(+), 92 deletions(-)

-- 
2.43.0


^ permalink raw reply	[flat|nested] 20+ messages in thread

* [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06  9:51     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore Wandun Chen
                     ` (7 subsequent siblings)
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

Add MEMBLOCK_NODUMP to mark regions that should be excluded from
kdump vmcores.

The flag is meant for reserved memory that carries no data useful for
crash analysis. Reusable reserved regions such as CMA may hold useful
data, so these regions must not be marked MEMBLOCK_NODUMP. Subsequent
patches wire this up for /reserved-memory and /memreserve/ entries.

Suggested-by: Rob Herring <robh@kernel.org>
Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 include/linux/memblock.h |  9 +++++++++
 mm/memblock.c            | 16 ++++++++++++++++
 2 files changed, 25 insertions(+)

diff --git a/include/linux/memblock.h b/include/linux/memblock.h
index d62db9e776cf..b2fcf11fba2b 100644
--- a/include/linux/memblock.h
+++ b/include/linux/memblock.h
@@ -52,6 +52,8 @@ extern unsigned long long max_possible_pfn;
  * kernel that we know is good to use. It is the only memory that
  * allocations may happen from in this phase.
  * @MEMBLOCK_RSRV_HUGETLB: memory is reserved for hugetlb pages
+ * @MEMBLOCK_NODUMP: exclude from kdump vmcore. It carries no data useful
+ * for crash analysis (e.g. firmware carveouts).
  */
 enum memblock_flags {
 	MEMBLOCK_NONE		= 0x0,	/* No special request */
@@ -63,6 +65,7 @@ enum memblock_flags {
 	MEMBLOCK_RSRV_KERN	= 0x20,	/* memory reserved for kernel use */
 	MEMBLOCK_KHO_SCRATCH	= 0x40,	/* scratch memory for kexec handover */
 	MEMBLOCK_RSRV_HUGETLB	= 0x80, /* memory reserved for hugetlb pages */
+	MEMBLOCK_NODUMP		= 0x100,/* exclude from kdump vmcore */
 };
 
 /**
@@ -160,6 +163,7 @@ int memblock_reserved_mark_noinit(phys_addr_t base, phys_addr_t size);
 int memblock_reserved_mark_kern(phys_addr_t base, phys_addr_t size);
 int memblock_mark_kho_scratch(phys_addr_t base, phys_addr_t size);
 int memblock_clear_kho_scratch(phys_addr_t base, phys_addr_t size);
+int memblock_mark_nodump(phys_addr_t base, phys_addr_t size);
 
 void memblock_free(void *ptr, size_t size);
 void reset_all_zones_managed_pages(void);
@@ -306,6 +310,11 @@ static inline bool memblock_is_kho_scratch(struct memblock_region *m)
 	return m->flags & MEMBLOCK_KHO_SCRATCH;
 }
 
+static inline bool memblock_is_nodump(struct memblock_region *m)
+{
+	return m->flags & MEMBLOCK_NODUMP;
+}
+
 int memblock_search_pfn_nid(unsigned long pfn, unsigned long *start_pfn,
 			    unsigned long  *end_pfn);
 void __next_mem_pfn_range(int *idx, int nid, unsigned long *out_start_pfn,
diff --git a/mm/memblock.c b/mm/memblock.c
index 9ce86349a29f..79231634c25b 100644
--- a/mm/memblock.c
+++ b/mm/memblock.c
@@ -1204,6 +1204,21 @@ __init int memblock_clear_kho_scratch(phys_addr_t base, phys_addr_t size)
 				    MEMBLOCK_KHO_SCRATCH);
 }
 
+/**
+ * memblock_mark_nodump - Mark a memory region with flag MEMBLOCK_NODUMP.
+ * @base: the base phys addr of the region
+ * @size: the size of the region
+ *
+ * Mark the region as not to be included in crash dumps.
+ *
+ * Return: 0 on success, -errno on failure.
+ */
+int __init_memblock memblock_mark_nodump(phys_addr_t base, phys_addr_t size)
+{
+	return memblock_setclr_flag(&memblock.memory, base, size, 1,
+				    MEMBLOCK_NODUMP);
+}
+
 static bool should_skip_region(struct memblock_type *type,
 			       struct memblock_region *m,
 			       int nid, int flags)
@@ -2886,6 +2901,7 @@ static const char * const flagname[] = {
 	[ilog2(MEMBLOCK_RSRV_NOINIT)] = "RSV_NIT",
 	[ilog2(MEMBLOCK_RSRV_KERN)] = "RSV_KERN",
 	[ilog2(MEMBLOCK_KHO_SCRATCH)] = "KHO_SCRATCH",
+	[ilog2(MEMBLOCK_NODUMP)] = "NODUMP",
 };
 
 static int memblock_debug_show(struct seq_file *m, void *private)
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
  2026-08-06  9:35   ` [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06  9:47     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP Wandun Chen
                     ` (6 subsequent siblings)
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

Add a 'dumpable' flag to struct reserved_mem to decide whether a
reserved area should be included in the kdump vmcore. Non-dumpable
regions are later marked MEMBLOCK_NODUMP;the filtering itself happens
in memblock, keeping the arch kdump code independent of the DT API.

Most reserved regions are owned by devices and do not contain data
useful for kernel crash analysis, so dumpable default to false.
Reusable CMA regions are different: their pages are handed back to the
buddy allocator and may contain key data for crash analysis, so set
dumpable to true in rmem_cma_setup().

The dumpable flag is also used to check /memreserve/ entries for overlap
with other dumpable regions.

Suggested-by: Rob Herring <robh@kernel.org>
Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
Acked-by: Marek Szyprowski <m.szyprowski@samsung.com>
---
 include/linux/of_reserved_mem.h | 1 +
 kernel/dma/contiguous.c         | 1 +
 2 files changed, 2 insertions(+)

diff --git a/include/linux/of_reserved_mem.h b/include/linux/of_reserved_mem.h
index e8b20b29fa68..55a67cee41ea 100644
--- a/include/linux/of_reserved_mem.h
+++ b/include/linux/of_reserved_mem.h
@@ -15,6 +15,7 @@ struct reserved_mem {
 	phys_addr_t			base;
 	phys_addr_t			size;
 	void				*priv;
+	bool				dumpable;
 };
 
 struct reserved_mem_ops {
diff --git a/kernel/dma/contiguous.c b/kernel/dma/contiguous.c
index f754079a287d..63ff134dadd4 100644
--- a/kernel/dma/contiguous.c
+++ b/kernel/dma/contiguous.c
@@ -565,6 +565,7 @@ static int __init rmem_cma_setup(unsigned long node, struct reserved_mem *rmem)
 		dma_contiguous_default_area = cma;
 
 	rmem->priv = cma;
+	rmem->dumpable = true;
 
 	pr_info("Reserved memory: created CMA memory pool at %pa, size %ld MiB\n",
 		&rmem->base, (unsigned long)rmem->size / SZ_1M);
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
  2026-08-06  9:35   ` [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag Wandun Chen
  2026-08-06  9:35   ` [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06 10:06     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP Wandun Chen
                     ` (5 subsequent siblings)
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

Mark non-dumpable reserved-memory regions with MEMBLOCK_NODUMP so
kdump can omit them from the vmcore.

The marking is guarded by CONFIG_CRASH_DUMP so non-kdump kernels do not
pay the cost of splitting memblock.memory entries at NODUMP boundaries.

Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 drivers/of/of_reserved_mem.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/drivers/of/of_reserved_mem.c b/drivers/of/of_reserved_mem.c
index 7b1616b9c6c2..f38d11df6f15 100644
--- a/drivers/of/of_reserved_mem.c
+++ b/drivers/of/of_reserved_mem.c
@@ -674,6 +674,9 @@ static void __init fdt_init_reserved_mem_node(unsigned long node, const char *un
 			rmem->name ? rmem->name : "unknown");
 	}
 
+	if (IS_ENABLED(CONFIG_CRASH_DUMP) && !rmem->dumpable)
+		memblock_mark_nodump(rmem->base, rmem->size);
+
 	reserved_mem_count++;
 }
 
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
                     ` (2 preceding siblings ...)
  2026-08-06  9:35   ` [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06  9:57     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree Wandun Chen
                     ` (4 subsequent siblings)
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

The /memreserve/ entries are memory reservations made by the bootloader
or firmware, their contents are not needed for kernel crash analysis,
so mark them MEMBLOCK_NODUMP to have kdump omit them from the vmcore.

Entries that overlap a dumpable region (such as CMA) are left unmarked,
because the pages of a dumpable region may carry crash-relevant data.

Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 drivers/of/fdt.c             |  2 ++
 drivers/of/of_private.h      |  1 +
 drivers/of/of_reserved_mem.c | 32 ++++++++++++++++++++++++++++++++
 3 files changed, 35 insertions(+)

diff --git a/drivers/of/fdt.c b/drivers/of/fdt.c
index a64afc3ded3d..2aa888997e9b 100644
--- a/drivers/of/fdt.c
+++ b/drivers/of/fdt.c
@@ -1286,6 +1286,8 @@ void __init unflatten_device_tree(void)
 	/* Save the statically-placed regions in the reserved_mem array */
 	fdt_scan_reserved_mem_late();
 
+	fdt_mark_memreserve_nodump();
+
 	/* Populate an empty root node when bootloader doesn't provide one */
 	if (!fdt) {
 		fdt = (void *) __dtb_empty_root_begin;
diff --git a/drivers/of/of_private.h b/drivers/of/of_private.h
index 0ae16da066e2..667ce9e46aab 100644
--- a/drivers/of/of_private.h
+++ b/drivers/of/of_private.h
@@ -187,6 +187,7 @@ static inline struct device_node *__of_get_dma_parent(const struct device_node *
 
 int fdt_scan_reserved_mem(void);
 void __init fdt_scan_reserved_mem_late(void);
+void __init fdt_mark_memreserve_nodump(void);
 
 bool of_fdt_device_is_available(const void *blob, unsigned long node);
 
diff --git a/drivers/of/of_reserved_mem.c b/drivers/of/of_reserved_mem.c
index f38d11df6f15..f0683b5d77b3 100644
--- a/drivers/of/of_reserved_mem.c
+++ b/drivers/of/of_reserved_mem.c
@@ -251,6 +251,38 @@ static void __init __rmem_check_for_overlap(void)
 	}
 }
 
+void __init fdt_mark_memreserve_nodump(void)
+{
+	u64 base, size;
+	int n;
+	const void *fdt = initial_boot_params;
+
+	if (!IS_ENABLED(CONFIG_CRASH_DUMP))
+		return;
+
+	if (!fdt)
+		return;
+
+	for (n = 0; ; n++) {
+		int i;
+
+		if (fdt_get_mem_rsv(fdt, n, &base, &size))
+			break;
+		if (!size)
+			break;
+
+		for (i = 0; i < reserved_mem_count; i++) {
+			struct reserved_mem *rmem = &reserved_mem[i];
+
+			if (rmem->dumpable && base < rmem->base + rmem->size &&
+			    rmem->base < base + size)
+				break;
+		}
+		if (i == reserved_mem_count)
+			memblock_mark_nodump(base, size);
+	}
+}
+
 /**
  * fdt_scan_reserved_mem_late() - Scan FDT and initialize remaining reserved
  * memory regions.
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
                     ` (3 preceding siblings ...)
  2026-08-06  9:35   ` [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06 10:10     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default Wandun Chen
                     ` (3 subsequent siblings)
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

Replace walk_system_ram_res() with for_each_mem_range(). The
MEMBLOCK_NODUMP flag lives in memblock, so only by walking memblock
can the reserved-memory regions marked MEMBLOCK_NODUMP be excluded
from the vmcore.

for_each_mem_range() iterates memblock.memory, which is freed after
init unless ARCH_KEEP_MEMBLOCK is selected. riscv needs
ARCH_KEEP_MEMBLOCK to filter reserved memory from the vmcore, so
extend its condition (ACPI || KEXEC) with (KEXEC_FILE &&
CRASH_DUMP). arm64 and loongarch already select ARCH_KEEP_MEMBLOCK
unconditionally.

Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 arch/riscv/Kconfig                     |  2 +-
 arch/riscv/kernel/machine_kexec_file.c | 31 ++++++++++----------------
 2 files changed, 13 insertions(+), 20 deletions(-)

diff --git a/arch/riscv/Kconfig b/arch/riscv/Kconfig
index ef1101bec76c..bd8726b4dfbe 100644
--- a/arch/riscv/Kconfig
+++ b/arch/riscv/Kconfig
@@ -57,7 +57,7 @@ config RISCV
 	select ARCH_HAS_UBSAN
 	select ARCH_HAS_VDSO_ARCH_DATA
 	select ARCH_HAVE_NMI_SAFE_CMPXCHG
-	select ARCH_KEEP_MEMBLOCK if ACPI || KEXEC
+	select ARCH_KEEP_MEMBLOCK if ACPI || KEXEC || (KEXEC_FILE && CRASH_DUMP)
 	select ARCH_MHP_MEMMAP_ON_MEMORY_ENABLE	if 64BIT && MMU
 	select ARCH_OPTIONAL_KERNEL_RWX if ARCH_HAS_STRICT_KERNEL_RWX
 	select ARCH_OPTIONAL_KERNEL_RWX_DEFAULT
diff --git a/arch/riscv/kernel/machine_kexec_file.c b/arch/riscv/kernel/machine_kexec_file.c
index 26cd2a8bd0cd..808e872f4063 100644
--- a/arch/riscv/kernel/machine_kexec_file.c
+++ b/arch/riscv/kernel/machine_kexec_file.c
@@ -37,39 +37,32 @@ int arch_kimage_file_post_load_cleanup(struct kimage *image)
 }
 
 #ifdef CONFIG_CRASH_DUMP
-static int get_nr_ram_ranges_callback(struct resource *res, void *arg)
-{
-	unsigned int *nr_ranges = arg;
-
-	(*nr_ranges)++;
-	return 0;
-}
-
 unsigned int arch_get_system_nr_ranges(void)
 {
 	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* For exclusion of crashkernel region */
+	u64 i;
+	phys_addr_t start, end;
 
-	walk_system_ram_res(0, -1, &nr_ranges, get_nr_ram_ranges_callback);
+	for_each_mem_range(i, &start, &end)
+		nr_ranges++;
 
 	return nr_ranges;
 }
 
-static int prepare_elf64_ram_headers_callback(struct resource *res, void *arg)
+int arch_crash_populate_cmem(struct crash_mem *cmem)
 {
-	struct crash_mem *cmem = arg;
+	u64 i;
+	phys_addr_t start, end;
 
-	cmem->ranges[cmem->nr_ranges].start = res->start;
-	cmem->ranges[cmem->nr_ranges].end = res->end;
-	cmem->nr_ranges++;
+	for_each_mem_range(i, &start, &end) {
+		cmem->ranges[cmem->nr_ranges].start = start;
+		cmem->ranges[cmem->nr_ranges].end = end - 1;
+		cmem->nr_ranges++;
+	}
 
 	return 0;
 }
 
-int arch_crash_populate_cmem(struct crash_mem *cmem)
-{
-	return walk_system_ram_res(0, -1, cmem, prepare_elf64_ram_headers_callback);
-}
-
 static char *setup_kdump_cmdline(struct kimage *image, char *cmdline,
 				 unsigned long cmdline_len)
 {
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
                     ` (4 preceding siblings ...)
  2026-08-06  9:35   ` [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06  9:56     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region() Wandun Chen
                     ` (2 subsequent siblings)
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

The weak defaults are only consumed by crash_prepare_headers(), which is
called only by arm64, riscv, loongarch (via the weak default) and x86
(via its own non-weak override).

arm64, loongarch and riscv open-code the same memblock walk in
arch_get_system_nr_ranges() and arch_crash_populate_cmem(). Move it into
the __weak defaults in kernel/crash_core.c and delete the arch copies.

No functional change.

Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 arch/arm64/kernel/machine_kexec_file.c     | 29 ----------------------
 arch/loongarch/kernel/machine_kexec_file.c | 27 --------------------
 arch/riscv/kernel/machine_kexec_file.c     | 26 -------------------
 kernel/crash_core.c                        | 25 +++++++++++++++++--
 4 files changed, 23 insertions(+), 84 deletions(-)

diff --git a/arch/arm64/kernel/machine_kexec_file.c b/arch/arm64/kernel/machine_kexec_file.c
index 854d872dfd0f..34d944d3f22f 100644
--- a/arch/arm64/kernel/machine_kexec_file.c
+++ b/arch/arm64/kernel/machine_kexec_file.c
@@ -14,7 +14,6 @@
 #include <linux/kernel.h>
 #include <linux/kexec.h>
 #include <linux/libfdt.h>
-#include <linux/memblock.h>
 #include <linux/of.h>
 #include <linux/of_fdt.h>
 #include <linux/slab.h>
@@ -39,34 +38,6 @@ int arch_kimage_file_post_load_cleanup(struct kimage *image)
 	return kexec_image_post_load_cleanup_default(image);
 }
 
-#ifdef CONFIG_CRASH_DUMP
-unsigned int arch_get_system_nr_ranges(void)
-{
-	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* for exclusion of crashkernel region */
-	phys_addr_t start, end;
-	u64 i;
-
-	for_each_mem_range(i, &start, &end)
-		nr_ranges++;
-
-	return nr_ranges;
-}
-
-int arch_crash_populate_cmem(struct crash_mem *cmem)
-{
-	phys_addr_t start, end;
-	u64 i;
-
-	for_each_mem_range(i, &start, &end) {
-		cmem->ranges[cmem->nr_ranges].start = start;
-		cmem->ranges[cmem->nr_ranges].end = end - 1;
-		cmem->nr_ranges++;
-	}
-
-	return 0;
-}
-#endif
-
 /*
  * Tries to add the initrd and DTB to the image. If it is not possible to find
  * valid locations, this function will undo changes to the image and return non
diff --git a/arch/loongarch/kernel/machine_kexec_file.c b/arch/loongarch/kernel/machine_kexec_file.c
index 5412aa9f3568..481b8f906a56 100644
--- a/arch/loongarch/kernel/machine_kexec_file.c
+++ b/arch/loongarch/kernel/machine_kexec_file.c
@@ -13,7 +13,6 @@
 #include <linux/ioport.h>
 #include <linux/kernel.h>
 #include <linux/kexec.h>
-#include <linux/memblock.h>
 #include <linux/slab.h>
 #include <linux/string.h>
 #include <linux/types.h>
@@ -56,32 +55,6 @@ static void cmdline_add_initrd(struct kimage *image, unsigned long *cmdline_tmpl
 }
 
 #ifdef CONFIG_CRASH_DUMP
-unsigned int arch_get_system_nr_ranges(void)
-{
-	int nr_ranges = 2; /* for exclusion of crashkernel region */
-	phys_addr_t start, end;
-	uint64_t i;
-
-	for_each_mem_range(i, &start, &end)
-		nr_ranges++;
-
-	return nr_ranges;
-}
-
-int arch_crash_populate_cmem(struct crash_mem *cmem)
-{
-	phys_addr_t start, end;
-	uint64_t i;
-
-	for_each_mem_range(i, &start, &end) {
-		cmem->ranges[cmem->nr_ranges].start = start;
-		cmem->ranges[cmem->nr_ranges].end = end - 1;
-		cmem->nr_ranges++;
-	}
-
-	return 0;
-}
-
 /*
  * Add the "mem=size@start" command line parameter to command line, indicating the
  * memory region the new kernel can use to boot into.
diff --git a/arch/riscv/kernel/machine_kexec_file.c b/arch/riscv/kernel/machine_kexec_file.c
index 808e872f4063..fdc6695e8588 100644
--- a/arch/riscv/kernel/machine_kexec_file.c
+++ b/arch/riscv/kernel/machine_kexec_file.c
@@ -37,32 +37,6 @@ int arch_kimage_file_post_load_cleanup(struct kimage *image)
 }
 
 #ifdef CONFIG_CRASH_DUMP
-unsigned int arch_get_system_nr_ranges(void)
-{
-	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* For exclusion of crashkernel region */
-	u64 i;
-	phys_addr_t start, end;
-
-	for_each_mem_range(i, &start, &end)
-		nr_ranges++;
-
-	return nr_ranges;
-}
-
-int arch_crash_populate_cmem(struct crash_mem *cmem)
-{
-	u64 i;
-	phys_addr_t start, end;
-
-	for_each_mem_range(i, &start, &end) {
-		cmem->ranges[cmem->nr_ranges].start = start;
-		cmem->ranges[cmem->nr_ranges].end = end - 1;
-		cmem->nr_ranges++;
-	}
-
-	return 0;
-}
-
 static char *setup_kdump_cmdline(struct kimage *image, char *cmdline,
 				 unsigned long cmdline_len)
 {
diff --git a/kernel/crash_core.c b/kernel/crash_core.c
index 2b36aa9fade0..77285ae3ce60 100644
--- a/kernel/crash_core.c
+++ b/kernel/crash_core.c
@@ -281,8 +281,29 @@ static struct crash_mem *alloc_cmem(unsigned int nr_ranges)
 	return cmem;
 }
 
-unsigned int __weak arch_get_system_nr_ranges(void) { return 0; }
-int __weak arch_crash_populate_cmem(struct crash_mem *cmem) { return -1; }
+unsigned int __weak arch_get_system_nr_ranges(void)
+{
+	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* crashk_res + crashk_low_res, +CMA splits */
+	phys_addr_t start, end;
+	u64 i;
+
+	for_each_mem_range(i, &start, &end)
+		nr_ranges++;
+	return nr_ranges;
+}
+
+int __weak arch_crash_populate_cmem(struct crash_mem *cmem)
+{
+	phys_addr_t start, end;
+	u64 i;
+
+	for_each_mem_range(i, &start, &end) {
+		cmem->ranges[cmem->nr_ranges].start = start;
+		cmem->ranges[cmem->nr_ranges].end = end - 1;
+		cmem->nr_ranges++;
+	}
+	return 0;
+}
 int __weak arch_crash_exclude_ranges(struct crash_mem *cmem) { return 0; }
 
 int __weak arch_crash_exclude_mem_range(struct crash_mem **mem,
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region()
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
                     ` (5 preceding siblings ...)
  2026-08-06  9:35   ` [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06 10:07     ` sashiko-bot
  2026-08-06  9:35   ` [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header Wandun Chen
  2026-08-06 10:11   ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Marek Szyprowski
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

for_each_mem_range() skips MEMBLOCK_NOMAP regions implicitly. Switch the
weak defaults to for_each_mem_region(), which exposes struct
memblock_region and per-region flags, and filter NOMAP regions explicitly
via the new crash_should_skip_region() helper. This prepares for a
subsequent patch to extend the skip filter.

No functional change.

Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 kernel/crash_core.c | 25 +++++++++++++++++--------
 1 file changed, 17 insertions(+), 8 deletions(-)

diff --git a/kernel/crash_core.c b/kernel/crash_core.c
index 77285ae3ce60..fb78b7814f18 100644
--- a/kernel/crash_core.c
+++ b/kernel/crash_core.c
@@ -269,6 +269,12 @@ int crash_prepare_elf64_headers(struct crash_mem *mem, int need_kernel_map,
 	return 0;
 }
 
+/* Exclude NOMAP regions from the vmcore. */
+static bool crash_should_skip_region(struct memblock_region *reg)
+{
+	return memblock_is_nomap(reg);
+}
+
 static struct crash_mem *alloc_cmem(unsigned int nr_ranges)
 {
 	struct crash_mem *cmem;
@@ -284,22 +290,25 @@ static struct crash_mem *alloc_cmem(unsigned int nr_ranges)
 unsigned int __weak arch_get_system_nr_ranges(void)
 {
 	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* crashk_res + crashk_low_res, +CMA splits */
-	phys_addr_t start, end;
-	u64 i;
+	struct memblock_region *reg;
 
-	for_each_mem_range(i, &start, &end)
+	for_each_mem_region(reg) {
+		if (crash_should_skip_region(reg))
+			continue;
 		nr_ranges++;
+	}
 	return nr_ranges;
 }
 
 int __weak arch_crash_populate_cmem(struct crash_mem *cmem)
 {
-	phys_addr_t start, end;
-	u64 i;
+	struct memblock_region *reg;
 
-	for_each_mem_range(i, &start, &end) {
-		cmem->ranges[cmem->nr_ranges].start = start;
-		cmem->ranges[cmem->nr_ranges].end = end - 1;
+	for_each_mem_region(reg) {
+		if (crash_should_skip_region(reg))
+			continue;
+		cmem->ranges[cmem->nr_ranges].start = reg->base;
+		cmem->ranges[cmem->nr_ranges].end = reg->base + reg->size - 1;
 		cmem->nr_ranges++;
 	}
 	return 0;
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
                     ` (6 preceding siblings ...)
  2026-08-06  9:35   ` [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region() Wandun Chen
@ 2026-08-06  9:35   ` Wandun Chen
  2026-08-06 10:24     ` sashiko-bot
  2026-08-06 10:11   ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Marek Szyprowski
  8 siblings, 1 reply; 20+ messages in thread
From: Wandun Chen @ 2026-08-06  9:35 UTC (permalink / raw)
  To: catalin.marinas, will, chenhuacai, pjw, palmer, aou, robh,
	saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	m.szyprowski, linux-arm-kernel, linux-kernel, loongarch,
	linux-riscv, devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

From: Wandun Chen <chenwandun@lixiang.com>

Reserve regions (for GPU, DSP, ...) carry no data useful for crash
analysis. Exclude MEMBLOCK_NODUMP regions from the vmcore ELF header to
reduce vmcore size and capture time. crash_should_skip_region() now also
returns true for MEMBLOCK_NODUMP.

Signed-off-by: Wandun Chen <chenwandun@lixiang.com>
Tested-by: Meijing Zhao <zhaomeijing@lixiang.com>
---
 kernel/crash_core.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/kernel/crash_core.c b/kernel/crash_core.c
index fb78b7814f18..8cc9d666bc54 100644
--- a/kernel/crash_core.c
+++ b/kernel/crash_core.c
@@ -269,10 +269,10 @@ int crash_prepare_elf64_headers(struct crash_mem *mem, int need_kernel_map,
 	return 0;
 }
 
-/* Exclude NOMAP regions from the vmcore. */
+/* Exclude NOMAP and NODUMP regions from the vmcore. */
 static bool crash_should_skip_region(struct memblock_region *reg)
 {
-	return memblock_is_nomap(reg);
+	return memblock_is_nomap(reg) || memblock_is_nodump(reg);
 }
 
 static struct crash_mem *alloc_cmem(unsigned int nr_ranges)
-- 
2.43.0


^ permalink raw reply related	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore
  2026-08-06  9:35   ` [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore Wandun Chen
@ 2026-08-06  9:47     ` sashiko-bot
  2026-08-06 11:48       ` Wandun
  0 siblings, 1 reply; 20+ messages in thread
From: sashiko-bot @ 2026-08-06  9:47 UTC (permalink / raw)
  To: Wandun Chen; +Cc: conor+dt, devicetree, robh

Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
- [Medium] Incomplete implementation and write-only dead code: the `dumpable` flag is introduced and set, but the promised kdump filtering and overlap checks are missing.
--

--- Patch [2]: [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore ---
commit 873defcf6278254b5c39d8d3500f986e38a79da0
Author: Wandun Chen <chenwandun@lixiang.com>

of: reserved_mem: add dumpable flag to opt-in vmcore

This commit adds a dumpable flag to struct reserved_mem to track whether
a reserved area should be included in the kdump vmcore. It sets the flag
for CMA regions to true in rmem_cma_setup().

> diff --git a/include/linux/of_reserved_mem.h b/include/linux/of_reserved_mem.h
> index e8b20b29fa68c..55a67cee41ea0 100644
> --- a/include/linux/of_reserved_mem.h
> +++ b/include/linux/of_reserved_mem.h
> @@ -15,6 +15,7 @@ struct reserved_mem {
>  	phys_addr_t			base;
>  	phys_addr_t			size;
>  	void				*priv;
> +	bool				dumpable;

[Severity: Medium]
Is the logic that checks this flag missing from this patch?

The commit message states that non-dumpable regions are later marked
MEMBLOCK_NODUMP, and that the flag is used to check for overlap with
/memreserve/ entries. However, this flag appears to be write-only,
as there are no corresponding checks or calls to memblock_mark_nodump()
implemented in this commit.

>  };

[ ... ]

> diff --git a/kernel/dma/contiguous.c b/kernel/dma/contiguous.c
> index f754079a287d6..63ff134dadd42 100644
> --- a/kernel/dma/contiguous.c
> +++ b/kernel/dma/contiguous.c
> @@ -565,6 +565,7 @@ static int __init rmem_cma_setup(unsigned long node, struct reserved_mem *rmem)
>  		dma_contiguous_default_area = cma;
>  
>  	rmem->priv = cma;
> +	rmem->dumpable = true;

[Severity: Medium]
Does setting this flag have any effect?

Since the promised kdump filtering and overlap checks are missing from the
code, this assignment currently acts as dead code. Were those checks meant
to be included in this submission?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=2

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag
  2026-08-06  9:35   ` [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag Wandun Chen
@ 2026-08-06  9:51     ` sashiko-bot
  2026-08-06 11:43       ` Wandun
  0 siblings, 1 reply; 20+ messages in thread
From: sashiko-bot @ 2026-08-06  9:51 UTC (permalink / raw)
  To: Wandun Chen; +Cc: robh, conor+dt, devicetree

Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
- [High] The patch completely omits the filtering logic required to exclude MEMBLOCK_NODUMP regions from kdump vmcores.
- [Medium] The MEMBLOCK_NODUMP flag extends the flagname array but leaves an uninitialized hole for MEMBLOCK_RSRV_HUGETLB, leading to a NULL format argument.
--

--- Patch [1]: [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag ---
commit b30a0bfd2a4e00657ccc3f49bdfa4a7ca5fdfa1d
Author: Wandun Chen <chenwandun@lixiang.com>

memblock: introduce MEMBLOCK_NODUMP flag

Add MEMBLOCK_NODUMP to mark regions that should be excluded from kdump vmcores.
The flag is meant for reserved memory that carries no data useful for crash
analysis. Subsequent patches wire this up for /reserved-memory and
/memreserve/ entries.

> diff --git a/mm/memblock.c b/mm/memblock.c
> index 9ce86349a29fa..79231634c25b0 100644
> --- a/mm/memblock.c
> +++ b/mm/memblock.c
> @@ -1204,6 +1204,21 @@ __init int memblock_clear_kho_scratch(phys_addr_t base, phys_addr_t size)
>  				    MEMBLOCK_KHO_SCRATCH);
>  }
>  
> +/**
> + * memblock_mark_nodump - Mark a memory region with flag MEMBLOCK_NODUMP.
> + * @base: the base phys addr of the region
> + * @size: the size of the region
> + *
> + * Mark the region as not to be included in crash dumps.
> + *
> + * Return: 0 on success, -errno on failure.
> + */
> +int __init_memblock memblock_mark_nodump(phys_addr_t base, phys_addr_t size)
> +{
> +	return memblock_setclr_flag(&memblock.memory, base, size, 1,
> +				    MEMBLOCK_NODUMP);
> +}
> +

[Severity: High]
Is it intentional that the filtering logic for this new flag was omitted?

Without updating should_skip_region() in this file to filter out regions
marked with MEMBLOCK_NODUMP, the flag appears to have no functional effect.

When architecture kdump setup iterates over memory ranges (e.g., using
for_each_mem_range()) to build the crash dump list, these regions will still
be included because should_skip_region() does not know to skip them.

[ ... ]

> @@ -2886,6 +2901,7 @@ static const char * const flagname[] = {
>  	[ilog2(MEMBLOCK_RSRV_NOINIT)] = "RSV_NIT",
>  	[ilog2(MEMBLOCK_RSRV_KERN)] = "RSV_KERN",
>  	[ilog2(MEMBLOCK_KHO_SCRATCH)] = "KHO_SCRATCH",
> +	[ilog2(MEMBLOCK_NODUMP)] = "NODUMP",
>  };
>  
>  static int memblock_debug_show(struct seq_file *m, void *private)

[Severity: Medium]
Will this expansion of the array leave a NULL pointer hole for the
MEMBLOCK_RSRV_HUGETLB flag?

Prior to this patch, the max index was 6. MEMBLOCK_RSRV_HUGETLB is bit 7,
which safely fell back to printing "UNKNOWN". 

Adding MEMBLOCK_NODUMP (bit 8) expands the array size to 9. Due to designated
initialization, index 7 becomes NULL.

When memblock_debug_show() prints a region with MEMBLOCK_RSRV_HUGETLB set,
it will read the NULL pointer and pass it to seq_printf():

    if (reg->flags & (1U << j)) {
        seq_printf(m, "%s\n", flagname[j]);
        break;
    }

While seq_printf() will safely print "(null)", this will break out of the
printing loop early and omit any other flags. Could MEMBLOCK_RSRV_HUGETLB
be added to the array as well to avoid this hole?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=1

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default
  2026-08-06  9:35   ` [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default Wandun Chen
@ 2026-08-06  9:56     ` sashiko-bot
  0 siblings, 0 replies; 20+ messages in thread
From: sashiko-bot @ 2026-08-06  9:56 UTC (permalink / raw)
  To: Wandun Chen; +Cc: conor+dt, devicetree, robh

Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:

New issues:
- [Low] Leftover unused `#include <linux/memblock.h>` in `arch/riscv/kernel/machine_kexec_file.c`.

Pre-existing issues:
- [High] A time-of-check to time-of-use (TOCTOU) race condition in `crash_prepare_headers()` allows an out-of-bounds array write and Use-After-Free (UAF) during concurrent memory hotplug.
--

--- Patch [6]: [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default ---
commit 1003e078862f2080b60e5f21352f7989a4d125c2
Author: Wandun Chen <chenwandun@lixiang.com>

crash_core: fold duplicated memblock arch hooks into the weak default

arm64, loongarch and riscv open-code the same memblock walk in
arch_get_system_nr_ranges() and arch_crash_populate_cmem(). Move it into
the __weak defaults in kernel/crash_core.c and delete the arch copies.

> diff --git a/arch/riscv/kernel/machine_kexec_file.c b/arch/riscv/kernel/machine_kexec_file.c
> index 808e872f40634..fdc6695e85882 100644
> --- a/arch/riscv/kernel/machine_kexec_file.c
> +++ b/arch/riscv/kernel/machine_kexec_file.c
> @@ -37,32 +37,6 @@ int arch_kimage_file_post_load_cleanup(struct kimage *image)
>  }
>  
>  #ifdef CONFIG_CRASH_DUMP

[Severity: Low]
This isn't a bug, but can we also drop the #include <linux/memblock.h>
from arch/riscv/kernel/machine_kexec_file.c?

The patch successfully relocates all memblock usage out of the riscv file,
and the include was correctly dropped for arm64 and loongarch, but it looks
like it was missed here.

> -unsigned int arch_get_system_nr_ranges(void)
> -{

[ ... ]

> diff --git a/kernel/crash_core.c b/kernel/crash_core.c
> index 2b36aa9fade06..77285ae3ce600 100644
> --- a/kernel/crash_core.c
> +++ b/kernel/crash_core.c

[ ... ]

> +int __weak arch_crash_populate_cmem(struct crash_mem *cmem)
> +{
> +	phys_addr_t start, end;
> +	u64 i;
> +
> +	for_each_mem_range(i, &start, &end) {
> +		cmem->ranges[cmem->nr_ranges].start = start;
> +		cmem->ranges[cmem->nr_ranges].end = end - 1;
> +		cmem->nr_ranges++;
> +	}

[Severity: High]
This is a pre-existing issue, but does this loop risk an out-of-bounds array
write during concurrent memory hotplug?

The loop unconditionally writes to cmem->ranges and increments the index
without verifying bounds against cmem->max_nr_ranges.

In crash_prepare_headers(), the code sequentially counts the regions,
allocates memory, and then calls arch_crash_populate_cmem():

	max_nr_ranges = arch_get_system_nr_ranges();
	if (!max_nr_ranges)
		return -ENOMEM;

	cmem = alloc_cmem(max_nr_ranges);
	if (!cmem)
		return -ENOMEM;

	ret = arch_crash_populate_cmem(cmem);

Since neither kexec_file_load nor these functions hold the memory hotplug
read lock (get_online_mems()), couldn't memblock.memory be modified
concurrently between the check and the use? If regions are added or split,
this loop would write past the allocated array size.

> +	return 0;
> +}
>  int __weak arch_crash_exclude_ranges(struct crash_mem *cmem) { return 0; }

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=6

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP
  2026-08-06  9:35   ` [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP Wandun Chen
@ 2026-08-06  9:57     ` sashiko-bot
  0 siblings, 0 replies; 20+ messages in thread
From: sashiko-bot @ 2026-08-06  9:57 UTC (permalink / raw)
  To: Wandun Chen; +Cc: robh, conor+dt, devicetree

Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
- [High] 64-bit FDT memreserve base and size values bypass overlap checks due to type mismatch and implicit truncation to 32-bit.
- [High] The overlap check between the memreserve region and dumpable reserved memory regions fails due to 32-bit arithmetic overflow.
--

--- Patch [4]: [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP ---
commit 224ae2a2bcff895e0e857319035a55e95d869a02
Author: Wandun Chen <chenwandun@lixiang.com>

of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP
    
The /memreserve/ entries are memory reservations made by the bootloader
or firmware, their contents are not needed for kernel crash analysis,
so mark them MEMBLOCK_NODUMP to have kdump omit them from the vmcore.

Entries that overlap a dumpable region (such as CMA) are left unmarked,
because the pages of a dumpable region may carry crash-relevant data.

> diff --git a/drivers/of/of_reserved_mem.c b/drivers/of/of_reserved_mem.c
> index f38d11df6f152..f0683b5d77b30 100644
> --- a/drivers/of/of_reserved_mem.c
> +++ b/drivers/of/of_reserved_mem.c
[ ... ]
> @@ -251,6 +251,38 @@ static void __init __rmem_check_for_overlap(void)
>  	}
>  }
>  
> +void __init fdt_mark_memreserve_nodump(void)
> +{
> +	u64 base, size;
> +	int n;
> +	const void *fdt = initial_boot_params;
> +
> +	if (!IS_ENABLED(CONFIG_CRASH_DUMP))
> +		return;
> +
> +	if (!fdt)
> +		return;
> +
> +	for (n = 0; ; n++) {
> +		int i;
> +
> +		if (fdt_get_mem_rsv(fdt, n, &base, &size))
> +			break;
> +		if (!size)
> +			break;
> +
> +		for (i = 0; i < reserved_mem_count; i++) {
> +			struct reserved_mem *rmem = &reserved_mem[i];
> +
> +			if (rmem->dumpable && base < rmem->base + rmem->size &&
> +			    rmem->base < base + size)

[Severity: High]
Does this overlap check suffer from a 32-bit arithmetic overflow?

Both rmem->base and rmem->size are phys_addr_t. On 32-bit systems, their
addition evaluates as a 32-bit operation. If a dumpable memory region extends
exactly to the end of the 32-bit address space, rmem->base + rmem->size could
overflow and wrap to 0.

The wrapped value 0 would then be zero-extended to u64 for the comparison
against the u64 base. The comparison base < 0ULL will always evaluate to false,
causing the overlap check to silently fail and incorrectly mark the memreserve
as MEMBLOCK_NODUMP.

> +				break;
> +		}
> +		if (i == reserved_mem_count)
> +			memblock_mark_nodump(base, size);

[Severity: High]
Could this implicitly truncate the 64-bit base and size values to 32-bit?

The base and size variables are u64, but memblock_mark_nodump() expects 32-bit
phys_addr_t parameters on 32-bit systems without PAE.

If an FDT contains a memory reservation with a base address above 4GB, the
64-bit value passes the overlap check above but gets implicitly truncated here.
This modifies the truncated 32-bit address instead, completely bypassing the
overlap check for the address actually being modified, and could erroneously
mark valid dumpable memory regions as MEMBLOCK_NODUMP.

> +	}
> +}

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=4

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP
  2026-08-06  9:35   ` [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP Wandun Chen
@ 2026-08-06 10:06     ` sashiko-bot
  0 siblings, 0 replies; 20+ messages in thread
From: sashiko-bot @ 2026-08-06 10:06 UTC (permalink / raw)
  To: Wandun Chen; +Cc: devicetree, conor+dt, robh

Thank you for your contribution! Sashiko AI review found 4 potential issue(s) to consider:

New issues:
- [Critical] Marking reserved memory as MEMBLOCK_NODUMP causes a kernel panic by splitting memblock arrays before resizing is permitted.
- [High] The MEMBLOCK_NODUMP flag is inert dead code that fails to exclude regions from kdump.

Pre-existing issues:
- [High] Physical memory for dynamically allocated 'no-map' regions is leaked on driver initialization failure.
- [High] Error path unconditionally un-reserves statically placed memory, potentially corrupting overlapping critical reservations.
--

--- Patch [3]: [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP ---
commit 2e35731dcf703e597205458fb3ba8ad782294cfa
Author: Wandun Chen <chenwandun@lixiang.com>

of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP

This commit marks non-dumpable reserved-memory regions with MEMBLOCK_NODUMP
so kdump can omit them from the vmcore. The marking is guarded by
CONFIG_CRASH_DUMP so non-kdump kernels do not pay the cost of splitting
memblock.memory entries at NODUMP boundaries.

> diff --git a/drivers/of/of_reserved_mem.c b/drivers/of/of_reserved_mem.c
> index 7b1616b9c6c21..f38d11df6f152 100644
> --- a/drivers/of/of_reserved_mem.c
> +++ b/drivers/of/of_reserved_mem.c
> @@ -674,6 +674,9 @@ static void __init fdt_init_reserved_mem_node(unsigned long node, const char *un
>  			rmem->name ? rmem->name : "unknown");
>  	}
>  
> +	if (IS_ENABLED(CONFIG_CRASH_DUMP) && !rmem->dumpable)
> +		memblock_mark_nodump(rmem->base, rmem->size);

[Severity: Critical]
Does this memblock_mark_nodump() call trigger a boot-time panic?

fdt_init_reserved_mem_node() runs very early in the boot sequence.
When memblock_mark_nodump() is called, it splits existing memory regions to
isolate the nodump regions.

Since efi and e820 maps already consume many entries of the static 128-entry
memblock array, these new splits can quickly exhaust the array. When
memblock_double_array() is invoked to allocate more slots, it checks
memblock_can_resize, which is still 0 at this early stage.

Will this result in an immediate panic("memblock: cannot resize %s array\n")
for any platform booting with device tree reserved-memory nodes that exceed
the static array limits?

[Severity: High]
Does the MEMBLOCK_NODUMP flag actually exclude regions from kdump?

A full tree search reveals that this flag is never checked by
should_skip_region(), /proc/iomem exporters, or any kdump filtering logic.

Architecture setups like request_standard_resources() in arm64 only check
memblock_is_nomap(), meaning nodump regions are still exported unconditionally
to /proc/iomem as 'System RAM'.

Since the flag is never read by the kernel, will kexec-tools parse these
regions and include them in the vmcore anyway, defeating the purpose of
the patch?

> +
>  	reserved_mem_count++;
>  }

[Severity: High]
This is a pre-existing issue, but does fdt_init_reserved_mem_node() leak
physical memory for dynamically allocated 'no-map' regions on driver
initialization failure?

If __reserved_mem_init_node() returns an error, the error handling path
attempts to clean up the reservation:

drivers/of/of_reserved_mem.c:fdt_init_reserved_mem_node() {
    ...
	if (err != 0 && err != -ENODEV) {
		pr_info("node %s compatible matching fail\n", rmem->name);
		rmem->name = NULL;

		if (nomap)
			memblock_clear_nomap(rmem->base, rmem->size);
		else
			memblock_phys_free(rmem->base, rmem->size);
		return;
	}
    ...
}

For regions with the no-map property, it calls memblock_clear_nomap(), which
only removes the flag. It does not call memblock_phys_free().

Since dynamically placed regions were allocated via memblock_phys_alloc_range()
and added to memblock.reserved, doesn't this leave the physical memory
permanently in memblock.reserved without returning it to the buddy allocator?

[Severity: High]
This is also a pre-existing issue in the same error path, but does calling
memblock_phys_free() for statically placed memory unconditionally un-reserve
memory, potentially corrupting overlapping critical reservations?

For statically placed reserved-memory nodes, early_init_dt_reserve_memory()
calls memblock_reserve(), which successfully merges the region even if it
overlaps with an existing critical reservation like kernel text.

If __reserved_mem_init_node() later fails for this node, the error path
calls memblock_phys_free():

drivers/of/of_reserved_mem.c:fdt_init_reserved_mem_node() {
    ...
		else
			memblock_phys_free(rmem->base, rmem->size);
    ...
}

This translates to memblock_remove_range(&memblock.reserved, ...), which
blindly un-reserves the entire range.

If this overlapping critical memory loses its reservation, won't the buddy
allocator later hand those pages out for general use, corrupting the critical
data?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=3

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region()
  2026-08-06  9:35   ` [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region() Wandun Chen
@ 2026-08-06 10:07     ` sashiko-bot
  0 siblings, 0 replies; 20+ messages in thread
From: sashiko-bot @ 2026-08-06 10:07 UTC (permalink / raw)
  To: Wandun Chen; +Cc: robh, conor+dt, devicetree

Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:

New issues:
- [High] Use-after-free and wild pointer iteration in `for_each_mem_region` due to concurrent memory hotplug.

Pre-existing issues:
- [High] TOCTOU race between counting and populating memblock regions leading to an out-of-bounds write.
--

--- Patch [7]: [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region() ---
commit 50852c55d127f622d99b3ad7a91bdd709c53a6eb
Author: Wandun Chen <chenwandun@lixiang.com>

crash_core: replace for_each_mem_range() with for_each_mem_region()

This patch replaces the use of for_each_mem_range() with
for_each_mem_region() in the weak defaults for arch_get_system_nr_ranges()
and arch_crash_populate_cmem(). It also introduces a
crash_should_skip_region() helper to explicitly filter out MEMBLOCK_NOMAP
regions.

> diff --git a/kernel/crash_core.c b/kernel/crash_core.c
> index 77285ae3ce600..fb78b7814f188 100644
> --- a/kernel/crash_core.c
> +++ b/kernel/crash_core.c
[ ... ]
> @@ -284,22 +290,25 @@ static struct crash_mem *alloc_cmem(unsigned int nr_ranges)
>  unsigned int __weak arch_get_system_nr_ranges(void)
>  {
>  	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* crashk_res + crashk_low_res, +CMA splits */
> -	phys_addr_t start, end;
> -	u64 i;
> +	struct memblock_region *reg;
>  
> -	for_each_mem_range(i, &start, &end)
> +	for_each_mem_region(reg) {
[Severity: High]
Is it possible for a concurrent memory hotplug to cause a use-after-free and
unbounded iteration here?

If sys_kexec_file_load() calls this path without holding mem_hotplug_lock, a
concurrent memory hotplug (e.g., ACPI memory add) could add a new region via
memblock_add_node().

This could trigger memblock_double_array(), which frees the old
memblock.memory.regions array.

Because the for_each_mem_region(reg) macro initialized the reg pointer once,
would it now point to freed memory? Also, if the loop condition compares
against the new array's bounds, and the new array is at a higher address,
could the loop run out of bounds?

> +		if (crash_should_skip_region(reg))
> +			continue;
>  		nr_ranges++;
> +	}
>  	return nr_ranges;
>  }
>  
>  int __weak arch_crash_populate_cmem(struct crash_mem *cmem)
>  {
> -	phys_addr_t start, end;
> -	u64 i;
> +	struct memblock_region *reg;
>  
> -	for_each_mem_range(i, &start, &end) {
> -		cmem->ranges[cmem->nr_ranges].start = start;
> -		cmem->ranges[cmem->nr_ranges].end = end - 1;
> +	for_each_mem_region(reg) {
> +		if (crash_should_skip_region(reg))
> +			continue;
> +		cmem->ranges[cmem->nr_ranges].start = reg->base;
> +		cmem->ranges[cmem->nr_ranges].end = reg->base + reg->size - 1;
>  		cmem->nr_ranges++;
[Severity: High]
This is a pre-existing issue, but can this out-of-bounds write corrupt the
heap if a region is added concurrently?

crash_prepare_headers() performs two lockless passes over the regions:

	max_nr_ranges = arch_get_system_nr_ranges();
	if (!max_nr_ranges)
		return -ENOMEM;

	cmem = alloc_cmem(max_nr_ranges);
	if (!cmem)
		return -ENOMEM;

	ret = arch_crash_populate_cmem(cmem);

If memory hotplug adds a new region concurrently between these two passes,
the region count increases. Since the array assignment here lacks bounds
checking against cmem->max_nr_ranges, would the second pass iterate more
times than the allocated capacity and overwrite adjacent memory?

>  	}
>  	return 0;

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=7

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree
  2026-08-06  9:35   ` [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree Wandun Chen
@ 2026-08-06 10:10     ` sashiko-bot
  0 siblings, 0 replies; 20+ messages in thread
From: sashiko-bot @ 2026-08-06 10:10 UTC (permalink / raw)
  To: Wandun Chen; +Cc: devicetree, robh, conor+dt

Thank you for your contribution! Sashiko AI review found 3 potential issue(s) to consider:

New issues:
- [High] Lockless iteration over memblock regions introduces a Use-After-Free against concurrent memory hotplug.
- [Medium] for_each_mem_range() fails to filter MEMBLOCK_NODUMP regions, breaking the patch's core feature.

Pre-existing issues:
- [High] Time-of-Check to Time-of-Use (TOCTOU) race condition during lockless double-iteration causes an out-of-bounds array write.
--

--- Patch [5]: [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree ---
commit 6f60d7eb990c57ea1aef75ef70d369b6c9300b5a
Author: Wandun Chen <chenwandun@lixiang.com>

riscv: build crash_mem ranges from memblock instead of resource tree

This commit replaces walk_system_ram_res() with for_each_mem_range() to build
crash_mem ranges from memblock. It also updates the ARCH_KEEP_MEMBLOCK
config to keep memblock around when kexec file and crash dump are enabled,
allowing the exclusion of MEMBLOCK_NODUMP regions from the vmcore.

> diff --git a/arch/riscv/kernel/machine_kexec_file.c b/arch/riscv/kernel/machine_kexec_file.c
> index 26cd2a8bd0cd3..808e872f40634 100644
> --- a/arch/riscv/kernel/machine_kexec_file.c
> +++ b/arch/riscv/kernel/machine_kexec_file.c
[ ... ]
>  unsigned int arch_get_system_nr_ranges(void)
>  {
>  	unsigned int nr_ranges = 2 + crashk_cma_cnt; /* For exclusion of crashkernel region */
> +	u64 i;
> +	phys_addr_t start, end;
>  
> -	walk_system_ram_res(0, -1, &nr_ranges, get_nr_ram_ranges_callback);
> +	for_each_mem_range(i, &start, &end)
> +		nr_ranges++;

[Severity: High]
This isn't a bug introduced by this patch, but by performing a lockless count
here and then populating the array in arch_crash_populate_cmem() later,
couldn't a concurrent memory hotplug add regions in between the two calls?

If memblock regions are added after the cmem array is allocated but before it
is populated, the second loop will yield more regions than were counted,
leading to an out-of-bounds write in arch_crash_populate_cmem() since there
are no bounds checks on cmem->nr_ranges.

>  
>  	return nr_ranges;
>  }
>  
[ ... ]
> -int arch_crash_populate_cmem(struct crash_mem *cmem)
> -{
> -	return walk_system_ram_res(0, -1, cmem, prepare_elf64_ram_headers_callback);
> -}
> -
> +int arch_crash_populate_cmem(struct crash_mem *cmem)
> +{
> +	u64 i;
> +	phys_addr_t start, end;
>  
> +	for_each_mem_range(i, &start, &end) {

[Severity: Medium]
The commit message mentions that "only by walking memblock can the
reserved-memory regions marked MEMBLOCK_NODUMP be excluded". Does
for_each_mem_range() actually filter out MEMBLOCK_NODUMP regions?

Looking at for_each_mem_range(), it delegates to should_skip_region(), which
doesn't appear to have any logic to filter MEMBLOCK_NODUMP. Will this loop
end up blindly yielding all regions and failing to exclude the targeted memory
from the vmcore?

[Severity: High]
Since for_each_mem_range() iterates over memblock.memory.regions locklessly,
is it safe against concurrent memory hotplug?

If a memory hotplug operation runs concurrently and adds new memory regions,
memblock_add_node() might exceed the current region limit and trigger
memblock_double_array(). This allocates a new array and frees the old one,
potentially causing a use-after-free if this lockless iteration is still
accessing the freed array.

> +		cmem->ranges[cmem->nr_ranges].start = start;
> +		cmem->ranges[cmem->nr_ranges].end = end - 1;
> +		cmem->nr_ranges++;
> +	}
>  
>  	return 0;
>  }

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=5

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 0/8] kdump: reduce vmcore size and capture time
  2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
                     ` (7 preceding siblings ...)
  2026-08-06  9:35   ` [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header Wandun Chen
@ 2026-08-06 10:11   ` Marek Szyprowski
  8 siblings, 0 replies; 20+ messages in thread
From: Marek Szyprowski @ 2026-08-06 10:11 UTC (permalink / raw)
  To: Wandun Chen, catalin.marinas, will, chenhuacai, pjw, palmer, aou,
	robh, saravanak, rppt, baoquan.he, pasha.tatashin, pratyush,
	linux-arm-kernel, linux-kernel, loongarch, linux-riscv,
	devicetree, linux-mm, kexec, iommu
  Cc: kernel, alex, akpm, ruirui.yang, robin.murphy

On 06.08.2026 11:35, Wandun Chen wrote:
> From: Wandun Chen <chenwandun@lixiang.com>
>
> On SoCs that carve out large firmware-owned reserved memory (GPU,
> camera ISP, ...), kdump currently dumps those carveouts as part of
> system RAM even though their contents are firmware state that is not
> useful for kernel crash analysis.
>
> This series introduces a 'dumpable' flag on struct reserved_mem and a
> MEMBLOCK_NODUMP flag in memblock to filter vmcore ELF header on DT-based
> architectures (arm64, riscv, loongarch). Reserved regions default to
> non-dumpable and are marked MEMBLOCK_NODUMP so kdump omits them;
> reusable CMA regions are explicitly marked dumpable in rmem_cma_setup()
> because their pages are handed back to the buddy allocator and may carry
> crash-relevant data.
>
> Since the reserved memory regions are filtered out, the vmcore is
> smaller in size and faster to produce. ACPI systems already filter
> reserved memory out of the vmcore through their existing path; only
> DT-based systems currently fail to filter these regions, which is what
> this series addresses. The flag lives in memblock itself rather than
> in a DT-only structure, so the mechanism is generic and both ACPI and
> DT systems can benefit from it (suggested by Rob, thanks).
>
> The series is based on linux-next and is organized as follows:
>   Patches 1-2: Introduce MEMBLOCK_NODUMP in memblock and the dumpable
>                flag on struct reserved_mem.
>   Patches 3-4: Mark non-dumpable /reserved-memory and /memreserve/
>                entries with MEMBLOCK_NODUMP.
>   Patch 5:     Switch riscv to memblock so the NODUMP flag is visible
>                to the vmcore ELF header builder; add (KEXEC_FILE &&
>                CRASH_DUMP) to riscv's ARCH_KEEP_MEMBLOCK condition.
>   Patches 6-8: Fold the duplicated per-arch memblock walks into the
>                weak defaults in crash_core, switch to
>                for_each_mem_region(), and exclude MEMBLOCK_NODUMP
>                regions from the vmcore ELF header.
>
> v4 --> v5:
> 1. Rework the mechanism around a memblock-level MEMBLOCK_NODUMP flag
>    (suggested by Rob) instead of the v4 opt-in 'dumpable' flag on
>    DT-only struct reserved_mem.
>
> 2. Switch the riscv vmcore elf header preparation to use memblock
>    instead of the resource tree, aligning it with arm64 and loongarch,
>    so riscv also can exclude reserved memory from vmcore.
>
> 3. Deduplicate the vmcore elf header preparation: arm64, riscv and
>    loongarch open-coded the same logic, so fold it into shared
>     __weak defaults in crash_core.
>
> 4.  Drop the v4 patch that saved /memreserve/ entries into the
>     reserved_mem array; /memreserve/ is now marked MEMBLOCK_NODUMP
>     directly.

v5 looks much better, at least from the reserved memory regions perspective.


> v3 --> v4:
> 1. Rebase this series on v7.2-rc1.
> 2. Add two cleanup patches (patch 02/03).
> 3. Simplify patch 03 to avoid checking whether initial_boot_params is
>    NULL multiple times, suggested by Rob.
>
> v2 --> v3:
> 1. Fix out-of-bounds issue if device tree lacks /reserved-memory node.[2]
> 2. Fix UAF issue when alloc_reserved_mem_array() fails.
> 3. Add some prepare patches.
>
> v1 --> v2:
> 1. v1 added an opt-out DT property ('linux,no-dump'). Per Rob's
>    feedback [1], v2 drop that property and exclude reserve memory
>    by default.
> 2. Split some prepared patches from the original patches.
> 3. Address coding-style comments on patch 5 from Rob.
>
> [1] https://lore.kernel.org/lkml/20260506144542.GA2072596-robh@kernel.org/
> [2] https://protect2.fireeye.com/v1/url?k=05b72ed7-643c3bed-05b6a598-74fe4860008a-295907342918bd15&q=1&e=c408484d-fdd8-4fe4-8eee-690e883afb73&u=https%3A%2F%2Fsashiko.dev%2F%23%2Fpatchset%2F20260520091844.592753-1-chenwandun%2540lixiang.com%3Fpart%3D4
>
> Wandun Chen (8):
>   memblock: introduce MEMBLOCK_NODUMP flag
>   of: reserved_mem: add dumpable flag to opt-in vmcore
>   of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP
>   of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP
>   riscv: build crash_mem ranges from memblock instead of resource tree
>   crash_core: fold duplicated memblock arch hooks into the weak default
>   crash_core: replace for_each_mem_range() with for_each_mem_region()
>   crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF
>     header
>
>  arch/arm64/kernel/machine_kexec_file.c     | 29 ------------------
>  arch/loongarch/kernel/machine_kexec_file.c | 27 -----------------
>  arch/riscv/Kconfig                         |  2 +-
>  arch/riscv/kernel/machine_kexec_file.c     | 33 --------------------
>  drivers/of/fdt.c                           |  2 ++
>  drivers/of/of_private.h                    |  1 +
>  drivers/of/of_reserved_mem.c               | 35 ++++++++++++++++++++++
>  include/linux/memblock.h                   |  9 ++++++
>  include/linux/of_reserved_mem.h            |  1 +
>  kernel/crash_core.c                        | 34 +++++++++++++++++++--
>  kernel/dma/contiguous.c                    |  1 +
>  mm/memblock.c                              | 16 ++++++++++
>  12 files changed, 98 insertions(+), 92 deletions(-)
>
Best regards
-- 
Marek Szyprowski, PhD
Samsung R&D Institute Poland


^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header
  2026-08-06  9:35   ` [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header Wandun Chen
@ 2026-08-06 10:24     ` sashiko-bot
  0 siblings, 0 replies; 20+ messages in thread
From: sashiko-bot @ 2026-08-06 10:24 UTC (permalink / raw)
  To: Wandun Chen; +Cc: conor+dt, devicetree, robh

Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:

Pre-existing issues:
- [High] Lockless iteration over memblock regions without bounds checks can lead to Use-After-Free and Heap Buffer Overflow during concurrent memory hotplug.
--

--- Patch [8]: [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header ---
commit 7fdffadebf6d8803dc1491f6f55262a163ba9f05
Author: Wandun Chen <chenwandun@lixiang.com>

crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header

Reserve regions (for GPU, DSP, ...) carry no data useful for crash
analysis. Exclude MEMBLOCK_NODUMP regions from the vmcore ELF header to
reduce vmcore size and capture time. crash_should_skip_region() now also
returns true for MEMBLOCK_NODUMP.

> diff --git a/kernel/crash_core.c b/kernel/crash_core.c
> index fb78b7814f188..8cc9d666bc541 100644
> --- a/kernel/crash_core.c
> +++ b/kernel/crash_core.c
> @@ -269,10 +269,10 @@ int crash_prepare_elf64_headers(struct crash_mem *mem, int need_kernel_map,
>  	return 0;
>  }
>  
> -/* Exclude NOMAP regions from the vmcore. */
> +/* Exclude NOMAP and NODUMP regions from the vmcore. */
>  static bool crash_should_skip_region(struct memblock_region *reg)
>  {
> -	return memblock_is_nomap(reg);
> +	return memblock_is_nomap(reg) || memblock_is_nodump(reg);
>  }

[Severity: High]
This isn't a bug introduced by this patch, but is it safe to call this
function during a lockless memblock iteration?

The caller arch_get_system_nr_ranges() uses for_each_mem_region(reg) without
taking locks. If a privileged user initiates memory hotplug concurrently
while loading a crash kernel, memblock_add_node() could trigger
memblock_double_array(), which reallocates and frees the
memblock.memory.regions array mid-iteration.

Could this result in a use-after-free on the memblock array?

kernel/crash_core.c:arch_get_system_nr_ranges() {
	...
	for_each_mem_region(reg) {
		if (crash_should_skip_region(reg))
			continue;
		nr_ranges++;
	}
	...
}

Additionally, there appears to be a time-of-check to time-of-use window
in crash_prepare_headers() between sizing and populating. If memory is
hot-added during this window, the second iteration could encounter more
regions than originally counted:

kernel/crash_core.c:crash_prepare_headers() {
	...
	max_nr_ranges = arch_get_system_nr_ranges();
	if (!max_nr_ranges)
		return -ENOMEM;

	cmem = alloc_cmem(max_nr_ranges);
	...
	ret = arch_crash_populate_cmem(cmem);
	...
}

Because arch_crash_populate_cmem() writes to cmem->ranges without bounds
checking, could this race cause a heap buffer overflow on the cmem->ranges
array?

-- 
Sashiko AI review · https://sashiko.dev/#/patchset/20260806093519.2907771-1-chenwandun1@gmail.com?part=8

^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag
  2026-08-06  9:51     ` sashiko-bot
@ 2026-08-06 11:43       ` Wandun
  0 siblings, 0 replies; 20+ messages in thread
From: Wandun @ 2026-08-06 11:43 UTC (permalink / raw)
  To: sashiko-reviews; +Cc: robh, conor+dt, devicetree



On 8/6/26 17:51, sashiko-bot@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 2 potential issue(s) to consider:
> - [High] The patch completely omits the filtering logic required to exclude MEMBLOCK_NODUMP regions from kdump vmcores.
> - [Medium] The MEMBLOCK_NODUMP flag extends the flagname array but leaves an uninitialized hole for MEMBLOCK_RSRV_HUGETLB, leading to a NULL format argument.
> --
> 
> --- Patch [1]: [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag ---
> commit b30a0bfd2a4e00657ccc3f49bdfa4a7ca5fdfa1d
> Author: Wandun Chen <chenwandun@lixiang.com>
> 
> memblock: introduce MEMBLOCK_NODUMP flag
> 
> Add MEMBLOCK_NODUMP to mark regions that should be excluded from kdump vmcores.
> The flag is meant for reserved memory that carries no data useful for crash
> analysis. Subsequent patches wire this up for /reserved-memory and
> /memreserve/ entries.
> 
>> diff --git a/mm/memblock.c b/mm/memblock.c
>> index 9ce86349a29fa..79231634c25b0 100644
>> --- a/mm/memblock.c
>> +++ b/mm/memblock.c
>> @@ -1204,6 +1204,21 @@ __init int memblock_clear_kho_scratch(phys_addr_t base, phys_addr_t size)
>>  				    MEMBLOCK_KHO_SCRATCH);
>>  }
>>  
>> +/**
>> + * memblock_mark_nodump - Mark a memory region with flag MEMBLOCK_NODUMP.
>> + * @base: the base phys addr of the region
>> + * @size: the size of the region
>> + *
>> + * Mark the region as not to be included in crash dumps.
>> + *
>> + * Return: 0 on success, -errno on failure.
>> + */
>> +int __init_memblock memblock_mark_nodump(phys_addr_t base, phys_addr_t size)
>> +{
>> +	return memblock_setclr_flag(&memblock.memory, base, size, 1,
>> +				    MEMBLOCK_NODUMP);
>> +}
>> +
> 
> [Severity: High]
> Is it intentional that the filtering logic for this new flag was omitted?
> 
> Without updating should_skip_region() in this file to filter out regions
> marked with MEMBLOCK_NODUMP, the flag appears to have no functional effect.
> 
> When architecture kdump setup iterates over memory ranges (e.g., using
> for_each_mem_range()) to build the crash dump list, these regions will still
> be included because should_skip_region() does not know to skip them.

Not correct, will handle MEMBLOCK_NODUMP flag in patch8.

> 
> [ ... ]
> 
>> @@ -2886,6 +2901,7 @@ static const char * const flagname[] = {
>>  	[ilog2(MEMBLOCK_RSRV_NOINIT)] = "RSV_NIT",
>>  	[ilog2(MEMBLOCK_RSRV_KERN)] = "RSV_KERN",
>>  	[ilog2(MEMBLOCK_KHO_SCRATCH)] = "KHO_SCRATCH",
>> +	[ilog2(MEMBLOCK_NODUMP)] = "NODUMP",
>>  };
>>  
>>  static int memblock_debug_show(struct seq_file *m, void *private)
> 
> [Severity: Medium]
> Will this expansion of the array leave a NULL pointer hole for the
> MEMBLOCK_RSRV_HUGETLB flag?
> 
> Prior to this patch, the max index was 6. MEMBLOCK_RSRV_HUGETLB is bit 7,
> which safely fell back to printing "UNKNOWN". 
> 
> Adding MEMBLOCK_NODUMP (bit 8) expands the array size to 9. Due to designated
> initialization, index 7 becomes NULL.
> 
> When memblock_debug_show() prints a region with MEMBLOCK_RSRV_HUGETLB set,
> it will read the NULL pointer and pass it to seq_printf():
> 
>     if (reg->flags & (1U << j)) {
>         seq_printf(m, "%s\n", flagname[j]);
>         break;
>     }

This is indeed an issue, but it was not introduced by this patch.
A separate patch will be sent to fix it.

> 
> While seq_printf() will safely print "(null)", this will break out of the
> printing loop early and omit any other flags. Could MEMBLOCK_RSRV_HUGETLB
> be added to the array as well to avoid this hole?
> 


^ permalink raw reply	[flat|nested] 20+ messages in thread

* Re: [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore
  2026-08-06  9:47     ` sashiko-bot
@ 2026-08-06 11:48       ` Wandun
  0 siblings, 0 replies; 20+ messages in thread
From: Wandun @ 2026-08-06 11:48 UTC (permalink / raw)
  To: sashiko-reviews; +Cc: conor+dt, devicetree, robh



On 8/6/26 17:47, sashiko-bot@kernel.org wrote:
> Thank you for your contribution! Sashiko AI review found 1 potential issue(s) to consider:
> - [Medium] Incomplete implementation and write-only dead code: the `dumpable` flag is introduced and set, but the promised kdump filtering and overlap checks are missing.
> --
> 
> --- Patch [2]: [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore ---
> commit 873defcf6278254b5c39d8d3500f986e38a79da0
> Author: Wandun Chen <chenwandun@lixiang.com>
> 
> of: reserved_mem: add dumpable flag to opt-in vmcore
> 
> This commit adds a dumpable flag to struct reserved_mem to track whether
> a reserved area should be included in the kdump vmcore. It sets the flag
> for CMA regions to true in rmem_cma_setup().
> 
>> diff --git a/include/linux/of_reserved_mem.h b/include/linux/of_reserved_mem.h
>> index e8b20b29fa68c..55a67cee41ea0 100644
>> --- a/include/linux/of_reserved_mem.h
>> +++ b/include/linux/of_reserved_mem.h
>> @@ -15,6 +15,7 @@ struct reserved_mem {
>>  	phys_addr_t			base;
>>  	phys_addr_t			size;
>>  	void				*priv;
>> +	bool				dumpable;
> 
> [Severity: Medium]
> Is the logic that checks this flag missing from this patch?
> 
> The commit message states that non-dumpable regions are later marked
> MEMBLOCK_NODUMP, and that the flag is used to check for overlap with
> /memreserve/ entries. However, this flag appears to be write-only,
> as there are no corresponding checks or calls to memblock_mark_nodump()
> implemented in this commit.

Not correct. The checking of dumpable flag is in patch 03 and patch 04.

> 
>>  };
> 
> [ ... ]
> 
>> diff --git a/kernel/dma/contiguous.c b/kernel/dma/contiguous.c
>> index f754079a287d6..63ff134dadd42 100644
>> --- a/kernel/dma/contiguous.c
>> +++ b/kernel/dma/contiguous.c
>> @@ -565,6 +565,7 @@ static int __init rmem_cma_setup(unsigned long node, struct reserved_mem *rmem)
>>  		dma_contiguous_default_area = cma;
>>  
>>  	rmem->priv = cma;
>> +	rmem->dumpable = true;
> 
> [Severity: Medium]
> Does setting this flag have any effect?
> 
> Since the promised kdump filtering and overlap checks are missing from the
> code, this assignment currently acts as dead code. Were those checks meant
> to be included in this submission?

Not dead code, the checking of dumpable flag is in patch 03 and patch 04.>


^ permalink raw reply	[flat|nested] 20+ messages in thread

end of thread, other threads:[~2026-08-06 11:48 UTC | newest]

Thread overview: 20+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
     [not found] <CGME20260806093541eucas1p169d6fcb31de09012bdfca326867e86d6@eucas1p1.samsung.com>
2026-08-06  9:35 ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Wandun Chen
2026-08-06  9:35   ` [PATCH v5 1/8] memblock: introduce MEMBLOCK_NODUMP flag Wandun Chen
2026-08-06  9:51     ` sashiko-bot
2026-08-06 11:43       ` Wandun
2026-08-06  9:35   ` [PATCH v5 2/8] of: reserved_mem: add dumpable flag to opt-in vmcore Wandun Chen
2026-08-06  9:47     ` sashiko-bot
2026-08-06 11:48       ` Wandun
2026-08-06  9:35   ` [PATCH v5 3/8] of: reserved_mem: mark /reserved-memory entries with MEMBLOCK_NODUMP Wandun Chen
2026-08-06 10:06     ` sashiko-bot
2026-08-06  9:35   ` [PATCH v5 4/8] of: reserved_mem: mark /memreserve/ entries as MEMBLOCK_NODUMP Wandun Chen
2026-08-06  9:57     ` sashiko-bot
2026-08-06  9:35   ` [PATCH v5 5/8] riscv: build crash_mem ranges from memblock instead of resource tree Wandun Chen
2026-08-06 10:10     ` sashiko-bot
2026-08-06  9:35   ` [PATCH v5 6/8] crash_core: fold duplicated memblock arch hooks into the weak default Wandun Chen
2026-08-06  9:56     ` sashiko-bot
2026-08-06  9:35   ` [PATCH v5 7/8] crash_core: replace for_each_mem_range() with for_each_mem_region() Wandun Chen
2026-08-06 10:07     ` sashiko-bot
2026-08-06  9:35   ` [PATCH v5 8/8] crash_core: skip MEMBLOCK_NODUMP regions when building vmcore ELF header Wandun Chen
2026-08-06 10:24     ` sashiko-bot
2026-08-06 10:11   ` [PATCH v5 0/8] kdump: reduce vmcore size and capture time Marek Szyprowski

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).