summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2024-07-01 12:48:28 -0700
committerLinus Torvalds <torvalds@linux-foundation.org>2024-07-01 12:48:28 -0700
commitcfbc0ffea88c764d23f69efe6ecb74918e0f588e (patch)
tree8e5bf6b50da3d7b60c57b61fc451a5f1c9e21200
parent9903efbddba0d14133b5a3c75088b558d2e34ac3 (diff)
parent48f091fd50b2eb33ae5eaea9ed3c4f81603acf38 (diff)
downloadlinux-stable-cfbc0ffea88c764d23f69efe6ecb74918e0f588e.tar.gz
linux-stable-cfbc0ffea88c764d23f69efe6ecb74918e0f588e.tar.bz2
linux-stable-cfbc0ffea88c764d23f69efe6ecb74918e0f588e.zip
Merge tag 'for-6.10-rc6-tag' of git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux
Pull btrfs fix from David Sterba: "A fixup for a recent fix that prevents an infinite loop during block group reclaim. Unfortunately it introduced an unsafe way of updating block group list and could race with relocation. This could be hit on fast devices when relocation/balance does not have enough space" * tag 'for-6.10-rc6-tag' of git://git.kernel.org/pub/scm/linux/kernel/git/kdave/linux: btrfs: fix adding block group to a reclaim list and the unused list during reclaim
-rw-r--r--fs/btrfs/block-group.c13
1 files changed, 11 insertions, 2 deletions
diff --git a/fs/btrfs/block-group.c b/fs/btrfs/block-group.c
index 1a66be33bb04..60066822b532 100644
--- a/fs/btrfs/block-group.c
+++ b/fs/btrfs/block-group.c
@@ -1924,8 +1924,17 @@ void btrfs_reclaim_bgs_work(struct work_struct *work)
next:
if (ret) {
/* Refcount held by the reclaim_bgs list after splice. */
- btrfs_get_block_group(bg);
- list_add_tail(&bg->bg_list, &retry_list);
+ spin_lock(&fs_info->unused_bgs_lock);
+ /*
+ * This block group might be added to the unused list
+ * during the above process. Move it back to the
+ * reclaim list otherwise.
+ */
+ if (list_empty(&bg->bg_list)) {
+ btrfs_get_block_group(bg);
+ list_add_tail(&bg->bg_list, &retry_list);
+ }
+ spin_unlock(&fs_info->unused_bgs_lock);
}
btrfs_put_block_group(bg);