2014-02-28 16:11:12

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 1/8] xfstests: Create single function for testing xfs_io commands

Currently there are several function testing various xfs_io commands.
This commit creates _require_xfs_io_command() to test any xfs_command.

Signed-off-by: Lukas Czerner <[email protected]>
---
common/rc | 72 +++++++++++++++++++++++++++++++++------------------------------
1 file changed, 38 insertions(+), 34 deletions(-)

diff --git a/common/rc b/common/rc
index f2c3c3a..7f530d0 100644
--- a/common/rc
+++ b/common/rc
@@ -1296,12 +1296,43 @@ _user_do()
fi
}

+_require_xfs_io_command()
+{
+ if [ $# -ne 1 ]
+ then
+ echo "Usage: _require_xfs_io_command command" 1>&2
+ exit 1
+ fi
+ command=$1
+
+ testfile=$TEST_DIR/$$.xfs_io
+ case $command in
+ "falloc" )
+ testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
+ ;;
+ "fpunch" | "fcollapse" | "zero" )
+ testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
+ -c "$command 4k 8k" $testfile 2>&1`
+ ;;
+ "fiemap")
+ testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
+ -c "fiemap -v" $testfile 2>&1`
+ ;;
+ *)
+ testio=`$XFS_IO_PROG -c "$command help" 2>&1`
+ esac
+
+ rm -f $testfile 2>&1 > /dev/null
+ echo $testio | grep -q "not found" && \
+ _notrun "xfs_io $command support is missing"
+ echo $testio | grep -q "Operation not supported" && \
+ _notrun "xfs_io $command failed (old kernel/wrong fs?)"
+}
+
# check that xfs_io, kernel, and filesystem all support zero
_require_xfs_io_zero()
{
- testio=`$XFS_IO_PROG -c "zero help" 2>&1`
- echo $testio | grep -q 'command "zero" not found' && \
- _notrun "zero command not supported"
+ _require_xfs_io_command "zero"
}

# check that xfs_io, glibc, kernel, and filesystem all (!) support
@@ -1309,54 +1340,27 @@ _require_xfs_io_zero()
#
_require_xfs_io_falloc()
{
- testfile=$TEST_DIR/$$.falloc
- testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
- rm -f $testfile 2>&1 > /dev/null
- echo $testio | grep -q "not found" && \
- _notrun "xfs_io fallocate support is missing"
- echo $testio | grep -q "Operation not supported" && \
- _notrun "xfs_io fallocate command failed (old kernel/wrong fs?)"
+ _require_xfs_io_command "falloc"
}

# check that xfs_io, kernel and filesystem all support fallocate with hole
# punching
_require_xfs_io_falloc_punch()
{
- testfile=$TEST_DIR/$$.falloc
- testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
- -c "fpunch 4k 8k" $testfile 2>&1`
- rm -f $testfile 2>&1 > /dev/null
- echo $testio | grep -q "not found" && \
- _notrun "xfs_io fallocate punch support is missing"
- echo $testio | grep -q "Operation not supported" && \
- _notrun "xfs_io fallocate punch command failed (no fs support?)"
+ _require_xfs_io_command "fpunch"
}

# check that xfs_io, kernel and filesystem all support fallocate with collapse
# range
_require_xfs_io_falloc_collapse()
{
- testfile=$TEST_DIR/$$.falloc
- testio=`$XFS_IO_PROG -f -c "pwrite 0 20k" -c "fsync" \
- -c "fcollapse 4k 8k" $testfile 2>&1`
- rm -f $testfile 2>&1 > /dev/null
- echo $testio | grep -q "not found" && \
- _notrun "xfs_io fallocate collapse range support is missing"
- echo $testio | grep -q "Operation not supported" && \
- _notrun "xfs_io fallocate collapse range failed (no fs support?)"
+ _require_xfs_io_command "fcollapse"
}

# check that xfs_io, kernel and filesystem support fiemap
_require_xfs_io_fiemap()
{
- testfile=$TEST_DIR/$$.fiemap
- testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
- -c "fiemap -v" $testfile 2>&1`
- rm -f $testfile 2>&1 > /dev/null
- echo $testio | grep -q "not found" && \
- _notrun "xfs_io fiemap support is missing"
- echo $testio | grep -q "Operation not supported" && \
- _notrun "xfs_io fiemap command failed (no fs support?)"
+ _require_xfs_io_command "fiemap"
}

# Check that a fs has enough free space (in 1024b blocks)
--
1.8.3.1



2014-02-28 16:11:00

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 3/8] generic/008: Add test for fallocate zero range at block boundary

Add test for fallocate zero range at block boundary. This is similar to
the test xfs/290 however this one is generic and we're testing different
block sizes as well - namely 1k, 2k, 4k and 64k. Note that we're not
creating file systems with given block size buy rather test all 4
options.

Signed-off-by: Lukas Czerner <[email protected]>
---
common/rc | 2 +-
tests/generic/008 | 57 +++++++
tests/generic/008.out | 433 ++++++++++++++++++++++++++++++++++++++++++++++++++
tests/generic/group | 1 +
4 files changed, 492 insertions(+), 1 deletion(-)
create mode 100755 tests/generic/008
create mode 100644 tests/generic/008.out

diff --git a/common/rc b/common/rc
index 7f530d0..70b8ff5 100644
--- a/common/rc
+++ b/common/rc
@@ -1310,7 +1310,7 @@ _require_xfs_io_command()
"falloc" )
testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
;;
- "fpunch" | "fcollapse" | "zero" )
+ "fpunch" | "fcollapse" | "zero" | "fzero" )
testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
-c "$command 4k 8k" $testfile 2>&1`
;;
diff --git a/tests/generic/008 b/tests/generic/008
new file mode 100755
index 0000000..65e1661
--- /dev/null
+++ b/tests/generic/008
@@ -0,0 +1,57 @@
+#! /bin/bash
+# FS QA Test No. 008
+#
+# Makes calls to fallocate zero range and checks tossed ranges
+#
+# Primarily tests page boundries and boundries that are
+# off-by-one to ensure we're only tossing what's expected
+#
+#-----------------------------------------------------------------------
+# Copyright 2014 (C) Red Hat, Inc., Lukas Czerner <[email protected]>
+#
+# 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
+#-----------------------------------------------------------------------
+#
+
+seq=`basename $0`
+seqres=$RESULT_DIR/$seq
+echo "QA output created by $seq"
+
+here=`pwd`
+tmp=/tmp/$$
+status=1 # failure is the default!
+trap "exit \$status" 0 1 2 3 15
+
+# get standard environment, filters and checks
+. ./common/rc
+. ./common/filter
+. ./common/punch
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_os Linux
+
+_require_xfs_io_command "fzero"
+
+testfile=$TEST_DIR/008.$$
+
+_test_block_boundaries 1024 fzero _filter_xfs_io_unique $testfile
+_test_block_boundaries 2048 fzero _filter_xfs_io_unique $testfile
+_test_block_boundaries 4096 fzero _filter_xfs_io_unique $testfile
+_test_block_boundaries 65536 fzero _filter_xfs_io_unique $testfile
+
+# success, all done
+status=0
+exit
diff --git a/tests/generic/008.out b/tests/generic/008.out
new file mode 100644
index 0000000..0c3fb53
--- /dev/null
+++ b/tests/generic/008.out
@@ -0,0 +1,433 @@
+QA output created by 008
+zero 0, 1
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 .AAAAAAAAAAAAAAA
+00000010: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000400: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 1023
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+000003f0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 41 ...............A
+00000400: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 1024
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000400: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 1025
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000400: 00 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 .BBBBBBBBBBBBBBB
+00000410: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 1023, 1024
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+000003f0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00000400: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+000007f0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 42 ...............B
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 1023, 1025
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+000003f0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00000400: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 1023, 1026
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+000003f0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00000400: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 1024, 1024
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000400: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 512 , 1024
+wrote 1024/1024 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 1024/1024 bytes at offset 1024
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000200: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000600: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 1
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 .AAAAAAAAAAAAAAA
+00000010: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000800: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 2047
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+000007f0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 41 ...............A
+00000800: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 2048
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000800: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 2049
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000800: 00 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 .BBBBBBBBBBBBBBB
+00000810: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 2047, 2048
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+000007f0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00000800: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 42 ...............B
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 2047, 2049
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+000007f0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00000800: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 2047, 2050
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+000007f0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00000800: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 2048, 2048
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000800: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 1024 , 2048
+wrote 2048/2048 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 2048/2048 bytes at offset 2048
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000400: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000c00: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 1
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 .AAAAAAAAAAAAAAA
+00000010: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00001000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 4095
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00000ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 41 ...............A
+00001000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 4096
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00001000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 4097
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00001000: 00 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 .BBBBBBBBBBBBBBB
+00001010: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4095, 4096
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000ff0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00001000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00001ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 42 ...............B
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4095, 4097
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000ff0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00001000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4095, 4098
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000ff0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00001000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4096, 4096
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00001000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 2048 , 4096
+wrote 4096/4096 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 4096/4096 bytes at offset 4096
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00000800: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00001800: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 8192/8192 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 1
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 .AAAAAAAAAAAAAAA
+00000010: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00010000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 65535
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+0000fff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 41 ...............A
+00010000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 65536
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00010000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 65537
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00010000: 00 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 .BBBBBBBBBBBBBBB
+00010010: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 65535, 65536
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+0000fff0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00010000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+0001fff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 42 ...............B
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 65535, 65537
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+0000fff0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00010000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 65535, 65538
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+0000fff0: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 00 AAAAAAAAAAAAAAA.
+00010000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 65536, 65536
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00010000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 32768 , 65536
+wrote 65536/65536 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+wrote 65536/65536 bytes at offset 65536
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
+*
+00008000: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+*
+00018000: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+*
+read 131072/131072 bytes at offset 0
+XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
diff --git a/tests/generic/group b/tests/generic/group
index 34bd118..a99b6a1 100644
--- a/tests/generic/group
+++ b/tests/generic/group
@@ -9,6 +9,7 @@
005 dir udf auto quick
006 dir udf auto quick
007 dir udf auto quick
+008 auto quick prealloc
010 other udf auto
011 dir udf auto quick
013 other ioctl udf auto quick
--
1.8.3.1


2014-02-28 16:10:59

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 2/8] xfstests: create _test_block_boundaries in common/punch

Create new function _test_block_boundaries() which is testing content of
the blocks after the operation such as zero, or punch hole. The test is
doing the operation around block boundaries to assure correct behaviour
of the operation on block unaligned ranges.

This has been based on test xfs/290 which has been changed to use this
new function. A small change to the output file was required.

Signed-off-by: Lukas Czerner <[email protected]>
---
common/punch | 106 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/290 | 40 ++-------------------
tests/xfs/290.out | 13 +++++--
3 files changed, 119 insertions(+), 40 deletions(-)

diff --git a/common/punch b/common/punch
index 9340d3b..f2d538c 100644
--- a/common/punch
+++ b/common/punch
@@ -566,3 +566,109 @@ _test_generic_punch()
[ $? -ne 0 ] && die_now
od -x $testfile | head -n -1
}
+
+_test_block_boundaries()
+{
+
+ remove_testfile=1
+ sync_cmd="-c fsync"
+ unwritten_tests=1
+ OPTIND=1
+ while getopts 'dk' OPTION
+ do
+ case $OPTION in
+ k) remove_testfile=
+ ;;
+ d) sync_cmd=
+ ;;
+ ?) echo Invalid flag
+ exit 1
+ ;;
+ esac
+ done
+ shift $(($OPTIND - 1))
+
+ bs=$1
+ zero_cmd=$2
+ filter_cmd=$3
+ testfile=$4
+
+ # Block size plus 1
+ bs_p1=$(($bs + 1))
+ # Block size plus 2
+ bs_p2=$(($bs + 2))
+
+ # Block size minus 1
+ bs_m1=$(($bs - 1))
+
+ # Block size multiplied by 2
+ bs_t2=$(($bs * 2))
+
+ # Block size divided by 2
+ bs_d2=$(($bs / 2))
+
+ echo "zero 0, 1"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd 0 1" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+ echo "zero 0, $bs_m1"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd 0 $bs_m1" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+ echo "zero 0, $bs"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd 0 $bs" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+ echo "zero 0, $bs_p1"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd 0 $bs_p1" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+ echo "zero $bs_m1, $bs"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd $bs_m1 $bs" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+ echo "zero $bs_m1, $bs_p1"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd $bs_m1 $bs_p1" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+ echo "zero $bs_m1, $bs_p2"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd $bs_m1 $bs_p2" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+
+ echo "zero $bs, $bs"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd $bs $bs" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+
+
+ echo "zero $bs_d2 , $bs"
+ $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 $bs" \
+ -c "pwrite -S 0x42 $bs $bs" \
+ -c "$zero_cmd $bs_d2 $bs" \
+ -c "pread -v 0 $bs_t2" \
+ $testfile | $filter_cmd
+}
diff --git a/tests/xfs/290 b/tests/xfs/290
index 547a0ba..cbe7108 100755
--- a/tests/xfs/290
+++ b/tests/xfs/290
@@ -38,6 +38,7 @@ trap "exit \$status" 0 1 2 3 15
# get standard environment, filters and checks
. ./common/rc
. ./common/filter
+. ./common/punch

# real QA test starts here

@@ -49,44 +50,7 @@ _require_xfs_io_zero

testfile=$TEST_DIR/290.$$

-test_zero()
-{
- zero_start=$1
- zero_len=$2
-
- $XFS_IO_PROG -f -t -c "pwrite -S 0x41 0 4096" \
- -c "pwrite -S 0x42 4096 4096" \
- -c "zero $zero_start $zero_len" \
- -c "pread -v 0 8192" \
- $testfile | _filter_xfs_io_unique
-}
-
-# [0,1] -- Shouldn't toss anything
-test_zero 0 1
-
-#[0,4095] -- Shouldn't toss anything
-test_zero 0 4095
-
-#[0,4096] -- Should toss first page
-test_zero 0 4096
-
-#[0,4097] -- Should toss first page
-test_zero 0 4097
-
-#[4095,8191] -- Should toss last byte of first page
-test_zero 4095 4096
-
-#[4095,8192] -- Should toss second page & last byte of first page
-test_zero 4095 4097
-
-#[4095,8193] -- Should toss second page & last byte of first page
-test_zero 4095 4098
-
-#[4096,8192] -- Should toss second page
-test_zero 4096 4096
-
-#[1024,5120] -- Should toss from 1024 to end of first page
-test_zero 1024 4096
+_test_block_boundaries 4096 zero _filter_xfs_io_unique $testfile

# success, all done
status=0
diff --git a/tests/xfs/290.out b/tests/xfs/290.out
index 229c2b3..2487a93 100644
--- a/tests/xfs/290.out
+++ b/tests/xfs/290.out
@@ -1,4 +1,5 @@
QA output created by 290
+zero 0, 1
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -10,6 +11,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 4095
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -21,6 +23,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 4096
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -31,6 +34,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 0, 4097
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -42,6 +46,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4095, 4096
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -54,6 +59,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
00001ff0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 42 ...............B
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4095, 4097
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -65,6 +71,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4095, 4098
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -76,6 +83,7 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 4096, 4096
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
@@ -86,15 +94,16 @@ XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
+zero 2048 , 4096
wrote 4096/4096 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
wrote 4096/4096 bytes at offset 4096
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
00000000: 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 41 AAAAAAAAAAAAAAAA
*
-00000400: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
+00000800: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
*
-00001400: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
+00001800: 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 42 BBBBBBBBBBBBBBBB
*
read 8192/8192 bytes at offset 0
XXX Bytes, X ops; XX:XX:XX.X (XXX YYY/sec and XXX ops/sec)
--
1.8.3.1


2014-02-28 16:11:20

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 6/8] fsstress: translate flags in fiemap_f

Translate flags in fiemap_f output to human readable strings.

Signed-off-by: Lukas Czerner <[email protected]>
---
ltp/fsstress.c | 17 +++++++++++++++--
1 file changed, 15 insertions(+), 2 deletions(-)

diff --git a/ltp/fsstress.c b/ltp/fsstress.c
index 24864db..869a8ac 100644
--- a/ltp/fsstress.c
+++ b/ltp/fsstress.c
@@ -2252,6 +2252,18 @@ fdatasync_f(int opno, long r)
free_pathname(&f);
close(fd);
}
+
+#ifdef HAVE_LINUX_FIEMAP_H
+struct print_flags fiemap_flags[] = {
+ { FIEMAP_FLAG_SYNC, "SYNC"},
+ { FIEMAP_FLAG_XATTR, "XATTR"},
+ { -1, NULL}
+};
+
+#define translate_fiemap_flags(mode) \
+ ({translate_flags(mode, "|", fiemap_flags);})
+#endif
+
void
fiemap_f(int opno, long r)
{
@@ -2314,9 +2326,10 @@ fiemap_f(int opno, long r)

e = ioctl(fd, FS_IOC_FIEMAP, (unsigned long)fiemap);
if (v)
- printf("%d/%d: ioctl(FIEMAP) %s%s %lld %lld %x %d\n",
+ printf("%d/%d: ioctl(FIEMAP) %s%s %lld %lld (%s) %d\n",
procid, opno, f.path, st, (long long)fiemap->fm_start,
- (long long) fiemap->fm_length, fiemap->fm_flags, e);
+ (long long) fiemap->fm_length,
+ translate_fiemap_flags(fiemap->fm_flags), e);
free(fiemap);
free_pathname(&f);
close(fd);
--
1.8.3.1


2014-02-28 16:11:23

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 8/8] ext4/001: Add ext4 specific test for fallocate zero range

This is based on xfs/242. However it's better to make it file system
specific because the range can be zeroes either directly by writing
zeroes, or converting to unwritten extent, so the actual result might
differ from file system to file system. Also xfs results differ
depending on the page size which is not the case for ext4.

Signed-off-by: Lukas Czerner <[email protected]>
---
tests/ext4/001 | 64 ++++++++++
tests/ext4/001.out | 337 +++++++++++++++++++++++++++++++++++++++++++++++++++++
tests/ext4/group | 1 +
3 files changed, 402 insertions(+)
create mode 100755 tests/ext4/001
create mode 100644 tests/ext4/001.out

diff --git a/tests/ext4/001 b/tests/ext4/001
new file mode 100755
index 0000000..d575d9a
--- /dev/null
+++ b/tests/ext4/001
@@ -0,0 +1,64 @@
+#! /bin/bash
+# FS QA Test No. 001
+#
+# Test fallocate FALLOC_FL_ZERO_RANGE
+#
+#-----------------------------------------------------------------------
+# Copyright 2014 (C) Red Hat, Inc., Lukas Czerner <[email protected]>
+#
+# 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
+#
+#-----------------------------------------------------------------------
+#
+
+seq=`basename $0`
+seqres=$RESULT_DIR/$seq
+echo "QA output created by $seq"
+
+here=`pwd`
+tmp=/tmp/$$
+status=1 # failure is the default!
+
+_cleanup()
+{
+ rm -f $tmp.*
+}
+
+trap "_cleanup ; exit \$status" 0 1 2 3 15
+
+# get standard environment, filters and checks
+. ./common/rc
+. ./common/filter
+. ./common/punch
+
+# real QA test starts here
+_supported_fs ext4
+_supported_os Linux
+_require_xfs_io_falloc "fzero"
+
+testfile=$TEST_DIR/001.$$
+
+# Standard zero range tests
+_test_generic_punch falloc fzero fzero fiemap _filter_fiemap $testfile
+
+# Delayed allocation zero range tests
+_test_generic_punch -d falloc fzero fzero fiemap _filter_fiemap $testfile
+
+# Multi zero range tests
+_test_generic_punch -k falloc fzero fzero fiemap _filter_fiemap $testfile
+
+# Delayed allocation multi zero range tests
+_test_generic_punch -d -k falloc fzero fzero fiemap _filter_fiemap $testfile
+
+status=0 ; exit
diff --git a/tests/ext4/001.out b/tests/ext4/001.out
new file mode 100644
index 0000000..212c247
--- /dev/null
+++ b/tests/ext4/001.out
@@ -0,0 +1,337 @@
+QA output created by 001
+ 1. into a hole
+0: [0..7]: hole
+1: [8..23]: unwritten
+2: [24..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 2. into allocated space
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 3. into unwritten space
+0: [0..39]: unwritten
+daa100df6e6711906b61c9ab5aa16032
+ 4. hole -> data
+0: [0..7]: hole
+1: [8..23]: unwritten
+2: [24..31]: data
+3: [32..39]: hole
+cc63069677939f69a6e8f68cae6a6dac
+ 5. hole -> unwritten
+0: [0..7]: hole
+1: [8..31]: unwritten
+2: [32..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 6. data -> hole
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: hole
+1b3779878366498b28c702ef88c4a773
+ 7. data -> unwritten
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: hole
+1b3779878366498b28c702ef88c4a773
+ 8. unwritten -> hole
+0: [0..23]: unwritten
+1: [24..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 9. unwritten -> data
+0: [0..23]: unwritten
+1: [24..31]: data
+2: [32..39]: hole
+cc63069677939f69a6e8f68cae6a6dac
+ 10. hole -> data -> hole
+0: [0..7]: hole
+1: [8..31]: unwritten
+2: [32..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 11. data -> hole -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 12. unwritten -> data -> unwritten
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+daa100df6e6711906b61c9ab5aa16032
+ 13. data -> unwritten -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 14. data -> hole @ EOF
+0: [0..23]: data
+1: [24..39]: unwritten
+e1f024eedd27ea6b1c3e9b841c850404
+ 15. data -> hole @ 0
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 16. data -> cache cold ->hole
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 17. data -> hole in single block file
+0: [0..7]: data
+0000000 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+0000200 0000 0000 0000 0000 0000 0000 0000 0000
+*
+0000400 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+ 1. into a hole
+0: [0..7]: hole
+1: [8..23]: unwritten
+2: [24..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 2. into allocated space
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 3. into unwritten space
+0: [0..39]: unwritten
+daa100df6e6711906b61c9ab5aa16032
+ 4. hole -> data
+0: [0..7]: hole
+1: [8..23]: unwritten
+2: [24..31]: data
+3: [32..39]: hole
+cc63069677939f69a6e8f68cae6a6dac
+ 5. hole -> unwritten
+0: [0..7]: hole
+1: [8..31]: unwritten
+2: [32..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 6. data -> hole
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: hole
+1b3779878366498b28c702ef88c4a773
+ 7. data -> unwritten
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: hole
+1b3779878366498b28c702ef88c4a773
+ 8. unwritten -> hole
+0: [0..23]: unwritten
+1: [24..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 9. unwritten -> data
+0: [0..23]: unwritten
+1: [24..31]: data
+2: [32..39]: hole
+cc63069677939f69a6e8f68cae6a6dac
+ 10. hole -> data -> hole
+0: [0..7]: hole
+1: [8..31]: unwritten
+2: [32..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 11. data -> hole -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 12. unwritten -> data -> unwritten
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+daa100df6e6711906b61c9ab5aa16032
+ 13. data -> unwritten -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 14. data -> hole @ EOF
+0: [0..23]: data
+1: [24..39]: unwritten
+e1f024eedd27ea6b1c3e9b841c850404
+ 15. data -> hole @ 0
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 16. data -> cache cold ->hole
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 17. data -> hole in single block file
+0: [0..7]: data
+0000000 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+0000200 0000 0000 0000 0000 0000 0000 0000 0000
+*
+0000400 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+ 1. into a hole
+0: [0..7]: hole
+1: [8..23]: unwritten
+2: [24..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 2. into allocated space
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 3. into unwritten space
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 4. hole -> data
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 5. hole -> unwritten
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 6. data -> hole
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 7. data -> unwritten
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 8. unwritten -> hole
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 9. unwritten -> data
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 10. hole -> data -> hole
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 11. data -> hole -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 12. unwritten -> data -> unwritten
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 13. data -> unwritten -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 14. data -> hole @ EOF
+0: [0..23]: data
+1: [24..39]: unwritten
+e1f024eedd27ea6b1c3e9b841c850404
+ 15. data -> hole @ 0
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 16. data -> cache cold ->hole
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 17. data -> hole in single block file
+0: [0..7]: data
+0000000 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+0000200 0000 0000 0000 0000 0000 0000 0000 0000
+*
+0000400 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+ 1. into a hole
+0: [0..7]: hole
+1: [8..23]: unwritten
+2: [24..39]: hole
+daa100df6e6711906b61c9ab5aa16032
+ 2. into allocated space
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 3. into unwritten space
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 4. hole -> data
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 5. hole -> unwritten
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 6. data -> hole
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 7. data -> unwritten
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 8. unwritten -> hole
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 9. unwritten -> data
+0: [0..7]: data
+1: [8..23]: unwritten
+2: [24..39]: data
+cc58a7417c2d7763adc45b6fcd3fa024
+ 10. hole -> data -> hole
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 11. data -> hole -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 12. unwritten -> data -> unwritten
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 13. data -> unwritten -> data
+0: [0..7]: data
+1: [8..31]: unwritten
+2: [32..39]: data
+f6aeca13ec49e5b266cd1c913cd726e3
+ 14. data -> hole @ EOF
+0: [0..23]: data
+1: [24..39]: unwritten
+e1f024eedd27ea6b1c3e9b841c850404
+ 15. data -> hole @ 0
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 16. data -> cache cold ->hole
+0: [0..15]: unwritten
+1: [16..39]: data
+eecb7aa303d121835de05028751d301c
+ 17. data -> hole in single block file
+0: [0..7]: data
+0000000 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
+0000200 0000 0000 0000 0000 0000 0000 0000 0000
+*
+0000400 cdcd cdcd cdcd cdcd cdcd cdcd cdcd cdcd
+*
diff --git a/tests/ext4/group b/tests/ext4/group
index 7e1a68b..dd2841e 100644
--- a/tests/ext4/group
+++ b/tests/ext4/group
@@ -3,6 +3,7 @@
# - do not start group names with a digit
# - comment line before each group is "new" description
#
+001 auto prealloc quick
271 auto rw quick
301 aio dangerous ioctl rw stress
302 aio dangerous ioctl rw stress
--
1.8.3.1


2014-02-28 16:11:01

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 4/8] xfstests: Move fallocate include into global.h

Move the inclusion of falloc.h with all it's possible defines for the
fallocate mode into global.h header file so we do not have to include
and define it manually in every tool using fallocate.

Signed-off-by: Lukas Czerner <[email protected]>
---
configure.ac | 3 ++-
ltp/fsstress.c | 11 ++---------
ltp/fsx.c | 11 ++++-------
src/global.h | 25 +++++++++++++++++++++++++
4 files changed, 33 insertions(+), 17 deletions(-)

diff --git a/configure.ac b/configure.ac
index 6fba3ad..2f95c4c 100644
--- a/configure.ac
+++ b/configure.ac
@@ -25,7 +25,8 @@ AC_HEADER_STDC
sys/wait.h \
sys/types.h \
strings.h \
- err.h
+ err.h \
+ linux/falloc.h
])
AC_CHECK_HEADERS([ sys/fs/xfs_fsops.h \
sys/fs/xfs_itable.h \
diff --git a/ltp/fsstress.c b/ltp/fsstress.c
index c56f168..7dec7c6 100644
--- a/ltp/fsstress.c
+++ b/ltp/fsstress.c
@@ -27,13 +27,6 @@
#ifdef HAVE_LINUX_FIEMAP_H
#include <linux/fiemap.h>
#endif
-#ifdef FALLOCATE
-#include <linux/falloc.h>
-#ifndef FALLOC_FL_PUNCH_HOLE
-/* Copy-paste from linux/falloc.h */
-#define FALLOC_FL_PUNCH_HOLE 0x02 /* de-allocates range */
-#endif
-#endif
#ifndef HAVE_ATTR_LIST
#define attr_list(path, buf, size, flags, cursor) (errno = -ENOSYS, -1)
#endif
@@ -2085,7 +2078,7 @@ dwrite_f(int opno, long r)
void
fallocate_f(int opno, long r)
{
-#ifdef FALLOCATE
+#ifdef HAVE_LINUX_FALLOC_H
int e;
pathname_t f;
int fd;
@@ -2507,7 +2500,7 @@ mknod_f(int opno, long r)
void
punch_f(int opno, long r)
{
-#ifdef FALLOCATE
+#ifdef HAVE_LINUX_FALLOC_H
int e;
pathname_t f;
int fd;
diff --git a/ltp/fsx.c b/ltp/fsx.c
index 2f1e3e8..c36a038 100644
--- a/ltp/fsx.c
+++ b/ltp/fsx.c
@@ -33,9 +33,6 @@
#ifdef AIO
#include <libaio.h>
#endif
-#ifdef FALLOCATE
-#include <linux/falloc.h>
-#endif

#ifndef MAP_FILE
# define MAP_FILE 0
@@ -882,7 +879,7 @@ do_punch_hole(unsigned offset, unsigned length)
}
#endif

-#ifdef FALLOCATE
+#ifdef HAVE_LINUX_FALLOC_H
/* fallocate is basically a no-op unless extending, then a lot like a truncate */
void
do_preallocate(unsigned offset, unsigned length)
@@ -1139,7 +1136,7 @@ usage(void)
" -A: Use the AIO system calls\n"
#endif
" -D startingop: debug output starting at specified operation\n"
-#ifdef FALLOCATE
+#ifdef HAVE_LINUX_FALLOC_H
" -F: Do not use fallocate (preallocation) calls\n"
#endif
#ifdef FALLOC_FL_PUNCH_HOLE
@@ -1296,7 +1293,7 @@ int aio_rw(int rw, int fd, char *buf, unsigned len, unsigned offset)
void
test_fallocate()
{
-#ifdef FALLOCATE
+#ifdef HAVE_LINUX_FALLOC_H
if (!lite && fallocate_calls) {
if (fallocate(fd, 0, 0, 1) && errno == EOPNOTSUPP) {
if(!quiet)
@@ -1306,7 +1303,7 @@ test_fallocate()
ftruncate(fd, 0);
}
}
-#else /* ! FALLOCATE */
+#else /* ! HAVE_LINUX_FALLOC_H */
fallocate_calls = 0;
#endif

diff --git a/src/global.h b/src/global.h
index e6a2c2b..8180f66 100644
--- a/src/global.h
+++ b/src/global.h
@@ -149,4 +149,29 @@
#include <sys/param.h>
#endif

+#ifdef HAVE_LINUX_FALLOC_H
+#include <linux/falloc.h>
+
+#ifndef FALLOC_FL_KEEP_SIZE
+#define FALLOC_FL_KEEP_SIZE 0x01
+#endif
+
+#ifndef FALLOC_FL_PUNCH_HOLE
+#define FALLOC_FL_PUNCH_HOLE 0x02
#endif
+
+#ifndef FALLOC_FL_NO_HIDE_STALE
+#define FALLOC_FL_NO_HIDE_STALE 0x04
+#endif
+
+#ifndef FALLOC_FL_COLLAPSE_RANGE
+#define FALLOC_FL_COLLAPSE_RANGE 0x08
+#endif
+
+#ifndef FALLOC_FL_ZERO_RANGE
+#define FALLOC_FL_ZERO_RANGE 0x10
+#endif
+
+#endif /* HAVE_LINUX_FALLOC_H */
+
+#endif /* GLOBAL_H */
--
1.8.3.1


2014-02-28 16:11:21

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 7/8] xfstests: Add fallocate zero range operation to fsx

This commit adds fallocate FALLOC_FL_ZERO_RANGE support for fsx.

Signed-off-by: Lukas Czerner <[email protected]>
---
ltp/fsx.c | 128 +++++++++++++++++++++++++++++++++++++++++++++++---------------
1 file changed, 98 insertions(+), 30 deletions(-)

diff --git a/ltp/fsx.c b/ltp/fsx.c
index c36a038..5d6d198 100644
--- a/ltp/fsx.c
+++ b/ltp/fsx.c
@@ -69,6 +69,7 @@ int logcount = 0; /* total ops */
* TRUNCATE: - 4
* FALLOCATE: - 5
* PUNCH HOLE: - 6
+ * ZERO RANGE: - 7
*
* When mapped read/writes are disabled, they are simply converted to normal
* reads and writes. When fallocate/fpunch calls are disabled, they are
@@ -92,7 +93,8 @@ int logcount = 0; /* total ops */
#define OP_TRUNCATE 4
#define OP_FALLOCATE 5
#define OP_PUNCH_HOLE 6
-#define OP_MAX_FULL 7
+#define OP_ZERO_RANGE 7
+#define OP_MAX_FULL 8

/* operation modifiers */
#define OP_CLOSEOPEN 100
@@ -139,6 +141,7 @@ int seed = 1; /* -S flag */
int mapped_writes = 1; /* -W flag disables */
int fallocate_calls = 1; /* -F flag disables */
int punch_hole_calls = 1; /* -H flag disables */
+int zero_range_calls = 1; /* -z flag disables */
int mapped_reads = 1; /* -R flag disables it */
int fsxgoodfd = 0;
int o_direct; /* -Z */
@@ -317,6 +320,14 @@ logdump(void)
lp->args[0] + lp->args[1])
prt("\t******PPPP");
break;
+ case OP_ZERO_RANGE:
+ prt("ZERO 0x%x thru 0x%x\t(0x%x bytes)",
+ lp->args[0], lp->args[0] + lp->args[1] - 1,
+ lp->args[1]);
+ if (badoff >= lp->args[0] && badoff <
+ lp->args[0] + lp->args[1])
+ prt("\t******ZZZZ");
+ break;
case OP_SKIPPED:
prt("SKIPPED (no operation)");
break;
@@ -879,6 +890,65 @@ do_punch_hole(unsigned offset, unsigned length)
}
#endif

+#ifdef FALLOC_FL_ZERO_RANGE
+void
+do_zero_range(unsigned offset, unsigned length)
+{
+ unsigned end_offset;
+ int mode = FALLOC_FL_ZERO_RANGE;
+ int keep_size;
+
+ if (length == 0) {
+ if (!quiet && testcalls > simulatedopcount)
+ prt("skipping zero length zero range\n");
+ log4(OP_SKIPPED, OP_ZERO_RANGE, offset, length);
+ return;
+ }
+
+ keep_size = random() % 2;
+
+ end_offset = keep_size ? 0 : offset + length;
+
+ if (end_offset > biggest) {
+ biggest = end_offset;
+ if (!quiet && testcalls > simulatedopcount)
+ prt("zero_range to largest ever: 0x%x\n", end_offset);
+ }
+
+ /*
+ * last arg matches fallocate string array index in logdump:
+ * 0: allocate past EOF
+ * 1: extending prealloc
+ * 2: interior prealloc
+ */
+ log4(OP_ZERO_RANGE, offset, length, (end_offset > file_size) ? (keep_size ? 0 : 1) : 2);
+
+ if (testcalls <= simulatedopcount)
+ return;
+
+ if ((progressinterval && testcalls % progressinterval == 0) ||
+ (debug && (monitorstart == -1 || monitorend == -1 ||
+ end_offset <= monitorend))) {
+ prt("%lu zero\tfrom 0x%x to 0x%x, (0x%x bytes)\n", testcalls,
+ offset, offset+length, length);
+ }
+ if (fallocate(fd, mode, (loff_t)offset, (loff_t)length) == -1) {
+ prt("%pzero range: %x to %x\n", offset, length);
+ prterr("do_zero_range: fallocate");
+ report_failure(161);
+ }
+
+ memset(good_buf + offset, '\0', length);
+}
+
+#else
+void
+do_zero_range(unsigned offset, unsigned length)
+{
+ return;
+}
+#endif
+
#ifdef HAVE_LINUX_FALLOC_H
/* fallocate is basically a no-op unless extending, then a lot like a truncate */
void
@@ -1047,6 +1117,12 @@ test(void)
goto out;
}
break;
+ case OP_ZERO_RANGE:
+ if (!zero_range_calls) {
+ log4(OP_SKIPPED, OP_ZERO_RANGE, offset, size);
+ goto out;
+ }
+ break;
}

switch (op) {
@@ -1085,6 +1161,10 @@ test(void)
TRIM_OFF_LEN(offset, size, file_size);
do_punch_hole(offset, size);
break;
+ case OP_ZERO_RANGE:
+ TRIM_OFF_LEN(offset, size, file_size);
+ do_zero_range(offset, size);
+ break;
default:
prterr("test: unknown operation");
report_failure(42);
@@ -1140,7 +1220,10 @@ usage(void)
" -F: Do not use fallocate (preallocation) calls\n"
#endif
#ifdef FALLOC_FL_PUNCH_HOLE
-" -H: Do not use punch hole calls\n"
+" -H: Do not use punch hole calls\n"
+#endif
+#ifdef FALLOC_FL_ZERO_RANGE
+" -E: Do not use zero range calls\n"
#endif
" -L: fsxLite - no file creations & no file size changes\n\
-N numops: total # operations to do (default infinity)\n\
@@ -1290,40 +1373,21 @@ int aio_rw(int rw, int fd, char *buf, unsigned len, unsigned offset)

#endif

-void
-test_fallocate()
+int
+test_fallocate(int mode)
{
#ifdef HAVE_LINUX_FALLOC_H
+ int ret = 0;
if (!lite && fallocate_calls) {
- if (fallocate(fd, 0, 0, 1) && errno == EOPNOTSUPP) {
+ if (fallocate(fd, mode, 0, 1) && errno == EOPNOTSUPP) {
if(!quiet)
warn("main: filesystem does not support fallocate, disabling\n");
- fallocate_calls = 0;
} else {
+ ret = 1;
ftruncate(fd, 0);
}
}
-#else /* ! HAVE_LINUX_FALLOC_H */
- fallocate_calls = 0;
-#endif
-
-}
-
-void
-test_punch_hole()
-{
-#ifdef FALLOC_FL_PUNCH_HOLE
- if (!lite && punch_hole_calls) {
- if (fallocate(fd, FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE,
- 0, 1) && errno == EOPNOTSUPP) {
- if(!quiet)
- warn("main: filesystem does not support fallocate punch hole, disabling");
- punch_hole_calls = 0;
- } else
- ftruncate(fd, 0);
- }
-#else /* ! PUNCH HOLE */
- punch_hole_calls = 0;
+ return ret;
#endif
}

@@ -1345,7 +1409,7 @@ main(int argc, char **argv)

setvbuf(stdout, (char *)0, _IOLBF, 0); /* line buffered stdout */

- while ((ch = getopt(argc, argv, "b:c:dfl:m:no:p:qr:s:t:w:xyAD:FHLN:OP:RS:WZ"))
+ while ((ch = getopt(argc, argv, "b:c:dfl:m:no:p:qr:s:t:w:xyAD:FHzLN:OP:RS:WZ"))
!= EOF)
switch (ch) {
case 'b':
@@ -1445,6 +1509,9 @@ main(int argc, char **argv)
case 'H':
punch_hole_calls = 0;
break;
+ case 'z':
+ zero_range_calls = 0;
+ break;
case 'L':
lite = 1;
break;
@@ -1590,8 +1657,9 @@ main(int argc, char **argv)
} else
check_trunc_hack();

- test_fallocate();
- test_punch_hole();
+ fallocate_calls = test_fallocate(0);
+ punch_hole_calls = test_fallocate(FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE);
+ zero_range_calls = test_fallocate(FALLOC_FL_ZERO_RANGE);

while (numops == -1 || numops--)
test();
--
1.8.3.1


2014-02-28 16:11:18

by Lukas Czerner

[permalink] [raw]
Subject: [PATCH 5/8] xfstests: Add fallocate zero range operation to fsstress

This commit adds fzero operation support for fsstress, which is meant to
exercise fallocate FALLOC_FL_ZERO_RANGE support.

Also reorganise the common fallocate code into a single do_fallocate()
function and use flags use the right mode.

Also in order to make more obvious which fallocate mode fsstress is
testing translate fallocate flags into human readable strings.

Signed-off-by: Lukas Czerner <[email protected]>
---
ltp/fsstress.c | 164 +++++++++++++++++++++++++++++++++++++--------------------
1 file changed, 106 insertions(+), 58 deletions(-)

diff --git a/ltp/fsstress.c b/ltp/fsstress.c
index 7dec7c6..24864db 100644
--- a/ltp/fsstress.c
+++ b/ltp/fsstress.c
@@ -70,6 +70,7 @@ typedef enum {
OP_MKDIR,
OP_MKNOD,
OP_PUNCH,
+ OP_ZERO,
OP_READ,
OP_READLINK,
OP_RENAME,
@@ -114,6 +115,17 @@ typedef struct pathname {
char *path;
} pathname_t;

+struct print_flags {
+ unsigned long mask;
+ const char *name;
+};
+
+struct print_string {
+ char *buffer;
+ int len;
+ int max;
+};
+
#define FT_DIR 0
#define FT_DIRm (1 << FT_DIR)
#define FT_REG 1
@@ -155,6 +167,7 @@ void link_f(int, long);
void mkdir_f(int, long);
void mknod_f(int, long);
void punch_f(int, long);
+void zero_f(int, long);
void read_f(int, long);
void readlink_f(int, long);
void rename_f(int, long);
@@ -192,6 +205,7 @@ opdesc_t ops[] = {
{ OP_MKDIR, "mkdir", mkdir_f, 2, 1 },
{ OP_MKNOD, "mknod", mknod_f, 2, 1 },
{ OP_PUNCH, "punch", punch_f, 1, 1 },
+ { OP_ZERO, "zero", zero_f, 1, 1 },
{ OP_READ, "read", read_f, 1, 0 },
{ OP_READLINK, "readlink", readlink_f, 1, 0 },
{ OP_RENAME, "rename", rename_f, 2, 1 },
@@ -242,6 +256,7 @@ int verbose = 0;
sig_atomic_t should_stop = 0;
char *execute_cmd = NULL;
int execute_freq = 1;
+struct print_string flag_str = {0};

void add_to_flist(int, int, int);
void append_pathname(pathname_t *, char *);
@@ -543,6 +558,59 @@ int main(int argc, char **argv)
return 0;
}

+int
+add_string(struct print_string *str, const char *add)
+{
+ int len = strlen(add);
+
+ if (len <= 0)
+ return 0;
+
+ if (len > (str->max - 1) - str->len) {
+ str->len = str->max - 1;
+ return 0;
+ }
+
+ memcpy(str->buffer + str->len, add, len);
+ str->len += len;
+ str->buffer[str->len] = '\0';
+
+ return len;
+}
+
+char *
+translate_flags(int flags, const char *delim,
+ const struct print_flags *flag_array)
+{
+ int i, mask, first = 1;
+ const char *add;
+
+ if (!flag_str.buffer) {
+ flag_str.buffer = malloc(4096);
+ flag_str.max = 4096;
+ flag_str.len = 0;
+ }
+ if (!flag_str.buffer)
+ return NULL;
+ flag_str.len = 0;
+ flag_str.buffer[0] = '\0';
+
+ for (i = 0; flag_array[i].name && flags; i++) {
+ mask = flag_array[i].mask;
+ if ((flags & mask) != mask)
+ continue;
+
+ add = flag_array[i].name;
+ flags &= ~mask;
+ if (!first && delim)
+ add_string(&flag_str, delim);
+ else
+ first = 0;
+ add_string(&flag_str, add);
+ }
+ return flag_str.buffer;
+}
+
void
add_to_flist(int ft, int id, int parent)
{
@@ -2075,8 +2143,23 @@ dwrite_f(int opno, long r)
close(fd);
}

+
+#ifdef HAVE_LINUX_FALLOC_H
+struct print_flags falloc_flags [] = {
+ { FALLOC_FL_KEEP_SIZE, "KEEP_SIZE"},
+ { FALLOC_FL_PUNCH_HOLE, "PUNCH_HOLE"},
+ { FALLOC_FL_NO_HIDE_STALE, "NO_HIDE_STALE"},
+ { FALLOC_FL_COLLAPSE_RANGE, "COLLAPSE_RANGE"},
+ { FALLOC_FL_ZERO_RANGE, "ZERO_RANGE"},
+ { -1, NULL}
+};
+
+#define translate_falloc_flags(mode) \
+ ({translate_flags(mode, "|", falloc_flags);})
+#endif
+
void
-fallocate_f(int opno, long r)
+do_fallocate(int opno, long r, int mode)
{
#ifdef HAVE_LINUX_FALLOC_H
int e;
@@ -2088,28 +2171,26 @@ fallocate_f(int opno, long r)
struct stat64 stb;
int v;
char st[1024];
- int mode = 0;

init_pathname(&f);
if (!get_fname(FT_REGFILE, r, &f, NULL, NULL, &v)) {
if (v)
- printf("%d/%d: fallocate - no filename\n", procid, opno);
+ printf("%d/%d: do_fallocate - no filename\n", procid, opno);
free_pathname(&f);
return;
}
fd = open_path(&f, O_RDWR);
- e = fd < 0 ? errno : 0;
- check_cwd();
if (fd < 0) {
if (v)
- printf("%d/%d: fallocate - open %s failed %d\n",
- procid, opno, f.path, e);
+ printf("%d/%d: do_fallocate - open %s failed %d\n",
+ procid, opno, f.path, errno);
free_pathname(&f);
return;
}
+ check_cwd();
if (fstat64(fd, &stb) < 0) {
if (v)
- printf("%d/%d: fallocate - fstat64 %s failed %d\n",
+ printf("%d/%d: do_fallocate - fstat64 %s failed %d\n",
procid, opno, f.path, errno);
free_pathname(&f);
close(fd);
@@ -2123,14 +2204,21 @@ fallocate_f(int opno, long r)
mode |= FALLOC_FL_KEEP_SIZE & random();
e = fallocate(fd, mode, (loff_t)off, (loff_t)len) < 0 ? errno : 0;
if (v)
- printf("%d/%d: fallocate(%d) %s %st %lld %lld %d\n",
- procid, opno, mode,
+ printf("%d/%d: fallocate(%s) %s %st %lld %lld %d\n",
+ procid, opno, translate_falloc_flags(mode),
f.path, st, (long long)off, (long long)len, e);
free_pathname(&f);
close(fd);
#endif
}

+void
+fallocate_f(int opno, long r)
+{
+#ifdef HAVE_LINUX_FALLOC_H
+ do_fallocate(opno, r, 0);
+#endif
+}

void
fdatasync_f(int opno, long r)
@@ -2501,55 +2589,15 @@ void
punch_f(int opno, long r)
{
#ifdef HAVE_LINUX_FALLOC_H
- int e;
- pathname_t f;
- int fd;
- __int64_t lr;
- off64_t off;
- off64_t len;
- struct stat64 stb;
- int v;
- char st[1024];
- int mode = FALLOC_FL_PUNCH_HOLE;
+ do_fallocate(opno, r, FALLOC_FL_PUNCH_HOLE);
+#endif
+}

- init_pathname(&f);
- if (!get_fname(FT_REGFILE, r, &f, NULL, NULL, &v)) {
- if (v)
- printf("%d/%d: punch hole - no filename\n", procid, opno);
- free_pathname(&f);
- return;
- }
- fd = open_path(&f, O_RDWR);
- e = fd < 0 ? errno : 0;
- check_cwd();
- if (fd < 0) {
- if (v)
- printf("%d/%d: punch hole - open %s failed %d\n",
- procid, opno, f.path, e);
- free_pathname(&f);
- return;
- }
- if (fstat64(fd, &stb) < 0) {
- if (v)
- printf("%d/%d: punch hole - fstat64 %s failed %d\n",
- procid, opno, f.path, errno);
- free_pathname(&f);
- close(fd);
- return;
- }
- inode_info(st, sizeof(st), &stb, v);
- lr = ((__int64_t)random() << 32) + random();
- off = (off64_t)(lr % MIN(stb.st_size + (1024 * 1024), MAXFSIZE));
- off %= maxfsize;
- len = (off64_t)(random() % (1024 * 1024));
- mode |= FALLOC_FL_KEEP_SIZE & random();
- e = fallocate(fd, mode, (loff_t)off, (loff_t)len) < 0 ? errno : 0;
- if (v)
- printf("%d/%d: punch hole(%d) %s %s %lld %lld %d\n",
- procid, opno, mode,
- f.path, st, (long long)off, (long long)len, e);
- free_pathname(&f);
- close(fd);
+void
+zero_f(int opno, long r)
+{
+#ifdef HAVE_LINUX_FALLOC_H
+ do_fallocate(opno, r, FALLOC_FL_ZERO_RANGE);
#endif
}

--
1.8.3.1


2014-02-28 16:40:59

by Eric Sandeen

[permalink] [raw]
Subject: Re: [PATCH 1/8] xfstests: Create single function for testing xfs_io commands

On 2/28/14, 10:10 AM, Lukas Czerner wrote:
> Currently there are several function testing various xfs_io commands.
> This commit creates _require_xfs_io_command() to test any xfs_command.
>
> Signed-off-by: Lukas Czerner <[email protected]>

Nice,

So to be clear, is the difference here that the explicitly listed commands
also ensure that the running kernel supports it, whereas the default simply
makes sure that xfs_io accepts it? I suppose it's self-explanatory.

Looks good to me,

Reviewed-by: Eric Sandeen <[email protected]>



> ---
> common/rc | 72 +++++++++++++++++++++++++++++++++------------------------------
> 1 file changed, 38 insertions(+), 34 deletions(-)
>
> diff --git a/common/rc b/common/rc
> index f2c3c3a..7f530d0 100644
> --- a/common/rc
> +++ b/common/rc
> @@ -1296,12 +1296,43 @@ _user_do()
> fi
> }
>
> +_require_xfs_io_command()
> +{
> + if [ $# -ne 1 ]
> + then
> + echo "Usage: _require_xfs_io_command command" 1>&2
> + exit 1
> + fi
> + command=$1
> +
> + testfile=$TEST_DIR/$$.xfs_io
> + case $command in
> + "falloc" )
> + testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
> + ;;
> + "fpunch" | "fcollapse" | "zero" )
> + testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> + -c "$command 4k 8k" $testfile 2>&1`
> + ;;
> + "fiemap")
> + testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> + -c "fiemap -v" $testfile 2>&1`
> + ;;
> + *)
> + testio=`$XFS_IO_PROG -c "$command help" 2>&1`
> + esac
> +
> + rm -f $testfile 2>&1 > /dev/null
> + echo $testio | grep -q "not found" && \
> + _notrun "xfs_io $command support is missing"
> + echo $testio | grep -q "Operation not supported" && \
> + _notrun "xfs_io $command failed (old kernel/wrong fs?)"
> +}
> +
> # check that xfs_io, kernel, and filesystem all support zero
> _require_xfs_io_zero()
> {
> - testio=`$XFS_IO_PROG -c "zero help" 2>&1`
> - echo $testio | grep -q 'command "zero" not found' && \
> - _notrun "zero command not supported"
> + _require_xfs_io_command "zero"
> }

Nice, so now this actually *does* test the 2nd and 3rd items. :)

> # check that xfs_io, glibc, kernel, and filesystem all (!) support
> @@ -1309,54 +1340,27 @@ _require_xfs_io_zero()
> #
> _require_xfs_io_falloc()
> {
> - testfile=$TEST_DIR/$$.falloc
> - testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
> - rm -f $testfile 2>&1 > /dev/null
> - echo $testio | grep -q "not found" && \
> - _notrun "xfs_io fallocate support is missing"
> - echo $testio | grep -q "Operation not supported" && \
> - _notrun "xfs_io fallocate command failed (old kernel/wrong fs?)"
> + _require_xfs_io_command "falloc"
> }
>
> # check that xfs_io, kernel and filesystem all support fallocate with hole
> # punching
> _require_xfs_io_falloc_punch()
> {
> - testfile=$TEST_DIR/$$.falloc
> - testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> - -c "fpunch 4k 8k" $testfile 2>&1`
> - rm -f $testfile 2>&1 > /dev/null
> - echo $testio | grep -q "not found" && \
> - _notrun "xfs_io fallocate punch support is missing"
> - echo $testio | grep -q "Operation not supported" && \
> - _notrun "xfs_io fallocate punch command failed (no fs support?)"
> + _require_xfs_io_command "fpunch"
> }
>
> # check that xfs_io, kernel and filesystem all support fallocate with collapse
> # range
> _require_xfs_io_falloc_collapse()
> {
> - testfile=$TEST_DIR/$$.falloc
> - testio=`$XFS_IO_PROG -f -c "pwrite 0 20k" -c "fsync" \
> - -c "fcollapse 4k 8k" $testfile 2>&1`
> - rm -f $testfile 2>&1 > /dev/null
> - echo $testio | grep -q "not found" && \
> - _notrun "xfs_io fallocate collapse range support is missing"
> - echo $testio | grep -q "Operation not supported" && \
> - _notrun "xfs_io fallocate collapse range failed (no fs support?)"
> + _require_xfs_io_command "fcollapse"
> }
>
> # check that xfs_io, kernel and filesystem support fiemap
> _require_xfs_io_fiemap()
> {
> - testfile=$TEST_DIR/$$.fiemap
> - testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> - -c "fiemap -v" $testfile 2>&1`
> - rm -f $testfile 2>&1 > /dev/null
> - echo $testio | grep -q "not found" && \
> - _notrun "xfs_io fiemap support is missing"
> - echo $testio | grep -q "Operation not supported" && \
> - _notrun "xfs_io fiemap command failed (no fs support?)"
> + _require_xfs_io_command "fiemap"
> }
>
> # Check that a fs has enough free space (in 1024b blocks)
>

_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs

2014-02-28 16:51:57

by Lukas Czerner

[permalink] [raw]
Subject: Re: [PATCH 1/8] xfstests: Create single function for testing xfs_io commands

On Fri, 28 Feb 2014, Eric Sandeen wrote:

> Date: Fri, 28 Feb 2014 10:40:59 -0600
> From: Eric Sandeen <[email protected]>
> To: Lukas Czerner <[email protected]>, [email protected]
> Cc: [email protected], [email protected]
> Subject: Re: [PATCH 1/8] xfstests: Create single function for testing xfs_io
> commands
>
> On 2/28/14, 10:10 AM, Lukas Czerner wrote:
> > Currently there are several function testing various xfs_io commands.
> > This commit creates _require_xfs_io_command() to test any xfs_command.
> >
> > Signed-off-by: Lukas Czerner <[email protected]>
>
> Nice,
>
> So to be clear, is the difference here that the explicitly listed commands
> also ensure that the running kernel supports it, whereas the default simply
> makes sure that xfs_io accepts it? I suppose it's self-explanatory.

The only command where we only tested xfs_io support was zero. Now
we test both xfs_io and kernel support with every command.


>
> Looks good to me,
>
> Reviewed-by: Eric Sandeen <[email protected]>

Thanks!
-Lukas

>
>
>
> > ---
> > common/rc | 72 +++++++++++++++++++++++++++++++++------------------------------
> > 1 file changed, 38 insertions(+), 34 deletions(-)
> >
> > diff --git a/common/rc b/common/rc
> > index f2c3c3a..7f530d0 100644
> > --- a/common/rc
> > +++ b/common/rc
> > @@ -1296,12 +1296,43 @@ _user_do()
> > fi
> > }
> >
> > +_require_xfs_io_command()
> > +{
> > + if [ $# -ne 1 ]
> > + then
> > + echo "Usage: _require_xfs_io_command command" 1>&2
> > + exit 1
> > + fi
> > + command=$1
> > +
> > + testfile=$TEST_DIR/$$.xfs_io
> > + case $command in
> > + "falloc" )
> > + testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
> > + ;;
> > + "fpunch" | "fcollapse" | "zero" )
> > + testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> > + -c "$command 4k 8k" $testfile 2>&1`
> > + ;;
> > + "fiemap")
> > + testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> > + -c "fiemap -v" $testfile 2>&1`
> > + ;;
> > + *)
> > + testio=`$XFS_IO_PROG -c "$command help" 2>&1`
> > + esac
> > +
> > + rm -f $testfile 2>&1 > /dev/null
> > + echo $testio | grep -q "not found" && \
> > + _notrun "xfs_io $command support is missing"
> > + echo $testio | grep -q "Operation not supported" && \
> > + _notrun "xfs_io $command failed (old kernel/wrong fs?)"
> > +}
> > +
> > # check that xfs_io, kernel, and filesystem all support zero
> > _require_xfs_io_zero()
> > {
> > - testio=`$XFS_IO_PROG -c "zero help" 2>&1`
> > - echo $testio | grep -q 'command "zero" not found' && \
> > - _notrun "zero command not supported"
> > + _require_xfs_io_command "zero"
> > }
>
> Nice, so now this actually *does* test the 2nd and 3rd items. :)
>
> > # check that xfs_io, glibc, kernel, and filesystem all (!) support
> > @@ -1309,54 +1340,27 @@ _require_xfs_io_zero()
> > #
> > _require_xfs_io_falloc()
> > {
> > - testfile=$TEST_DIR/$$.falloc
> > - testio=`$XFS_IO_PROG -F -f -c "falloc 0 1m" $testfile 2>&1`
> > - rm -f $testfile 2>&1 > /dev/null
> > - echo $testio | grep -q "not found" && \
> > - _notrun "xfs_io fallocate support is missing"
> > - echo $testio | grep -q "Operation not supported" && \
> > - _notrun "xfs_io fallocate command failed (old kernel/wrong fs?)"
> > + _require_xfs_io_command "falloc"
> > }
> >
> > # check that xfs_io, kernel and filesystem all support fallocate with hole
> > # punching
> > _require_xfs_io_falloc_punch()
> > {
> > - testfile=$TEST_DIR/$$.falloc
> > - testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> > - -c "fpunch 4k 8k" $testfile 2>&1`
> > - rm -f $testfile 2>&1 > /dev/null
> > - echo $testio | grep -q "not found" && \
> > - _notrun "xfs_io fallocate punch support is missing"
> > - echo $testio | grep -q "Operation not supported" && \
> > - _notrun "xfs_io fallocate punch command failed (no fs support?)"
> > + _require_xfs_io_command "fpunch"
> > }
> >
> > # check that xfs_io, kernel and filesystem all support fallocate with collapse
> > # range
> > _require_xfs_io_falloc_collapse()
> > {
> > - testfile=$TEST_DIR/$$.falloc
> > - testio=`$XFS_IO_PROG -f -c "pwrite 0 20k" -c "fsync" \
> > - -c "fcollapse 4k 8k" $testfile 2>&1`
> > - rm -f $testfile 2>&1 > /dev/null
> > - echo $testio | grep -q "not found" && \
> > - _notrun "xfs_io fallocate collapse range support is missing"
> > - echo $testio | grep -q "Operation not supported" && \
> > - _notrun "xfs_io fallocate collapse range failed (no fs support?)"
> > + _require_xfs_io_command "fcollapse"
> > }
> >
> > # check that xfs_io, kernel and filesystem support fiemap
> > _require_xfs_io_fiemap()
> > {
> > - testfile=$TEST_DIR/$$.fiemap
> > - testio=`$XFS_IO_PROG -F -f -c "pwrite 0 20k" -c "fsync" \
> > - -c "fiemap -v" $testfile 2>&1`
> > - rm -f $testfile 2>&1 > /dev/null
> > - echo $testio | grep -q "not found" && \
> > - _notrun "xfs_io fiemap support is missing"
> > - echo $testio | grep -q "Operation not supported" && \
> > - _notrun "xfs_io fiemap command failed (no fs support?)"
> > + _require_xfs_io_command "fiemap"
> > }
> >
> > # Check that a fs has enough free space (in 1024b blocks)
> >
>
>

_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs

2014-02-28 17:17:43

by Eric Sandeen

[permalink] [raw]
Subject: Re: [PATCH 4/8] xfstests: Move fallocate include into global.h

On 2/28/14, 10:11 AM, Lukas Czerner wrote:
> Move the inclusion of falloc.h with all it's possible defines for the
> fallocate mode into global.h header file so we do not have to include
> and define it manually in every tool using fallocate.
>
> Signed-off-by: Lukas Czerner <[email protected]>

I like the direction, but I think this changes behavior a little bit.

#ifdef FALLOCATE came from an autoconf macro:

AC_DEFUN([AC_PACKAGE_WANT_FALLOCATE],
[ AC_MSG_CHECKING([for fallocate])
AC_TRY_LINK([
#define _GNU_SOURCE
#define _FILE_OFFSET_BITS 64
#include <fcntl.h>
#include <linux/falloc.h> ],
[ fallocate(0, 0, 0, 0); ],
[ have_fallocate=true; AC_MSG_RESULT(yes) ],
[ have_fallocate=false; AC_MSG_RESULT(no) ])
AC_SUBST(have_fallocate)
])

(at least I think so?) and so #ifdef FALLOCATE meant that
an fallocate syscall actually exists. With your changes,
the test is now whether the fallocate *header* exists.

falloc.h is part of kernel-headers, not glibc. So it's
possible that there's a divergence between the two.

I think it's probably ok. Build-time checks should
determine whether we are able to _build_ and yours do that.
Each caller of fallocate (or each test using it) then probably
needs to ensure that the functionality it wants is actually
available at runtime and handle it if not.

So I'll give this a

Reviewed-by: Eric Sandeen <[email protected]>

but maybe the above rambling will ring alarm bells for
someone else... ;)

-Eric

> ---
> configure.ac | 3 ++-
> ltp/fsstress.c | 11 ++---------
> ltp/fsx.c | 11 ++++-------
> src/global.h | 25 +++++++++++++++++++++++++
> 4 files changed, 33 insertions(+), 17 deletions(-)
>
> diff --git a/configure.ac b/configure.ac
> index 6fba3ad..2f95c4c 100644
> --- a/configure.ac
> +++ b/configure.ac
> @@ -25,7 +25,8 @@ AC_HEADER_STDC
> sys/wait.h \
> sys/types.h \
> strings.h \
> - err.h
> + err.h \
> + linux/falloc.h
> ])
> AC_CHECK_HEADERS([ sys/fs/xfs_fsops.h \
> sys/fs/xfs_itable.h \
> diff --git a/ltp/fsstress.c b/ltp/fsstress.c
> index c56f168..7dec7c6 100644
> --- a/ltp/fsstress.c
> +++ b/ltp/fsstress.c
> @@ -27,13 +27,6 @@
> #ifdef HAVE_LINUX_FIEMAP_H
> #include <linux/fiemap.h>
> #endif
> -#ifdef FALLOCATE
> -#include <linux/falloc.h>
> -#ifndef FALLOC_FL_PUNCH_HOLE
> -/* Copy-paste from linux/falloc.h */
> -#define FALLOC_FL_PUNCH_HOLE 0x02 /* de-allocates range */
> -#endif
> -#endif
> #ifndef HAVE_ATTR_LIST
> #define attr_list(path, buf, size, flags, cursor) (errno = -ENOSYS, -1)
> #endif
> @@ -2085,7 +2078,7 @@ dwrite_f(int opno, long r)
> void
> fallocate_f(int opno, long r)
> {
> -#ifdef FALLOCATE
> +#ifdef HAVE_LINUX_FALLOC_H
> int e;
> pathname_t f;
> int fd;
> @@ -2507,7 +2500,7 @@ mknod_f(int opno, long r)
> void
> punch_f(int opno, long r)
> {
> -#ifdef FALLOCATE
> +#ifdef HAVE_LINUX_FALLOC_H
> int e;
> pathname_t f;
> int fd;
> diff --git a/ltp/fsx.c b/ltp/fsx.c
> index 2f1e3e8..c36a038 100644
> --- a/ltp/fsx.c
> +++ b/ltp/fsx.c
> @@ -33,9 +33,6 @@
> #ifdef AIO
> #include <libaio.h>
> #endif
> -#ifdef FALLOCATE
> -#include <linux/falloc.h>
> -#endif
>
> #ifndef MAP_FILE
> # define MAP_FILE 0
> @@ -882,7 +879,7 @@ do_punch_hole(unsigned offset, unsigned length)
> }
> #endif
>
> -#ifdef FALLOCATE
> +#ifdef HAVE_LINUX_FALLOC_H
> /* fallocate is basically a no-op unless extending, then a lot like a truncate */
> void
> do_preallocate(unsigned offset, unsigned length)
> @@ -1139,7 +1136,7 @@ usage(void)
> " -A: Use the AIO system calls\n"
> #endif
> " -D startingop: debug output starting at specified operation\n"
> -#ifdef FALLOCATE
> +#ifdef HAVE_LINUX_FALLOC_H
> " -F: Do not use fallocate (preallocation) calls\n"
> #endif
> #ifdef FALLOC_FL_PUNCH_HOLE
> @@ -1296,7 +1293,7 @@ int aio_rw(int rw, int fd, char *buf, unsigned len, unsigned offset)
> void
> test_fallocate()
> {
> -#ifdef FALLOCATE
> +#ifdef HAVE_LINUX_FALLOC_H
> if (!lite && fallocate_calls) {
> if (fallocate(fd, 0, 0, 1) && errno == EOPNOTSUPP) {
> if(!quiet)
> @@ -1306,7 +1303,7 @@ test_fallocate()
> ftruncate(fd, 0);
> }
> }
> -#else /* ! FALLOCATE */
> +#else /* ! HAVE_LINUX_FALLOC_H */
> fallocate_calls = 0;
> #endif
>
> diff --git a/src/global.h b/src/global.h
> index e6a2c2b..8180f66 100644
> --- a/src/global.h
> +++ b/src/global.h
> @@ -149,4 +149,29 @@
> #include <sys/param.h>
> #endif
>
> +#ifdef HAVE_LINUX_FALLOC_H
> +#include <linux/falloc.h>
> +
> +#ifndef FALLOC_FL_KEEP_SIZE
> +#define FALLOC_FL_KEEP_SIZE 0x01
> +#endif
> +
> +#ifndef FALLOC_FL_PUNCH_HOLE
> +#define FALLOC_FL_PUNCH_HOLE 0x02
> #endif
> +
> +#ifndef FALLOC_FL_NO_HIDE_STALE
> +#define FALLOC_FL_NO_HIDE_STALE 0x04
> +#endif
> +
> +#ifndef FALLOC_FL_COLLAPSE_RANGE
> +#define FALLOC_FL_COLLAPSE_RANGE 0x08
> +#endif
> +
> +#ifndef FALLOC_FL_ZERO_RANGE
> +#define FALLOC_FL_ZERO_RANGE 0x10
> +#endif
> +
> +#endif /* HAVE_LINUX_FALLOC_H */
> +
> +#endif /* GLOBAL_H */
>


2014-02-28 17:40:08

by Eric Sandeen

[permalink] [raw]
Subject: Re: [PATCH 5/8] xfstests: Add fallocate zero range operation to fsstress

On 2/28/14, 10:11 AM, Lukas Czerner wrote:
> This commit adds fzero operation support for fsstress, which is meant to
> exercise fallocate FALLOC_FL_ZERO_RANGE support.
>
> Also reorganise the common fallocate code into a single do_fallocate()
> function and use flags use the right mode.
>
> Also in order to make more obvious which fallocate mode fsstress is
> testing translate fallocate flags into human readable strings.

Can you enhance that so that if it's passed a flag which isn't
in the known array, it prints the leftover values? Otherwise
they are silently dropped, which might be confusing.

Handling the case where a flag is not in the array would future-proof
it, I think.

-Eric

_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs

2014-02-28 17:55:11

by Eric Sandeen

[permalink] [raw]
Subject: Re: [PATCH 6/8] fsstress: translate flags in fiemap_f

On 2/28/14, 10:11 AM, Lukas Czerner wrote:
> Translate flags in fiemap_f output to human readable strings.

This looks fine, w/ the caveats about translate_flags that I mentioned
on the earlier patch.

Reviewed-by: Eric Sandeen <[email protected]>

> Signed-off-by: Lukas Czerner <[email protected]>
> ---
> ltp/fsstress.c | 17 +++++++++++++++--
> 1 file changed, 15 insertions(+), 2 deletions(-)
>
> diff --git a/ltp/fsstress.c b/ltp/fsstress.c
> index 24864db..869a8ac 100644
> --- a/ltp/fsstress.c
> +++ b/ltp/fsstress.c
> @@ -2252,6 +2252,18 @@ fdatasync_f(int opno, long r)
> free_pathname(&f);
> close(fd);
> }
> +
> +#ifdef HAVE_LINUX_FIEMAP_H
> +struct print_flags fiemap_flags[] = {
> + { FIEMAP_FLAG_SYNC, "SYNC"},
> + { FIEMAP_FLAG_XATTR, "XATTR"},
> + { -1, NULL}
> +};
> +
> +#define translate_fiemap_flags(mode) \
> + ({translate_flags(mode, "|", fiemap_flags);})
> +#endif
> +
> void
> fiemap_f(int opno, long r)
> {
> @@ -2314,9 +2326,10 @@ fiemap_f(int opno, long r)
>
> e = ioctl(fd, FS_IOC_FIEMAP, (unsigned long)fiemap);
> if (v)
> - printf("%d/%d: ioctl(FIEMAP) %s%s %lld %lld %x %d\n",
> + printf("%d/%d: ioctl(FIEMAP) %s%s %lld %lld (%s) %d\n",
> procid, opno, f.path, st, (long long)fiemap->fm_start,
> - (long long) fiemap->fm_length, fiemap->fm_flags, e);
> + (long long) fiemap->fm_length,
> + translate_fiemap_flags(fiemap->fm_flags), e);
> free(fiemap);
> free_pathname(&f);
> close(fd);
>

_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs

2014-02-28 18:11:47

by Eric Sandeen

[permalink] [raw]
Subject: Re: [PATCH 7/8] xfstests: Add fallocate zero range operation to fsx

On 2/28/14, 10:11 AM, Lukas Czerner wrote:
> This commit adds fallocate FALLOC_FL_ZERO_RANGE support for fsx.

and reworks/consolidates testing of which fallocate ops are available.

Couple things below

> Signed-off-by: Lukas Czerner <[email protected]>
> ---
> ltp/fsx.c | 128 +++++++++++++++++++++++++++++++++++++++++++++++---------------
> 1 file changed, 98 insertions(+), 30 deletions(-)
>
> diff --git a/ltp/fsx.c b/ltp/fsx.c
> index c36a038..5d6d198 100644
> --- a/ltp/fsx.c
> +++ b/ltp/fsx.c
> @@ -69,6 +69,7 @@ int logcount = 0; /* total ops */
> * TRUNCATE: - 4
> * FALLOCATE: - 5
> * PUNCH HOLE: - 6
> + * ZERO RANGE: - 7
> *
> * When mapped read/writes are disabled, they are simply converted to normal
> * reads and writes. When fallocate/fpunch calls are disabled, they are
> @@ -92,7 +93,8 @@ int logcount = 0; /* total ops */
> #define OP_TRUNCATE 4
> #define OP_FALLOCATE 5
> #define OP_PUNCH_HOLE 6
> -#define OP_MAX_FULL 7
> +#define OP_ZERO_RANGE 7
> +#define OP_MAX_FULL 8
>
> /* operation modifiers */
> #define OP_CLOSEOPEN 100
> @@ -139,6 +141,7 @@ int seed = 1; /* -S flag */
> int mapped_writes = 1; /* -W flag disables */
> int fallocate_calls = 1; /* -F flag disables */
> int punch_hole_calls = 1; /* -H flag disables */
> +int zero_range_calls = 1; /* -z flag disables */
> int mapped_reads = 1; /* -R flag disables it */
> int fsxgoodfd = 0;
> int o_direct; /* -Z */
> @@ -317,6 +320,14 @@ logdump(void)
> lp->args[0] + lp->args[1])
> prt("\t******PPPP");
> break;
> + case OP_ZERO_RANGE:
> + prt("ZERO 0x%x thru 0x%x\t(0x%x bytes)",
> + lp->args[0], lp->args[0] + lp->args[1] - 1,
> + lp->args[1]);
> + if (badoff >= lp->args[0] && badoff <
> + lp->args[0] + lp->args[1])
> + prt("\t******ZZZZ");
> + break;
> case OP_SKIPPED:
> prt("SKIPPED (no operation)");
> break;
> @@ -879,6 +890,65 @@ do_punch_hole(unsigned offset, unsigned length)
> }
> #endif
>
> +#ifdef FALLOC_FL_ZERO_RANGE
> +void
> +do_zero_range(unsigned offset, unsigned length)
> +{
> + unsigned end_offset;
> + int mode = FALLOC_FL_ZERO_RANGE;
> + int keep_size;
> +
> + if (length == 0) {
> + if (!quiet && testcalls > simulatedopcount)
> + prt("skipping zero length zero range\n");
> + log4(OP_SKIPPED, OP_ZERO_RANGE, offset, length);
> + return;
> + }
> +
> + keep_size = random() % 2;
> +
> + end_offset = keep_size ? 0 : offset + length;
> +
> + if (end_offset > biggest) {
> + biggest = end_offset;
> + if (!quiet && testcalls > simulatedopcount)
> + prt("zero_range to largest ever: 0x%x\n", end_offset);
> + }
> +
> + /*
> + * last arg matches fallocate string array index in logdump:
> + * 0: allocate past EOF
> + * 1: extending prealloc
> + * 2: interior prealloc
> + */
> + log4(OP_ZERO_RANGE, offset, length, (end_offset > file_size) ? (keep_size ? 0 : 1) : 2);
> +
> + if (testcalls <= simulatedopcount)
> + return;
> +
> + if ((progressinterval && testcalls % progressinterval == 0) ||
> + (debug && (monitorstart == -1 || monitorend == -1 ||
> + end_offset <= monitorend))) {
> + prt("%lu zero\tfrom 0x%x to 0x%x, (0x%x bytes)\n", testcalls,
> + offset, offset+length, length);
> + }
> + if (fallocate(fd, mode, (loff_t)offset, (loff_t)length) == -1) {
> + prt("%pzero range: %x to %x\n", offset, length);
> + prterr("do_zero_range: fallocate");
> + report_failure(161);

This "161" isn't unique; do_punch_hole and do_preallocate both use the same number.
Is that ok? I guess there are other dups too, different bug (which probably
nobody cares much about) ;)


> + }
> +
> + memset(good_buf + offset, '\0', length);
> +}
> +
> +#else
> +void
> +do_zero_range(unsigned offset, unsigned length)
> +{
> + return;
> +}
> +#endif
> +
> #ifdef HAVE_LINUX_FALLOC_H
> /* fallocate is basically a no-op unless extending, then a lot like a truncate */
> void
> @@ -1047,6 +1117,12 @@ test(void)
> goto out;
> }
> break;
> + case OP_ZERO_RANGE:
> + if (!zero_range_calls) {
> + log4(OP_SKIPPED, OP_ZERO_RANGE, offset, size);
> + goto out;
> + }
> + break;
> }
>
> switch (op) {
> @@ -1085,6 +1161,10 @@ test(void)
> TRIM_OFF_LEN(offset, size, file_size);
> do_punch_hole(offset, size);
> break;
> + case OP_ZERO_RANGE:
> + TRIM_OFF_LEN(offset, size, file_size);
> + do_zero_range(offset, size);
> + break;
> default:
> prterr("test: unknown operation");
> report_failure(42);
> @@ -1140,7 +1220,10 @@ usage(void)
> " -F: Do not use fallocate (preallocation) calls\n"
> #endif
> #ifdef FALLOC_FL_PUNCH_HOLE
> -" -H: Do not use punch hole calls\n"
> +" -H: Do not use punch hole calls\n"
> +#endif
> +#ifdef FALLOC_FL_ZERO_RANGE
> +" -E: Do not use zero range calls\n"
> #endif
> " -L: fsxLite - no file creations & no file size changes\n\
> -N numops: total # operations to do (default infinity)\n\
> @@ -1290,40 +1373,21 @@ int aio_rw(int rw, int fd, char *buf, unsigned len, unsigned offset)
>
> #endif
>
> -void
> -test_fallocate()
> +int
> +test_fallocate(int mode)
> {
> #ifdef HAVE_LINUX_FALLOC_H
> + int ret = 0;
> if (!lite && fallocate_calls) {
> - if (fallocate(fd, 0, 0, 1) && errno == EOPNOTSUPP) {
> + if (fallocate(fd, mode, 0, 1) && errno == EOPNOTSUPP) {
> if(!quiet)
> warn("main: filesystem does not support fallocate, disabling\n");

we've lost which mode isn't supported, now. Maybe you should print the
flags which didn't pass? Too bad your fancy flag stuff is in fsstress.c. ;)
or do ("does not support fallocate mode 0x%x", mode) ?


> - fallocate_calls = 0;
> } else {
> + ret = 1;
> ftruncate(fd, 0);
> }
> }
> -#else /* ! HAVE_LINUX_FALLOC_H */
> - fallocate_calls = 0;
> -#endif
> -
> -}
> -
> -void
> -test_punch_hole()
> -{
> -#ifdef FALLOC_FL_PUNCH_HOLE
> - if (!lite && punch_hole_calls) {
> - if (fallocate(fd, FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE,
> - 0, 1) && errno == EOPNOTSUPP) {
> - if(!quiet)
> - warn("main: filesystem does not support fallocate punch hole, disabling");
> - punch_hole_calls = 0;
> - } else
> - ftruncate(fd, 0);
> - }
> -#else /* ! PUNCH HOLE */
> - punch_hole_calls = 0;
> + return ret;
> #endif
> }
>
> @@ -1345,7 +1409,7 @@ main(int argc, char **argv)
>
> setvbuf(stdout, (char *)0, _IOLBF, 0); /* line buffered stdout */
>
> - while ((ch = getopt(argc, argv, "b:c:dfl:m:no:p:qr:s:t:w:xyAD:FHLN:OP:RS:WZ"))
> + while ((ch = getopt(argc, argv, "b:c:dfl:m:no:p:qr:s:t:w:xyAD:FHzLN:OP:RS:WZ"))
> != EOF)
> switch (ch) {
> case 'b':
> @@ -1445,6 +1509,9 @@ main(int argc, char **argv)
> case 'H':
> punch_hole_calls = 0;
> break;
> + case 'z':
> + zero_range_calls = 0;
> + break;
> case 'L':
> lite = 1;
> break;
> @@ -1590,8 +1657,9 @@ main(int argc, char **argv)
> } else
> check_trunc_hack();
>
> - test_fallocate();
> - test_punch_hole();
> + fallocate_calls = test_fallocate(0);
> + punch_hole_calls = test_fallocate(FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE);
> + zero_range_calls = test_fallocate(FALLOC_FL_ZERO_RANGE);

Could probably add the do_warn() stuff here, explicitly stating what got disabled.

-Eric

>
> while (numops == -1 || numops--)
> test();
>


2014-02-28 19:08:47

by Andreas Dilger

[permalink] [raw]
Subject: Re: [PATCH 7/8] xfstests: Add fallocate zero range operation to fsx

On Feb 28, 2014, at 9:11 AM, Lukas Czerner <[email protected]> wrote:
> This commit adds fallocate FALLOC_FL_ZERO_RANGE support for fsx.

It looks like this patch breaks the option handling for these
fallocate features.

> int fallocate_calls = 1; /* -F flag disables */
> int punch_hole_calls = 1; /* -H flag disables */
> +int zero_range_calls = 1; /* -z flag disables */

So these fallocate tests are on by default...

> +int
> +test_fallocate(int mode)
> {
> #ifdef HAVE_LINUX_FALLOC_H
> + int ret = 0;
> if (!lite && fallocate_calls) {
> + if (fallocate(fd, mode, 0, 1) && errno == EOPNOTSUPP) {
> if(!quiet)
> warn("main: filesystem does not support fallocate, disabling\n");
> } else {
> + ret = 1;
> ftruncate(fd, 0);
> }
> }
> #endif
> }

And this returns 1 or 0 depending if they are supported or not...

> + while ((ch = getopt(argc, argv, "b:c:dfl:m:no:p:qr:s:t:w:xyAD:FHzLN:OP:RS:WZ"))
> != EOF)
> switch (ch) {
> case 'H':
> punch_hole_calls = 0;
> break;
> + case 'z':
> + zero_range_calls = 0;
> + break;

And the option parsing sets the values to zero if they are disabled,
so far, so good...

> + fallocate_calls = test_fallocate(0);
> + punch_hole_calls = test_fallocate(FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE);
> + zero_range_calls = test_fallocate(FALLOC_FL_ZERO_RANGE);

But here, the values set by option parsing are clobbered and the
tests are only enabled or disabled depending on whether the kernel
supports that feature or not. I think you need something like:

if (fallocate_calls)
fallocate_calls = test_fallocate(0);
if (punch_hole_calls)
punch_hole_calls = test_fallocate(FALLOC_FL_PUNCH_HOLE |
FALLOC_FL_KEEP_SIZE);
if (zero_range_calls)
zero_range_calls = test_fallocate(FALLOC_FL_ZERO_RANGE);

Cheers, Andreas






Attachments:
signature.asc (833.00 B)
Message signed with OpenPGP using GPGMail
(No filename) (121.00 B)
Download all attachments

2014-02-28 22:31:05

by Dave Chinner

[permalink] [raw]
Subject: Re: [PATCH 4/8] xfstests: Move fallocate include into global.h

On Fri, Feb 28, 2014 at 11:17:41AM -0600, Eric Sandeen wrote:
> On 2/28/14, 10:11 AM, Lukas Czerner wrote:
> > Move the inclusion of falloc.h with all it's possible defines for the
> > fallocate mode into global.h header file so we do not have to include
> > and define it manually in every tool using fallocate.
> >
> > Signed-off-by: Lukas Czerner <[email protected]>
>
> I like the direction, but I think this changes behavior a little bit.
>
> #ifdef FALLOCATE came from an autoconf macro:
>
> AC_DEFUN([AC_PACKAGE_WANT_FALLOCATE],
> [ AC_MSG_CHECKING([for fallocate])
> AC_TRY_LINK([
> #define _GNU_SOURCE
> #define _FILE_OFFSET_BITS 64
> #include <fcntl.h>
> #include <linux/falloc.h> ],
> [ fallocate(0, 0, 0, 0); ],
> [ have_fallocate=true; AC_MSG_RESULT(yes) ],
> [ have_fallocate=false; AC_MSG_RESULT(no) ])
> AC_SUBST(have_fallocate)
> ])
>
> (at least I think so?)

Not quite. autoconf defines "have_fallocate" to match the variable
name in the AC_SUBST() macro above. The makefiles do this:

include/builddefs.in:HAVE_FALLOCATE = @have_fallocate@
include/builddefs.in:HAVE_FALLOCATE = @have_fallocate@

to define HAVE_FALLOCATE at the makefile level, and then they do
this to pass it into the C source:

ltp/Makefile:ifeq ($(HAVE_FALLOCATE), true)
ltp/Makefile:LCFLAGS += -DFALLOCATE

src/Makefile:ifeq ($(HAVE_FALLOCATE), true)
src/Makefile:LCFLAGS += -DHAVE_FALLOCATE

> and so #ifdef FALLOCATE meant that
> an fallocate syscall actually exists. With your changes,
> the test is now whether the fallocate *header* exists.

It actually tests both, because if header doesn't exist, the compile
of the test stub will fail in the macro will fail. So, no change
there, really.

> falloc.h is part of kernel-headers, not glibc. So it's
> possible that there's a divergence between the two.

Right, which is why we need to test both ;)

> I think it's probably ok. Build-time checks should
> determine whether we are able to _build_ and yours do that.
> Each caller of fallocate (or each test using it) then probably
> needs to ensure that the functionality it wants is actually
> available at runtime and handle it if not.
>
> So I'll give this a
>
> Reviewed-by: Eric Sandeen <[email protected]>
>
> but maybe the above rambling will ring alarm bells for
> someone else... ;)

I need to look at it all in more detail. I thought I'd just explain
exactly what was happening with autoconf here...

Cheers,

Dave.
--
Dave Chinner
[email protected]

2014-03-03 12:16:28

by Lukas Czerner

[permalink] [raw]
Subject: Re: [PATCH 5/8] xfstests: Add fallocate zero range operation to fsstress

On Fri, 28 Feb 2014, Eric Sandeen wrote:

> Date: Fri, 28 Feb 2014 11:40:08 -0600
> From: Eric Sandeen <[email protected]>
> To: Lukas Czerner <[email protected]>, [email protected]
> Cc: [email protected], [email protected]
> Subject: Re: [PATCH 5/8] xfstests: Add fallocate zero range operation to
> fsstress
>
> On 2/28/14, 10:11 AM, Lukas Czerner wrote:
> > This commit adds fzero operation support for fsstress, which is meant to
> > exercise fallocate FALLOC_FL_ZERO_RANGE support.
> >
> > Also reorganise the common fallocate code into a single do_fallocate()
> > function and use flags use the right mode.
> >
> > Also in order to make more obvious which fallocate mode fsstress is
> > testing translate fallocate flags into human readable strings.
>
> Can you enhance that so that if it's passed a flag which isn't
> in the known array, it prints the leftover values? Otherwise
> they are silently dropped, which might be confusing.
>
> Handling the case where a flag is not in the array would future-proof
> it, I think.
>
> -Eric

Yes, I can do that. The only reason I've left this out was to force
people to actually update it when they update the test with new
flag.

Thanks!
-Lukas

2014-03-03 12:21:03

by Lukas Czerner

[permalink] [raw]
Subject: Re: [PATCH 7/8] xfstests: Add fallocate zero range operation to fsx

On Fri, 28 Feb 2014, Andreas Dilger wrote:

> Date: Fri, 28 Feb 2014 12:08:47 -0700
> From: Andreas Dilger <[email protected]>
> To: Lukas Czerner <[email protected]>
> Cc: [email protected], [email protected], [email protected]
> Subject: Re: [PATCH 7/8] xfstests: Add fallocate zero range operation to fsx
>
> On Feb 28, 2014, at 9:11 AM, Lukas Czerner <[email protected]> wrote:
> > This commit adds fallocate FALLOC_FL_ZERO_RANGE support for fsx.
>
> It looks like this patch breaks the option handling for these
> fallocate features.
>
> > int fallocate_calls = 1; /* -F flag disables */
> > int punch_hole_calls = 1; /* -H flag disables */
> > +int zero_range_calls = 1; /* -z flag disables */
>
> So these fallocate tests are on by default...
>
> > +int
> > +test_fallocate(int mode)
> > {
> > #ifdef HAVE_LINUX_FALLOC_H
> > + int ret = 0;
> > if (!lite && fallocate_calls) {
^^^^^^^^^^^^^^^

Right, I forgot about this.


> > + if (fallocate(fd, mode, 0, 1) && errno == EOPNOTSUPP) {
> > if(!quiet)
> > warn("main: filesystem does not support fallocate, disabling\n");
> > } else {
> > + ret = 1;
> > ftruncate(fd, 0);
> > }
> > }
> > #endif
> > }
>
> And this returns 1 or 0 depending if they are supported or not...
>
> > + while ((ch = getopt(argc, argv, "b:c:dfl:m:no:p:qr:s:t:w:xyAD:FHzLN:OP:RS:WZ"))
> > != EOF)
> > switch (ch) {
> > case 'H':
> > punch_hole_calls = 0;
> > break;
> > + case 'z':
> > + zero_range_calls = 0;
> > + break;
>
> And the option parsing sets the values to zero if they are disabled,
> so far, so good...
>
> > + fallocate_calls = test_fallocate(0);
> > + punch_hole_calls = test_fallocate(FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE);
> > + zero_range_calls = test_fallocate(FALLOC_FL_ZERO_RANGE);
>
> But here, the values set by option parsing are clobbered and the
> tests are only enabled or disabled depending on whether the kernel
> supports that feature or not. I think you need something like:

Right, and the 'fallocate_calls' test needs to disappear from
test_fallocate().

Thanks!
-Lukas

>
> if (fallocate_calls)
> fallocate_calls = test_fallocate(0);
> if (punch_hole_calls)
> punch_hole_calls = test_fallocate(FALLOC_FL_PUNCH_HOLE |
> FALLOC_FL_KEEP_SIZE);
> if (zero_range_calls)
> zero_range_calls = test_fallocate(FALLOC_FL_ZERO_RANGE);
>
> Cheers, Andreas
>
>
>
>
>
>

_______________________________________________
xfs mailing list
[email protected]
http://oss.sgi.com/mailman/listinfo/xfs