xref: /linux/include/vdso/futex.h (revision 0eaed89c18aeedf0898baf2dbf5ff027c6795152)
1 /* SPDX-License-Identifier: GPL-2.0 */
2 #ifndef _VDSO_FUTEX_H
3 #define _VDSO_FUTEX_H
4 
5 #include <uapi/linux/types.h>
6 
7 /**
8  * __vdso_futex_robust_list64_try_unlock - Try to unlock an uncontended robust futex
9  *					   with a 64-bit pending op pointer
10  * @lock:	Pointer to the futex lock object
11  * @tid:	The TID of the calling task
12  * @pop:	Pointer to the task's robust_list_head::list_pending_op
13  *
14  * Return: The content of *@lock. On success this is the same as @tid.
15  *
16  * The function implements:
17  *	if (atomic_try_cmpxchg(lock, &tid, 0))
18  *		*op = NULL;
19  *	return tid;
20  *
21  * There is a race between a successful unlock and clearing the pending op
22  * pointer in the robust list head. If the calling task is interrupted in the
23  * race window and has to handle a (fatal) signal on return to user space then
24  * the kernel handles the clearing of @pending_op before attempting to deliver
25  * the signal. That ensures that a task cannot exit with a potentially invalid
26  * pending op pointer.
27  *
28  * User space uses it in the following way:
29  *
30  * if (__vdso_futex_robust_list64_try_unlock(lock, tid, &pending_op) != tid)
31  *	err = sys_futex($OP | FUTEX_ROBUST_UNLOCK,....);
32  *
33  * If the unlock attempt fails due to the FUTEX_WAITERS bit set in the lock,
34  * then the syscall does the unlock, clears the pending op pointer and wakes the
35  * requested number of waiters.
36  */
37 __u32 __vdso_futex_robust_list64_try_unlock(__u32 *lock, __u32 tid, __u64 *pop);
38 
39 /**
40  * __vdso_futex_robust_list32_try_unlock - Try to unlock an uncontended robust futex
41  *					   with a 32-bit pending op pointer
42  * @lock:	Pointer to the futex lock object
43  * @tid:	The TID of the calling task
44  * @pop:	Pointer to the task's robust_list_head::list_pending_op
45  *
46  * Return: The content of *@lock. On success this is the same as @tid.
47  *
48  * Same as __vdso_futex_robust_list64_try_unlock() just with a 32-bit @pop pointer.
49  */
50 __u32 __vdso_futex_robust_list32_try_unlock(__u32 *lock, __u32 tid, __u32 *pop);
51 
52 #endif
53