| From: Yuntao Wang <ytcoode@gmail.com> |
| Subject: x86/crash: fix potential cmem->ranges array overflow |
| Date: Mon, 18 Dec 2023 16:19:14 +0800 |
| |
| The max_nr_ranges field of cmem allocated in crash_setup_memmap_entries() |
| is not initialized, its default value is 0. |
| |
| When elfcorehdr is allocated from the middle of crashk_res due to any |
| potential reason, that is, `image->elf_load_addr > crashk_res.start && |
| image->elf_load_addr + image->elf_headers_sz - 1 < crashk_res.end`, |
| executing memmap_exclude_ranges() will cause a range split to occur in |
| crash_exclude_mem_range(), which eventually leads to an overflow of the |
| cmem->ranges array. |
| |
| Set cmem->max_nr_ranges to 1 to make crash_exclude_mem_range() return |
| -ENOMEM instead of causing cmem->ranges array overflow even when a split |
| happens. |
| |
| Link: https://lkml.kernel.org/r/20231218081915.24120-2-ytcoode@gmail.com |
| Signed-off-by: Yuntao Wang <ytcoode@gmail.com> |
| Cc: Borislav Petkov (AMD) <bp@alien8.de> |
| Cc: Dave Hansen <dave.hansen@linux.intel.com> |
| Cc: Dave Young <dyoung@redhat.com> |
| Cc: Hari Bathini <hbathini@linux.ibm.com> |
| Cc: "H. Peter Anvin" <hpa@zytor.com> |
| Cc: Ingo Molnar <mingo@redhat.com> |
| Cc: Sean Christopherson <seanjc@google.com> |
| Cc: Takashi Iwai <tiwai@suse.de> |
| Cc: Thomas Gleixner <tglx@linutronix.de> |
| Cc: Vivek Goyal <vgoyal@redhat.com> |
| Signed-off-by: Andrew Morton <akpm@linux-foundation.org> |
| --- |
| |
| arch/x86/kernel/crash.c | 9 +++++---- |
| 1 file changed, 5 insertions(+), 4 deletions(-) |
| |
| --- a/arch/x86/kernel/crash.c~x86-crash-fix-potential-cmem-ranges-array-overflow |
| +++ a/arch/x86/kernel/crash.c |
| @@ -282,10 +282,6 @@ int crash_setup_memmap_entries(struct ki |
| struct crash_memmap_data cmd; |
| struct crash_mem *cmem; |
| |
| - cmem = vzalloc(struct_size(cmem, ranges, 1)); |
| - if (!cmem) |
| - return -ENOMEM; |
| - |
| memset(&cmd, 0, sizeof(struct crash_memmap_data)); |
| cmd.params = params; |
| |
| @@ -321,6 +317,11 @@ int crash_setup_memmap_entries(struct ki |
| } |
| |
| /* Exclude some ranges from crashk_res and add rest to memmap */ |
| + cmem = vzalloc(struct_size(cmem, ranges, 1)); |
| + if (!cmem) |
| + return -ENOMEM; |
| + cmem->max_nr_ranges = 1; |
| + |
| ret = memmap_exclude_ranges(image, cmem, crashk_res.start, crashk_res.end); |
| if (ret) |
| goto out; |
| _ |