diff options
author | Josef Bacik <josef@toxicpanda.com> | 2020-01-24 09:32:27 -0500 |
---|---|---|
committer | David Sterba <dsterba@suse.com> | 2020-02-10 14:40:29 +0100 |
commit | 6cd796e8a077d5e9942d26a2c13af2aef31bd18a (patch) | |
tree | e8a9baa76f4392ebecafe91e3a29a75bf4946e0a | |
parent | 903287ce55ed5d5b5d1c62827a3ba0fa3afa705a (diff) | |
download | btrfs-next-6cd796e8a077d5e9942d26a2c13af2aef31bd18a.tar.gz |
btrfs: hold a ref on fs roots while they're in the radix tree
If the root is sitting in the radix tree, we should probably have a ref
for the radix tree. Grab a ref on the root when we insert it, and drop
it when it gets deleted.
Reviewed-by: Nikolay Borisov <nborisov@suse.com>
Signed-off-by: Josef Bacik <josef@toxicpanda.com>
Reviewed-by: David Sterba <dsterba@suse.com>
Signed-off-by: David Sterba <dsterba@suse.com>
-rw-r--r-- | fs/btrfs/disk-io.c | 6 |
1 files changed, 5 insertions, 1 deletions
diff --git a/fs/btrfs/disk-io.c b/fs/btrfs/disk-io.c index 28622de9e642c4..4d8fbac5a35092 100644 --- a/fs/btrfs/disk-io.c +++ b/fs/btrfs/disk-io.c @@ -1513,8 +1513,10 @@ int btrfs_insert_fs_root(struct btrfs_fs_info *fs_info, ret = radix_tree_insert(&fs_info->fs_roots_radix, (unsigned long)root->root_key.objectid, root); - if (ret == 0) + if (ret == 0) { + btrfs_grab_fs_root(root); set_bit(BTRFS_ROOT_IN_RADIX, &root->state); + } spin_unlock(&fs_info->fs_roots_radix_lock); radix_tree_preload_end(); @@ -3815,6 +3817,8 @@ void btrfs_drop_and_free_fs_root(struct btrfs_fs_info *fs_info, spin_lock(&fs_info->fs_roots_radix_lock); radix_tree_delete(&fs_info->fs_roots_radix, (unsigned long)root->root_key.objectid); + if (test_and_clear_bit(BTRFS_ROOT_IN_RADIX, &root->state)) + btrfs_put_fs_root(root); spin_unlock(&fs_info->fs_roots_radix_lock); if (btrfs_root_refs(&root->root_item) == 0) |