btrfs-progs: mkfs: avoid BUG_ON for chunk allocation when ENOSPC happens

When passing directory larger than block device using --rootdir
parameter, we get the following backtrace:

------
extent-tree.c:2693: btrfs_reserve_extent: BUG_ON `ret` triggered, value -28
./mkfs.btrfs(+0x1a05d)[0x557939e6b05d]
./mkfs.btrfs(btrfs_reserve_extent+0xb5a)[0x557939e710c8]
./mkfs.btrfs(+0xb0b6)[0x557939e5c0b6]
./mkfs.btrfs(main+0x15d5)[0x557939e5de04]
/usr/lib/libc.so.6(__libc_start_main+0xea)[0x7f83b101af6a]
./mkfs.btrfs(_start+0x2a)[0x557939e5af5a]
------

Nothing special, just BUG_ON() abusing from ancient code.

Fix them by using correct return.

Signed-off-by: Qu Wenruo <wqu@suse.com>
Reviewed-by: Nikolay Borisov <nborisov@suse.com>
Signed-off-by: David Sterba <dsterba@suse.com>
master
Qu Wenruo 2017-10-19 13:41:33 +08:00 committed by David Sterba
parent a624f16167
commit 66e485873c
2 changed files with 16 additions and 5 deletions

View File

@ -2690,7 +2690,8 @@ int btrfs_reserve_extent(struct btrfs_trans_handle *trans,
search_start, search_end, hint_byte, ins,
trans->alloc_exclude_start,
trans->alloc_exclude_nr, data);
BUG_ON(ret);
if (ret < 0)
return ret;
clear_extent_dirty(&info->free_space_cache,
ins->objectid, ins->objectid + ins->offset - 1);
return ret;

View File

@ -1046,11 +1046,13 @@ again:
info->chunk_root->root_key.objectid,
BTRFS_FIRST_CHUNK_TREE_OBJECTID, key.offset,
calc_size, &dev_offset, 0);
BUG_ON(ret);
if (ret < 0)
goto out_chunk_map;
device->bytes_used += calc_size;
ret = btrfs_update_device(trans, device);
BUG_ON(ret);
if (ret < 0)
goto out_chunk_map;
map->stripes[index].dev = device;
map->stripes[index].physical = dev_offset;
@ -1089,16 +1091,24 @@ again:
map->ce.size = *num_bytes;
ret = insert_cache_extent(&info->mapping_tree.cache_tree, &map->ce);
BUG_ON(ret);
if (ret < 0)
goto out_chunk_map;
if (type & BTRFS_BLOCK_GROUP_SYSTEM) {
ret = btrfs_add_system_chunk(info, &key,
chunk, btrfs_chunk_item_size(num_stripes));
BUG_ON(ret);
if (ret < 0)
goto out_chunk;
}
kfree(chunk);
return ret;
out_chunk_map:
kfree(map);
out_chunk:
kfree(chunk);
return ret;
}
/*