diff --git a/include/linux/osq_lock.h b/include/linux/osq_lock.h index 5581dbd3bd3407c6009b565fb935e0797585ab3b..deb90ad5f560d9d48897f94496047cf1cdc2b88e 100644 --- a/include/linux/osq_lock.h +++ b/include/linux/osq_lock.h @@ -9,7 +9,7 @@ struct optimistic_spin_node { struct optimistic_spin_node *next, *prev; int locked; /* 1 if lock acquired */ - int cpu; /* encoded CPU # + 1 value */ + int cpu ____cacheline_aligned; /* encoded CPU # + 1 value */ }; struct optimistic_spin_queue { diff --git a/kernel/locking/osq_lock.c b/kernel/locking/osq_lock.c index d5610ad52b92b55b98b6a35f8700c5df940e8f81..17618d62343f47a58c294f99d3fc146a4f58ddd7 100644 --- a/kernel/locking/osq_lock.c +++ b/kernel/locking/osq_lock.c @@ -96,7 +96,13 @@ bool osq_lock(struct optimistic_spin_queue *lock) node->locked = 0; node->next = NULL; - node->cpu = curr; + /* + * After this cpu member is initialized for the first time, it + * would no longer change in fact. That could avoid cache misses + * when spin and access the cpu member by other CPUs. + */ + if (node->cpu != curr) + node->cpu = curr; /* * We need both ACQUIRE (pairs with corresponding RELEASE in