diff options
author | Kent Overstreet <kent.overstreet@linux.dev> | 2023-05-25 14:35:06 -0400 |
---|---|---|
committer | Kent Overstreet <kent.overstreet@linux.dev> | 2023-08-14 12:28:33 -0400 |
commit | 75563db56729f09af1167feae21f99bd3d237635 (patch) | |
tree | 388bee020bdcd385ea57e0b47b07a56bfccb7a7d | |
parent | ec54bc7684c970d1d35d75e5932f8a76db4e0583 (diff) |
six locks: Use atomic_try_cmpxchg_acquire()
This switches to a newer cmpxchg variant which updates @old for us on
failure, simplifying the cmpxchg loops a bit and supposedly generating
better code.
Signed-off-by: Kent Overstreet <kent.overstreet@linux.dev>
-rw-r--r-- | fs/bcachefs/six.c | 17 |
1 files changed, 6 insertions, 11 deletions
diff --git a/fs/bcachefs/six.c b/fs/bcachefs/six.c index e7a802629fb3..23d62874faf0 100644 --- a/fs/bcachefs/six.c +++ b/fs/bcachefs/six.c @@ -116,7 +116,7 @@ static int __do_six_trylock(struct six_lock *lock, enum six_lock_type type, struct task_struct *task, bool try) { int ret; - u32 old, new, v; + u32 old; EBUG_ON(type == SIX_LOCK_write && lock->owner != task); EBUG_ON(type == SIX_LOCK_write && @@ -177,19 +177,14 @@ static int __do_six_trylock(struct six_lock *lock, enum six_lock_type type, ret = -1 - SIX_LOCK_read; } } else { - v = atomic_read(&lock->state); + old = atomic_read(&lock->state); do { - new = old = v; - ret = !(old & l[type].lock_fail); - if (!ret || (type == SIX_LOCK_write && !try)) { smp_mb(); break; } - - new += l[type].lock_val; - } while ((v = atomic_cmpxchg_acquire(&lock->state, old, new)) != old); + } while (!atomic_try_cmpxchg_acquire(&lock->state, &old, old + l[type].lock_val)); EBUG_ON(ret && !(atomic_read(&lock->state) & l[type].held_mask)); } @@ -675,10 +670,10 @@ EXPORT_SYMBOL_GPL(six_lock_downgrade); */ bool six_lock_tryupgrade(struct six_lock *lock) { - u32 old, new, v = atomic_read(&lock->state); + u32 old = atomic_read(&lock->state), new; do { - new = old = v; + new = old; if (new & SIX_LOCK_HELD_intent) return false; @@ -689,7 +684,7 @@ bool six_lock_tryupgrade(struct six_lock *lock) } new |= SIX_LOCK_HELD_intent; - } while ((v = atomic_cmpxchg_acquire(&lock->state, old, new)) != old); + } while (!atomic_try_cmpxchg_acquire(&lock->state, &old, new)); if (lock->readers) this_cpu_dec(*lock->readers); |