Files
apfstests/common/defrag
T
Ross Zwisler 1637c06780 ext4: defrag not supported with DAX
As of this kernel commit:

commit 73f34a5e2ced ("ext4: online defrag not supported with DAX")

online defrag operations for ext4 are disallowed when the filesystem is
mounted with the DAX option.

This causes several xfstests to fail because they expect the defrag
operation to change the file layout:

ext4/308	 [failed, exit status 1] - output mismatch (see /root/xfstests/results//ext4/308.out.bad)
    --- tests/ext4/308.out	2015-10-02 10:19:36.791795792 -0600
    +++ /root/xfstests/results//ext4/308.out.bad	2016-02-17 16:20:52.330454602 -0700
    @@ -23,659 +23,5 @@
     50f924a5dc9b03609a4577f9f961414b  SCRATCH_MNT/test.10
     Perform compacting
     50f924a5dc9b03609a4577f9f961414b  SCRATCH_MNT/test.10
    -Perform compacting, second pass
    -50f924a5dc9b03609a4577f9f961414b  SCRATCH_MNT/test.10
    -Create file with 20 * 2 fragments
    -wrote 1234/1234 bytes at offset 0
    ...
    (Run 'diff -u tests/ext4/308.out /root/xfstests/results//ext4/308.out.bad'  to see the entire diff)
generic/018 1s ... [failed, exit status 1] - output mismatch (see /root/xfstests/results//generic/018.out.bad)
    --- tests/generic/018.out	2016-02-17 16:02:40.103656140 -0700
    +++ /root/xfstests/results//generic/018.out.bad	2016-02-17 16:20:53.117459173 -0700
    @@ -10,10 +10,6 @@
     After: 1
     Write backwards sync, but contiguous - should defrag to 1 extent
     Before: in_range(5, 10)
    -After: 1
    -Write backwards sync leaving holes - defrag should do nothing
    -Before: 16
    -After: 16
    ...
    (Run 'diff -u tests/generic/018.out /root/xfstests/results//generic/018.out.bad'  to see the entire diff)

Avoid this by skipping over defrag tests if we are using ext4 + DAX.

Signed-off-by: Ross Zwisler <ross.zwisler@linux.intel.com>
Reviewed-by: Dave Chinner <dchinner@redhat.com>
Signed-off-by: Dave Chinner <david@fromorbit.com>
2016-03-23 14:33:40 +11:00

175 lines
4.1 KiB
Plaintext

##/bin/bash
#
# Copyright (c) 2009 Eric Sandeen
# All Rights Reserved.
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License as
# published by the Free Software Foundation.
#
# This program is distributed in the hope that it would be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write the Free Software Foundation,
# Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#
#
# Functions useful for defragmentation tests
#
_require_defrag()
{
case "$FSTYP" in
xfs)
DEFRAG_PROG="$XFS_FSR_PROG"
;;
ext4|ext4dev)
echo $MOUNT_OPTIONS | grep -q dax
if [ $? -eq 0 ]; then
_notrun "$FSTYP defragmentation not supported with DAX"
else
DEFRAG_PROG="$E4DEFRAG_PROG"
fi
dumpe2fs -h $SCRATCH_DEV 2> /dev/null | grep -wq extent || \
_notrun "file system does not have extents, needed for defrag"
;;
btrfs)
DEFRAG_PROG="$BTRFS_UTIL_PROG filesystem defragment"
;;
*)
_notrun "defragmentation not supported for fstype \"$FSTYP\""
;;
esac
_require_command "$DEFRAG_PROG" defragment
_require_xfs_io_command "fiemap"
}
_extent_count()
{
$XFS_IO_PROG -c "fiemap" $1 >> $seqres.full 2>&1
$XFS_IO_PROG -c "fiemap" $1 | tail -n +2 | grep -v hole | wc -l| $AWK_PROG '{print $1}'
}
_check_extent_count()
{
min=$1
max=$2
ext_cnt=$3
# Return failure if $3 isn't between $1 and $2; let caller decide
# action if it's not, we just return status here.
if [ "$min" -gt "$ext_cnt" ]; then
echo "Found $ext_cnt extents min:$max"
return 1;
fi
if [ "$max" -ne -1 ] && [ "$ext_cnt" -gt "$max" ]; then
echo "Found $ext_cnt max: $max"
return 1;
fi
if [ $max -ne $min ]; then
echo "in_range($min, $max)"
else
echo "$ext_cnt"
fi
# success
return 0
}
# Defrag file, check it, and remove it.
_defrag()
{
min_before=0
max_before=-1
min_after=0
max_after=-1
csum=1
mtime=1
while [ $# -gt 1 ]
do
case $1
in
--min_before)
[ -z "$2" ] && _fail "missing argument for --min_before"
min_before=$2
shift
;;
--max_before)
[ -z "$2" ] && _fail "missing argument for --max_before"
max_before=$2
shift
;;
--min_after)
[ -z "$2" ] && _fail "missing argument for --min_after"
min_after=$2
shift
;;
--max_after)
[ -z "$2" ] && _fail "missing argument for --max_after"
max_after=$2
shift
;;
--before)
[ -z "$2" ] && _fail "missing argument for --before"
min_before=$2
max_before=$2
shift
;;
--after)
[ -z "$2" ] && _fail "missing argument for --after"
min_after=$2
max_after=$2
shift
;;
--no_csum)
csum=
;;
--no_mtime)
mtime=
;;
--no_unlink)
no_unlink=1
;;
*)
_fail "invalid argument to common/dump function: $1"
;;
esac
shift
done
echo -n "Before: "
ext_before=$(_extent_count $1)
_check_extent_count $min_before $max_before $ext_before
[ $? -eq 0 ] || _notrun "Could not adequately fragment file"
[ ! -z $csum ] && CSUM_BEFORE=`md5sum $1`
STAT_BEFORE=`stat -c "a: %x m: %y c: %z" $1`
$DEFRAG_PROG -v $1 >> $seqres.full 2>&1
_scratch_cycle_mount
STAT_AFTER=`stat -c "a: %x m: %y c: %z" $1`
[ ! -z $csum ] && CSUM_AFTER=`md5sum $1`
echo -n "After: "
ext_after=$(_extent_count $1)
_check_extent_count $min_after $max_after $ext_after
[ $? -eq 0 ] || _fail "Failed to adequately defragment file"
[ "$ext_before" -lt "$ext_after" ] && \
_fail "Number of extents increased after defragmentation," \
" before:$ext_before, after:$ext_after"
if [ ! -z $csum ] && [ "$CSUM_BEFORE" != "$CSUM_AFTER" ]; then
_fail "file checksum changed post-defrag ($CSUM_BEFORE/$CSUM_AFTER)"
fi
if [ ! -z $mtime ] && [ "$STAT_BEFORE" != "$STAT_AFTER" ]; then
_fail "file timestamps changed post-defrag:\n$STAT_BEFORE\n$STAT_AFTER"
fi
[ -z $no_unlink ] && rm -f $1
}