liblzma: Prevent uninitialzed warning in mt stream encoder.
[xz/debian.git] / src / scripts / xzdiff.in
blobc17d78b2c2da4d0b9c3bf00ec967954aafb3481d
1 #!@POSIX_SHELL@
3 # Copyright (C) 1998, 2002, 2006, 2007 Free Software Foundation
4 # Copyright (C) 1993 Jean-loup Gailly
6 # Modified for XZ Utils by Andrew Dudman and Lasse Collin.
8 # This program is free software; you can redistribute it and/or modify
9 # it under the terms of the GNU General Public License as published by
10 # the Free Software Foundation; either version 2 of the License, or
11 # (at your option) any later version.
13 # This program is distributed in the hope that it will be useful,
14 # but WITHOUT ANY WARRANTY; without even the implied warranty of
15 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 # GNU General Public License for more details.
18 @enable_path_for_scripts@
19 #SET_PATH - This line is a placeholder to ease patching this script.
21 # Instead of unsetting XZ_OPT, just make sure that xz will use file format
22 # autodetection. This way memory usage limit and thread limit can be
23 # specified via XZ_OPT. With gzip, bzip2, and lzop it's OK to just unset the
24 # environment variables.
25 xz='@xz@ --format=auto'
26 unset GZIP BZIP BZIP2 LZOP
28 case ${0##*/} in
29   *cmp*) prog=xzcmp; cmp=${CMP:-cmp};;
30   *)     prog=xzdiff; cmp=${DIFF:-diff};;
31 esac
33 version="$prog (@PACKAGE_NAME@) @VERSION@"
35 usage="Usage: ${0##*/} [OPTION]... FILE1 [FILE2]
36 Compare FILE1 to FILE2, using their uncompressed contents if they are
37 compressed.  If FILE2 is omitted, then the files compared are FILE1 and
38 FILE1 from which the compression format suffix has been stripped.
40 Do comparisons like '$cmp' does.  OPTIONs are the same as for '$cmp'.
42 Report bugs to <@PACKAGE_BUGREPORT@>."
44 # sed script to escape all ' for the shell, and then (to handle trailing
45 # newlines correctly) turn trailing X on last line into '.
46 escape='
47   s/'\''/'\''\\'\'''\''/g
48   $s/X$/'\''/
51 while :; do
52   case $1 in
53     --h*) printf '%s\n' "$usage" || exit 2; exit;;
54     --v*) printf '%s\n' "$version" || exit 2; exit;;
55     --) shift; break;;
56     -*\'*) cmp="$cmp '"`printf '%sX\n' "$1" | sed "$escape"`;;
57     -?*) cmp="$cmp '$1'";;
58     *) break;;
59   esac
60   shift
61 done
62 cmp="$cmp --"
64 for file; do
65   test "X$file" = X- || <"$file" || exit 2
66 done
68 # xz needs -qQ to ignore warnings like unsupported check type.
69 xz1="$xz -qQ"
70 xz2="$xz -qQ"
71 xz_status=0
72 exec 3>&1
74 if test $# -eq 1; then
75   case $1 in
76     *[-.]xz | *[-.]lzma | *[-.]lz | *.t[lx]z)
77       ;;
78     *[-.]bz2 | *.tbz | *.tbz2)
79       xz1=bzip2;;
80     *[-.][zZ] | *_z | *[-.]gz | *.t[ag]z)
81       xz1=gzip;;
82     *[-.]lzo | *.tzo)
83       xz1=lzop;;
84     *[-.]zst | *.tzst)
85       xz1='zstd -q';;
86     *)
87       printf '%s\n' "$0: $1: Unknown compressed file name suffix" >&2
88       exit 2;;
89   esac
90   case $1 in
91     *[-.][zZ] | *_z | *[-.][gx]z | *[-.]bz2 | *[-.]lzma | *[-.]lz | *[-.]lzo | *[-.]zst)
92       FILE=`expr "X$1" : 'X\(.*\)[-.][abglmostxzZ2]*$'`;;
93     *.t[abglx]z)
94       FILE=`expr "X$1" : 'X\(.*[-.]t\)[abglx]z$'`ar;;
95     *.tbz2)
96       FILE=`expr "X$1" : 'X\(.*[-.]t\)bz2$'`ar;;
97     *.tzo)
98       FILE=`expr "X$1" : 'X\(.*[-.]t\)zo$'`ar;;
99     *.tzst)
100       FILE=`expr "X$1" : 'X\(.*[-.]t\)zst$'`ar;;
101   esac
102   xz_status=$(
103     exec 4>&1
104     ($xz1 -cd -- "$1" 4>&-; echo $? >&4) 3>&- | eval "$cmp" - '"$FILE"' >&3
105   )
106 elif test $# -eq 2; then
107   case $1 in
108     *[-.]bz2 | *.tbz | *.tbz2) xz1=bzip2;;
109     *[-.][zZ] | *_z | *[-.]gz | *.t[ag]z) xz1=gzip;;
110     *[-.]lzo | *.tzo) xz1=lzop;;
111     *[-.]zst | *.tzst) xz1='zstd -q';;
112   esac
113   case $2 in
114     *[-.]bz2 | *.tbz | *.tbz2) xz2=bzip2;;
115     *[-.][zZ] | *_z | *[-.]gz | *.t[ag]z) xz2=gzip;;
116     *[-.]lzo | *.tzo) xz2=lzop;;
117     *[-.]zst | *.tzst) xz2='zstd -q';;
118   esac
119   case $1 in
120     *[-.][zZ] | *_z | *[-.][gx]z | *[-.]bz2 | *[-.]lzma | *[-.]lz | *.t[abglx]z | *.tbz2 | *[-.]lzo | *.tzo | *[-.]zst | *.tzst | -)
121       case "$2" in
122         *[-.][zZ] | *_z | *[-.][gx]z | *[-.]bz2 | *[-.]lzma | *[-.]lz | *.t[abglx]z | *.tbz2 | *[-.]lzo | *.tzo | *[-.]zst | *.tzst | -)
123           if test "$1$2" = --; then
124             xz_status=$(
125               exec 4>&1
126               ($xz1 -cdf - 4>&-; echo $? >&4) 3>&- |
127                 eval "$cmp" - - >&3
128             )
129           elif # Reject Solaris 8's buggy /bin/bash 2.03.
130               echo X | (echo X | eval "$cmp" /dev/fd/5 - >/dev/null 2>&1) 5<&0; then
131             # NOTE: xz_status will contain two numbers.
132             xz_status=$(
133               exec 4>&1
134               ($xz1 -cdf -- "$1" 4>&-; echo $? >&4) 3>&- |
135                 ( ($xz2 -cdf -- "$2" 4>&-; echo $? >&4) 3>&- 5<&- </dev/null |
136                 eval "$cmp" /dev/fd/5 - >&3) 5<&0
137             )
138           else
139             F=`expr "/$2" : '.*/\(.*\)[-.][ablmotxz2]*$'` || F=$prog
140             tmp=
141             trap '
142               test -n "$tmp" && rm -rf "$tmp"
143               (exit 2); exit 2
144             ' HUP INT PIPE TERM 0
145             if type mktemp >/dev/null 2>&1; then
146               # Note that FreeBSD's mktemp isn't fully compatible with
147               # the implementations from mktemp.org and GNU coreutils.
148               # It is important that the -t argument is the last argument
149               # and that no "--" is used between -t and the template argument.
150               # This way this command works on all implementations.
151               tmp=`mktemp -d -t "$prog.XXXXXXXXXX"` || exit 2
152             else
153               # Fallback code if mktemp is missing. This isn't as
154               # robust as using mktemp since this doesn't try with
155               # different file names in case of a file name conflict.
156               #
157               # There's no need to save the original umask since
158               # we don't create any non-temp files. Note that using
159               # mkdir -m 0077 isn't secure since some mkdir implementations
160               # create the dir with the default umask and chmod the
161               # the dir afterwards.
162               umask 0077
163               mkdir -- "${TMPDIR-/tmp}/$prog.$$" || exit 2
164               tmp="${TMPDIR-/tmp}/$prog.$$"
165             fi
166             $xz2 -cdf -- "$2" > "$tmp/$F" || exit 2
167             xz_status=$(
168               exec 4>&1
169               ($xz1 -cdf -- "$1" 4>&-; echo $? >&4) 3>&- |
170                 eval "$cmp" - '"$tmp/$F"' >&3
171             )
172             cmp_status=$?
173             rm -rf "$tmp" || xz_status=$?
174             trap - HUP INT PIPE TERM 0
175             (exit $cmp_status)
176           fi;;
177       *)
178         xz_status=$(
179           exec 4>&1
180           ($xz1 -cdf -- "$1" 4>&-; echo $? >&4) 3>&- |
181             eval "$cmp" - '"$2"' >&3
182         );;
183     esac;;
184   *)
185     case "$2" in
186       *[-.][zZ] | *_z | *[-.][gx]z | *[-.]bz2 | *[-.]lzma | *[-.]lz | *.t[abglx]z | *.tbz2 | *[-.]lzo | *.tzo | *[-.]zst | *.tzst | -)
187         xz_status=$(
188           exec 4>&1
189           ($xz2 -cdf -- "$2" 4>&-; echo $? >&4) 3>&- |
190             eval "$cmp" '"$1"' - >&3
191          );;
192       *)
193         eval "$cmp" '"$1"' '"$2"';;
194     esac;;
195   esac
196 else
197   printf '%s\n' "$0: Invalid number of operands; try \`${0##*/} --help' for help" >&2
198   exit 2
201 cmp_status=$?
202 for num in $xz_status ; do
203   # 0 from decompressor means successful decompression. SIGPIPE from
204   # decompressor is possible when diff or cmp exits before the whole file
205   # has been decompressed. In that case we want to retain the exit status
206   # from diff or cmp. Note that using "trap '' PIPE" is not possible
207   # because gzip changes its behavior (including exit status) if SIGPIPE
208   # is ignored.
209   test "$num" -eq 0 && continue
210   test "$num" -ge 128 \
211       && test "$(kill -l "$num" 2> /dev/null)" = "PIPE" \
212       && continue
213   exit 2
214 done
215 exit $cmp_status