The kernel vmcore may contain a new elf-note of type NT_NOCOREDUMP. Include this
new note, whose address and length are made available at
/sys/kernel/nt_nocoredump, while loading elf-headers.

Signed-off-by: K.Prasad <[email protected]>
---

diff --git a/kexec/crashdump-elf.c b/kexec/crashdump-elf.c
index 8d82db9..b009227 100644
--- a/kexec/crashdump-elf.c
+++ b/kexec/crashdump-elf.c
@@ -39,7 +39,9 @@ int FUNC(struct kexec_info *info,
        long int nr_cpus = 0;
        uint64_t notes_addr, notes_len;
        uint64_t vmcoreinfo_addr, vmcoreinfo_len;
+       uint64_t nt_nocoredump_addr, nt_nocoredump_len;
        int has_vmcoreinfo = 0;
+       int has_nt_nocoredump = 0;
        uint64_t vmcoreinfo_addr_xen, vmcoreinfo_len_xen;
        int has_vmcoreinfo_xen = 0;
        int (*get_note_info)(int cpu, uint64_t *addr, uint64_t *len);
@@ -57,6 +59,9 @@ int FUNC(struct kexec_info *info,
                has_vmcoreinfo = 1;
        }
 
+       if (get_kernel_nt_nocoredump(&nt_nocoredump_addr, &nt_nocoredump_len) 
== 0)
+               has_nt_nocoredump = 1;
+
        if (xen_present() &&
            get_xen_vmcoreinfo(&vmcoreinfo_addr_xen, &vmcoreinfo_len_xen) == 0) 
{
                has_vmcoreinfo_xen = 1;
@@ -179,6 +184,21 @@ int FUNC(struct kexec_info *info,
                dbgprintf_phdr("vmcoreinfo header", phdr);
        }
 
+       if (has_nt_nocoredump && !(info->kexec_flags & KEXEC_PRESERVE_CONTEXT)) 
{
+               phdr = (PHDR *) bufp;
+               bufp += sizeof(PHDR);
+               phdr->p_type    = PT_NOTE;
+               phdr->p_flags   = 0;
+               phdr->p_offset  = phdr->p_paddr = nt_nocoredump_addr;
+               phdr->p_vaddr   = 0;
+               phdr->p_filesz  = phdr->p_memsz = nt_nocoredump_len;
+               /* Do we need any alignment of segments? */
+               phdr->p_align   = 0;
+
+               (elf->e_phnum)++;
+               dbgprintf_phdr("nocoredump note present", phdr);
+       }
+
        if (has_vmcoreinfo_xen) {
                phdr = (PHDR *) bufp;
                bufp += sizeof(PHDR);
diff --git a/kexec/crashdump.c b/kexec/crashdump.c
index 945b052..0ee05f0 100644
--- a/kexec/crashdump.c
+++ b/kexec/crashdump.c
@@ -136,12 +136,43 @@ static int get_vmcoreinfo(const char *kdump_info, 
uint64_t *addr, uint64_t *len)
        return 0;
 }
 
+static int get_nt_nocoredump(const char *kdump_info, uint64_t *addr, uint64_t 
*len)
+{
+       char line[MAX_LINE];
+       int count;
+       FILE *fp;
+       unsigned int temp2;
+       unsigned long long temp;
+
+       *addr = 0;
+       *len = 0;
+
+       if (!(fp = fopen(kdump_info, "r")))
+               return -1;
+       if (!fgets(line, sizeof(line), fp))
+               die("Cannot parse %s: %s\n", kdump_info, strerror(errno));
+       count = sscanf(line, "%Lx %x", &temp, &temp2);
+       if (count != 2)
+               die("Cannot parse %s: %s\n", kdump_info, strerror(errno));
+
+       *addr = (uint64_t) temp;
+       *len = (uint64_t) temp2;
+
+       fclose(fp);
+       return 0;
+}
 /* Returns the physical address of start of crash notes buffer for a kernel. */
 int get_kernel_vmcoreinfo(uint64_t *addr, uint64_t *len)
 {
        return get_vmcoreinfo("/sys/kernel/vmcoreinfo", addr, len);
 }
 
+/* Returns the physical address of start of nocoredump buffer for a kernel. */
+int get_kernel_nt_nocoredump(uint64_t *addr, uint64_t *len)
+{
+       return get_nt_nocoredump("/sys/kernel/nt_nocoredump", addr, len);
+}
+
 int get_xen_vmcoreinfo(uint64_t *addr, uint64_t *len)
 {
        return get_vmcoreinfo("/sys/hypervisor/vmcoreinfo", addr, len);
-- 
1.7.4.1

--
Crash-utility mailing list
[email protected]
https://www.redhat.com/mailman/listinfo/crash-utility

Reply via email to