2 # FS QA Test No. xfs/010
4 # Test xfs_repair of the free inode btree (finobt). Make a couple targeted
5 # corruptions and verify that xfs_repair detects and repairs the filesystem to
8 #-----------------------------------------------------------------------
9 # Copyright (c) 2014 Red Hat, Inc. All Rights Reserved.
11 # This program is free software; you can redistribute it and/or
12 # modify it under the terms of the GNU General Public License as
13 # published by the Free Software Foundation.
15 # This program is distributed in the hope that it would be useful,
16 # but WITHOUT ANY WARRANTY; without even the implied warranty of
17 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 # GNU General Public License for more details.
20 # You should have received a copy of the GNU General Public License
21 # along with this program; if not, write the Free Software Foundation,
22 # Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
24 #-----------------------------------------------------------------------
28 seqres=$RESULT_DIR/$seq
29 echo "QA output created by $seq"
33 status=1 # failure is the default!
35 # get standard environment, filters and checks
43 _scratch_unmount 2>/dev/null
46 trap "_cleanup; exit \$status" 0 1 2 3 15
48 _sparse_inode_populate()
53 for i in $(seq 0 $count)
58 # Inode chunks are allocated 64 inodes at a time. If we remove 1 out of
59 # every 32 we allocated above, we'll end up leaving an inode or two free
60 # in each chunk. This ensures that most records are inserted into the
62 for i in $(seq 0 32 $count)
73 _corrupt_finobt_records()
77 # determine the root block of the finobt
78 free_root=`$XFS_DB_PROG -c "agi 0" -c "p free_root" $dev |
81 # Corrupt a freecount value. This should never exceed 64.
82 $XFS_DB_PROG -x -c "fsb $free_root" -c "type inobt" \
83 -c "write recs[1].freecount 70" $dev
85 # Create a corrupted non-free record, which should never appear in the
87 $XFS_DB_PROG -x -c "fsb $free_root" -c "type inobt" \
88 -c "write recs[2].freecount 0" $dev
89 $XFS_DB_PROG -x -c "fsb $free_root" -c "type inobt" \
90 -c "write recs[2].free 0" $dev
93 _corrupt_finobt_root()
97 # nuke the agi finobt root fields
100 -c "write -c free_root 0" \
101 -c "write -c free_level 0" \
102 $dev | grep -v "Allowing write of corrupted"
105 # real QA test starts here
110 _require_xfs_mkfs_finobt
115 _scratch_mkfs_xfs "-m crc=1,finobt=1 -d agcount=2" | _filter_mkfs 2>$seqres.full
117 # sparsely populate the fs such that we create records with free inodes
119 _sparse_inode_populate $SCRATCH_MNT 999
122 # corrupt some finobt records
123 _corrupt_finobt_records $SCRATCH_DEV
125 # repair should detect the inconsistencies
126 _scratch_xfs_repair 2>&1 | _filter_repair
129 # nuke the finobt root, repair will have to regenerate from the inobt
130 _corrupt_finobt_root $SCRATCH_DEV
132 _scratch_xfs_repair 2>&1 | _filter_repair