Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/kern Fix a read-beyond-end string read.



details:   https://anonhg.NetBSD.org/src/rev/6516921983c7
branches:  trunk
changeset: 328894:6516921983c7
user:      maxv <maxv%NetBSD.org@localhost>
date:      Tue Apr 22 19:01:47 2014 +0000

description:
Fix a read-beyond-end string read.

coredump_buildname() copies 'pattern' into 'name', and handles special
characters such as "%n". "%n", if present, will be replaced by p->p_comm.

        error = coredump_buildname(p, name, pattern, MAXPATHLEN);

This function handles overflows, and returns an error when 'name' becomes
larger than MAXPATHLEN. However, when coredump() calls it, 'name' is used
before the error check, with:

        lastslash = strrchr(name, '/');

'name' is not guaranteed to be NUL-terminated, because of the *d = *s in
coredump_buildname(). This strrchr will read a string which is not NUL-
terminated (ie. until finding a '\0' in memory).

'pattern' can't be higher than MAXPATHLEN. A user can fill it in via a
PT_DUMPCORE ptrace call, given the input is not longer than MAXPATHLEN.
Since the 2-bytes-sized "%n"s will be replaced by p->p_comm (which is
user-settable, like a 10-bytes-sized "0123456789"), 'name' can become
longer than 'pattern' (and thus longer than MAXPATHLEN). Some 'a's at the
end of the buffer will make sure 'name' is not NUL-terminated.

    pattern: "%n%n%naaaaaaaaaaaaaaaaaaaaaaaaaaaa\0"
              | | | |||||||||||||||||||||||||||||
  ->   name: "012345678901234567890123456789aaaaa" [no \0]
              |         |         |         |||||MAXPATHLEN

Fix it by checking 'error' before calling strrchr.

diffstat:

 sys/kern/kern_core.c |  10 ++++++++--
 1 files changed, 8 insertions(+), 2 deletions(-)

diffs (31 lines):

diff -r 920c868e73b1 -r 6516921983c7 sys/kern/kern_core.c
--- a/sys/kern/kern_core.c      Tue Apr 22 18:51:35 2014 +0000
+++ b/sys/kern/kern_core.c      Tue Apr 22 19:01:47 2014 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: kern_core.c,v 1.22 2014/01/03 20:52:47 dsl Exp $       */
+/*     $NetBSD: kern_core.c,v 1.23 2014/04/22 19:01:47 maxv Exp $      */
 
 /*
  * Copyright (c) 1982, 1986, 1989, 1991, 1993
@@ -37,7 +37,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: kern_core.c,v 1.22 2014/01/03 20:52:47 dsl Exp $");
+__KERNEL_RCSID(0, "$NetBSD: kern_core.c,v 1.23 2014/04/22 19:01:47 maxv Exp $");
 
 #include <sys/param.h>
 #include <sys/vnode.h>
@@ -155,6 +155,12 @@
        error = coredump_buildname(p, name, pattern, MAXPATHLEN);
        mutex_exit(&lim->pl_lock);
 
+       if (error) {
+               mutex_exit(p->p_lock);
+               mutex_exit(proc_lock);
+               goto done;
+       }
+
        /*
         * On a simple filename, see if the filesystem allow us to write
         * core dumps there.



Home | Main Index | Thread Index | Old Index