aboutsummaryrefslogtreecommitdiffstats
path: root/include/linux/rcupdate.h
diff options
context:
space:
mode:
Diffstat (limited to 'include/linux/rcupdate.h')
-rw-r--r--include/linux/rcupdate.h49
1 files changed, 40 insertions, 9 deletions
diff --git a/include/linux/rcupdate.h b/include/linux/rcupdate.h
index c84373626336..3024050c82a1 100644
--- a/include/linux/rcupdate.h
+++ b/include/linux/rcupdate.h
@@ -41,6 +41,10 @@
41#include <linux/lockdep.h> 41#include <linux/lockdep.h>
42#include <linux/completion.h> 42#include <linux/completion.h>
43 43
44#ifdef CONFIG_RCU_TORTURE_TEST
45extern int rcutorture_runnable; /* for sysctl */
46#endif /* #ifdef CONFIG_RCU_TORTURE_TEST */
47
44/** 48/**
45 * struct rcu_head - callback structure for use with RCU 49 * struct rcu_head - callback structure for use with RCU
46 * @next: next update requests in a list 50 * @next: next update requests in a list
@@ -97,6 +101,11 @@ extern struct lockdep_map rcu_sched_lock_map;
97# define rcu_read_release_sched() \ 101# define rcu_read_release_sched() \
98 lock_release(&rcu_sched_lock_map, 1, _THIS_IP_) 102 lock_release(&rcu_sched_lock_map, 1, _THIS_IP_)
99 103
104static inline int debug_lockdep_rcu_enabled(void)
105{
106 return likely(rcu_scheduler_active && debug_locks);
107}
108
100/** 109/**
101 * rcu_read_lock_held - might we be in RCU read-side critical section? 110 * rcu_read_lock_held - might we be in RCU read-side critical section?
102 * 111 *
@@ -104,12 +113,14 @@ extern struct lockdep_map rcu_sched_lock_map;
104 * an RCU read-side critical section. In absence of CONFIG_PROVE_LOCKING, 113 * an RCU read-side critical section. In absence of CONFIG_PROVE_LOCKING,
105 * this assumes we are in an RCU read-side critical section unless it can 114 * this assumes we are in an RCU read-side critical section unless it can
106 * prove otherwise. 115 * prove otherwise.
116 *
117 * Check rcu_scheduler_active to prevent false positives during boot.
107 */ 118 */
108static inline int rcu_read_lock_held(void) 119static inline int rcu_read_lock_held(void)
109{ 120{
110 if (debug_locks) 121 if (!debug_lockdep_rcu_enabled())
111 return lock_is_held(&rcu_lock_map); 122 return 1;
112 return 1; 123 return lock_is_held(&rcu_lock_map);
113} 124}
114 125
115/** 126/**
@@ -119,12 +130,14 @@ static inline int rcu_read_lock_held(void)
119 * an RCU-bh read-side critical section. In absence of CONFIG_PROVE_LOCKING, 130 * an RCU-bh read-side critical section. In absence of CONFIG_PROVE_LOCKING,
120 * this assumes we are in an RCU-bh read-side critical section unless it can 131 * this assumes we are in an RCU-bh read-side critical section unless it can
121 * prove otherwise. 132 * prove otherwise.
133 *
134 * Check rcu_scheduler_active to prevent false positives during boot.
122 */ 135 */
123static inline int rcu_read_lock_bh_held(void) 136static inline int rcu_read_lock_bh_held(void)
124{ 137{
125 if (debug_locks) 138 if (!debug_lockdep_rcu_enabled())
126 return lock_is_held(&rcu_bh_lock_map); 139 return 1;
127 return 1; 140 return lock_is_held(&rcu_bh_lock_map);
128} 141}
129 142
130/** 143/**
@@ -135,15 +148,26 @@ static inline int rcu_read_lock_bh_held(void)
135 * this assumes we are in an RCU-sched read-side critical section unless it 148 * this assumes we are in an RCU-sched read-side critical section unless it
136 * can prove otherwise. Note that disabling of preemption (including 149 * can prove otherwise. Note that disabling of preemption (including
137 * disabling irqs) counts as an RCU-sched read-side critical section. 150 * disabling irqs) counts as an RCU-sched read-side critical section.
151 *
152 * Check rcu_scheduler_active to prevent false positives during boot.
138 */ 153 */
154#ifdef CONFIG_PREEMPT
139static inline int rcu_read_lock_sched_held(void) 155static inline int rcu_read_lock_sched_held(void)
140{ 156{
141 int lockdep_opinion = 0; 157 int lockdep_opinion = 0;
142 158
159 if (!debug_lockdep_rcu_enabled())
160 return 1;
143 if (debug_locks) 161 if (debug_locks)
144 lockdep_opinion = lock_is_held(&rcu_sched_lock_map); 162 lockdep_opinion = lock_is_held(&rcu_sched_lock_map);
145 return lockdep_opinion || preempt_count() != 0 || !rcu_scheduler_active; 163 return lockdep_opinion || preempt_count() != 0;
164}
165#else /* #ifdef CONFIG_PREEMPT */
166static inline int rcu_read_lock_sched_held(void)
167{
168 return 1;
146} 169}
170#endif /* #else #ifdef CONFIG_PREEMPT */
147 171
148#else /* #ifdef CONFIG_DEBUG_LOCK_ALLOC */ 172#else /* #ifdef CONFIG_DEBUG_LOCK_ALLOC */
149 173
@@ -164,10 +188,17 @@ static inline int rcu_read_lock_bh_held(void)
164 return 1; 188 return 1;
165} 189}
166 190
191#ifdef CONFIG_PREEMPT
167static inline int rcu_read_lock_sched_held(void) 192static inline int rcu_read_lock_sched_held(void)
168{ 193{
169 return preempt_count() != 0 || !rcu_scheduler_active; 194 return !rcu_scheduler_active || preempt_count() != 0;
195}
196#else /* #ifdef CONFIG_PREEMPT */
197static inline int rcu_read_lock_sched_held(void)
198{
199 return 1;
170} 200}
201#endif /* #else #ifdef CONFIG_PREEMPT */
171 202
172#endif /* #else #ifdef CONFIG_DEBUG_LOCK_ALLOC */ 203#endif /* #else #ifdef CONFIG_DEBUG_LOCK_ALLOC */
173 204
@@ -184,7 +215,7 @@ static inline int rcu_read_lock_sched_held(void)
184 */ 215 */
185#define rcu_dereference_check(p, c) \ 216#define rcu_dereference_check(p, c) \
186 ({ \ 217 ({ \
187 if (debug_locks && !(c)) \ 218 if (debug_lockdep_rcu_enabled() && !(c)) \
188 lockdep_rcu_dereference(__FILE__, __LINE__); \ 219 lockdep_rcu_dereference(__FILE__, __LINE__); \
189 rcu_dereference_raw(p); \ 220 rcu_dereference_raw(p); \
190 }) 221 })