kexec-tools/kexec-tools-2.0.3-vmcore-dmesg-Do-not-write-beyond-end-of-buffer.patch
Dave Young 7468d46e9c Pull vmcore-dmesg patches from vivek
Add below two commits from upstream:
1.
commit c96e7736d85e40685939011e6d51b3c0a28739a3
Author: Vivek Goyal <vgoyal@redhat.com>
Date:   Wed Jul 18 09:33:51 2012 -0400

    vmcore-dmesg: Do not write beyond end of buffer

    scan_vmcoreinfo() currently assumes that every vmcoreinfo note line ends
    with \n and overwrites new line with \0. But last entry in note, CRASHTIME=
    does not end with \n and this leads to corrupting memory as we write beyond
    end of buffer.

    Normally things were fine but when I added some fields to vmcoreinfo, this
    bug started showing and vmcore-dmesg started crashing.

    I am planning to send a patch to fix this in kernel but it might be good
    idea to handle this case in user space too so that vmcore-dmesg works
    fine with cores of older kernels.

    Signed-off-by: Vivek Goyal <vgoyal@redhat.com>
    Signed-off-by: Simon Horman <horms@verge.net.au>
2.
commit df88cab364cd1a3b8c992042d62efe5e350e6b2a
Author: Vivek Goyal <vgoyal@redhat.com>
Date:   Mon Jul 30 13:32:48 2012 -0400

    vmcore-dmesg: vmcore-dmesg: Make it work with new structured logging format

    Now kernel has made kernel logging structured and exsisting vmcore-dmesg
    does not work with this new format. Hence kernel version 3.5 is broken. In
    3.6 now a kernel patch has been put which exports relevant fields. This
    patch parses those fields and makes vmcore-dmesg work with new logging
    format.

    Currently it does not display log levels or dictionary. I personally think
    that log levels are not very useful and it also requires additional kernel
    patches so that log levels are not bitfields and relevant information is
    exported to user space properly.

    Concept of dictionary is new and relevant information is exported. One can
    possibly enahnce vmcore-dmesg to also print dictionary contents based on
    a user command line option.

    Signed-off-by: Vivek Goyal <vgoyal@redhat.com>
    Signed-off-by: Simon Horman <horms@verge.net.au>
2012-09-29 13:19:03 +08:00

88 lines
2.6 KiB
Diff

From c96e7736d85e40685939011e6d51b3c0a28739a3 Mon Sep 17 00:00:00 2001
From: Vivek Goyal <vgoyal@redhat.com>
Date: Wed, 18 Jul 2012 09:33:51 -0400
Subject: [PATCH] vmcore-dmesg: Do not write beyond end of buffer
scan_vmcoreinfo() currently assumes that every vmcoreinfo note line ends
with \n and overwrites new line with \0. But last entry in note, CRASHTIME=
does not end with \n and this leads to corrupting memory as we write beyond
end of buffer.
Normally things were fine but when I added some fields to vmcoreinfo, this
bug started showing and vmcore-dmesg started crashing.
I am planning to send a patch to fix this in kernel but it might be good
idea to handle this case in user space too so that vmcore-dmesg works
fine with cores of older kernels.
Signed-off-by: Vivek Goyal <vgoyal@redhat.com>
Signed-off-by: Simon Horman <horms@verge.net.au>
---
vmcore-dmesg/vmcore-dmesg.c | 29 ++++++++++++++++++++++++++++-
1 files changed, 28 insertions(+), 1 deletions(-)
diff --git a/vmcore-dmesg/vmcore-dmesg.c b/vmcore-dmesg/vmcore-dmesg.c
index 8518150..2e692de 100644
--- a/vmcore-dmesg/vmcore-dmesg.c
+++ b/vmcore-dmesg/vmcore-dmesg.c
@@ -14,6 +14,7 @@
#include <sys/stat.h>
#include <fcntl.h>
#include <elf.h>
+#include <stdbool.h>
/* The 32bit and 64bit note headers make it clear we don't care */
typedef Elf32_Nhdr Elf_Nhdr;
@@ -220,6 +221,9 @@ static void scan_vmcoreinfo(char *start, size_t size)
{
char *last = start + size - 1;
char *pos, *eol;
+ char temp_buf[1024];
+ bool last_line = false;
+
#define SYMBOL(sym) { \
.str = "SYMBOL(" #sym ")=", \
.name = #sym, \
@@ -243,7 +247,27 @@ static void scan_vmcoreinfo(char *start, size_t size)
/* Find the end of the current line */
for (eol = pos; (eol <= last) && (*eol != '\n') ; eol++)
;
- len = eol - pos + 1;
+ if (eol > last) {
+ /*
+ * We did not find \n and note ended. Currently kernel
+ * is appending last field CRASH_TIME without \n. It
+ * is ugly but handle it.
+ */
+ eol = last;
+ len = eol - pos + 1;
+ if (len >= sizeof(temp_buf))
+ len = sizeof(temp_buf) - 1;
+ strncpy(temp_buf, pos, len);
+ temp_buf[len + 1] = '\0';
+
+ pos = temp_buf;
+ len = len + 1;
+ eol = pos + len -1;
+ last_line = true;
+ } else {
+ len = eol - pos + 1;
+ }
+
/* Stomp the last character so I am guaranteed a terminating null */
*eol = '\0';
/* Copy OSRELEASE if I see it */
@@ -266,6 +290,9 @@ static void scan_vmcoreinfo(char *start, size_t size)
/* Remember the virtual address */
*symbol[i].vaddr = vaddr;
}
+
+ if (last_line)
+ break;
}
}
--
1.7.1