Whamcloud - gitweb
tests: fix problems in the m_rootgnutar test
[tools/e2fsprogs.git] / tests / m_rootgnutar / script
1 # vim: filetype=sh
2
3 use_mkgnutar=
4
5 test_description="create fs image from GNU tarball"
6 if ! test -x "$DEBUGFS_EXE"; then
7         echo "$test_name: $test_description: skipped (no debugfs)"
8         return 0
9 fi
10 if [ "$(grep -c 'define HAVE_ARCHIVE_H' ../lib/config.h)" -eq 0 ]; then
11         echo "$test_name: $test_description: skipped (no libarchive)"
12         exit 0
13 fi
14
15 if test -z "$use_mkgnutar" ; then
16     if type ztar > /dev/null 2>&1 && \
17             tar --version 2>&1 | head -1 | grep -q "GNU tar" ; then
18         TAR=tar
19     elif type gtar > /dev/null 2>&1 && \
20             gtar --version 2>&1 | head -1 | grep -q "GNU tar" ; then
21         TAR=gtar
22     else
23         # if GNU tar is not available, fall back to using mkgnutar.pl
24         use_mkgnutar=yes
25 #       echo "$test_name: $test_description: skipped (no GNU tar)"
26 #       exit 0
27     fi
28 fi
29
30 MKFS_TAR="$TMPFILE.tar"
31 MKFS_DIR="$TMPFILE.dir"
32 OUT="$test_name.log"
33 EXP="$test_dir/expect"
34 DEBUGFS_EXE_MTIME=$(perl -e 'print((stat ($ARGV[0]))[9])' "$DEBUGFS_EXE")
35
36 # we put everything in a subdir because we cannot rdump the root as that would
37 # require permissions to changing ownership of /lost+found
38 rm -rf "$MKFS_DIR"
39 mkdir -p "$MKFS_DIR/test"
40 touch "$MKFS_DIR/test/emptyfile"
41 dd if=/dev/zero bs=1024 count=32 2> /dev/null | tr '\0' 'a' > "$MKFS_DIR/test/bigfile"
42 dd if=/dev/zero of="$MKFS_DIR/test/zerofile" bs=1 count=1 seek=1024 2> /dev/null
43 ln -s /silly_bs_link "$MKFS_DIR/test/silly_bs_link"
44 mkdir "$MKFS_DIR/test/emptydir"
45 mkdir "$MKFS_DIR/test/dir"
46 echo "will be overwritten" > "$MKFS_DIR/test/dir/file"
47
48 if test -z "$use_mkgnutar"; then
49         # debugfs rdump does not preserve the timestamps when it extracts the
50         # files so we ignore them by using tar --clamp-mtime
51         # first write a partial tar
52     $TAR --sort=name -C "$MKFS_DIR" --mtime="$DEBUGFS_EXE" --clamp-mtime \
53          --format=gnu -cf "$MKFS_TAR.dupl" test
54         # now overwrite the contents of a file
55         echo "Test me" > "$MKFS_DIR/test/dir/file"
56         # and update the tar so that it contains two entries for the same file
57         # we need this to test the code path that first unlinks and then overwrites an
58         # existing file
59         $TAR -C "$MKFS_DIR" --mtime="$DEBUGFS_EXE" --clamp-mtime \
60              --format=gnu -rf "$MKFS_TAR.dupl" test/dir/file
61         # also add a duplicate directory entry because those must not be unlinked
62         echo test | $TAR -C "$MKFS_DIR" --mtime="$DEBUGFS_EXE" --clamp-mtime \
63                          --format=gnu -rf "$MKFS_TAR.dupl" --no-recursion \
64                          --verbatim-files-from --files-from=-
65         # also create a tarball of the directory with only one entry per file
66         $TAR --sort=name -C "$MKFS_DIR" --mtime="$DEBUGFS_EXE" --clamp-mtime \
67              --format=gnu -cf "$MKFS_TAR.uniq" test
68 else
69         # same as above but without using GNU tar
70         perl $test_dir/mkgnutar.pl --nopadding --directory="$MKFS_DIR" --mtime "$DEBUGFS_EXE_MTIME" test > "$MKFS_TAR.dupl"
71         echo "Test me" > "$MKFS_DIR/test/dir/file"
72         perl $test_dir/mkgnutar.pl --nopadding --directory="$MKFS_DIR" --mtime "$DEBUGFS_EXE_MTIME" test/dir/file >> "$MKFS_TAR.dupl"
73         perl $test_dir/mkgnutar.pl --nopadding --directory="$MKFS_DIR" --mtime "$DEBUGFS_EXE_MTIME" --no-recursion test/ >> "$MKFS_TAR.dupl"
74         # add end-of-archive entry
75         truncate -s +1024 "$MKFS_TAR.dupl"
76         # pad to a multiple of the record size
77         truncate -s %10240 "$MKFS_TAR.dupl"
78         perl $test_dir/mkgnutar.pl --directory="$MKFS_DIR" --mtime "$DEBUGFS_EXE_MTIME" test > "$MKFS_TAR.uniq"
79 fi
80
81 rm -r "$MKFS_DIR"
82
83 cat > "$TMPFILE.cmd1" << ENDL
84 stat /test/emptyfile
85 stat /test/bigfile
86 stat /test/zerofile
87 stat /test/silly_bs_link
88 stat /test/emptydir
89 stat /test/dir
90 stat /test/dir/file
91 ENDL
92
93 cat > "$TMPFILE.cmd2" << ENDL
94 ex /test/emptyfile
95 ex /test/bigfile
96 ex /test/zerofile
97 ex /test/silly_bs_link
98 ex /test/emptydir
99 ex /test/dir
100 ex /test/dir/file
101 ENDL
102
103 # Create two file systems, one for each tar that was created above. The
104 # tarballs differ but should result in the same filesystem contents
105 #
106 for ext in uniq dupl; do
107         mkdir "$MKFS_DIR"
108         {
109                 $MKE2FS -q -F -o Linux -T ext4 -O metadata_csum,64bit -E lazy_itable_init=1 -b 1024 -d "$MKFS_TAR.$ext" "$TMPFILE.$ext" 16384 2>&1;
110                 echo Exit status is $?;
111                 $DUMPE2FS "$TMPFILE.$ext" 2>&1;
112                 echo Exit status is $?;
113                 $DEBUGFS -f "$TMPFILE.cmd1" "$TMPFILE.$ext" 2>&1 | grep -E "(stat|Size:|Type:|Links:|Blockcount:)"
114                 echo Exit status is $?;
115                 $DEBUGFS -f "$TMPFILE.cmd2" "$TMPFILE.$ext" 2>&1;
116                 echo Exit status is $?;
117                 $DEBUGFS -R "dump /test/dir/file $TMPFILE.testme" "$TMPFILE.$ext" 2>&1;
118                 echo Exit status is $?;
119                 # extract the files and directories from the image and tar them
120                 # again to make sure that a tarball from the image contents is
121                 # bit-by-bit identical to the tarball the image was created
122                 # from -- essentially this checks whether a roundtrip from tar
123                 # to ext4 to tar remains identical
124                 $DEBUGFS -R "rdump /test $MKFS_DIR" "$TMPFILE.$ext" 2>&1;
125                 echo Exit status is $?;
126                 # debugfs rdump does not preserve the timestamps when it extracts the
127                 if test -z "$use_mkgnutar"; then
128                         # files so we ignore them by using tar --clamp-mtime
129                     $TAR --sort=name -C "$MKFS_DIR" \
130                          --mtime="$DEBUGFS_EXE" --clamp-mtime --format=gnu \
131                          -cvf "$TMPFILE.new.tar" test 2>&1;
132                 else
133                         perl $test_dir/mkgnutar.pl --verbose --directory="$MKFS_DIR" --mtime "$DEBUGFS_EXE_MTIME" test 2>&1 > "$TMPFILE.new.tar";
134                 fi;
135                 echo Exit status is $?;
136                 $FSCK -f -n "$TMPFILE.$ext" 2>&1;
137                 echo Exit status is $?;
138                 # independent from which tarball the ext4 image was created,
139                 # the tarball created from the files in it should be bit-by-bit
140                 # identical to the tarball without duplicate entries
141                 cmp "$MKFS_TAR.uniq" "$TMPFILE.new.tar" 2>&1;
142                 echo Exit status is $?;
143         } | sed -f "$cmd_dir/filter.sed" -f "$test_dir/output.sed" -e "s;$TMPFILE.$ext;test.img;" | {
144                 # In the first pass, store the output and append to the log
145                 # file. In the second pass, compare the output to the output
146                 # to the one from the first.
147                 case $ext in
148                         uniq) tee "$TMPFILE.log" >> "$OUT";;
149                         dupl) cmp - "$TMPFILE.log" >> "$OUT" 2>&1 || echo "cmp failed" >> "$OUT";;
150                 esac
151         }
152         rm -r "$MKFS_DIR" "$TMPFILE.new.tar"
153 done
154
155 # Do the verification
156 cmp -s "$OUT" "$EXP"
157 status=$?
158
159 if [ "$status" = 0 ] ; then
160         echo "$test_name: $test_description: ok"
161         touch "$test_name.ok"
162 else
163         echo "$test_name: $test_description: failed"
164         diff $DIFF_OPTS "$EXP" "$OUT" > "$test_name.failed"
165 fi
166
167 rm -rf "$MKFS_TAR.dupl" "$MKFS_TAR.uniq" "$TMPFILE.cmd1" "$TMPFILE.cmd2" \
168    "$TMPFILE.log" "$TMPFILE.dupl" "$TMPFILE.uniq" "$TMPFILE.testme"
169 unset MKFS_TAR MKFS_DIR OUT EXP