summaryrefslogtreecommitdiffstats
path: root/fs
diff options
context:
space:
mode:
authorZhao Lei <zhaolei@cn.fujitsu.com>2015-09-29 09:03:54 -0400
committerChris Mason <clm@fb.com>2015-11-10 22:27:16 -0500
commitaefbe9a633b50a6124dbeb33a5d4efcdc6de6c30 (patch)
treec78cefbebcadc5283680c2bc859077b5e014f418 /fs
parent3b5753ec23597b05fd41d3f19ef582d6af1a6477 (diff)
btrfs: Fix lost-data-profile caused by auto removing bg
Reproduce: (In integration-4.3 branch) TEST_DEV=(/dev/vdg /dev/vdh) TEST_DIR=/mnt/tmp umount "$TEST_DEV" >/dev/null mkfs.btrfs -f -d raid1 "${TEST_DEV[@]}" mount -o nospace_cache "$TEST_DEV" "$TEST_DIR" umount "$TEST_DEV" mount -o nospace_cache "$TEST_DEV" "$TEST_DIR" btrfs filesystem usage $TEST_DIR We can see the data chunk changed from raid1 to single: # btrfs filesystem usage $TEST_DIR Data,single: Size:8.00MiB, Used:0.00B /dev/vdg 8.00MiB # Reason: When a empty filesystem mount with -o nospace_cache, the last data blockgroup will be auto-removed in umount. Then if we mount it again, there is no data chunk in the filesystem, so the only available data profile is 0x0, result is all new chunks are created as single type. Fix: Don't auto-delete last blockgroup for a raid type. Test: Test by above script, and confirmed the logic by debug output. Reviewed-by: Filipe Manana <fdmanana@suse.com> Signed-off-by: Zhao Lei <zhaolei@cn.fujitsu.com> Signed-off-by: Chris Mason <clm@fb.com>
Diffstat (limited to 'fs')
-rw-r--r--fs/btrfs/extent-tree.c7
1 files changed, 5 insertions, 2 deletions
diff --git a/fs/btrfs/extent-tree.c b/fs/btrfs/extent-tree.c
index 99a8e57da8a1..b77ffbc3a145 100644
--- a/fs/btrfs/extent-tree.c
+++ b/fs/btrfs/extent-tree.c
@@ -10279,8 +10279,10 @@ void btrfs_delete_unused_bgs(struct btrfs_fs_info *fs_info)
10279 block_group = list_first_entry(&fs_info->unused_bgs, 10279 block_group = list_first_entry(&fs_info->unused_bgs,
10280 struct btrfs_block_group_cache, 10280 struct btrfs_block_group_cache,
10281 bg_list); 10281 bg_list);
10282 space_info = block_group->space_info;
10283 list_del_init(&block_group->bg_list); 10282 list_del_init(&block_group->bg_list);
10283
10284 space_info = block_group->space_info;
10285
10284 if (ret || btrfs_mixed_space_info(space_info)) { 10286 if (ret || btrfs_mixed_space_info(space_info)) {
10285 btrfs_put_block_group(block_group); 10287 btrfs_put_block_group(block_group);
10286 continue; 10288 continue;
@@ -10294,7 +10296,8 @@ void btrfs_delete_unused_bgs(struct btrfs_fs_info *fs_info)
10294 spin_lock(&block_group->lock); 10296 spin_lock(&block_group->lock);
10295 if (block_group->reserved || 10297 if (block_group->reserved ||
10296 btrfs_block_group_used(&block_group->item) || 10298 btrfs_block_group_used(&block_group->item) ||
10297 block_group->ro) { 10299 block_group->ro ||
10300 list_is_singular(&block_group->list)) {
10298 /* 10301 /*
10299 * We want to bail if we made new allocations or have 10302 * We want to bail if we made new allocations or have
10300 * outstanding allocations in this block group. We do 10303 * outstanding allocations in this block group. We do