4 # Check if btrfs can correctly trim free space in block groups
6 # An ancient regression prevent btrfs from trimming free space inside
7 # existing block groups, if bytenr of block group starts beyond
8 # btrfs_super_block->total_bytes.
9 # However all bytenr in btrfs is in btrfs logical address space,
10 # where any bytenr in range [0, U64_MAX] is valid.
12 # Fixed by patch named "btrfs: Ensure btrfs_trim_fs can trim the whole fs".
14 #-----------------------------------------------------------------------
15 # Copyright (c) 2017 SUSE Linux Products GmbH. All Rights Reserved.
17 # This program is free software; you can redistribute it and/or
18 # modify it under the terms of the GNU General Public License as
19 # published by the Free Software Foundation.
21 # This program is distributed in the hope that it would be useful,
22 # but WITHOUT ANY WARRANTY; without even the implied warranty of
23 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 # GNU General Public License for more details.
26 # You should have received a copy of the GNU General Public License
27 # along with this program; if not, write the Free Software Foundation,
28 # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
29 #-----------------------------------------------------------------------
33 seqres=$RESULT_DIR/$seq
34 echo "QA output created by $seq"
38 status=1 # failure is the default!
39 trap "_cleanup; exit \$status" 0 1 2 3 15
47 # get standard environment, filters and checks
51 # remove previous $seqres.full before test
54 # real QA test starts here
56 # Modify as appropriate.
63 fs_size=$((1024 * 1024 * 1024))
65 # Use small files to fill half of the fs
66 file_size=$(( 1024 * 1024 ))
67 nr_files=$(( $fs_size / $file_size / 2))
69 # Force to use single data and meta profile.
70 # Since the test relies on fstrim output, which will differ for different
72 _scratch_mkfs -b $fs_size -m single -d single > /dev/null
75 _require_batched_discard "$SCRATCH_MNT"
77 for n in $(seq -w 0 $(( $nr_files - 1))); do
78 $XFS_IO_PROG -f -c "pwrite 0 $file_size" "$SCRATCH_MNT/file_$n" \
82 # Flush all buffer data into disk, to trigger chunk allocation
85 # Now we have take at least 50% of the filesystem, relocate all chunks twice
86 # so all chunks will start after 1G in logical space.
87 # (Btrfs chunk allocation will not rewind to reuse lower space)
88 _run_btrfs_util_prog balance start --full-balance "$SCRATCH_MNT"
90 # To avoid possible false ENOSPC alert on v4.15-rc1, seems to be a
91 # reserved space related bug (maybe related to outstanding space rework?),
92 # but that's another story.
95 _run_btrfs_util_prog balance start --full-balance "$SCRATCH_MNT"
97 # Now remove half of the files to make some holes for later trim.
98 # While still keep the chunk space fragmented, so no chunk will be freed
99 rm $SCRATCH_MNT/file_*[13579] -f
101 # Make sure space is freed
104 trimmed=$($FSTRIM_PROG -v "$SCRATCH_MNT" | _filter_fstrim)
105 echo "Trimmed=$trimmed total_size=$fs_size ratio=$(($trimmed * 100 / $fs_size))%" \
108 # For correct full fs trim, both unallocated space (less than 50%)
109 # and free space in existing block groups (about 25%) should be trimmed.
110 # If less than 50% is trimmed, then only unallocated space is trimmed.
111 # BTW, without fix only 31% can be trimmed, while after fix it's 64%.
112 if [ $trimmed -lt $(( $fs_size / 2)) ]; then
113 echo "Free space in block groups not trimmed"
114 echo "Trimmed=$trimmed total_size=$fs_size ratio=$(($trimmed * 100 / $fs_size))%"
117 echo "Silence is golden"