blob: 82bb4a9e9009270c1cf2008e5dbddc60a1f9e950 [file] [log] [blame]
Waiman Longa33fda32015-04-24 14:56:30 -04001/*
2 * Queued spinlock
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; either version 2 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * (C) Copyright 2013-2015 Hewlett-Packard Development Company, L.P.
15 * (C) Copyright 2013-2014 Red Hat, Inc.
16 * (C) Copyright 2015 Intel Corp.
17 *
18 * Authors: Waiman Long <waiman.long@hp.com>
19 * Peter Zijlstra <peterz@infradead.org>
20 */
21#include <linux/smp.h>
22#include <linux/bug.h>
23#include <linux/cpumask.h>
24#include <linux/percpu.h>
25#include <linux/hardirq.h>
26#include <linux/mutex.h>
27#include <asm/qspinlock.h>
28
29/*
30 * The basic principle of a queue-based spinlock can best be understood
31 * by studying a classic queue-based spinlock implementation called the
32 * MCS lock. The paper below provides a good description for this kind
33 * of lock.
34 *
35 * http://www.cise.ufl.edu/tr/DOC/REP-1992-71.pdf
36 *
37 * This queued spinlock implementation is based on the MCS lock, however to make
38 * it fit the 4 bytes we assume spinlock_t to be, and preserve its existing
39 * API, we must modify it somehow.
40 *
41 * In particular; where the traditional MCS lock consists of a tail pointer
42 * (8 bytes) and needs the next pointer (another 8 bytes) of its own node to
43 * unlock the next pending (next->locked), we compress both these: {tail,
44 * next->locked} into a single u32 value.
45 *
46 * Since a spinlock disables recursion of its own context and there is a limit
47 * to the contexts that can nest; namely: task, softirq, hardirq, nmi. As there
48 * are at most 4 nesting levels, it can be encoded by a 2-bit number. Now
49 * we can encode the tail by combining the 2-bit nesting level with the cpu
50 * number. With one byte for the lock value and 3 bytes for the tail, only a
51 * 32-bit word is now needed. Even though we only need 1 bit for the lock,
52 * we extend it to a full byte to achieve better performance for architectures
53 * that support atomic byte write.
54 *
55 * We also change the first spinner to spin on the lock bit instead of its
56 * node; whereby avoiding the need to carry a node from lock to unlock, and
57 * preserving existing lock API. This also makes the unlock code simpler and
58 * faster.
59 */
60
61#include "mcs_spinlock.h"
62
63/*
64 * Per-CPU queue node structures; we can never have more than 4 nested
65 * contexts: task, softirq, hardirq, nmi.
66 *
67 * Exactly fits one 64-byte cacheline on a 64-bit architecture.
68 */
69static DEFINE_PER_CPU_ALIGNED(struct mcs_spinlock, mcs_nodes[4]);
70
71/*
72 * We must be able to distinguish between no-tail and the tail at 0:0,
73 * therefore increment the cpu number by one.
74 */
75
76static inline u32 encode_tail(int cpu, int idx)
77{
78 u32 tail;
79
80#ifdef CONFIG_DEBUG_SPINLOCK
81 BUG_ON(idx > 3);
82#endif
83 tail = (cpu + 1) << _Q_TAIL_CPU_OFFSET;
84 tail |= idx << _Q_TAIL_IDX_OFFSET; /* assume < 4 */
85
86 return tail;
87}
88
89static inline struct mcs_spinlock *decode_tail(u32 tail)
90{
91 int cpu = (tail >> _Q_TAIL_CPU_OFFSET) - 1;
92 int idx = (tail & _Q_TAIL_IDX_MASK) >> _Q_TAIL_IDX_OFFSET;
93
94 return per_cpu_ptr(&mcs_nodes[idx], cpu);
95}
96
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -040097#define _Q_LOCKED_PENDING_MASK (_Q_LOCKED_MASK | _Q_PENDING_MASK)
98
Waiman Longa33fda32015-04-24 14:56:30 -040099/**
Waiman Long6403bd72015-04-24 14:56:33 -0400100 * clear_pending_set_locked - take ownership and clear the pending bit.
101 * @lock: Pointer to queued spinlock structure
102 *
103 * *,1,0 -> *,0,1
104 */
105static __always_inline void clear_pending_set_locked(struct qspinlock *lock)
106{
107 atomic_add(-_Q_PENDING_VAL + _Q_LOCKED_VAL, &lock->val);
108}
109
110/**
111 * xchg_tail - Put in the new queue tail code word & retrieve previous one
112 * @lock : Pointer to queued spinlock structure
113 * @tail : The new queue tail code word
114 * Return: The previous queue tail code word
115 *
116 * xchg(lock, tail)
117 *
118 * p,*,* -> n,*,* ; prev = xchg(lock, node)
119 */
120static __always_inline u32 xchg_tail(struct qspinlock *lock, u32 tail)
121{
122 u32 old, new, val = atomic_read(&lock->val);
123
124 for (;;) {
125 new = (val & _Q_LOCKED_PENDING_MASK) | tail;
126 old = atomic_cmpxchg(&lock->val, val, new);
127 if (old == val)
128 break;
129
130 val = old;
131 }
132 return old;
133}
134
135/**
Waiman Longa33fda32015-04-24 14:56:30 -0400136 * queued_spin_lock_slowpath - acquire the queued spinlock
137 * @lock: Pointer to queued spinlock structure
138 * @val: Current value of the queued spinlock 32-bit word
139 *
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400140 * (queue tail, pending bit, lock value)
Waiman Longa33fda32015-04-24 14:56:30 -0400141 *
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400142 * fast : slow : unlock
143 * : :
144 * uncontended (0,0,0) -:--> (0,0,1) ------------------------------:--> (*,*,0)
145 * : | ^--------.------. / :
146 * : v \ \ | :
147 * pending : (0,1,1) +--> (0,1,0) \ | :
148 * : | ^--' | | :
149 * : v | | :
150 * uncontended : (n,x,y) +--> (n,0,0) --' | :
151 * queue : | ^--' | :
152 * : v | :
153 * contended : (*,x,y) +--> (*,0,0) ---> (*,0,1) -' :
154 * queue : ^--' :
Waiman Longa33fda32015-04-24 14:56:30 -0400155 */
156void queued_spin_lock_slowpath(struct qspinlock *lock, u32 val)
157{
158 struct mcs_spinlock *prev, *next, *node;
159 u32 new, old, tail;
160 int idx;
161
162 BUILD_BUG_ON(CONFIG_NR_CPUS >= (1U << _Q_TAIL_CPU_BITS));
163
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400164 /*
165 * wait for in-progress pending->locked hand-overs
166 *
167 * 0,1,0 -> 0,0,1
168 */
169 if (val == _Q_PENDING_VAL) {
170 while ((val = atomic_read(&lock->val)) == _Q_PENDING_VAL)
171 cpu_relax();
172 }
173
174 /*
175 * trylock || pending
176 *
177 * 0,0,0 -> 0,0,1 ; trylock
178 * 0,0,1 -> 0,1,1 ; pending
179 */
180 for (;;) {
181 /*
182 * If we observe any contention; queue.
183 */
184 if (val & ~_Q_LOCKED_MASK)
185 goto queue;
186
187 new = _Q_LOCKED_VAL;
188 if (val == new)
189 new |= _Q_PENDING_VAL;
190
191 old = atomic_cmpxchg(&lock->val, val, new);
192 if (old == val)
193 break;
194
195 val = old;
196 }
197
198 /*
199 * we won the trylock
200 */
201 if (new == _Q_LOCKED_VAL)
202 return;
203
204 /*
205 * we're pending, wait for the owner to go away.
206 *
207 * *,1,1 -> *,1,0
208 */
209 while ((val = atomic_read(&lock->val)) & _Q_LOCKED_MASK)
210 cpu_relax();
211
212 /*
213 * take ownership and clear the pending bit.
214 *
215 * *,1,0 -> *,0,1
216 */
Waiman Long6403bd72015-04-24 14:56:33 -0400217 clear_pending_set_locked(lock);
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400218 return;
219
220 /*
221 * End of pending bit optimistic spinning and beginning of MCS
222 * queuing.
223 */
224queue:
Waiman Longa33fda32015-04-24 14:56:30 -0400225 node = this_cpu_ptr(&mcs_nodes[0]);
226 idx = node->count++;
227 tail = encode_tail(smp_processor_id(), idx);
228
229 node += idx;
230 node->locked = 0;
231 node->next = NULL;
232
233 /*
Waiman Long6403bd72015-04-24 14:56:33 -0400234 * We touched a (possibly) cold cacheline in the per-cpu queue node;
235 * attempt the trylock once more in the hope someone let go while we
236 * weren't watching.
237 */
238 if (queued_spin_trylock(lock))
239 goto release;
240
241 /*
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400242 * We have already touched the queueing cacheline; don't bother with
243 * pending stuff.
244 *
Waiman Long6403bd72015-04-24 14:56:33 -0400245 * p,*,* -> n,*,*
Waiman Longa33fda32015-04-24 14:56:30 -0400246 */
Waiman Long6403bd72015-04-24 14:56:33 -0400247 old = xchg_tail(lock, tail);
Waiman Longa33fda32015-04-24 14:56:30 -0400248
249 /*
250 * if there was a previous node; link it and wait until reaching the
251 * head of the waitqueue.
252 */
Waiman Long6403bd72015-04-24 14:56:33 -0400253 if (old & _Q_TAIL_MASK) {
Waiman Longa33fda32015-04-24 14:56:30 -0400254 prev = decode_tail(old);
255 WRITE_ONCE(prev->next, node);
256
257 arch_mcs_spin_lock_contended(&node->locked);
258 }
259
260 /*
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400261 * we're at the head of the waitqueue, wait for the owner & pending to
262 * go away.
Waiman Longa33fda32015-04-24 14:56:30 -0400263 *
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400264 * *,x,y -> *,0,0
Waiman Longa33fda32015-04-24 14:56:30 -0400265 */
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400266 while ((val = atomic_read(&lock->val)) & _Q_LOCKED_PENDING_MASK)
Waiman Longa33fda32015-04-24 14:56:30 -0400267 cpu_relax();
268
269 /*
270 * claim the lock:
271 *
Peter Zijlstra (Intel)c1fb1592015-04-24 14:56:32 -0400272 * n,0,0 -> 0,0,1 : lock, uncontended
273 * *,0,0 -> *,0,1 : lock, contended
Waiman Longa33fda32015-04-24 14:56:30 -0400274 */
275 for (;;) {
276 new = _Q_LOCKED_VAL;
277 if (val != tail)
278 new |= val;
279
280 old = atomic_cmpxchg(&lock->val, val, new);
281 if (old == val)
282 break;
283
284 val = old;
285 }
286
287 /*
288 * contended path; wait for next, release.
289 */
290 if (new != _Q_LOCKED_VAL) {
291 while (!(next = READ_ONCE(node->next)))
292 cpu_relax();
293
294 arch_mcs_spin_unlock_contended(&next->locked);
295 }
296
297release:
298 /*
299 * release the node
300 */
301 this_cpu_dec(mcs_nodes[0].count);
302}
303EXPORT_SYMBOL(queued_spin_lock_slowpath);