--- /dev/null
+From 1dae7e0e58b484eaa43d530f211098fdeeb0f404 Mon Sep 17 00:00:00 2001
+From: Qu Wenruo <wqu@suse.com>
+Date: Wed, 20 May 2020 14:58:51 +0800
+Subject: btrfs: reloc: clear DEAD_RELOC_TREE bit for orphan roots to prevent runaway balance
+
+From: Qu Wenruo <wqu@suse.com>
+
+commit 1dae7e0e58b484eaa43d530f211098fdeeb0f404 upstream.
+
+[BUG]
+There are several reported runaway balance, that balance is flooding the
+log with "found X extents" where the X never changes.
+
+[CAUSE]
+Commit d2311e698578 ("btrfs: relocation: Delay reloc tree deletion after
+merge_reloc_roots") introduced BTRFS_ROOT_DEAD_RELOC_TREE bit to
+indicate that one subvolume has finished its tree blocks swap with its
+reloc tree.
+
+However if balance is canceled or hits ENOSPC halfway, we didn't clear
+the BTRFS_ROOT_DEAD_RELOC_TREE bit, leaving that bit hanging forever
+until unmount.
+
+Any subvolume root with that bit, would cause backref cache to skip this
+tree block, as it has finished its tree block swap. This would cause
+all tree blocks of that root be ignored by balance, leading to runaway
+balance.
+
+[FIX]
+Fix the problem by also clearing the BTRFS_ROOT_DEAD_RELOC_TREE bit for
+the original subvolume of orphan reloc root.
+
+Add an umount check for the stale bit still set.
+
+Fixes: d2311e698578 ("btrfs: relocation: Delay reloc tree deletion after merge_reloc_roots")
+Signed-off-by: Qu Wenruo <wqu@suse.com>
+Signed-off-by: David Sterba <dsterba@suse.com>
+Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
+
+
+---
+ fs/btrfs/disk-io.c | 1 +
+ fs/btrfs/relocation.c | 2 ++
+ 2 files changed, 3 insertions(+)
+
+--- a/fs/btrfs/disk-io.c
++++ b/fs/btrfs/disk-io.c
+@@ -1998,6 +1998,7 @@ void btrfs_put_root(struct btrfs_root *r
+
+ if (refcount_dec_and_test(&root->refs)) {
+ WARN_ON(!RB_EMPTY_ROOT(&root->inode_tree));
++ WARN_ON(test_bit(BTRFS_ROOT_DEAD_RELOC_TREE, &root->state));
+ if (root->anon_dev)
+ free_anon_bdev(root->anon_dev);
+ btrfs_drew_lock_destroy(&root->snapshot_lock);
+--- a/fs/btrfs/relocation.c
++++ b/fs/btrfs/relocation.c
+@@ -2642,6 +2642,8 @@ again:
+ root->reloc_root = NULL;
+ btrfs_put_root(reloc_root);
+ }
++ clear_bit(BTRFS_ROOT_DEAD_RELOC_TREE,
++ &root->state);
+ btrfs_put_root(root);
+ }
+