1*4882a593Smuzhiyun /* SPDX-License-Identifier: GPL-2.0 WITH Linux-syscall-note */ 2*4882a593Smuzhiyun #ifndef _UAPI_LINUX_FUTEX_H 3*4882a593Smuzhiyun #define _UAPI_LINUX_FUTEX_H 4*4882a593Smuzhiyun 5*4882a593Smuzhiyun #include <linux/compiler.h> 6*4882a593Smuzhiyun #include <linux/types.h> 7*4882a593Smuzhiyun 8*4882a593Smuzhiyun /* Second argument to futex syscall */ 9*4882a593Smuzhiyun 10*4882a593Smuzhiyun 11*4882a593Smuzhiyun #define FUTEX_WAIT 0 12*4882a593Smuzhiyun #define FUTEX_WAKE 1 13*4882a593Smuzhiyun #define FUTEX_FD 2 14*4882a593Smuzhiyun #define FUTEX_REQUEUE 3 15*4882a593Smuzhiyun #define FUTEX_CMP_REQUEUE 4 16*4882a593Smuzhiyun #define FUTEX_WAKE_OP 5 17*4882a593Smuzhiyun #define FUTEX_LOCK_PI 6 18*4882a593Smuzhiyun #define FUTEX_UNLOCK_PI 7 19*4882a593Smuzhiyun #define FUTEX_TRYLOCK_PI 8 20*4882a593Smuzhiyun #define FUTEX_WAIT_BITSET 9 21*4882a593Smuzhiyun #define FUTEX_WAKE_BITSET 10 22*4882a593Smuzhiyun #define FUTEX_WAIT_REQUEUE_PI 11 23*4882a593Smuzhiyun #define FUTEX_CMP_REQUEUE_PI 12 24*4882a593Smuzhiyun 25*4882a593Smuzhiyun #define FUTEX_PRIVATE_FLAG 128 26*4882a593Smuzhiyun #define FUTEX_CLOCK_REALTIME 256 27*4882a593Smuzhiyun #define FUTEX_CMD_MASK ~(FUTEX_PRIVATE_FLAG | FUTEX_CLOCK_REALTIME) 28*4882a593Smuzhiyun 29*4882a593Smuzhiyun #define FUTEX_WAIT_PRIVATE (FUTEX_WAIT | FUTEX_PRIVATE_FLAG) 30*4882a593Smuzhiyun #define FUTEX_WAKE_PRIVATE (FUTEX_WAKE | FUTEX_PRIVATE_FLAG) 31*4882a593Smuzhiyun #define FUTEX_REQUEUE_PRIVATE (FUTEX_REQUEUE | FUTEX_PRIVATE_FLAG) 32*4882a593Smuzhiyun #define FUTEX_CMP_REQUEUE_PRIVATE (FUTEX_CMP_REQUEUE | FUTEX_PRIVATE_FLAG) 33*4882a593Smuzhiyun #define FUTEX_WAKE_OP_PRIVATE (FUTEX_WAKE_OP | FUTEX_PRIVATE_FLAG) 34*4882a593Smuzhiyun #define FUTEX_LOCK_PI_PRIVATE (FUTEX_LOCK_PI | FUTEX_PRIVATE_FLAG) 35*4882a593Smuzhiyun #define FUTEX_UNLOCK_PI_PRIVATE (FUTEX_UNLOCK_PI | FUTEX_PRIVATE_FLAG) 36*4882a593Smuzhiyun #define FUTEX_TRYLOCK_PI_PRIVATE (FUTEX_TRYLOCK_PI | FUTEX_PRIVATE_FLAG) 37*4882a593Smuzhiyun #define FUTEX_WAIT_BITSET_PRIVATE (FUTEX_WAIT_BITSET | FUTEX_PRIVATE_FLAG) 38*4882a593Smuzhiyun #define FUTEX_WAKE_BITSET_PRIVATE (FUTEX_WAKE_BITSET | FUTEX_PRIVATE_FLAG) 39*4882a593Smuzhiyun #define FUTEX_WAIT_REQUEUE_PI_PRIVATE (FUTEX_WAIT_REQUEUE_PI | \ 40*4882a593Smuzhiyun FUTEX_PRIVATE_FLAG) 41*4882a593Smuzhiyun #define FUTEX_CMP_REQUEUE_PI_PRIVATE (FUTEX_CMP_REQUEUE_PI | \ 42*4882a593Smuzhiyun FUTEX_PRIVATE_FLAG) 43*4882a593Smuzhiyun 44*4882a593Smuzhiyun /* 45*4882a593Smuzhiyun * Support for robust futexes: the kernel cleans up held futexes at 46*4882a593Smuzhiyun * thread exit time. 47*4882a593Smuzhiyun */ 48*4882a593Smuzhiyun 49*4882a593Smuzhiyun /* 50*4882a593Smuzhiyun * Per-lock list entry - embedded in user-space locks, somewhere close 51*4882a593Smuzhiyun * to the futex field. (Note: user-space uses a double-linked list to 52*4882a593Smuzhiyun * achieve O(1) list add and remove, but the kernel only needs to know 53*4882a593Smuzhiyun * about the forward link) 54*4882a593Smuzhiyun * 55*4882a593Smuzhiyun * NOTE: this structure is part of the syscall ABI, and must not be 56*4882a593Smuzhiyun * changed. 57*4882a593Smuzhiyun */ 58*4882a593Smuzhiyun struct robust_list { 59*4882a593Smuzhiyun struct robust_list __user *next; 60*4882a593Smuzhiyun }; 61*4882a593Smuzhiyun 62*4882a593Smuzhiyun /* 63*4882a593Smuzhiyun * Per-thread list head: 64*4882a593Smuzhiyun * 65*4882a593Smuzhiyun * NOTE: this structure is part of the syscall ABI, and must only be 66*4882a593Smuzhiyun * changed if the change is first communicated with the glibc folks. 67*4882a593Smuzhiyun * (When an incompatible change is done, we'll increase the structure 68*4882a593Smuzhiyun * size, which glibc will detect) 69*4882a593Smuzhiyun */ 70*4882a593Smuzhiyun struct robust_list_head { 71*4882a593Smuzhiyun /* 72*4882a593Smuzhiyun * The head of the list. Points back to itself if empty: 73*4882a593Smuzhiyun */ 74*4882a593Smuzhiyun struct robust_list list; 75*4882a593Smuzhiyun 76*4882a593Smuzhiyun /* 77*4882a593Smuzhiyun * This relative offset is set by user-space, it gives the kernel 78*4882a593Smuzhiyun * the relative position of the futex field to examine. This way 79*4882a593Smuzhiyun * we keep userspace flexible, to freely shape its data-structure, 80*4882a593Smuzhiyun * without hardcoding any particular offset into the kernel: 81*4882a593Smuzhiyun */ 82*4882a593Smuzhiyun long futex_offset; 83*4882a593Smuzhiyun 84*4882a593Smuzhiyun /* 85*4882a593Smuzhiyun * The death of the thread may race with userspace setting 86*4882a593Smuzhiyun * up a lock's links. So to handle this race, userspace first 87*4882a593Smuzhiyun * sets this field to the address of the to-be-taken lock, 88*4882a593Smuzhiyun * then does the lock acquire, and then adds itself to the 89*4882a593Smuzhiyun * list, and then clears this field. Hence the kernel will 90*4882a593Smuzhiyun * always have full knowledge of all locks that the thread 91*4882a593Smuzhiyun * _might_ have taken. We check the owner TID in any case, 92*4882a593Smuzhiyun * so only truly owned locks will be handled. 93*4882a593Smuzhiyun */ 94*4882a593Smuzhiyun struct robust_list __user *list_op_pending; 95*4882a593Smuzhiyun }; 96*4882a593Smuzhiyun 97*4882a593Smuzhiyun /* 98*4882a593Smuzhiyun * Are there any waiters for this robust futex: 99*4882a593Smuzhiyun */ 100*4882a593Smuzhiyun #define FUTEX_WAITERS 0x80000000 101*4882a593Smuzhiyun 102*4882a593Smuzhiyun /* 103*4882a593Smuzhiyun * The kernel signals via this bit that a thread holding a futex 104*4882a593Smuzhiyun * has exited without unlocking the futex. The kernel also does 105*4882a593Smuzhiyun * a FUTEX_WAKE on such futexes, after setting the bit, to wake 106*4882a593Smuzhiyun * up any possible waiters: 107*4882a593Smuzhiyun */ 108*4882a593Smuzhiyun #define FUTEX_OWNER_DIED 0x40000000 109*4882a593Smuzhiyun 110*4882a593Smuzhiyun /* 111*4882a593Smuzhiyun * The rest of the robust-futex field is for the TID: 112*4882a593Smuzhiyun */ 113*4882a593Smuzhiyun #define FUTEX_TID_MASK 0x3fffffff 114*4882a593Smuzhiyun 115*4882a593Smuzhiyun /* 116*4882a593Smuzhiyun * This limit protects against a deliberately circular list. 117*4882a593Smuzhiyun * (Not worth introducing an rlimit for it) 118*4882a593Smuzhiyun */ 119*4882a593Smuzhiyun #define ROBUST_LIST_LIMIT 2048 120*4882a593Smuzhiyun 121*4882a593Smuzhiyun /* 122*4882a593Smuzhiyun * bitset with all bits set for the FUTEX_xxx_BITSET OPs to request a 123*4882a593Smuzhiyun * match of any bit. 124*4882a593Smuzhiyun */ 125*4882a593Smuzhiyun #define FUTEX_BITSET_MATCH_ANY 0xffffffff 126*4882a593Smuzhiyun 127*4882a593Smuzhiyun 128*4882a593Smuzhiyun #define FUTEX_OP_SET 0 /* *(int *)UADDR2 = OPARG; */ 129*4882a593Smuzhiyun #define FUTEX_OP_ADD 1 /* *(int *)UADDR2 += OPARG; */ 130*4882a593Smuzhiyun #define FUTEX_OP_OR 2 /* *(int *)UADDR2 |= OPARG; */ 131*4882a593Smuzhiyun #define FUTEX_OP_ANDN 3 /* *(int *)UADDR2 &= ~OPARG; */ 132*4882a593Smuzhiyun #define FUTEX_OP_XOR 4 /* *(int *)UADDR2 ^= OPARG; */ 133*4882a593Smuzhiyun 134*4882a593Smuzhiyun #define FUTEX_OP_OPARG_SHIFT 8 /* Use (1 << OPARG) instead of OPARG. */ 135*4882a593Smuzhiyun 136*4882a593Smuzhiyun #define FUTEX_OP_CMP_EQ 0 /* if (oldval == CMPARG) wake */ 137*4882a593Smuzhiyun #define FUTEX_OP_CMP_NE 1 /* if (oldval != CMPARG) wake */ 138*4882a593Smuzhiyun #define FUTEX_OP_CMP_LT 2 /* if (oldval < CMPARG) wake */ 139*4882a593Smuzhiyun #define FUTEX_OP_CMP_LE 3 /* if (oldval <= CMPARG) wake */ 140*4882a593Smuzhiyun #define FUTEX_OP_CMP_GT 4 /* if (oldval > CMPARG) wake */ 141*4882a593Smuzhiyun #define FUTEX_OP_CMP_GE 5 /* if (oldval >= CMPARG) wake */ 142*4882a593Smuzhiyun 143*4882a593Smuzhiyun /* FUTEX_WAKE_OP will perform atomically 144*4882a593Smuzhiyun int oldval = *(int *)UADDR2; 145*4882a593Smuzhiyun *(int *)UADDR2 = oldval OP OPARG; 146*4882a593Smuzhiyun if (oldval CMP CMPARG) 147*4882a593Smuzhiyun wake UADDR2; */ 148*4882a593Smuzhiyun 149*4882a593Smuzhiyun #define FUTEX_OP(op, oparg, cmp, cmparg) \ 150*4882a593Smuzhiyun (((op & 0xf) << 28) | ((cmp & 0xf) << 24) \ 151*4882a593Smuzhiyun | ((oparg & 0xfff) << 12) | (cmparg & 0xfff)) 152*4882a593Smuzhiyun 153*4882a593Smuzhiyun #endif /* _UAPI_LINUX_FUTEX_H */ 154