diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2026-10-19 19:23:18 -1000 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2026-10-19 19:23:18 -1000 |
| commit | ae78eff333746326e630e505d7fac0d237e644ef (patch) | |
| tree | 5fedc5998b5394d65b8af49ad80464034e07566c /kernel | |
| parent | b040da2a0046ae64eeeed256b4465f231d5ee6de (diff) | |
compat: use scoped user access in get_compat_sigevent()
get_compat_sigevent() does one access_ok() on the user structure and
then reads four fields with __get_user(). Each of those reads enables
and disables user access on its own, so the single range check no longer
buys anything.
Read the fields inside a scoped_user_read_access() instead.
This is part of getting rid of __get_user() and __put_user() entirely.
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'kernel')
| -rw-r--r-- | kernel/compat.c | 20 |
1 files changed, 12 insertions, 8 deletions
diff --git a/kernel/compat.c b/kernel/compat.c index fb50f29d9b36..c754793c7d65 100644 --- a/kernel/compat.c +++ b/kernel/compat.c @@ -180,14 +180,18 @@ int get_compat_sigevent(struct sigevent *event, const struct compat_sigevent __user *u_event) { memset(event, 0, sizeof(*event)); - return (!access_ok(u_event, sizeof(*u_event)) || - __get_user(event->sigev_value.sival_int, - &u_event->sigev_value.sival_int) || - __get_user(event->sigev_signo, &u_event->sigev_signo) || - __get_user(event->sigev_notify, &u_event->sigev_notify) || - __get_user(event->sigev_notify_thread_id, - &u_event->sigev_notify_thread_id)) - ? -EFAULT : 0; + scoped_user_read_access(u_event, Efault) { + unsafe_get_user(event->sigev_value.sival_int, + &u_event->sigev_value.sival_int, Efault); + unsafe_get_user(event->sigev_signo, &u_event->sigev_signo, Efault); + unsafe_get_user(event->sigev_notify, &u_event->sigev_notify, Efault); + unsafe_get_user(event->sigev_notify_thread_id, + &u_event->sigev_notify_thread_id, Efault); + } + return 0; + +Efault: + return -EFAULT; } long compat_get_bitmap(unsigned long *mask, const compat_ulong_t __user *umask, |
