#! /bin/bash
# SPDX-License-Identifier: GPL-2.0-or-later
# Copyright (c) 2022 Oracle.  All Rights Reserved.
#
# FS QA Test No. 791
#
# Test scatter-gather atomic file writes.  We create a temporary file, write
# 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.

. ./common/preamble
_begin_fstest auto quick fiexchange

# Override the default cleanup function.
_cleanup()
{
	cd /
	rm -r -f $tmp.* $dir
}

# Import common functions.
. ./common/filter
. ./common/inject

_require_xfs_io_command exchangerange
_require_xfs_scratch_atomicswap
_require_xfs_io_error_injection "bmap_finish_one"

_scratch_mkfs >> $seqres.full
_scratch_mount
_require_congruent_file_oplen $SCRATCH_MNT 65536

# Create original file
_pwrite_byte 0x58 0 1m $SCRATCH_MNT/a >> $seqres.full

# Create the donor file
$XFS_IO_PROG -f -c 'truncate 1m' $SCRATCH_MNT/b
_pwrite_byte 0x59 64k 64k $SCRATCH_MNT/b >> $seqres.full
_pwrite_byte 0x57 768k 64k $SCRATCH_MNT/b >> $seqres.full
_scratch_sync

md5sum $SCRATCH_MNT/a | _filter_scratch
md5sum $SCRATCH_MNT/b | _filter_scratch

# 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 -w $SCRATCH_MNT/b" $SCRATCH_MNT/a
_scratch_cycle_mount

md5sum $SCRATCH_MNT/a | _filter_scratch
md5sum $SCRATCH_MNT/b | _filter_scratch

# success, all done
status=0
exit
