* [PATCH 08/11] common: add helpers for parent pointer tests
2023-04-06 19:16 [PATCHSET v11 00/11] fstests: adjust tests for xfs parent pointers Darrick J. Wong
@ 2023-04-06 19:43 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2023-04-06 19:43 UTC (permalink / raw)
To: zlang, djwong
Cc: Allison Henderson, Catherine Hoang, linux-xfs, fstests, guan
From: Allison Henderson <allison.henderson@oracle.com>
Add helper functions in common/parent to parse and verify parent
pointers. Also add functions to check that mkfs, kernel, and xfs_io
support parent pointers.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: add license and copyright, dont _fail tests immediately, make
sure the pptr-generated paths match the dir-generated paths]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
common/parent | 209 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
common/rc | 3 +
common/xfs | 12 +++
3 files changed, 224 insertions(+)
create mode 100644 common/parent
diff --git a/common/parent b/common/parent
new file mode 100644
index 0000000000..f849e4b27c
--- /dev/null
+++ b/common/parent
@@ -0,0 +1,209 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2023, Oracle and/or its affiliates. All Rights Reserved.
+#
+# Parent pointer common functions
+#
+
+#
+# parse_parent_pointer parents parent_inode parent_pointer_name
+#
+# Given a list of parent pointers, find the record that matches
+# the given inode and filename
+#
+# inputs:
+# parents : A list of parent pointers in the format of:
+# inode/generation/name_length/name
+# parent_inode : The parent inode to search for
+# parent_name : The parent name to search for
+#
+# outputs:
+# PPINO : Parent pointer inode
+# PPGEN : Parent pointer generation
+# PPNAME : Parent pointer name
+# PPNAME_LEN : Parent pointer name length
+#
+_parse_parent_pointer()
+{
+ local parents=$1
+ local pino=$2
+ local parent_pointer_name=$3
+
+ local found=0
+
+ # Find the entry that has the same inode as the parent
+ # and parse out the entry info
+ while IFS=\/ read PPINO PPGEN PPNAME_LEN PPNAME; do
+ if [ "$PPINO" != "$pino" ]; then
+ continue
+ fi
+
+ if [ "$PPNAME" != "$parent_pointer_name" ]; then
+ continue
+ fi
+
+ found=1
+ break
+ done <<< $(echo "$parents")
+
+ # Check to see if we found anything
+ # We do not fail the test because we also use this
+ # routine to verify when parent pointers should
+ # be removed or updated (ie a rename or a move
+ # operation changes your parent pointer)
+ if [ $found -eq "0" ]; then
+ return 1
+ fi
+
+ # Verify the parent pointer name length is correct
+ if [ "$PPNAME_LEN" -ne "${#parent_pointer_name}" ]
+ then
+ echo "*** Bad parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ fi
+
+ #return sucess
+ return 0
+}
+
+#
+# _verify_parent parent_path parent_pointer_name child_path
+#
+# Verify that the given child path lists the given parent as a parent pointer
+# and that the parent pointer name matches the given name
+#
+# Examples:
+#
+# #simple example
+# mkdir testfolder1
+# touch testfolder1/file1
+# verify_parent testfolder1 file1 testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder1"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1"
+#
+#
+# #hardlink example
+# mkdir testfolder1
+# mkdir testfolder2
+# touch testfolder1/file1
+# ln testfolder1/file1 testfolder2/file1_ln
+# verify_parent testfolder2 file1_ln testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder2"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1_ln"
+#
+_verify_parent()
+{
+ local parent_path=$1
+ local parent_pointer_name=$2
+ local child_path=$3
+
+ local parent_ppath="$parent_path/$parent_pointer_name"
+
+ # Verify parent exists
+ if [ ! -d $SCRATCH_MNT/$parent_path ]; then
+ echo "$SCRATCH_MNT/$parent_path not found"
+ else
+ echo "*** $parent_path OK"
+ fi
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Verify the parent pointer name exists as a child of the parent
+ if [ ! -f $SCRATCH_MNT/$parent_ppath ]; then
+ echo "$SCRATCH_MNT/$parent_ppath not found"
+ else
+ echo "*** $parent_ppath OK"
+ fi
+
+ # Get the inodes of both parent and child
+ pino="$(stat -c '%i' $SCRATCH_MNT/$parent_path)"
+ cino="$(stat -c '%i' $SCRATCH_MNT/$child_path)"
+
+ # Get all the parent pointers of the child
+ parents=($($XFS_IO_PROG -x -c \
+ "parent -f -i $pino -n $parent_pointer_name" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ echo "No parent pointers found for $child_path"
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pointer_name
+
+ # If we didnt find one, bail out
+ if [ $? -ne 0 ]; then
+ echo "No parent pointer record found for $parent_path"\
+ "in $child_path"
+ fi
+
+ # Verify the inode generated by the parent pointer name is
+ # the same as the child inode
+ pppino="$(stat -c '%i' $SCRATCH_MNT/$parent_ppath)"
+ if [ $cino -ne $pppino ]
+ then
+ echo "Bad parent pointer name value for $child_path."\
+ "$SCRATCH_MNT/$parent_ppath belongs to inode $PPPINO,"\
+ "but should be $cino"
+ fi
+
+ # Make sure path printing works by checking that the paths returned
+ # all point to the same inode.
+ local tgt="$SCRATCH_MNT/$child_path"
+ $XFS_IO_PROG -x -c 'parent -p' "$tgt" | while read pptr_path; do
+ test "$tgt" -ef "$pptr_path" || \
+ echo "$tgt parent pointer $pptr_path should be the same file"
+ done
+
+ echo "*** Verified parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ echo "*** Parent pointer OK for child $child_path"
+}
+
+#
+# _verify_parent parent_pointer_name pino child_path
+#
+# Verify that the given child path contains no parent pointer entry
+# for the given inode and file name
+#
+_verify_no_parent()
+{
+ local parent_pname=$1
+ local pino=$2
+ local child_path=$3
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Get all the parent pointers of the child
+ local parents=($($XFS_IO_PROG -x -c \
+ "parent -f -i $pino -n $parent_pname" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ return 0
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pname
+
+ # If we didnt find one, return sucess
+ if [ $? -ne 0 ]; then
+ return 0
+ fi
+
+ echo "Parent pointer entry found where none should:"\
+ "inode:$PPINO, gen:$PPGEN,"
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+}
diff --git a/common/rc b/common/rc
index a7e7d1f25b..bf53d62aac 100644
--- a/common/rc
+++ b/common/rc
@@ -2565,6 +2565,9 @@ _require_xfs_io_command()
echo $testio | grep -q "invalid option" && \
_notrun "xfs_io $command support is missing"
;;
+ "parent")
+ testio=`$XFS_IO_PROG -x -c "parent" $TEST_DIR 2>&1`
+ ;;
"pwrite")
# -N (RWF_NOWAIT) only works with direct vectored I/O writes
local pwrite_opts=" "
diff --git a/common/xfs b/common/xfs
index b211c7a6d8..81ac143374 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1791,3 +1791,15 @@ _xfs_discard_max_offset_kb()
$XFS_IO_PROG -c 'statfs' "$1" | \
awk '{g[$1] = $3} END {print (g["geom.bsize"] * g["geom.datablocks"] / 1024)}'
}
+
+# this test requires the xfs parent pointers feature
+#
+_require_xfs_parent()
+{
+ _scratch_mkfs_xfs_supported -n parent > /dev/null 2>&1 \
+ || _notrun "mkfs.xfs does not support parent pointers"
+ _scratch_mkfs_xfs -n parent > /dev/null 2>&1
+ _try_scratch_mount >/dev/null 2>&1 \
+ || _notrun "kernel does not support parent pointers"
+ _scratch_unmount
+}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 08/11] common: add helpers for parent pointer tests
2023-05-26 2:00 [PATCHSET RFC v12.0 00/11] fstests: adjust tests for xfs parent pointers Darrick J. Wong
@ 2023-05-26 2:04 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2023-05-26 2:04 UTC (permalink / raw)
To: zlang, djwong
Cc: Allison Henderson, Catherine Hoang, linux-xfs, fstests, guan,
allison.henderson, catherine.hoang
From: Allison Henderson <allison.henderson@oracle.com>
Add helper functions in common/parent to parse and verify parent
pointers. Also add functions to check that mkfs, kernel, and xfs_io
support parent pointers.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: add license and copyright, dont _fail tests immediately, make
sure the pptr-generated paths match the dir-generated paths]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
common/parent | 209 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
common/rc | 3 +
common/xfs | 12 +++
3 files changed, 224 insertions(+)
create mode 100644 common/parent
diff --git a/common/parent b/common/parent
new file mode 100644
index 0000000000..f849e4b27c
--- /dev/null
+++ b/common/parent
@@ -0,0 +1,209 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2023, Oracle and/or its affiliates. All Rights Reserved.
+#
+# Parent pointer common functions
+#
+
+#
+# parse_parent_pointer parents parent_inode parent_pointer_name
+#
+# Given a list of parent pointers, find the record that matches
+# the given inode and filename
+#
+# inputs:
+# parents : A list of parent pointers in the format of:
+# inode/generation/name_length/name
+# parent_inode : The parent inode to search for
+# parent_name : The parent name to search for
+#
+# outputs:
+# PPINO : Parent pointer inode
+# PPGEN : Parent pointer generation
+# PPNAME : Parent pointer name
+# PPNAME_LEN : Parent pointer name length
+#
+_parse_parent_pointer()
+{
+ local parents=$1
+ local pino=$2
+ local parent_pointer_name=$3
+
+ local found=0
+
+ # Find the entry that has the same inode as the parent
+ # and parse out the entry info
+ while IFS=\/ read PPINO PPGEN PPNAME_LEN PPNAME; do
+ if [ "$PPINO" != "$pino" ]; then
+ continue
+ fi
+
+ if [ "$PPNAME" != "$parent_pointer_name" ]; then
+ continue
+ fi
+
+ found=1
+ break
+ done <<< $(echo "$parents")
+
+ # Check to see if we found anything
+ # We do not fail the test because we also use this
+ # routine to verify when parent pointers should
+ # be removed or updated (ie a rename or a move
+ # operation changes your parent pointer)
+ if [ $found -eq "0" ]; then
+ return 1
+ fi
+
+ # Verify the parent pointer name length is correct
+ if [ "$PPNAME_LEN" -ne "${#parent_pointer_name}" ]
+ then
+ echo "*** Bad parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ fi
+
+ #return sucess
+ return 0
+}
+
+#
+# _verify_parent parent_path parent_pointer_name child_path
+#
+# Verify that the given child path lists the given parent as a parent pointer
+# and that the parent pointer name matches the given name
+#
+# Examples:
+#
+# #simple example
+# mkdir testfolder1
+# touch testfolder1/file1
+# verify_parent testfolder1 file1 testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder1"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1"
+#
+#
+# #hardlink example
+# mkdir testfolder1
+# mkdir testfolder2
+# touch testfolder1/file1
+# ln testfolder1/file1 testfolder2/file1_ln
+# verify_parent testfolder2 file1_ln testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder2"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1_ln"
+#
+_verify_parent()
+{
+ local parent_path=$1
+ local parent_pointer_name=$2
+ local child_path=$3
+
+ local parent_ppath="$parent_path/$parent_pointer_name"
+
+ # Verify parent exists
+ if [ ! -d $SCRATCH_MNT/$parent_path ]; then
+ echo "$SCRATCH_MNT/$parent_path not found"
+ else
+ echo "*** $parent_path OK"
+ fi
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Verify the parent pointer name exists as a child of the parent
+ if [ ! -f $SCRATCH_MNT/$parent_ppath ]; then
+ echo "$SCRATCH_MNT/$parent_ppath not found"
+ else
+ echo "*** $parent_ppath OK"
+ fi
+
+ # Get the inodes of both parent and child
+ pino="$(stat -c '%i' $SCRATCH_MNT/$parent_path)"
+ cino="$(stat -c '%i' $SCRATCH_MNT/$child_path)"
+
+ # Get all the parent pointers of the child
+ parents=($($XFS_IO_PROG -x -c \
+ "parent -f -i $pino -n $parent_pointer_name" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ echo "No parent pointers found for $child_path"
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pointer_name
+
+ # If we didnt find one, bail out
+ if [ $? -ne 0 ]; then
+ echo "No parent pointer record found for $parent_path"\
+ "in $child_path"
+ fi
+
+ # Verify the inode generated by the parent pointer name is
+ # the same as the child inode
+ pppino="$(stat -c '%i' $SCRATCH_MNT/$parent_ppath)"
+ if [ $cino -ne $pppino ]
+ then
+ echo "Bad parent pointer name value for $child_path."\
+ "$SCRATCH_MNT/$parent_ppath belongs to inode $PPPINO,"\
+ "but should be $cino"
+ fi
+
+ # Make sure path printing works by checking that the paths returned
+ # all point to the same inode.
+ local tgt="$SCRATCH_MNT/$child_path"
+ $XFS_IO_PROG -x -c 'parent -p' "$tgt" | while read pptr_path; do
+ test "$tgt" -ef "$pptr_path" || \
+ echo "$tgt parent pointer $pptr_path should be the same file"
+ done
+
+ echo "*** Verified parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ echo "*** Parent pointer OK for child $child_path"
+}
+
+#
+# _verify_parent parent_pointer_name pino child_path
+#
+# Verify that the given child path contains no parent pointer entry
+# for the given inode and file name
+#
+_verify_no_parent()
+{
+ local parent_pname=$1
+ local pino=$2
+ local child_path=$3
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Get all the parent pointers of the child
+ local parents=($($XFS_IO_PROG -x -c \
+ "parent -f -i $pino -n $parent_pname" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ return 0
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pname
+
+ # If we didnt find one, return sucess
+ if [ $? -ne 0 ]; then
+ return 0
+ fi
+
+ echo "Parent pointer entry found where none should:"\
+ "inode:$PPINO, gen:$PPGEN,"
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+}
diff --git a/common/rc b/common/rc
index a86be288ac..0f9aeceea6 100644
--- a/common/rc
+++ b/common/rc
@@ -2634,6 +2634,9 @@ _require_xfs_io_command()
echo $testio | grep -q "invalid option" && \
_notrun "xfs_io $command support is missing"
;;
+ "parent")
+ testio=`$XFS_IO_PROG -x -c "parent" $TEST_DIR 2>&1`
+ ;;
"pwrite")
# -N (RWF_NOWAIT) only works with direct vectored I/O writes
local pwrite_opts=" "
diff --git a/common/xfs b/common/xfs
index f48d7306a5..c39bf392dc 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1816,3 +1816,15 @@ _xfs_discard_max_offset_kb()
$XFS_IO_PROG -c 'statfs' "$1" | \
awk '{g[$1] = $3} END {print (g["geom.bsize"] * g["geom.datablocks"] / 1024)}'
}
+
+# this test requires the xfs parent pointers feature
+#
+_require_xfs_parent()
+{
+ _scratch_mkfs_xfs_supported -n parent > /dev/null 2>&1 \
+ || _notrun "mkfs.xfs does not support parent pointers"
+ _scratch_mkfs_xfs -n parent > /dev/null 2>&1
+ _try_scratch_mount >/dev/null 2>&1 \
+ || _notrun "kernel does not support parent pointers"
+ _scratch_unmount
+}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 08/11] common: add helpers for parent pointer tests
2023-12-31 19:59 [PATCHSET v13.0 1/3] fstests: adjust tests for xfs parent pointers Darrick J. Wong
@ 2023-12-27 13:48 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2023-12-27 13:48 UTC (permalink / raw)
To: zlang, djwong
Cc: Allison Henderson, Catherine Hoang, fstests, catherine.hoang,
allison.henderson, guan, linux-xfs
From: Allison Henderson <allison.henderson@oracle.com>
Add helper functions in common/parent to parse and verify parent
pointers. Also add functions to check that mkfs, kernel, and xfs_io
support parent pointers.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: add license and copyright, dont _fail tests immediately, make
sure the pptr-generated paths match the dir-generated paths]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
common/parent | 209 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
common/rc | 3 +
common/xfs | 12 +++
3 files changed, 224 insertions(+)
create mode 100644 common/parent
diff --git a/common/parent b/common/parent
new file mode 100644
index 0000000000..3f7ac4ca35
--- /dev/null
+++ b/common/parent
@@ -0,0 +1,209 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle and/or its affiliates. All Rights Reserved.
+#
+# Parent pointer common functions
+#
+
+#
+# parse_parent_pointer parents parent_inode parent_pointer_name
+#
+# Given a list of parent pointers, find the record that matches
+# the given inode and filename
+#
+# inputs:
+# parents : A list of parent pointers in the format of:
+# inode/generation/name_length/name
+# parent_inode : The parent inode to search for
+# parent_name : The parent name to search for
+#
+# outputs:
+# PPINO : Parent pointer inode
+# PPGEN : Parent pointer generation
+# PPNAME : Parent pointer name
+# PPNAME_LEN : Parent pointer name length
+#
+_parse_parent_pointer()
+{
+ local parents=$1
+ local pino=$2
+ local parent_pointer_name=$3
+
+ local found=0
+
+ # Find the entry that has the same inode as the parent
+ # and parse out the entry info
+ while IFS=\/ read PPINO PPGEN PPNAME_LEN PPNAME; do
+ if [ "$PPINO" != "$pino" ]; then
+ continue
+ fi
+
+ if [ "$PPNAME" != "$parent_pointer_name" ]; then
+ continue
+ fi
+
+ found=1
+ break
+ done <<< $(echo "$parents")
+
+ # Check to see if we found anything
+ # We do not fail the test because we also use this
+ # routine to verify when parent pointers should
+ # be removed or updated (ie a rename or a move
+ # operation changes your parent pointer)
+ if [ $found -eq "0" ]; then
+ return 1
+ fi
+
+ # Verify the parent pointer name length is correct
+ if [ "$PPNAME_LEN" -ne "${#parent_pointer_name}" ]
+ then
+ echo "*** Bad parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ fi
+
+ #return sucess
+ return 0
+}
+
+#
+# _verify_parent parent_path parent_pointer_name child_path
+#
+# Verify that the given child path lists the given parent as a parent pointer
+# and that the parent pointer name matches the given name
+#
+# Examples:
+#
+# #simple example
+# mkdir testfolder1
+# touch testfolder1/file1
+# verify_parent testfolder1 file1 testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder1"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1"
+#
+#
+# #hardlink example
+# mkdir testfolder1
+# mkdir testfolder2
+# touch testfolder1/file1
+# ln testfolder1/file1 testfolder2/file1_ln
+# verify_parent testfolder2 file1_ln testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder2"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1_ln"
+#
+_verify_parent()
+{
+ local parent_path=$1
+ local parent_pointer_name=$2
+ local child_path=$3
+
+ local parent_ppath="$parent_path/$parent_pointer_name"
+
+ # Verify parent exists
+ if [ ! -d $SCRATCH_MNT/$parent_path ]; then
+ echo "$SCRATCH_MNT/$parent_path not found"
+ else
+ echo "*** $parent_path OK"
+ fi
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Verify the parent pointer name exists as a child of the parent
+ if [ ! -f $SCRATCH_MNT/$parent_ppath ]; then
+ echo "$SCRATCH_MNT/$parent_ppath not found"
+ else
+ echo "*** $parent_ppath OK"
+ fi
+
+ # Get the inodes of both parent and child
+ pino="$(stat -c '%i' $SCRATCH_MNT/$parent_path)"
+ cino="$(stat -c '%i' $SCRATCH_MNT/$child_path)"
+
+ # Get all the parent pointers of the child
+ parents=($($XFS_IO_PROG -x -c \
+ "parent -f -i $pino -n $parent_pointer_name" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ echo "No parent pointers found for $child_path"
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pointer_name
+
+ # If we didnt find one, bail out
+ if [ $? -ne 0 ]; then
+ echo "No parent pointer record found for $parent_path"\
+ "in $child_path"
+ fi
+
+ # Verify the inode generated by the parent pointer name is
+ # the same as the child inode
+ pppino="$(stat -c '%i' $SCRATCH_MNT/$parent_ppath)"
+ if [ $cino -ne $pppino ]
+ then
+ echo "Bad parent pointer name value for $child_path."\
+ "$SCRATCH_MNT/$parent_ppath belongs to inode $PPPINO,"\
+ "but should be $cino"
+ fi
+
+ # Make sure path printing works by checking that the paths returned
+ # all point to the same inode.
+ local tgt="$SCRATCH_MNT/$child_path"
+ $XFS_IO_PROG -x -c 'parent -p' "$tgt" | while read pptr_path; do
+ test "$tgt" -ef "$pptr_path" || \
+ echo "$tgt parent pointer $pptr_path should be the same file"
+ done
+
+ echo "*** Verified parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ echo "*** Parent pointer OK for child $child_path"
+}
+
+#
+# _verify_parent parent_pointer_name pino child_path
+#
+# Verify that the given child path contains no parent pointer entry
+# for the given inode and file name
+#
+_verify_no_parent()
+{
+ local parent_pname=$1
+ local pino=$2
+ local child_path=$3
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Get all the parent pointers of the child
+ local parents=($($XFS_IO_PROG -x -c \
+ "parent -f -i $pino -n $parent_pname" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ return 0
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pname
+
+ # If we didnt find one, return sucess
+ if [ $? -ne 0 ]; then
+ return 0
+ fi
+
+ echo "Parent pointer entry found where none should:"\
+ "inode:$PPINO, gen:$PPGEN,"
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+}
diff --git a/common/rc b/common/rc
index 0898ac08eb..f760eedc26 100644
--- a/common/rc
+++ b/common/rc
@@ -2656,6 +2656,9 @@ _require_xfs_io_command()
echo $testio | grep -q "invalid option" && \
_notrun "xfs_io $command support is missing"
;;
+ "parent")
+ testio=`$XFS_IO_PROG -x -c "parent" $TEST_DIR 2>&1`
+ ;;
"pwrite")
# -N (RWF_NOWAIT) only works with direct vectored I/O writes
local pwrite_opts=" "
diff --git a/common/xfs b/common/xfs
index 88fa6fb55a..f77d4639b9 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1831,3 +1831,15 @@ _xfs_force_no_pptrs()
MKFS_OPTIONS="$MKFS_OPTIONS -n parent=0"
}
+
+# this test requires the xfs parent pointers feature
+#
+_require_xfs_parent()
+{
+ _scratch_mkfs_xfs_supported -n parent > /dev/null 2>&1 \
+ || _notrun "mkfs.xfs does not support parent pointers"
+ _scratch_mkfs_xfs -n parent > /dev/null 2>&1
+ _try_scratch_mount >/dev/null 2>&1 \
+ || _notrun "kernel does not support parent pointers"
+ _scratch_unmount
+}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 08/11] common: add helpers for parent pointer tests
2024-06-18 0:46 [PATCHSET v13.5 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
@ 2024-06-18 0:51 ` Darrick J. Wong
2024-06-19 6:17 ` Christoph Hellwig
0 siblings, 1 reply; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-18 0:51 UTC (permalink / raw)
To: djwong, zlang
Cc: Allison Henderson, Catherine Hoang, fstests, guan, linux-xfs,
allison.henderson, catherine.hoang
From: Allison Henderson <allison.henderson@oracle.com>
Add helper functions in common/parent to parse and verify parent
pointers. Also add functions to check that mkfs, kernel, and xfs_io
support parent pointers.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: add license and copyright, dont _fail tests immediately, make
sure the pptr-generated paths match the dir-generated paths]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
common/parent | 209 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
common/rc | 3 +
common/xfs | 12 +++
3 files changed, 224 insertions(+)
create mode 100644 common/parent
diff --git a/common/parent b/common/parent
new file mode 100644
index 0000000000..5ef0172bef
--- /dev/null
+++ b/common/parent
@@ -0,0 +1,209 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle and/or its affiliates. All Rights Reserved.
+#
+# Parent pointer common functions
+#
+
+#
+# parse_parent_pointer parents parent_inode parent_pointer_name
+#
+# Given a list of parent pointers, find the record that matches
+# the given inode and filename
+#
+# inputs:
+# parents : A list of parent pointers in the format of:
+# inode/generation/name_length/name
+# parent_inode : The parent inode to search for
+# parent_name : The parent name to search for
+#
+# outputs:
+# PPINO : Parent pointer inode
+# PPGEN : Parent pointer generation
+# PPNAME : Parent pointer name
+# PPNAME_LEN : Parent pointer name length
+#
+_parse_parent_pointer()
+{
+ local parents=$1
+ local pino=$2
+ local parent_pointer_name=$3
+
+ local found=0
+
+ # Find the entry that has the same inode as the parent
+ # and parse out the entry info
+ while IFS=':' read PPINO PPGEN PPNAME_LEN PPNAME; do
+ if [ "$PPINO" != "$pino" ]; then
+ continue
+ fi
+
+ if [ "$PPNAME" != "$parent_pointer_name" ]; then
+ continue
+ fi
+
+ found=1
+ break
+ done <<< $(echo "$parents")
+
+ # Check to see if we found anything
+ # We do not fail the test because we also use this
+ # routine to verify when parent pointers should
+ # be removed or updated (ie a rename or a move
+ # operation changes your parent pointer)
+ if [ $found -eq "0" ]; then
+ return 1
+ fi
+
+ # Verify the parent pointer name length is correct
+ if [ "$PPNAME_LEN" -ne "${#parent_pointer_name}" ]
+ then
+ echo "*** Bad parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ fi
+
+ #return sucess
+ return 0
+}
+
+#
+# _verify_parent parent_path parent_pointer_name child_path
+#
+# Verify that the given child path lists the given parent as a parent pointer
+# and that the parent pointer name matches the given name
+#
+# Examples:
+#
+# #simple example
+# mkdir testfolder1
+# touch testfolder1/file1
+# verify_parent testfolder1 file1 testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder1"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1"
+#
+#
+# #hardlink example
+# mkdir testfolder1
+# mkdir testfolder2
+# touch testfolder1/file1
+# ln testfolder1/file1 testfolder2/file1_ln
+# verify_parent testfolder2 file1_ln testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder2"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1_ln"
+#
+_verify_parent()
+{
+ local parent_path=$1
+ local parent_pointer_name=$2
+ local child_path=$3
+
+ local parent_ppath="$parent_path/$parent_pointer_name"
+
+ # Verify parent exists
+ if [ ! -d $SCRATCH_MNT/$parent_path ]; then
+ echo "$SCRATCH_MNT/$parent_path not found"
+ else
+ echo "*** $parent_path OK"
+ fi
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Verify the parent pointer name exists as a child of the parent
+ if [ ! -f $SCRATCH_MNT/$parent_ppath ]; then
+ echo "$SCRATCH_MNT/$parent_ppath not found"
+ else
+ echo "*** $parent_ppath OK"
+ fi
+
+ # Get the inodes of both parent and child
+ pino="$(stat -c '%i' $SCRATCH_MNT/$parent_path)"
+ cino="$(stat -c '%i' $SCRATCH_MNT/$child_path)"
+
+ # Get all the parent pointers of the child
+ parents=($($XFS_IO_PROG -x -c \
+ "parent -s -i $pino -n $parent_pointer_name" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ echo "No parent pointers found for $child_path"
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pointer_name
+
+ # If we didnt find one, bail out
+ if [ $? -ne 0 ]; then
+ echo "No parent pointer record found for $parent_path"\
+ "in $child_path"
+ fi
+
+ # Verify the inode generated by the parent pointer name is
+ # the same as the child inode
+ pppino="$(stat -c '%i' $SCRATCH_MNT/$parent_ppath)"
+ if [ $cino -ne $pppino ]
+ then
+ echo "Bad parent pointer name value for $child_path."\
+ "$SCRATCH_MNT/$parent_ppath belongs to inode $PPPINO,"\
+ "but should be $cino"
+ fi
+
+ # Make sure path printing works by checking that the paths returned
+ # all point to the same inode.
+ local tgt="$SCRATCH_MNT/$child_path"
+ $XFS_IO_PROG -x -c 'parent -p' "$tgt" | while read pptr_path; do
+ test "$tgt" -ef "$pptr_path" || \
+ echo "$tgt parent pointer $pptr_path should be the same file"
+ done
+
+ echo "*** Verified parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ echo "*** Parent pointer OK for child $child_path"
+}
+
+#
+# _verify_parent parent_pointer_name pino child_path
+#
+# Verify that the given child path contains no parent pointer entry
+# for the given inode and file name
+#
+_verify_no_parent()
+{
+ local parent_pname=$1
+ local pino=$2
+ local child_path=$3
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Get all the parent pointers of the child
+ local parents=($($XFS_IO_PROG -x -c \
+ "parent -s -i $pino -n $parent_pname" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ return 0
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _parse_parent_pointer $parents $pino $parent_pname
+
+ # If we didnt find one, return sucess
+ if [ $? -ne 0 ]; then
+ return 0
+ fi
+
+ echo "Parent pointer entry found where none should:"\
+ "inode:$PPINO, gen:$PPGEN,"
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+}
diff --git a/common/rc b/common/rc
index ba26fda6e6..0e0d49b87a 100644
--- a/common/rc
+++ b/common/rc
@@ -2742,6 +2742,9 @@ _require_xfs_io_command()
echo $testio | grep -q "invalid option" && \
_notrun "xfs_io $command support is missing"
;;
+ "parent")
+ testio=`$XFS_IO_PROG -x -c "parent" $TEST_DIR 2>&1`
+ ;;
"pwrite")
# -N (RWF_NOWAIT) only works with direct vectored I/O writes
local pwrite_opts=" "
diff --git a/common/xfs b/common/xfs
index 6fc7d83251..fc1ef60dbb 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1862,3 +1862,15 @@ _xfs_force_no_pptrs()
MKFS_OPTIONS="$MKFS_OPTIONS -n parent=0"
}
+
+# this test requires the xfs parent pointers feature
+#
+_require_xfs_parent()
+{
+ _scratch_mkfs_xfs_supported -n parent > /dev/null 2>&1 \
+ || _notrun "mkfs.xfs does not support parent pointers"
+ _scratch_mkfs_xfs -n parent > /dev/null 2>&1
+ _try_scratch_mount >/dev/null 2>&1 \
+ || _notrun "kernel does not support parent pointers"
+ _scratch_unmount
+}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* Re: [PATCH 08/11] common: add helpers for parent pointer tests
2024-06-18 0:51 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
@ 2024-06-19 6:17 ` Christoph Hellwig
2024-06-19 17:28 ` Darrick J. Wong
0 siblings, 1 reply; 49+ messages in thread
From: Christoph Hellwig @ 2024-06-19 6:17 UTC (permalink / raw)
To: Darrick J. Wong
Cc: zlang, Allison Henderson, Catherine Hoang, fstests, guan,
linux-xfs
> +++ b/common/parent
Should the file and functions have an xfs_ prefix as it's all about
xfs parent pointers, which won't be portable to other file systems?
Or maybe just merge it into common/xfs?
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCH 08/11] common: add helpers for parent pointer tests
2024-06-19 6:17 ` Christoph Hellwig
@ 2024-06-19 17:28 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-19 17:28 UTC (permalink / raw)
To: Christoph Hellwig
Cc: zlang, Allison Henderson, Catherine Hoang, fstests, guan,
linux-xfs
On Tue, Jun 18, 2024 at 11:17:20PM -0700, Christoph Hellwig wrote:
> > +++ b/common/parent
>
> Should the file and functions have an xfs_ prefix as it's all about
> xfs parent pointers, which won't be portable to other file systems?
> Or maybe just merge it into common/xfs?
I've been trying not to add to the clutter in common/xfs -- except for
the three parent pointers tests, nobody else needs those helpers. I
don't want to make every xfs fstest parse that stuff.
I'll prefix the pptr helpers though.
--D
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHBOMB] fstests: catch us up to 6.10
@ 2024-06-20 20:50 Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET 1/6] xfsprogs: scale shards on ssds Darrick J. Wong
` (6 more replies)
0 siblings, 7 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:50 UTC (permalink / raw)
To: Zorro Lang, Christoph Hellwig; +Cc: fstests, linux-xfs
Hi everyone,
This patchbomb are all the fixes that xfs needs to bring fstests up to
date with what's in 6.10-rc. Except for these two patches:
[PATCHSET v30.7 2/6] fstests: atomic file updates
[PATCH 03/11] generic/709,710: rework these for exchangerange vs.
[PATCH 04/11] generic/711,xfs/537: actually fork these tests for
everything else in here is fully reviewed and ready for PRs.
--D
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHSET 1/6] xfsprogs: scale shards on ssds
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
@ 2024-06-20 20:52 ` Darrick J. Wong
2024-06-20 20:54 ` [PATCH 1/1] xfs: test scaling of the mkfs concurrency options Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (5 subsequent siblings)
6 siblings, 1 reply; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:52 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
Hi all,
For a long time, the maintainers have had a gut feeling that we could
optimize performance of XFS filesystems on non-mechanical storage by
scaling the number of allocation groups to be a multiple of the CPU
count.
With modern ~2022 hardware, it is common for systems to have more than
four CPU cores and non-striped SSDs ranging in size from 256GB to 4TB.
The default mkfs geometry still defaults to 4 AGs regardless of core
count, which was settled on in the age of spinning rust.
This patchset adds a different computation for AG count and log size
that is based entirely on a desired level of concurrency. If we detect
storage that is non-rotational (or the sysadmin provides a CLI option),
then we will try to match the AG count to the CPU count to minimize AGF
contention and make the log large enough to minimize grant head
contention.
If you're going to start using this code, I strongly recommend pulling
from my git trees, which are linked below.
This has been running on the djcloud for months with no problems. Enjoy!
Comments and questions are, as always, welcome.
--D
xfsprogs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfsprogs-dev.git/log/?h=mkfs-scale-geo-on-ssds
fstests git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfstests-dev.git/log/?h=mkfs-scale-geo-on-ssds
---
Commits in this patchset:
* xfs: test scaling of the mkfs concurrency options
---
tests/xfs/1842 | 55 ++++++++++++++
tests/xfs/1842.cfg | 4 +
tests/xfs/1842.out.lba1024 | 177 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1842.out.lba2048 | 177 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1842.out.lba4096 | 177 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1842.out.lba512 | 177 ++++++++++++++++++++++++++++++++++++++++++++
6 files changed, 767 insertions(+)
create mode 100755 tests/xfs/1842
create mode 100644 tests/xfs/1842.cfg
create mode 100644 tests/xfs/1842.out.lba1024
create mode 100644 tests/xfs/1842.out.lba2048
create mode 100644 tests/xfs/1842.out.lba4096
create mode 100644 tests/xfs/1842.out.lba512
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHSET v30.7 2/6] fstests: atomic file updates
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET 1/6] xfsprogs: scale shards on ssds Darrick J. Wong
@ 2024-06-20 20:52 ` Darrick J. Wong
2024-06-20 20:54 ` [PATCH 01/11] misc: split swapext and exchangerange Darrick J. Wong
` (10 more replies)
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (4 subsequent siblings)
6 siblings, 11 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:52 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
Hi all,
This series creates a new XFS_IOC_EXCHANGE_RANGE ioctl to exchange
ranges of bytes between two files atomically.
This new functionality enables data storage programs to stage and commit
file updates such that reader programs will see either the old contents
or the new contents in their entirety, with no chance of torn writes. A
successful call completion guarantees that the new contents will be seen
even if the system fails.
The ability to exchange file fork mappings between files in this manner
is critical to supporting online filesystem repair, which is built upon
the strategy of constructing a clean copy of a damaged structure and
committing the new structure into the metadata file atomically. The
ioctls exist to facilitate testing of the new functionality and to
enable future application program designs.
User programs will be able to update files atomically by opening an
O_TMPFILE, reflinking the source file to it, making whatever updates
they want to make, and exchange the relevant ranges of the temp file
with the original file. If the updates are aligned with the file block
size, a new (since v2) flag provides for exchanging only the written
areas. Note that application software must quiesce writes to the file
while it stages an atomic update. This will be addressed by a
subsequent series.
This mechanism solves the clunkiness of two existing atomic file update
mechanisms: for O_TRUNC + rewrite, this eliminates the brief period
where other programs can see an empty file. For create tempfile +
rename, the need to copy file attributes and extended attributes for
each file update is eliminated.
However, this method introduces its own awkwardness -- any program
initiating an exchange now needs to have a way to signal to other
programs that the file contents have changed. For file access mediated
via read and write, fanotify or inotify are probably sufficient. For
mmaped files, that may not be fast enough.
The reference implementation in XFS creates a new log incompat feature
and log intent items to track high level progress of swapping ranges of
two files and finish interrupted work if the system goes down. Sample
code can be found in the corresponding changes to xfs_io to exercise the
use case mentioned above.
Note that this function is /not/ the O_DIRECT atomic untorn file writes
concept that has also been floating around for years. It is also not
the RWF_ATOMIC patchset that has been shared. This RFC is constructed
entirely in software, which means that there are no limitations other
than the general filesystem limits.
As a side note, the original motivation behind the kernel functionality
is online repair of file-based metadata. The atomic file content
exchange is implemented as an atomic exchange of file fork mappings,
which means that we can implement online reconstruction of extended
attributes and directories by building a new one in another inode and
exchanging the contents.
Subsequent patchsets adapt the online filesystem repair code to use
atomic file exchanges. This enables repair functions to construct a
clean copy of a directory, xattr information, symbolic links, realtime
bitmaps, and realtime summary information in a temporary inode. If this
completes successfully, the new contents can be committed atomically
into the inode being repaired. This is essential to avoid making
corruption problems worse if the system goes down in the middle of
running repair.
For userspace, this series also includes the userspace pieces needed to
test the new functionality, and a sample implementation of atomic file
updates.
If you're going to start using this code, I strongly recommend pulling
from my git trees, which are linked below.
This has been running on the djcloud for months with no problems. Enjoy!
Comments and questions are, as always, welcome.
--D
kernel git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-linux.git/log/?h=atomic-file-updates
xfsprogs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfsprogs-dev.git/log/?h=atomic-file-updates
fstests git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfstests-dev.git/log/?h=atomic-file-updates
xfsdocs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-documentation.git/log/?h=atomic-file-updates
---
Commits in this patchset:
* misc: split swapext and exchangerange
* misc: change xfs_io -c swapext to exchangerange
* generic/709,710: rework these for exchangerange vs. quota testing
* generic/711,xfs/537: actually fork these tests for exchange-range
* generic/717: remove obsolete check
* ltp/{fsstress,fsx}: make the exchangerange naming consistent
* misc: flip HAVE_XFS_IOC_EXCHANGE_RANGE logic
* src/fiexchange.h: update XFS_IOC_EXCHANGE_RANGE definitions
* xfs/122: fix for exchrange conversion
* xfs/206: screen out exchange-range from golden output
* exchangerange: make sure that we don't swap unwritten extents unless they're part of a rt extent
---
common/rc | 2
common/xfs | 2
configure.ac | 2
include/builddefs.in | 2
ltp/Makefile | 4 -
ltp/fsstress.c | 34 +++----
ltp/fsx.c | 43 +++------
m4/package_xfslibs.m4 | 15 ++-
src/Makefile | 4 -
src/fiexchange.h | 84 ++++-------------
src/global.h | 12 ++
src/vfs/Makefile | 4 -
src/xfsfind.c | 1
tests/generic/1221 | 45 +++++++++
tests/generic/1221.out | 2
tests/generic/709 | 12 +-
tests/generic/710 | 14 +--
tests/generic/710.out | 2
tests/generic/711 | 4 -
tests/generic/712 | 10 +-
tests/generic/713 | 42 ++++-----
tests/generic/713.out | 38 ++++----
tests/generic/714 | 40 ++++----
tests/generic/714.out | 34 ++++---
tests/generic/715 | 26 +++--
tests/generic/715.out | 14 +--
tests/generic/716 | 4 -
tests/generic/717 | 39 ++++----
tests/generic/717.out | 32 +++----
tests/generic/718 | 12 +-
tests/generic/718.out | 2
tests/generic/719 | 4 -
tests/generic/720 | 10 +-
tests/generic/721 | 2
tests/generic/722 | 8 +-
tests/generic/723 | 12 +-
tests/generic/724 | 10 +-
tests/generic/725 | 4 -
tests/generic/726 | 4 -
tests/generic/727 | 4 -
tests/xfs/1213 | 73 +++++++++++++++
tests/xfs/1213.out | 2
tests/xfs/1214 | 232 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1214.out | 2
tests/xfs/1215 | 89 ++++++++++++++++++
tests/xfs/1215.out | 13 +++
tests/xfs/122.out | 6 +
tests/xfs/206 | 1
tests/xfs/300 | 2
tests/xfs/443 | 4 -
tests/xfs/789 | 4 -
tests/xfs/790 | 10 +-
tests/xfs/790.out | 2
tests/xfs/791 | 10 +-
tests/xfs/791.out | 2
tests/xfs/792 | 4 -
tests/xfs/795 | 2
57 files changed, 748 insertions(+), 349 deletions(-)
create mode 100755 tests/generic/1221
create mode 100644 tests/generic/1221.out
create mode 100755 tests/xfs/1213
create mode 100644 tests/xfs/1213.out
create mode 100755 tests/xfs/1214
create mode 100644 tests/xfs/1214.out
create mode 100755 tests/xfs/1215
create mode 100644 tests/xfs/1215.out
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET 1/6] xfsprogs: scale shards on ssds Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
@ 2024-06-20 20:53 ` Darrick J. Wong
2024-06-20 20:57 ` [PATCH 01/11] generic: test recovery of extended attribute updates Darrick J. Wong
` (10 more replies)
2024-06-20 20:53 ` [PATCHSET v30.7 4/6] xfs: detect and correct directory tree structures Darrick J. Wong
` (3 subsequent siblings)
6 siblings, 11 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:53 UTC (permalink / raw)
To: djwong, zlang
Cc: Allison Henderson, Christoph Hellwig, Catherine Hoang, fstests,
allison.henderson, catherine.hoang, linux-xfs
Hi all,
These are the test adjustments that are required for parent pointers.
There's also a few new tests to ensure that the GETPARENTS ioctl (and
file extent can cross an rtgroup boundary.
The best advantage for rtgroups will become evident later when we get to
adding rmap and reflink to the realtime volume, since the geometry
constraints are the same for rt groups and AGs. Hence we can reuse all
that code directly.
If you're going to start using this code, I strongly recommend pulling
from my git trees, which are linked below.
This has been running on the djcloud for months with no problems. Enjoy!
Comments and questions are, as always, welcome.
--D
kernel git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-linux.git/log/?h=pptrs
xfsprogs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfsprogs-dev.git/log/?h=pptrs
fstests git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfstests-dev.git/log/?h=pptrs
xfsdocs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-documentation.git/log/?h=pptrs
---
Commits in this patchset:
* generic: test recovery of extended attribute updates
* xfs/206: filter out the parent= status from mkfs
* xfs/122: update for parent pointers
* populate: create hardlinks for parent pointers
* xfs/021: adapt golden output files for parent pointers
* xfs/{018,191,288}: disable parent pointers for these tests
* xfs/306: fix formatting failures with parent pointers
* common: add helpers for parent pointer tests
* xfs: add parent pointer test
* xfs: add multi link parent pointer test
* xfs: add parent pointer inject test
---
common/parent | 209 +++++++++
common/populate | 42 ++
common/rc | 7
common/xfs | 28 +
doc/group-names.txt | 1
src/popdir.pl | 11
tests/generic/1834 | 93 ++++
tests/generic/1834.out | 2
tests/xfs/018 | 4
tests/xfs/021 | 15 +
tests/xfs/021.cfg | 1
tests/xfs/021.out.default | 0
tests/xfs/021.out.parent | 64 +++
tests/xfs/122.out | 4
tests/xfs/1851 | 116 +++++
tests/xfs/1851.out | 69 +++
tests/xfs/1852 | 69 +++
tests/xfs/1852.out | 1002 +++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1853 | 85 ++++
tests/xfs/1853.out | 14 +
tests/xfs/191 | 3
tests/xfs/206 | 1
tests/xfs/288 | 4
tests/xfs/306 | 9
24 files changed, 1846 insertions(+), 7 deletions(-)
create mode 100644 common/parent
create mode 100755 tests/generic/1834
create mode 100644 tests/generic/1834.out
create mode 100644 tests/xfs/021.cfg
rename tests/xfs/{021.out => 021.out.default} (100%)
create mode 100644 tests/xfs/021.out.parent
create mode 100755 tests/xfs/1851
create mode 100644 tests/xfs/1851.out
create mode 100755 tests/xfs/1852
create mode 100644 tests/xfs/1852.out
create mode 100755 tests/xfs/1853
create mode 100644 tests/xfs/1853.out
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHSET v30.7 4/6] xfs: detect and correct directory tree structures
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
` (2 preceding siblings ...)
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
@ 2024-06-20 20:53 ` Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/2] common/fuzzy: stress directory tree modifications with the dirtree tester Darrick J. Wong
2024-06-20 21:00 ` [PATCH 2/2] scrub: test correction of directory tree corruptions Darrick J. Wong
2024-06-20 20:53 ` [PATCHSET v30.7 5/6] xfs_scrub: vectorize kernel calls Darrick J. Wong
` (2 subsequent siblings)
6 siblings, 2 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:53 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
Hi all,
Historically, checking the tree-ness of the directory tree structure has
not been complete. Cycles of subdirectories break the tree properties,
as do subdirectories with multiple parents. It's easy enough for DFS to
detect problems as long as one of the participants is reachable from the
root, but this technique cannot find unconnected cycles.
Directory parent pointers change that, because we can discover all of
these problems from a simple walk from a subdirectory towards the root.
For each child we start with, if the walk terminates without reaching
the root, we know the path is disconnected and ought to be attached to
the lost and found. If we find ourselves, we know this is a cycle and
can delete an incoming edge. If we find multiple paths to the root, we
know to delete an incoming edge.
Even better, once we've finished walking paths, we've identified the
good ones and know which other path(s) to remove.
If you're going to start using this code, I strongly recommend pulling
from my git trees, which are linked below.
This has been running on the djcloud for months with no problems. Enjoy!
Comments and questions are, as always, welcome.
--D
kernel git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-linux.git/log/?h=scrub-directory-tree
xfsprogs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfsprogs-dev.git/log/?h=scrub-directory-tree
fstests git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfstests-dev.git/log/?h=scrub-directory-tree
---
Commits in this patchset:
* common/fuzzy: stress directory tree modifications with the dirtree tester
* scrub: test correction of directory tree corruptions
---
tests/xfs/1864 | 38 +++++++++++++
tests/xfs/1864.out | 2 +
tests/xfs/1865 | 38 +++++++++++++
tests/xfs/1865.out | 2 +
tests/xfs/1866 | 122 ++++++++++++++++++++++++++++++++++++++++
tests/xfs/1866.out | 19 ++++++
tests/xfs/1867 | 133 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1867.out | 25 ++++++++
tests/xfs/1868 | 121 ++++++++++++++++++++++++++++++++++++++++
tests/xfs/1868.out | 21 +++++++
tests/xfs/1869 | 157 ++++++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1869.out | 32 +++++++++++
tests/xfs/1870 | 146 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1870.out | 30 ++++++++++
tests/xfs/1871 | 78 ++++++++++++++++++++++++++
tests/xfs/1871.out | 2 +
16 files changed, 966 insertions(+)
create mode 100755 tests/xfs/1864
create mode 100644 tests/xfs/1864.out
create mode 100755 tests/xfs/1865
create mode 100644 tests/xfs/1865.out
create mode 100755 tests/xfs/1866
create mode 100644 tests/xfs/1866.out
create mode 100755 tests/xfs/1867
create mode 100644 tests/xfs/1867.out
create mode 100755 tests/xfs/1868
create mode 100644 tests/xfs/1868.out
create mode 100755 tests/xfs/1869
create mode 100644 tests/xfs/1869.out
create mode 100755 tests/xfs/1870
create mode 100644 tests/xfs/1870.out
create mode 100755 tests/xfs/1871
create mode 100644 tests/xfs/1871.out
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHSET v30.7 5/6] xfs_scrub: vectorize kernel calls
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
` (3 preceding siblings ...)
2024-06-20 20:53 ` [PATCHSET v30.7 4/6] xfs: detect and correct directory tree structures Darrick J. Wong
@ 2024-06-20 20:53 ` Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/1] xfs/122: update for vectored scrub Darrick J. Wong
2024-06-20 20:53 ` [PATCHSET 6/6] fstests: minor fixes for 6.10-rc1 Darrick J. Wong
2024-06-21 17:20 ` [PATCHBOMB] fstests: catch us up to 6.10 Zorro Lang
6 siblings, 1 reply; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:53 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
Hi all,
Create a vectorized version of the metadata scrub and repair ioctl, and
adapt xfs_scrub to use that. This is an experiment to measure overhead
and to try refactoring xfs_scrub.
If you're going to start using this code, I strongly recommend pulling
from my git trees, which are linked below.
This has been running on the djcloud for months with no problems. Enjoy!
Comments and questions are, as always, welcome.
--D
kernel git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-linux.git/log/?h=vectorized-scrub
xfsprogs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfsprogs-dev.git/log/?h=vectorized-scrub
fstests git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfstests-dev.git/log/?h=vectorized-scrub
---
Commits in this patchset:
* xfs/122: update for vectored scrub
---
tests/xfs/122.out | 2 ++
1 file changed, 2 insertions(+)
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCHSET 6/6] fstests: minor fixes for 6.10-rc1
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
` (4 preceding siblings ...)
2024-06-20 20:53 ` [PATCHSET v30.7 5/6] xfs_scrub: vectorize kernel calls Darrick J. Wong
@ 2024-06-20 20:53 ` Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/2] xfs/348: partially revert dbcc549317 ("xfs/348: golden output is not correct") Darrick J. Wong
2024-06-20 21:01 ` [PATCH 2/2] generic: test creating and removing symlink xattrs Darrick J. Wong
2024-06-21 17:20 ` [PATCHBOMB] fstests: catch us up to 6.10 Zorro Lang
6 siblings, 2 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:53 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, hch, linux-xfs
Hi all,
Here are some fixes for the stuff that just got merged for 6.10-rc1.
If you're going to start using this code, I strongly recommend pulling
from my git trees, which are linked below.
This has been running on the djcloud for months with no problems. Enjoy!
Comments and questions are, as always, welcome.
--D
kernel git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfs-linux.git/log/?h=xfs-6.10-fixes
xfsprogs git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfsprogs-dev.git/log/?h=xfs-6.10-fixes
fstests git tree:
https://git.kernel.org/cgit/linux/kernel/git/djwong/xfstests-dev.git/log/?h=xfs-6.10-fixes
---
Commits in this patchset:
* xfs/348: partially revert dbcc549317 ("xfs/348: golden output is not correct")
* generic: test creating and removing symlink xattrs
---
tests/generic/1836 | 58 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/generic/1836.out | 2 ++
tests/xfs/348.out | 2 +-
3 files changed, 61 insertions(+), 1 deletion(-)
create mode 100755 tests/generic/1836
create mode 100644 tests/generic/1836.out
^ permalink raw reply [flat|nested] 49+ messages in thread
* [PATCH 1/1] xfs: test scaling of the mkfs concurrency options
2024-06-20 20:52 ` [PATCHSET 1/6] xfsprogs: scale shards on ssds Darrick J. Wong
@ 2024-06-20 20:54 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:54 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Make sure that the AG count and log size scale up with the new
concurrency options to mkfs.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/1842 | 55 ++++++++++++++
tests/xfs/1842.cfg | 4 +
tests/xfs/1842.out.lba1024 | 177 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1842.out.lba2048 | 177 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1842.out.lba4096 | 177 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1842.out.lba512 | 177 ++++++++++++++++++++++++++++++++++++++++++++
6 files changed, 767 insertions(+)
create mode 100755 tests/xfs/1842
create mode 100644 tests/xfs/1842.cfg
create mode 100644 tests/xfs/1842.out.lba1024
create mode 100644 tests/xfs/1842.out.lba2048
create mode 100644 tests/xfs/1842.out.lba4096
create mode 100644 tests/xfs/1842.out.lba512
diff --git a/tests/xfs/1842 b/tests/xfs/1842
new file mode 100755
index 0000000000..8180ca7a6e
--- /dev/null
+++ b/tests/xfs/1842
@@ -0,0 +1,55 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1842
+#
+# mkfs concurrency test - ensure the log and agsize scaling works for various
+# concurrency= parameters
+#
+. ./common/preamble
+_begin_fstest log metadata auto quick
+
+# Import common functions.
+. ./common/filter
+. ./common/reflink
+
+_cleanup()
+{
+ cd /
+ rm -r -f $tmp.* $loop_file
+}
+
+# real QA test starts here
+_supported_fs xfs
+
+_require_test
+_require_loop
+$MKFS_XFS_PROG 2>&1 | grep -q concurrency || \
+ _notrun "mkfs does not support concurrency options"
+
+test_dev_lbasize=$(blockdev --getss $TEST_DEV)
+seqfull=$0
+_link_out_file "lba${test_dev_lbasize}"
+
+loop_file=$TEST_DIR/$seq.loop
+
+rm -f "$loop_file"
+for sz in 16M 512M 1G 2G 16G 64G 256G 512G 1T 2T 4T 16T 64T 256T 512T 1P; do
+ for cpus in 2 4 8 16 32 40 64 96 160 512; do
+ truncate -s "$sz" "$loop_file"
+ echo "sz $sz cpus $cpus" >> $seqres.full
+ echo "-----------------" >> $seqres.full
+
+ $MKFS_XFS_PROG -f -N "$loop_file" -d concurrency=$cpus -l concurrency=$cpus &> $tmp.mkfsout
+ cat $tmp.mkfsout >> $seqres.full
+
+ _filter_mkfs > /dev/null 2> $tmp.mkfs < $tmp.mkfsout
+ . $tmp.mkfs
+ echo "sz $sz cpus $cpus agcount $agcount logblocks $lblocks"
+ done
+ echo "-----------------"
+done
+
+status=0
+exit
diff --git a/tests/xfs/1842.cfg b/tests/xfs/1842.cfg
new file mode 100644
index 0000000000..0678032432
--- /dev/null
+++ b/tests/xfs/1842.cfg
@@ -0,0 +1,4 @@
+lba512: lba512
+lba1024: lba1024
+lba2048: lba2048
+lba4096: lba4096
diff --git a/tests/xfs/1842.out.lba1024 b/tests/xfs/1842.out.lba1024
new file mode 100644
index 0000000000..758cdf51a8
--- /dev/null
+++ b/tests/xfs/1842.out.lba1024
@@ -0,0 +1,177 @@
+QA output created by 1842
+sz 16M cpus 2 agcount 1 logblocks 2766
+sz 16M cpus 4 agcount 1 logblocks 2766
+sz 16M cpus 8 agcount 1 logblocks 2766
+sz 16M cpus 16 agcount 1 logblocks 2766
+sz 16M cpus 32 agcount 1 logblocks 2766
+sz 16M cpus 40 agcount 1 logblocks 2766
+sz 16M cpus 64 agcount 1 logblocks 2766
+sz 16M cpus 96 agcount 1 logblocks 2766
+sz 16M cpus 160 agcount 1 logblocks 2766
+sz 16M cpus 512 agcount 1 logblocks 2766
+-----------------
+sz 512M cpus 2 agcount 4 logblocks 16384
+sz 512M cpus 4 agcount 4 logblocks 16384
+sz 512M cpus 8 agcount 4 logblocks 16384
+sz 512M cpus 16 agcount 4 logblocks 16384
+sz 512M cpus 32 agcount 4 logblocks 16384
+sz 512M cpus 40 agcount 4 logblocks 16384
+sz 512M cpus 64 agcount 4 logblocks 16384
+sz 512M cpus 96 agcount 4 logblocks 16384
+sz 512M cpus 160 agcount 4 logblocks 16384
+sz 512M cpus 512 agcount 4 logblocks 16384
+-----------------
+sz 1G cpus 2 agcount 4 logblocks 16384
+sz 1G cpus 4 agcount 4 logblocks 16384
+sz 1G cpus 8 agcount 4 logblocks 16384
+sz 1G cpus 16 agcount 4 logblocks 22698
+sz 1G cpus 32 agcount 4 logblocks 45396
+sz 1G cpus 40 agcount 4 logblocks 56745
+sz 1G cpus 64 agcount 4 logblocks 65524
+sz 1G cpus 96 agcount 4 logblocks 65524
+sz 1G cpus 160 agcount 4 logblocks 65524
+sz 1G cpus 512 agcount 4 logblocks 65524
+-----------------
+sz 2G cpus 2 agcount 4 logblocks 16384
+sz 2G cpus 4 agcount 4 logblocks 16384
+sz 2G cpus 8 agcount 4 logblocks 16384
+sz 2G cpus 16 agcount 4 logblocks 25866
+sz 2G cpus 32 agcount 4 logblocks 51732
+sz 2G cpus 40 agcount 4 logblocks 64665
+sz 2G cpus 64 agcount 4 logblocks 103464
+sz 2G cpus 96 agcount 4 logblocks 131060
+sz 2G cpus 160 agcount 4 logblocks 131060
+sz 2G cpus 512 agcount 4 logblocks 131060
+-----------------
+sz 16G cpus 2 agcount 4 logblocks 16384
+sz 16G cpus 4 agcount 4 logblocks 16384
+sz 16G cpus 8 agcount 4 logblocks 16384
+sz 16G cpus 16 agcount 4 logblocks 25866
+sz 16G cpus 32 agcount 4 logblocks 51732
+sz 16G cpus 40 agcount 4 logblocks 64665
+sz 16G cpus 64 agcount 4 logblocks 103464
+sz 16G cpus 96 agcount 4 logblocks 155196
+sz 16G cpus 160 agcount 4 logblocks 258660
+sz 16G cpus 512 agcount 4 logblocks 521728
+-----------------
+sz 64G cpus 2 agcount 4 logblocks 16384
+sz 64G cpus 4 agcount 4 logblocks 16384
+sz 64G cpus 8 agcount 8 logblocks 16384
+sz 64G cpus 16 agcount 16 logblocks 25866
+sz 64G cpus 32 agcount 16 logblocks 51732
+sz 64G cpus 40 agcount 16 logblocks 64665
+sz 64G cpus 64 agcount 16 logblocks 103464
+sz 64G cpus 96 agcount 16 logblocks 155196
+sz 64G cpus 160 agcount 16 logblocks 258660
+sz 64G cpus 512 agcount 16 logblocks 521728
+-----------------
+sz 256G cpus 2 agcount 4 logblocks 32768
+sz 256G cpus 4 agcount 4 logblocks 32768
+sz 256G cpus 8 agcount 8 logblocks 32768
+sz 256G cpus 16 agcount 16 logblocks 32768
+sz 256G cpus 32 agcount 32 logblocks 51732
+sz 256G cpus 40 agcount 40 logblocks 64665
+sz 256G cpus 64 agcount 64 logblocks 103464
+sz 256G cpus 96 agcount 64 logblocks 155196
+sz 256G cpus 160 agcount 64 logblocks 258660
+sz 256G cpus 512 agcount 64 logblocks 521728
+-----------------
+sz 512G cpus 2 agcount 4 logblocks 65536
+sz 512G cpus 4 agcount 4 logblocks 65536
+sz 512G cpus 8 agcount 8 logblocks 65536
+sz 512G cpus 16 agcount 16 logblocks 65536
+sz 512G cpus 32 agcount 32 logblocks 65536
+sz 512G cpus 40 agcount 40 logblocks 65535
+sz 512G cpus 64 agcount 64 logblocks 103464
+sz 512G cpus 96 agcount 96 logblocks 155196
+sz 512G cpus 160 agcount 128 logblocks 258660
+sz 512G cpus 512 agcount 128 logblocks 521728
+-----------------
+sz 1T cpus 2 agcount 4 logblocks 131072
+sz 1T cpus 4 agcount 4 logblocks 131072
+sz 1T cpus 8 agcount 8 logblocks 131072
+sz 1T cpus 16 agcount 16 logblocks 131072
+sz 1T cpus 32 agcount 32 logblocks 131072
+sz 1T cpus 40 agcount 40 logblocks 131071
+sz 1T cpus 64 agcount 64 logblocks 131072
+sz 1T cpus 96 agcount 96 logblocks 155196
+sz 1T cpus 160 agcount 160 logblocks 258660
+sz 1T cpus 512 agcount 256 logblocks 521728
+-----------------
+sz 2T cpus 2 agcount 4 logblocks 262144
+sz 2T cpus 4 agcount 4 logblocks 262144
+sz 2T cpus 8 agcount 8 logblocks 262144
+sz 2T cpus 16 agcount 16 logblocks 262144
+sz 2T cpus 32 agcount 32 logblocks 262144
+sz 2T cpus 40 agcount 40 logblocks 262143
+sz 2T cpus 64 agcount 64 logblocks 262144
+sz 2T cpus 96 agcount 96 logblocks 262143
+sz 2T cpus 160 agcount 160 logblocks 262143
+sz 2T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 4T cpus 2 agcount 4 logblocks 521728
+sz 4T cpus 4 agcount 4 logblocks 521728
+sz 4T cpus 8 agcount 8 logblocks 521728
+sz 4T cpus 16 agcount 16 logblocks 521728
+sz 4T cpus 32 agcount 32 logblocks 521728
+sz 4T cpus 40 agcount 40 logblocks 521728
+sz 4T cpus 64 agcount 64 logblocks 521728
+sz 4T cpus 96 agcount 96 logblocks 521728
+sz 4T cpus 160 agcount 160 logblocks 521728
+sz 4T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 16T cpus 2 agcount 16 logblocks 521728
+sz 16T cpus 4 agcount 16 logblocks 521728
+sz 16T cpus 8 agcount 16 logblocks 521728
+sz 16T cpus 16 agcount 16 logblocks 521728
+sz 16T cpus 32 agcount 32 logblocks 521728
+sz 16T cpus 40 agcount 40 logblocks 521728
+sz 16T cpus 64 agcount 64 logblocks 521728
+sz 16T cpus 96 agcount 96 logblocks 521728
+sz 16T cpus 160 agcount 160 logblocks 521728
+sz 16T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 64T cpus 2 agcount 64 logblocks 521728
+sz 64T cpus 4 agcount 64 logblocks 521728
+sz 64T cpus 8 agcount 64 logblocks 521728
+sz 64T cpus 16 agcount 64 logblocks 521728
+sz 64T cpus 32 agcount 64 logblocks 521728
+sz 64T cpus 40 agcount 64 logblocks 521728
+sz 64T cpus 64 agcount 64 logblocks 521728
+sz 64T cpus 96 agcount 96 logblocks 521728
+sz 64T cpus 160 agcount 160 logblocks 521728
+sz 64T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 256T cpus 2 agcount 256 logblocks 521728
+sz 256T cpus 4 agcount 256 logblocks 521728
+sz 256T cpus 8 agcount 256 logblocks 521728
+sz 256T cpus 16 agcount 256 logblocks 521728
+sz 256T cpus 32 agcount 256 logblocks 521728
+sz 256T cpus 40 agcount 256 logblocks 521728
+sz 256T cpus 64 agcount 256 logblocks 521728
+sz 256T cpus 96 agcount 256 logblocks 521728
+sz 256T cpus 160 agcount 256 logblocks 521728
+sz 256T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 512T cpus 2 agcount 512 logblocks 521728
+sz 512T cpus 4 agcount 512 logblocks 521728
+sz 512T cpus 8 agcount 512 logblocks 521728
+sz 512T cpus 16 agcount 512 logblocks 521728
+sz 512T cpus 32 agcount 512 logblocks 521728
+sz 512T cpus 40 agcount 512 logblocks 521728
+sz 512T cpus 64 agcount 512 logblocks 521728
+sz 512T cpus 96 agcount 512 logblocks 521728
+sz 512T cpus 160 agcount 512 logblocks 521728
+sz 512T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 1P cpus 2 agcount 1024 logblocks 521728
+sz 1P cpus 4 agcount 1024 logblocks 521728
+sz 1P cpus 8 agcount 1024 logblocks 521728
+sz 1P cpus 16 agcount 1024 logblocks 521728
+sz 1P cpus 32 agcount 1024 logblocks 521728
+sz 1P cpus 40 agcount 1024 logblocks 521728
+sz 1P cpus 64 agcount 1024 logblocks 521728
+sz 1P cpus 96 agcount 1024 logblocks 521728
+sz 1P cpus 160 agcount 1024 logblocks 521728
+sz 1P cpus 512 agcount 1024 logblocks 521728
+-----------------
diff --git a/tests/xfs/1842.out.lba2048 b/tests/xfs/1842.out.lba2048
new file mode 100644
index 0000000000..5ec8e640c8
--- /dev/null
+++ b/tests/xfs/1842.out.lba2048
@@ -0,0 +1,177 @@
+QA output created by 1842
+sz 16M cpus 2 agcount 1 logblocks 2820
+sz 16M cpus 4 agcount 1 logblocks 2820
+sz 16M cpus 8 agcount 1 logblocks 2820
+sz 16M cpus 16 agcount 1 logblocks 2820
+sz 16M cpus 32 agcount 1 logblocks 2820
+sz 16M cpus 40 agcount 1 logblocks 2820
+sz 16M cpus 64 agcount 1 logblocks 2820
+sz 16M cpus 96 agcount 1 logblocks 2820
+sz 16M cpus 160 agcount 1 logblocks 2820
+sz 16M cpus 512 agcount 1 logblocks 2820
+-----------------
+sz 512M cpus 2 agcount 4 logblocks 16384
+sz 512M cpus 4 agcount 4 logblocks 16384
+sz 512M cpus 8 agcount 4 logblocks 16384
+sz 512M cpus 16 agcount 4 logblocks 16384
+sz 512M cpus 32 agcount 4 logblocks 16384
+sz 512M cpus 40 agcount 4 logblocks 16384
+sz 512M cpus 64 agcount 4 logblocks 16384
+sz 512M cpus 96 agcount 4 logblocks 16384
+sz 512M cpus 160 agcount 4 logblocks 16384
+sz 512M cpus 512 agcount 4 logblocks 16384
+-----------------
+sz 1G cpus 2 agcount 4 logblocks 16384
+sz 1G cpus 4 agcount 4 logblocks 16384
+sz 1G cpus 8 agcount 4 logblocks 16384
+sz 1G cpus 16 agcount 4 logblocks 23130
+sz 1G cpus 32 agcount 4 logblocks 46260
+sz 1G cpus 40 agcount 4 logblocks 57825
+sz 1G cpus 64 agcount 4 logblocks 65523
+sz 1G cpus 96 agcount 4 logblocks 65523
+sz 1G cpus 160 agcount 4 logblocks 65523
+sz 1G cpus 512 agcount 4 logblocks 65523
+-----------------
+sz 2G cpus 2 agcount 4 logblocks 16384
+sz 2G cpus 4 agcount 4 logblocks 16384
+sz 2G cpus 8 agcount 4 logblocks 16384
+sz 2G cpus 16 agcount 4 logblocks 26298
+sz 2G cpus 32 agcount 4 logblocks 52596
+sz 2G cpus 40 agcount 4 logblocks 65745
+sz 2G cpus 64 agcount 4 logblocks 105192
+sz 2G cpus 96 agcount 4 logblocks 131059
+sz 2G cpus 160 agcount 4 logblocks 131059
+sz 2G cpus 512 agcount 4 logblocks 131059
+-----------------
+sz 16G cpus 2 agcount 4 logblocks 16384
+sz 16G cpus 4 agcount 4 logblocks 16384
+sz 16G cpus 8 agcount 4 logblocks 16384
+sz 16G cpus 16 agcount 4 logblocks 26298
+sz 16G cpus 32 agcount 4 logblocks 52596
+sz 16G cpus 40 agcount 4 logblocks 65745
+sz 16G cpus 64 agcount 4 logblocks 105192
+sz 16G cpus 96 agcount 4 logblocks 157788
+sz 16G cpus 160 agcount 4 logblocks 262980
+sz 16G cpus 512 agcount 4 logblocks 521728
+-----------------
+sz 64G cpus 2 agcount 4 logblocks 16384
+sz 64G cpus 4 agcount 4 logblocks 16384
+sz 64G cpus 8 agcount 8 logblocks 16384
+sz 64G cpus 16 agcount 16 logblocks 26298
+sz 64G cpus 32 agcount 16 logblocks 52596
+sz 64G cpus 40 agcount 16 logblocks 65745
+sz 64G cpus 64 agcount 16 logblocks 105192
+sz 64G cpus 96 agcount 16 logblocks 157788
+sz 64G cpus 160 agcount 16 logblocks 262980
+sz 64G cpus 512 agcount 16 logblocks 521728
+-----------------
+sz 256G cpus 2 agcount 4 logblocks 32768
+sz 256G cpus 4 agcount 4 logblocks 32768
+sz 256G cpus 8 agcount 8 logblocks 32768
+sz 256G cpus 16 agcount 16 logblocks 32768
+sz 256G cpus 32 agcount 32 logblocks 52596
+sz 256G cpus 40 agcount 40 logblocks 65745
+sz 256G cpus 64 agcount 64 logblocks 105192
+sz 256G cpus 96 agcount 64 logblocks 157788
+sz 256G cpus 160 agcount 64 logblocks 262980
+sz 256G cpus 512 agcount 64 logblocks 521728
+-----------------
+sz 512G cpus 2 agcount 4 logblocks 65536
+sz 512G cpus 4 agcount 4 logblocks 65536
+sz 512G cpus 8 agcount 8 logblocks 65536
+sz 512G cpus 16 agcount 16 logblocks 65536
+sz 512G cpus 32 agcount 32 logblocks 65536
+sz 512G cpus 40 agcount 40 logblocks 65745
+sz 512G cpus 64 agcount 64 logblocks 105192
+sz 512G cpus 96 agcount 96 logblocks 157788
+sz 512G cpus 160 agcount 128 logblocks 262980
+sz 512G cpus 512 agcount 128 logblocks 521728
+-----------------
+sz 1T cpus 2 agcount 4 logblocks 131072
+sz 1T cpus 4 agcount 4 logblocks 131072
+sz 1T cpus 8 agcount 8 logblocks 131072
+sz 1T cpus 16 agcount 16 logblocks 131072
+sz 1T cpus 32 agcount 32 logblocks 131072
+sz 1T cpus 40 agcount 40 logblocks 131071
+sz 1T cpus 64 agcount 64 logblocks 131072
+sz 1T cpus 96 agcount 96 logblocks 157788
+sz 1T cpus 160 agcount 160 logblocks 262980
+sz 1T cpus 512 agcount 256 logblocks 521728
+-----------------
+sz 2T cpus 2 agcount 4 logblocks 262144
+sz 2T cpus 4 agcount 4 logblocks 262144
+sz 2T cpus 8 agcount 8 logblocks 262144
+sz 2T cpus 16 agcount 16 logblocks 262144
+sz 2T cpus 32 agcount 32 logblocks 262144
+sz 2T cpus 40 agcount 40 logblocks 262143
+sz 2T cpus 64 agcount 64 logblocks 262144
+sz 2T cpus 96 agcount 96 logblocks 262143
+sz 2T cpus 160 agcount 160 logblocks 262980
+sz 2T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 4T cpus 2 agcount 4 logblocks 521728
+sz 4T cpus 4 agcount 4 logblocks 521728
+sz 4T cpus 8 agcount 8 logblocks 521728
+sz 4T cpus 16 agcount 16 logblocks 521728
+sz 4T cpus 32 agcount 32 logblocks 521728
+sz 4T cpus 40 agcount 40 logblocks 521728
+sz 4T cpus 64 agcount 64 logblocks 521728
+sz 4T cpus 96 agcount 96 logblocks 521728
+sz 4T cpus 160 agcount 160 logblocks 521728
+sz 4T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 16T cpus 2 agcount 16 logblocks 521728
+sz 16T cpus 4 agcount 16 logblocks 521728
+sz 16T cpus 8 agcount 16 logblocks 521728
+sz 16T cpus 16 agcount 16 logblocks 521728
+sz 16T cpus 32 agcount 32 logblocks 521728
+sz 16T cpus 40 agcount 40 logblocks 521728
+sz 16T cpus 64 agcount 64 logblocks 521728
+sz 16T cpus 96 agcount 96 logblocks 521728
+sz 16T cpus 160 agcount 160 logblocks 521728
+sz 16T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 64T cpus 2 agcount 64 logblocks 521728
+sz 64T cpus 4 agcount 64 logblocks 521728
+sz 64T cpus 8 agcount 64 logblocks 521728
+sz 64T cpus 16 agcount 64 logblocks 521728
+sz 64T cpus 32 agcount 64 logblocks 521728
+sz 64T cpus 40 agcount 64 logblocks 521728
+sz 64T cpus 64 agcount 64 logblocks 521728
+sz 64T cpus 96 agcount 96 logblocks 521728
+sz 64T cpus 160 agcount 160 logblocks 521728
+sz 64T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 256T cpus 2 agcount 256 logblocks 521728
+sz 256T cpus 4 agcount 256 logblocks 521728
+sz 256T cpus 8 agcount 256 logblocks 521728
+sz 256T cpus 16 agcount 256 logblocks 521728
+sz 256T cpus 32 agcount 256 logblocks 521728
+sz 256T cpus 40 agcount 256 logblocks 521728
+sz 256T cpus 64 agcount 256 logblocks 521728
+sz 256T cpus 96 agcount 256 logblocks 521728
+sz 256T cpus 160 agcount 256 logblocks 521728
+sz 256T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 512T cpus 2 agcount 512 logblocks 521728
+sz 512T cpus 4 agcount 512 logblocks 521728
+sz 512T cpus 8 agcount 512 logblocks 521728
+sz 512T cpus 16 agcount 512 logblocks 521728
+sz 512T cpus 32 agcount 512 logblocks 521728
+sz 512T cpus 40 agcount 512 logblocks 521728
+sz 512T cpus 64 agcount 512 logblocks 521728
+sz 512T cpus 96 agcount 512 logblocks 521728
+sz 512T cpus 160 agcount 512 logblocks 521728
+sz 512T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 1P cpus 2 agcount 1024 logblocks 521728
+sz 1P cpus 4 agcount 1024 logblocks 521728
+sz 1P cpus 8 agcount 1024 logblocks 521728
+sz 1P cpus 16 agcount 1024 logblocks 521728
+sz 1P cpus 32 agcount 1024 logblocks 521728
+sz 1P cpus 40 agcount 1024 logblocks 521728
+sz 1P cpus 64 agcount 1024 logblocks 521728
+sz 1P cpus 96 agcount 1024 logblocks 521728
+sz 1P cpus 160 agcount 1024 logblocks 521728
+sz 1P cpus 512 agcount 1024 logblocks 521728
+-----------------
diff --git a/tests/xfs/1842.out.lba4096 b/tests/xfs/1842.out.lba4096
new file mode 100644
index 0000000000..6f5376f508
--- /dev/null
+++ b/tests/xfs/1842.out.lba4096
@@ -0,0 +1,177 @@
+QA output created by 1842
+sz 16M cpus 2 agcount 1 logblocks 2928
+sz 16M cpus 4 agcount 1 logblocks 2928
+sz 16M cpus 8 agcount 1 logblocks 2928
+sz 16M cpus 16 agcount 1 logblocks 2928
+sz 16M cpus 32 agcount 1 logblocks 2928
+sz 16M cpus 40 agcount 1 logblocks 2928
+sz 16M cpus 64 agcount 1 logblocks 2928
+sz 16M cpus 96 agcount 1 logblocks 2928
+sz 16M cpus 160 agcount 1 logblocks 2928
+sz 16M cpus 512 agcount 1 logblocks 2928
+-----------------
+sz 512M cpus 2 agcount 4 logblocks 16384
+sz 512M cpus 4 agcount 4 logblocks 16384
+sz 512M cpus 8 agcount 4 logblocks 16384
+sz 512M cpus 16 agcount 4 logblocks 16384
+sz 512M cpus 32 agcount 4 logblocks 16384
+sz 512M cpus 40 agcount 4 logblocks 16384
+sz 512M cpus 64 agcount 4 logblocks 16384
+sz 512M cpus 96 agcount 4 logblocks 16384
+sz 512M cpus 160 agcount 4 logblocks 16384
+sz 512M cpus 512 agcount 4 logblocks 16384
+-----------------
+sz 1G cpus 2 agcount 4 logblocks 16384
+sz 1G cpus 4 agcount 4 logblocks 16384
+sz 1G cpus 8 agcount 4 logblocks 16384
+sz 1G cpus 16 agcount 4 logblocks 23994
+sz 1G cpus 32 agcount 4 logblocks 47988
+sz 1G cpus 40 agcount 4 logblocks 59985
+sz 1G cpus 64 agcount 4 logblocks 65521
+sz 1G cpus 96 agcount 4 logblocks 65521
+sz 1G cpus 160 agcount 4 logblocks 65521
+sz 1G cpus 512 agcount 4 logblocks 65521
+-----------------
+sz 2G cpus 2 agcount 4 logblocks 16384
+sz 2G cpus 4 agcount 4 logblocks 16384
+sz 2G cpus 8 agcount 4 logblocks 16384
+sz 2G cpus 16 agcount 4 logblocks 27162
+sz 2G cpus 32 agcount 4 logblocks 54324
+sz 2G cpus 40 agcount 4 logblocks 67905
+sz 2G cpus 64 agcount 4 logblocks 108648
+sz 2G cpus 96 agcount 4 logblocks 131057
+sz 2G cpus 160 agcount 4 logblocks 131057
+sz 2G cpus 512 agcount 4 logblocks 131057
+-----------------
+sz 16G cpus 2 agcount 4 logblocks 16384
+sz 16G cpus 4 agcount 4 logblocks 16384
+sz 16G cpus 8 agcount 4 logblocks 16384
+sz 16G cpus 16 agcount 4 logblocks 27162
+sz 16G cpus 32 agcount 4 logblocks 54324
+sz 16G cpus 40 agcount 4 logblocks 67905
+sz 16G cpus 64 agcount 4 logblocks 108648
+sz 16G cpus 96 agcount 4 logblocks 162972
+sz 16G cpus 160 agcount 4 logblocks 271620
+sz 16G cpus 512 agcount 4 logblocks 521728
+-----------------
+sz 64G cpus 2 agcount 4 logblocks 16384
+sz 64G cpus 4 agcount 4 logblocks 16384
+sz 64G cpus 8 agcount 8 logblocks 16384
+sz 64G cpus 16 agcount 16 logblocks 27162
+sz 64G cpus 32 agcount 16 logblocks 54324
+sz 64G cpus 40 agcount 16 logblocks 67905
+sz 64G cpus 64 agcount 16 logblocks 108648
+sz 64G cpus 96 agcount 16 logblocks 162972
+sz 64G cpus 160 agcount 16 logblocks 271620
+sz 64G cpus 512 agcount 16 logblocks 521728
+-----------------
+sz 256G cpus 2 agcount 4 logblocks 32768
+sz 256G cpus 4 agcount 4 logblocks 32768
+sz 256G cpus 8 agcount 8 logblocks 32768
+sz 256G cpus 16 agcount 16 logblocks 32768
+sz 256G cpus 32 agcount 32 logblocks 54324
+sz 256G cpus 40 agcount 40 logblocks 67905
+sz 256G cpus 64 agcount 64 logblocks 108648
+sz 256G cpus 96 agcount 64 logblocks 162972
+sz 256G cpus 160 agcount 64 logblocks 271620
+sz 256G cpus 512 agcount 64 logblocks 521728
+-----------------
+sz 512G cpus 2 agcount 4 logblocks 65536
+sz 512G cpus 4 agcount 4 logblocks 65536
+sz 512G cpus 8 agcount 8 logblocks 65536
+sz 512G cpus 16 agcount 16 logblocks 65536
+sz 512G cpus 32 agcount 32 logblocks 65536
+sz 512G cpus 40 agcount 40 logblocks 67905
+sz 512G cpus 64 agcount 64 logblocks 108648
+sz 512G cpus 96 agcount 96 logblocks 162972
+sz 512G cpus 160 agcount 128 logblocks 271620
+sz 512G cpus 512 agcount 128 logblocks 521728
+-----------------
+sz 1T cpus 2 agcount 4 logblocks 131072
+sz 1T cpus 4 agcount 4 logblocks 131072
+sz 1T cpus 8 agcount 8 logblocks 131072
+sz 1T cpus 16 agcount 16 logblocks 131072
+sz 1T cpus 32 agcount 32 logblocks 131072
+sz 1T cpus 40 agcount 40 logblocks 131071
+sz 1T cpus 64 agcount 64 logblocks 131072
+sz 1T cpus 96 agcount 96 logblocks 162972
+sz 1T cpus 160 agcount 160 logblocks 271620
+sz 1T cpus 512 agcount 256 logblocks 521728
+-----------------
+sz 2T cpus 2 agcount 4 logblocks 262144
+sz 2T cpus 4 agcount 4 logblocks 262144
+sz 2T cpus 8 agcount 8 logblocks 262144
+sz 2T cpus 16 agcount 16 logblocks 262144
+sz 2T cpus 32 agcount 32 logblocks 262144
+sz 2T cpus 40 agcount 40 logblocks 262143
+sz 2T cpus 64 agcount 64 logblocks 262144
+sz 2T cpus 96 agcount 96 logblocks 262143
+sz 2T cpus 160 agcount 160 logblocks 271620
+sz 2T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 4T cpus 2 agcount 4 logblocks 521728
+sz 4T cpus 4 agcount 4 logblocks 521728
+sz 4T cpus 8 agcount 8 logblocks 521728
+sz 4T cpus 16 agcount 16 logblocks 521728
+sz 4T cpus 32 agcount 32 logblocks 521728
+sz 4T cpus 40 agcount 40 logblocks 521728
+sz 4T cpus 64 agcount 64 logblocks 521728
+sz 4T cpus 96 agcount 96 logblocks 521728
+sz 4T cpus 160 agcount 160 logblocks 521728
+sz 4T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 16T cpus 2 agcount 16 logblocks 521728
+sz 16T cpus 4 agcount 16 logblocks 521728
+sz 16T cpus 8 agcount 16 logblocks 521728
+sz 16T cpus 16 agcount 16 logblocks 521728
+sz 16T cpus 32 agcount 32 logblocks 521728
+sz 16T cpus 40 agcount 40 logblocks 521728
+sz 16T cpus 64 agcount 64 logblocks 521728
+sz 16T cpus 96 agcount 96 logblocks 521728
+sz 16T cpus 160 agcount 160 logblocks 521728
+sz 16T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 64T cpus 2 agcount 64 logblocks 521728
+sz 64T cpus 4 agcount 64 logblocks 521728
+sz 64T cpus 8 agcount 64 logblocks 521728
+sz 64T cpus 16 agcount 64 logblocks 521728
+sz 64T cpus 32 agcount 64 logblocks 521728
+sz 64T cpus 40 agcount 64 logblocks 521728
+sz 64T cpus 64 agcount 64 logblocks 521728
+sz 64T cpus 96 agcount 96 logblocks 521728
+sz 64T cpus 160 agcount 160 logblocks 521728
+sz 64T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 256T cpus 2 agcount 256 logblocks 521728
+sz 256T cpus 4 agcount 256 logblocks 521728
+sz 256T cpus 8 agcount 256 logblocks 521728
+sz 256T cpus 16 agcount 256 logblocks 521728
+sz 256T cpus 32 agcount 256 logblocks 521728
+sz 256T cpus 40 agcount 256 logblocks 521728
+sz 256T cpus 64 agcount 256 logblocks 521728
+sz 256T cpus 96 agcount 256 logblocks 521728
+sz 256T cpus 160 agcount 256 logblocks 521728
+sz 256T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 512T cpus 2 agcount 512 logblocks 521728
+sz 512T cpus 4 agcount 512 logblocks 521728
+sz 512T cpus 8 agcount 512 logblocks 521728
+sz 512T cpus 16 agcount 512 logblocks 521728
+sz 512T cpus 32 agcount 512 logblocks 521728
+sz 512T cpus 40 agcount 512 logblocks 521728
+sz 512T cpus 64 agcount 512 logblocks 521728
+sz 512T cpus 96 agcount 512 logblocks 521728
+sz 512T cpus 160 agcount 512 logblocks 521728
+sz 512T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 1P cpus 2 agcount 1024 logblocks 521728
+sz 1P cpus 4 agcount 1024 logblocks 521728
+sz 1P cpus 8 agcount 1024 logblocks 521728
+sz 1P cpus 16 agcount 1024 logblocks 521728
+sz 1P cpus 32 agcount 1024 logblocks 521728
+sz 1P cpus 40 agcount 1024 logblocks 521728
+sz 1P cpus 64 agcount 1024 logblocks 521728
+sz 1P cpus 96 agcount 1024 logblocks 521728
+sz 1P cpus 160 agcount 1024 logblocks 521728
+sz 1P cpus 512 agcount 1024 logblocks 521728
+-----------------
diff --git a/tests/xfs/1842.out.lba512 b/tests/xfs/1842.out.lba512
new file mode 100644
index 0000000000..e28742e8ae
--- /dev/null
+++ b/tests/xfs/1842.out.lba512
@@ -0,0 +1,177 @@
+QA output created by 1842
+sz 16M cpus 2 agcount 1 logblocks 3075
+sz 16M cpus 4 agcount 1 logblocks 3075
+sz 16M cpus 8 agcount 1 logblocks 3075
+sz 16M cpus 16 agcount 1 logblocks 3075
+sz 16M cpus 32 agcount 1 logblocks 3075
+sz 16M cpus 40 agcount 1 logblocks 3075
+sz 16M cpus 64 agcount 1 logblocks 3075
+sz 16M cpus 96 agcount 1 logblocks 3075
+sz 16M cpus 160 agcount 1 logblocks 3075
+sz 16M cpus 512 agcount 1 logblocks 3075
+-----------------
+sz 512M cpus 2 agcount 4 logblocks 16384
+sz 512M cpus 4 agcount 4 logblocks 16384
+sz 512M cpus 8 agcount 4 logblocks 16384
+sz 512M cpus 16 agcount 4 logblocks 16384
+sz 512M cpus 32 agcount 4 logblocks 16384
+sz 512M cpus 40 agcount 4 logblocks 16384
+sz 512M cpus 64 agcount 4 logblocks 16384
+sz 512M cpus 96 agcount 4 logblocks 16384
+sz 512M cpus 160 agcount 4 logblocks 16384
+sz 512M cpus 512 agcount 4 logblocks 16384
+-----------------
+sz 1G cpus 2 agcount 4 logblocks 16384
+sz 1G cpus 4 agcount 4 logblocks 16384
+sz 1G cpus 8 agcount 4 logblocks 16384
+sz 1G cpus 16 agcount 4 logblocks 22482
+sz 1G cpus 32 agcount 4 logblocks 44964
+sz 1G cpus 40 agcount 4 logblocks 56205
+sz 1G cpus 64 agcount 4 logblocks 65524
+sz 1G cpus 96 agcount 4 logblocks 65524
+sz 1G cpus 160 agcount 4 logblocks 65524
+sz 1G cpus 512 agcount 4 logblocks 65524
+-----------------
+sz 2G cpus 2 agcount 4 logblocks 16384
+sz 2G cpus 4 agcount 4 logblocks 16384
+sz 2G cpus 8 agcount 4 logblocks 16384
+sz 2G cpus 16 agcount 4 logblocks 25650
+sz 2G cpus 32 agcount 4 logblocks 51300
+sz 2G cpus 40 agcount 4 logblocks 64125
+sz 2G cpus 64 agcount 4 logblocks 102600
+sz 2G cpus 96 agcount 4 logblocks 131060
+sz 2G cpus 160 agcount 4 logblocks 131060
+sz 2G cpus 512 agcount 4 logblocks 131060
+-----------------
+sz 16G cpus 2 agcount 4 logblocks 16384
+sz 16G cpus 4 agcount 4 logblocks 16384
+sz 16G cpus 8 agcount 4 logblocks 16384
+sz 16G cpus 16 agcount 4 logblocks 25650
+sz 16G cpus 32 agcount 4 logblocks 51300
+sz 16G cpus 40 agcount 4 logblocks 64125
+sz 16G cpus 64 agcount 4 logblocks 102600
+sz 16G cpus 96 agcount 4 logblocks 153900
+sz 16G cpus 160 agcount 4 logblocks 256500
+sz 16G cpus 512 agcount 4 logblocks 521728
+-----------------
+sz 64G cpus 2 agcount 4 logblocks 16384
+sz 64G cpus 4 agcount 4 logblocks 16384
+sz 64G cpus 8 agcount 8 logblocks 16384
+sz 64G cpus 16 agcount 16 logblocks 25650
+sz 64G cpus 32 agcount 16 logblocks 51300
+sz 64G cpus 40 agcount 16 logblocks 64125
+sz 64G cpus 64 agcount 16 logblocks 102600
+sz 64G cpus 96 agcount 16 logblocks 153900
+sz 64G cpus 160 agcount 16 logblocks 256500
+sz 64G cpus 512 agcount 16 logblocks 521728
+-----------------
+sz 256G cpus 2 agcount 4 logblocks 32768
+sz 256G cpus 4 agcount 4 logblocks 32768
+sz 256G cpus 8 agcount 8 logblocks 32768
+sz 256G cpus 16 agcount 16 logblocks 32768
+sz 256G cpus 32 agcount 32 logblocks 51300
+sz 256G cpus 40 agcount 40 logblocks 64125
+sz 256G cpus 64 agcount 64 logblocks 102600
+sz 256G cpus 96 agcount 64 logblocks 153900
+sz 256G cpus 160 agcount 64 logblocks 256500
+sz 256G cpus 512 agcount 64 logblocks 521728
+-----------------
+sz 512G cpus 2 agcount 4 logblocks 65536
+sz 512G cpus 4 agcount 4 logblocks 65536
+sz 512G cpus 8 agcount 8 logblocks 65536
+sz 512G cpus 16 agcount 16 logblocks 65536
+sz 512G cpus 32 agcount 32 logblocks 65536
+sz 512G cpus 40 agcount 40 logblocks 65535
+sz 512G cpus 64 agcount 64 logblocks 102600
+sz 512G cpus 96 agcount 96 logblocks 153900
+sz 512G cpus 160 agcount 128 logblocks 256500
+sz 512G cpus 512 agcount 128 logblocks 521728
+-----------------
+sz 1T cpus 2 agcount 4 logblocks 131072
+sz 1T cpus 4 agcount 4 logblocks 131072
+sz 1T cpus 8 agcount 8 logblocks 131072
+sz 1T cpus 16 agcount 16 logblocks 131072
+sz 1T cpus 32 agcount 32 logblocks 131072
+sz 1T cpus 40 agcount 40 logblocks 131071
+sz 1T cpus 64 agcount 64 logblocks 131072
+sz 1T cpus 96 agcount 96 logblocks 153900
+sz 1T cpus 160 agcount 160 logblocks 256500
+sz 1T cpus 512 agcount 256 logblocks 521728
+-----------------
+sz 2T cpus 2 agcount 4 logblocks 262144
+sz 2T cpus 4 agcount 4 logblocks 262144
+sz 2T cpus 8 agcount 8 logblocks 262144
+sz 2T cpus 16 agcount 16 logblocks 262144
+sz 2T cpus 32 agcount 32 logblocks 262144
+sz 2T cpus 40 agcount 40 logblocks 262143
+sz 2T cpus 64 agcount 64 logblocks 262144
+sz 2T cpus 96 agcount 96 logblocks 262143
+sz 2T cpus 160 agcount 160 logblocks 262143
+sz 2T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 4T cpus 2 agcount 4 logblocks 521728
+sz 4T cpus 4 agcount 4 logblocks 521728
+sz 4T cpus 8 agcount 8 logblocks 521728
+sz 4T cpus 16 agcount 16 logblocks 521728
+sz 4T cpus 32 agcount 32 logblocks 521728
+sz 4T cpus 40 agcount 40 logblocks 521728
+sz 4T cpus 64 agcount 64 logblocks 521728
+sz 4T cpus 96 agcount 96 logblocks 521728
+sz 4T cpus 160 agcount 160 logblocks 521728
+sz 4T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 16T cpus 2 agcount 16 logblocks 521728
+sz 16T cpus 4 agcount 16 logblocks 521728
+sz 16T cpus 8 agcount 16 logblocks 521728
+sz 16T cpus 16 agcount 16 logblocks 521728
+sz 16T cpus 32 agcount 32 logblocks 521728
+sz 16T cpus 40 agcount 40 logblocks 521728
+sz 16T cpus 64 agcount 64 logblocks 521728
+sz 16T cpus 96 agcount 96 logblocks 521728
+sz 16T cpus 160 agcount 160 logblocks 521728
+sz 16T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 64T cpus 2 agcount 64 logblocks 521728
+sz 64T cpus 4 agcount 64 logblocks 521728
+sz 64T cpus 8 agcount 64 logblocks 521728
+sz 64T cpus 16 agcount 64 logblocks 521728
+sz 64T cpus 32 agcount 64 logblocks 521728
+sz 64T cpus 40 agcount 64 logblocks 521728
+sz 64T cpus 64 agcount 64 logblocks 521728
+sz 64T cpus 96 agcount 96 logblocks 521728
+sz 64T cpus 160 agcount 160 logblocks 521728
+sz 64T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 256T cpus 2 agcount 256 logblocks 521728
+sz 256T cpus 4 agcount 256 logblocks 521728
+sz 256T cpus 8 agcount 256 logblocks 521728
+sz 256T cpus 16 agcount 256 logblocks 521728
+sz 256T cpus 32 agcount 256 logblocks 521728
+sz 256T cpus 40 agcount 256 logblocks 521728
+sz 256T cpus 64 agcount 256 logblocks 521728
+sz 256T cpus 96 agcount 256 logblocks 521728
+sz 256T cpus 160 agcount 256 logblocks 521728
+sz 256T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 512T cpus 2 agcount 512 logblocks 521728
+sz 512T cpus 4 agcount 512 logblocks 521728
+sz 512T cpus 8 agcount 512 logblocks 521728
+sz 512T cpus 16 agcount 512 logblocks 521728
+sz 512T cpus 32 agcount 512 logblocks 521728
+sz 512T cpus 40 agcount 512 logblocks 521728
+sz 512T cpus 64 agcount 512 logblocks 521728
+sz 512T cpus 96 agcount 512 logblocks 521728
+sz 512T cpus 160 agcount 512 logblocks 521728
+sz 512T cpus 512 agcount 512 logblocks 521728
+-----------------
+sz 1P cpus 2 agcount 1024 logblocks 521728
+sz 1P cpus 4 agcount 1024 logblocks 521728
+sz 1P cpus 8 agcount 1024 logblocks 521728
+sz 1P cpus 16 agcount 1024 logblocks 521728
+sz 1P cpus 32 agcount 1024 logblocks 521728
+sz 1P cpus 40 agcount 1024 logblocks 521728
+sz 1P cpus 64 agcount 1024 logblocks 521728
+sz 1P cpus 96 agcount 1024 logblocks 521728
+sz 1P cpus 160 agcount 1024 logblocks 521728
+sz 1P cpus 512 agcount 1024 logblocks 521728
+-----------------
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 01/11] misc: split swapext and exchangerange
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
@ 2024-06-20 20:54 ` Darrick J. Wong
2024-06-20 20:54 ` [PATCH 02/11] misc: change xfs_io -c swapext to exchangerange Darrick J. Wong
` (9 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:54 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
These two commands (and the kernel implementations) are splitting, so we
need to split the xfs_io usage.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
common/rc | 2 +-
common/xfs | 2 +-
tests/generic/709 | 2 +-
tests/generic/710 | 2 +-
tests/generic/711 | 2 +-
tests/generic/712 | 2 +-
tests/generic/713 | 4 ++--
tests/generic/714 | 4 ++--
tests/generic/715 | 4 ++--
tests/generic/716 | 2 +-
tests/generic/717 | 2 +-
tests/generic/718 | 2 +-
tests/generic/719 | 2 +-
tests/generic/720 | 2 +-
tests/generic/722 | 4 ++--
tests/generic/723 | 6 +++---
tests/generic/724 | 4 ++--
tests/generic/725 | 2 +-
tests/generic/726 | 2 +-
tests/generic/727 | 2 +-
tests/xfs/789 | 2 +-
tests/xfs/790 | 2 +-
tests/xfs/791 | 4 ++--
tests/xfs/792 | 2 +-
24 files changed, 32 insertions(+), 32 deletions(-)
diff --git a/common/rc b/common/rc
index 163041fea5..9e69af1527 100644
--- a/common/rc
+++ b/common/rc
@@ -2771,7 +2771,7 @@ _require_xfs_io_command()
_notrun "xfs_io $command $param kernel support is missing"
param_checked="$param"
;;
- "swapext")
+ "swapext"|"exchangerange")
$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 128k -b 128k' $testfile > /dev/null
$XFS_IO_PROG -f -c 'truncate 128k' $testfile.1 > /dev/null
testio=`$XFS_IO_PROG -c "$command $param $testfile.1" $testfile 2>&1`
diff --git a/common/xfs b/common/xfs
index 11481180bd..0b0863f1dc 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1823,7 +1823,7 @@ _require_xfs_scratch_atomicswap()
{
_require_xfs_mkfs_atomicswap
_require_scratch
- _require_xfs_io_command swapext '-v exchrange -a'
+ _require_xfs_io_command exchangerange
_scratch_mkfs -m reflink=1 > /dev/null
_try_scratch_mount || \
_notrun "atomicswap dependencies not supported by scratch filesystem type: $FSTYP"
diff --git a/tests/generic/709 b/tests/generic/709
index 4bd591b873..4fc938bb6a 100755
--- a/tests/generic/709
+++ b/tests/generic/709
@@ -14,7 +14,7 @@ _begin_fstest auto quick fiexchange swapext quota
. ./common/quota
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command swapext
_require_user
_require_nobody
_require_quota
diff --git a/tests/generic/710 b/tests/generic/710
index c7fca05d4c..6c6aa08f63 100755
--- a/tests/generic/710
+++ b/tests/generic/710
@@ -14,7 +14,7 @@ _begin_fstest auto quick fiexchange swapext quota
. ./common/quota
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command swapext
_require_user
_require_nobody
_require_quota
diff --git a/tests/generic/711 b/tests/generic/711
index f1318b30dd..b107f976ef 100755
--- a/tests/generic/711
+++ b/tests/generic/711
@@ -21,7 +21,7 @@ _cleanup()
. ./common/filter
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command swapext
_require_test
dir=$TEST_DIR/test-$seq
diff --git a/tests/generic/712 b/tests/generic/712
index d4a705478e..f2862c3f8e 100755
--- a/tests/generic/712
+++ b/tests/generic/712
@@ -21,7 +21,7 @@ _cleanup()
# real QA test starts here
_require_test_program punch-alternating
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_test
dir=$TEST_DIR/test-$seq
diff --git a/tests/generic/713 b/tests/generic/713
index 9b742ee0cb..b2d3260806 100755
--- a/tests/generic/713
+++ b/tests/generic/713
@@ -21,7 +21,7 @@ _cleanup()
. ./common/reflink
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange -s 64k -l 64k'
+_require_xfs_io_command exchangerange ' -s 64k -l 64k'
_require_xfs_io_command "falloc"
_require_test
@@ -36,7 +36,7 @@ filesnap() {
test_swapext_once() {
filesnap "$1: before swapext" $dir/$3 $dir/$4
- $XFS_IO_PROG -c "swapext -v exchrange $2 $dir/$3" $dir/$4
+ $XFS_IO_PROG -c "exchangerange $2 $dir/$3" $dir/$4
filesnap "$1: after swapext" $dir/$3 $dir/$4
_test_cycle_mount
filesnap "$1: after cycling mount" $dir/$3 $dir/$4
diff --git a/tests/generic/714 b/tests/generic/714
index b48a4b7d31..ea963fdfa7 100755
--- a/tests/generic/714
+++ b/tests/generic/714
@@ -22,7 +22,7 @@ _cleanup()
. ./common/reflink
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_xfs_io_command "falloc"
_require_test_reflink
@@ -37,7 +37,7 @@ filesnap() {
test_swapext_once() {
filesnap "$1: before swapext" $dir/$3 $dir/$4
- $XFS_IO_PROG -c "swapext -v exchrange $2 $dir/$3" $dir/$4
+ $XFS_IO_PROG -c "exchangerange $2 $dir/$3" $dir/$4
filesnap "$1: after swapext" $dir/$3 $dir/$4
_test_cycle_mount
filesnap "$1: after cycling mount" $dir/$3 $dir/$4
diff --git a/tests/generic/715 b/tests/generic/715
index 595953dfcf..eb164a848a 100755
--- a/tests/generic/715
+++ b/tests/generic/715
@@ -21,7 +21,7 @@ _cleanup()
. ./common/reflink
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange -s 64k -l 64k'
+_require_xfs_io_command exchangerange ' -s 64k -l 64k'
_require_test
filesnap() {
@@ -51,7 +51,7 @@ test_swapext_once() {
_pwrite_byte 0x59 0 $((blksz * b_len)) $dir/b >> $seqres.full
filesnap "$tag: before swapext" $dir/a $dir/b
- cmd="swapext -v exchrange -s $((blksz * a_off)) -d $((blksz * b_off)) $len $dir/a"
+ cmd="exchangerange -s $((blksz * a_off)) -d $((blksz * b_off)) $len $dir/a"
echo "$cmd" >> $seqres.full
$XFS_IO_PROG -c "$cmd" $dir/b
filesnap "$tag: after swapext" $dir/a $dir/b
diff --git a/tests/generic/716 b/tests/generic/716
index 25976ab898..5d3fa5e721 100755
--- a/tests/generic/716
+++ b/tests/generic/716
@@ -24,7 +24,7 @@ _cleanup()
. ./common/reflink
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate
_require_test_reflink
_require_test
diff --git a/tests/generic/717 b/tests/generic/717
index 2c45e715f4..dd2f3dcdc4 100755
--- a/tests/generic/717
+++ b/tests/generic/717
@@ -21,7 +21,7 @@ _cleanup()
. ./common/reflink
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate
_require_test
_require_scratch
diff --git a/tests/generic/718 b/tests/generic/718
index f53d1840d0..23e092df4d 100755
--- a/tests/generic/718
+++ b/tests/generic/718
@@ -21,7 +21,7 @@ _cleanup()
. ./common/reflink
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_test
dir=$TEST_DIR/test-$seq
diff --git a/tests/generic/719 b/tests/generic/719
index fe0b9d082e..70d1ae5d0c 100755
--- a/tests/generic/719
+++ b/tests/generic/719
@@ -23,7 +23,7 @@ _cleanup()
. ./common/filter
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate '-e'
_require_test
diff --git a/tests/generic/720 b/tests/generic/720
index 4db69c6921..25253968a2 100755
--- a/tests/generic/720
+++ b/tests/generic/720
@@ -20,7 +20,7 @@ _cleanup()
. ./common/filter
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_test_program punch-alternating
_require_test
diff --git a/tests/generic/722 b/tests/generic/722
index 40eab9bbb3..3ec831e708 100755
--- a/tests/generic/722
+++ b/tests/generic/722
@@ -23,7 +23,7 @@ _cleanup()
# real QA test starts here
_require_test_program "punch-alternating"
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_scratch
_require_scratch_shutdown
@@ -43,7 +43,7 @@ od -tx1 -Ad -c $SCRATCH_MNT/a > /tmp/a0
od -tx1 -Ad -c $SCRATCH_MNT/b > /tmp/b0
echo swap >> $seqres.full
-$XFS_IO_PROG -c "swapext -v exchrange -a -e -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
+$XFS_IO_PROG -c "exchangerange -e -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
_scratch_shutdown
_scratch_cycle_mount
diff --git a/tests/generic/723 b/tests/generic/723
index b452de0208..0e1de3ec1f 100755
--- a/tests/generic/723
+++ b/tests/generic/723
@@ -22,7 +22,7 @@ _cleanup()
# real QA test starts here
_require_test_program "punch-alternating"
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command exchangerange
_require_scratch
_scratch_mkfs >> $seqres.full
@@ -41,7 +41,7 @@ echo "md5 a: $old_a md5 b: $old_b" >> $seqres.full
# Test swapext with the -n option, which will do all the input parameter
# checking and return 0 without changing anything.
echo dry run swap >> $seqres.full
-$XFS_IO_PROG -c "swapext -v exchrange -n -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
+$XFS_IO_PROG -c "exchangerange -n -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
_scratch_cycle_mount
new_a=$(md5sum $SCRATCH_MNT/a | awk '{print $1}')
@@ -54,7 +54,7 @@ test $old_b = $new_b || echo "scratch file B should not have swapped"
# Do it again, but without the -n option, to prove that we can actually
# swap the file contents.
echo actual swap >> $seqres.full
-$XFS_IO_PROG -c "swapext -v exchrange -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
+$XFS_IO_PROG -c "exchangerange -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
_scratch_cycle_mount
new_a=$(md5sum $SCRATCH_MNT/a | awk '{print $1}')
diff --git a/tests/generic/724 b/tests/generic/724
index 12324fb156..9536705503 100755
--- a/tests/generic/724
+++ b/tests/generic/724
@@ -22,7 +22,7 @@ _cleanup()
. ./common/filter
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_scratch
_scratch_mkfs >> $seqres.full
@@ -42,7 +42,7 @@ md5sum $SCRATCH_MNT/b | _filter_scratch
# Test swapext. -h means skip holes in /b, and -e means operate to EOF
echo swap | tee -a $seqres.full
-$XFS_IO_PROG -c "swapext -v exchrange -f -u -h -e -a $SCRATCH_MNT/b" $SCRATCH_MNT/a
+$XFS_IO_PROG -c "exchangerange -f -u -h -e $SCRATCH_MNT/b" $SCRATCH_MNT/a
_scratch_cycle_mount
md5sum $SCRATCH_MNT/a | _filter_scratch
diff --git a/tests/generic/725 b/tests/generic/725
index bf60127b39..3c6180fcbb 100755
--- a/tests/generic/725
+++ b/tests/generic/725
@@ -22,7 +22,7 @@ _cleanup()
. ./common/filter
# real QA test starts here
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate '-e'
_require_scratch
diff --git a/tests/generic/726 b/tests/generic/726
index 4cf18bd0e5..05d8a2372a 100755
--- a/tests/generic/726
+++ b/tests/generic/726
@@ -25,7 +25,7 @@ _begin_fstest auto fiexchange swapext quick
# Modify as appropriate.
_supported_fs generic
_require_user
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate
_require_scratch
diff --git a/tests/generic/727 b/tests/generic/727
index af9612c967..4b0d5bd372 100755
--- a/tests/generic/727
+++ b/tests/generic/727
@@ -28,7 +28,7 @@ _supported_fs generic
_require_user
_require_command "$GETCAP_PROG" getcap
_require_command "$SETCAP_PROG" setcap
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate
_require_scratch
_require_attrs security
diff --git a/tests/xfs/789 b/tests/xfs/789
index b966c65119..00b98020f2 100755
--- a/tests/xfs/789
+++ b/tests/xfs/789
@@ -21,7 +21,7 @@ _cleanup()
# real QA test starts here
_supported_fs xfs
-_require_xfs_io_command swapext '-v exchrange'
+_require_xfs_io_command swapext
_require_test
# We can't do any reasonable swapping if the files we're going to create are
diff --git a/tests/xfs/790 b/tests/xfs/790
index db6ce741d7..62bbd1fea6 100755
--- a/tests/xfs/790
+++ b/tests/xfs/790
@@ -24,7 +24,7 @@ _cleanup()
# real QA test starts here
_supported_fs xfs
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_test_program "punch-alternating"
_require_xfs_io_command startupdate
_require_xfs_io_error_injection "bmap_finish_one"
diff --git a/tests/xfs/791 b/tests/xfs/791
index 84e3bee9b9..b4ded88d68 100755
--- a/tests/xfs/791
+++ b/tests/xfs/791
@@ -25,7 +25,7 @@ _cleanup()
# real QA test starts here
_supported_fs xfs
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_xfs_scratch_atomicswap
_require_xfs_io_error_injection "bmap_finish_one"
@@ -48,7 +48,7 @@ md5sum $SCRATCH_MNT/b | _filter_scratch
# Test swapext. -h means skip holes in /b, and -e means operate to EOF
echo swap | tee -a $seqres.full
$XFS_IO_PROG -x -c 'inject bmap_finish_one' \
- -c "swapext -v exchrange -f -u -h -e -a $SCRATCH_MNT/b" $SCRATCH_MNT/a
+ -c "exchangerange -f -u -h -e $SCRATCH_MNT/b" $SCRATCH_MNT/a
_scratch_cycle_mount
md5sum $SCRATCH_MNT/a | _filter_scratch
diff --git a/tests/xfs/792 b/tests/xfs/792
index bfbfbce4aa..fded7a5a52 100755
--- a/tests/xfs/792
+++ b/tests/xfs/792
@@ -25,7 +25,7 @@ _cleanup()
# real QA test starts here
_supported_fs xfs
-_require_xfs_io_command swapext '-v exchrange -a'
+_require_xfs_io_command exchangerange
_require_xfs_io_command startupdate '-e'
_require_xfs_scratch_atomicswap
_require_xfs_io_error_injection "bmap_finish_one"
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 02/11] misc: change xfs_io -c swapext to exchangerange
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
2024-06-20 20:54 ` [PATCH 01/11] misc: split swapext and exchangerange Darrick J. Wong
@ 2024-06-20 20:54 ` Darrick J. Wong
2024-06-20 20:54 ` [PATCH 03/11] generic/709,710: rework these for exchangerange vs. quota testing Darrick J. Wong
` (8 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:54 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Update the swapext command to use exchangerange as part of severing the
connection between the two ioctls.
Flags changed:
-h (only exchange written extents) is now -w.
-a (atomic mode) is always enabled now.
-e (to eof) is now the default; -l (length) disables this flag.
-u (unconditonal swap) is inverted to -c (commit only if fresh).
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/generic/712 | 8 ++++----
tests/generic/713 | 38 +++++++++++++++++++-------------------
tests/generic/713.out | 38 +++++++++++++++++++-------------------
tests/generic/714 | 36 ++++++++++++++++++------------------
tests/generic/714.out | 34 +++++++++++++++++-----------------
tests/generic/715 | 22 ++++++++++++----------
tests/generic/715.out | 14 +++++++-------
tests/generic/716 | 2 +-
tests/generic/717 | 34 +++++++++++++++++-----------------
tests/generic/717.out | 32 ++++++++++++++++----------------
tests/generic/718 | 10 +++++-----
tests/generic/718.out | 2 +-
tests/generic/719 | 2 +-
tests/generic/720 | 8 ++++----
tests/generic/721 | 2 +-
tests/generic/722 | 6 +++---
tests/generic/723 | 10 +++++-----
tests/generic/724 | 8 ++++----
tests/generic/725 | 2 +-
tests/generic/726 | 2 +-
tests/generic/727 | 2 +-
tests/xfs/300 | 2 +-
tests/xfs/443 | 4 ++--
tests/xfs/790 | 8 ++++----
tests/xfs/790.out | 2 +-
tests/xfs/791 | 8 ++++----
tests/xfs/791.out | 2 +-
tests/xfs/792 | 2 +-
tests/xfs/795 | 2 +-
29 files changed, 172 insertions(+), 170 deletions(-)
diff --git a/tests/generic/712 b/tests/generic/712
index f2862c3f8e..a5f2ac26fd 100755
--- a/tests/generic/712
+++ b/tests/generic/712
@@ -4,10 +4,10 @@
#
# FS QA Test No. 712
#
-# Make sure that swapext modifies ctime and not mtime of the file.
+# Make sure that exchangerange modifies ctime and not mtime of the file.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -39,8 +39,8 @@ old_mtime="$(echo $(stat -c '%y' $dir/a $dir/b))"
old_ctime="$(echo $(stat -c '%z' $dir/a $dir/b))"
stat -c '%y %Y %z %Z' $dir/a $dir/b >> $seqres.full
-# Now try to swapext
-$XFS_IO_PROG -c "swapext $dir/b" $dir/a
+# Now try to exchangerange
+$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
# Snapshot the 'a' file after we swap
echo after >> $seqres.full
diff --git a/tests/generic/713 b/tests/generic/713
index b2d3260806..b0165b1d91 100755
--- a/tests/generic/713
+++ b/tests/generic/713
@@ -4,10 +4,10 @@
#
# FS QA Test No. 713
#
-# Test swapext between ranges of two different files.
+# Test exchangerange between ranges of two different files.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -34,26 +34,26 @@ filesnap() {
fi
}
-test_swapext_once() {
- filesnap "$1: before swapext" $dir/$3 $dir/$4
+test_exchangerange_once() {
+ filesnap "$1: before exchangerange" $dir/$3 $dir/$4
$XFS_IO_PROG -c "exchangerange $2 $dir/$3" $dir/$4
- filesnap "$1: after swapext" $dir/$3 $dir/$4
+ filesnap "$1: after exchangerange" $dir/$3 $dir/$4
_test_cycle_mount
filesnap "$1: after cycling mount" $dir/$3 $dir/$4
echo
}
-test_swapext_two() {
- # swapext the same range of two files
- test_swapext_once "$*: samerange" \
+test_exchangerange_two() {
+ # exchangerange the same range of two files
+ test_exchangerange_once "$*: samerange" \
"-s $((blksz * 3)) -d $((blksz * 3)) -l $((blksz * 5))" b a
- # swapext different ranges of two files
- test_swapext_once "$*: diffrange" \
+ # exchangerange different ranges of two files
+ test_exchangerange_once "$*: diffrange" \
"-s $((blksz * 37)) -d $((blksz * 47)) -l $((blksz * 7))" b a
- # swapext overlapping ranges of two files
- test_swapext_once "$*: overlap" \
+ # exchangerange overlapping ranges of two files
+ test_exchangerange_once "$*: overlap" \
"-s $((blksz * 17)) -d $((blksz * 23)) -l $((blksz * 7))" b a
}
@@ -67,19 +67,19 @@ _require_congruent_file_oplen $TEST_DIR $blksz
rm -rf $dir/a $dir/b
_pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/a >> $seqres.full
_pwrite_byte 0x59 0 $((blksz * nrblks)) $dir/b >> $seqres.full
-test_swapext_two "simple"
+test_exchangerange_two "simple"
# Make some files that don't end an aligned offset.
rm -rf $dir/a $dir/b
_pwrite_byte 0x58 0 $(( (blksz * nrblks) + 37)) $dir/a >> $seqres.full
_pwrite_byte 0x59 0 $(( (blksz * nrblks) + 37)) $dir/b >> $seqres.full
-test_swapext_once "unalignedeof" "" a b
+test_exchangerange_once "unalignedeof" "" a b
# Set up some crazy rainbow files
rm -rf $dir/a $dir/b
_weave_file_rainbow $blksz $nrblks $dir/a >> $seqres.full
_weave_file_rainbow $blksz $nrblks $dir/b >> $seqres.full
-test_swapext_two "rainbow"
+test_exchangerange_two "rainbow"
# Now set up a simple file for testing within the same file
rm -rf $dir/c
@@ -87,12 +87,12 @@ $XFS_IO_PROG -f -c "pwrite -S 0x58 0 $((blksz * nrblks))" \
-c "pwrite -S 0x59 $((blksz * nrblks)) $((blksz * nrblks))" \
$dir/c >> $seqres.full
-# swapext the same offset into the 'X' and 'Y' regions of the file
-test_swapext_once "single: sameXandY" \
+# exchangerange the same offset into the 'X' and 'Y' regions of the file
+test_exchangerange_once "single: sameXandY" \
"-s $((blksz * 3)) -d $((blksz * (nrblks + 3))) -l $((blksz * 5))" c c
-# swapext the same offset into the 'X' and 'Y' regions of the file
-test_swapext_once "single: overlap" \
+# exchangerange the same offset into the 'X' and 'Y' regions of the file
+test_exchangerange_once "single: overlap" \
"-s $((blksz * 13)) -d $((blksz * 17)) -l $((blksz * 5))" c c
# success, all done
diff --git a/tests/generic/713.out b/tests/generic/713.out
index cb58e93aa6..87e26c5372 100644
--- a/tests/generic/713.out
+++ b/tests/generic/713.out
@@ -1,85 +1,85 @@
QA output created by 713
-simple: samerange: before swapext
+simple: samerange: before exchangerange
db85d578204631f2b4eb1e73974253c2 TEST_DIR/test-713/b
d0425612f15c6071022cf7127620f63d TEST_DIR/test-713/a
-simple: samerange: after swapext
+simple: samerange: after exchangerange
20beef1c9ed7de02e4229c69bd43bd8f TEST_DIR/test-713/b
e7697fa99d08f7eb76fa3fb963fe916a TEST_DIR/test-713/a
simple: samerange: after cycling mount
20beef1c9ed7de02e4229c69bd43bd8f TEST_DIR/test-713/b
e7697fa99d08f7eb76fa3fb963fe916a TEST_DIR/test-713/a
-simple: diffrange: before swapext
+simple: diffrange: before exchangerange
20beef1c9ed7de02e4229c69bd43bd8f TEST_DIR/test-713/b
e7697fa99d08f7eb76fa3fb963fe916a TEST_DIR/test-713/a
-simple: diffrange: after swapext
+simple: diffrange: after exchangerange
cd32ce54c295fcdf571ce7f8220fac56 TEST_DIR/test-713/b
d9771c5bb6d9db00b9abe65a4410e1a6 TEST_DIR/test-713/a
simple: diffrange: after cycling mount
cd32ce54c295fcdf571ce7f8220fac56 TEST_DIR/test-713/b
d9771c5bb6d9db00b9abe65a4410e1a6 TEST_DIR/test-713/a
-simple: overlap: before swapext
+simple: overlap: before exchangerange
cd32ce54c295fcdf571ce7f8220fac56 TEST_DIR/test-713/b
d9771c5bb6d9db00b9abe65a4410e1a6 TEST_DIR/test-713/a
-simple: overlap: after swapext
+simple: overlap: after exchangerange
e0fff655f6a08fc2f03ee01e4767060c TEST_DIR/test-713/b
ec7d764c85e583e305028c9cba5b25b6 TEST_DIR/test-713/a
simple: overlap: after cycling mount
e0fff655f6a08fc2f03ee01e4767060c TEST_DIR/test-713/b
ec7d764c85e583e305028c9cba5b25b6 TEST_DIR/test-713/a
-unalignedeof: before swapext
+unalignedeof: before exchangerange
9f8c731a4f1946ffdda8c33e82417f2d TEST_DIR/test-713/a
7a5d2ba7508226751c835292e28cd227 TEST_DIR/test-713/b
-unalignedeof: after swapext
+unalignedeof: after exchangerange
7a5d2ba7508226751c835292e28cd227 TEST_DIR/test-713/a
9f8c731a4f1946ffdda8c33e82417f2d TEST_DIR/test-713/b
unalignedeof: after cycling mount
7a5d2ba7508226751c835292e28cd227 TEST_DIR/test-713/a
9f8c731a4f1946ffdda8c33e82417f2d TEST_DIR/test-713/b
-rainbow: samerange: before swapext
+rainbow: samerange: before exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
-rainbow: samerange: after swapext
+rainbow: samerange: after exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
rainbow: samerange: after cycling mount
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
-rainbow: diffrange: before swapext
+rainbow: diffrange: before exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
-rainbow: diffrange: after swapext
+rainbow: diffrange: after exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
rainbow: diffrange: after cycling mount
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
-rainbow: overlap: before swapext
+rainbow: overlap: before exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-713/a
-rainbow: overlap: after swapext
+rainbow: overlap: after exchangerange
6753bc585e3c71d53bfaae11d2ffee99 TEST_DIR/test-713/b
39597abd4d9d0c9ceac22b77eb00c373 TEST_DIR/test-713/a
rainbow: overlap: after cycling mount
6753bc585e3c71d53bfaae11d2ffee99 TEST_DIR/test-713/b
39597abd4d9d0c9ceac22b77eb00c373 TEST_DIR/test-713/a
-single: sameXandY: before swapext
+single: sameXandY: before exchangerange
39e17753fa9e923a3b5928e13775e358 TEST_DIR/test-713/c
-single: sameXandY: after swapext
+single: sameXandY: after exchangerange
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-713/c
single: sameXandY: after cycling mount
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-713/c
-single: overlap: before swapext
+single: overlap: before exchangerange
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-713/c
-swapext: Invalid argument
-single: overlap: after swapext
+exchangerange: Invalid argument
+single: overlap: after exchangerange
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-713/c
single: overlap: after cycling mount
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-713/c
diff --git a/tests/generic/714 b/tests/generic/714
index ea963fdfa7..4d2d4a0b49 100755
--- a/tests/generic/714
+++ b/tests/generic/714
@@ -4,11 +4,11 @@
#
# FS QA Test No. 714
#
-# Test swapext between ranges of two different files, when one of the files
+# Test exchangerange between ranges of two different files, when one of the files
# is shared.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -35,26 +35,26 @@ filesnap() {
fi
}
-test_swapext_once() {
- filesnap "$1: before swapext" $dir/$3 $dir/$4
+test_exchangerange_once() {
+ filesnap "$1: before exchangerange" $dir/$3 $dir/$4
$XFS_IO_PROG -c "exchangerange $2 $dir/$3" $dir/$4
- filesnap "$1: after swapext" $dir/$3 $dir/$4
+ filesnap "$1: after exchangerange" $dir/$3 $dir/$4
_test_cycle_mount
filesnap "$1: after cycling mount" $dir/$3 $dir/$4
echo
}
-test_swapext_two() {
- # swapext the same range of two files
- test_swapext_once "$*: samerange" \
+test_exchangerange_two() {
+ # exchangerange the same range of two files
+ test_exchangerange_once "$*: samerange" \
"-s $((blksz * 3)) -d $((blksz * 3)) -l $((blksz * 5))" b a
- # swapext different ranges of two files
- test_swapext_once "$*: diffrange" \
+ # exchangerange different ranges of two files
+ test_exchangerange_once "$*: diffrange" \
"-s $((blksz * 37)) -d $((blksz * 47)) -l $((blksz * 7))" b a
- # swapext overlapping ranges of two files
- test_swapext_once "$*: overlap" \
+ # exchangerange overlapping ranges of two files
+ test_exchangerange_once "$*: overlap" \
"-s $((blksz * 17)) -d $((blksz * 23)) -l $((blksz * 7))" b a
# Now let's overwrite a entirely to make sure COW works
@@ -79,14 +79,14 @@ rm -f $dir/a $dir/b $dir/sharea
_pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/a >> $seqres.full
_pwrite_byte 0x59 0 $((blksz * nrblks)) $dir/b >> $seqres.full
_cp_reflink $dir/a $dir/sharea
-test_swapext_two "simple"
+test_exchangerange_two "simple"
# Set up some crazy rainbow files
rm -f $dir/a $dir/b $dir/sharea
_weave_file_rainbow $blksz $nrblks $dir/a >> $seqres.full
_weave_file_rainbow $blksz $nrblks $dir/b >> $seqres.full
_cp_reflink $dir/a $dir/sharea
-test_swapext_two "rainbow"
+test_exchangerange_two "rainbow"
# Now set up a simple file for testing within the same file
rm -f $dir/c $dir/sharec
@@ -95,12 +95,12 @@ $XFS_IO_PROG -f -c "pwrite -S 0x58 0 $((blksz * nrblks))" \
$dir/c >> $seqres.full
_cp_reflink $dir/c $dir/sharec
-# swapext the same offset into the 'X' and 'Y' regions of the file
-test_swapext_once "single: sameXandY" \
+# exchangerange the same offset into the 'X' and 'Y' regions of the file
+test_exchangerange_once "single: sameXandY" \
"-s $((blksz * 3)) -d $((blksz * (nrblks + 3))) -l $((blksz * 5))" c c
-# swapext the same offset into the 'X' and 'Y' regions of the file
-test_swapext_once "single: overlap" \
+# exchangerange the same offset into the 'X' and 'Y' regions of the file
+test_exchangerange_once "single: overlap" \
"-s $((blksz * 13)) -d $((blksz * 17)) -l $((blksz * 5))" c c
# Now let's overwrite a entirely to make sure COW works
diff --git a/tests/generic/714.out b/tests/generic/714.out
index bd45efc141..0d1714bf0c 100644
--- a/tests/generic/714.out
+++ b/tests/generic/714.out
@@ -1,28 +1,28 @@
QA output created by 714
-simple: samerange: before swapext
+simple: samerange: before exchangerange
db85d578204631f2b4eb1e73974253c2 TEST_DIR/test-714/b
d0425612f15c6071022cf7127620f63d TEST_DIR/test-714/a
-simple: samerange: after swapext
+simple: samerange: after exchangerange
20beef1c9ed7de02e4229c69bd43bd8f TEST_DIR/test-714/b
e7697fa99d08f7eb76fa3fb963fe916a TEST_DIR/test-714/a
simple: samerange: after cycling mount
20beef1c9ed7de02e4229c69bd43bd8f TEST_DIR/test-714/b
e7697fa99d08f7eb76fa3fb963fe916a TEST_DIR/test-714/a
-simple: diffrange: before swapext
+simple: diffrange: before exchangerange
20beef1c9ed7de02e4229c69bd43bd8f TEST_DIR/test-714/b
e7697fa99d08f7eb76fa3fb963fe916a TEST_DIR/test-714/a
-simple: diffrange: after swapext
+simple: diffrange: after exchangerange
cd32ce54c295fcdf571ce7f8220fac56 TEST_DIR/test-714/b
d9771c5bb6d9db00b9abe65a4410e1a6 TEST_DIR/test-714/a
simple: diffrange: after cycling mount
cd32ce54c295fcdf571ce7f8220fac56 TEST_DIR/test-714/b
d9771c5bb6d9db00b9abe65a4410e1a6 TEST_DIR/test-714/a
-simple: overlap: before swapext
+simple: overlap: before exchangerange
cd32ce54c295fcdf571ce7f8220fac56 TEST_DIR/test-714/b
d9771c5bb6d9db00b9abe65a4410e1a6 TEST_DIR/test-714/a
-simple: overlap: after swapext
+simple: overlap: after exchangerange
e0fff655f6a08fc2f03ee01e4767060c TEST_DIR/test-714/b
ec7d764c85e583e305028c9cba5b25b6 TEST_DIR/test-714/a
simple: overlap: after cycling mount
@@ -34,30 +34,30 @@ d0425612f15c6071022cf7127620f63d TEST_DIR/test-714/sharea
d0425612f15c6071022cf7127620f63d TEST_DIR/test-714/sharea
d0425612f15c6071022cf7127620f63d TEST_DIR/test-714/sharea
-rainbow: samerange: before swapext
+rainbow: samerange: before exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
-rainbow: samerange: after swapext
+rainbow: samerange: after exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
rainbow: samerange: after cycling mount
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
-rainbow: diffrange: before swapext
+rainbow: diffrange: before exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
-rainbow: diffrange: after swapext
+rainbow: diffrange: after exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
rainbow: diffrange: after cycling mount
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
-rainbow: overlap: before swapext
+rainbow: overlap: before exchangerange
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/b
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/a
-rainbow: overlap: after swapext
+rainbow: overlap: after exchangerange
6753bc585e3c71d53bfaae11d2ffee99 TEST_DIR/test-714/b
39597abd4d9d0c9ceac22b77eb00c373 TEST_DIR/test-714/a
rainbow: overlap: after cycling mount
@@ -69,17 +69,17 @@ overwrite A and B entirely
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/sharea
48b41ee1970eb71064b77181f42634cf TEST_DIR/test-714/sharea
-single: sameXandY: before swapext
+single: sameXandY: before exchangerange
39e17753fa9e923a3b5928e13775e358 TEST_DIR/test-714/c
-single: sameXandY: after swapext
+single: sameXandY: after exchangerange
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-714/c
single: sameXandY: after cycling mount
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-714/c
-single: overlap: before swapext
+single: overlap: before exchangerange
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-714/c
-swapext: Invalid argument
-single: overlap: after swapext
+exchangerange: Invalid argument
+single: overlap: after exchangerange
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-714/c
single: overlap: after cycling mount
8262c617070703fb0e2a28d8f05e3112 TEST_DIR/test-714/c
diff --git a/tests/generic/715 b/tests/generic/715
index eb164a848a..60a5381eaa 100755
--- a/tests/generic/715
+++ b/tests/generic/715
@@ -4,10 +4,10 @@
#
# FS QA Test No. 715
#
-# Test swapext between two files of unlike size.
+# Test exchangerange between two files of unlike size.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -33,7 +33,7 @@ filesnap() {
fi
}
-test_swapext_once() {
+test_exchangerange_once() {
local tag=$1
local a_len=$2
local b_len=$3
@@ -41,20 +41,22 @@ test_swapext_once() {
local b_off=$5
local len=$6
- # len is either a block count or -e to swap to EOF
- if [ "$len" != "-e" ]; then
+ # len is either a block count or "EOF"
+ if [ "$len" = "EOF" ]; then
+ len=""
+ else
len="-l $((blksz * len))"
fi
rm -f $dir/a $dir/b
_pwrite_byte 0x58 0 $((blksz * a_len)) $dir/a >> $seqres.full
_pwrite_byte 0x59 0 $((blksz * b_len)) $dir/b >> $seqres.full
- filesnap "$tag: before swapext" $dir/a $dir/b
+ filesnap "$tag: before exchangerange" $dir/a $dir/b
cmd="exchangerange -s $((blksz * a_off)) -d $((blksz * b_off)) $len $dir/a"
echo "$cmd" >> $seqres.full
$XFS_IO_PROG -c "$cmd" $dir/b
- filesnap "$tag: after swapext" $dir/a $dir/b
+ filesnap "$tag: after exchangerange" $dir/a $dir/b
_test_cycle_mount
filesnap "$tag: after cycling mount" $dir/a $dir/b
@@ -65,11 +67,11 @@ dir=$TEST_DIR/test-$seq
mkdir -p $dir
blksz=65536
-test_swapext_once "last 5 blocks" 27 37 22 32 5
+test_exchangerange_once "last 5 blocks" 27 37 22 32 5
-test_swapext_once "whole file to eof" 27 37 0 0 -e
+test_exchangerange_once "whole file to eof" 27 37 0 0 EOF
-test_swapext_once "blocks 30-40" 27 37 30 30 10
+test_exchangerange_once "blocks 30-40" 27 37 30 30 10
# success, all done
status=0
diff --git a/tests/generic/715.out b/tests/generic/715.out
index b4a6565aba..c2652e632b 100644
--- a/tests/generic/715.out
+++ b/tests/generic/715.out
@@ -1,29 +1,29 @@
QA output created by 715
-last 5 blocks: before swapext
+last 5 blocks: before exchangerange
207ea56e0ccbf50d38fd3a2d842aa170 TEST_DIR/test-715/a
eb58941d31f5be1e4e22df8c536dd490 TEST_DIR/test-715/b
-last 5 blocks: after swapext
+last 5 blocks: after exchangerange
3f34470fe9feb8513d5f3a8538f2c5f3 TEST_DIR/test-715/a
c3daca7dd9218371cd0dc64f11e4b0bf TEST_DIR/test-715/b
last 5 blocks: after cycling mount
3f34470fe9feb8513d5f3a8538f2c5f3 TEST_DIR/test-715/a
c3daca7dd9218371cd0dc64f11e4b0bf TEST_DIR/test-715/b
-whole file to eof: before swapext
+whole file to eof: before exchangerange
207ea56e0ccbf50d38fd3a2d842aa170 TEST_DIR/test-715/a
eb58941d31f5be1e4e22df8c536dd490 TEST_DIR/test-715/b
-whole file to eof: after swapext
+whole file to eof: after exchangerange
eb58941d31f5be1e4e22df8c536dd490 TEST_DIR/test-715/a
207ea56e0ccbf50d38fd3a2d842aa170 TEST_DIR/test-715/b
whole file to eof: after cycling mount
eb58941d31f5be1e4e22df8c536dd490 TEST_DIR/test-715/a
207ea56e0ccbf50d38fd3a2d842aa170 TEST_DIR/test-715/b
-blocks 30-40: before swapext
+blocks 30-40: before exchangerange
207ea56e0ccbf50d38fd3a2d842aa170 TEST_DIR/test-715/a
eb58941d31f5be1e4e22df8c536dd490 TEST_DIR/test-715/b
-swapext: Invalid argument
-blocks 30-40: after swapext
+exchangerange: Invalid argument
+blocks 30-40: after exchangerange
207ea56e0ccbf50d38fd3a2d842aa170 TEST_DIR/test-715/a
eb58941d31f5be1e4e22df8c536dd490 TEST_DIR/test-715/b
blocks 30-40: after cycling mount
diff --git a/tests/generic/716 b/tests/generic/716
index 5d3fa5e721..dbfa426378 100755
--- a/tests/generic/716
+++ b/tests/generic/716
@@ -10,7 +10,7 @@
# and some of the contents are updated.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
diff --git a/tests/generic/717 b/tests/generic/717
index dd2f3dcdc4..ffabe2eaa1 100755
--- a/tests/generic/717
+++ b/tests/generic/717
@@ -7,7 +7,7 @@
# Try invalid parameters to see if they fail.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -39,62 +39,62 @@ _pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/a >> $seqres.full
_pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/b >> $seqres.full
echo Immutable files
-$XFS_IO_PROG -c 'chattr +i' -c "swapext $dir/b" $dir/a
+$XFS_IO_PROG -c 'chattr +i' -c "exchangerange $dir/b" $dir/a
$CHATTR_PROG -i $dir/a
echo Readonly files
-$XFS_IO_PROG -r -c "swapext $dir/b" $dir/a
+$XFS_IO_PROG -r -c "exchangerange $dir/b" $dir/a
echo Directories
-$XFS_IO_PROG -c "swapext $dir/b" $dir
+$XFS_IO_PROG -c "exchangerange $dir/b" $dir
echo Unaligned ranges
-$XFS_IO_PROG -c "swapext -s 37 -d 61 -l 17 $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -s 37 -d 61 -l 17 $dir/b" $dir/a
echo file1 range entirely beyond EOF
-$XFS_IO_PROG -c "swapext -s $(( blksz * (nrblks + 500) )) -d 0 -l $blksz $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -s $(( blksz * (nrblks + 500) )) -d 0 -l $blksz $dir/b" $dir/a
echo file2 range entirely beyond EOF
-$XFS_IO_PROG -c "swapext -d $(( blksz * (nrblks + 500) )) -s 0 -l $blksz $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -d $(( blksz * (nrblks + 500) )) -s 0 -l $blksz $dir/b" $dir/a
echo Both ranges entirely beyond EOF
-$XFS_IO_PROG -c "swapext -d $(( blksz * (nrblks + 500) )) -s $(( blksz * (nrblks + 500) )) -l $blksz $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -d $(( blksz * (nrblks + 500) )) -s $(( blksz * (nrblks + 500) )) -l $blksz $dir/b" $dir/a
echo file1 range crossing EOF
-$XFS_IO_PROG -c "swapext -s $(( blksz * (nrblks - 1) )) -d 0 -l $((2 * blksz)) $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -s $(( blksz * (nrblks - 1) )) -d 0 -l $((2 * blksz)) $dir/b" $dir/a
echo file2 range crossing EOF
-$XFS_IO_PROG -c "swapext -d $(( blksz * (nrblks - 1) )) -s 0 -l $((2 * blksz)) $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -d $(( blksz * (nrblks - 1) )) -s 0 -l $((2 * blksz)) $dir/b" $dir/a
echo Both ranges crossing EOF
-$XFS_IO_PROG -c "swapext -d $(( blksz * (nrblks - 1) )) -s $(( blksz * (nrblks - 1) )) -l $((blksz * 2)) $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -d $(( blksz * (nrblks - 1) )) -s $(( blksz * (nrblks - 1) )) -l $((blksz * 2)) $dir/b" $dir/a
echo file1 unaligned EOF to file2 nowhere near EOF
_pwrite_byte 0x58 $((blksz * nrblks)) 37 $dir/a >> $seqres.full
_pwrite_byte 0x59 $((blksz * nrblks)) 37 $dir/b >> $seqres.full
-$XFS_IO_PROG -c "swapext -d 0 -s $(( blksz * nrblks )) -l 37 $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -d 0 -s $(( blksz * nrblks )) -l 37 $dir/b" $dir/a
echo file2 unaligned EOF to file1 nowhere near EOF
-$XFS_IO_PROG -c "swapext -s 0 -d $(( blksz * nrblks )) -l 37 $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange -s 0 -d $(( blksz * nrblks )) -l 37 $dir/b" $dir/a
echo Files of unequal length
_pwrite_byte 0x58 $((blksz * nrblks)) $((blksz * 2)) $dir/a >> $seqres.full
_pwrite_byte 0x59 $((blksz * nrblks)) $blksz $dir/b >> $seqres.full
-$XFS_IO_PROG -c "swapext $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
echo Files on different filesystems
_pwrite_byte 0x58 0 $((blksz * nrblks)) $SCRATCH_MNT/c >> $seqres.full
-$XFS_IO_PROG -c "swapext $SCRATCH_MNT/c" $dir/a
+$XFS_IO_PROG -c "exchangerange $SCRATCH_MNT/c" $dir/a
echo Files on different mounts
mkdir -p $SCRATCH_MNT/xyz
mount --bind $dir $SCRATCH_MNT/xyz --bind
_pwrite_byte 0x60 0 $((blksz * (nrblks + 2))) $dir/c >> $seqres.full
-$XFS_IO_PROG -c "swapext $SCRATCH_MNT/xyz/c" $dir/a
+$XFS_IO_PROG -c "exchangerange $SCRATCH_MNT/xyz/c" $dir/a
umount $SCRATCH_MNT/xyz
echo Swapping a file with itself
-$XFS_IO_PROG -c "swapext $dir/a" $dir/a
+$XFS_IO_PROG -c "exchangerange $dir/a" $dir/a
# success, all done
status=0
diff --git a/tests/generic/717.out b/tests/generic/717.out
index 7a7ab30b59..85137bf412 100644
--- a/tests/generic/717.out
+++ b/tests/generic/717.out
@@ -1,33 +1,33 @@
QA output created by 717
Immutable files
-swapext: Operation not permitted
+exchangerange: Operation not permitted
Readonly files
-swapext: Bad file descriptor
+exchangerange: Bad file descriptor
Directories
-swapext: Is a directory
+exchangerange: Is a directory
Unaligned ranges
-swapext: Invalid argument
+exchangerange: Invalid argument
file1 range entirely beyond EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
file2 range entirely beyond EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
Both ranges entirely beyond EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
file1 range crossing EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
file2 range crossing EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
Both ranges crossing EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
file1 unaligned EOF to file2 nowhere near EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
file2 unaligned EOF to file1 nowhere near EOF
-swapext: Invalid argument
+exchangerange: Invalid argument
Files of unequal length
-swapext: Bad address
+exchangerange: Bad address
Files on different filesystems
-swapext: Invalid cross-device link
+exchangerange: Invalid cross-device link
Files on different mounts
-swapext: Invalid cross-device link
+exchangerange: Invalid cross-device link
Swapping a file with itself
-swapext: Invalid argument
+exchangerange: Invalid argument
diff --git a/tests/generic/718 b/tests/generic/718
index 23e092df4d..ab81dbec95 100755
--- a/tests/generic/718
+++ b/tests/generic/718
@@ -4,10 +4,10 @@
#
# FS QA Test No. 718
#
-# Make sure swapext honors RLIMIT_FSIZE.
+# Make sure exchangerange honors RLIMIT_FSIZE.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -29,7 +29,7 @@ mkdir -p $dir
blksz=65536
nrblks=64
-# Create some 4M files to test swapext
+# Create some 4M files to test exchangerange
_pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/a >> $seqres.full
_pwrite_byte 0x59 0 $((blksz * nrblks)) $dir/b >> $seqres.full
sync
@@ -39,8 +39,8 @@ md5sum $dir/a $dir/b | _filter_test_dir
ulimit -f $(( (blksz * 2) / 512))
ulimit -a >> $seqres.full
-# Now try to swapext
-$XFS_IO_PROG -c "swapext $dir/b" $dir/a
+# Now try to exchangerange
+$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
md5sum $dir/a $dir/b | _filter_test_dir
# success, all done
diff --git a/tests/generic/718.out b/tests/generic/718.out
index f3f26f7c13..c96c466b7d 100644
--- a/tests/generic/718.out
+++ b/tests/generic/718.out
@@ -1,6 +1,6 @@
QA output created by 718
d712f003e9d467e063cda1baf319b928 TEST_DIR/test-718/a
901e136269b8d283d311697b7c6dc1f2 TEST_DIR/test-718/b
-swapext: Invalid argument
+exchangerange: Invalid argument
d712f003e9d467e063cda1baf319b928 TEST_DIR/test-718/a
901e136269b8d283d311697b7c6dc1f2 TEST_DIR/test-718/b
diff --git a/tests/generic/719 b/tests/generic/719
index 70d1ae5d0c..1f8da3a9fd 100755
--- a/tests/generic/719
+++ b/tests/generic/719
@@ -10,7 +10,7 @@
# caller wants a full file replacement.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
diff --git a/tests/generic/720 b/tests/generic/720
index 25253968a2..b444988841 100755
--- a/tests/generic/720
+++ b/tests/generic/720
@@ -7,7 +7,7 @@
# Stress testing with a lot of extents.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -31,18 +31,18 @@ nrblks=$((LOAD_FACTOR * 100000))
_require_fs_space $TEST_DIR $(( (2 * blksz * nrblks) / 1024 ))
-# Create some big swiss cheese files to test swapext with a lot of extents
+# Create some big swiss cheese files to test exchangerange with a lot of extents
_pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/a >> $seqres.full
$here/src/punch-alternating $dir/a
_pwrite_byte 0x59 0 $((blksz * nrblks)) $dir/b >> $seqres.full
$here/src/punch-alternating -o 1 $dir/b
filefrag -v $dir/a $dir/b >> $seqres.full
-# Now try to swapext
+# Now try to exchangerange
md5_a="$(md5sum < $dir/a)"
md5_b="$(md5sum < $dir/b)"
date >> $seqres.full
-$XFS_IO_PROG -c "swapext $dir/b" $dir/a
+$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
date >> $seqres.full
echo "md5_a=$md5_a" >> $seqres.full
diff --git a/tests/generic/721 b/tests/generic/721
index 0beb08927b..406e2b688f 100755
--- a/tests/generic/721
+++ b/tests/generic/721
@@ -8,7 +8,7 @@
# the staging file; and (b) when the staging file is created empty.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
diff --git a/tests/generic/722 b/tests/generic/722
index 3ec831e708..85afa2e0c1 100755
--- a/tests/generic/722
+++ b/tests/generic/722
@@ -4,11 +4,11 @@
#
# FS QA Test No. 722
#
-# Test swapext with the fsync flag flushes everything to disk before the call
+# Test exchangerange with the fsync flag flushes everything to disk before the call
# returns.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -43,7 +43,7 @@ od -tx1 -Ad -c $SCRATCH_MNT/a > /tmp/a0
od -tx1 -Ad -c $SCRATCH_MNT/b > /tmp/b0
echo swap >> $seqres.full
-$XFS_IO_PROG -c "exchangerange -e -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
+$XFS_IO_PROG -c "exchangerange -f $SCRATCH_MNT/a" $SCRATCH_MNT/b
_scratch_shutdown
_scratch_cycle_mount
diff --git a/tests/generic/723 b/tests/generic/723
index 0e1de3ec1f..f1df1e53e1 100755
--- a/tests/generic/723
+++ b/tests/generic/723
@@ -4,10 +4,10 @@
#
# FS QA Test No. 723
#
-# Test swapext with the dry run flag doesn't change anything.
+# Test exchangerange with the dry run flag doesn't change anything.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -38,10 +38,10 @@ old_a=$(md5sum $SCRATCH_MNT/a | awk '{print $1}')
old_b=$(md5sum $SCRATCH_MNT/b | awk '{print $1}')
echo "md5 a: $old_a md5 b: $old_b" >> $seqres.full
-# Test swapext with the -n option, which will do all the input parameter
+# Test exchangerange with the -n option, which will do all the input parameter
# checking and return 0 without changing anything.
echo dry run swap >> $seqres.full
-$XFS_IO_PROG -c "exchangerange -n -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
+$XFS_IO_PROG -c "exchangerange -n -f $SCRATCH_MNT/a" $SCRATCH_MNT/b
_scratch_cycle_mount
new_a=$(md5sum $SCRATCH_MNT/a | awk '{print $1}')
@@ -54,7 +54,7 @@ test $old_b = $new_b || echo "scratch file B should not have swapped"
# Do it again, but without the -n option, to prove that we can actually
# swap the file contents.
echo actual swap >> $seqres.full
-$XFS_IO_PROG -c "exchangerange -f -u $SCRATCH_MNT/a" $SCRATCH_MNT/b
+$XFS_IO_PROG -c "exchangerange -f $SCRATCH_MNT/a" $SCRATCH_MNT/b
_scratch_cycle_mount
new_a=$(md5sum $SCRATCH_MNT/a | awk '{print $1}')
diff --git a/tests/generic/724 b/tests/generic/724
index 9536705503..4cc02946dd 100755
--- a/tests/generic/724
+++ b/tests/generic/724
@@ -5,11 +5,11 @@
# FS QA Test No. 724
#
# Test scatter-gather atomic file writes. We create a temporary file, write
-# sparsely to it, then use XFS_EXCH_RANGE_FILE1_WRITTEN flag to swap
+# sparsely to it, then use XFS_EXCHRANGE_FILE1_WRITTEN flag to swap
# atomicallly only the ranges that we wrote.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -40,9 +40,9 @@ _pwrite_byte 0x57 768k 64k $SCRATCH_MNT/b >> $seqres.full
md5sum $SCRATCH_MNT/a | _filter_scratch
md5sum $SCRATCH_MNT/b | _filter_scratch
-# Test swapext. -h means skip holes in /b, and -e means operate to EOF
+# Test exchangerange. -w means skip holes in /b
echo swap | tee -a $seqres.full
-$XFS_IO_PROG -c "exchangerange -f -u -h -e $SCRATCH_MNT/b" $SCRATCH_MNT/a
+$XFS_IO_PROG -c "exchangerange -f -w $SCRATCH_MNT/b" $SCRATCH_MNT/a
_scratch_cycle_mount
md5sum $SCRATCH_MNT/a | _filter_scratch
diff --git a/tests/generic/725 b/tests/generic/725
index 3c6180fcbb..e5e2139c6e 100755
--- a/tests/generic/725
+++ b/tests/generic/725
@@ -9,7 +9,7 @@
# perform the scattered update.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
diff --git a/tests/generic/726 b/tests/generic/726
index 05d8a2372a..3b186ab6ac 100755
--- a/tests/generic/726
+++ b/tests/generic/726
@@ -8,7 +8,7 @@
# commit.
#
. ./common/preamble
-_begin_fstest auto fiexchange swapext quick
+_begin_fstest auto fiexchange quick
# Override the default cleanup function.
# _cleanup()
diff --git a/tests/generic/727 b/tests/generic/727
index 4b0d5bd372..f737d4dd39 100755
--- a/tests/generic/727
+++ b/tests/generic/727
@@ -8,7 +8,7 @@
# commit.
#
. ./common/preamble
-_begin_fstest auto fiexchange swapext quick
+_begin_fstest auto fiexchange quick
# Override the default cleanup function.
# _cleanup()
diff --git a/tests/xfs/300 b/tests/xfs/300
index bc1f0efc6a..e21ea2e320 100755
--- a/tests/xfs/300
+++ b/tests/xfs/300
@@ -4,7 +4,7 @@
#
# FS QA Test No. 300
#
-# Test xfs_fsr / swapext management of di_forkoff w/ selinux
+# Test xfs_fsr / exchangerange management of di_forkoff w/ selinux
#
. ./common/preamble
_begin_fstest auto fsr
diff --git a/tests/xfs/443 b/tests/xfs/443
index 56828decae..069d976cb8 100755
--- a/tests/xfs/443
+++ b/tests/xfs/443
@@ -29,7 +29,7 @@ _require_scratch
_require_test_program "punch-alternating"
_require_xfs_io_command "falloc"
_require_xfs_io_command "fpunch"
-_require_xfs_io_command "swapext"
+_require_xfs_io_command "exchangerange"
_require_xfs_io_command "fiemap"
_scratch_mkfs | _filter_mkfs >> $seqres.full 2> $tmp.mkfs
@@ -56,7 +56,7 @@ $here/src/punch-alternating $file2
for i in $(seq 1 2 399); do
# punch one extent from the tmpfile and swap
$XFS_IO_PROG -c "fpunch $((i * dbsize)) $dbsize" $file2
- $XFS_IO_PROG -c "swapext $file2" $file1
+ $XFS_IO_PROG -c "exchangerange $file2" $file1
# punch the same extent from the old fork (now in file2) to resync the
# extent counts and repeat
diff --git a/tests/xfs/790 b/tests/xfs/790
index 62bbd1fea6..88b79611ef 100755
--- a/tests/xfs/790
+++ b/tests/xfs/790
@@ -4,11 +4,11 @@
#
# FS QA Test No. 790
#
-# Make sure an atomic swapext actually runs to completion even if we shut
+# Make sure an atomic exchangerange actually runs to completion even if we shut
# down the filesystem midway through.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -49,9 +49,9 @@ _pwrite_byte 0x59 0 $((blksz * nrblks)) $dir/c >> $seqres.full
_pwrite_byte 0x58 0 $((blksz * nrblks)) $dir/a >> $seqres.full
sync
-# Inject a bmap error and trigger it via swapext.
+# Inject a bmap error and trigger it via exchangerange.
filesnap "before commit"
-$XFS_IO_PROG -x -c 'inject bmap_finish_one' -c "swapext $dir/b" $dir/a
+$XFS_IO_PROG -x -c 'inject bmap_finish_one' -c "exchangerange $dir/b" $dir/a
# Check the file afterwards.
_test_cycle_mount
diff --git a/tests/xfs/790.out b/tests/xfs/790.out
index 70ebb2f18f..d1321e8342 100644
--- a/tests/xfs/790.out
+++ b/tests/xfs/790.out
@@ -3,7 +3,7 @@ before commit
c7221b1494117327570a0958b0abca51 TEST_DIR/test-790/a
30cc2b6b307081e10972317013efb0f3 TEST_DIR/test-790/b
30cc2b6b307081e10972317013efb0f3 TEST_DIR/test-790/c
-swapext: Input/output error
+exchangerange: Input/output error
after commit
30cc2b6b307081e10972317013efb0f3 TEST_DIR/test-790/a
c7221b1494117327570a0958b0abca51 TEST_DIR/test-790/b
diff --git a/tests/xfs/791 b/tests/xfs/791
index b4ded88d68..37f58972c4 100755
--- a/tests/xfs/791
+++ b/tests/xfs/791
@@ -5,12 +5,12 @@
# FS QA Test No. 791
#
# Test scatter-gather atomic file writes. We create a temporary file, write
-# sparsely to it, then use XFS_EXCH_RANGE_FILE1_WRITTEN flag to swap
+# sparsely to it, then use XFS_EXCHRANGE_FILE1_WRITTEN flag to swap
# atomicallly only the ranges that we wrote. Inject an error so that we can
# test that log recovery finishes the swap.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
@@ -45,10 +45,10 @@ sync
md5sum $SCRATCH_MNT/a | _filter_scratch
md5sum $SCRATCH_MNT/b | _filter_scratch
-# Test swapext. -h means skip holes in /b, and -e means operate to EOF
+# Test exchangerange. -w means skip holes in /b
echo swap | tee -a $seqres.full
$XFS_IO_PROG -x -c 'inject bmap_finish_one' \
- -c "exchangerange -f -u -h -e $SCRATCH_MNT/b" $SCRATCH_MNT/a
+ -c "exchangerange -f -w $SCRATCH_MNT/b" $SCRATCH_MNT/a
_scratch_cycle_mount
md5sum $SCRATCH_MNT/a | _filter_scratch
diff --git a/tests/xfs/791.out b/tests/xfs/791.out
index 015b6d3c46..2153548e91 100644
--- a/tests/xfs/791.out
+++ b/tests/xfs/791.out
@@ -2,6 +2,6 @@ QA output created by 791
310f146ce52077fcd3308dcbe7632bb2 SCRATCH_MNT/a
c9fb827e2e3e579dc2a733ddad486d1d SCRATCH_MNT/b
swap
-swapext: Input/output error
+exchangerange: Input/output error
e9cbfe8489a68efaa5fcf40cf3106118 SCRATCH_MNT/a
faf8ed02a5b0638096a817abcc6c2127 SCRATCH_MNT/b
diff --git a/tests/xfs/792 b/tests/xfs/792
index fded7a5a52..1da36fb97c 100755
--- a/tests/xfs/792
+++ b/tests/xfs/792
@@ -10,7 +10,7 @@
# recovery finishes the swap.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick fiexchange
# Override the default cleanup function.
_cleanup()
diff --git a/tests/xfs/795 b/tests/xfs/795
index a381db320f..a4e65921a5 100755
--- a/tests/xfs/795
+++ b/tests/xfs/795
@@ -6,7 +6,7 @@
#
# Ensure that the sysadmin won't hit EDQUOT while repairing file data contents
# even if the file's quota limits have been exceeded. This tests the quota
-# reservation handling inside the swapext code used by repair.
+# reservation handling inside the exchangerange code used by repair.
#
. ./common/preamble
_begin_fstest online_repair
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 03/11] generic/709,710: rework these for exchangerange vs. quota testing
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
2024-06-20 20:54 ` [PATCH 01/11] misc: split swapext and exchangerange Darrick J. Wong
2024-06-20 20:54 ` [PATCH 02/11] misc: change xfs_io -c swapext to exchangerange Darrick J. Wong
@ 2024-06-20 20:54 ` Darrick J. Wong
2024-06-21 4:35 ` Christoph Hellwig
2024-06-20 20:55 ` [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range Darrick J. Wong
` (7 subsequent siblings)
10 siblings, 1 reply; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:54 UTC (permalink / raw)
To: djwong, zlang; +Cc: fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
The exchange-range implementation is now completely separate from the
old swapext ioctl, so let's migrate these quota tests to exchangerange.
There's no point in maintaining these tests for the legacy swapext code
because it returns EINVAL if any quota is enabled and the two files have
different user/group/project ids. Originally I had forward ported the
old swapext ioctl to use commitrange as its backend, but that will be
dropped in favor of porting xfs_fsr to use commitrange directly.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
tests/generic/709 | 12 ++++++------
tests/generic/710 | 14 +++++++-------
tests/generic/710.out | 2 +-
3 files changed, 14 insertions(+), 14 deletions(-)
diff --git a/tests/generic/709 b/tests/generic/709
index 4fc938bb6a..f3b827cb04 100755
--- a/tests/generic/709
+++ b/tests/generic/709
@@ -4,17 +4,17 @@
#
# FS QA Test No. 709
#
-# Can we use swapext to make the quota accounting incorrect?
+# Can we use exchangerange to make the quota accounting incorrect?
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext quota
+_begin_fstest auto quick fiexchange quota
# Import common functions.
. ./common/filter
. ./common/quota
# real QA test starts here
-_require_xfs_io_command swapext
+_require_xfs_io_command exchangerange
_require_user
_require_nobody
_require_quota
@@ -32,7 +32,7 @@ chown $qa_user $SCRATCH_MNT/a
$XFS_IO_PROG -f -c 'pwrite -S 0x59 0 64k -b 64k' -c 'truncate 256k' $SCRATCH_MNT/b >> $seqres.full
chown nobody $SCRATCH_MNT/b
-echo before swapext >> $seqres.full
+echo before exchangerange >> $seqres.full
$XFS_QUOTA_PROG -x -c 'report -a' $SCRATCH_MNT >> $seqres.full
stat $SCRATCH_MNT/* >> $seqres.full
@@ -40,11 +40,11 @@ stat $SCRATCH_MNT/* >> $seqres.full
# fail with -EINVAL (since that's what the first kernel fix does) or succeed
# (because subsequent rewrites can handle quota). Whatever the outcome, the
# quota usage check at the end should never show a discrepancy.
-$XFS_IO_PROG -c "swapext $SCRATCH_MNT/b" $SCRATCH_MNT/a &> $tmp.swap
+$XFS_IO_PROG -c "exchangerange $SCRATCH_MNT/b" $SCRATCH_MNT/a &> $tmp.swap
cat $tmp.swap >> $seqres.full
grep -v 'Invalid argument' $tmp.swap
-echo after swapext >> $seqres.full
+echo after exchangerange >> $seqres.full
$XFS_QUOTA_PROG -x -c 'report -a' $SCRATCH_MNT >> $seqres.full
stat $SCRATCH_MNT/* >> $seqres.full
diff --git a/tests/generic/710 b/tests/generic/710
index 6c6aa08f63..c344bd898b 100755
--- a/tests/generic/710
+++ b/tests/generic/710
@@ -4,17 +4,17 @@
#
# FS QA Test No. 710
#
-# Can we use swapext to exceed the quota enforcement?
+# Can we use exchangerange to exceed the quota enforcement?
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext quota
+_begin_fstest auto quick fiexchange quota
# Import common functions.
. ./common/filter
. ./common/quota
# real QA test starts here
-_require_xfs_io_command swapext
+_require_xfs_io_command exchangerange
_require_user
_require_nobody
_require_quota
@@ -35,14 +35,14 @@ chown nobody $SCRATCH_MNT/b
# Set up a quota limit
$XFS_QUOTA_PROG -x -c "limit -u bhard=70k nobody" $SCRATCH_MNT
-echo before swapext >> $seqres.full
+echo before exchangerange >> $seqres.full
$XFS_QUOTA_PROG -x -c 'report -a' $SCRATCH_MNT >> $seqres.full
stat $SCRATCH_MNT/* >> $seqres.full
-# Now try to swapext
-$XFS_IO_PROG -c "swapext $SCRATCH_MNT/b" $SCRATCH_MNT/a
+# Now try to exchangerange
+$XFS_IO_PROG -c "exchangerange $SCRATCH_MNT/b" $SCRATCH_MNT/a
-echo after swapext >> $seqres.full
+echo after exchangerange >> $seqres.full
$XFS_QUOTA_PROG -x -c 'report -a' $SCRATCH_MNT >> $seqres.full
stat $SCRATCH_MNT/* >> $seqres.full
diff --git a/tests/generic/710.out b/tests/generic/710.out
index a2aa981919..fcc006c279 100644
--- a/tests/generic/710.out
+++ b/tests/generic/710.out
@@ -1,4 +1,4 @@
QA output created by 710
-swapext: Disk quota exceeded
+exchangerange: Disk quota exceeded
Comparing user usage
Comparing group usage
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (2 preceding siblings ...)
2024-06-20 20:54 ` [PATCH 03/11] generic/709,710: rework these for exchangerange vs. quota testing Darrick J. Wong
@ 2024-06-20 20:55 ` Darrick J. Wong
2024-06-21 4:35 ` Christoph Hellwig
2024-06-21 16:14 ` Zorro Lang
2024-06-20 20:55 ` [PATCH 05/11] generic/717: remove obsolete check Darrick J. Wong
` (6 subsequent siblings)
10 siblings, 2 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:55 UTC (permalink / raw)
To: djwong, zlang; +Cc: fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Fork these tests to check the same things with exchange-range as they do
for swapext, since the code porting swapext to commit-range has been
dropped.
I was going to fork xfs/789 as well, but it turns out that generic/714
covers this sufficiently so for that one, we just strike fiexchange from
the group tag.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
tests/generic/1221 | 45 ++++++++++++++++++++++++
tests/generic/1221.out | 2 +
tests/generic/711 | 2 +
tests/xfs/1215 | 89 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1215.out | 13 +++++++
tests/xfs/789 | 2 +
6 files changed, 151 insertions(+), 2 deletions(-)
create mode 100755 tests/generic/1221
create mode 100644 tests/generic/1221.out
create mode 100755 tests/xfs/1215
create mode 100644 tests/xfs/1215.out
diff --git a/tests/generic/1221 b/tests/generic/1221
new file mode 100755
index 0000000000..5569f59734
--- /dev/null
+++ b/tests/generic/1221
@@ -0,0 +1,45 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0-or-later
+# Copyright (c) 2022 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1221
+#
+# Make sure that exchangerange won't touch a swap file.
+
+. ./common/preamble
+_begin_fstest auto quick fiexchange
+
+# Override the default cleanup function.
+_cleanup()
+{
+ cd /
+ test -e "$dir/a" && swapoff $dir/a
+ rm -r -f $tmp.* $dir
+}
+
+# Import common functions.
+. ./common/filter
+
+# real QA test starts here
+_require_xfs_io_command exchangerange
+_require_test
+
+dir=$TEST_DIR/test-$seq
+mkdir -p $dir
+
+# Set up a fragmented swapfile and a dummy donor file.
+$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
+$here/src/punch-alternating $dir/a
+$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
+$MKSWAP_PROG $dir/a >> $seqres.full
+
+$XFS_IO_PROG -f -c 'pwrite -S 0x59 0 32m -b 1m' $dir/b >> $seqres.full
+
+swapon $dir/a || _notrun 'failed to swapon'
+
+# Now try to exchangerange.
+$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
+
+# success, all done
+status=0
+exit
diff --git a/tests/generic/1221.out b/tests/generic/1221.out
new file mode 100644
index 0000000000..698ac87303
--- /dev/null
+++ b/tests/generic/1221.out
@@ -0,0 +1,2 @@
+QA output created by 1221
+exchangerange: Text file busy
diff --git a/tests/generic/711 b/tests/generic/711
index b107f976ef..792136306c 100755
--- a/tests/generic/711
+++ b/tests/generic/711
@@ -7,7 +7,7 @@
# Make sure that swapext won't touch a swap file.
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick swapext
# Override the default cleanup function.
_cleanup()
diff --git a/tests/xfs/1215 b/tests/xfs/1215
new file mode 100755
index 0000000000..5e7633c5ea
--- /dev/null
+++ b/tests/xfs/1215
@@ -0,0 +1,89 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1215
+#
+# Verify that XFS does not cause inode fork's extent count to overflow when
+# exchanging ranges between files
+. ./common/preamble
+_begin_fstest auto quick collapse fiexchange
+
+# Import common functions.
+. ./common/filter
+. ./common/inject
+
+# real QA test starts here
+
+_supported_fs xfs
+_require_scratch
+_require_xfs_debug
+_require_xfs_scratch_rmapbt
+_require_xfs_io_command "fcollapse"
+_require_xfs_io_command "exchangerange"
+_require_xfs_io_error_injection "reduce_max_iextents"
+
+echo "* Exchange extent forks"
+
+echo "Format and mount fs"
+_scratch_mkfs >> $seqres.full
+_scratch_mount >> $seqres.full
+
+bsize=$(_get_file_block_size $SCRATCH_MNT)
+
+srcfile=${SCRATCH_MNT}/srcfile
+donorfile=${SCRATCH_MNT}/donorfile
+
+echo "Create \$donorfile having an extent of length 67 blocks"
+$XFS_IO_PROG -f -s -c "pwrite -b $((17 * bsize)) 0 $((17 * bsize))" $donorfile \
+ >> $seqres.full
+
+# After the for loop the donor file will have the following extent layout
+# | 0-4 | 5 | 6 | 7 | 8 | 9 | 10 |
+echo "Fragment \$donorfile"
+for i in $(seq 5 10); do
+ start_offset=$((i * bsize))
+ $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $donorfile >> $seqres.full
+done
+
+echo "Create \$srcfile having an extent of length 18 blocks"
+$XFS_IO_PROG -f -s -c "pwrite -b $((18 * bsize)) 0 $((18 * bsize))" $srcfile \
+ >> $seqres.full
+
+echo "Fragment \$srcfile"
+# After the for loop the src file will have the following extent layout
+# | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7-10 |
+for i in $(seq 1 7); do
+ start_offset=$((i * bsize))
+ $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $srcfile >> $seqres.full
+done
+
+echo "Collect \$donorfile's extent count"
+donor_nr_exts=$(_xfs_get_fsxattr nextents $donorfile)
+
+echo "Collect \$srcfile's extent count"
+src_nr_exts=$(_xfs_get_fsxattr nextents $srcfile)
+
+echo "Inject reduce_max_iextents error tag"
+_scratch_inject_error reduce_max_iextents 1
+
+echo "Exchange \$srcfile's and \$donorfile's extent forks"
+$XFS_IO_PROG -f -c "exchangerange $donorfile" $srcfile >> $seqres.full 2>&1
+
+echo "Check for \$donorfile's extent count overflow"
+nextents=$(_xfs_get_fsxattr nextents $donorfile)
+
+if (( $nextents == $src_nr_exts )); then
+ echo "\$donorfile: Extent count overflow check failed"
+fi
+
+echo "Check for \$srcfile's extent count overflow"
+nextents=$(_xfs_get_fsxattr nextents $srcfile)
+
+if (( $nextents == $donor_nr_exts )); then
+ echo "\$srcfile: Extent count overflow check failed"
+fi
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1215.out b/tests/xfs/1215.out
new file mode 100644
index 0000000000..48edd56376
--- /dev/null
+++ b/tests/xfs/1215.out
@@ -0,0 +1,13 @@
+QA output created by 1215
+* Exchange extent forks
+Format and mount fs
+Create $donorfile having an extent of length 67 blocks
+Fragment $donorfile
+Create $srcfile having an extent of length 18 blocks
+Fragment $srcfile
+Collect $donorfile's extent count
+Collect $srcfile's extent count
+Inject reduce_max_iextents error tag
+Exchange $srcfile's and $donorfile's extent forks
+Check for $donorfile's extent count overflow
+Check for $srcfile's extent count overflow
diff --git a/tests/xfs/789 b/tests/xfs/789
index 00b98020f2..e3a332d7cf 100755
--- a/tests/xfs/789
+++ b/tests/xfs/789
@@ -7,7 +7,7 @@
# Simple tests of the old xfs swapext ioctl
. ./common/preamble
-_begin_fstest auto quick fiexchange swapext
+_begin_fstest auto quick swapext
# Override the default cleanup function.
_cleanup()
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 05/11] generic/717: remove obsolete check
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (3 preceding siblings ...)
2024-06-20 20:55 ` [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range Darrick J. Wong
@ 2024-06-20 20:55 ` Darrick J. Wong
2024-06-20 20:55 ` [PATCH 06/11] ltp/{fsstress,fsx}: make the exchangerange naming consistent Darrick J. Wong
` (5 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:55 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
The final version of the EXCHANGERANGE ioctl has dropped the flag that
enforced that the two files being operated upon were exactly the same
length as was specified in the ioctl parameters. Remove this check
since it's now defunct.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/generic/717 | 5 -----
tests/generic/717.out | 2 --
2 files changed, 7 deletions(-)
diff --git a/tests/generic/717 b/tests/generic/717
index ffabe2eaa1..7bc917e555 100755
--- a/tests/generic/717
+++ b/tests/generic/717
@@ -77,11 +77,6 @@ $XFS_IO_PROG -c "exchangerange -d 0 -s $(( blksz * nrblks )) -l 37 $dir/b" $dir/
echo file2 unaligned EOF to file1 nowhere near EOF
$XFS_IO_PROG -c "exchangerange -s 0 -d $(( blksz * nrblks )) -l 37 $dir/b" $dir/a
-echo Files of unequal length
-_pwrite_byte 0x58 $((blksz * nrblks)) $((blksz * 2)) $dir/a >> $seqres.full
-_pwrite_byte 0x59 $((blksz * nrblks)) $blksz $dir/b >> $seqres.full
-$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
-
echo Files on different filesystems
_pwrite_byte 0x58 0 $((blksz * nrblks)) $SCRATCH_MNT/c >> $seqres.full
$XFS_IO_PROG -c "exchangerange $SCRATCH_MNT/c" $dir/a
diff --git a/tests/generic/717.out b/tests/generic/717.out
index 85137bf412..e2c630d6d9 100644
--- a/tests/generic/717.out
+++ b/tests/generic/717.out
@@ -23,8 +23,6 @@ file1 unaligned EOF to file2 nowhere near EOF
exchangerange: Invalid argument
file2 unaligned EOF to file1 nowhere near EOF
exchangerange: Invalid argument
-Files of unequal length
-exchangerange: Bad address
Files on different filesystems
exchangerange: Invalid cross-device link
Files on different mounts
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 06/11] ltp/{fsstress,fsx}: make the exchangerange naming consistent
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (4 preceding siblings ...)
2024-06-20 20:55 ` [PATCH 05/11] generic/717: remove obsolete check Darrick J. Wong
@ 2024-06-20 20:55 ` Darrick J. Wong
2024-06-20 20:55 ` [PATCH 07/11] misc: flip HAVE_XFS_IOC_EXCHANGE_RANGE logic Darrick J. Wong
` (4 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:55 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
xchg_range/xchgrange -> exchangerange, since that's what the name has
become.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
ltp/fsstress.c | 24 ++++++++++++------------
ltp/fsx.c | 24 ++++++++++++------------
2 files changed, 24 insertions(+), 24 deletions(-)
diff --git a/ltp/fsstress.c b/ltp/fsstress.c
index 9d2631f7f9..70e0616521 100644
--- a/ltp/fsstress.c
+++ b/ltp/fsstress.c
@@ -143,7 +143,7 @@ typedef enum {
OP_URING_WRITE,
OP_WRITE,
OP_WRITEV,
- OP_XCHGRANGE,
+ OP_EXCHANGE_RANGE,
OP_LAST
} opty_t;
@@ -273,7 +273,7 @@ void uring_read_f(opnum_t, long);
void uring_write_f(opnum_t, long);
void write_f(opnum_t, long);
void writev_f(opnum_t, long);
-void xchgrange_f(opnum_t, long);
+void exchangerange_f(opnum_t, long);
char *xattr_flag_to_string(int);
@@ -343,7 +343,7 @@ struct opdesc ops[OP_LAST] = {
[OP_URING_WRITE] = {"uring_write", uring_write_f, 1, 1 },
[OP_WRITE] = {"write", write_f, 4, 1 },
[OP_WRITEV] = {"writev", writev_f, 4, 1 },
- [OP_XCHGRANGE] = {"xchgrange", xchgrange_f, 2, 1 },
+ [OP_EXCHANGE_RANGE]= {"exchangerange", exchangerange_f, 2, 1 },
}, *ops_end;
flist_t flist[FT_nft] = {
@@ -2604,7 +2604,7 @@ chown_f(opnum_t opno, long r)
/* exchange some arbitrary range of f1 to f2...fn. */
void
-xchgrange_f(
+exchangerange_f(
opnum_t opno,
long r)
{
@@ -2634,7 +2634,7 @@ xchgrange_f(
init_pathname(&fpath1);
if (!get_fname(FT_REGm, r, &fpath1, NULL, NULL, &v1)) {
if (v1)
- printf("%d/%lld: xchgrange read - no filename\n",
+ printf("%d/%lld: exchangerange read - no filename\n",
procid, opno);
goto out_fpath1;
}
@@ -2642,7 +2642,7 @@ xchgrange_f(
init_pathname(&fpath2);
if (!get_fname(FT_REGm, random(), &fpath2, NULL, NULL, &v2)) {
if (v2)
- printf("%d/%lld: xchgrange write - no filename\n",
+ printf("%d/%lld: exchangerange write - no filename\n",
procid, opno);
goto out_fpath2;
}
@@ -2653,7 +2653,7 @@ xchgrange_f(
check_cwd();
if (fd1 < 0) {
if (v1)
- printf("%d/%lld: xchgrange read - open %s failed %d\n",
+ printf("%d/%lld: exchangerange read - open %s failed %d\n",
procid, opno, fpath1.path, e);
goto out_fpath2;
}
@@ -2663,7 +2663,7 @@ xchgrange_f(
check_cwd();
if (fd2 < 0) {
if (v2)
- printf("%d/%lld: xchgrange write - open %s failed %d\n",
+ printf("%d/%lld: exchangerange write - open %s failed %d\n",
procid, opno, fpath2.path, e);
goto out_fd1;
}
@@ -2671,7 +2671,7 @@ xchgrange_f(
/* Get file stats */
if (fstat64(fd1, &stat1) < 0) {
if (v1)
- printf("%d/%lld: xchgrange read - fstat64 %s failed %d\n",
+ printf("%d/%lld: exchangerange read - fstat64 %s failed %d\n",
procid, opno, fpath1.path, errno);
goto out_fd2;
}
@@ -2679,7 +2679,7 @@ xchgrange_f(
if (fstat64(fd2, &stat2) < 0) {
if (v2)
- printf("%d/%lld: xchgrange write - fstat64 %s failed %d\n",
+ printf("%d/%lld: exchangerange write - fstat64 %s failed %d\n",
procid, opno, fpath2.path, errno);
goto out_fd2;
}
@@ -2688,7 +2688,7 @@ xchgrange_f(
if (stat1.st_size < (stat1.st_blksize * 2) ||
stat2.st_size < (stat2.st_blksize * 2)) {
if (v2)
- printf("%d/%lld: xchgrange - files are too small\n",
+ printf("%d/%lld: exchangerange - files are too small\n",
procid, opno);
goto out_fd2;
}
@@ -2745,7 +2745,7 @@ xchgrange_f(
goto retry;
}
if (v1 || v2) {
- printf("%d/%lld: xchgrange %s%s [%lld,%lld] -> %s%s [%lld,%lld]",
+ printf("%d/%lld: exchangerange %s%s [%lld,%lld] -> %s%s [%lld,%lld]",
procid, opno,
fpath1.path, inoinfo1, (long long)off1, (long long)len,
fpath2.path, inoinfo2, (long long)off2, (long long)len);
diff --git a/ltp/fsx.c b/ltp/fsx.c
index 777ba0de5d..6ff5e3720f 100644
--- a/ltp/fsx.c
+++ b/ltp/fsx.c
@@ -176,7 +176,7 @@ int check_file = 0; /* -X flag enables */
int clone_range_calls = 1; /* -J flag disables */
int dedupe_range_calls = 1; /* -B flag disables */
int copy_range_calls = 1; /* -E flag disables */
-int xchg_range_calls = 1; /* -0 flag disables */
+int exchange_range_calls = 1; /* -0 flag disables */
int integrity = 0; /* -i flag */
int fsxgoodfd = 0;
int o_direct; /* -Z */
@@ -272,7 +272,7 @@ static const char *op_names[] = {
[OP_DEDUPE_RANGE] = "dedupe_range",
[OP_COPY_RANGE] = "copy_range",
[OP_FSYNC] = "fsync",
- [OP_EXCHANGE_RANGE] = "xchg_range",
+ [OP_EXCHANGE_RANGE] = "exchange_range",
};
static const char *op_name(int operation)
@@ -1393,7 +1393,7 @@ do_insert_range(unsigned offset, unsigned length)
static __u64 swap_flags = 0;
int
-test_xchg_range(void)
+test_exchange_range(void)
{
struct xfs_exch_range fsr = {
.file1_fd = fd,
@@ -1425,7 +1425,7 @@ test_xchg_range(void)
}
void
-do_xchg_range(unsigned offset, unsigned length, unsigned dest)
+do_exchange_range(unsigned offset, unsigned length, unsigned dest)
{
struct xfs_exch_range fsr = {
.file1_fd = fd,
@@ -1473,7 +1473,7 @@ do_xchg_range(unsigned offset, unsigned length, unsigned dest)
if (ioctl(fd, XFS_IOC_EXCHANGE_RANGE, &fsr) == -1) {
prt("exchange range: 0x%x to 0x%x at 0x%x\n", offset,
offset + length, dest);
- prterr("do_xchg_range: XFS_IOC_EXCHANGE_RANGE");
+ prterr("do_exchange_range: XFS_IOC_EXCHANGE_RANGE");
report_failure(161);
goto out_free;
}
@@ -1487,13 +1487,13 @@ do_xchg_range(unsigned offset, unsigned length, unsigned dest)
#else
int
-test_xchg_range(void)
+test_exchange_range(void)
{
return 0;
}
void
-do_xchg_range(unsigned offset, unsigned length, unsigned dest)
+do_exchange_range(unsigned offset, unsigned length, unsigned dest)
{
return;
}
@@ -2231,7 +2231,7 @@ test(void)
}
break;
case OP_EXCHANGE_RANGE:
- if (!xchg_range_calls) {
+ if (!exchange_range_calls) {
log5(op, offset, size, offset2, FL_SKIPPED);
goto out;
}
@@ -2330,7 +2330,7 @@ test(void)
goto out;
}
- do_xchg_range(offset, size, offset2);
+ do_exchange_range(offset, size, offset2);
break;
case OP_CLONE_RANGE:
if (size == 0) {
@@ -2936,7 +2936,7 @@ main(int argc, char **argv)
insert_range_calls = 0;
break;
case '0':
- xchg_range_calls = 0;
+ exchange_range_calls = 0;
break;
case 'J':
clone_range_calls = 0;
@@ -3199,8 +3199,8 @@ main(int argc, char **argv)
dedupe_range_calls = test_dedupe_range();
if (copy_range_calls)
copy_range_calls = test_copy_range();
- if (xchg_range_calls)
- xchg_range_calls = test_xchg_range();
+ if (exchange_range_calls)
+ exchange_range_calls = test_exchange_range();
while (keep_running())
if (!test())
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 07/11] misc: flip HAVE_XFS_IOC_EXCHANGE_RANGE logic
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (5 preceding siblings ...)
2024-06-20 20:55 ` [PATCH 06/11] ltp/{fsstress,fsx}: make the exchangerange naming consistent Darrick J. Wong
@ 2024-06-20 20:55 ` Darrick J. Wong
2024-06-20 20:56 ` [PATCH 08/11] src/fiexchange.h: update XFS_IOC_EXCHANGE_RANGE definitions Darrick J. Wong
` (3 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:55 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
We only need to include src/fiexchange.h if the system's xfslibs package
either doesn't define it or is so old that we want a newer definition.
Invert the logic so that we only use src/fiexchange if we need the
override.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
configure.ac | 2 +-
include/builddefs.in | 2 +-
ltp/Makefile | 4 ++--
m4/package_xfslibs.m4 | 13 +++++++------
src/Makefile | 4 ++--
src/global.h | 2 +-
src/vfs/Makefile | 4 ++--
7 files changed, 16 insertions(+), 15 deletions(-)
diff --git a/configure.ac b/configure.ac
index 4e567d3c96..c81411e735 100644
--- a/configure.ac
+++ b/configure.ac
@@ -70,7 +70,7 @@ AC_HAVE_SEEK_DATA
AC_HAVE_BMV_OF_SHARED
AC_HAVE_NFTW
AC_HAVE_RLIMIT_NOFILE
-AC_HAVE_XFS_IOC_EXCHANGE_RANGE
+AC_NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
AC_HAVE_FICLONE
AC_CHECK_FUNCS([renameat2])
diff --git a/include/builddefs.in b/include/builddefs.in
index ce95fe7d4b..7274cde8d0 100644
--- a/include/builddefs.in
+++ b/include/builddefs.in
@@ -72,7 +72,7 @@ HAVE_SEEK_DATA = @have_seek_data@
HAVE_NFTW = @have_nftw@
HAVE_BMV_OF_SHARED = @have_bmv_of_shared@
HAVE_RLIMIT_NOFILE = @have_rlimit_nofile@
-HAVE_XFS_IOC_EXCHANGE_RANGE = @have_xfs_ioc_exchange_range@
+NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE = @need_internal_xfs_ioc_exchange_range@
HAVE_FICLONE = @have_ficlone@
GCCFLAGS = -funsigned-char -fno-strict-aliasing -Wall
diff --git a/ltp/Makefile b/ltp/Makefile
index c0b2824076..0611c5efe9 100644
--- a/ltp/Makefile
+++ b/ltp/Makefile
@@ -36,8 +36,8 @@ ifeq ($(HAVE_COPY_FILE_RANGE),yes)
LCFLAGS += -DHAVE_COPY_FILE_RANGE
endif
-ifeq ($(HAVE_XFS_IOC_EXCHANGE_RANGE),yes)
-LCFLAGS += -DHAVE_XFS_IOC_EXCHANGE_RANGE
+ifeq ($(NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE),yes)
+LCFLAGS += -DNEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
endif
default: depend $(TARGETS)
diff --git a/m4/package_xfslibs.m4 b/m4/package_xfslibs.m4
index 2f1dbc6951..3cc88a27d2 100644
--- a/m4/package_xfslibs.m4
+++ b/m4/package_xfslibs.m4
@@ -92,16 +92,17 @@ AC_DEFUN([AC_HAVE_BMV_OF_SHARED],
AC_SUBST(have_bmv_of_shared)
])
-# Check if we have XFS_IOC_EXCHANGE_RANGE
-AC_DEFUN([AC_HAVE_XFS_IOC_EXCHANGE_RANGE],
- [ AC_MSG_CHECKING([for XFS_IOC_EXCHANGE_RANGE])
+# Check if we need to override the system XFS_IOC_EXCHANGE_RANGE
+AC_DEFUN([AC_NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE],
+ [ AC_MSG_CHECKING([for new enough XFS_IOC_EXCHANGE_RANGE])
AC_LINK_IFELSE([AC_LANG_PROGRAM([[
#define _GNU_SOURCE
#include <xfs/xfs.h>
]], [[
struct xfs_exch_range obj;
ioctl(-1, XFS_IOC_EXCHANGE_RANGE, &obj);
- ]])],[have_xfs_ioc_exchange_range=yes
- AC_MSG_RESULT(yes)],[AC_MSG_RESULT(no)])
- AC_SUBST(have_xfs_ioc_exchange_range)
+ ]])],[AC_MSG_RESULT(yes)],
+ [need_internal_xfs_ioc_exchange_range=yes
+ AC_MSG_RESULT(no)])
+ AC_SUBST(need_internal_xfs_ioc_exchange_range)
])
diff --git a/src/Makefile b/src/Makefile
index ab98a06f49..9979613711 100644
--- a/src/Makefile
+++ b/src/Makefile
@@ -99,8 +99,8 @@ ifeq ($(HAVE_FICLONE),yes)
TARGETS += t_reflink_read_race
endif
-ifeq ($(HAVE_XFS_IOC_EXCHANGE_RANGE),yes)
-LCFLAGS += -DHAVE_XFS_IOC_EXCHANGE_RANGE
+ifeq ($(NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE),yes)
+LCFLAGS += -DNEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
endif
CFILES = $(TARGETS:=.c)
diff --git a/src/global.h b/src/global.h
index 4f92308d6c..157c898065 100644
--- a/src/global.h
+++ b/src/global.h
@@ -171,7 +171,7 @@
#include <sys/mman.h>
#endif
-#ifndef HAVE_XFS_IOC_EXCHANGE_RANGE
+#ifdef NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
# include "fiexchange.h"
#endif
diff --git a/src/vfs/Makefile b/src/vfs/Makefile
index 868540f578..a9c37e92ea 100644
--- a/src/vfs/Makefile
+++ b/src/vfs/Makefile
@@ -19,8 +19,8 @@ ifeq ($(HAVE_URING), true)
LLDLIBS += -luring
endif
-ifeq ($(HAVE_XFS_IOC_EXCHANGE_RANGE),yes)
-LCFLAGS += -DHAVE_XFS_IOC_EXCHANGE_RANGE
+ifeq ($(NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE),yes)
+LCFLAGS += -DNEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
endif
default: depend $(TARGETS)
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 08/11] src/fiexchange.h: update XFS_IOC_EXCHANGE_RANGE definitions
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (6 preceding siblings ...)
2024-06-20 20:55 ` [PATCH 07/11] misc: flip HAVE_XFS_IOC_EXCHANGE_RANGE logic Darrick J. Wong
@ 2024-06-20 20:56 ` Darrick J. Wong
2024-06-20 20:56 ` [PATCH 09/11] xfs/122: fix for exchrange conversion Darrick J. Wong
` (2 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:56 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Update to use our new file content exchange ioctl definitions.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
ltp/fsstress.c | 10 +-----
ltp/fsx.c | 19 ++---------
m4/package_xfslibs.m4 | 2 +
src/fiexchange.h | 84 ++++++++++++-------------------------------------
src/global.h | 10 ++++++
src/xfsfind.c | 1 -
tests/generic/724 | 2 +
tests/xfs/791 | 2 +
8 files changed, 37 insertions(+), 93 deletions(-)
diff --git a/ltp/fsstress.c b/ltp/fsstress.c
index 70e0616521..3749da0e9a 100644
--- a/ltp/fsstress.c
+++ b/ltp/fsstress.c
@@ -2609,8 +2609,7 @@ exchangerange_f(
long r)
{
#ifdef XFS_IOC_EXCHANGE_RANGE
- struct xfs_exch_range fxr = { 0 };
- static __u64 swap_flags = 0;
+ struct xfs_exchange_range fxr = { 0 };
struct pathname fpath1;
struct pathname fpath2;
struct stat64 stat1;
@@ -2734,16 +2733,9 @@ exchangerange_f(
fxr.file1_offset = off1;
fxr.length = len;
fxr.file2_offset = off2;
- fxr.flags = swap_flags;
-retry:
ret = ioctl(fd2, XFS_IOC_EXCHANGE_RANGE, &fxr);
e = ret < 0 ? errno : 0;
- if (e == EOPNOTSUPP && !(swap_flags & XFS_EXCH_RANGE_NONATOMIC)) {
- swap_flags = XFS_EXCH_RANGE_NONATOMIC;
- fxr.flags |= swap_flags;
- goto retry;
- }
if (v1 || v2) {
printf("%d/%lld: exchangerange %s%s [%lld,%lld] -> %s%s [%lld,%lld]",
procid, opno,
diff --git a/ltp/fsx.c b/ltp/fsx.c
index 6ff5e3720f..2dc59b06fc 100644
--- a/ltp/fsx.c
+++ b/ltp/fsx.c
@@ -1390,29 +1390,17 @@ do_insert_range(unsigned offset, unsigned length)
#endif
#ifdef XFS_IOC_EXCHANGE_RANGE
-static __u64 swap_flags = 0;
-
int
test_exchange_range(void)
{
- struct xfs_exch_range fsr = {
+ struct xfs_exchange_range fsr = {
.file1_fd = fd,
- .flags = XFS_EXCH_RANGE_DRY_RUN | swap_flags,
+ .flags = XFS_EXCHANGE_RANGE_DRY_RUN,
};
int ret, e;
-retry:
ret = ioctl(fd, XFS_IOC_EXCHANGE_RANGE, &fsr);
e = ret < 0 ? errno : 0;
- if (e == EOPNOTSUPP && !(swap_flags & XFS_EXCH_RANGE_NONATOMIC)) {
- /*
- * If the call fails with atomic mode, try again with non
- * atomic mode.
- */
- swap_flags = XFS_EXCH_RANGE_NONATOMIC;
- fsr.flags |= swap_flags;
- goto retry;
- }
if (e == EOPNOTSUPP || errno == ENOTTY) {
if (!quiet)
fprintf(stderr,
@@ -1427,12 +1415,11 @@ test_exchange_range(void)
void
do_exchange_range(unsigned offset, unsigned length, unsigned dest)
{
- struct xfs_exch_range fsr = {
+ struct xfs_exchange_range fsr = {
.file1_fd = fd,
.file1_offset = offset,
.file2_offset = dest,
.length = length,
- .flags = swap_flags,
};
void *p;
diff --git a/m4/package_xfslibs.m4 b/m4/package_xfslibs.m4
index 3cc88a27d2..5604989e34 100644
--- a/m4/package_xfslibs.m4
+++ b/m4/package_xfslibs.m4
@@ -99,7 +99,7 @@ AC_DEFUN([AC_NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE],
#define _GNU_SOURCE
#include <xfs/xfs.h>
]], [[
- struct xfs_exch_range obj;
+ struct xfs_exchange_range obj;
ioctl(-1, XFS_IOC_EXCHANGE_RANGE, &obj);
]])],[AC_MSG_RESULT(yes)],
[need_internal_xfs_ioc_exchange_range=yes
diff --git a/src/fiexchange.h b/src/fiexchange.h
index 6a3ae8964d..1f556e69dc 100644
--- a/src/fiexchange.h
+++ b/src/fiexchange.h
@@ -16,86 +16,42 @@
* called against (which we'll call file2). Filesystems must be able to
* restart and complete the operation even after the system goes down.
*/
-struct xfs_exch_range {
- __s64 file1_fd;
- __s64 file1_offset; /* file1 offset, bytes */
- __s64 file2_offset; /* file2 offset, bytes */
- __s64 length; /* bytes to exchange */
+struct xfs_exchange_range {
+ __s32 file1_fd;
+ __u32 pad; /* must be zeroes */
+ __u64 file1_offset; /* file1 offset, bytes */
+ __u64 file2_offset; /* file2 offset, bytes */
+ __u64 length; /* bytes to exchange */
- __u64 flags; /* see XFS_EXCH_RANGE_* below */
-
- /* file2 metadata for optional freshness checks */
- __s64 file2_ino; /* inode number */
- __s64 file2_mtime; /* modification time */
- __s64 file2_ctime; /* change time */
- __s32 file2_mtime_nsec; /* mod time, nsec */
- __s32 file2_ctime_nsec; /* change time, nsec */
-
- __u64 pad[6]; /* must be zeroes */
+ __u64 flags; /* see XFS_EXCHANGE_RANGE_* below */
};
-/*
- * Atomic exchange operations are not required. This relaxes the requirement
- * that the filesystem must be able to complete the operation after a crash.
- */
-#define XFS_EXCH_RANGE_NONATOMIC (1 << 0)
-
-/*
- * Check that file2's inode number, mtime, and ctime against the values
- * provided, and return -EBUSY if there isn't an exact match.
- */
-#define XFS_EXCH_RANGE_FILE2_FRESH (1 << 1)
-
-/*
- * Check that the file1's length is equal to file1_offset + length, and that
- * file2's length is equal to file2_offset + length. Returns -EDOM if there
- * isn't an exact match.
- */
-#define XFS_EXCH_RANGE_FULL_FILES (1 << 2)
-
/*
* Exchange file data all the way to the ends of both files, and then exchange
* the file sizes. This flag can be used to replace a file's contents with a
* different amount of data. length will be ignored.
*/
-#define XFS_EXCH_RANGE_TO_EOF (1 << 3)
+#define XFS_EXCHANGE_RANGE_TO_EOF (1ULL << 0)
/* Flush all changes in file data and file metadata to disk before returning. */
-#define XFS_EXCH_RANGE_FSYNC (1 << 4)
+#define XFS_EXCHANGE_RANGE_DSYNC (1ULL << 1)
/* Dry run; do all the parameter verification but do not change anything. */
-#define XFS_EXCH_RANGE_DRY_RUN (1 << 5)
+#define XFS_EXCHANGE_RANGE_DRY_RUN (1ULL << 2)
/*
- * Only exchange ranges where file1's range maps to a written extent. This can
- * be used to emulate scatter-gather atomic writes with a temp file.
+ * Exchange only the parts of the two files where the file allocation units
+ * mapped to file1's range have been written to. This can accelerate
+ * scatter-gather atomic writes with a temp file if all writes are aligned to
+ * the file allocation unit.
*/
-#define XFS_EXCH_RANGE_FILE1_WRITTEN (1 << 6)
+#define XFS_EXCHANGE_RANGE_FILE1_WRITTEN (1ULL << 3)
-/*
- * Commit the contents of file1 into file2 if file2 has the same inode number,
- * mtime, and ctime as the arguments provided to the call. The old contents of
- * file2 will be moved to file1.
- *
- * With this flag, all committed information can be retrieved even if the
- * system crashes or is rebooted. This includes writing through or flushing a
- * disk cache if present. The call blocks until the device reports that the
- * commit is complete.
- *
- * This flag should not be combined with NONATOMIC. It can be combined with
- * FILE1_WRITTEN.
- */
-#define XFS_EXCH_RANGE_COMMIT (XFS_EXCH_RANGE_FILE2_FRESH | \
- XFS_EXCH_RANGE_FSYNC)
-
-#define XFS_EXCH_RANGE_ALL_FLAGS (XFS_EXCH_RANGE_NONATOMIC | \
- XFS_EXCH_RANGE_FILE2_FRESH | \
- XFS_EXCH_RANGE_FULL_FILES | \
- XFS_EXCH_RANGE_TO_EOF | \
- XFS_EXCH_RANGE_FSYNC | \
- XFS_EXCH_RANGE_DRY_RUN | \
- XFS_EXCH_RANGE_FILE1_WRITTEN)
+#define XFS_EXCHANGE_RANGE_ALL_FLAGS (XFS_EXCHANGE_RANGE_TO_EOF | \
+ XFS_EXCHANGE_RANGE_DSYNC | \
+ XFS_EXCHANGE_RANGE_DRY_RUN | \
+ XFS_EXCHANGE_RANGE_FILE1_WRITTEN)
-#define XFS_IOC_EXCHANGE_RANGE _IOWR('X', 129, struct xfs_exch_range)
+#define XFS_IOC_EXCHANGE_RANGE _IOWR('X', 129, struct xfs_exchange_range)
#endif /* _LINUX_FIEXCHANGE_H */
diff --git a/src/global.h b/src/global.h
index 157c898065..fc48d82e03 100644
--- a/src/global.h
+++ b/src/global.h
@@ -9,10 +9,20 @@
#include <config.h>
+#ifdef NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
+/* Override struct xfs_exchange_range in xfslibs */
+# define xfs_exchange_range sys_xfs_exchange_range
+#endif
+
#ifdef HAVE_XFS_XFS_H
#include <xfs/xfs.h>
#endif
+#ifdef NEED_INTERNAL_XFS_IOC_EXCHANGE_RANGE
+# undef xfs_exchange_range
+# undef XFS_IOC_EXCHANGE_RANGE
+#endif
+
#ifdef HAVE_XFS_LIBXFS_H
#include <xfs/libxfs.h>
#endif
diff --git a/src/xfsfind.c b/src/xfsfind.c
index 6b0a93e793..c81deaf64f 100644
--- a/src/xfsfind.c
+++ b/src/xfsfind.c
@@ -10,7 +10,6 @@
#include <unistd.h>
#include <ftw.h>
#include <linux/fs.h>
-#include <xfs/xfs.h>
#include "global.h"
diff --git a/tests/generic/724 b/tests/generic/724
index 4cc02946dd..2d58ccb9d5 100755
--- a/tests/generic/724
+++ b/tests/generic/724
@@ -5,7 +5,7 @@
# FS QA Test No. 724
#
# Test scatter-gather atomic file writes. We create a temporary file, write
-# sparsely to it, then use XFS_EXCHRANGE_FILE1_WRITTEN flag to swap
+# sparsely to it, then use XFS_EXCHANGE_RANGE_FILE1_WRITTEN flag to swap
# atomicallly only the ranges that we wrote.
. ./common/preamble
diff --git a/tests/xfs/791 b/tests/xfs/791
index 37f58972c4..62d89f71bc 100755
--- a/tests/xfs/791
+++ b/tests/xfs/791
@@ -5,7 +5,7 @@
# FS QA Test No. 791
#
# Test scatter-gather atomic file writes. We create a temporary file, write
-# sparsely to it, then use XFS_EXCHRANGE_FILE1_WRITTEN flag to swap
+# sparsely to it, then use XFS_EXCHANGE_RANGE_FILE1_WRITTEN flag to swap
# atomicallly only the ranges that we wrote. Inject an error so that we can
# test that log recovery finishes the swap.
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 09/11] xfs/122: fix for exchrange conversion
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (7 preceding siblings ...)
2024-06-20 20:56 ` [PATCH 08/11] src/fiexchange.h: update XFS_IOC_EXCHANGE_RANGE definitions Darrick J. Wong
@ 2024-06-20 20:56 ` Darrick J. Wong
2024-06-20 20:56 ` [PATCH 10/11] xfs/206: screen out exchange-range from golden output Darrick J. Wong
2024-06-20 20:56 ` [PATCH 11/11] exchangerange: make sure that we don't swap unwritten extents unless they're part of a rt extent Darrick J. Wong
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:56 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Fix this test for the swapext -> exchrange conversion.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/122.out | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/tests/xfs/122.out b/tests/xfs/122.out
index a2b57cfb9b..86c806d4b5 100644
--- a/tests/xfs/122.out
+++ b/tests/xfs/122.out
@@ -92,7 +92,7 @@ sizeof(struct xfs_disk_dquot) = 104
sizeof(struct xfs_dqblk) = 136
sizeof(struct xfs_dsb) = 264
sizeof(struct xfs_dsymlink_hdr) = 56
-sizeof(struct xfs_exch_range) = 120
+sizeof(struct xfs_exchange_range) = 40
sizeof(struct xfs_extent_data) = 24
sizeof(struct xfs_extent_data_info) = 32
sizeof(struct xfs_fs_eofblocks) = 128
@@ -121,9 +121,9 @@ sizeof(struct xfs_rud_log_format) = 16
sizeof(struct xfs_rui_log_format) = 16
sizeof(struct xfs_scrub_metadata) = 64
sizeof(struct xfs_swap_extent) = 64
-sizeof(struct xfs_sxd_log_format) = 16
-sizeof(struct xfs_sxi_log_format) = 80
sizeof(struct xfs_unmount_log_format) = 8
+sizeof(struct xfs_xmd_log_format) = 16
+sizeof(struct xfs_xmi_log_format) = 88
sizeof(union xfs_rtword_raw) = 4
sizeof(union xfs_suminfo_raw) = 4
sizeof(xfs_agf_t) = 224
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 10/11] xfs/206: screen out exchange-range from golden output
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (8 preceding siblings ...)
2024-06-20 20:56 ` [PATCH 09/11] xfs/122: fix for exchrange conversion Darrick J. Wong
@ 2024-06-20 20:56 ` Darrick J. Wong
2024-06-20 20:56 ` [PATCH 11/11] exchangerange: make sure that we don't swap unwritten extents unless they're part of a rt extent Darrick J. Wong
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:56 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Fix this so that exchange-range doesn't trigger test failures.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/206 | 1 +
1 file changed, 1 insertion(+)
diff --git a/tests/xfs/206 b/tests/xfs/206
index cb346b6dc9..f973980eb2 100755
--- a/tests/xfs/206
+++ b/tests/xfs/206
@@ -64,6 +64,7 @@ mkfs_filter()
-e "s/\(sunit=\)\([0-9]* blks,\)/\10 blks,/" \
-e "s/, lazy-count=[0-9]//" \
-e "/.*crc=/d" \
+ -e "/exchange=/d" \
-e "/^Default configuration/d"
}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 11/11] exchangerange: make sure that we don't swap unwritten extents unless they're part of a rt extent
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
` (9 preceding siblings ...)
2024-06-20 20:56 ` [PATCH 10/11] xfs/206: screen out exchange-range from golden output Darrick J. Wong
@ 2024-06-20 20:56 ` Darrick J. Wong
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:56 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
By default, the FILE1_WRITTEN flag for the EXCHANGERANGE ioctl isn't
supposed to touch anything except for written extents. In other words,
it shouldn't exchange delalloc reservations, unwritten preallocations,
or holes. The XFS implementation flushes dirty pagecache to disk so
there should never be delalloc reservations running through the
exchangerange machinery, but there can be unwritten extents.
Hence, write a test to make sure that unwritten extents don't get moved
around. This test opts itself out for realtime filesystems where the
allocation unit is larger than 1 fsblock because xfs has to move full
allocation units, and that requires exchanging of partially written rt
extents.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/1213 | 73 ++++++++++++++++
tests/xfs/1213.out | 2
tests/xfs/1214 | 232 ++++++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1214.out | 2
4 files changed, 309 insertions(+)
create mode 100755 tests/xfs/1213
create mode 100644 tests/xfs/1213.out
create mode 100755 tests/xfs/1214
create mode 100644 tests/xfs/1214.out
diff --git a/tests/xfs/1213 b/tests/xfs/1213
new file mode 100755
index 0000000000..a9f7e3706e
--- /dev/null
+++ b/tests/xfs/1213
@@ -0,0 +1,73 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1213
+#
+# Make sure that the XFS_EXCHANGE_RANGE_FILE1_WRITTEN actually skips holes and
+# unwritten extents on the data device and the rt device when the rextsize
+# is 1 fsblock.
+#
+. ./common/preamble
+_begin_fstest auto fiexchange
+
+. ./common/filter
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs generic
+_require_xfs_io_command "falloc"
+_require_xfs_io_command exchangerange
+_require_scratch
+
+_scratch_mkfs >> $seqres.full
+_scratch_mount
+
+# This test doesn't deal with the unwritten extents that must be created when
+# the realtime file allocation unit is larger than the fs blocksize.
+file_blksz=$(_get_file_block_size $SCRATCH_MNT)
+fs_blksz=$(_get_block_size $SCRATCH_MNT)
+test "$file_blksz" -eq "$fs_blksz" || \
+ _notrun "test requires file alloc unit ($file_blksz) == fs block size ($fs_blksz)"
+
+swap_and_check_contents() {
+ local a="$1"
+ local b="$2"
+ local tag="$3"
+
+ local a_md5_before=$(md5sum $a | awk '{print $1}')
+ local b_md5_before=$(md5sum $b | awk '{print $1}')
+
+ # Test exchangerange. -w means skip holes in /b
+ echo "swap $tag" >> $seqres.full
+ $XFS_IO_PROG -c fsync -c 'bmap -elpvvvv' $a $b >> $seqres.full
+ $XFS_IO_PROG -c "exchangerange -f -w $b" $a >> $seqres.full
+ $XFS_IO_PROG -c 'bmap -elpvvvv' $a $b >> $seqres.full
+ _scratch_cycle_mount
+
+ local a_md5_after=$(md5sum $a | awk '{print $1}')
+ local b_md5_after=$(md5sum $b | awk '{print $1}')
+
+ test "$a_md5_before" != "$a_md5_after" && \
+ echo "$a: md5 $a_md5_before -> $a_md5_after in $tag"
+
+ test "$b_md5_before" != "$b_md5_after" && \
+ echo "$b: md5 $b_md5_before -> $b_md5_after in $tag"
+}
+
+# plain preallocations on the data device
+$XFS_IO_PROG -c 'extsize 0' $SCRATCH_MNT
+_pwrite_byte 0x58 0 1m $SCRATCH_MNT/dar >> $seqres.full
+$XFS_IO_PROG -f -c 'truncate 1m' -c "falloc 640k 64k" $SCRATCH_MNT/dbr
+swap_and_check_contents $SCRATCH_MNT/dar $SCRATCH_MNT/dbr "plain prealloc"
+
+# extent size hints on the data device
+$XFS_IO_PROG -c 'extsize 1m' $SCRATCH_MNT
+_pwrite_byte 0x58 0 1m $SCRATCH_MNT/dae >> $seqres.full
+$XFS_IO_PROG -f -c 'truncate 1m' -c "falloc 640k 64k" $SCRATCH_MNT/dbe
+swap_and_check_contents $SCRATCH_MNT/dae $SCRATCH_MNT/dbe "data dev extsize prealloc"
+
+echo Silence is golden
+status=0
+exit
diff --git a/tests/xfs/1213.out b/tests/xfs/1213.out
new file mode 100644
index 0000000000..5a28b8b45f
--- /dev/null
+++ b/tests/xfs/1213.out
@@ -0,0 +1,2 @@
+QA output created by 1213
+Silence is golden
diff --git a/tests/xfs/1214 b/tests/xfs/1214
new file mode 100755
index 0000000000..3451565445
--- /dev/null
+++ b/tests/xfs/1214
@@ -0,0 +1,232 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1214
+#
+# Make sure that the XFS_EXCHANGE_RANGE_FILE1_WRITTEN actually skips holes and
+# unwritten extents on the realtime device when the rextsize is larger than 1
+# fs block.
+#
+. ./common/preamble
+_begin_fstest auto fiexchange
+
+. ./common/filter
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs generic
+_require_xfs_io_command "falloc"
+_require_xfs_io_command exchangerange
+_require_realtime
+_require_scratch
+
+_scratch_mkfs >> $seqres.full
+_scratch_mount
+
+# This test only deals with the unwritten extents that must be created when
+# the realtime file allocation unit is larger than the fs blocksize.
+file_blksz=$(_get_file_block_size $SCRATCH_MNT)
+fs_blksz=$(_get_block_size $SCRATCH_MNT)
+test "$file_blksz" -ge "$((3 * fs_blksz))" || \
+ _notrun "test requires file alloc unit ($file_blksz) >= 3 * fs block size ($fs_blksz)"
+
+swap_and_check_contents() {
+ local a="$1"
+ local b="$2"
+ local tag="$3"
+
+ sync
+
+ # Test exchangerange. -w means skip holes in /b
+ echo "swap $tag" >> $seqres.full
+ $XFS_IO_PROG -c 'bmap -elpvvvv' $a $b >> $seqres.full
+ $XFS_IO_PROG -c "exchangerange -f -w $b" $a >> $seqres.full
+ $XFS_IO_PROG -c 'bmap -elpvvvv' $a $b >> $seqres.full
+
+ local a_md5_before=$(md5sum $a | awk '{print $1}')
+ local b_md5_before=$(md5sum $b | awk '{print $1}')
+
+ _scratch_cycle_mount
+
+ local a_md5_check=$(md5sum $a.chk | awk '{print $1}')
+ local b_md5_check=$(md5sum $b.chk | awk '{print $1}')
+
+ local a_md5_after=$(md5sum $a | awk '{print $1}')
+ local b_md5_after=$(md5sum $b | awk '{print $1}')
+
+ test "$a_md5_before" != "$a_md5_after" && \
+ echo "$a: md5 $a_md5_before -> $a_md5_after in $tag"
+
+ test "$b_md5_before" != "$b_md5_after" && \
+ echo "$b: md5 $b_md5_before -> $b_md5_after in $tag"
+
+ if [ "$a_md5_check" != "$a_md5_after" ]; then
+ echo "$a: md5 $a_md5_after, expected $a_md5_check in $tag" | tee -a $seqres.full
+ echo "$a contents" >> $seqres.full
+ od -tx1 -Ad -c $a >> $seqres.full
+ echo "$a.chk contents" >> $seqres.full
+ od -tx1 -Ad -c $a.chk >> $seqres.full
+ fi
+
+ if [ "$b_md5_check" != "$b_md5_after" ]; then
+ echo "$b: md5 $b_md5_after, expected $b_md5_check in $tag" | tee -a $seqres.full
+ echo "$b contents" >> $seqres.full
+ od -tx1 -Ad -c $b >> $seqres.full
+ echo "$b.chk contents" >> $seqres.full
+ od -tx1 -Ad -c $b.chk >> $seqres.full
+ fi
+}
+
+filesz=$((5 * file_blksz))
+
+# first rtblock of the second rtextent is unwritten
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x59 $((file_blksz + fs_blksz)) $((file_blksz - fs_blksz))" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $file_blksz" \
+ -c "pwrite -S 0x00 $file_blksz $fs_blksz" \
+ -c "pwrite -S 0x59 $((file_blksz + fs_blksz)) $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x58 $((file_blksz * 2)) $((filesz - (file_blksz * 2) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $file_blksz $file_blksz" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "first rtb of second rtx"
+
+# second rtblock of the second rtextent is unwritten
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x59 $file_blksz $fs_blksz" \
+ -c "pwrite -S 0x59 $((file_blksz + (2 * fs_blksz) )) $((file_blksz - (2 * fs_blksz) ))" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $file_blksz" \
+ -c "pwrite -S 0x59 $file_blksz $fs_blksz" \
+ -c "pwrite -S 0x00 $((file_blksz + fs_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x59 $((file_blksz + (2 * fs_blksz) )) $((file_blksz - (2 * fs_blksz) ))" \
+ -c "pwrite -S 0x58 $((file_blksz * 2)) $((filesz - (file_blksz * 2) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $file_blksz $file_blksz" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "second rtb of second rtx"
+
+# last rtblock of the second rtextent is unwritten
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $file_blksz" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x00 $(( (2 * file_blksz) - fs_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x58 $((file_blksz * 2)) $((filesz - (file_blksz * 2) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $file_blksz $file_blksz" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "last rtb of second rtx"
+
+# last rtb of the 2nd rtx and first rtb of the 3rd rtx is unwritten
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "falloc $file_blksz $((2 * file_blksz))" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x59 $(( (2 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $file_blksz" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x00 $(( (2 * file_blksz) - fs_blksz)) $((2 * fs_blksz))" \
+ -c "pwrite -S 0x59 $(( (2 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x58 $((file_blksz * 3)) $((filesz - (file_blksz * 3) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $file_blksz $((2 * file_blksz))" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "last rtb of 2nd rtx and first rtb of 3rd rtx"
+
+# last rtb of the 2nd rtx and first rtb of the 4th rtx is unwritten; 3rd rtx
+# is a hole
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x59 $(( (3 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ -c "fpunch $((2 * file_blksz)) $file_blksz" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $file_blksz" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x00 $(( (2 * file_blksz) - fs_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x58 $((file_blksz * 2)) $file_blksz" \
+ -c "pwrite -S 0x00 $((3 * file_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x59 $(( (3 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x58 $((file_blksz * 4)) $((filesz - (file_blksz * 4) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $file_blksz $file_blksz" \
+ -c "pwrite -S 0x58 $((file_blksz * 3)) $file_blksz" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "last rtb of 2nd rtx and first rtb of 4th rtx; 3rd rtx is hole"
+
+# last rtb of the 2nd rtx and first rtb of the 4th rtx is unwritten; 3rd rtx
+# is preallocated
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "falloc $file_blksz $((file_blksz * 3))" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x59 $(( (3 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $file_blksz" \
+ -c "pwrite -S 0x59 $file_blksz $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x00 $(( (2 * file_blksz) - fs_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x58 $((file_blksz * 2)) $file_blksz" \
+ -c "pwrite -S 0x00 $((3 * file_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x59 $(( (3 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x58 $((file_blksz * 4)) $((filesz - (file_blksz * 4) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $file_blksz $file_blksz" \
+ -c "pwrite -S 0x58 $((file_blksz * 3)) $file_blksz" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "last rtb of 2nd rtx and first rtb of 4th rtx; 3rd rtx is prealloc"
+
+# 2nd rtx is preallocated and first rtb of 3rd rtx is unwritten
+rm -f $SCRATCH_MNT/da $SCRATCH_MNT/db $SCRATCH_MNT/*.chk
+_pwrite_byte 0x58 0 $filesz $SCRATCH_MNT/da >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "falloc $file_blksz $((file_blksz * 2))" \
+ -c "pwrite -S 0x59 $(( (2 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ $SCRATCH_MNT/db >> $seqres.full
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 0 $((2 * file_blksz))" \
+ -c "pwrite -S 0x00 $((2 * file_blksz)) $fs_blksz" \
+ -c "pwrite -S 0x59 $(( (2 * file_blksz) + fs_blksz)) $((file_blksz - fs_blksz))" \
+ -c "pwrite -S 0x58 $((file_blksz * 3)) $((filesz - (file_blksz * 3) ))" \
+ $SCRATCH_MNT/da.chk >> /dev/null
+$XFS_IO_PROG -f -c "truncate $filesz" \
+ -c "pwrite -S 0x58 $((2 * file_blksz)) $file_blksz" \
+ $SCRATCH_MNT/db.chk >> /dev/null
+swap_and_check_contents $SCRATCH_MNT/da $SCRATCH_MNT/db \
+ "2nd rtx is prealloc and first rtb of 3rd rtx is unwritten"
+
+echo Silence is golden
+status=0
+exit
diff --git a/tests/xfs/1214.out b/tests/xfs/1214.out
new file mode 100644
index 0000000000..a529e42333
--- /dev/null
+++ b/tests/xfs/1214.out
@@ -0,0 +1,2 @@
+QA output created by 1214
+Silence is golden
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 01/11] generic: test recovery of extended attribute updates
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
@ 2024-06-20 20:57 ` Darrick J. Wong
2024-06-20 20:57 ` [PATCH 02/11] xfs/206: filter out the parent= status from mkfs Darrick J. Wong
` (9 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:57 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Fork generic/475 to test recovery of extended attribute modifications
and log recovery.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/generic/1834 | 93 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/generic/1834.out | 2 +
2 files changed, 95 insertions(+)
create mode 100755 tests/generic/1834
create mode 100644 tests/generic/1834.out
diff --git a/tests/generic/1834 b/tests/generic/1834
new file mode 100755
index 0000000000..7910a40545
--- /dev/null
+++ b/tests/generic/1834
@@ -0,0 +1,93 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle, Inc. All Rights Reserved.
+#
+# FS QA Test No. 1834
+#
+# Test log recovery with repeated (simulated) disk failures. We kick
+# off fsstress on the scratch fs to exercise extended attribute operations,
+# then switch out the underlying device with dm-error to see what happens when
+# the disk goes down. Having taken down the fs in this manner, remount it and
+# repeat.
+#
+. ./common/preamble
+_begin_fstest shutdown auto log metadata eio recoveryloop attr
+
+# Override the default cleanup function.
+_cleanup()
+{
+ cd /
+ rm -f $tmp.*
+ $KILLALL_PROG -9 fsstress > /dev/null 2>&1
+ _dmerror_unmount
+ _dmerror_cleanup
+}
+
+# Import common functions.
+. ./common/dmerror
+
+# Modify as appropriate.
+_supported_fs generic
+
+_require_scratch
+_require_dm_target error
+_require_command "$KILLALL_PROG" "killall"
+
+echo "Silence is golden."
+
+_scratch_mkfs >> $seqres.full 2>&1
+_require_metadata_journaling $SCRATCH_DEV
+_dmerror_init
+_dmerror_mount
+
+args=('-z' '-S' 'c')
+
+# Do some directory tree modifications, but the bulk of this is geared towards
+# exercising the xattr code, especially attr_set which can do up to 10k values.
+for verb in unlink rmdir; do
+ args+=('-f' "${verb}=50")
+done
+for verb in creat mkdir; do
+ args+=('-f' "${verb}=2")
+done
+for verb in getfattr listfattr; do
+ args+=('-f' "${verb}=3")
+done
+for verb in attr_remove removefattr; do
+ args+=('-f' "${verb}=4")
+done
+args+=('-f' "setfattr=20")
+args+=('-f' "attr_set=60") # sets larger xattrs
+
+while _soak_loop_running $((50 * TIME_FACTOR)); do
+ ($FSSTRESS_PROG "${args[@]}" $FSSTRESS_AVOID -d $SCRATCH_MNT -n 999999 -p $((LOAD_FACTOR * 4)) >> $seqres.full &) \
+ > /dev/null 2>&1
+
+ # purposely include 0 second sleeps to test shutdown immediately after
+ # recovery
+ sleep $((RANDOM % 3))
+
+ # This test aims to simulate sudden disk failure, which means that we
+ # do not want to quiesce the filesystem or otherwise give it a chance
+ # to flush its logs. Therefore we want to call dmsetup with the
+ # --nolockfs parameter; to make this happen we must call the load
+ # error table helper *without* 'lockfs'.
+ _dmerror_load_error_table
+
+ ps -e | grep fsstress > /dev/null 2>&1
+ while [ $? -eq 0 ]; do
+ $KILLALL_PROG -9 fsstress > /dev/null 2>&1
+ wait > /dev/null 2>&1
+ ps -e | grep fsstress > /dev/null 2>&1
+ done
+
+ # Mount again to replay log after loading working table, so we have a
+ # consistent XFS after test.
+ _dmerror_unmount || _fail "unmount failed"
+ _dmerror_load_working_table
+ _dmerror_mount || _fail "mount failed"
+done
+
+# success, all done
+status=0
+exit
diff --git a/tests/generic/1834.out b/tests/generic/1834.out
new file mode 100644
index 0000000000..5efe2033b5
--- /dev/null
+++ b/tests/generic/1834.out
@@ -0,0 +1,2 @@
+QA output created by 1834
+Silence is golden.
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 02/11] xfs/206: filter out the parent= status from mkfs
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2024-06-20 20:57 ` [PATCH 01/11] generic: test recovery of extended attribute updates Darrick J. Wong
@ 2024-06-20 20:57 ` Darrick J. Wong
2024-06-20 20:57 ` [PATCH 03/11] xfs/122: update for parent pointers Darrick J. Wong
` (8 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:57 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Filter out the parent pointer bits from the mkfs output so that we don't
cause a regression in this test.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/206 | 1 +
1 file changed, 1 insertion(+)
diff --git a/tests/xfs/206 b/tests/xfs/206
index f973980eb2..d81fe19857 100755
--- a/tests/xfs/206
+++ b/tests/xfs/206
@@ -65,6 +65,7 @@ mkfs_filter()
-e "s/, lazy-count=[0-9]//" \
-e "/.*crc=/d" \
-e "/exchange=/d" \
+ -e 's/, parent=[01]//' \
-e "/^Default configuration/d"
}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 03/11] xfs/122: update for parent pointers
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2024-06-20 20:57 ` [PATCH 01/11] generic: test recovery of extended attribute updates Darrick J. Wong
2024-06-20 20:57 ` [PATCH 02/11] xfs/206: filter out the parent= status from mkfs Darrick J. Wong
@ 2024-06-20 20:57 ` Darrick J. Wong
2024-06-20 20:57 ` [PATCH 04/11] populate: create hardlinks " Darrick J. Wong
` (7 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:57 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Update test for parent pointers.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/122.out | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/tests/xfs/122.out b/tests/xfs/122.out
index 86c806d4b5..7be14ed993 100644
--- a/tests/xfs/122.out
+++ b/tests/xfs/122.out
@@ -100,6 +100,9 @@ sizeof(struct xfs_fsop_ag_resblks) = 64
sizeof(struct xfs_fsop_geom) = 256
sizeof(struct xfs_fsop_geom_v1) = 112
sizeof(struct xfs_fsop_geom_v4) = 112
+sizeof(struct xfs_getparents) = 40
+sizeof(struct xfs_getparents_by_handle) = 64
+sizeof(struct xfs_getparents_rec) = 32
sizeof(struct xfs_icreate_log) = 28
sizeof(struct xfs_inode_log_format) = 56
sizeof(struct xfs_inode_log_format_32) = 52
@@ -109,6 +112,7 @@ sizeof(struct xfs_legacy_timestamp) = 8
sizeof(struct xfs_log_dinode) = 176
sizeof(struct xfs_log_legacy_timestamp) = 8
sizeof(struct xfs_map_extent) = 32
+sizeof(struct xfs_parent_rec) = 12
sizeof(struct xfs_phys_extent) = 16
sizeof(struct xfs_refcount_key) = 4
sizeof(struct xfs_refcount_rec) = 12
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 04/11] populate: create hardlinks for parent pointers
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (2 preceding siblings ...)
2024-06-20 20:57 ` [PATCH 03/11] xfs/122: update for parent pointers Darrick J. Wong
@ 2024-06-20 20:57 ` Darrick J. Wong
2024-06-20 20:58 ` [PATCH 05/11] xfs/021: adapt golden output files " Darrick J. Wong
` (6 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:57 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Create some hardlinked files so that we can exercise parent pointers.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
common/populate | 42 ++++++++++++++++++++++++++++++++++++++++++
src/popdir.pl | 11 +++++++++++
2 files changed, 53 insertions(+)
diff --git a/common/populate b/common/populate
index 15f8055c2c..9fda19df06 100644
--- a/common/populate
+++ b/common/populate
@@ -464,6 +464,48 @@ _scratch_xfs_populate() {
cp --reflink=always "${SCRATCH_MNT}/REFCOUNTBT" "${SCRATCH_MNT}/REFCOUNTBT2"
fi
+ # Parent pointers
+ is_pptr="$(_xfs_has_feature "$SCRATCH_MNT" parent -v)"
+ if [ $is_pptr -gt 0 ]; then
+ echo "+ parent pointers"
+
+ # Create a couple of parent pointers
+ __populate_create_dir "${SCRATCH_MNT}/PPTRS" 1 '' \
+ --hardlink --format "two_%d"
+
+ # Create one xattr leaf block of parent pointers
+ nr="$((blksz * 2 / 16))"
+ __populate_create_dir "${SCRATCH_MNT}/PPTRS" ${nr} '' \
+ --hardlink --format "many%04d"
+
+ # Create multiple xattr leaf blocks of large parent pointers
+ nr="$((blksz * 16 / 16))"
+ __populate_create_dir "${SCRATCH_MNT}/PPTRS" ${nr} '' \
+ --hardlink --format "y%0254d"
+
+ # Create multiple paths to a file
+ local moof="${SCRATCH_MNT}/PPTRS/moofile"
+ touch "${moof}"
+ for ((i = 0; i < 4; i++)); do
+ mkdir -p "${SCRATCH_MNT}/PPTRS/SUB${i}"
+ ln "${moof}" "${SCRATCH_MNT}/PPTRS/SUB${i}/moofile"
+ done
+
+ # Create parent pointers of various lengths
+ touch "${SCRATCH_MNT}/PPTRS/vlength"
+ local len_len
+ local tst
+ local fname
+ ln "${SCRATCH_MNT}/PPTRS/vlength" "${SCRATCH_MNT}/PPTRS/b"
+ for len in 32 64 96 128 160 192 224 250 255; do
+ len_len="${#len}"
+ tst="$(perl -e "print \"b\" x (${len} - (${len_len} + 1))")"
+ fname="v${tst}${len}"
+ ln "${SCRATCH_MNT}/PPTRS/vlength" \
+ "${SCRATCH_MNT}/PPTRS/${fname}"
+ done
+ fi
+
# Copy some real files (xfs tests, I guess...)
echo "+ real files"
test $fill -ne 0 && __populate_fill_fs "${SCRATCH_MNT}" 5
diff --git a/src/popdir.pl b/src/popdir.pl
index e89095aafe..0104957a3c 100755
--- a/src/popdir.pl
+++ b/src/popdir.pl
@@ -17,6 +17,7 @@ GetOptions("start=i" => \$start,
"dir=s" => \$dir,
"remove!" => \$remove,
"help!" => \$help,
+ "hardlink!" => \$hardlink,
"verbose!" => \$verbose);
@@ -35,6 +36,7 @@ Options:
--format=str printf formatting string for file name ("%08d")
--verbose verbose output
--help this help screen
+ --hardlink hardlink subsequent files to the first one created
EOF
exit(1) unless defined $help;
# otherwise...
@@ -56,12 +58,21 @@ if ($file_pct < 0) {
$file_pct = 100;
}
+if ($hardlink) {
+ $file_pct = 100;
+ $link_fname = sprintf($format, $start);
+}
+
for ($i = $start; $i <= $end; $i += $incr) {
$fname = sprintf($format, $i);
if ($remove) {
$verbose && print "rm $fname\n";
unlink($fname) or rmdir($fname) or die("unlink $fname");
+ } elsif ($hardlink && $i > $start) {
+ # hardlink everything after the first file
+ $verbose && print "ln $link_fname $fname\n";
+ link $link_fname, $fname;
} elsif (($i % 100) < $file_pct) {
# create a file
$verbose && print "touch $fname\n";
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 05/11] xfs/021: adapt golden output files for parent pointers
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (3 preceding siblings ...)
2024-06-20 20:57 ` [PATCH 04/11] populate: create hardlinks " Darrick J. Wong
@ 2024-06-20 20:58 ` Darrick J. Wong
2024-06-20 20:58 ` [PATCH 06/11] xfs/{018,191,288}: disable parent pointers for these tests Darrick J. Wong
` (5 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:58 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Parent pointers change the xattr structure dramatically, so fix this
test to handle them. For the most part we can get away with filtering
out the parent pointer fields (which xfs_db decodes for us), but the
namelen/valuelen/attr_filter fields still show through.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
common/rc | 4 +++
tests/xfs/021 | 15 +++++++++--
tests/xfs/021.cfg | 1 +
tests/xfs/021.out.default | 0
tests/xfs/021.out.parent | 64 +++++++++++++++++++++++++++++++++++++++++++++
5 files changed, 82 insertions(+), 2 deletions(-)
create mode 100644 tests/xfs/021.cfg
rename tests/xfs/{021.out => 021.out.default} (100%)
create mode 100644 tests/xfs/021.out.parent
diff --git a/common/rc b/common/rc
index 9e69af1527..ba26fda6e6 100644
--- a/common/rc
+++ b/common/rc
@@ -3472,6 +3472,8 @@ _get_os_name()
_link_out_file_named()
{
+ test -n "$seqfull" || _fail "need to set seqfull"
+
local features=$2
local suffix=$(FEATURES="$features" perl -e '
my %feathash;
@@ -3507,6 +3509,8 @@ _link_out_file()
{
local features
+ test -n "$seqfull" || _fail "need to set seqfull"
+
if [ $# -eq 0 ]; then
features="$(_get_os_name),$FSTYP"
if [ -n "$MOUNT_OPTIONS" ]; then
diff --git a/tests/xfs/021 b/tests/xfs/021
index 9432e2acb0..ef307fc064 100755
--- a/tests/xfs/021
+++ b/tests/xfs/021
@@ -67,6 +67,13 @@ _scratch_mkfs_xfs >/dev/null \
echo "*** mount FS"
_scratch_mount
+seqfull=$0
+if _xfs_has_feature $SCRATCH_MNT parent; then
+ _link_out_file "parent"
+else
+ _link_out_file ""
+fi
+
testfile=$SCRATCH_MNT/testfile
echo "*** make test file 1"
@@ -108,7 +115,10 @@ _scratch_unmount >>$seqres.full 2>&1 \
echo "*** dump attributes (1)"
_scratch_xfs_db -r -c "inode $inum_1" -c "print a.sfattr" | \
- sed -e '/secure = /d' | sed -e '/parent = /d'
+ perl -ne '
+/\.secure/ && next;
+/\.parent/ && next;
+ print unless /^\d+:\[.*/;'
echo "*** dump attributes (2)"
@@ -124,10 +134,11 @@ s/info.hdr/info/;
/hdr.info.uuid/ && next;
/hdr.info.lsn/ && next;
/hdr.info.owner/ && next;
+/\.parent/ && next;
s/^(hdr.info.magic =) 0x3bee/\1 0xfbee/;
s/^(hdr.firstused =) (\d+)/\1 FIRSTUSED/;
s/^(hdr.freemap\[0-2] = \[base,size]).*/\1 [FREEMAP..]/;
-s/^(entries\[0-2] = \[hashval,nameidx,incomplete,root,local]).*/\1 [ENTRIES..]/;
+s/^(entries\[0-[23]] = \[hashval,nameidx,incomplete,root,local]).*/\1 [ENTRIES..]/;
print unless /^\d+:\[.*/;'
echo "*** done"
diff --git a/tests/xfs/021.cfg b/tests/xfs/021.cfg
new file mode 100644
index 0000000000..73b127260c
--- /dev/null
+++ b/tests/xfs/021.cfg
@@ -0,0 +1 @@
+parent: parent
diff --git a/tests/xfs/021.out b/tests/xfs/021.out.default
similarity index 100%
rename from tests/xfs/021.out
rename to tests/xfs/021.out.default
diff --git a/tests/xfs/021.out.parent b/tests/xfs/021.out.parent
new file mode 100644
index 0000000000..34f120c713
--- /dev/null
+++ b/tests/xfs/021.out.parent
@@ -0,0 +1,64 @@
+QA output created by 021
+*** mkfs
+*** mount FS
+*** make test file 1
+# file: <TESTFILE>.1
+user.a1
+user.a2--
+
+*** make test file 2
+1+0 records in
+1+0 records out
+# file: <TESTFILE>.2
+user.a1
+user.a2-----
+user.a3
+
+Attribute "a3" had a 65535 byte value for <TESTFILE>.2:
+size of attr value = 65536
+
+*** unmount FS
+*** dump attributes (1)
+a.sfattr.hdr.totsize = 49
+a.sfattr.hdr.count = 3
+a.sfattr.list[0].namelen = 10
+a.sfattr.list[0].valuelen = 12
+a.sfattr.list[0].root = 0
+a.sfattr.list[0].name = "testfile.1"
+a.sfattr.list[1].namelen = 2
+a.sfattr.list[1].valuelen = 3
+a.sfattr.list[1].root = 0
+a.sfattr.list[1].name = "a1"
+a.sfattr.list[1].value = "v1\d"
+a.sfattr.list[2].namelen = 4
+a.sfattr.list[2].valuelen = 5
+a.sfattr.list[2].root = 0
+a.sfattr.list[2].name = "a2--"
+a.sfattr.list[2].value = "v2--\d"
+*** dump attributes (2)
+hdr.info.forw = 0
+hdr.info.back = 0
+hdr.info.magic = 0xfbee
+hdr.count = 4
+hdr.usedbytes = 80
+hdr.firstused = FIRSTUSED
+hdr.holes = 0
+hdr.freemap[0-2] = [base,size] [FREEMAP..]
+entries[0-3] = [hashval,nameidx,incomplete,root,local] [ENTRIES..]
+nvlist[0].valuelen = 8
+nvlist[0].namelen = 2
+nvlist[0].name = "a1"
+nvlist[0].value = "value_1\d"
+nvlist[1].valueblk = 0x1
+nvlist[1].valuelen = 65535
+nvlist[1].namelen = 2
+nvlist[1].name = "a3"
+nvlist[2].valuelen = 8
+nvlist[2].namelen = 7
+nvlist[2].name = "a2-----"
+nvlist[2].value = "value_2\d"
+nvlist[3].valuelen = 12
+nvlist[3].namelen = 10
+nvlist[3].name = "testfile.2"
+*** done
+*** unmount
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 06/11] xfs/{018,191,288}: disable parent pointers for these tests
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (4 preceding siblings ...)
2024-06-20 20:58 ` [PATCH 05/11] xfs/021: adapt golden output files " Darrick J. Wong
@ 2024-06-20 20:58 ` Darrick J. Wong
2024-06-20 20:58 ` [PATCH 07/11] xfs/306: fix formatting failures with parent pointers Darrick J. Wong
` (4 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:58 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
These tests depend heavily on the xattr formats created for new files.
Parent pointers break those assumptions, so force parent pointers off.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
common/xfs | 16 ++++++++++++++++
tests/xfs/018 | 4 ++++
tests/xfs/191 | 3 +++
tests/xfs/288 | 4 ++++
4 files changed, 27 insertions(+)
diff --git a/common/xfs b/common/xfs
index 0b0863f1dc..b392237575 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1847,3 +1847,19 @@ _require_xfs_nocrc()
_notrun "v4 file systems not supported"
_scratch_unmount
}
+
+# Adjust MKFS_OPTIONS as necessary to avoid having parent pointers formatted
+# onto the filesystem
+_xfs_force_no_pptrs()
+{
+ # Nothing to do if parent pointers aren't supported by mkfs
+ $MKFS_XFS_PROG 2>&1 | grep -q parent=0 || return
+
+ if echo "$MKFS_OPTIONS" | grep -q 'parent='; then
+ MKFS_OPTIONS="$(echo "$MKFS_OPTIONS" | \
+ sed -e 's/parent=[01]/parent=0/g')"
+ return
+ fi
+
+ MKFS_OPTIONS="$MKFS_OPTIONS -n parent=0"
+}
diff --git a/tests/xfs/018 b/tests/xfs/018
index 73040edc92..7d1b861d1c 100755
--- a/tests/xfs/018
+++ b/tests/xfs/018
@@ -111,6 +111,10 @@ attr32l="X$attr32k"
attr64k="$attr32k$attr32k"
echo "*** mkfs"
+
+# Parent pointers change the xattr formats sufficiently to break this test.
+# Disable parent pointers if mkfs supports it.
+_xfs_force_no_pptrs
_scratch_mkfs >/dev/null
blk_sz=$(_scratch_xfs_get_sb_field blocksize)
diff --git a/tests/xfs/191 b/tests/xfs/191
index 7a02f1be21..e2150bf797 100755
--- a/tests/xfs/191
+++ b/tests/xfs/191
@@ -33,6 +33,9 @@ _fixed_by_kernel_commit 7be3bd8856fb "xfs: empty xattr leaf header blocks are no
_fixed_by_kernel_commit e87021a2bc10 "xfs: use larger in-core attr firstused field and detect overflow"
_fixed_by_git_commit xfsprogs f50d3462c654 "xfs_repair: ignore empty xattr leaf blocks"
+# Parent pointers change the xattr formats sufficiently to break this test.
+# Disable parent pointers if mkfs supports it.
+_xfs_force_no_pptrs
_scratch_mkfs_xfs | _filter_mkfs >$seqres.full 2>$tmp.mkfs
cat $tmp.mkfs >> $seqres.full
source $tmp.mkfs
diff --git a/tests/xfs/288 b/tests/xfs/288
index aa664a266e..60fb9360f4 100755
--- a/tests/xfs/288
+++ b/tests/xfs/288
@@ -19,6 +19,10 @@ _supported_fs xfs
_require_scratch
_require_attrs
+# Parent pointers change the xattr formats sufficiently to break this test.
+# Disable parent pointers if mkfs supports it.
+_xfs_force_no_pptrs
+
# get block size ($dbsize) from the mkfs output
_scratch_mkfs_xfs 2>/dev/null | _filter_mkfs 2>$tmp.mkfs >/dev/null
. $tmp.mkfs
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 07/11] xfs/306: fix formatting failures with parent pointers
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (5 preceding siblings ...)
2024-06-20 20:58 ` [PATCH 06/11] xfs/{018,191,288}: disable parent pointers for these tests Darrick J. Wong
@ 2024-06-20 20:58 ` Darrick J. Wong
2024-06-20 20:59 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
` (3 subsequent siblings)
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:58 UTC (permalink / raw)
To: djwong, zlang
Cc: Christoph Hellwig, fstests, allison.henderson, catherine.hoang,
linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
The parent pointers feature isn't supported on tiny 20MB filesystems
because the larger directory transactions result in larger minimum log
sizes, particularly with nrext64 enabled:
** mkfs failed with extra mkfs options added to " -m rmapbt=0, -i nrext64=1, -n parent=1," by test 306 **
** attempting to mkfs using only test 306 options: -d size=20m -n size=64k **
max log size 5108 smaller than min log size 5310, filesystem is too small
We don't support 20M filesystems anymore, so bump the filesystem size up
to 100M and skip this test if we can't actually format the filesystem.
Convert the open-coded punch-alternating logic into a call to that
program to reduce execve overhead, which more than makes up having to
write 5x as much data to fragment the free space.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/306 | 9 ++++-----
1 file changed, 4 insertions(+), 5 deletions(-)
diff --git a/tests/xfs/306 b/tests/xfs/306
index b57bf4c0a9..152971cfc3 100755
--- a/tests/xfs/306
+++ b/tests/xfs/306
@@ -23,6 +23,7 @@ _supported_fs xfs
_require_scratch_nocheck # check complains about single AG fs
_require_xfs_io_command "fpunch"
_require_command $UUIDGEN_PROG uuidgen
+_require_test_program "punch-alternating"
# Disable the scratch rt device to avoid test failures relating to the rt
# bitmap consuming all the free space in our small data device.
@@ -30,7 +31,8 @@ unset SCRATCH_RTDEV
# Create a small fs with a large directory block size. We want to fill up the fs
# quickly and then create multi-fsb dirblocks over fragmented free space.
-_scratch_mkfs_xfs -d size=20m -n size=64k >> $seqres.full 2>&1
+_scratch_mkfs_xfs -d size=100m -n size=64k >> $seqres.full 2>&1 || \
+ _notrun 'could not format tiny scratch fs'
_scratch_mount
# Fill a source directory with many largish-named files. 1k uuid-named entries
@@ -49,10 +51,7 @@ done
$XFS_IO_PROG -xc "resblks 16" $SCRATCH_MNT >> $seqres.full 2>&1
dd if=/dev/zero of=$SCRATCH_MNT/file bs=4k >> $seqres.full 2>&1
$XFS_IO_PROG -c "fsync" $SCRATCH_MNT/file >> $seqres.full 2>&1
-size=`_get_filesize $SCRATCH_MNT/file`
-for i in $(seq 0 8192 $size); do
- $XFS_IO_PROG -c "fpunch $i 4k" $SCRATCH_MNT/file >> $seqres.full 2>&1
-done
+$here/src/punch-alternating $SCRATCH_MNT/file
# Replicate the src dir several times into fragmented free space. After one or
# two dirs, we should have nothing but non-contiguous directory blocks.
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 08/11] common: add helpers for parent pointer tests
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (6 preceding siblings ...)
2024-06-20 20:58 ` [PATCH 07/11] xfs/306: fix formatting failures with parent pointers Darrick J. Wong
@ 2024-06-20 20:59 ` Darrick J. Wong
2024-06-21 4:36 ` Christoph Hellwig
2024-06-20 20:59 ` [PATCH 09/11] xfs: add parent pointer test Darrick J. Wong
` (2 subsequent siblings)
10 siblings, 1 reply; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:59 UTC (permalink / raw)
To: djwong, zlang
Cc: Allison Henderson, Catherine Hoang, fstests, allison.henderson,
catherine.hoang, linux-xfs
From: Allison Henderson <allison.henderson@oracle.com>
Add helper functions in common/parent to parse and verify parent
pointers. Also add functions to check that mkfs, kernel, and xfs_io
support parent pointers.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: add license and copyright, dont _fail tests immediately, make
sure the pptr-generated paths match the dir-generated paths]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
---
common/parent | 209 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
common/rc | 3 +
common/xfs | 12 +++
3 files changed, 224 insertions(+)
create mode 100644 common/parent
diff --git a/common/parent b/common/parent
new file mode 100644
index 0000000000..ccdf2bb4bd
--- /dev/null
+++ b/common/parent
@@ -0,0 +1,209 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle and/or its affiliates. All Rights Reserved.
+#
+# Parent pointer common functions
+#
+
+#
+# parse_parent_pointer parents parent_inode parent_pointer_name
+#
+# Given a list of parent pointers, find the record that matches
+# the given inode and filename
+#
+# inputs:
+# parents : A list of parent pointers in the format of:
+# inode/generation/name_length/name
+# parent_inode : The parent inode to search for
+# parent_name : The parent name to search for
+#
+# outputs:
+# PPINO : Parent pointer inode
+# PPGEN : Parent pointer generation
+# PPNAME : Parent pointer name
+# PPNAME_LEN : Parent pointer name length
+#
+_xfs_parse_parent_pointer()
+{
+ local parents=$1
+ local pino=$2
+ local parent_pointer_name=$3
+
+ local found=0
+
+ # Find the entry that has the same inode as the parent
+ # and parse out the entry info
+ while IFS=':' read PPINO PPGEN PPNAME_LEN PPNAME; do
+ if [ "$PPINO" != "$pino" ]; then
+ continue
+ fi
+
+ if [ "$PPNAME" != "$parent_pointer_name" ]; then
+ continue
+ fi
+
+ found=1
+ break
+ done <<< $(echo "$parents")
+
+ # Check to see if we found anything
+ # We do not fail the test because we also use this
+ # routine to verify when parent pointers should
+ # be removed or updated (ie a rename or a move
+ # operation changes your parent pointer)
+ if [ $found -eq "0" ]; then
+ return 1
+ fi
+
+ # Verify the parent pointer name length is correct
+ if [ "$PPNAME_LEN" -ne "${#parent_pointer_name}" ]
+ then
+ echo "*** Bad parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ fi
+
+ #return sucess
+ return 0
+}
+
+#
+# _xfs_verify_parent parent_path parent_pointer_name child_path
+#
+# Verify that the given child path lists the given parent as a parent pointer
+# and that the parent pointer name matches the given name
+#
+# Examples:
+#
+# #simple example
+# mkdir testfolder1
+# touch testfolder1/file1
+# verify_parent testfolder1 file1 testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder1"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1"
+#
+#
+# #hardlink example
+# mkdir testfolder1
+# mkdir testfolder2
+# touch testfolder1/file1
+# ln testfolder1/file1 testfolder2/file1_ln
+# verify_parent testfolder2 file1_ln testfolder1/file1
+#
+# # In this above example, we want to verify that "testfolder2"
+# # appears as a parent pointer of "testfolder1/file1". Additionally
+# # we verify that the name record of the parent pointer is "file1_ln"
+#
+_xfs_verify_parent()
+{
+ local parent_path=$1
+ local parent_pointer_name=$2
+ local child_path=$3
+
+ local parent_ppath="$parent_path/$parent_pointer_name"
+
+ # Verify parent exists
+ if [ ! -d $SCRATCH_MNT/$parent_path ]; then
+ echo "$SCRATCH_MNT/$parent_path not found"
+ else
+ echo "*** $parent_path OK"
+ fi
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Verify the parent pointer name exists as a child of the parent
+ if [ ! -f $SCRATCH_MNT/$parent_ppath ]; then
+ echo "$SCRATCH_MNT/$parent_ppath not found"
+ else
+ echo "*** $parent_ppath OK"
+ fi
+
+ # Get the inodes of both parent and child
+ pino="$(stat -c '%i' $SCRATCH_MNT/$parent_path)"
+ cino="$(stat -c '%i' $SCRATCH_MNT/$child_path)"
+
+ # Get all the parent pointers of the child
+ parents=($($XFS_IO_PROG -x -c \
+ "parent -s -i $pino -n $parent_pointer_name" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ echo "No parent pointers found for $child_path"
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _xfs_parse_parent_pointer $parents $pino $parent_pointer_name
+
+ # If we didnt find one, bail out
+ if [ $? -ne 0 ]; then
+ echo "No parent pointer record found for $parent_path"\
+ "in $child_path"
+ fi
+
+ # Verify the inode generated by the parent pointer name is
+ # the same as the child inode
+ pppino="$(stat -c '%i' $SCRATCH_MNT/$parent_ppath)"
+ if [ $cino -ne $pppino ]
+ then
+ echo "Bad parent pointer name value for $child_path."\
+ "$SCRATCH_MNT/$parent_ppath belongs to inode $PPPINO,"\
+ "but should be $cino"
+ fi
+
+ # Make sure path printing works by checking that the paths returned
+ # all point to the same inode.
+ local tgt="$SCRATCH_MNT/$child_path"
+ $XFS_IO_PROG -x -c 'parent -p' "$tgt" | while read pptr_path; do
+ test "$tgt" -ef "$pptr_path" || \
+ echo "$tgt parent pointer $pptr_path should be the same file"
+ done
+
+ echo "*** Verified parent pointer:"\
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+ echo "*** Parent pointer OK for child $child_path"
+}
+
+#
+# _xfs_verify_parent parent_pointer_name pino child_path
+#
+# Verify that the given child path contains no parent pointer entry
+# for the given inode and file name
+#
+_xfs_verify_no_parent()
+{
+ local parent_pname=$1
+ local pino=$2
+ local child_path=$3
+
+ # Verify child exists
+ if [ ! -f $SCRATCH_MNT/$child_path ]; then
+ echo "$SCRATCH_MNT/$child_path not found"
+ else
+ echo "*** $child_path OK"
+ fi
+
+ # Get all the parent pointers of the child
+ local parents=($($XFS_IO_PROG -x -c \
+ "parent -s -i $pino -n $parent_pname" $SCRATCH_MNT/$child_path))
+ if [[ $? != 0 ]]; then
+ return 0
+ fi
+
+ # Parse parent pointer output.
+ # This sets PPINO PPGEN PPNAME PPNAME_LEN
+ _xfs_parse_parent_pointer $parents $pino $parent_pname
+
+ # If we didnt find one, return sucess
+ if [ $? -ne 0 ]; then
+ return 0
+ fi
+
+ echo "Parent pointer entry found where none should:"\
+ "inode:$PPINO, gen:$PPGEN,"
+ "name:$PPNAME, namelen:$PPNAME_LEN"
+}
diff --git a/common/rc b/common/rc
index ba26fda6e6..0e0d49b87a 100644
--- a/common/rc
+++ b/common/rc
@@ -2742,6 +2742,9 @@ _require_xfs_io_command()
echo $testio | grep -q "invalid option" && \
_notrun "xfs_io $command support is missing"
;;
+ "parent")
+ testio=`$XFS_IO_PROG -x -c "parent" $TEST_DIR 2>&1`
+ ;;
"pwrite")
# -N (RWF_NOWAIT) only works with direct vectored I/O writes
local pwrite_opts=" "
diff --git a/common/xfs b/common/xfs
index b392237575..7706b56260 100644
--- a/common/xfs
+++ b/common/xfs
@@ -1863,3 +1863,15 @@ _xfs_force_no_pptrs()
MKFS_OPTIONS="$MKFS_OPTIONS -n parent=0"
}
+
+# this test requires the xfs parent pointers feature
+#
+_require_xfs_parent()
+{
+ _scratch_mkfs_xfs_supported -n parent > /dev/null 2>&1 \
+ || _notrun "mkfs.xfs does not support parent pointers"
+ _scratch_mkfs_xfs -n parent > /dev/null 2>&1
+ _try_scratch_mount >/dev/null 2>&1 \
+ || _notrun "kernel does not support parent pointers"
+ _scratch_unmount
+}
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 09/11] xfs: add parent pointer test
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (7 preceding siblings ...)
2024-06-20 20:59 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
@ 2024-06-20 20:59 ` Darrick J. Wong
2024-06-20 20:59 ` [PATCH 10/11] xfs: add multi link " Darrick J. Wong
2024-06-20 20:59 ` [PATCH 11/11] xfs: add parent pointer inject test Darrick J. Wong
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:59 UTC (permalink / raw)
To: djwong, zlang
Cc: Allison Henderson, Catherine Hoang, Christoph Hellwig, fstests,
allison.henderson, catherine.hoang, linux-xfs
From: Allison Henderson <allison.henderson@oracle.com>
Add a test to verify basic parent pointers operations (create, move, link,
unlink, rename, overwrite).
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
[djwong: test the xfs_io parent -p argument too]
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
doc/group-names.txt | 1
tests/xfs/1851 | 116 +++++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1851.out | 69 ++++++++++++++++++++++++++++++
3 files changed, 186 insertions(+)
create mode 100755 tests/xfs/1851
create mode 100644 tests/xfs/1851.out
diff --git a/doc/group-names.txt b/doc/group-names.txt
index 2c4c312700..6cf717969d 100644
--- a/doc/group-names.txt
+++ b/doc/group-names.txt
@@ -83,6 +83,7 @@ nfs4_acl NFSv4 access control lists
nonsamefs overlayfs layers on different filesystems
online_repair online repair functionality tests
other dumping ground, do not add more tests to this group
+parent Parent pointer tests
pattern specific IO pattern tests
perms access control and permission checking
pipe pipe functionality
diff --git a/tests/xfs/1851 b/tests/xfs/1851
new file mode 100755
index 0000000000..99c1a28a8c
--- /dev/null
+++ b/tests/xfs/1851
@@ -0,0 +1,116 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle and/or its affiliates. All Rights Reserved.
+#
+# FS QA Test No. 1851
+#
+# simple parent pointer test
+#
+
+. ./common/preamble
+_begin_fstest auto quick parent
+
+# get standard environment, filters and checks
+. ./common/parent
+. ./common/filter
+
+# Modify as appropriate
+_supported_fs xfs
+_require_scratch
+_require_xfs_sysfs debug/larp
+_require_xfs_parent
+_require_xfs_io_command "parent"
+
+# real QA test starts here
+
+# Create a directory tree using a protofile and
+# make sure all inodes created have parent pointers
+
+protofile=$tmp.proto
+
+cat >$protofile <<EOF
+DUMMY1
+0 0
+: root directory
+d--777 3 1
+: a directory
+testfolder1 d--755 3 1
+file1 ---755 3 1 /dev/null
+$
+: back in the root
+testfolder2 d--755 3 1
+file2 ---755 3 1 /dev/null
+: done
+$
+EOF
+
+_scratch_mkfs -f -n parent=1 -p $protofile >>$seqres.full 2>&1 \
+ || _fail "mkfs failed"
+_check_scratch_fs
+
+_scratch_mount >>$seqres.full 2>&1 \
+ || _fail "mount failed"
+
+testfolder1="testfolder1"
+testfolder2="testfolder2"
+file1="file1"
+file2="file2"
+file3="file3"
+file1_ln="file1_link"
+
+echo ""
+# Create parent pointer test
+_xfs_verify_parent "$testfolder1" "$file1" "$testfolder1/$file1"
+
+echo ""
+# Move parent pointer test
+mv $SCRATCH_MNT/$testfolder1/$file1 $SCRATCH_MNT/$testfolder2/$file1
+_xfs_verify_parent "$testfolder2" "$file1" "$testfolder2/$file1"
+
+echo ""
+# Hard link parent pointer test
+ln $SCRATCH_MNT/$testfolder2/$file1 $SCRATCH_MNT/$testfolder1/$file1_ln
+_xfs_verify_parent "$testfolder1" "$file1_ln" "$testfolder1/$file1_ln"
+_xfs_verify_parent "$testfolder1" "$file1_ln" "$testfolder2/$file1"
+_xfs_verify_parent "$testfolder2" "$file1" "$testfolder1/$file1_ln"
+_xfs_verify_parent "$testfolder2" "$file1" "$testfolder2/$file1"
+
+echo ""
+# Remove hard link parent pointer test
+ino="$(stat -c '%i' $SCRATCH_MNT/$testfolder2/$file1)"
+rm $SCRATCH_MNT/$testfolder2/$file1
+_xfs_verify_parent "$testfolder1" "$file1_ln" "$testfolder1/$file1_ln"
+_xfs_verify_no_parent "$file1" "$ino" "$testfolder1/$file1_ln"
+
+echo ""
+# Rename parent pointer test
+ino="$(stat -c '%i' $SCRATCH_MNT/$testfolder1/$file1_ln)"
+mv $SCRATCH_MNT/$testfolder1/$file1_ln $SCRATCH_MNT/$testfolder1/$file2
+_xfs_verify_parent "$testfolder1" "$file2" "$testfolder1/$file2"
+_xfs_verify_no_parent "$file1_ln" "$ino" "$testfolder1/$file2"
+
+echo ""
+# Over write parent pointer test
+touch $SCRATCH_MNT/$testfolder2/$file3
+_xfs_verify_parent "$testfolder2" "$file3" "$testfolder2/$file3"
+ino="$(stat -c '%i' $SCRATCH_MNT/$testfolder2/$file3)"
+mv -f $SCRATCH_MNT/$testfolder2/$file3 $SCRATCH_MNT/$testfolder1/$file2
+_xfs_verify_parent "$testfolder1" "$file2" "$testfolder1/$file2"
+
+# Make sure that parent -p filtering works
+mkdir -p $SCRATCH_MNT/dira/ $SCRATCH_MNT/dirb/
+dira_inum=$(stat -c '%i' $SCRATCH_MNT/dira)
+dirb_inum=$(stat -c '%i' $SCRATCH_MNT/dirb)
+touch $SCRATCH_MNT/gorn
+ln $SCRATCH_MNT/gorn $SCRATCH_MNT/dira/file1
+ln $SCRATCH_MNT/gorn $SCRATCH_MNT/dirb/file1
+echo look for both
+$XFS_IO_PROG -c 'parent -p' $SCRATCH_MNT/gorn | _filter_scratch
+echo look for dira
+$XFS_IO_PROG -c 'parent -p -n dira' -c "parent -p -i $dira_inum" $SCRATCH_MNT/gorn | _filter_scratch
+echo look for dirb
+$XFS_IO_PROG -c 'parent -p -n dirb' -c "parent -p -i $dirb_inum" $SCRATCH_MNT/gorn | _filter_scratch
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1851.out b/tests/xfs/1851.out
new file mode 100644
index 0000000000..99a9d42892
--- /dev/null
+++ b/tests/xfs/1851.out
@@ -0,0 +1,69 @@
+QA output created by 1851
+
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1
+
+*** testfolder2 OK
+*** testfolder2/file1 OK
+*** testfolder2/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder2/file1
+
+*** testfolder1 OK
+*** testfolder1/file1_link OK
+*** testfolder1/file1_link OK
+*** Verified parent pointer: name:file1_link, namelen:10
+*** Parent pointer OK for child testfolder1/file1_link
+*** testfolder1 OK
+*** testfolder2/file1 OK
+*** testfolder1/file1_link OK
+*** Verified parent pointer: name:file1_link, namelen:10
+*** Parent pointer OK for child testfolder2/file1
+*** testfolder2 OK
+*** testfolder1/file1_link OK
+*** testfolder2/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link
+*** testfolder2 OK
+*** testfolder2/file1 OK
+*** testfolder2/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder2/file1
+
+*** testfolder1 OK
+*** testfolder1/file1_link OK
+*** testfolder1/file1_link OK
+*** Verified parent pointer: name:file1_link, namelen:10
+*** Parent pointer OK for child testfolder1/file1_link
+*** testfolder1/file1_link OK
+
+*** testfolder1 OK
+*** testfolder1/file2 OK
+*** testfolder1/file2 OK
+*** Verified parent pointer: name:file2, namelen:5
+*** Parent pointer OK for child testfolder1/file2
+*** testfolder1/file2 OK
+
+*** testfolder2 OK
+*** testfolder2/file3 OK
+*** testfolder2/file3 OK
+*** Verified parent pointer: name:file3, namelen:5
+*** Parent pointer OK for child testfolder2/file3
+*** testfolder1 OK
+*** testfolder1/file2 OK
+*** testfolder1/file2 OK
+*** Verified parent pointer: name:file2, namelen:5
+*** Parent pointer OK for child testfolder1/file2
+look for both
+SCRATCH_MNT/gorn
+SCRATCH_MNT/dira/file1
+SCRATCH_MNT/dirb/file1
+look for dira
+SCRATCH_MNT/dira/file1
+SCRATCH_MNT/dira/file1
+look for dirb
+SCRATCH_MNT/dirb/file1
+SCRATCH_MNT/dirb/file1
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 10/11] xfs: add multi link parent pointer test
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (8 preceding siblings ...)
2024-06-20 20:59 ` [PATCH 09/11] xfs: add parent pointer test Darrick J. Wong
@ 2024-06-20 20:59 ` Darrick J. Wong
2024-06-20 20:59 ` [PATCH 11/11] xfs: add parent pointer inject test Darrick J. Wong
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:59 UTC (permalink / raw)
To: djwong, zlang
Cc: Allison Henderson, Catherine Hoang, Christoph Hellwig, fstests,
allison.henderson, catherine.hoang, linux-xfs
From: Allison Henderson <allison.henderson@oracle.com>
Add a test to verify parent pointers while multiple links to a file are
created and removed.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/1852 | 69 ++++
tests/xfs/1852.out | 1002 ++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 1071 insertions(+)
create mode 100755 tests/xfs/1852
create mode 100644 tests/xfs/1852.out
diff --git a/tests/xfs/1852 b/tests/xfs/1852
new file mode 100755
index 0000000000..f0559604a3
--- /dev/null
+++ b/tests/xfs/1852
@@ -0,0 +1,69 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle and/or its affiliates. All Rights Reserved.
+#
+# FS QA Test No. 1852
+#
+# multi link parent pointer test
+#
+. ./common/preamble
+_begin_fstest auto quick parent
+
+# get standard environment, filters and checks
+. ./common/parent
+
+# Modify as appropriate
+_supported_fs xfs
+_require_scratch
+_require_xfs_sysfs debug/larp
+_require_xfs_parent
+_require_xfs_io_command "parent"
+
+# real QA test starts here
+
+# Create a directory tree using a protofile and
+# make sure all inodes created have parent pointers
+
+protofile=$tmp.proto
+
+cat >$protofile <<EOF
+DUMMY1
+0 0
+: root directory
+d--777 3 1
+: a directory
+testfolder1 d--755 3 1
+file1 ---755 3 1 /dev/null
+: done
+$
+EOF
+
+_scratch_mkfs -f -n parent=1 -p $protofile >>$seqresres.full 2>&1 \
+ || _fail "mkfs failed"
+_check_scratch_fs
+
+_scratch_mount >>$seqres.full 2>&1 \
+ || _fail "mount failed"
+
+testfolder1="testfolder1"
+file1="file1"
+file1_ln="file1_link"
+
+echo ""
+# Multi link parent pointer test
+NLINKS=100
+for (( j=0; j<$NLINKS; j++ )); do
+ ln $SCRATCH_MNT/$testfolder1/$file1 $SCRATCH_MNT/$testfolder1/$file1_ln.$j
+ _xfs_verify_parent "$testfolder1" "$file1_ln.$j" "$testfolder1/$file1"
+ _xfs_verify_parent "$testfolder1" "$file1" "$testfolder1/$file1_ln.$j"
+done
+# Multi unlink parent pointer test
+for (( j=$NLINKS-1; j<=0; j-- )); do
+ ino="$(stat -c '%i' $SCRATCH_MNT/$testfolder1/$file1_ln.$j)"
+ rm $SCRATCH_MNT/$testfolder1/$file1_ln.$j
+ _xfs_verify_no_parent "$file1_ln.$j" "$ino" "$testfolder1/$file1"
+done
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1852.out b/tests/xfs/1852.out
new file mode 100644
index 0000000000..a13664d481
--- /dev/null
+++ b/tests/xfs/1852.out
@@ -0,0 +1,1002 @@
+QA output created by 1852
+
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.0 OK
+*** Verified parent pointer: name:file1_link.0, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.0 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.0
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.1 OK
+*** Verified parent pointer: name:file1_link.1, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.1 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.1
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.2 OK
+*** Verified parent pointer: name:file1_link.2, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.2 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.2
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.3 OK
+*** Verified parent pointer: name:file1_link.3, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.3 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.3
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.4 OK
+*** Verified parent pointer: name:file1_link.4, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.4 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.4
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.5 OK
+*** Verified parent pointer: name:file1_link.5, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.5 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.5
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.6 OK
+*** Verified parent pointer: name:file1_link.6, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.6 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.6
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.7 OK
+*** Verified parent pointer: name:file1_link.7, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.7 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.7
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.8 OK
+*** Verified parent pointer: name:file1_link.8, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.8 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.8
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.9 OK
+*** Verified parent pointer: name:file1_link.9, namelen:12
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.9 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.9
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.10 OK
+*** Verified parent pointer: name:file1_link.10, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.10 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.10
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.11 OK
+*** Verified parent pointer: name:file1_link.11, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.11 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.11
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.12 OK
+*** Verified parent pointer: name:file1_link.12, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.12 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.12
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.13 OK
+*** Verified parent pointer: name:file1_link.13, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.13 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.13
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.14 OK
+*** Verified parent pointer: name:file1_link.14, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.14 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.14
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.15 OK
+*** Verified parent pointer: name:file1_link.15, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.15 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.15
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.16 OK
+*** Verified parent pointer: name:file1_link.16, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.16 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.16
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.17 OK
+*** Verified parent pointer: name:file1_link.17, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.17 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.17
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.18 OK
+*** Verified parent pointer: name:file1_link.18, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.18 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.18
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.19 OK
+*** Verified parent pointer: name:file1_link.19, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.19 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.19
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.20 OK
+*** Verified parent pointer: name:file1_link.20, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.20 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.20
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.21 OK
+*** Verified parent pointer: name:file1_link.21, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.21 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.21
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.22 OK
+*** Verified parent pointer: name:file1_link.22, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.22 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.22
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.23 OK
+*** Verified parent pointer: name:file1_link.23, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.23 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.23
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.24 OK
+*** Verified parent pointer: name:file1_link.24, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.24 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.24
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.25 OK
+*** Verified parent pointer: name:file1_link.25, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.25 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.25
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.26 OK
+*** Verified parent pointer: name:file1_link.26, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.26 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.26
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.27 OK
+*** Verified parent pointer: name:file1_link.27, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.27 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.27
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.28 OK
+*** Verified parent pointer: name:file1_link.28, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.28 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.28
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.29 OK
+*** Verified parent pointer: name:file1_link.29, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.29 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.29
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.30 OK
+*** Verified parent pointer: name:file1_link.30, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.30 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.30
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.31 OK
+*** Verified parent pointer: name:file1_link.31, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.31 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.31
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.32 OK
+*** Verified parent pointer: name:file1_link.32, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.32 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.32
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.33 OK
+*** Verified parent pointer: name:file1_link.33, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.33 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.33
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.34 OK
+*** Verified parent pointer: name:file1_link.34, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.34 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.34
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.35 OK
+*** Verified parent pointer: name:file1_link.35, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.35 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.35
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.36 OK
+*** Verified parent pointer: name:file1_link.36, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.36 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.36
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.37 OK
+*** Verified parent pointer: name:file1_link.37, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.37 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.37
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.38 OK
+*** Verified parent pointer: name:file1_link.38, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.38 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.38
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.39 OK
+*** Verified parent pointer: name:file1_link.39, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.39 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.39
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.40 OK
+*** Verified parent pointer: name:file1_link.40, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.40 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.40
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.41 OK
+*** Verified parent pointer: name:file1_link.41, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.41 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.41
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.42 OK
+*** Verified parent pointer: name:file1_link.42, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.42 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.42
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.43 OK
+*** Verified parent pointer: name:file1_link.43, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.43 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.43
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.44 OK
+*** Verified parent pointer: name:file1_link.44, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.44 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.44
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.45 OK
+*** Verified parent pointer: name:file1_link.45, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.45 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.45
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.46 OK
+*** Verified parent pointer: name:file1_link.46, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.46 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.46
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.47 OK
+*** Verified parent pointer: name:file1_link.47, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.47 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.47
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.48 OK
+*** Verified parent pointer: name:file1_link.48, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.48 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.48
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.49 OK
+*** Verified parent pointer: name:file1_link.49, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.49 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.49
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.50 OK
+*** Verified parent pointer: name:file1_link.50, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.50 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.50
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.51 OK
+*** Verified parent pointer: name:file1_link.51, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.51 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.51
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.52 OK
+*** Verified parent pointer: name:file1_link.52, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.52 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.52
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.53 OK
+*** Verified parent pointer: name:file1_link.53, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.53 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.53
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.54 OK
+*** Verified parent pointer: name:file1_link.54, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.54 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.54
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.55 OK
+*** Verified parent pointer: name:file1_link.55, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.55 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.55
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.56 OK
+*** Verified parent pointer: name:file1_link.56, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.56 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.56
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.57 OK
+*** Verified parent pointer: name:file1_link.57, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.57 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.57
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.58 OK
+*** Verified parent pointer: name:file1_link.58, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.58 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.58
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.59 OK
+*** Verified parent pointer: name:file1_link.59, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.59 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.59
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.60 OK
+*** Verified parent pointer: name:file1_link.60, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.60 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.60
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.61 OK
+*** Verified parent pointer: name:file1_link.61, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.61 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.61
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.62 OK
+*** Verified parent pointer: name:file1_link.62, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.62 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.62
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.63 OK
+*** Verified parent pointer: name:file1_link.63, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.63 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.63
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.64 OK
+*** Verified parent pointer: name:file1_link.64, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.64 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.64
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.65 OK
+*** Verified parent pointer: name:file1_link.65, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.65 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.65
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.66 OK
+*** Verified parent pointer: name:file1_link.66, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.66 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.66
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.67 OK
+*** Verified parent pointer: name:file1_link.67, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.67 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.67
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.68 OK
+*** Verified parent pointer: name:file1_link.68, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.68 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.68
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.69 OK
+*** Verified parent pointer: name:file1_link.69, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.69 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.69
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.70 OK
+*** Verified parent pointer: name:file1_link.70, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.70 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.70
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.71 OK
+*** Verified parent pointer: name:file1_link.71, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.71 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.71
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.72 OK
+*** Verified parent pointer: name:file1_link.72, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.72 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.72
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.73 OK
+*** Verified parent pointer: name:file1_link.73, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.73 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.73
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.74 OK
+*** Verified parent pointer: name:file1_link.74, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.74 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.74
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.75 OK
+*** Verified parent pointer: name:file1_link.75, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.75 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.75
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.76 OK
+*** Verified parent pointer: name:file1_link.76, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.76 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.76
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.77 OK
+*** Verified parent pointer: name:file1_link.77, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.77 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.77
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.78 OK
+*** Verified parent pointer: name:file1_link.78, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.78 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.78
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.79 OK
+*** Verified parent pointer: name:file1_link.79, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.79 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.79
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.80 OK
+*** Verified parent pointer: name:file1_link.80, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.80 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.80
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.81 OK
+*** Verified parent pointer: name:file1_link.81, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.81 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.81
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.82 OK
+*** Verified parent pointer: name:file1_link.82, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.82 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.82
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.83 OK
+*** Verified parent pointer: name:file1_link.83, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.83 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.83
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.84 OK
+*** Verified parent pointer: name:file1_link.84, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.84 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.84
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.85 OK
+*** Verified parent pointer: name:file1_link.85, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.85 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.85
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.86 OK
+*** Verified parent pointer: name:file1_link.86, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.86 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.86
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.87 OK
+*** Verified parent pointer: name:file1_link.87, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.87 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.87
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.88 OK
+*** Verified parent pointer: name:file1_link.88, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.88 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.88
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.89 OK
+*** Verified parent pointer: name:file1_link.89, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.89 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.89
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.90 OK
+*** Verified parent pointer: name:file1_link.90, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.90 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.90
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.91 OK
+*** Verified parent pointer: name:file1_link.91, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.91 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.91
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.92 OK
+*** Verified parent pointer: name:file1_link.92, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.92 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.92
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.93 OK
+*** Verified parent pointer: name:file1_link.93, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.93 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.93
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.94 OK
+*** Verified parent pointer: name:file1_link.94, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.94 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.94
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.95 OK
+*** Verified parent pointer: name:file1_link.95, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.95 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.95
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.96 OK
+*** Verified parent pointer: name:file1_link.96, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.96 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.96
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.97 OK
+*** Verified parent pointer: name:file1_link.97, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.97 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.97
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.98 OK
+*** Verified parent pointer: name:file1_link.98, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.98 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.98
+*** testfolder1 OK
+*** testfolder1/file1 OK
+*** testfolder1/file1_link.99 OK
+*** Verified parent pointer: name:file1_link.99, namelen:13
+*** Parent pointer OK for child testfolder1/file1
+*** testfolder1 OK
+*** testfolder1/file1_link.99 OK
+*** testfolder1/file1 OK
+*** Verified parent pointer: name:file1, namelen:5
+*** Parent pointer OK for child testfolder1/file1_link.99
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 11/11] xfs: add parent pointer inject test
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
` (9 preceding siblings ...)
2024-06-20 20:59 ` [PATCH 10/11] xfs: add multi link " Darrick J. Wong
@ 2024-06-20 20:59 ` Darrick J. Wong
10 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 20:59 UTC (permalink / raw)
To: djwong, zlang
Cc: Allison Henderson, Catherine Hoang, Christoph Hellwig, fstests,
allison.henderson, catherine.hoang, linux-xfs
From: Allison Henderson <allison.henderson@oracle.com>
Add a test to verify parent pointers after an error injection and log
replay.
Signed-off-by: Allison Henderson <allison.henderson@oracle.com>
Signed-off-by: Catherine Hoang <catherine.hoang@oracle.com>
Reviewed-by: Darrick J. Wong <djwong@kernel.org>
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/1853 | 85 ++++++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1853.out | 14 +++++++++
2 files changed, 99 insertions(+)
create mode 100755 tests/xfs/1853
create mode 100644 tests/xfs/1853.out
diff --git a/tests/xfs/1853 b/tests/xfs/1853
new file mode 100755
index 0000000000..7fdb46a580
--- /dev/null
+++ b/tests/xfs/1853
@@ -0,0 +1,85 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2022-2024 Oracle and/or its affiliates. All Rights Reserved.
+#
+# FS QA Test No. 1853
+#
+# parent pointer inject test
+#
+. ./common/preamble
+_begin_fstest auto quick parent
+
+# get standard environment, filters and checks
+. ./common/filter
+. ./common/inject
+. ./common/parent
+
+# Modify as appropriate
+_supported_fs xfs
+_require_scratch
+_require_xfs_sysfs debug/larp
+_require_xfs_io_error_injection "larp"
+_require_xfs_parent
+_require_xfs_io_command "parent"
+
+# real QA test starts here
+
+# Create a directory tree using a protofile and
+# make sure all inodes created have parent pointers
+
+protofile=$tmp.proto
+
+cat >$protofile <<EOF
+DUMMY1
+0 0
+: root directory
+d--777 3 1
+: a directory
+testfolder1 d--755 3 1
+$
+: back in the root
+testfolder2 d--755 3 1
+: done
+$
+EOF
+
+_scratch_mkfs -f -n parent=1 -p $protofile >>$seqres.full 2>&1 \
+ || _fail "mkfs failed"
+_check_scratch_fs
+
+_scratch_mount >>$seqres.full 2>&1 \
+ || _fail "mount failed"
+
+testfolder1="testfolder1"
+testfolder2="testfolder2"
+file4="file4"
+file5="file5"
+
+echo ""
+
+# Create files
+touch $SCRATCH_MNT/$testfolder1/$file4
+_xfs_verify_parent "$testfolder1" "$file4" "$testfolder1/$file4"
+
+# Inject error
+_scratch_inject_error "larp"
+
+# Move files
+mv $SCRATCH_MNT/$testfolder1/$file4 $SCRATCH_MNT/$testfolder2/$file5 2>&1 \
+ | _filter_scratch
+
+# FS should be shut down, touch will fail
+touch $SCRATCH_MNT/$testfolder2/$file5 2>&1 | _filter_scratch
+
+# Remount to replay log
+_scratch_remount_dump_log >> $seqres.full
+
+# FS should be online, touch should succeed
+touch $SCRATCH_MNT/$testfolder2/$file5
+
+# Check files again
+_xfs_verify_parent "$testfolder2" "$file5" "$testfolder2/$file5"
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1853.out b/tests/xfs/1853.out
new file mode 100644
index 0000000000..736f6dec00
--- /dev/null
+++ b/tests/xfs/1853.out
@@ -0,0 +1,14 @@
+QA output created by 1853
+
+*** testfolder1 OK
+*** testfolder1/file4 OK
+*** testfolder1/file4 OK
+*** Verified parent pointer: name:file4, namelen:5
+*** Parent pointer OK for child testfolder1/file4
+mv: cannot stat 'SCRATCH_MNT/testfolder1/file4': Input/output error
+touch: cannot touch 'SCRATCH_MNT/testfolder2/file5': Input/output error
+*** testfolder2 OK
+*** testfolder2/file5 OK
+*** testfolder2/file5 OK
+*** Verified parent pointer: name:file5, namelen:5
+*** Parent pointer OK for child testfolder2/file5
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 1/2] common/fuzzy: stress directory tree modifications with the dirtree tester
2024-06-20 20:53 ` [PATCHSET v30.7 4/6] xfs: detect and correct directory tree structures Darrick J. Wong
@ 2024-06-20 21:00 ` Darrick J. Wong
2024-06-20 21:00 ` [PATCH 2/2] scrub: test correction of directory tree corruptions Darrick J. Wong
1 sibling, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 21:00 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Stress test the directory tree corruption detector by racing it with
fsstress.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/1864 | 38 ++++++++++++++++++++++++++++++++++++++
tests/xfs/1864.out | 2 ++
tests/xfs/1865 | 38 ++++++++++++++++++++++++++++++++++++++
tests/xfs/1865.out | 2 ++
4 files changed, 80 insertions(+)
create mode 100755 tests/xfs/1864
create mode 100644 tests/xfs/1864.out
create mode 100755 tests/xfs/1865
create mode 100644 tests/xfs/1865.out
diff --git a/tests/xfs/1864 b/tests/xfs/1864
new file mode 100755
index 0000000000..d00bcb28b4
--- /dev/null
+++ b/tests/xfs/1864
@@ -0,0 +1,38 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1864
+#
+# Race fsstress and directory tree structure corruption detector for a while to
+# see if we crash or livelock.
+#
+. ./common/preamble
+_begin_fstest scrub dangerous_fsstress_scrub
+
+_cleanup() {
+ _scratch_xfs_stress_scrub_cleanup &> /dev/null
+ cd /
+ rm -r -f $tmp.*
+}
+_register_cleanup "_cleanup" BUS
+
+# Import common functions.
+. ./common/filter
+. ./common/fuzzy
+. ./common/inject
+. ./common/xfs
+
+# real QA test starts here
+_supported_fs xfs
+_require_scratch
+_require_xfs_stress_scrub
+
+_scratch_mkfs > "$seqres.full" 2>&1
+_scratch_mount
+_scratch_xfs_stress_scrub -x 'dir' -s "scrub dirtree" -t "%dir%"
+
+# success, all done
+echo Silence is golden
+status=0
+exit
diff --git a/tests/xfs/1864.out b/tests/xfs/1864.out
new file mode 100644
index 0000000000..472f56323a
--- /dev/null
+++ b/tests/xfs/1864.out
@@ -0,0 +1,2 @@
+QA output created by 1864
+Silence is golden
diff --git a/tests/xfs/1865 b/tests/xfs/1865
new file mode 100755
index 0000000000..098891536c
--- /dev/null
+++ b/tests/xfs/1865
@@ -0,0 +1,38 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1865
+#
+# Race fsstress and directory tree structure repair for a while to see if we
+# crash or livelock.
+#
+. ./common/preamble
+_begin_fstest online_repair dangerous_fsstress_repair
+
+_cleanup() {
+ _scratch_xfs_stress_scrub_cleanup &> /dev/null
+ cd /
+ rm -r -f $tmp.*
+}
+_register_cleanup "_cleanup" BUS
+
+# Import common functions.
+. ./common/filter
+. ./common/fuzzy
+. ./common/inject
+. ./common/xfs
+
+# real QA test starts here
+_supported_fs xfs
+_require_scratch
+_require_xfs_stress_online_repair
+
+_scratch_mkfs > "$seqres.full" 2>&1
+_scratch_mount
+_scratch_xfs_stress_online_repair -x 'dir' -s "repair dirtree" -t "%dir%"
+
+# success, all done
+echo Silence is golden
+status=0
+exit
diff --git a/tests/xfs/1865.out b/tests/xfs/1865.out
new file mode 100644
index 0000000000..9f2fecad3f
--- /dev/null
+++ b/tests/xfs/1865.out
@@ -0,0 +1,2 @@
+QA output created by 1865
+Silence is golden
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 2/2] scrub: test correction of directory tree corruptions
2024-06-20 20:53 ` [PATCHSET v30.7 4/6] xfs: detect and correct directory tree structures Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/2] common/fuzzy: stress directory tree modifications with the dirtree tester Darrick J. Wong
@ 2024-06-20 21:00 ` Darrick J. Wong
1 sibling, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 21:00 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Make sure that we can fix directory tree loops and multiply-owned dirs.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/1866 | 122 ++++++++++++++++++++++++++++++++++++++++
tests/xfs/1866.out | 19 ++++++
tests/xfs/1867 | 133 ++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1867.out | 25 ++++++++
tests/xfs/1868 | 121 ++++++++++++++++++++++++++++++++++++++++
tests/xfs/1868.out | 21 +++++++
tests/xfs/1869 | 157 ++++++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1869.out | 32 +++++++++++
tests/xfs/1870 | 146 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/xfs/1870.out | 30 ++++++++++
tests/xfs/1871 | 78 ++++++++++++++++++++++++++
tests/xfs/1871.out | 2 +
12 files changed, 886 insertions(+)
create mode 100755 tests/xfs/1866
create mode 100644 tests/xfs/1866.out
create mode 100755 tests/xfs/1867
create mode 100644 tests/xfs/1867.out
create mode 100755 tests/xfs/1868
create mode 100644 tests/xfs/1868.out
create mode 100755 tests/xfs/1869
create mode 100644 tests/xfs/1869.out
create mode 100755 tests/xfs/1870
create mode 100644 tests/xfs/1870.out
create mode 100755 tests/xfs/1871
create mode 100644 tests/xfs/1871.out
diff --git a/tests/xfs/1866 b/tests/xfs/1866
new file mode 100755
index 0000000000..280c33da3e
--- /dev/null
+++ b/tests/xfs/1866
@@ -0,0 +1,122 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1866
+#
+# Functional testing for online fsck of a directory loop that is not accessible
+# from the root directory.
+#
+. ./common/preamble
+_begin_fstest auto online_repair
+
+# Import common functions.
+. ./common/filter
+. ./common/inject
+. ./common/fuzzy
+. ./common/populate
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs xfs
+_require_xfs_db_command "link"
+_require_xfs_db_command "unlink"
+_require_scratch
+_require_xfs_stress_online_repair
+
+prepare_fs() {
+ _scratch_mkfs >> $seqres.full
+ _scratch_mount
+ __stress_scrub_check_commands "%dir%" '' '' 'scrub dirtree'
+
+ # Begin by creating the following directory tree:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ mkdir -p "$SCRATCH_MNT/A/B/C"
+
+ root_inum="$(stat -c '%i' "$SCRATCH_MNT/")"
+ a_inum="$(stat -c '%i' "$SCRATCH_MNT/A")"
+ b_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B")"
+ c_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C")"
+
+ echo "root: $root_inum; a: $a_inum; b: $b_inum; c: $c_inum" >> $seqres.full
+
+ # Next, we complete the loop by creating C["A"]->A and deleting root["A"]->A.
+ # Directory tree is now:
+ # A["B"]->B
+ # B["C"]->C
+ # C["A"]->A
+ _scratch_unmount
+
+ root_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $root_inum")
+ a_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $a_inum")
+ b_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $b_inum")
+ c_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $c_inum")
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before C $c_inum" -c "inode $c_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before A $a_inum" -c "inode $a_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+
+ _scratch_xfs_db -x \
+ -c "inode $c_inum" -c "link -i $a_inum A" \
+ -c "inode $root_inum" -c "unlink A" \
+ >> $seqres.full
+
+ _scratch_xfs_db \
+ -c "echo after root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo after C $c_inum" -c "inode $c_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo after A $a_inum" -c "inode $a_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+}
+
+simple_online_repair() {
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+
+ echo "repair root"
+ $XFS_IO_PROG -x -c "repair dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "repair A"
+ $XFS_IO_PROG -x -c "repair dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "repair B"
+ $XFS_IO_PROG -x -c "repair dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "repair C"
+ $XFS_IO_PROG -x -c "repair dirtree $c_inum $c_gen" $SCRATCH_MNT
+
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+}
+
+# Part 1: Use raw ioctls to detect the loop and fix it.
+prepare_fs
+_scratch_mount
+simple_online_repair
+_check_scratch_fs
+_scratch_unmount
+
+# Part 2: Use xfs_scrub to detect the loop and fix it.
+prepare_fs
+_scratch_mount
+_scratch_scrub &>> $seqres.full
+echo "xfs_scrub returned $?" >> $seqres.full
+_check_scratch_fs
+_scratch_unmount
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1866.out b/tests/xfs/1866.out
new file mode 100644
index 0000000000..b6b08aea7f
--- /dev/null
+++ b/tests/xfs/1866.out
@@ -0,0 +1,19 @@
+QA output created by 1866
+check root
+check A
+Corruption detected.
+check B
+Corruption detected.
+check C
+Corruption detected.
+repair root
+Metadata did not need repair or optimization.
+repair A
+repair B
+Metadata did not need repair or optimization.
+repair C
+Metadata did not need repair or optimization.
+check root
+check A
+check B
+check C
diff --git a/tests/xfs/1867 b/tests/xfs/1867
new file mode 100755
index 0000000000..2c34b56503
--- /dev/null
+++ b/tests/xfs/1867
@@ -0,0 +1,133 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1867
+#
+# Functional testing for online fsck of a directory loop that is accessible
+# from the root directory.
+#
+. ./common/preamble
+_begin_fstest auto online_repair
+
+# Import common functions.
+. ./common/filter
+. ./common/inject
+. ./common/fuzzy
+. ./common/populate
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs xfs
+_require_xfs_db_command "link"
+_require_xfs_db_command "unlink"
+_require_scratch
+_require_xfs_stress_online_repair
+
+prepare_fs() {
+ _scratch_mkfs >> $seqres.full
+ _scratch_mount
+ __stress_scrub_check_commands "%dir%" '' '' 'scrub dirtree'
+
+ # Begin by creating the following directory tree:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ # C["D"]->D
+ mkdir -p "$SCRATCH_MNT/A/B/C/D"
+
+ root_inum="$(stat -c '%i' "$SCRATCH_MNT/")"
+ a_inum="$(stat -c '%i' "$SCRATCH_MNT/A")"
+ b_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B")"
+ c_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C")"
+ d_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C/D")"
+
+ echo "root: $root_inum; a: $a_inum; b: $b_inum; c: $c_inum; d: $d_inum" >> $seqres.full
+
+ # Next, we complete the loop by creating D["B1"]->B. Directory tree is now:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ # C["D"]->D
+ # D["B1"]->B
+ _scratch_unmount
+
+ root_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $root_inum")
+ a_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $a_inum")
+ b_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $b_inum")
+ c_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $c_inum")
+ d_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $d_inum")
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before D $d_inum" -c "inode $d_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before B $b_inum" -c "inode $b_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+
+ _scratch_xfs_db -x \
+ -c "inode $d_inum" -c "link -i $b_inum B1" \
+ >> $seqres.full
+
+ _scratch_xfs_db \
+ -c "echo after root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo after D $c_inum" -c "inode $d_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo after B $a_inum" -c "inode $b_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+}
+
+simple_online_repair() {
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "check D"
+ $XFS_IO_PROG -c "scrub dirtree $d_inum $d_gen" $SCRATCH_MNT
+
+ echo "repair root"
+ $XFS_IO_PROG -x -c "repair dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "repair A"
+ $XFS_IO_PROG -x -c "repair dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "repair D"
+ $XFS_IO_PROG -x -c "repair dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "repair B"
+ $XFS_IO_PROG -x -c "repair dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "repair C"
+ $XFS_IO_PROG -x -c "repair dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "repair D"
+ $XFS_IO_PROG -x -c "repair dirtree $d_inum $d_gen" $SCRATCH_MNT
+
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "check D"
+ $XFS_IO_PROG -c "scrub dirtree $d_inum $d_gen" $SCRATCH_MNT
+}
+
+# Part 1: Use raw ioctls to detect the loop and fix it.
+prepare_fs
+_scratch_mount
+simple_online_repair
+_check_scratch_fs
+_scratch_unmount
+
+# Part 2: Use xfs_scrub to detect the loop and fix it.
+prepare_fs
+_scratch_mount
+_scratch_scrub &>> $seqres.full
+echo "xfs_scrub returned $?" >> $seqres.full
+_check_scratch_fs
+_scratch_unmount
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1867.out b/tests/xfs/1867.out
new file mode 100644
index 0000000000..88fbb85e50
--- /dev/null
+++ b/tests/xfs/1867.out
@@ -0,0 +1,25 @@
+QA output created by 1867
+check root
+check A
+check B
+Corruption detected.
+check C
+Corruption detected during cross-referencing.
+check D
+Corruption detected during cross-referencing.
+repair root
+Metadata did not need repair or optimization.
+repair A
+Metadata did not need repair or optimization.
+repair D
+Corruption still detected during cross-referencing.
+repair B
+repair C
+Metadata did not need repair or optimization.
+repair D
+Metadata did not need repair or optimization.
+check root
+check A
+check B
+check C
+check D
diff --git a/tests/xfs/1868 b/tests/xfs/1868
new file mode 100755
index 0000000000..7436343c0c
--- /dev/null
+++ b/tests/xfs/1868
@@ -0,0 +1,121 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1868
+#
+# Functional testing for online fsck of a directory chain that is not
+# accessible from the root directory.
+#
+. ./common/preamble
+_begin_fstest auto online_repair
+
+# Import common functions.
+. ./common/filter
+. ./common/inject
+. ./common/fuzzy
+. ./common/populate
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs xfs
+_require_xfs_db_command "link"
+_require_xfs_db_command "unlink"
+_require_scratch
+_require_xfs_stress_online_repair
+
+prepare_fs() {
+ _scratch_mkfs >> $seqres.full
+ _scratch_mount
+ __stress_scrub_check_commands "%dir%" '' '' 'scrub dirtree'
+
+ # Begin by creating the following directory tree:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ mkdir -p "$SCRATCH_MNT/A/B/C"
+
+ root_inum="$(stat -c '%i' "$SCRATCH_MNT/")"
+ a_inum="$(stat -c '%i' "$SCRATCH_MNT/A")"
+ b_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B")"
+ c_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C")"
+
+ echo "root: $root_inum; a: $a_inum; b: $b_inum; c: $c_inum" >> $seqres.full
+
+ # Next, we sever the tree by deleting root["A"]->A. Directory tree is now:
+ # A["B"]->B
+ # B["C"]->C
+ _scratch_unmount
+
+ root_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $root_inum")
+ a_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $a_inum")
+ b_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $b_inum")
+ c_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $c_inum")
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before C $c_inum" -c "inode $c_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before A $a_inum" -c "inode $a_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+
+ _scratch_xfs_db -x \
+ -c "inode $root_inum" -c "unlink A" \
+ >> $seqres.full
+
+ _scratch_xfs_db \
+ -c "echo after root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo after C $c_inum" -c "inode $c_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo after A $a_inum" -c "inode $a_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+}
+
+simple_online_repair() {
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+
+ echo "repair C"
+ $XFS_IO_PROG -x -c "repair dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "repair root"
+ $XFS_IO_PROG -x -c "repair dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "repair A"
+ $XFS_IO_PROG -x -c "repair dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "repair B"
+ $XFS_IO_PROG -x -c "repair dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "repair C"
+ $XFS_IO_PROG -x -c "repair dirtree $c_inum $c_gen" $SCRATCH_MNT
+
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+}
+
+# Part 1: Use raw ioctls to detect the chain and fix it.
+prepare_fs
+_scratch_mount
+simple_online_repair
+_check_scratch_fs
+_scratch_unmount
+
+# Part 2: Use xfs_scrub to detect the chain and fix it.
+prepare_fs
+_scratch_mount
+_scratch_scrub &>> $seqres.full
+echo "xfs_scrub returned $?" >> $seqres.full
+_check_scratch_fs
+_scratch_unmount
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1868.out b/tests/xfs/1868.out
new file mode 100644
index 0000000000..f4f444ed52
--- /dev/null
+++ b/tests/xfs/1868.out
@@ -0,0 +1,21 @@
+QA output created by 1868
+check root
+check A
+Corruption detected.
+check B
+Corruption detected during cross-referencing.
+check C
+Corruption detected during cross-referencing.
+repair C
+Corruption still detected during cross-referencing.
+repair root
+Metadata did not need repair or optimization.
+repair A
+repair B
+Metadata did not need repair or optimization.
+repair C
+Metadata did not need repair or optimization.
+check root
+check A
+check B
+check C
diff --git a/tests/xfs/1869 b/tests/xfs/1869
new file mode 100755
index 0000000000..188bc0adc8
--- /dev/null
+++ b/tests/xfs/1869
@@ -0,0 +1,157 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1869
+#
+# Functional testing for online fsck of a multiply-owned directory that is
+# accessible from the root directory.
+#
+. ./common/preamble
+_begin_fstest auto online_repair
+
+# Import common functions.
+. ./common/filter
+. ./common/inject
+. ./common/fuzzy
+. ./common/populate
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs xfs
+_require_xfs_db_command "link"
+_require_xfs_db_command "unlink"
+_require_scratch
+_require_xfs_stress_online_repair
+
+prepare_fs() {
+ _scratch_mkfs >> $seqres.full
+ _scratch_mount
+ __stress_scrub_check_commands "%dir%" '' '' 'scrub dirtree'
+
+ # Begin by creating the following directory tree:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ # C["D"]->D
+ # root["Z"]->Z
+ # Z["Y"]->Y
+ mkdir -p "$SCRATCH_MNT/A/B/C/D" "$SCRATCH_MNT/Z/Y"
+
+ root_inum="$(stat -c '%i' "$SCRATCH_MNT/")"
+ a_inum="$(stat -c '%i' "$SCRATCH_MNT/A")"
+ b_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B")"
+ c_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C")"
+ d_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C/D")"
+ z_inum="$(stat -c '%i' "$SCRATCH_MNT/Z")"
+ y_inum="$(stat -c '%i' "$SCRATCH_MNT/Z/Y")"
+
+ echo "root: $root_inum; a: $a_inum; b: $b_inum; c: $c_inum; d: $d_inum" >> $seqres.full
+ echo "root: $root_inum; z: $z_inum; y: $y_inum" >> $seqres.full
+
+ # Next, we create the multiply-owned directory by creating Y["C1"]->C.
+ # Directory tree is now:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ # C["D"]->D
+ # root["Z"]->Z
+ # Z["Y"]->Y
+ # Y["C1"]->C
+ _scratch_unmount
+
+ root_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $root_inum")
+ a_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $a_inum")
+ b_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $b_inum")
+ c_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $c_inum")
+ d_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $d_inum")
+ z_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $z_inum")
+ y_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $y_inum")
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before Y $y_inum" -c "inode $y_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before B $b_inum" -c "inode $b_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before C $c_inum" -c "inode $c_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+
+ _scratch_xfs_db -x \
+ -c "inode $y_inum" -c "link -i $c_inum C1" \
+ >> $seqres.full
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before Y $y_inum" -c "inode $y_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before B $b_inum" -c "inode $b_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before C $c_inum" -c "inode $c_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+}
+
+simple_online_repair() {
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "check D"
+ $XFS_IO_PROG -c "scrub dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "check Z"
+ $XFS_IO_PROG -c "scrub dirtree $z_inum $z_gen" $SCRATCH_MNT
+ echo "check Y"
+ $XFS_IO_PROG -c "scrub dirtree $y_inum $y_gen" $SCRATCH_MNT
+
+ echo "repair D"
+ $XFS_IO_PROG -x -c "repair dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "repair root"
+ $XFS_IO_PROG -x -c "repair dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "repair A"
+ $XFS_IO_PROG -x -c "repair dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "repair B"
+ $XFS_IO_PROG -x -c "repair dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "repair C"
+ $XFS_IO_PROG -x -c "repair dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "repair D"
+ $XFS_IO_PROG -x -c "repair dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "repair Z"
+ $XFS_IO_PROG -x -c "repair dirtree $z_inum $z_gen" $SCRATCH_MNT
+ echo "repair Y"
+ $XFS_IO_PROG -x -c "repair dirtree $y_inum $y_gen" $SCRATCH_MNT
+
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "check D"
+ $XFS_IO_PROG -c "scrub dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "check Z"
+ $XFS_IO_PROG -c "scrub dirtree $z_inum $z_gen" $SCRATCH_MNT
+ echo "check Y"
+ $XFS_IO_PROG -c "scrub dirtree $y_inum $y_gen" $SCRATCH_MNT
+}
+
+# Part 1: Use raw ioctls to detect the multi-parent dir and fix it.
+prepare_fs
+_scratch_mount
+simple_online_repair
+_check_scratch_fs
+_scratch_unmount
+
+# Part 2: Use xfs_scrub to detect the multi-parent dir and fix it.
+prepare_fs
+_scratch_mount
+_scratch_scrub &>> $seqres.full
+echo "xfs_scrub returned $?" >> $seqres.full
+_check_scratch_fs
+_scratch_unmount
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1869.out b/tests/xfs/1869.out
new file mode 100644
index 0000000000..a7ea4c2223
--- /dev/null
+++ b/tests/xfs/1869.out
@@ -0,0 +1,32 @@
+QA output created by 1869
+check root
+check A
+check B
+check C
+Corruption detected.
+check D
+Corruption detected during cross-referencing.
+check Z
+check Y
+repair D
+Corruption still detected during cross-referencing.
+repair root
+Metadata did not need repair or optimization.
+repair A
+Metadata did not need repair or optimization.
+repair B
+Metadata did not need repair or optimization.
+repair C
+repair D
+Metadata did not need repair or optimization.
+repair Z
+Metadata did not need repair or optimization.
+repair Y
+Metadata did not need repair or optimization.
+check root
+check A
+check B
+check C
+check D
+check Z
+check Y
diff --git a/tests/xfs/1870 b/tests/xfs/1870
new file mode 100755
index 0000000000..c4a32de061
--- /dev/null
+++ b/tests/xfs/1870
@@ -0,0 +1,146 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1870
+#
+# Functional testing for online fsck of a directory loop that is inaccessible
+# from the root directory and has subdirectories.
+#
+. ./common/preamble
+_begin_fstest auto online_repair
+
+# Import common functions.
+. ./common/filter
+. ./common/inject
+. ./common/fuzzy
+. ./common/populate
+
+# real QA test starts here
+
+# Modify as appropriate.
+_supported_fs xfs
+_require_xfs_db_command "link"
+_require_xfs_db_command "unlink"
+_require_scratch
+_require_xfs_stress_online_repair
+
+prepare_fs() {
+ _scratch_mkfs >> $seqres.full
+ _scratch_mount
+ __stress_scrub_check_commands "%dir%" '' '' 'scrub dirtree'
+
+ # Begin by creating the following directory tree:
+ # root["A"]->A
+ # A["B"]->B
+ # B["C"]->C
+ # C["D"]->D
+ # D["E"]->E
+ mkdir -p "$SCRATCH_MNT/A/B/C/D/E"
+
+ root_inum="$(stat -c '%i' "$SCRATCH_MNT/")"
+ a_inum="$(stat -c '%i' "$SCRATCH_MNT/A")"
+ b_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B")"
+ c_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C")"
+ d_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C/D")"
+ e_inum="$(stat -c '%i' "$SCRATCH_MNT/A/B/C/D/E")"
+
+ echo "root: $root_inum; a: $a_inum; b: $b_inum; c: $c_inum; d: $d_inum; e: $e_inum" >> $seqres.full
+
+ # Complete the loop by creating D["B1"]->B and severing A["B"]->B. Directory
+ # tree is now:
+ # root["A"]->A
+ # B["C"]->C
+ # C["D"]->D
+ # D["E"]->E
+ # D["B1"]->B
+ _scratch_unmount
+
+ root_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $root_inum")
+ a_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $a_inum")
+ b_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $b_inum")
+ c_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $c_inum")
+ d_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $d_inum")
+ e_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $e_inum")
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before A $d_inum" -c "inode $a_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before D $d_inum" -c "inode $d_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before B $b_inum" -c "inode $b_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+
+ _scratch_xfs_db -x \
+ -c "inode $d_inum" -c "link -i $b_inum B1" \
+ -c "inode $a_inum" -c "unlink B" \
+ >> $seqres.full
+
+ _scratch_xfs_db \
+ -c "echo before root $root_inum" -c "inode $root_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before A $d_inum" -c "inode $a_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before D $d_inum" -c "inode $d_inum" -c 'print core.nlinkv2' -c "ls" \
+ -c "echo before B $b_inum" -c "inode $b_inum" -c 'print core.nlinkv2' -c "parent" \
+ >> $seqres.full
+}
+
+simple_online_repair() {
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "check D"
+ $XFS_IO_PROG -c "scrub dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "check E"
+ $XFS_IO_PROG -c "scrub dirtree $e_inum $e_gen" $SCRATCH_MNT
+
+ echo "repair root"
+ $XFS_IO_PROG -x -c "repair dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "repair A"
+ $XFS_IO_PROG -x -c "repair dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "repair E"
+ $XFS_IO_PROG -x -c "repair dirtree $e_inum $e_gen" $SCRATCH_MNT
+ echo "repair B"
+ $XFS_IO_PROG -x -c "repair dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "repair C"
+ $XFS_IO_PROG -x -c "repair dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "repair D"
+ $XFS_IO_PROG -x -c "repair dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "repair E"
+ $XFS_IO_PROG -x -c "repair dirtree $e_inum $e_gen" $SCRATCH_MNT
+
+ echo "check root"
+ $XFS_IO_PROG -c "scrub dirtree $root_inum $root_gen" $SCRATCH_MNT
+ echo "check A"
+ $XFS_IO_PROG -c "scrub dirtree $a_inum $a_gen" $SCRATCH_MNT
+ echo "check B"
+ $XFS_IO_PROG -c "scrub dirtree $b_inum $b_gen" $SCRATCH_MNT
+ echo "check C"
+ $XFS_IO_PROG -c "scrub dirtree $c_inum $c_gen" $SCRATCH_MNT
+ echo "check D"
+ $XFS_IO_PROG -c "scrub dirtree $d_inum $d_gen" $SCRATCH_MNT
+ echo "check E"
+ $XFS_IO_PROG -c "scrub dirtree $e_inum $e_gen" $SCRATCH_MNT
+}
+
+# Part 1: Use raw ioctls to detect the loop and fix it.
+prepare_fs
+_scratch_mount
+simple_online_repair
+_check_scratch_fs
+_scratch_unmount
+
+# Part 2: Use xfs_scrub to detect the loop and fix it.
+prepare_fs
+_scratch_mount
+_scratch_scrub &>> $seqres.full
+echo "xfs_scrub returned $?" >> $seqres.full
+_check_scratch_fs
+_scratch_unmount
+
+# success, all done
+status=0
+exit
diff --git a/tests/xfs/1870.out b/tests/xfs/1870.out
new file mode 100644
index 0000000000..8274c6602c
--- /dev/null
+++ b/tests/xfs/1870.out
@@ -0,0 +1,30 @@
+QA output created by 1870
+check root
+check A
+check B
+Corruption detected.
+check C
+Corruption detected.
+check D
+Corruption detected.
+check E
+Corruption detected during cross-referencing.
+repair root
+Metadata did not need repair or optimization.
+repair A
+Metadata did not need repair or optimization.
+repair E
+Corruption still detected during cross-referencing.
+repair B
+repair C
+Metadata did not need repair or optimization.
+repair D
+Metadata did not need repair or optimization.
+repair E
+Metadata did not need repair or optimization.
+check root
+check A
+check B
+check C
+check D
+check E
diff --git a/tests/xfs/1871 b/tests/xfs/1871
new file mode 100755
index 0000000000..760259d18b
--- /dev/null
+++ b/tests/xfs/1871
@@ -0,0 +1,78 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2023-2024 Oracle. All Rights Reserved.
+#
+# FS QA Test No. 1871
+#
+# Race rename and directory tree structure corruption detector for a while to
+# exercise the dirtree code's directory path invalidation and its ability to
+# handle unlinked directories.
+#
+. ./common/preamble
+_begin_fstest scrub dangerous_fsstress_scrub
+
+# Import common functions.
+. ./common/filter
+. ./common/fuzzy
+. ./common/inject
+. ./common/xfs
+
+# real QA test starts here
+_supported_fs xfs
+_require_scratch
+_require_xfs_stress_scrub
+
+_scratch_mkfs > "$seqres.full" 2>&1
+_scratch_mount
+__stress_scrub_check_commands "%dir%" '' '' 'scrub dirtree'
+
+parentA="$SCRATCH_MNT/a"
+parentB="$SCRATCH_MNT/b"
+child="$parentA/c/d/e/f/g/h/i/j/k/l/m/n/o/p"
+unlinked="$SCRATCH_MNT/unlinked"
+
+mkdir -p "$parentA" "$parentB" "$child" "$unlinked"
+
+# Find handle info for the child so that we can scrub by handle
+child_inum="$(stat -c '%i' "$child")"
+_scratch_unmount
+child_gen=$(_scratch_xfs_get_metadata_field core.gen "inode $child_inum")
+_scratch_mount
+
+# Queue up a bunch of scrub requests per invocation
+ioargs=()
+for ((i = 0; i < 100; i++)); do
+ ioargs+=('-c' "scrub dirtree $child_inum $child_gen")
+done
+
+renamer() {
+ # Make sure the scrubber handles unlinked directories correctly
+ # by squatting on an empty directory
+ cd "$unlinked"
+ rm -r -f "$unlinked"
+
+ # Bounce the second level directory between parents to stress the
+ # invalidation detector
+ while [ -e $RUNNING_FILE ]; do
+ mv "$parentA/c" "$parentB/"
+ mv "$parentB/c" "$parentA/"
+ done
+}
+
+RUNNING_FILE="$SCRATCH_MNT/run"
+touch $RUNNING_FILE
+renamer &
+
+# Exercise the directory tree scrubber in two ways -- scrubbing the lowest
+# subdir by handle, and running xfs_scrub on the entire fs.
+while _soak_loop_running $((10 * TIME_FACTOR)); do
+ $XFS_IO_PROG "${ioargs[@]}" "$SCRATCH_MNT"
+ XFS_SCRUB_PHASE=5 _scratch_scrub -n >> $seqres.full
+done
+rm -f $RUNNING_FILE
+wait
+
+# success, all done
+echo Silence is golden
+status=0
+exit
diff --git a/tests/xfs/1871.out b/tests/xfs/1871.out
new file mode 100644
index 0000000000..24331e63d5
--- /dev/null
+++ b/tests/xfs/1871.out
@@ -0,0 +1,2 @@
+QA output created by 1871
+Silence is golden
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 1/1] xfs/122: update for vectored scrub
2024-06-20 20:53 ` [PATCHSET v30.7 5/6] xfs_scrub: vectorize kernel calls Darrick J. Wong
@ 2024-06-20 21:00 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 21:00 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
Add the two new vectored scrub structures.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/122.out | 2 ++
1 file changed, 2 insertions(+)
diff --git a/tests/xfs/122.out b/tests/xfs/122.out
index 7be14ed993..60d8294551 100644
--- a/tests/xfs/122.out
+++ b/tests/xfs/122.out
@@ -124,6 +124,8 @@ sizeof(struct xfs_rtrmap_root) = 4
sizeof(struct xfs_rud_log_format) = 16
sizeof(struct xfs_rui_log_format) = 16
sizeof(struct xfs_scrub_metadata) = 64
+sizeof(struct xfs_scrub_vec) = 16
+sizeof(struct xfs_scrub_vec_head) = 40
sizeof(struct xfs_swap_extent) = 64
sizeof(struct xfs_unmount_log_format) = 8
sizeof(struct xfs_xmd_log_format) = 16
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 1/2] xfs/348: partially revert dbcc549317 ("xfs/348: golden output is not correct")
2024-06-20 20:53 ` [PATCHSET 6/6] fstests: minor fixes for 6.10-rc1 Darrick J. Wong
@ 2024-06-20 21:00 ` Darrick J. Wong
2024-06-20 21:01 ` [PATCH 2/2] generic: test creating and removing symlink xattrs Darrick J. Wong
1 sibling, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 21:00 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, hch, linux-xfs
From: Dave Chinner <dchinner@redhat.com>
In kernel commit 1eb70f54c445f ("xfs: validate inode fork size against
fork format"), we incorrectly started flagging as corrupt symlinks with
short targets that would fit in the inode core but are remote. The
kernel has historically written out symlinks this way and read them back
in, so we're fixing that.
The 1eb70 change came with change dbcc to fstests to adjust the golden
output; since we're adjusting the kernel back to old behavior, we need
to adjust the test too.
Fixes: dbcc549317 ("xfs/348: golden output is not correct")
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/xfs/348.out | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tests/xfs/348.out b/tests/xfs/348.out
index 9130f42af7..591b1a77a6 100644
--- a/tests/xfs/348.out
+++ b/tests/xfs/348.out
@@ -240,7 +240,7 @@ would have junked entry "DIR" in directory PARENT_INO
would have junked entry "EMPTY" in directory PARENT_INO
would have junked entry "FIFO" in directory PARENT_INO
stat: cannot statx 'SCRATCH_MNT/test/DIR': Structure needs cleaning
-stat: cannot statx 'SCRATCH_MNT/test/DATA': Structure needs cleaning
+stat: 'SCRATCH_MNT/test/DATA' is a symbolic link
stat: cannot statx 'SCRATCH_MNT/test/EMPTY': Structure needs cleaning
stat: 'SCRATCH_MNT/test/SYMLINK' is a symbolic link
stat: cannot statx 'SCRATCH_MNT/test/CHRDEV': Structure needs cleaning
^ permalink raw reply related [flat|nested] 49+ messages in thread
* [PATCH 2/2] generic: test creating and removing symlink xattrs
2024-06-20 20:53 ` [PATCHSET 6/6] fstests: minor fixes for 6.10-rc1 Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/2] xfs/348: partially revert dbcc549317 ("xfs/348: golden output is not correct") Darrick J. Wong
@ 2024-06-20 21:01 ` Darrick J. Wong
1 sibling, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-20 21:01 UTC (permalink / raw)
To: djwong, zlang; +Cc: Christoph Hellwig, fstests, hch, linux-xfs
From: Darrick J. Wong <djwong@kernel.org>
This began as a regression test for the issues identified in "xfs: allow
symlinks with short remote targets". To summarize, the kernel XFS code
does not convert a remote symlink back to a shortform symlink after
deleting the attr fork. Recent attempts to tighten validation have
flagged this incorrectly, so we need a regression test to focus on this
dusty corner of the codebase.
However, there's nothing in here that's xfs-specific so it's a generic
test.
Signed-off-by: Darrick J. Wong <djwong@kernel.org>
Reviewed-by: Christoph Hellwig <hch@lst.de>
---
tests/generic/1836 | 58 ++++++++++++++++++++++++++++++++++++++++++++++++
tests/generic/1836.out | 2 ++
2 files changed, 60 insertions(+)
create mode 100755 tests/generic/1836
create mode 100644 tests/generic/1836.out
diff --git a/tests/generic/1836 b/tests/generic/1836
new file mode 100755
index 0000000000..1778e207ab
--- /dev/null
+++ b/tests/generic/1836
@@ -0,0 +1,58 @@
+#! /bin/bash
+# SPDX-License-Identifier: GPL-2.0
+# Copyright (c) 2024 Oracle. All Rights Reserved.
+#
+# FS QA Test 1836
+#
+# Test that we can add xattrs to a symbolic link, remove all the xattrs, and
+# that the symbolic link doesn't get corrupted. This is a regression test for
+# some incorrect checks in the xfs inode verifier.
+#
+. ./common/preamble
+_begin_fstest auto
+
+_supported_fs generic
+_require_scratch
+
+test $FSTYP = "xfs" && \
+ _fixed_by_git_commit kernel XXXXXXXXXXXXX \
+ "xfs: allow symlinks with short remote targets"
+
+_scratch_mkfs >> $seqres.full
+_scratch_mount >> $seqres.full
+
+SYMLINK_ADD="0123456789ABCDEF01234567890ABCDEF"
+
+# test from 32 to MAXPATHLEN sized symlink. This should make sure that
+# 256-1024 byte version 2 and 3 inodes are covered.
+SYMLINK=""
+for ((SIZE = 32; SIZE < 1024; SIZE += 32)); do
+ SYMLINK_FILE="$SCRATCH_MNT/symlink.$SIZE"
+ SYMLINK="${SYMLINK}${SYMLINK_ADD}"
+ ln -s $SYMLINK $SYMLINK_FILE > /dev/null 2>&1
+
+# add the extended attributes
+ attr -Rs 1234567890ab $SYMLINK_FILE < /dev/null > /dev/null 2>&1
+ attr -Rs 1234567890ac $SYMLINK_FILE < /dev/null > /dev/null 2>&1
+ attr -Rs 1234567890ad $SYMLINK_FILE < /dev/null > /dev/null 2>&1
+# remove the extended attributes
+ attr -Rr 1234567890ab $SYMLINK_FILE > /dev/null 2>&1
+ attr -Rr 1234567890ac $SYMLINK_FILE > /dev/null 2>&1
+ attr -Rr 1234567890ad $SYMLINK_FILE > /dev/null 2>&1
+done
+
+_scratch_cycle_mount
+
+# Now check the symlink target contents
+SYMLINK=""
+for ((SIZE = 32; SIZE < 1024; SIZE += 32)); do
+ SYMLINK_FILE="$SCRATCH_MNT/symlink.$SIZE"
+ SYMLINK="${SYMLINK}${SYMLINK_ADD}"
+
+ target="$(readlink $SYMLINK_FILE)"
+ test "$target" = "$SYMLINK" || echo "$SYMLINK_FILE: target is corrupt"
+done
+
+echo Silence is golden
+status=0
+exit
diff --git a/tests/generic/1836.out b/tests/generic/1836.out
new file mode 100644
index 0000000000..cf78922dea
--- /dev/null
+++ b/tests/generic/1836.out
@@ -0,0 +1,2 @@
+QA output created by 1836
+Silence is golden
^ permalink raw reply related [flat|nested] 49+ messages in thread
* Re: [PATCH 03/11] generic/709,710: rework these for exchangerange vs. quota testing
2024-06-20 20:54 ` [PATCH 03/11] generic/709,710: rework these for exchangerange vs. quota testing Darrick J. Wong
@ 2024-06-21 4:35 ` Christoph Hellwig
0 siblings, 0 replies; 49+ messages in thread
From: Christoph Hellwig @ 2024-06-21 4:35 UTC (permalink / raw)
To: Darrick J. Wong; +Cc: zlang, fstests, linux-xfs
Looks good:
Reviewed-by: Christoph Hellwig <hch@lst.de>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range
2024-06-20 20:55 ` [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range Darrick J. Wong
@ 2024-06-21 4:35 ` Christoph Hellwig
2024-06-21 16:14 ` Zorro Lang
1 sibling, 0 replies; 49+ messages in thread
From: Christoph Hellwig @ 2024-06-21 4:35 UTC (permalink / raw)
To: Darrick J. Wong; +Cc: zlang, fstests, linux-xfs
Looks good:
Reviewed-by: Christoph Hellwig <hch@lst.de>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCH 08/11] common: add helpers for parent pointer tests
2024-06-20 20:59 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
@ 2024-06-21 4:36 ` Christoph Hellwig
0 siblings, 0 replies; 49+ messages in thread
From: Christoph Hellwig @ 2024-06-21 4:36 UTC (permalink / raw)
To: Darrick J. Wong
Cc: zlang, Allison Henderson, Catherine Hoang, fstests, linux-xfs
Looks good:
Reviewed-by: Christoph Hellwig <hch@lst.de>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range
2024-06-20 20:55 ` [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range Darrick J. Wong
2024-06-21 4:35 ` Christoph Hellwig
@ 2024-06-21 16:14 ` Zorro Lang
2024-06-21 17:49 ` Darrick J. Wong
1 sibling, 1 reply; 49+ messages in thread
From: Zorro Lang @ 2024-06-21 16:14 UTC (permalink / raw)
To: Darrick J. Wong; +Cc: fstests, linux-xfs
On Thu, Jun 20, 2024 at 01:55:06PM -0700, Darrick J. Wong wrote:
> From: Darrick J. Wong <djwong@kernel.org>
>
> Fork these tests to check the same things with exchange-range as they do
> for swapext, since the code porting swapext to commit-range has been
> dropped.
>
> I was going to fork xfs/789 as well, but it turns out that generic/714
> covers this sufficiently so for that one, we just strike fiexchange from
> the group tag.
>
> Signed-off-by: Darrick J. Wong <djwong@kernel.org>
> ---
> tests/generic/1221 | 45 ++++++++++++++++++++++++
> tests/generic/1221.out | 2 +
> tests/generic/711 | 2 +
> tests/xfs/1215 | 89 ++++++++++++++++++++++++++++++++++++++++++++++++
> tests/xfs/1215.out | 13 +++++++
> tests/xfs/789 | 2 +
Shouldn't the "xfs/537" (in subject) be xfs/789? I'll change that when
I merge it.
Thanks,
Zorro
> 6 files changed, 151 insertions(+), 2 deletions(-)
> create mode 100755 tests/generic/1221
> create mode 100644 tests/generic/1221.out
> create mode 100755 tests/xfs/1215
> create mode 100644 tests/xfs/1215.out
>
>
> diff --git a/tests/generic/1221 b/tests/generic/1221
> new file mode 100755
> index 0000000000..5569f59734
> --- /dev/null
> +++ b/tests/generic/1221
> @@ -0,0 +1,45 @@
> +#! /bin/bash
> +# SPDX-License-Identifier: GPL-2.0-or-later
> +# Copyright (c) 2022 Oracle. All Rights Reserved.
> +#
> +# FS QA Test No. 1221
> +#
> +# Make sure that exchangerange won't touch a swap file.
> +
> +. ./common/preamble
> +_begin_fstest auto quick fiexchange
> +
> +# Override the default cleanup function.
> +_cleanup()
> +{
> + cd /
> + test -e "$dir/a" && swapoff $dir/a
> + rm -r -f $tmp.* $dir
> +}
> +
> +# Import common functions.
> +. ./common/filter
> +
> +# real QA test starts here
> +_require_xfs_io_command exchangerange
> +_require_test
> +
> +dir=$TEST_DIR/test-$seq
> +mkdir -p $dir
> +
> +# Set up a fragmented swapfile and a dummy donor file.
> +$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
> +$here/src/punch-alternating $dir/a
> +$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
> +$MKSWAP_PROG $dir/a >> $seqres.full
> +
> +$XFS_IO_PROG -f -c 'pwrite -S 0x59 0 32m -b 1m' $dir/b >> $seqres.full
> +
> +swapon $dir/a || _notrun 'failed to swapon'
> +
> +# Now try to exchangerange.
> +$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
> +
> +# success, all done
> +status=0
> +exit
> diff --git a/tests/generic/1221.out b/tests/generic/1221.out
> new file mode 100644
> index 0000000000..698ac87303
> --- /dev/null
> +++ b/tests/generic/1221.out
> @@ -0,0 +1,2 @@
> +QA output created by 1221
> +exchangerange: Text file busy
> diff --git a/tests/generic/711 b/tests/generic/711
> index b107f976ef..792136306c 100755
> --- a/tests/generic/711
> +++ b/tests/generic/711
> @@ -7,7 +7,7 @@
> # Make sure that swapext won't touch a swap file.
>
> . ./common/preamble
> -_begin_fstest auto quick fiexchange swapext
> +_begin_fstest auto quick swapext
>
> # Override the default cleanup function.
> _cleanup()
> diff --git a/tests/xfs/1215 b/tests/xfs/1215
> new file mode 100755
> index 0000000000..5e7633c5ea
> --- /dev/null
> +++ b/tests/xfs/1215
> @@ -0,0 +1,89 @@
> +#! /bin/bash
> +# SPDX-License-Identifier: GPL-2.0
> +# Copyright (c) 2024 Oracle. All Rights Reserved.
> +#
> +# FS QA Test No. 1215
> +#
> +# Verify that XFS does not cause inode fork's extent count to overflow when
> +# exchanging ranges between files
> +. ./common/preamble
> +_begin_fstest auto quick collapse fiexchange
> +
> +# Import common functions.
> +. ./common/filter
> +. ./common/inject
> +
> +# real QA test starts here
> +
> +_supported_fs xfs
> +_require_scratch
> +_require_xfs_debug
> +_require_xfs_scratch_rmapbt
> +_require_xfs_io_command "fcollapse"
> +_require_xfs_io_command "exchangerange"
> +_require_xfs_io_error_injection "reduce_max_iextents"
> +
> +echo "* Exchange extent forks"
> +
> +echo "Format and mount fs"
> +_scratch_mkfs >> $seqres.full
> +_scratch_mount >> $seqres.full
> +
> +bsize=$(_get_file_block_size $SCRATCH_MNT)
> +
> +srcfile=${SCRATCH_MNT}/srcfile
> +donorfile=${SCRATCH_MNT}/donorfile
> +
> +echo "Create \$donorfile having an extent of length 67 blocks"
> +$XFS_IO_PROG -f -s -c "pwrite -b $((17 * bsize)) 0 $((17 * bsize))" $donorfile \
> + >> $seqres.full
> +
> +# After the for loop the donor file will have the following extent layout
> +# | 0-4 | 5 | 6 | 7 | 8 | 9 | 10 |
> +echo "Fragment \$donorfile"
> +for i in $(seq 5 10); do
> + start_offset=$((i * bsize))
> + $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $donorfile >> $seqres.full
> +done
> +
> +echo "Create \$srcfile having an extent of length 18 blocks"
> +$XFS_IO_PROG -f -s -c "pwrite -b $((18 * bsize)) 0 $((18 * bsize))" $srcfile \
> + >> $seqres.full
> +
> +echo "Fragment \$srcfile"
> +# After the for loop the src file will have the following extent layout
> +# | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7-10 |
> +for i in $(seq 1 7); do
> + start_offset=$((i * bsize))
> + $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $srcfile >> $seqres.full
> +done
> +
> +echo "Collect \$donorfile's extent count"
> +donor_nr_exts=$(_xfs_get_fsxattr nextents $donorfile)
> +
> +echo "Collect \$srcfile's extent count"
> +src_nr_exts=$(_xfs_get_fsxattr nextents $srcfile)
> +
> +echo "Inject reduce_max_iextents error tag"
> +_scratch_inject_error reduce_max_iextents 1
> +
> +echo "Exchange \$srcfile's and \$donorfile's extent forks"
> +$XFS_IO_PROG -f -c "exchangerange $donorfile" $srcfile >> $seqres.full 2>&1
> +
> +echo "Check for \$donorfile's extent count overflow"
> +nextents=$(_xfs_get_fsxattr nextents $donorfile)
> +
> +if (( $nextents == $src_nr_exts )); then
> + echo "\$donorfile: Extent count overflow check failed"
> +fi
> +
> +echo "Check for \$srcfile's extent count overflow"
> +nextents=$(_xfs_get_fsxattr nextents $srcfile)
> +
> +if (( $nextents == $donor_nr_exts )); then
> + echo "\$srcfile: Extent count overflow check failed"
> +fi
> +
> +# success, all done
> +status=0
> +exit
> diff --git a/tests/xfs/1215.out b/tests/xfs/1215.out
> new file mode 100644
> index 0000000000..48edd56376
> --- /dev/null
> +++ b/tests/xfs/1215.out
> @@ -0,0 +1,13 @@
> +QA output created by 1215
> +* Exchange extent forks
> +Format and mount fs
> +Create $donorfile having an extent of length 67 blocks
> +Fragment $donorfile
> +Create $srcfile having an extent of length 18 blocks
> +Fragment $srcfile
> +Collect $donorfile's extent count
> +Collect $srcfile's extent count
> +Inject reduce_max_iextents error tag
> +Exchange $srcfile's and $donorfile's extent forks
> +Check for $donorfile's extent count overflow
> +Check for $srcfile's extent count overflow
> diff --git a/tests/xfs/789 b/tests/xfs/789
> index 00b98020f2..e3a332d7cf 100755
> --- a/tests/xfs/789
> +++ b/tests/xfs/789
> @@ -7,7 +7,7 @@
> # Simple tests of the old xfs swapext ioctl
>
> . ./common/preamble
> -_begin_fstest auto quick fiexchange swapext
> +_begin_fstest auto quick swapext
>
> # Override the default cleanup function.
> _cleanup()
>
>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCHBOMB] fstests: catch us up to 6.10
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
` (5 preceding siblings ...)
2024-06-20 20:53 ` [PATCHSET 6/6] fstests: minor fixes for 6.10-rc1 Darrick J. Wong
@ 2024-06-21 17:20 ` Zorro Lang
2024-06-21 17:53 ` Darrick J. Wong
6 siblings, 1 reply; 49+ messages in thread
From: Zorro Lang @ 2024-06-21 17:20 UTC (permalink / raw)
To: Darrick J. Wong; +Cc: Christoph Hellwig, fstests, linux-xfs
On Thu, Jun 20, 2024 at 01:50:17PM -0700, Darrick J. Wong wrote:
> Hi everyone,
>
> This patchbomb are all the fixes that xfs needs to bring fstests up to
> date with what's in 6.10-rc. Except for these two patches:
>
> [PATCHSET v30.7 2/6] fstests: atomic file updates
> [PATCH 03/11] generic/709,710: rework these for exchangerange vs.
> [PATCH 04/11] generic/711,xfs/537: actually fork these tests for
>
> everything else in here is fully reviewed and ready for PRs.
Thanks for big updates!
This patchset is big, I've merged and pushed all these patches to
fstests' 'patches-in-queue' branch, feel free to check that.
I need more time to give them more tests, will try to release fstests
at this weekend or middle of next week.
Thanks,
Zorro
>
> --D
>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range
2024-06-21 16:14 ` Zorro Lang
@ 2024-06-21 17:49 ` Darrick J. Wong
2024-06-23 12:30 ` Zorro Lang
0 siblings, 1 reply; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-21 17:49 UTC (permalink / raw)
To: Zorro Lang; +Cc: fstests, linux-xfs
On Sat, Jun 22, 2024 at 12:14:37AM +0800, Zorro Lang wrote:
> On Thu, Jun 20, 2024 at 01:55:06PM -0700, Darrick J. Wong wrote:
> > From: Darrick J. Wong <djwong@kernel.org>
> >
> > Fork these tests to check the same things with exchange-range as they do
> > for swapext, since the code porting swapext to commit-range has been
> > dropped.
> >
> > I was going to fork xfs/789 as well, but it turns out that generic/714
> > covers this sufficiently so for that one, we just strike fiexchange from
> > the group tag.
> >
> > Signed-off-by: Darrick J. Wong <djwong@kernel.org>
> > ---
> > tests/generic/1221 | 45 ++++++++++++++++++++++++
> > tests/generic/1221.out | 2 +
> > tests/generic/711 | 2 +
> > tests/xfs/1215 | 89 ++++++++++++++++++++++++++++++++++++++++++++++++
> > tests/xfs/1215.out | 13 +++++++
> > tests/xfs/789 | 2 +
>
> Shouldn't the "xfs/537" (in subject) be xfs/789? I'll change that when
> I merge it.
No. generic/711 is forked to become generic/1221, and xfs/537 is forked
to become xfs/1215. Maybe I should say that explicitly?
"Fork these tests to check the same things with exchange-range as they do
for swapext, since the code porting swapext to commit-range has been
dropped. generic/711 is forked to generic/1221, and xfs/537 is forked
to xfs/1215.
"I was going to fork xfs/789 as well, but it turns out that generic/714
covers this sufficiently so for that one, we just strike fiexchange from
the group tag."
--D
> Thanks,
> Zorro
>
> > 6 files changed, 151 insertions(+), 2 deletions(-)
> > create mode 100755 tests/generic/1221
> > create mode 100644 tests/generic/1221.out
> > create mode 100755 tests/xfs/1215
> > create mode 100644 tests/xfs/1215.out
> >
> >
> > diff --git a/tests/generic/1221 b/tests/generic/1221
> > new file mode 100755
> > index 0000000000..5569f59734
> > --- /dev/null
> > +++ b/tests/generic/1221
> > @@ -0,0 +1,45 @@
> > +#! /bin/bash
> > +# SPDX-License-Identifier: GPL-2.0-or-later
> > +# Copyright (c) 2022 Oracle. All Rights Reserved.
> > +#
> > +# FS QA Test No. 1221
> > +#
> > +# Make sure that exchangerange won't touch a swap file.
> > +
> > +. ./common/preamble
> > +_begin_fstest auto quick fiexchange
> > +
> > +# Override the default cleanup function.
> > +_cleanup()
> > +{
> > + cd /
> > + test -e "$dir/a" && swapoff $dir/a
> > + rm -r -f $tmp.* $dir
> > +}
> > +
> > +# Import common functions.
> > +. ./common/filter
> > +
> > +# real QA test starts here
> > +_require_xfs_io_command exchangerange
> > +_require_test
> > +
> > +dir=$TEST_DIR/test-$seq
> > +mkdir -p $dir
> > +
> > +# Set up a fragmented swapfile and a dummy donor file.
> > +$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
> > +$here/src/punch-alternating $dir/a
> > +$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
> > +$MKSWAP_PROG $dir/a >> $seqres.full
> > +
> > +$XFS_IO_PROG -f -c 'pwrite -S 0x59 0 32m -b 1m' $dir/b >> $seqres.full
> > +
> > +swapon $dir/a || _notrun 'failed to swapon'
> > +
> > +# Now try to exchangerange.
> > +$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
> > +
> > +# success, all done
> > +status=0
> > +exit
> > diff --git a/tests/generic/1221.out b/tests/generic/1221.out
> > new file mode 100644
> > index 0000000000..698ac87303
> > --- /dev/null
> > +++ b/tests/generic/1221.out
> > @@ -0,0 +1,2 @@
> > +QA output created by 1221
> > +exchangerange: Text file busy
> > diff --git a/tests/generic/711 b/tests/generic/711
> > index b107f976ef..792136306c 100755
> > --- a/tests/generic/711
> > +++ b/tests/generic/711
> > @@ -7,7 +7,7 @@
> > # Make sure that swapext won't touch a swap file.
> >
> > . ./common/preamble
> > -_begin_fstest auto quick fiexchange swapext
> > +_begin_fstest auto quick swapext
> >
> > # Override the default cleanup function.
> > _cleanup()
> > diff --git a/tests/xfs/1215 b/tests/xfs/1215
> > new file mode 100755
> > index 0000000000..5e7633c5ea
> > --- /dev/null
> > +++ b/tests/xfs/1215
> > @@ -0,0 +1,89 @@
> > +#! /bin/bash
> > +# SPDX-License-Identifier: GPL-2.0
> > +# Copyright (c) 2024 Oracle. All Rights Reserved.
> > +#
> > +# FS QA Test No. 1215
> > +#
> > +# Verify that XFS does not cause inode fork's extent count to overflow when
> > +# exchanging ranges between files
> > +. ./common/preamble
> > +_begin_fstest auto quick collapse fiexchange
> > +
> > +# Import common functions.
> > +. ./common/filter
> > +. ./common/inject
> > +
> > +# real QA test starts here
> > +
> > +_supported_fs xfs
> > +_require_scratch
> > +_require_xfs_debug
> > +_require_xfs_scratch_rmapbt
> > +_require_xfs_io_command "fcollapse"
> > +_require_xfs_io_command "exchangerange"
> > +_require_xfs_io_error_injection "reduce_max_iextents"
> > +
> > +echo "* Exchange extent forks"
> > +
> > +echo "Format and mount fs"
> > +_scratch_mkfs >> $seqres.full
> > +_scratch_mount >> $seqres.full
> > +
> > +bsize=$(_get_file_block_size $SCRATCH_MNT)
> > +
> > +srcfile=${SCRATCH_MNT}/srcfile
> > +donorfile=${SCRATCH_MNT}/donorfile
> > +
> > +echo "Create \$donorfile having an extent of length 67 blocks"
> > +$XFS_IO_PROG -f -s -c "pwrite -b $((17 * bsize)) 0 $((17 * bsize))" $donorfile \
> > + >> $seqres.full
> > +
> > +# After the for loop the donor file will have the following extent layout
> > +# | 0-4 | 5 | 6 | 7 | 8 | 9 | 10 |
> > +echo "Fragment \$donorfile"
> > +for i in $(seq 5 10); do
> > + start_offset=$((i * bsize))
> > + $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $donorfile >> $seqres.full
> > +done
> > +
> > +echo "Create \$srcfile having an extent of length 18 blocks"
> > +$XFS_IO_PROG -f -s -c "pwrite -b $((18 * bsize)) 0 $((18 * bsize))" $srcfile \
> > + >> $seqres.full
> > +
> > +echo "Fragment \$srcfile"
> > +# After the for loop the src file will have the following extent layout
> > +# | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7-10 |
> > +for i in $(seq 1 7); do
> > + start_offset=$((i * bsize))
> > + $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $srcfile >> $seqres.full
> > +done
> > +
> > +echo "Collect \$donorfile's extent count"
> > +donor_nr_exts=$(_xfs_get_fsxattr nextents $donorfile)
> > +
> > +echo "Collect \$srcfile's extent count"
> > +src_nr_exts=$(_xfs_get_fsxattr nextents $srcfile)
> > +
> > +echo "Inject reduce_max_iextents error tag"
> > +_scratch_inject_error reduce_max_iextents 1
> > +
> > +echo "Exchange \$srcfile's and \$donorfile's extent forks"
> > +$XFS_IO_PROG -f -c "exchangerange $donorfile" $srcfile >> $seqres.full 2>&1
> > +
> > +echo "Check for \$donorfile's extent count overflow"
> > +nextents=$(_xfs_get_fsxattr nextents $donorfile)
> > +
> > +if (( $nextents == $src_nr_exts )); then
> > + echo "\$donorfile: Extent count overflow check failed"
> > +fi
> > +
> > +echo "Check for \$srcfile's extent count overflow"
> > +nextents=$(_xfs_get_fsxattr nextents $srcfile)
> > +
> > +if (( $nextents == $donor_nr_exts )); then
> > + echo "\$srcfile: Extent count overflow check failed"
> > +fi
> > +
> > +# success, all done
> > +status=0
> > +exit
> > diff --git a/tests/xfs/1215.out b/tests/xfs/1215.out
> > new file mode 100644
> > index 0000000000..48edd56376
> > --- /dev/null
> > +++ b/tests/xfs/1215.out
> > @@ -0,0 +1,13 @@
> > +QA output created by 1215
> > +* Exchange extent forks
> > +Format and mount fs
> > +Create $donorfile having an extent of length 67 blocks
> > +Fragment $donorfile
> > +Create $srcfile having an extent of length 18 blocks
> > +Fragment $srcfile
> > +Collect $donorfile's extent count
> > +Collect $srcfile's extent count
> > +Inject reduce_max_iextents error tag
> > +Exchange $srcfile's and $donorfile's extent forks
> > +Check for $donorfile's extent count overflow
> > +Check for $srcfile's extent count overflow
> > diff --git a/tests/xfs/789 b/tests/xfs/789
> > index 00b98020f2..e3a332d7cf 100755
> > --- a/tests/xfs/789
> > +++ b/tests/xfs/789
> > @@ -7,7 +7,7 @@
> > # Simple tests of the old xfs swapext ioctl
> >
> > . ./common/preamble
> > -_begin_fstest auto quick fiexchange swapext
> > +_begin_fstest auto quick swapext
> >
> > # Override the default cleanup function.
> > _cleanup()
> >
> >
>
>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCHBOMB] fstests: catch us up to 6.10
2024-06-21 17:20 ` [PATCHBOMB] fstests: catch us up to 6.10 Zorro Lang
@ 2024-06-21 17:53 ` Darrick J. Wong
0 siblings, 0 replies; 49+ messages in thread
From: Darrick J. Wong @ 2024-06-21 17:53 UTC (permalink / raw)
To: Zorro Lang; +Cc: Christoph Hellwig, fstests, linux-xfs
On Sat, Jun 22, 2024 at 01:20:34AM +0800, Zorro Lang wrote:
> On Thu, Jun 20, 2024 at 01:50:17PM -0700, Darrick J. Wong wrote:
> > Hi everyone,
> >
> > This patchbomb are all the fixes that xfs needs to bring fstests up to
> > date with what's in 6.10-rc. Except for these two patches:
> >
> > [PATCHSET v30.7 2/6] fstests: atomic file updates
> > [PATCH 03/11] generic/709,710: rework these for exchangerange vs.
> > [PATCH 04/11] generic/711,xfs/537: actually fork these tests for
> >
> > everything else in here is fully reviewed and ready for PRs.
>
> Thanks for big updates!
>
> This patchset is big, I've merged and pushed all these patches to
> fstests' 'patches-in-queue' branch, feel free to check that.
>
> I need more time to give them more tests, will try to release fstests
> at this weekend or middle of next week.
<nod> The patch "src/fiexchange.h: update XFS_IOC_EXCHANGE_RANGE
definitions" is going to need another update if Chandan pulls in[1]
before 6.10 closes:
[1] https://lore.kernel.org/linux-xfs/171892459317.3192151.14305994848485102437.stgit@frogsfrogsfrogs/
But I'll let that go upstream before I make the change to fstests.
--D
> Thanks,
> Zorro
>
> >
> > --D
> >
>
>
^ permalink raw reply [flat|nested] 49+ messages in thread
* Re: [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range
2024-06-21 17:49 ` Darrick J. Wong
@ 2024-06-23 12:30 ` Zorro Lang
0 siblings, 0 replies; 49+ messages in thread
From: Zorro Lang @ 2024-06-23 12:30 UTC (permalink / raw)
To: Darrick J. Wong; +Cc: fstests, linux-xfs
On Fri, Jun 21, 2024 at 10:49:48AM -0700, Darrick J. Wong wrote:
> On Sat, Jun 22, 2024 at 12:14:37AM +0800, Zorro Lang wrote:
> > On Thu, Jun 20, 2024 at 01:55:06PM -0700, Darrick J. Wong wrote:
> > > From: Darrick J. Wong <djwong@kernel.org>
> > >
> > > Fork these tests to check the same things with exchange-range as they do
> > > for swapext, since the code porting swapext to commit-range has been
> > > dropped.
> > >
> > > I was going to fork xfs/789 as well, but it turns out that generic/714
> > > covers this sufficiently so for that one, we just strike fiexchange from
> > > the group tag.
> > >
> > > Signed-off-by: Darrick J. Wong <djwong@kernel.org>
> > > ---
> > > tests/generic/1221 | 45 ++++++++++++++++++++++++
> > > tests/generic/1221.out | 2 +
> > > tests/generic/711 | 2 +
> > > tests/xfs/1215 | 89 ++++++++++++++++++++++++++++++++++++++++++++++++
> > > tests/xfs/1215.out | 13 +++++++
> > > tests/xfs/789 | 2 +
> >
> > Shouldn't the "xfs/537" (in subject) be xfs/789? I'll change that when
> > I merge it.
>
> No. generic/711 is forked to become generic/1221, and xfs/537 is forked
> to become xfs/1215. Maybe I should say that explicitly?
OK, I'll revert my change, and add this explanation. Thanks!
Thanks,
Zorro
>
> "Fork these tests to check the same things with exchange-range as they do
> for swapext, since the code porting swapext to commit-range has been
> dropped. generic/711 is forked to generic/1221, and xfs/537 is forked
> to xfs/1215.
>
> "I was going to fork xfs/789 as well, but it turns out that generic/714
> covers this sufficiently so for that one, we just strike fiexchange from
> the group tag."
>
> --D
>
> > Thanks,
> > Zorro
> >
> > > 6 files changed, 151 insertions(+), 2 deletions(-)
> > > create mode 100755 tests/generic/1221
> > > create mode 100644 tests/generic/1221.out
> > > create mode 100755 tests/xfs/1215
> > > create mode 100644 tests/xfs/1215.out
> > >
> > >
> > > diff --git a/tests/generic/1221 b/tests/generic/1221
> > > new file mode 100755
> > > index 0000000000..5569f59734
> > > --- /dev/null
> > > +++ b/tests/generic/1221
> > > @@ -0,0 +1,45 @@
> > > +#! /bin/bash
> > > +# SPDX-License-Identifier: GPL-2.0-or-later
> > > +# Copyright (c) 2022 Oracle. All Rights Reserved.
> > > +#
> > > +# FS QA Test No. 1221
> > > +#
> > > +# Make sure that exchangerange won't touch a swap file.
> > > +
> > > +. ./common/preamble
> > > +_begin_fstest auto quick fiexchange
> > > +
> > > +# Override the default cleanup function.
> > > +_cleanup()
> > > +{
> > > + cd /
> > > + test -e "$dir/a" && swapoff $dir/a
> > > + rm -r -f $tmp.* $dir
> > > +}
> > > +
> > > +# Import common functions.
> > > +. ./common/filter
> > > +
> > > +# real QA test starts here
> > > +_require_xfs_io_command exchangerange
> > > +_require_test
> > > +
> > > +dir=$TEST_DIR/test-$seq
> > > +mkdir -p $dir
> > > +
> > > +# Set up a fragmented swapfile and a dummy donor file.
> > > +$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
> > > +$here/src/punch-alternating $dir/a
> > > +$XFS_IO_PROG -f -c 'pwrite -S 0x58 0 32m -b 1m' -c fsync $dir/a >> $seqres.full
> > > +$MKSWAP_PROG $dir/a >> $seqres.full
> > > +
> > > +$XFS_IO_PROG -f -c 'pwrite -S 0x59 0 32m -b 1m' $dir/b >> $seqres.full
> > > +
> > > +swapon $dir/a || _notrun 'failed to swapon'
> > > +
> > > +# Now try to exchangerange.
> > > +$XFS_IO_PROG -c "exchangerange $dir/b" $dir/a
> > > +
> > > +# success, all done
> > > +status=0
> > > +exit
> > > diff --git a/tests/generic/1221.out b/tests/generic/1221.out
> > > new file mode 100644
> > > index 0000000000..698ac87303
> > > --- /dev/null
> > > +++ b/tests/generic/1221.out
> > > @@ -0,0 +1,2 @@
> > > +QA output created by 1221
> > > +exchangerange: Text file busy
> > > diff --git a/tests/generic/711 b/tests/generic/711
> > > index b107f976ef..792136306c 100755
> > > --- a/tests/generic/711
> > > +++ b/tests/generic/711
> > > @@ -7,7 +7,7 @@
> > > # Make sure that swapext won't touch a swap file.
> > >
> > > . ./common/preamble
> > > -_begin_fstest auto quick fiexchange swapext
> > > +_begin_fstest auto quick swapext
> > >
> > > # Override the default cleanup function.
> > > _cleanup()
> > > diff --git a/tests/xfs/1215 b/tests/xfs/1215
> > > new file mode 100755
> > > index 0000000000..5e7633c5ea
> > > --- /dev/null
> > > +++ b/tests/xfs/1215
> > > @@ -0,0 +1,89 @@
> > > +#! /bin/bash
> > > +# SPDX-License-Identifier: GPL-2.0
> > > +# Copyright (c) 2024 Oracle. All Rights Reserved.
> > > +#
> > > +# FS QA Test No. 1215
> > > +#
> > > +# Verify that XFS does not cause inode fork's extent count to overflow when
> > > +# exchanging ranges between files
> > > +. ./common/preamble
> > > +_begin_fstest auto quick collapse fiexchange
> > > +
> > > +# Import common functions.
> > > +. ./common/filter
> > > +. ./common/inject
> > > +
> > > +# real QA test starts here
> > > +
> > > +_supported_fs xfs
> > > +_require_scratch
> > > +_require_xfs_debug
> > > +_require_xfs_scratch_rmapbt
> > > +_require_xfs_io_command "fcollapse"
> > > +_require_xfs_io_command "exchangerange"
> > > +_require_xfs_io_error_injection "reduce_max_iextents"
> > > +
> > > +echo "* Exchange extent forks"
> > > +
> > > +echo "Format and mount fs"
> > > +_scratch_mkfs >> $seqres.full
> > > +_scratch_mount >> $seqres.full
> > > +
> > > +bsize=$(_get_file_block_size $SCRATCH_MNT)
> > > +
> > > +srcfile=${SCRATCH_MNT}/srcfile
> > > +donorfile=${SCRATCH_MNT}/donorfile
> > > +
> > > +echo "Create \$donorfile having an extent of length 67 blocks"
> > > +$XFS_IO_PROG -f -s -c "pwrite -b $((17 * bsize)) 0 $((17 * bsize))" $donorfile \
> > > + >> $seqres.full
> > > +
> > > +# After the for loop the donor file will have the following extent layout
> > > +# | 0-4 | 5 | 6 | 7 | 8 | 9 | 10 |
> > > +echo "Fragment \$donorfile"
> > > +for i in $(seq 5 10); do
> > > + start_offset=$((i * bsize))
> > > + $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $donorfile >> $seqres.full
> > > +done
> > > +
> > > +echo "Create \$srcfile having an extent of length 18 blocks"
> > > +$XFS_IO_PROG -f -s -c "pwrite -b $((18 * bsize)) 0 $((18 * bsize))" $srcfile \
> > > + >> $seqres.full
> > > +
> > > +echo "Fragment \$srcfile"
> > > +# After the for loop the src file will have the following extent layout
> > > +# | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7-10 |
> > > +for i in $(seq 1 7); do
> > > + start_offset=$((i * bsize))
> > > + $XFS_IO_PROG -f -c "fcollapse $start_offset $bsize" $srcfile >> $seqres.full
> > > +done
> > > +
> > > +echo "Collect \$donorfile's extent count"
> > > +donor_nr_exts=$(_xfs_get_fsxattr nextents $donorfile)
> > > +
> > > +echo "Collect \$srcfile's extent count"
> > > +src_nr_exts=$(_xfs_get_fsxattr nextents $srcfile)
> > > +
> > > +echo "Inject reduce_max_iextents error tag"
> > > +_scratch_inject_error reduce_max_iextents 1
> > > +
> > > +echo "Exchange \$srcfile's and \$donorfile's extent forks"
> > > +$XFS_IO_PROG -f -c "exchangerange $donorfile" $srcfile >> $seqres.full 2>&1
> > > +
> > > +echo "Check for \$donorfile's extent count overflow"
> > > +nextents=$(_xfs_get_fsxattr nextents $donorfile)
> > > +
> > > +if (( $nextents == $src_nr_exts )); then
> > > + echo "\$donorfile: Extent count overflow check failed"
> > > +fi
> > > +
> > > +echo "Check for \$srcfile's extent count overflow"
> > > +nextents=$(_xfs_get_fsxattr nextents $srcfile)
> > > +
> > > +if (( $nextents == $donor_nr_exts )); then
> > > + echo "\$srcfile: Extent count overflow check failed"
> > > +fi
> > > +
> > > +# success, all done
> > > +status=0
> > > +exit
> > > diff --git a/tests/xfs/1215.out b/tests/xfs/1215.out
> > > new file mode 100644
> > > index 0000000000..48edd56376
> > > --- /dev/null
> > > +++ b/tests/xfs/1215.out
> > > @@ -0,0 +1,13 @@
> > > +QA output created by 1215
> > > +* Exchange extent forks
> > > +Format and mount fs
> > > +Create $donorfile having an extent of length 67 blocks
> > > +Fragment $donorfile
> > > +Create $srcfile having an extent of length 18 blocks
> > > +Fragment $srcfile
> > > +Collect $donorfile's extent count
> > > +Collect $srcfile's extent count
> > > +Inject reduce_max_iextents error tag
> > > +Exchange $srcfile's and $donorfile's extent forks
> > > +Check for $donorfile's extent count overflow
> > > +Check for $srcfile's extent count overflow
> > > diff --git a/tests/xfs/789 b/tests/xfs/789
> > > index 00b98020f2..e3a332d7cf 100755
> > > --- a/tests/xfs/789
> > > +++ b/tests/xfs/789
> > > @@ -7,7 +7,7 @@
> > > # Simple tests of the old xfs swapext ioctl
> > >
> > > . ./common/preamble
> > > -_begin_fstest auto quick fiexchange swapext
> > > +_begin_fstest auto quick swapext
> > >
> > > # Override the default cleanup function.
> > > _cleanup()
> > >
> > >
> >
> >
>
^ permalink raw reply [flat|nested] 49+ messages in thread
end of thread, other threads:[~2024-06-23 12:30 UTC | newest]
Thread overview: 49+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2024-06-20 20:50 [PATCHBOMB] fstests: catch us up to 6.10 Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET 1/6] xfsprogs: scale shards on ssds Darrick J. Wong
2024-06-20 20:54 ` [PATCH 1/1] xfs: test scaling of the mkfs concurrency options Darrick J. Wong
2024-06-20 20:52 ` [PATCHSET v30.7 2/6] fstests: atomic file updates Darrick J. Wong
2024-06-20 20:54 ` [PATCH 01/11] misc: split swapext and exchangerange Darrick J. Wong
2024-06-20 20:54 ` [PATCH 02/11] misc: change xfs_io -c swapext to exchangerange Darrick J. Wong
2024-06-20 20:54 ` [PATCH 03/11] generic/709,710: rework these for exchangerange vs. quota testing Darrick J. Wong
2024-06-21 4:35 ` Christoph Hellwig
2024-06-20 20:55 ` [PATCH 04/11] generic/711,xfs/537: actually fork these tests for exchange-range Darrick J. Wong
2024-06-21 4:35 ` Christoph Hellwig
2024-06-21 16:14 ` Zorro Lang
2024-06-21 17:49 ` Darrick J. Wong
2024-06-23 12:30 ` Zorro Lang
2024-06-20 20:55 ` [PATCH 05/11] generic/717: remove obsolete check Darrick J. Wong
2024-06-20 20:55 ` [PATCH 06/11] ltp/{fsstress,fsx}: make the exchangerange naming consistent Darrick J. Wong
2024-06-20 20:55 ` [PATCH 07/11] misc: flip HAVE_XFS_IOC_EXCHANGE_RANGE logic Darrick J. Wong
2024-06-20 20:56 ` [PATCH 08/11] src/fiexchange.h: update XFS_IOC_EXCHANGE_RANGE definitions Darrick J. Wong
2024-06-20 20:56 ` [PATCH 09/11] xfs/122: fix for exchrange conversion Darrick J. Wong
2024-06-20 20:56 ` [PATCH 10/11] xfs/206: screen out exchange-range from golden output Darrick J. Wong
2024-06-20 20:56 ` [PATCH 11/11] exchangerange: make sure that we don't swap unwritten extents unless they're part of a rt extent Darrick J. Wong
2024-06-20 20:53 ` [PATCHSET v13.6 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2024-06-20 20:57 ` [PATCH 01/11] generic: test recovery of extended attribute updates Darrick J. Wong
2024-06-20 20:57 ` [PATCH 02/11] xfs/206: filter out the parent= status from mkfs Darrick J. Wong
2024-06-20 20:57 ` [PATCH 03/11] xfs/122: update for parent pointers Darrick J. Wong
2024-06-20 20:57 ` [PATCH 04/11] populate: create hardlinks " Darrick J. Wong
2024-06-20 20:58 ` [PATCH 05/11] xfs/021: adapt golden output files " Darrick J. Wong
2024-06-20 20:58 ` [PATCH 06/11] xfs/{018,191,288}: disable parent pointers for these tests Darrick J. Wong
2024-06-20 20:58 ` [PATCH 07/11] xfs/306: fix formatting failures with parent pointers Darrick J. Wong
2024-06-20 20:59 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
2024-06-21 4:36 ` Christoph Hellwig
2024-06-20 20:59 ` [PATCH 09/11] xfs: add parent pointer test Darrick J. Wong
2024-06-20 20:59 ` [PATCH 10/11] xfs: add multi link " Darrick J. Wong
2024-06-20 20:59 ` [PATCH 11/11] xfs: add parent pointer inject test Darrick J. Wong
2024-06-20 20:53 ` [PATCHSET v30.7 4/6] xfs: detect and correct directory tree structures Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/2] common/fuzzy: stress directory tree modifications with the dirtree tester Darrick J. Wong
2024-06-20 21:00 ` [PATCH 2/2] scrub: test correction of directory tree corruptions Darrick J. Wong
2024-06-20 20:53 ` [PATCHSET v30.7 5/6] xfs_scrub: vectorize kernel calls Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/1] xfs/122: update for vectored scrub Darrick J. Wong
2024-06-20 20:53 ` [PATCHSET 6/6] fstests: minor fixes for 6.10-rc1 Darrick J. Wong
2024-06-20 21:00 ` [PATCH 1/2] xfs/348: partially revert dbcc549317 ("xfs/348: golden output is not correct") Darrick J. Wong
2024-06-20 21:01 ` [PATCH 2/2] generic: test creating and removing symlink xattrs Darrick J. Wong
2024-06-21 17:20 ` [PATCHBOMB] fstests: catch us up to 6.10 Zorro Lang
2024-06-21 17:53 ` Darrick J. Wong
-- strict thread matches above, loose matches on Subject: below --
2024-06-18 0:46 [PATCHSET v13.5 3/6] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2024-06-18 0:51 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
2024-06-19 6:17 ` Christoph Hellwig
2024-06-19 17:28 ` Darrick J. Wong
2023-12-31 19:59 [PATCHSET v13.0 1/3] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2023-12-27 13:48 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
2023-05-26 2:00 [PATCHSET RFC v12.0 00/11] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2023-05-26 2:04 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
2023-04-06 19:16 [PATCHSET v11 00/11] fstests: adjust tests for xfs parent pointers Darrick J. Wong
2023-04-06 19:43 ` [PATCH 08/11] common: add helpers for parent pointer tests Darrick J. Wong
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox