btrfs: make sure btrfs can handle full fs trim correctly
authorQu Wenruo <wqu@suse.com>
Wed, 29 Nov 2017 06:14:19 +0000 (14:14 +0800)
committerEryu Guan <eguan@redhat.com>
Fri, 1 Dec 2017 08:51:00 +0000 (16:51 +0800)
commit88231c0c0b9d36384c859e9076ed4dd51b41cbae
tree9cb95816c21235c6c670d85e857b581d806a100c
parent959081e0d3ca963eb1e663e02b1a665b32ce531e
btrfs: make sure btrfs can handle full fs trim correctly

Ancient commit f4c697e6406d ("btrfs: return EINVAL if start >
total_bytes in fitrim ioctl") introduced a regression where btrfs
may fail to trim any free space in existing block groups.

It's caused by confusion with btrfs_super_block->total_bytes and
btrfs logical address space.

Unlike physical address, any aligned bytenr in range [0, U64_MAX) is
valid in btrfs logical address space, and it's chunk mapping
mechanism of btrfs to handle the logical<->physical mapping.

The test case will craft a btrfs with the following features:
0) Single data/meta profile
   Make trimmed bytes reporting and chunk allocation more predictable.

1) All chunks start beyond super_block->total_bytes (1G)
   By relocating these blocks several times.

2) Unallocated space is less than 50% of the whole fs

3) Fragmented data chunks
   Data chunks will be full of fragments, 50% of data chunks will be
   free space.

So in theory fstrim should be able to trim over 50% space of the fs.
(after fix, 64% of the fs can be trimmed)

While the regression makes btrfs only able to trim unallocated
space, which is less than 50% of the total space.
(without fix, it's only 31%)

Fixed by patch named "btrfs: Ensure btrfs_trim_fs can trim the whole
fs".

Signed-off-by: Qu Wenruo <wqu@suse.com>
Reviewed-by: Eryu Guan <eguan@redhat.com>
Signed-off-by: Eryu Guan <eguan@redhat.com>
tests/btrfs/156 [new file with mode: 0755]
tests/btrfs/156.out [new file with mode: 0644]
tests/btrfs/group