summaryrefslogtreecommitdiffstats
path: root/kernel/futex
diff options
context:
space:
mode:
authorpeterz@infradead.org <peterz@infradead.org>2023-09-21 12:45:10 +0200
committerPeter Zijlstra <peterz@infradead.org>2023-09-21 19:22:07 +0200
commit9f6c532f59b20580acf8ede9409c9b8dce6e74e1 (patch)
treea0ace6e28ec4b23343056bd4b889214ac2777d83 /kernel/futex
parentfutex: Validate futex value against futex size (diff)
downloadlinux-9f6c532f59b20580acf8ede9409c9b8dce6e74e1.tar.xz
linux-9f6c532f59b20580acf8ede9409c9b8dce6e74e1.zip
futex: Add sys_futex_wake()
To complement sys_futex_waitv() add sys_futex_wake(). This syscall implements what was previously known as FUTEX_WAKE_BITSET except it uses 'unsigned long' for the bitmask and takes FUTEX2 flags. The 'unsigned long' allows FUTEX2_SIZE_U64 on 64bit platforms. Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org> Reviewed-by: Thomas Gleixner <tglx@linutronix.de> Acked-by: Geert Uytterhoeven <geert@linux-m68k.org> Link: https://lore.kernel.org/r/20230921105247.936205525@noisy.programming.kicks-ass.net
Diffstat (limited to 'kernel/futex')
-rw-r--r--kernel/futex/syscalls.c30
1 files changed, 30 insertions, 0 deletions
diff --git a/kernel/futex/syscalls.c b/kernel/futex/syscalls.c
index 2339f9ccee7f..7049a52ef68e 100644
--- a/kernel/futex/syscalls.c
+++ b/kernel/futex/syscalls.c
@@ -306,6 +306,36 @@ destroy_timer:
return ret;
}
+/*
+ * sys_futex_wake - Wake a number of futexes
+ * @uaddr: Address of the futex(es) to wake
+ * @mask: bitmask
+ * @nr: Number of the futexes to wake
+ * @flags: FUTEX2 flags
+ *
+ * Identical to the traditional FUTEX_WAKE_BITSET op, except it is part of the
+ * futex2 family of calls.
+ */
+
+SYSCALL_DEFINE4(futex_wake,
+ void __user *, uaddr,
+ unsigned long, mask,
+ int, nr,
+ unsigned int, flags)
+{
+ if (flags & ~FUTEX2_VALID_MASK)
+ return -EINVAL;
+
+ flags = futex2_to_flags(flags);
+ if (!futex_flags_valid(flags))
+ return -EINVAL;
+
+ if (!futex_validate_input(flags, mask))
+ return -EINVAL;
+
+ return futex_wake(uaddr, flags, nr, mask);
+}
+
#ifdef CONFIG_COMPAT
COMPAT_SYSCALL_DEFINE2(set_robust_list,
struct compat_robust_list_head __user *, head,