]> wimlib.net Git - wimlib/blob - tests/test-imagex
v1.14.4
[wimlib] / tests / test-imagex
1 #!/usr/bin/env bash
2
3 # This script does some sanity testing of the 'wimlib-imagex' program.  It by no
4 # means tests every aspect of wimlib comprehensively.
5
6 set -e
7 cd tests
8 srcdir="${srcdir:-.}/.."
9 srcdir="$(cd $srcdir; pwd)"
10 . "$srcdir/tests/test_utils.sh"
11
12 TEST_SUBDIR=tmpdir_test-imagex
13
14 # Execute the tests in a subdirectory to avoid conflicts with concurrent tests
15 default_cleanup
16 mkdir $TEST_SUBDIR
17 cd $TEST_SUBDIR
18
19 # Make test directory
20 mkdir dir
21 cp $srcdir/src/*.c dir
22 mkdir dir/subdir
23 echo 'hello' > dir/subdir/hello
24 echo 'hello' > dir/subdir/hello2
25 ln dir/subdir/hello dir/subdir/hellolink
26 echo -n > dir/subdir/empty_file
27 ln -s hello dir/subdir/rel_symlink
28
29 mkdir dir2
30 echo 'testing' > dir2/file
31 dd if=/dev/zero of=dir2/zeroes bs=4096 count=5
32
33 # Capturing and applying WIM with None, LZX, and XPRESS compression
34
35 for comp_type in None LZX XPRESS; do
36         echo "Testing capture and application of $comp_type-compressed WIM"
37         if ! wimcapture dir dir.wim --compress=$comp_type; then
38                 error "'wimcapture' failed"
39         fi
40         if ! wimapply dir.wim tmp; then
41                 error "'wimapply' failed"
42         fi
43         if ! test `wim_ctype dir.wim` = "$comp_type"; then
44                 error "'wiminfo' didn't report the compression type correctly"
45         fi
46         if ! diff -q -r dir tmp; then
47                 error "Recursive diff of extracted directory with original failed"
48         fi
49         if ! test `get_link_count tmp/subdir/hello` = 2; then
50                 error "Incorrect number of hard links in extracted file"
51         fi
52         if ! test `get_inode_number tmp/subdir/hello` != `get_inode_number tmp/subdir/hello2`; then
53                 error "Expected different inode numbers in files not hard-linked"
54         fi
55         if ! test "`get_inode_number tmp/subdir/hello`" = "`get_inode_number tmp/subdir/hellolink`"; then
56                 error "Expected same inode numbers in hard-linked files"
57         fi
58         if ! test -L tmp/subdir/rel_symlink; then
59                 error "Symlink not extracted correctly"
60         fi
61         if ! test "`readlink tmp/subdir/rel_symlink`" = "hello"; then
62                 error "Symlink target not correct"
63         fi
64
65         rm -rf dir.wim tmp
66 done
67
68 # Test wimverify and the SHA-1 code
69 WIMLIB_DISABLE_CPU_FEATURES='*' wimcapture dir dir.wim --compress=none
70 disabled=''
71 for cpu_feature in '' sha1 bmi2 avx sse4.2 sse4.1 ssse3; do
72         [ -n "$disabled" ] && disabled+=','
73         disabled+="$cpu_feature"
74         if ! WIMLIB_DISABLE_CPU_FEATURES=$disabled wimverify dir.wim; then
75                 error "wimverify failed (cpu_features_disabled=$disabled)"
76         fi
77 done
78
79 # Test wimappend --create
80 rm -f dir.wim
81 if wimappend dir dir.wim; then
82         error "wimappend to nonexisting file unexpectedly succeeded"
83 fi
84 if ! wimappend dir dir.wim --create; then
85         error "wimappend --create to nonexisting file failed"
86 fi
87 if ! wimappend dir dir.wim --create; then
88         error "wimappend --create to existing file failed"
89 fi
90 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 2; then
91         error "Incorrect WIM image count after wimappend --create"
92 fi
93
94 # Capturing and modifying name, description, and bootable flag
95
96 echo "Testing capture of WIM with default name and description"
97 wimcapture dir dir.wim
98 if ! test "`wiminfo dir.wim | grep Name | awk '{print $2}'`" = "dir"; then
99         error "WIM name not set correctly"
100 fi
101 if ! test "`wiminfo dir.wim | grep Description | awk '{print $2}'`" = ""; then
102         error "WIM description not set correctly"
103 fi
104
105 echo "Testing capture of WIM with default boot flag"
106 wimcapture dir dir.wim
107 if ! test "`wiminfo dir.wim | grep '^Boot Index' | awk '{print $3}'`" = "0"; then
108         error "WIM boot flag not set correctly"
109 fi
110
111 echo "Testing changing image bootable flag"
112 if ! wiminfo dir.wim 1 --boot; then
113         error "Failed to change bootable image"
114 fi
115 if ! test "`wiminfo dir.wim | grep '^Boot Index' | awk '{print $3}'`" = "1"; then
116         error "Bootable image not changed correctly"
117 fi
118 echo "Testing changing image bootable flag"
119 if ! wiminfo dir.wim 0 --boot; then
120         error "Failed to reset bootable image"
121 fi
122 if ! test "`wiminfo dir.wim | grep '^Boot Index' | awk '{print $3}'`" = "0"; then
123         error "Bootable image not reset correctly"
124 fi
125 echo "Testing changing image bootable flag to invalid image (this should generate errors)"
126 if wiminfo dir.wim 2 --boot; then
127         error "Succeeded in changing bootable image to invalid number"
128 fi
129 if ! test "`wiminfo dir.wim | grep '^Boot Index' | awk '{print $3}'`" = "0"; then
130         error "Boot flag was changed even though the change command was supposed to fail"
131 fi
132 rm -rf dir.wim tmp
133
134 name_desc_test() {
135         local name=$1
136         local desc=$2
137         if ! wimcapture dir dir.wim "$name" "$desc"; then
138                 error "Failed to capture WIM with specified name and description"
139         fi
140         if ! test "`wiminfo dir.wim | grep Name | awk '{print $2}'`" = "$name"; then
141                 error "WIM name not set correctly"
142         fi
143         if ! test "`wiminfo dir.wim | grep Description | awk '{print $2}'`" = "$desc"; then
144                 error "WIM description not set correctly"
145         fi
146 }
147
148 echo "Testing capture of WIM with name and description"
149 name_desc_test "myname" "mydesc"
150
151 echo "Testing capture of WIM with non-ASCII name and description"
152 name_desc_test "áéíóú" "¿?"
153
154 echo "Testing printing WIM lookup table"
155 if ! wiminfo --lookup-table dir.wim > /dev/null; then
156         error "Failed to print WIM lookup table"
157 fi
158 echo "Testing printing WIM header"
159 if ! wiminfo --header dir.wim > /dev/null; then
160         error "Failed to print WIM header"
161 fi
162 echo "Testing printing WIM XML info"
163 if ! wiminfo --xml dir.wim > /dev/null; then
164         error "Failed to print WIM XML data"
165 fi
166 echo "Testing extracting WIM XML info"
167 if ! wiminfo --extract-xml=dir.xml dir.wim; then
168         error "Failed to extract WIM XML data"
169 fi
170 echo "Testing printing WIM metadata"
171 if ! wimdir --detailed dir.wim > /dev/null; then
172         error "Failed to print WIM metadata"
173 fi
174 rm -rf dir.wim tmp dir.xml
175
176 echo "Testing capture of bootable WIM"
177 if ! wimcapture dir dir.wim --boot; then
178         error "Failed to capture bootable WIM"
179 fi
180 if ! test "`wiminfo dir.wim | grep '^Boot Index' | awk '{print $3}'`" = "1"; then
181         error "Boot flag on bootable WIM not set correctly"
182 fi
183 rm -rf dir.wim tmp
184
185 # Integrity table
186
187 echo "Testing capture of WIM with integrity table"
188 if ! wimcapture dir dir.wim --check; then
189         error "Failed to capture WIM with integrity table"
190 fi
191 if ! wiminfo dir.wim | grep -q Integrity; then
192         error "Integrity table on WIM not made"
193 fi
194 if ! wimapply --check dir.wim tmp; then
195         error "Integrity table on WIM not made correctly"
196 fi
197 if ! diff -q -r dir tmp; then
198         error "Recursive diff of applied WIM with original directory failed"
199 fi
200 rm -rf dir.wim tmp
201
202 # Appending and deleting images
203
204 echo "Testing appending WIM image"
205 wimcapture dir dir.wim
206 if ! wimappend dir2 dir.wim; then
207         error "Appending WIM image failed"
208 fi
209 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 2; then
210         error "WIM image count not correct"
211 fi
212
213 echo "Testing appending WIM image with existing name (this should generate errors)"
214 if wimappend dir2 dir.wim "dir"; then
215         error "Adding duplicate image name didn't fail"
216 fi
217 echo "Testing appending WIM image with new name"
218 if ! wimappend dir2 dir.wim "newname"; then
219         error "Appending WIM image failed"
220 fi
221 echo "Testing appending WIM image with integrity check"
222 if ! wimappend dir2 dir.wim "newname2" --check; then
223         error "Appending WIM image failed"
224 fi
225 if ! wiminfo dir.wim | grep -q Integrity; then
226         error "Integrity table not set correctly on image append"
227 fi
228 echo "Testing appending WIM image with no integrity check"
229 if ! wimappend dir2 dir.wim "newname3" --nocheck; then
230         error "Appending WIM image failed"
231 fi
232 if wiminfo dir.wim | grep -q Integrity; then
233         error "WIM integrity table not removed"
234 fi
235 # 5 images at this point
236 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 5; then
237         error "WIM does not contain the expected 5 images"
238 fi
239 echo "Testing deleting first WIM image"
240 if ! wimdelete dir.wim 1; then
241         error "Failed to delete WIM image"
242 fi
243 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 4; then
244         error "WIM image not deleted correctly"
245 fi
246 echo "Testing deleting last WIM image"
247 if ! wimdelete dir.wim 4; then
248         error "Failed to delete WIM image"
249 fi
250 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 3; then
251         error "WIM image not deleted correctly"
252 fi
253 echo "Testing deleting invalid WIM image (this should generate errors)"
254 if wimdelete dir.wim 4; then
255         error "Expected to fail to delete non-existent WIM image"
256 fi
257 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 3; then
258         error "Image count changed even though we intentionally failed to delete an image"
259 fi
260 echo "Testing deleting all WIM images"
261 if ! wimdelete dir.wim all; then
262         error "Failed to delete all images from WIM"
263 fi
264 if ! test "`wiminfo dir.wim | grep 'Image Count' | awk '{print $3}'`" = 0; then
265         error "Couldn't delete all WIM images correctly"
266 fi
267 echo "Testing appending directory to empty WIM and making it bootable"
268 if ! wimappend dir dir.wim "myname" "mydesc" --check --boot; then
269         error "Couldn't append named, described, bootable image to empty WIM with integrity check"
270 fi
271 if ! wiminfo dir.wim | grep -q Integrity; then
272         error "Integrity check not found"
273 fi
274 if ! test "`wiminfo dir.wim | grep '^Boot Index' | awk '{print $3}'`" = "1"; then
275         error "Bootable image not set correctly"
276 fi
277 echo "Testing appending non-directory (should generate errors)"
278 if wimappend dir.wim dir.wim; then
279         error "Incorrectly succeeded to append non-directory to WIM"
280 fi
281 echo "Testing appending non-existent file (should generate errors)"
282 if wimappend SOME_NONEXISTENT_FILE dir.wim; then
283         error "Incorrectly succeeded to append non-existent file to WIM"
284 fi
285 if [ `id -u` != 0 ]; then
286         echo "Testing appending directory containing unreadable file (should generate errors)"
287         mkdir -p dir3
288         echo 1 > dir3/file
289         chmod -r dir3/file
290         if wimappend dir3 dir.wim; then
291                 error "Incorrectly succeeded in capturing directory with unreadable file"
292         fi
293 fi
294 rm -rf dir3 dir.wim
295
296 # Applying multiple images, applying with hardlinks/symlinks
297
298 echo "Testing application of multiple images"
299 if ! wimcapture dir dir.wim; then
300         error "Failed to prepare test WIM"
301 fi
302 if ! wimappend dir dir.wim "myname"; then
303         error "Failed to append image to test WIM"
304 fi
305 if ! wimapply dir.wim all tmp; then
306         error "Applying multiple images failed"
307 fi
308 if ! diff -q -r tmp/dir tmp/myname || ! diff -q -r dir tmp/dir; then
309         error "Recursive diff of applied WIM with original directory failed"
310 fi
311 if test "`get_link_count tmp/dir/write.c`" != 1; then
312         error "Incorrect link count on extracted file"
313 fi
314 if test "`get_link_count tmp/myname/write.c`" != 1; then
315         error "Incorrect link count on extracted file"
316 fi
317 if test "`get_inode_number tmp/myname/write.c`" = "`get_inode_number tmp/dir/write.c`"; then
318         error "Incorrect inode number"
319 fi
320 rm -rf tmp
321
322 echo "Testing application of single image containing identical files"
323 if ! wimapply dir.wim 1 tmp; then
324         error "Failed to apply WIM"
325 fi
326 if test "`get_link_count tmp/subdir/hello`" != 2; then
327         error "Incorrect link count on extracted file"
328 fi
329 if test "`get_link_count tmp/subdir/hello2`" != 1; then
330         error "Incorrect link count on extracted file"
331 fi
332 if test "`get_inode_number tmp/subdir/hello`" = "`get_inode_number tmp/subdir/hello2`"; then
333         error "Inode numbers on non-hard-linked files are the same"
334 fi
335 if test "`get_inode_number tmp/subdir/hello`" != "`get_inode_number tmp/subdir/hellolink`"; then
336         error "Inode numbers on hard-linked files are different"
337 fi
338 rm -rf tmp
339
340 # wimsplit, wimjoin
341
342 echo "Creating random files to test WIM splitting on"
343 mkdir tmp
344 for ((i = 0; i < 100; i++)); do
345         dd if=/dev/urandom of=tmp/file$i bs=4096 count=10 &> /dev/null
346 done
347 for flag in "--compress=none" "--compress=maximum" "--compress=fast"; do
348         echo "Using flag $flag"
349         if ! wimcapture tmp tmp.wim $flag; then
350                 error "Failed to capture test WIM"
351         fi
352         echo "Splitting WIM into 1 MiB chunks"
353         if ! wimsplit tmp.wim tmp.swm 1; then
354                 error "Failed to split WIM"
355         fi
356         echo "Verifying the split WIMs (some errors expected)"
357         if test "`wiminfo tmp.swm | grep 'Part Number' | awk '{print $3}'`" != "1/4"; then
358                 error "Part number of split WIM not correct"
359         fi
360         if ! wimdir tmp.swm > /dev/null; then
361                 error "Failed to list files in split WIM"
362         fi
363         if ! test -e tmp2.swm; then
364                 error "Could not find split-WIM part 2"
365         fi
366         if wimdir tmp2.swm > /dev/null; then
367                 error "Listed files in part 2 of split WIM (this should have failed)"
368         fi
369
370         # Unsupported, should fail
371         if wiminfo tmp.swm --boot 1; then
372                 error "Should not have been able to change boot index of split WIM"
373         fi
374         echo "Joining the split WIMs and applying the result"
375         if ! wimjoin tmp2.wim tmp*.wim; then
376                 error "Failed to join split WIMs"
377         fi
378         if ! wimapply tmp2.wim tmp2; then
379                 error "Failed to apply joined split WIM"
380         fi
381         if ! wimapply tmp.wim tmp3; then
382                 error "Failed to apply test WIM"
383         fi
384         if ! diff -q -r tmp tmp2 || ! diff -q -r tmp tmp3; then
385                 error "Recursive diff of applied joined split WIM with original directory failed"
386         fi
387         rm -f *.wim *.swm
388         rm -rf tmp2 tmp3
389 done
390 rm -rf tmp
391
392 # wimexport
393 echo "Testing export of single image to new WIM"
394 if ! wimcapture dir dir.wim; then
395         error "Failed to capture test WIM"
396 fi
397 if ! wimappend dir2 dir.wim; then
398         error "Failed to append image to test WIM"
399 fi
400 if ! wimexport dir.wim dir new.wim; then
401         error "Failed to export single image to new WIM"
402 fi
403 if test "`wiminfo new.wim | grep 'Image Count' | awk '{print $3}'`" != 1; then
404         error "Exporting single image to new WIM wasn't done correctly"
405 fi
406 echo "Testing export of single image to existing WIM"
407 if ! wimexport dir.wim dir2 new.wim; then
408         error "Failed to export single image to existing WIM"
409 fi
410 if test "`wiminfo new.wim | grep 'Image Count' | awk '{print $3}'`" != 2; then
411         error "Exporting single image to existing WIM wasn't done correctly"
412 fi
413 echo "Testing export of single image to existing WIM using wrong compression type"
414 if wimexport dir.wim dir2 new.wim newname --compress=xpress; then
415         error "Successfully exported image using wrong compression type"
416 fi
417 rm -f new.wim
418 echo "Testing export of multiple images to new WIM"
419 if ! wimexport dir.wim all new.wim; then
420         error "Failed to export multiple images to new WIM"
421 fi
422 if test "`wiminfo new.wim | grep 'Image Count' | awk '{print $3}'`" != 2; then
423         error "Exporting multiple images to new WIM wasn't done correctly"
424 fi
425 if ! wimcapture dir2 new.wim newname; then
426         error "Failed to capture test WIM"
427 fi
428 echo "Testing export of multiple images to existing WIM"
429 if ! wimexport dir.wim all new.wim; then
430         error "Failed to export multiple images to existing WIM"
431 fi
432 echo "Testing export of multiple images to existing WIM with --boot"
433 if ! wimcapture dir2 new.wim newname; then
434         error "Failed to capture test WIM"
435 fi
436 if ! wiminfo dir.wim --boot 1; then
437         error "Failed to set boot index on test WIM"
438 fi
439 if ! wimexport dir.wim all new.wim --boot; then
440         error "Failed to export multiple images to existing WIM with bootable image"
441 fi
442 echo "Testing export of multiple images to existing WIM with --boot, but no bootable image (errors expected)"
443 if ! wimcapture dir2 new.wim newname; then
444         error "Failed to capture test WIM"
445 fi
446 if ! wiminfo dir.wim --boot 0; then
447         error "Failed to clear boot index on test WIM"
448 fi
449 if wimexport dir.wim all new.wim --boot; then
450         error "Successfully exported multiple images with --boot but with no bootable images"
451 fi
452
453 # Test exporting an image to another WIM, then applying it.
454 # We try with 5 different combinations of compression types to make sure we go
455 # through all paths in the resource-handling code.
456 for i in 1 2 3 4 5; do
457         case $i in
458         1)
459                 cflag1="--compress=none";
460                 cflag2="--compress=none";
461                 ;;
462         2)
463                 cflag1="--compress=xpress";
464                 cflag2="--compress=xpress";
465                 ;;
466         3)
467                 cflag1="--compress=xpress"
468                 cflag2="--compress=lzx"
469                 ;;
470         4)
471                 cflag1="--compress=none"
472                 cflag2="--compress=xpress"
473                 ;;
474         5)
475                 cflag1="--compress=xpress"
476                 cflag2="--compress=none"
477                 ;;
478         esac
479         echo "Testing exporting then applying an image (\"$cflag1\" => \"$cflag2\")"
480         rm -rf dir.wim new.wim tmp tmp2
481         wimcapture dir dir.wim $cflag1
482         wimcapture dir2 dir2.wim $cflag2
483         wimexport dir.wim dir dir2.wim
484         wimapply dir.wim dir tmp
485         if ! wimapply dir2.wim dir tmp2; then
486                 error "Failed to apply image that was exported to a WIM"
487         fi
488         if ! diff -r tmp tmp2; then
489                 error "Image that was exported to a WIM was not applied correctly"
490         fi
491 done
492
493 echo "**********************************************************"
494 echo "             Basic wimlib-imagex tests passed             "
495 echo "**********************************************************"
496
497 # Leave test subdirectory and cleanup
498 cd ..
499 default_cleanup