Branch data Line data Source code
1 : : /* SPDX-License-Identifier: GPL-2.0 */ 2 : : #ifndef _LINUX_FUTEX_H 3 : : #define _LINUX_FUTEX_H 4 : : 5 : : #include <linux/sched.h> 6 : : #include <linux/ktime.h> 7 : : 8 : : #include <uapi/linux/futex.h> 9 : : 10 : : struct inode; 11 : : struct mm_struct; 12 : : struct task_struct; 13 : : 14 : : /* 15 : : * Futexes are matched on equal values of this key. 16 : : * The key type depends on whether it's a shared or private mapping. 17 : : * Don't rearrange members without looking at hash_futex(). 18 : : * 19 : : * offset is aligned to a multiple of sizeof(u32) (== 4) by definition. 20 : : * We use the two low order bits of offset to tell what is the kind of key : 21 : : * 00 : Private process futex (PTHREAD_PROCESS_PRIVATE) 22 : : * (no reference on an inode or mm) 23 : : * 01 : Shared futex (PTHREAD_PROCESS_SHARED) 24 : : * mapped on a file (reference on the underlying inode) 25 : : * 10 : Shared futex (PTHREAD_PROCESS_SHARED) 26 : : * (but private mapping on an mm, and reference taken on it) 27 : : */ 28 : : 29 : : #define FUT_OFF_INODE 1 /* We set bit 0 if key has a reference on inode */ 30 : : #define FUT_OFF_MMSHARED 2 /* We set bit 1 if key has a reference on mm */ 31 : : 32 : : union futex_key { 33 : : struct { 34 : : u64 i_seq; 35 : : unsigned long pgoff; 36 : : unsigned int offset; 37 : : } shared; 38 : : struct { 39 : : union { 40 : : struct mm_struct *mm; 41 : : u64 __tmp; 42 : : }; 43 : : unsigned long address; 44 : : unsigned int offset; 45 : : } private; 46 : : struct { 47 : : u64 ptr; 48 : : unsigned long word; 49 : : unsigned int offset; 50 : : } both; 51 : : }; 52 : : 53 : : #define FUTEX_KEY_INIT (union futex_key) { .both = { .ptr = 0ULL } } 54 : : 55 : : #ifdef CONFIG_FUTEX 56 : : enum { 57 : : FUTEX_STATE_OK, 58 : : FUTEX_STATE_EXITING, 59 : : FUTEX_STATE_DEAD, 60 : : }; 61 : : 62 : : static inline void futex_init_task(struct task_struct *tsk) 63 : : { 64 : 3 : tsk->robust_list = NULL; 65 : : #ifdef CONFIG_COMPAT 66 : : tsk->compat_robust_list = NULL; 67 : : #endif 68 : 3 : INIT_LIST_HEAD(&tsk->pi_state_list); 69 : 3 : tsk->pi_state_cache = NULL; 70 : 3 : tsk->futex_state = FUTEX_STATE_OK; 71 : 3 : mutex_init(&tsk->futex_exit_mutex); 72 : : } 73 : : 74 : : void futex_exit_recursive(struct task_struct *tsk); 75 : : void futex_exit_release(struct task_struct *tsk); 76 : : void futex_exec_release(struct task_struct *tsk); 77 : : 78 : : long do_futex(u32 __user *uaddr, int op, u32 val, ktime_t *timeout, 79 : : u32 __user *uaddr2, u32 val2, u32 val3); 80 : : #else 81 : : static inline void futex_init_task(struct task_struct *tsk) { } 82 : : static inline void futex_exit_recursive(struct task_struct *tsk) { } 83 : : static inline void futex_exit_release(struct task_struct *tsk) { } 84 : : static inline void futex_exec_release(struct task_struct *tsk) { } 85 : : static inline long do_futex(u32 __user *uaddr, int op, u32 val, 86 : : ktime_t *timeout, u32 __user *uaddr2, 87 : : u32 val2, u32 val3) 88 : : { 89 : : return -EINVAL; 90 : : } 91 : : #endif 92 : : 93 : : #endif