2 # SPDX-License-Identifier: GPL-2.0
3 # Copyright (C) 2015 SUSE Linux Products GmbH. All Rights Reserved.
7 # Test file A fsync after moving one other unrelated file B between directories
8 # and fsyncing B's old parent directory before fsyncing the file A. Check that
9 # after a crash all the file A data we fsynced is available.
11 # This test is motivated by an issue discovered in btrfs which caused the file
12 # data to be lost (despite fsync returning success to user space). That btrfs
13 # bug was fixed by the following linux kernel patch:
15 # Btrfs: fix data loss in the fast fsync path
18 seqres=$RESULT_DIR/$seq
19 echo "QA output created by $seq"
23 status=1 # failure is the default!
30 trap "_cleanup; exit \$status" 0 1 2 3 15
32 # get standard environment, filters and checks
37 # real QA test starts here
40 _require_dm_target flakey
44 _scratch_mkfs >> $seqres.full 2>&1
45 _require_metadata_journaling $SCRATCH_DEV
49 # Create our main test file 'foo', the one we check for data loss.
50 # By doing an fsync against our file, it makes btrfs clear the 'needs_full_sync'
51 # bit from its flags (btrfs inode specific flags).
52 $XFS_IO_PROG -f -c "pwrite -S 0xaa 0 8K" \
53 -c "fsync" $SCRATCH_MNT/foo | _filter_xfs_io
55 # Now create one other file and 2 directories. We will move this second file
56 # from one directory to the other later because it forces btrfs to commit its
57 # currently open transaction if we fsync the old parent directory. This is
58 # necessary to trigger the data loss bug that affected btrfs.
59 mkdir $SCRATCH_MNT/testdir_1
60 touch $SCRATCH_MNT/testdir_1/bar
61 mkdir $SCRATCH_MNT/testdir_2
63 # Make sure everything is durably persisted.
66 # Write more 8Kb of data to our file.
67 $XFS_IO_PROG -c "pwrite -S 0xbb 8K 8K" $SCRATCH_MNT/foo | _filter_xfs_io
69 # Move our 'bar' file into a new directory.
70 mv $SCRATCH_MNT/testdir_1/bar $SCRATCH_MNT/testdir_2/bar
72 # Fsync our first directory. Because it had a file moved into some other
73 # directory, this made btrfs commit the currently open transaction. This is
74 # a condition necessary to trigger the data loss bug.
75 $XFS_IO_PROG -c "fsync" $SCRATCH_MNT/testdir_1
77 # Now fsync our main test file. If the fsync succeeds, we expect the 8Kb of
78 # data we wrote previously to be persisted and available if a crash happens.
79 # This did not happen with btrfs, because of the transaction commit that
80 # happened when we fsynced the parent directory.
81 $XFS_IO_PROG -c "fsync" $SCRATCH_MNT/foo
83 _flakey_drop_and_remount
85 # Now check that all data we wrote before are available.
86 echo "File content after log replay:"
87 od -t x1 $SCRATCH_MNT/foo