Message ID | ed6897d89e53696370450d72a366f96ad954edbd.1710760179.git.fdmanana@suse.com (mailing list archive) |
---|---|
State | New, archived |
Headers | show |
Series | btrfs: avoid pointless wake ups of drew lock readers | expand |
On Mon, Mar 18, 2024 at 11:11:56AM +0000, fdmanana@kernel.org wrote: > From: Filipe Manana <fdmanana@suse.com> > > When unlocking a write lock on a drew lock, at btrfs_drew_write_unlock(), > it's pointless to wake up tasks waiting to acquire a read lock if we > didn't decrement the 'writers' counter down to 0, since a read lock can > only be acquired when the counter reaches a value of 0. Doing so is > harmless from a functional point of view, but it's not efficient due to > unnecessarily waking up tasks just for them to sleep again on the > waitqueue. > > So change this to wake up readers only if we decremented the 'writers' > counter to 0. > > Signed-off-by: Filipe Manana <fdmanana@suse.com> Reviewed-by: David Sterba <dsterba@suse.com>
diff --git a/fs/btrfs/locking.c b/fs/btrfs/locking.c index 508a3fdfcd58..72992e74c479 100644 --- a/fs/btrfs/locking.c +++ b/fs/btrfs/locking.c @@ -364,8 +364,12 @@ void btrfs_drew_write_lock(struct btrfs_drew_lock *lock) void btrfs_drew_write_unlock(struct btrfs_drew_lock *lock) { - atomic_dec(&lock->writers); - cond_wake_up(&lock->pending_readers); + /* + * atomic_dec_and_test() implies a full barrier, so woken up readers are + * guaranteed to see the decrement. + */ + if (atomic_dec_and_test(&lock->writers)) + wake_up(&lock->pending_readers); } void btrfs_drew_read_lock(struct btrfs_drew_lock *lock)