[PATCH v4 5/5] x86: implement crashkernel cma reservation

Jiri Bohac posted 5 patches 6 months, 2 weeks ago
There is a newer version of this series
[PATCH v4 5/5] x86: implement crashkernel cma reservation
Posted by Jiri Bohac 6 months, 2 weeks ago
Implement the crashkernel CMA reservation for x86:
- enable parsing of the cma suffix by parse_crashkernel()
- reserve memory with reserve_crashkernel_cma()
- add the CMA-reserved ranges to the e820 map for the crash kernel
- exclude the CMA-reserved ranges from vmcore

Signed-off-by: Jiri Bohac <jbohac@suse.cz>
---
 arch/x86/kernel/crash.c | 26 ++++++++++++++++++++++----
 arch/x86/kernel/setup.c |  5 +++--
 2 files changed, 25 insertions(+), 6 deletions(-)

diff --git a/arch/x86/kernel/crash.c b/arch/x86/kernel/crash.c
index 0be61c45400c..670aa9b8b0f8 100644
--- a/arch/x86/kernel/crash.c
+++ b/arch/x86/kernel/crash.c
@@ -163,10 +163,10 @@ static struct crash_mem *fill_up_crash_elf_data(void)
 		return NULL;
 
 	/*
-	 * Exclusion of crash region and/or crashk_low_res may cause
-	 * another range split. So add extra two slots here.
+	 * Exclusion of crash region, crashk_low_res and/or crashk_cma_ranges
+	 * may cause range splits. So add extra slots here.
 	 */
-	nr_ranges += 2;
+	nr_ranges += 2 + crashk_cma_cnt;
 	cmem = vzalloc(struct_size(cmem, ranges, nr_ranges));
 	if (!cmem)
 		return NULL;
@@ -184,6 +184,7 @@ static struct crash_mem *fill_up_crash_elf_data(void)
 static int elf_header_exclude_ranges(struct crash_mem *cmem)
 {
 	int ret = 0;
+	int i;
 
 	/* Exclude the low 1M because it is always reserved */
 	ret = crash_exclude_mem_range(cmem, 0, SZ_1M - 1);
@@ -198,8 +199,17 @@ static int elf_header_exclude_ranges(struct crash_mem *cmem)
 	if (crashk_low_res.end)
 		ret = crash_exclude_mem_range(cmem, crashk_low_res.start,
 					      crashk_low_res.end);
+	if (ret)
+		return ret;
 
-	return ret;
+	for (i = 0; i < crashk_cma_cnt; ++i) {
+		ret = crash_exclude_mem_range(cmem, crashk_cma_ranges[i].start,
+					      crashk_cma_ranges[i].end);
+		if (ret)
+			return ret;
+	}
+
+	return 0;
 }
 
 static int prepare_elf64_ram_headers_callback(struct resource *res, void *arg)
@@ -352,6 +362,14 @@ int crash_setup_memmap_entries(struct kimage *image, struct boot_params *params)
 		add_e820_entry(params, &ei);
 	}
 
+	for (i = 0; i < crashk_cma_cnt; ++i) {
+		ei.addr = crashk_cma_ranges[i].start;
+		ei.size = crashk_cma_ranges[i].end -
+			  crashk_cma_ranges[i].start + 1;
+		ei.type = E820_TYPE_RAM;
+		add_e820_entry(params, &ei);
+	}
+
 out:
 	vfree(cmem);
 	return ret;
diff --git a/arch/x86/kernel/setup.c b/arch/x86/kernel/setup.c
index 870b06571b2e..dcbeba344825 100644
--- a/arch/x86/kernel/setup.c
+++ b/arch/x86/kernel/setup.c
@@ -573,7 +573,7 @@ static void __init memblock_x86_reserve_range_setup_data(void)
 
 static void __init arch_reserve_crashkernel(void)
 {
-	unsigned long long crash_base, crash_size, low_size = 0;
+	unsigned long long crash_base, crash_size, low_size = 0, cma_size = 0;
 	bool high = false;
 	int ret;
 
@@ -582,7 +582,7 @@ static void __init arch_reserve_crashkernel(void)
 
 	ret = parse_crashkernel(boot_command_line, memblock_phys_mem_size(),
 				&crash_size, &crash_base,
-				&low_size, NULL, &high);
+				&low_size, &cma_size, &high);
 	if (ret)
 		return;
 
@@ -592,6 +592,7 @@ static void __init arch_reserve_crashkernel(void)
 	}
 
 	reserve_crashkernel_generic(crash_size, crash_base, low_size, high);
+	reserve_crashkernel_cma(cma_size);
 }
 
 static struct resource standard_io_resources[] = {


-- 
Jiri Bohac <jbohac@suse.cz>
SUSE Labs, Prague, Czechia
Re: [PATCH v4 5/5] x86: implement crashkernel cma reservation
Posted by Baoquan He 6 months, 2 weeks ago
On 05/30/25 at 10:31pm, Jiri Bohac wrote:
......snip.. 
> @@ -582,7 +582,7 @@ static void __init arch_reserve_crashkernel(void)
>  
>  	ret = parse_crashkernel(boot_command_line, memblock_phys_mem_size(),
>  				&crash_size, &crash_base,
> -				&low_size, NULL, &high);
> +				&low_size, &cma_size, &high);
>  	if (ret)
>  		return;
>  
> @@ -592,6 +592,7 @@ static void __init arch_reserve_crashkernel(void)
>  	}
>  
>  	reserve_crashkernel_generic(crash_size, crash_base, low_size, high);
> +	reserve_crashkernel_cma(cma_size);

Wondering if ,high|low is still allowed (or needed) when ,cma is specified.
Re: [PATCH v4 5/5] x86: implement crashkernel cma reservation
Posted by Jiri Bohac 6 months, 2 weeks ago
On Tue, Jun 03, 2025 at 07:02:06PM +0800, Baoquan He wrote:
> On 05/30/25 at 10:31pm, Jiri Bohac wrote:
> ......snip.. 
> > @@ -582,7 +582,7 @@ static void __init arch_reserve_crashkernel(void)
> >  
> >  	ret = parse_crashkernel(boot_command_line, memblock_phys_mem_size(),
> >  				&crash_size, &crash_base,
> > -				&low_size, NULL, &high);
> > +				&low_size, &cma_size, &high);
> >  	if (ret)
> >  		return;
> >  
> > @@ -592,6 +592,7 @@ static void __init arch_reserve_crashkernel(void)
> >  	}
> >  
> >  	reserve_crashkernel_generic(crash_size, crash_base, low_size, high);
> > +	reserve_crashkernel_cma(cma_size);
> 
> Wondering if ,high|low is still allowed (or needed) when ,cma is specified.

Probably not needed but it works, totally independent of the
extra CMA-reserved area.

I saw no reason to artificially prevent it.

-- 
Jiri Bohac <jbohac@suse.cz>
SUSE Labs, Prague, Czechia
Re: [PATCH v4 5/5] x86: implement crashkernel cma reservation
Posted by Baoquan He 6 months, 2 weeks ago
On 06/03/25 at 02:11pm, Jiri Bohac wrote:
> On Tue, Jun 03, 2025 at 07:02:06PM +0800, Baoquan He wrote:
> > On 05/30/25 at 10:31pm, Jiri Bohac wrote:
> > ......snip.. 
> > > @@ -582,7 +582,7 @@ static void __init arch_reserve_crashkernel(void)
> > >  
> > >  	ret = parse_crashkernel(boot_command_line, memblock_phys_mem_size(),
> > >  				&crash_size, &crash_base,
> > > -				&low_size, NULL, &high);
> > > +				&low_size, &cma_size, &high);
> > >  	if (ret)
> > >  		return;
> > >  
> > > @@ -592,6 +592,7 @@ static void __init arch_reserve_crashkernel(void)
> > >  	}
> > >  
> > >  	reserve_crashkernel_generic(crash_size, crash_base, low_size, high);
> > > +	reserve_crashkernel_cma(cma_size);
> > 
> > Wondering if ,high|low is still allowed (or needed) when ,cma is specified.
> 
> Probably not needed but it works, totally independent of the
> extra CMA-reserved area.

Allowing it can simplify the current code, while I can't imagine what
cases need people to specify
"crashkernel=xM,high crashkernel=xM,low crashkernel=zM,cma" at one time.

Just personal thought, I haven't think of a strong reason to prevent it
too.

> 
> I saw no reason to artificially prevent it.
> 
> -- 
> Jiri Bohac <jbohac@suse.cz>
> SUSE Labs, Prague, Czechia
>