]> asedeno.scripts.mit.edu Git - linux.git/commitdiff
s390/kdump: Fix memleak in nt_vmcoreinfo
authorPhilipp Rudo <prudo@linux.ibm.com>
Mon, 13 Aug 2018 09:16:57 +0000 (11:16 +0200)
committerHeiko Carstens <heiko.carstens@de.ibm.com>
Thu, 16 Aug 2018 12:49:14 +0000 (14:49 +0200)
The vmcoreinfo of a crashed system is potentially fragmented. Thus the
crash kernel has an intermediate step where the vmcoreinfo is copied into a
temporary, continuous buffer in the crash kernel memory. This temporary
buffer is never freed. Free it now to prevent the memleak.

While at it replace all occurrences of "VMCOREINFO" by its corresponding
macro to prevent potential renaming issues.

Signed-off-by: Philipp Rudo <prudo@linux.ibm.com>
Acked-by: Heiko Carstens <heiko.carstens@de.ibm.com>
Signed-off-by: Heiko Carstens <heiko.carstens@de.ibm.com>
arch/s390/kernel/crash_dump.c

index 4b2773e1ddfe2bdf78ab037a09eb2fe8e394d2a4..27d2b7093ea03c9982bc8e0d796b49ff0457c454 100644 (file)
@@ -451,11 +451,13 @@ static void *get_vmcoreinfo_old(unsigned long *size)
        if (copy_oldmem_kernel(nt_name, addr + sizeof(note),
                               sizeof(nt_name) - 1))
                return NULL;
-       if (strcmp(nt_name, "VMCOREINFO") != 0)
+       if (strcmp(nt_name, VMCOREINFO_NOTE_NAME) != 0)
                return NULL;
        vmcoreinfo = kzalloc_panic(note.n_descsz);
-       if (copy_oldmem_kernel(vmcoreinfo, addr + 24, note.n_descsz))
+       if (copy_oldmem_kernel(vmcoreinfo, addr + 24, note.n_descsz)) {
+               kfree(vmcoreinfo);
                return NULL;
+       }
        *size = note.n_descsz;
        return vmcoreinfo;
 }
@@ -465,15 +467,20 @@ static void *get_vmcoreinfo_old(unsigned long *size)
  */
 static void *nt_vmcoreinfo(void *ptr)
 {
+       const char *name = VMCOREINFO_NOTE_NAME;
        unsigned long size;
        void *vmcoreinfo;
 
        vmcoreinfo = os_info_old_entry(OS_INFO_VMCOREINFO, &size);
-       if (!vmcoreinfo)
-               vmcoreinfo = get_vmcoreinfo_old(&size);
+       if (vmcoreinfo)
+               return nt_init_name(ptr, 0, vmcoreinfo, size, name);
+
+       vmcoreinfo = get_vmcoreinfo_old(&size);
        if (!vmcoreinfo)
                return ptr;
-       return nt_init_name(ptr, 0, vmcoreinfo, size, "VMCOREINFO");
+       ptr = nt_init_name(ptr, 0, vmcoreinfo, size, name);
+       kfree(vmcoreinfo);
+       return ptr;
 }
 
 static size_t nt_vmcoreinfo_size(void)