Skip to content

Commit 11dc132

Browse files
wildea01Ingo Molnar
authored andcommitted
locking/qspinlock: Ensure node->count is updated before initialising node
When queuing on the qspinlock, the count field for the current CPU's head node is incremented. This needn't be atomic because locking in e.g. IRQ context is balanced and so an IRQ will return with node->count as it found it. However, the compiler could in theory reorder the initialisation of node[idx] before the increment of the head node->count, causing an IRQ to overwrite the initialised node and potentially corrupt the lock state. Avoid the potential for this harmful compiler reordering by placing a barrier() between the increment of the head node->count and the subsequent node initialisation. Signed-off-by: Will Deacon <[email protected]> Acked-by: Peter Zijlstra (Intel) <[email protected]> Cc: Linus Torvalds <[email protected]> Cc: Thomas Gleixner <[email protected]> Link: http://lkml.kernel.org/r/[email protected] Signed-off-by: Ingo Molnar <[email protected]>
1 parent 95bcade commit 11dc132

File tree

1 file changed

+8
-0
lines changed

1 file changed

+8
-0
lines changed

kernel/locking/qspinlock.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -379,6 +379,14 @@ void queued_spin_lock_slowpath(struct qspinlock *lock, u32 val)
379379
tail = encode_tail(smp_processor_id(), idx);
380380

381381
node += idx;
382+
383+
/*
384+
* Ensure that we increment the head node->count before initialising
385+
* the actual node. If the compiler is kind enough to reorder these
386+
* stores, then an IRQ could overwrite our assignments.
387+
*/
388+
barrier();
389+
382390
node->locked = 0;
383391
node->next = NULL;
384392
pv_init_node(node);

0 commit comments

Comments
 (0)