[patch V2 6/6] posix-cpu-timers: Return -EPERM if ptrace permission check fails

From: Thomas Gleixner
Date: Mon Sep 23 2019 - 10:56:57 EST


Returning -EINVAL when a permission check fails is not really intuitive and
can cause hard to diagnose problems.

The POSIX specification for clock_gettime() and timer_create() requires to
obtain the clock id first by invoking clock_getcpuclockid().

clock_getcpuclockid() can return -EPERM if the caller does not have
permissions. That does not make sense in two aspects:

- Nothing prevents the caller to make up a clockid and feed it into the
syscalls

- clock_getcpuclockid() is a helper function in glibc which just mangles
the PID/TID bits to the proper place and glibc cannot do any permission
checks at all for this function.

In order to prevent abuse the kernel has to do the permission checking in
timer_create() and clock_gettime(). Those functions have only -EINVAL as
documented return values, but returning -EINVAL for a valid clockid when
the permission check fails is not understandable for programmers.

So ignore the POSIX specification and return -EPERM when the ptrace
permission check fails.

Suggested-by: Peter Zijlstra <peterz@xxxxxxxxxxxxx>
Signed-off-by: Thomas Gleixner <tglx@xxxxxxxxxxxxx>
---
V2: New patch.

TODO: Update timer_create.2 and clock_gettime.2 manpages
---
kernel/time/posix-cpu-timers.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)

--- a/kernel/time/posix-cpu-timers.c
+++ b/kernel/time/posix-cpu-timers.c
@@ -107,7 +107,7 @@ static struct task_struct *lookup_task(c
}

/* Decide based on the ptrace permissions. */
- return ptrace_may_access(p, mode) ? p : ERR_PTR(-EINVAL);
+ return ptrace_may_access(p, mode) ? p : ERR_PTR(-EPERM);
}

static struct task_struct *__get_task_for_clock(const clockid_t clock,