diff options
author | Jann Horn <jann@thejh.net> | 2016-01-21 02:00:04 +0300 |
---|---|---|
committer | Ben Hutchings <ben@decadent.org.uk> | 2017-09-15 20:30:57 +0300 |
commit | 1c8d42255f4c55f9550f72bbcda758aeff3fd7c2 (patch) | |
tree | 78932bdc67795d81ceb60a992ad385431aa1410f /mm | |
parent | 33bab9221e22bab4ddc167f6c49b6ca9c35c2ccf (diff) | |
download | linux-1c8d42255f4c55f9550f72bbcda758aeff3fd7c2.tar.xz |
ptrace: use fsuid, fsgid, effective creds for fs access checks
commit caaee6234d05a58c5b4d05e7bf766131b810a657 upstream.
By checking the effective credentials instead of the real UID / permitted
capabilities, ensure that the calling process actually intended to use its
credentials.
To ensure that all ptrace checks use the correct caller credentials (e.g.
in case out-of-tree code or newly added code omits the PTRACE_MODE_*CREDS
flag), use two new flags and require one of them to be set.
The problem was that when a privileged task had temporarily dropped its
privileges, e.g. by calling setreuid(0, user_uid), with the intent to
perform following syscalls with the credentials of a user, it still passed
ptrace access checks that the user would not be able to pass.
While an attacker should not be able to convince the privileged task to
perform a ptrace() syscall, this is a problem because the ptrace access
check is reused for things in procfs.
In particular, the following somewhat interesting procfs entries only rely
on ptrace access checks:
/proc/$pid/stat - uses the check for determining whether pointers
should be visible, useful for bypassing ASLR
/proc/$pid/maps - also useful for bypassing ASLR
/proc/$pid/cwd - useful for gaining access to restricted
directories that contain files with lax permissions, e.g. in
this scenario:
lrwxrwxrwx root root /proc/13020/cwd -> /root/foobar
drwx------ root root /root
drwxr-xr-x root root /root/foobar
-rw-r--r-- root root /root/foobar/secret
Therefore, on a system where a root-owned mode 6755 binary changes its
effective credentials as described and then dumps a user-specified file,
this could be used by an attacker to reveal the memory layout of root's
processes or reveal the contents of files he is not allowed to access
(through /proc/$pid/cwd).
[akpm@linux-foundation.org: fix warning]
Signed-off-by: Jann Horn <jann@thejh.net>
Acked-by: Kees Cook <keescook@chromium.org>
Cc: Casey Schaufler <casey@schaufler-ca.com>
Cc: Oleg Nesterov <oleg@redhat.com>
Cc: Ingo Molnar <mingo@redhat.com>
Cc: James Morris <james.l.morris@oracle.com>
Cc: "Serge E. Hallyn" <serge.hallyn@ubuntu.com>
Cc: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
Cc: Andy Lutomirski <luto@kernel.org>
Cc: Al Viro <viro@zeniv.linux.org.uk>
Cc: "Eric W. Biederman" <ebiederm@xmission.com>
Cc: Willy Tarreau <w@1wt.eu>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
[bwh: Backported to 3.2:
- Drop changes to kcmp, procfs map_files, procfs has_pid_permissions()
- Keep using uid_t, gid_t and == operator for IDs
- Adjust context]
Signed-off-by: Ben Hutchings <ben@decadent.org.uk>
Diffstat (limited to 'mm')
-rw-r--r-- | mm/process_vm_access.c | 2 |
1 files changed, 1 insertions, 1 deletions
diff --git a/mm/process_vm_access.c b/mm/process_vm_access.c index 70e814a4d0b8..88c35c9e4407 100644 --- a/mm/process_vm_access.c +++ b/mm/process_vm_access.c @@ -299,7 +299,7 @@ static ssize_t process_vm_rw_core(pid_t pid, const struct iovec *lvec, } task_lock(task); - if (__ptrace_may_access(task, PTRACE_MODE_ATTACH)) { + if (__ptrace_may_access(task, PTRACE_MODE_ATTACH_REALCREDS)) { task_unlock(task); rc = -EPERM; goto put_task_struct; |