--- x/fs/btrfs/super.c +++ y/fs/btrfs/super.c @@ -1486,13 +1486,14 @@ static struct dentry *btrfs_mount_root(s goto error_fs_info; } fs_info->fs_devices = device->fs_devices; + fs_info->fs_devices->user++; mutex_unlock(&uuid_mutex); s = sget(fs_type, btrfs_test_super, btrfs_set_super, flags | SB_NOSEC, fs_info); if (IS_ERR(s)) { error = PTR_ERR(s); - goto error_fs_info; + goto error_close_devices; } if (s->s_root) { @@ -1531,6 +1532,11 @@ out_deactivate: error_sec_opts: security_free_mnt_opts(&new_sec_opts); return ERR_PTR(error); +error_close_devices: + mutex_lock(&uuid_mutex); + fs_info->fs_devices->user--; + mutex_unlock(&uuid_mutex); + btrfs_close_devices(fs_info->fs_devices); error_fs_info: btrfs_free_fs_info(fs_info); goto error_sec_opts; --- x/fs/btrfs/volumes.c +++ y/fs/btrfs/volumes.c @@ -406,6 +406,8 @@ static void free_fs_devices(struct btrfs struct btrfs_device *device; WARN_ON(fs_devices->opened); + if (fs_devices->user) + return; while (!list_empty(&fs_devices->devices)) { device = list_entry(fs_devices->devices.next, struct btrfs_device, dev_list); @@ -1285,6 +1287,8 @@ int btrfs_open_devices(struct btrfs_fs_d list_sort(NULL, &fs_devices->devices, devid_cmp); ret = open_fs_devices(fs_devices, flags, holder); } + if (fs_devices->user) + fs_devices->user--; mutex_unlock(&uuid_mutex); return ret; --- x/fs/btrfs/volumes.h +++ y/fs/btrfs/volumes.h @@ -348,6 +348,7 @@ struct btrfs_fs_devices { /* Count fs-devices opened. */ int opened; + int user; /* Set when we find or add a device that doesn't have the nonrot flag set. */ bool rotating;