Bug 194215 - CVE-2006-2448 missing access_ok checks in powerpc signal*.c
Summary: CVE-2006-2448 missing access_ok checks in powerpc signal*.c
Keywords:
Status: CLOSED ERRATA
Alias: None
Product: Red Hat Enterprise Linux 4
Classification: Red Hat
Component: kernel
Version: 4.0
Hardware: All
OS: Linux
medium
high
Target Milestone: ---
: ---
Assignee: David Woodhouse
QA Contact: Brian Brock
URL:
Whiteboard: impact=important,source=kernelsec,rep...
Depends On:
Blocks: 181411
TreeView+ depends on / blocked
 
Reported: 2006-06-06 12:04 UTC by Marcel Holtmann
Modified: 2007-11-30 22:07 UTC (History)
4 users (show)

Fixed In Version: RHSA-2006-0575
Doc Type: Bug Fix
Doc Text:
Clone Of:
Environment:
Last Closed: 2006-08-10 23:26:47 UTC
Target Upstream Version:
Embargoed:


Attachments (Terms of Use)
RHEL4 patch (1.35 KB, patch)
2006-06-08 14:03 UTC, David Woodhouse
no flags Details | Diff
Test case from David Woodhouse (693 bytes, text/x-csrc)
2006-06-14 10:31 UTC, Marcel Holtmann
no flags Details
Updated minimal and correct patch (576 bytes, patch)
2006-06-14 22:43 UTC, David Woodhouse
no flags Details | Diff


Links
System ID Private Priority Status Summary Last Updated
Red Hat Product Errata RHSA-2006:0575 0 normal SHIPPED_LIVE Important: Updated kernel packages available for Red Hat Enterprise Linux 4 Update 4 2006-08-10 04:00:00 UTC

Description Marcel Holtmann 2006-06-06 12:04:16 UTC
Dave Jones reported that he was able to provoke a machine check on ppc32 with
his scrashme program, apparently as a result of missing access_ok checks on the
arguments to the sys_debug_setcontext system call. In signal_32.c and
signal_64.c there were other similar issues.

Some of them are pretty serious. One of them will let an unprivileged user
program read any kernel memory on ppc64 systems with Altivec. Both 32-bit and
64-bit kernels are affected and some of the problems go back to the 2.4 days. It
appears that some of the people that did the original ppc64 port liked to do

        ret = put_user(&p->a);
        ret |= __put_user(&p->b);
        if (ret)
                return -EFAULT;

which is of course *not* a good idea, although

        if (put_user(&p->a) || __put_user(&p->b))
                return -EFAULT;

is OK on ppc64 because of the large gap between TASK_SIZE and KERNELBASE.

Comment 2 Marcel Holtmann 2006-06-06 15:42:24 UTC
Paul Mackerras revised his initial post and mentioned that those of the
bogosities found that are in the 32-bit compatibility code for 64-bit kernels
aren't actually security holes, since it isn't possible for a 32-bit process to
generate a kernel address. That leaves:

- a hole in the 64-bit kernel that lets unprivileged processes read (but not
write) arbitrary kernel memory on systems that have Altivec.

- a hole that lets processes on a 32-bit kernel restore their register set from
an arbitrary kernel address (on signal return or with the sys_swapcontext or
sys_debug_setcontext system calls). That only reads kernel memory and would be
hard to exploit as a method of reading kernel memory since the program counter
would be set to some hard-to-predict value. It could be used to crash the system
though.


Comment 3 Marcel Holtmann 2006-06-07 10:27:43 UTC
The arch/powerpc/kernel/signal_32.c changes from the patch map to
ppc64/kernel/signal32.c in the RHEL4 kernel.

In sys32_rt_sigaction() we see the same problems addressed in the upstream patch.

The do_setcontext32() function is missing a verify_area() call.

In sys32_swapcontext() the RHEL4 kernel has the needed verify_area() call
already. So it seems this one got removed upstream during the PowerPC
re-organization.

The verify_area() call in arch/ppc64/kernel/signal.c for the Altivec specific
issue is missing.


Comment 4 David Woodhouse 2006-06-08 13:40:23 UTC
Of which, the only one which actually matters is the last, because the rest will
all be limited to 32-bit addresses anyway. 

There's also a suspect read from regs->rip in fix_alignment(), in some
circumstances.


Comment 5 David Woodhouse 2006-06-08 14:03:22 UTC
Created attachment 130744 [details]
RHEL4 patch

Comment 6 Marcel Holtmann 2006-06-14 10:26:39 UTC
The final upstream patch can be found here:

http://www.kernel.org/git/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=7c85d1f9d358b24c5b05c3a2783a78423775a080


Comment 9 Josh Bressers 2006-06-14 12:39:30 UTC
------- Additional Comments From holtmann  2006-06-12 03:11 EST -------
For reference the upstream fix can be found here:

http://www.kernel.org/git/?p=linux/kernel/git/torvalds/linux-2.6.git;a=commit;h=7c85d1f9d358b24c5b05c3a2783a78423775a080


Comment 10 David Woodhouse 2006-06-14 22:43:29 UTC
Created attachment 130940 [details]
Updated minimal and correct patch

The part in fix_alignment() in the previous patch was not necessary.

Also, revert to using access_ok() as in the original upstream patch, having
corrected the length.

This is the version which was tested.

Comment 17 Jason Baron 2006-06-27 01:15:02 UTC
committed in stream U4 build 39.2. A test kernel with this patch is available
from http://people.redhat.com/~jbaron/rhel4/

Comment 22 Red Hat Bugzilla 2006-08-10 23:26:53 UTC
An advisory has been issued which should help the problem
described in this bug report. This report is therefore being
closed with a resolution of ERRATA. For more information
on the solution and/or where to find the updated files,
please follow the link below. You may reopen this bug report
if the solution does not work for you.

http://rhn.redhat.com/errata/RHSA-2006-0575.html



Note You need to log in before you can comment on or make changes to this bug.