root/kernel/locking/rtmutex_common.h

/* [<][>][^][v][top][bottom][index][help] */

INCLUDED FROM


DEFINITIONS

This source file includes following definitions.
  1. rt_mutex_has_waiters
  2. rt_mutex_top_waiter
  3. task_has_pi_waiters
  4. task_top_pi_waiter
  5. rt_mutex_has_waiters
  6. rt_mutex_top_waiter
  7. task_has_pi_waiters
  8. task_top_pi_waiter
  9. rt_mutex_owner

   1 /* SPDX-License-Identifier: GPL-2.0 */
   2 /*
   3  * RT Mutexes: blocking mutual exclusion locks with PI support
   4  *
   5  * started by Ingo Molnar and Thomas Gleixner:
   6  *
   7  *  Copyright (C) 2004-2006 Red Hat, Inc., Ingo Molnar <mingo@redhat.com>
   8  *  Copyright (C) 2006, Timesys Corp., Thomas Gleixner <tglx@timesys.com>
   9  *
  10  * This file contains the private data structure and API definitions.
  11  */
  12 
  13 #ifndef __KERNEL_RTMUTEX_COMMON_H
  14 #define __KERNEL_RTMUTEX_COMMON_H
  15 
  16 #include <linux/rtmutex.h>
  17 #include <linux/sched/wake_q.h>
  18 
  19 /*
  20  * This is the control structure for tasks blocked on a rt_mutex,
  21  * which is allocated on the kernel stack on of the blocked task.
  22  *
  23  * @tree_entry:         pi node to enqueue into the mutex waiters tree
  24  * @pi_tree_entry:      pi node to enqueue into the mutex owner waiters tree
  25  * @task:               task reference to the blocked task
  26  */
  27 struct rt_mutex_waiter {
  28         struct rb_node          tree_entry;
  29         struct rb_node          pi_tree_entry;
  30         struct task_struct      *task;
  31         struct rt_mutex         *lock;
  32 #ifdef CONFIG_DEBUG_RT_MUTEXES
  33         unsigned long           ip;
  34         struct pid              *deadlock_task_pid;
  35         struct rt_mutex         *deadlock_lock;
  36 #endif
  37         int prio;
  38         u64 deadline;
  39 };
  40 
  41 /*
  42  * Various helpers to access the waiters-tree:
  43  */
  44 
  45 #ifdef CONFIG_RT_MUTEXES
  46 
  47 static inline int rt_mutex_has_waiters(struct rt_mutex *lock)
  48 {
  49         return !RB_EMPTY_ROOT(&lock->waiters.rb_root);
  50 }
  51 
  52 static inline struct rt_mutex_waiter *
  53 rt_mutex_top_waiter(struct rt_mutex *lock)
  54 {
  55         struct rb_node *leftmost = rb_first_cached(&lock->waiters);
  56         struct rt_mutex_waiter *w = NULL;
  57 
  58         if (leftmost) {
  59                 w = rb_entry(leftmost, struct rt_mutex_waiter, tree_entry);
  60                 BUG_ON(w->lock != lock);
  61         }
  62         return w;
  63 }
  64 
  65 static inline int task_has_pi_waiters(struct task_struct *p)
  66 {
  67         return !RB_EMPTY_ROOT(&p->pi_waiters.rb_root);
  68 }
  69 
  70 static inline struct rt_mutex_waiter *
  71 task_top_pi_waiter(struct task_struct *p)
  72 {
  73         return rb_entry(p->pi_waiters.rb_leftmost,
  74                         struct rt_mutex_waiter, pi_tree_entry);
  75 }
  76 
  77 #else
  78 
  79 static inline int rt_mutex_has_waiters(struct rt_mutex *lock)
  80 {
  81         return false;
  82 }
  83 
  84 static inline struct rt_mutex_waiter *
  85 rt_mutex_top_waiter(struct rt_mutex *lock)
  86 {
  87         return NULL;
  88 }
  89 
  90 static inline int task_has_pi_waiters(struct task_struct *p)
  91 {
  92         return false;
  93 }
  94 
  95 static inline struct rt_mutex_waiter *
  96 task_top_pi_waiter(struct task_struct *p)
  97 {
  98         return NULL;
  99 }
 100 
 101 #endif
 102 
 103 /*
 104  * lock->owner state tracking:
 105  */
 106 #define RT_MUTEX_HAS_WAITERS    1UL
 107 
 108 static inline struct task_struct *rt_mutex_owner(struct rt_mutex *lock)
 109 {
 110         unsigned long owner = (unsigned long) READ_ONCE(lock->owner);
 111 
 112         return (struct task_struct *) (owner & ~RT_MUTEX_HAS_WAITERS);
 113 }
 114 
 115 /*
 116  * Constants for rt mutex functions which have a selectable deadlock
 117  * detection.
 118  *
 119  * RT_MUTEX_MIN_CHAINWALK:      Stops the lock chain walk when there are
 120  *                              no further PI adjustments to be made.
 121  *
 122  * RT_MUTEX_FULL_CHAINWALK:     Invoke deadlock detection with a full
 123  *                              walk of the lock chain.
 124  */
 125 enum rtmutex_chainwalk {
 126         RT_MUTEX_MIN_CHAINWALK,
 127         RT_MUTEX_FULL_CHAINWALK,
 128 };
 129 
 130 /*
 131  * PI-futex support (proxy locking functions, etc.):
 132  */
 133 extern struct task_struct *rt_mutex_next_owner(struct rt_mutex *lock);
 134 extern void rt_mutex_init_proxy_locked(struct rt_mutex *lock,
 135                                        struct task_struct *proxy_owner);
 136 extern void rt_mutex_proxy_unlock(struct rt_mutex *lock,
 137                                   struct task_struct *proxy_owner);
 138 extern void rt_mutex_init_waiter(struct rt_mutex_waiter *waiter);
 139 extern int __rt_mutex_start_proxy_lock(struct rt_mutex *lock,
 140                                      struct rt_mutex_waiter *waiter,
 141                                      struct task_struct *task);
 142 extern int rt_mutex_start_proxy_lock(struct rt_mutex *lock,
 143                                      struct rt_mutex_waiter *waiter,
 144                                      struct task_struct *task);
 145 extern int rt_mutex_wait_proxy_lock(struct rt_mutex *lock,
 146                                struct hrtimer_sleeper *to,
 147                                struct rt_mutex_waiter *waiter);
 148 extern bool rt_mutex_cleanup_proxy_lock(struct rt_mutex *lock,
 149                                  struct rt_mutex_waiter *waiter);
 150 
 151 extern int rt_mutex_futex_trylock(struct rt_mutex *l);
 152 extern int __rt_mutex_futex_trylock(struct rt_mutex *l);
 153 
 154 extern void rt_mutex_futex_unlock(struct rt_mutex *lock);
 155 extern bool __rt_mutex_futex_unlock(struct rt_mutex *lock,
 156                                  struct wake_q_head *wqh);
 157 
 158 extern void rt_mutex_postunlock(struct wake_q_head *wake_q);
 159 
 160 #ifdef CONFIG_DEBUG_RT_MUTEXES
 161 # include "rtmutex-debug.h"
 162 #else
 163 # include "rtmutex.h"
 164 #endif
 165 
 166 #endif

/* [<][>][^][v][top][bottom][index][help] */