#! /bin/bash # SPDX-License-Identifier: GPL-2.0 # Copyright (c) 2022 BingJing Chang. # # FS QA Test No. btrfs/272 # # Regression test for btrfs incremental send issue where a link instruction # is sent against an existing path, causing btrfs receive to fail. # # This issue is fixed by the following linux kernel btrfs patch: # # commit 3aa5bd367fa5a3 ("btrfs: send: fix sending link commands for # existing file paths") # . ./common/preamble _begin_fstest auto quick send _supported_fs btrfs _fixed_by_kernel_commit 3aa5bd367fa5a3 \ "btrfs: send: fix sending link commands for existing file paths" _require_test _require_scratch _require_fssum send_files_dir=$TEST_DIR/btrfs-test-$seq rm -fr $send_files_dir mkdir $send_files_dir _scratch_mkfs >>$seqres.full 2>&1 _scratch_mount # Create a file and 2000 hard links to the same inode _btrfs subvolume create $SCRATCH_MNT/vol touch $SCRATCH_MNT/vol/foo for i in {1..2000}; do link $SCRATCH_MNT/vol/foo $SCRATCH_MNT/vol/$i done # Create a snapshot for a full send operation _btrfs subvolume snapshot -r $SCRATCH_MNT/vol $SCRATCH_MNT/snap1 _btrfs send -f $send_files_dir/1.snap $SCRATCH_MNT/snap1 # Remove 2000 hard links and re-create the last 1000 links for i in {1..2000}; do rm $SCRATCH_MNT/vol/$i done for i in {1001..2000}; do link $SCRATCH_MNT/vol/foo $SCRATCH_MNT/vol/$i done # Create another snapshot for an incremental send operation _btrfs subvolume snapshot -r $SCRATCH_MNT/vol $SCRATCH_MNT/snap2 _btrfs send -p $SCRATCH_MNT/snap1 -f $send_files_dir/2.snap \ $SCRATCH_MNT/snap2 $FSSUM_PROG -A -f -w $send_files_dir/1.fssum $SCRATCH_MNT/snap1 $FSSUM_PROG -A -f -w $send_files_dir/2.fssum \ -x $SCRATCH_MNT/snap2/snap1 $SCRATCH_MNT/snap2 # Recreate the filesystem by receiving both send streams and verify we get # the same content that the original filesystem had. _scratch_unmount _scratch_mkfs >>$seqres.full 2>&1 _scratch_mount # Add the first snapshot to the new filesystem by applying the first send # stream. _btrfs receive -f $send_files_dir/1.snap $SCRATCH_MNT # The incremental receive operation below used to fail with the following # error: # # ERROR: link 1238 -> foo failed: File exists # # This is because the path "1238" was stored as an extended ref item in the # original snapshot but as a normal ref item in the next snapshot. The send # operation cannot handle the duplicated paths, which are stored in # different ways, well, so it decides to issue a link operation for the # existing path. This results in the receiver to fail with the above error. _btrfs receive -f $send_files_dir/2.snap $SCRATCH_MNT $FSSUM_PROG -r $send_files_dir/1.fssum $SCRATCH_MNT/snap1 $FSSUM_PROG -r $send_files_dir/2.fssum $SCRATCH_MNT/snap2 status=0 exit