| From: Jiri Bohac <jbohac@suse.cz> |
| Subject: x86: implement crashkernel cma reservation |
| Date: Thu, 12 Jun 2025 12:20:04 +0200 |
| |
| 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 |
| |
| Link: https://lkml.kernel.org/r/aEqp1LD2og4QeBw9@dwarf.suse.cz |
| Signed-off-by: Jiri Bohac <jbohac@suse.cz> |
| Cc: Baoquan He <bhe@redhat.com> |
| Cc: Dave Young <dyoung@redhat.com> |
| Cc: David Hildenbrand <david@redhat.com> |
| Cc: Donald Dutile <ddutile@redhat.com> |
| Cc: Michal Hocko <mhocko@suse.cz> |
| Cc: Philipp Rudo <prudo@redhat.com> |
| Cc: Pingfan Liu <piliu@redhat.com> |
| Cc: Tao Liu <ltao@redhat.com> |
| Cc: Vivek Goyal <vgoyal@redhat.com> |
| Signed-off-by: Andrew Morton <akpm@linux-foundation.org> |
| --- |
| |
| arch/x86/kernel/crash.c | 26 ++++++++++++++++++++++---- |
| arch/x86/kernel/setup.c | 5 +++-- |
| 2 files changed, 25 insertions(+), 6 deletions(-) |
| |
| --- a/arch/x86/kernel/crash.c~x86-implement-crashkernel-cma-reservation |
| +++ a/arch/x86/kernel/crash.c |
| @@ -163,10 +163,10 @@ static struct crash_mem *fill_up_crash_e |
| 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_e |
| 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(str |
| 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) |
| @@ -373,6 +383,14 @@ int crash_setup_memmap_entries(struct ki |
| ei.type = E820_TYPE_RAM; |
| 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); |
| --- a/arch/x86/kernel/setup.c~x86-implement-crashkernel-cma-reservation |
| +++ a/arch/x86/kernel/setup.c |
| @@ -599,7 +599,7 @@ static void __init memblock_x86_reserve_ |
| |
| 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; |
| |
| @@ -608,7 +608,7 @@ static void __init arch_reserve_crashker |
| |
| 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; |
| |
| @@ -618,6 +618,7 @@ static void __init arch_reserve_crashker |
| } |
| |
| reserve_crashkernel_generic(crash_size, crash_base, low_size, high); |
| + reserve_crashkernel_cma(cma_size); |
| } |
| |
| static struct resource standard_io_resources[] = { |
| _ |