2 # SPDX-License-Identifier: GPL-2.0
3 # Copyright 2018 Google LLC
5 # FS QA Test generic/572
7 # This is a basic fs-verity test which verifies:
9 # - conditions for enabling verity
10 # - verity files have correct contents and size
11 # - can't change contents of verity files, but can change metadata
12 # - can retrieve a verity file's measurement via FS_IOC_MEASURE_VERITY
15 seqres=$RESULT_DIR/$seq
16 echo "QA output created by $seq"
20 status=1 # failure is the default!
21 trap "_cleanup; exit \$status" 0 1 2 3 15
26 _restore_fsverity_signatures
30 # get standard environment, filters and checks
35 # remove previous $seqres.full before test
38 # real QA test starts here
40 _require_scratch_verity
41 _disable_fsverity_signatures
43 _scratch_mkfs_verity &>> $seqres.full
45 fsv_orig_file=$SCRATCH_MNT/file
46 fsv_file=$SCRATCH_MNT/file.fsv
48 verify_data_readable()
52 md5sum $file > /dev/null
55 verify_data_unreadable()
59 # try both reading just the first data block, and reading until EOF
60 head -c $FSV_BLOCK_SIZE $file 2>&1 >/dev/null | _filter_scratch
61 md5sum $file |& _filter_scratch
64 _fsv_scratch_begin_subtest "Enabling verity on file with verity already enabled fails with EEXIST"
65 _fsv_create_enable_file $fsv_file
67 _fsv_enable $fsv_file |& _filter_scratch
69 _fsv_scratch_begin_subtest "Enabling verity with invalid hash algorithm fails with EINVAL"
70 _fsv_create_enable_file $fsv_file --hash-alg=257 |& _filter_scratch
71 verify_data_readable $fsv_file
73 _fsv_scratch_begin_subtest "Enabling verity with invalid block size fails with EINVAL"
74 _fsv_create_enable_file $fsv_file --block-size=1 |& _filter_scratch
75 verify_data_readable $fsv_file
77 _fsv_scratch_begin_subtest "Enabling verity on directory fails with EISDIR"
78 mkdir $SCRATCH_MNT/dir
79 _fsv_enable $SCRATCH_MNT/dir |& _filter_scratch
81 _fsv_scratch_begin_subtest "Enabling verity with too-long salt fails with EMSGSIZE"
82 _fsv_create_enable_file $fsv_file --salt=$(perl -e 'print "A" x 1000') |& _filter_scratch
83 verify_data_readable $fsv_file
85 _fsv_scratch_begin_subtest "Enabling verity on file on read-only filesystem fails with EROFS"
88 _fsv_enable $fsv_file |& _filter_scratch
91 _fsv_scratch_begin_subtest "Enabling verity on file open for writing fails with ETXTBSY"
94 _fsv_enable $fsv_file |& _filter_scratch
96 verify_data_readable $fsv_file
98 _fsv_scratch_begin_subtest "Enabling verity can be interrupted"
99 dd if=/dev/zero of=$fsv_file bs=1 count=0 seek=$((1 << 34)) status=none
100 start_time=$(date +%s)
101 $FSVERITY_PROG enable $fsv_file &
105 elapsed=$(( $(date +%s) - start_time ))
106 if (( elapsed > 5 )); then
107 echo "Failed to interrupt FS_IOC_ENABLE_VERITY ($elapsed seconds elapsed)"
110 _fsv_scratch_begin_subtest "Enabling verity on file with verity already being enabled fails with EBUSY"
111 dd if=/dev/zero of=$fsv_file bs=1 count=0 seek=$((1 << 34)) status=none
112 start_time=$(date +%s)
113 $FSVERITY_PROG enable $fsv_file &
115 _fsv_enable $fsv_file |& _filter_scratch
119 _fsv_scratch_begin_subtest "verity file can't be opened for writing"
120 _fsv_create_enable_file $fsv_file >> $seqres.full
122 $XFS_IO_PROG -r $fsv_file -c ''
123 echo "* xfs_io writing, should be O_RDWR"
124 $XFS_IO_PROG $fsv_file -c '' |& _filter_scratch
125 echo "* bash >>, should be O_APPEND"
126 bash -c "echo >> $fsv_file" |& _filter_scratch
127 echo "* bash >, should be O_WRONLY|O_CREAT|O_TRUNC"
128 bash -c "echo > $fsv_file" |& _filter_scratch
130 _fsv_scratch_begin_subtest "verity file can be read"
131 _fsv_create_enable_file $fsv_file >> $seqres.full
132 verify_data_readable $fsv_file
134 _fsv_scratch_begin_subtest "verity file can be measured"
135 _fsv_create_enable_file $fsv_file >> $seqres.full
136 _fsv_measure $fsv_file
138 _fsv_scratch_begin_subtest "verity file can be renamed"
139 _fsv_create_enable_file $fsv_file
140 mv $fsv_file $fsv_file.newname
142 _fsv_scratch_begin_subtest "verity file can be unlinked"
143 _fsv_create_enable_file $fsv_file
146 _fsv_scratch_begin_subtest "verity file can be linked to"
147 _fsv_create_enable_file $fsv_file
148 ln $fsv_file $fsv_file.newname
150 _fsv_scratch_begin_subtest "verity file can be chmodded"
151 _fsv_create_enable_file $fsv_file
155 _fsv_scratch_begin_subtest "verity file can be chowned"
156 _fsv_create_enable_file $fsv_file
160 _fsv_scratch_begin_subtest "verity file has correct contents and size"
161 head -c 100000 /dev/urandom > $fsv_orig_file
162 cp $fsv_orig_file $fsv_file
163 _fsv_enable $fsv_file >> $seqres.full
164 cmp $fsv_file $fsv_orig_file
165 _get_filesize $fsv_file
167 cmp $fsv_file $fsv_orig_file
168 _get_filesize $fsv_file
170 _fsv_scratch_begin_subtest "Trying to measure non-verity file fails with ENODATA"
172 _fsv_measure $fsv_file |& _filter_scratch
173 verify_data_readable $fsv_file
175 # Test files <= 1 block in size. These are a bit of a special case since there
176 # are no hash blocks; the root hash is calculated directly over the data block.
177 for size in 1 $((FSV_BLOCK_SIZE - 1)) $FSV_BLOCK_SIZE; do
178 _fsv_scratch_begin_subtest "verity on $size-byte file"
179 head -c $size /dev/urandom > $fsv_orig_file
180 cp $fsv_orig_file $fsv_file
181 _fsv_enable $fsv_file
182 cmp $fsv_orig_file $fsv_file && echo "Files matched"
186 _fsv_scratch_begin_subtest "verity on 100M file (multiple levels in hash tree)"
187 head -c 100000000 /dev/urandom > $fsv_orig_file
188 cp $fsv_orig_file $fsv_file
189 _fsv_enable $fsv_file
190 cmp $fsv_orig_file $fsv_file && echo "Files matched"
192 _fsv_scratch_begin_subtest "verity on sparse file"
193 dd if=/dev/zero of=$fsv_orig_file bs=1 count=1 seek=1000000 status=none
194 cp $fsv_orig_file $fsv_file
195 _fsv_enable $fsv_file
196 cmp $fsv_orig_file $fsv_file && echo "Files matched"