Pass the kbuf fields to crash_prepare_headers() and set
elf_headers before kexec_add_buffer(), so the error path needs
no vfree() because arch_kimage_file_post_load_cleanup() will do it.

Cc: Huacai Chen <[email protected]>
Cc: Baoquan He <[email protected]>
Signed-off-by: Jinjie Ruan <[email protected]>
---
 arch/loongarch/kernel/machine_kexec_file.c | 38 +++++++++-------------
 1 file changed, 16 insertions(+), 22 deletions(-)

diff --git a/arch/loongarch/kernel/machine_kexec_file.c 
b/arch/loongarch/kernel/machine_kexec_file.c
index 3beb6977ecc6..6ea60e0faa2c 100644
--- a/arch/loongarch/kernel/machine_kexec_file.c
+++ b/arch/loongarch/kernel/machine_kexec_file.c
@@ -127,11 +127,12 @@ int load_other_segments(struct kimage *image,
        unsigned long initrd_load_addr = 0;
        unsigned long orig_segments = image->nr_segments;
        char *modified_cmdline = NULL;
-       struct kexec_buf kbuf = {};
-
-       kbuf.image = image;
-       /* Don't allocate anything below the kernel */
-       kbuf.buf_min = kernel_load_addr + kernel_size;
+       struct kexec_buf kbuf = {
+               .image = image,
+               /* Don't allocate anything below the kernel */
+               .buf_min = kernel_load_addr + kernel_size,
+               .buf_max = ULONG_MAX,
+       };
 
        modified_cmdline = kzalloc(COMMAND_LINE_SIZE, GFP_KERNEL);
        if (!modified_cmdline)
@@ -144,35 +145,28 @@ int load_other_segments(struct kimage *image,
 #ifdef CONFIG_CRASH_DUMP
        /* Load elf core header */
        if (image->type == KEXEC_TYPE_CRASH) {
-               void *headers;
-               unsigned long headers_sz;
-
-               ret = crash_prepare_headers(true, &headers, &headers_sz, NULL);
+               ret = crash_prepare_headers(true, &kbuf.buffer, &kbuf.bufsz, 
NULL);
                if (ret < 0) {
                        pr_err("Preparing elf core header failed\n");
                        goto out_err;
                }
 
-               kbuf.buffer = headers;
-               kbuf.bufsz = headers_sz;
+               if (unlikely(image->elf_headers))
+                       vfree(image->elf_headers);
+
+               image->elf_headers = kbuf.buffer;
+               image->elf_headers_sz = kbuf.bufsz;
+
                kbuf.mem = KEXEC_BUF_MEM_UNKNOWN;
-               kbuf.memsz = headers_sz;
+               kbuf.memsz = kbuf.bufsz;
                kbuf.buf_align = SZ_64K; /* largest supported page size */
-               kbuf.buf_max = ULONG_MAX;
                kbuf.top_down = true;
 
                ret = kexec_add_buffer(&kbuf);
-               if (ret < 0) {
-                       vfree(headers);
+               if (ret < 0)
                        goto out_err;
-               }
-
-               if (unlikely(image->elf_headers))
-                       vfree(image->elf_headers);
 
-               image->elf_headers = headers;
                image->elf_load_addr = kbuf.mem;
-               image->elf_headers_sz = headers_sz;
 
                kexec_dprintk("Loaded elf core header at 0x%lx bufsz=0x%lx 
memsz=0x%lx\n",
                              image->elf_load_addr, kbuf.bufsz, kbuf.memsz);
@@ -181,7 +175,7 @@ int load_other_segments(struct kimage *image,
                cmdline_add_mem(&cmdline_tmplen, modified_cmdline);
 
                /* Add the elfcorehdr=size@start parameter to the command line 
*/
-               cmdline_add_elfcorehdr(image, &cmdline_tmplen, 
modified_cmdline, headers_sz);
+               cmdline_add_elfcorehdr(image, &cmdline_tmplen, 
modified_cmdline, kbuf.bufsz);
        }
 #endif
 
-- 
2.34.1


Reply via email to