zlib 1.0-pre

This commit is contained in:
Mark Adler 2011-09-09 23:13:27 -07:00
parent 56bcb184fa
commit 8a2acbffc8
32 changed files with 588 additions and 1274 deletions

View File

@ -2,32 +2,19 @@
ChangeLog file for zlib ChangeLog file for zlib
Changes in 1.0 (15 Jan 96) Changes in 1.0 (15 Jan 96)
- allow preset dictionary shared between compressor and decompressor
- allow compression level 0 (no compression)
- add deflateParams in zlib.h: allow dynamic change of compression level
and compression strategy.
- test large buffers and deflateParams in example.c
- add optional "configure" to build zlib as a shared library
- suppress Makefile.qnx, use configure instead
- fixed deflate for 64-bit systems (detected on Cray) - fixed deflate for 64-bit systems (detected on Cray)
- fixed inflate_blocks for 64-bit systems (detected on Alpha) - fixed inflate_blocks for 64-bit systems (detected on Alpha)
- declare Z_DEFLATED in zlib.h (possible parameter for deflateInit2)
- always return Z_BUF_ERROR when deflate() has nothing to do
- deflateInit and inflateInit are now macros to allow version checking
- prefix all global functions and types with z_ with -DZ_PREFIX
- make falloc completely reentrant (inftrees.c) - make falloc completely reentrant (inftrees.c)
- fixed very unlikely race condition in ct_static_init - fixed very unlikely race condition in ct_static_init
- free in reverse order of allocation to help memory manager - always return Z_BUF_ERROR when deflate() has nothing to do
- use zlib-1.0/* instead of zlib/* inside the tar.gz - add deflateParams in zlib.h.
- make zlib warning-free with "gcc -O3 -Wall -Wwrite-strings -Wpointer-arith - test large buffers and deflateParams in example.c
-Wconversion -Wstrict-prototypes -Wmissing-prototypes" - declare Z_DEFLATED in zlib.h (possible parameter for deflateInit2)
- allow gzread on concatenated .gz files
- deflateEnd now returns Z_DATA_ERROR if it was premature
- deflate is finally (?) fully deterministic (no matches beyond end of input)
- Document Z_SYNC_FLUSH - Document Z_SYNC_FLUSH
- add uninstall in Makefile - added deflateGetAdler32 and deflateSetAdler32
- free in reverse order of allocation to help memory manager
- Check for __cpluplus in zlib.h - Check for __cpluplus in zlib.h
- Better test in ct_align for partial flush - Finer test in ct_align for partial flush
- avoid harmless warnings for Borland C++ - avoid harmless warnings for Borland C++
- initialize hash_head in deflate.c - initialize hash_head in deflate.c
- avoid warning on fdopen (gzio.c) for HP cc -Aa - avoid warning on fdopen (gzio.c) for HP cc -Aa
@ -36,7 +23,7 @@ Changes in 1.0 (15 Jan 96)
- ignore error if ranlib doesn't exist - ignore error if ranlib doesn't exist
- call ranlib twice for NeXTSTEP - call ranlib twice for NeXTSTEP
- use exec_prefix instead of prefix for libz.a - use exec_prefix instead of prefix for libz.a
- renamed ct_* as _tr_* to avoid conflict with applications - renamed ct_* as tr_* to avoid conflict with another application.
- clear z->msg in inflateInit2 before any error return - clear z->msg in inflateInit2 before any error return
- initialize opaque in example.c, gzio.c, deflate.c and inflate.c - initialize opaque in example.c, gzio.c, deflate.c and inflate.c
- fixed typo in zconf.h (_GNUC__ => __GNUC__) - fixed typo in zconf.h (_GNUC__ => __GNUC__)
@ -45,22 +32,6 @@ Changes in 1.0 (15 Jan 96)
- in fcalloc, normalize pointer if size > 65520 bytes - in fcalloc, normalize pointer if size > 65520 bytes
- don't use special fcalloc for 32 bit Borland C++ - don't use special fcalloc for 32 bit Borland C++
- use STDC instead of __GO32__ to avoid redeclaring exit, calloc, etc... - use STDC instead of __GO32__ to avoid redeclaring exit, calloc, etc...
- use Z_BINARY instead of BINARY
- document that gzclose after gzdopen will close the file
- allow "a" as mode in gzopen.
- fix error checking in gzread
- allow skipping .gz extra-field on pipes
- added reference to Perl interface in README
- put the crc table in FAR data (I dislike more and more the medium model :)
- added get_crc_table
- added a dimension to all arrays (Borland C can't count).
- workaround Borland C bug in declaration of inflate_codes_new & inflate_fast
- guard against multiple inclusion of *.h (for precompiled header on Mac)
- Watcom C pretends to be Microsoft C small model even in 32 bit mode.
- don't use unsized arrays to avoid silly warnings by Visual C++:
warning C4746: 'inflate_mask' : unsized array treated as '__far'
(what's wrong with far data in far model?).
- define enum out of inflate_blocks_state to allow compilation with C++
Changes in 0.95 (16 Aug 95) Changes in 0.95 (16 Aug 95)
- fix MSDOS small and medium model (now easier to adapt to any compiler) - fix MSDOS small and medium model (now easier to adapt to any compiler)

121
Makefile
View File

@ -2,129 +2,78 @@
# Copyright (C) 1995-1996 Jean-loup Gailly. # Copyright (C) 1995-1996 Jean-loup Gailly.
# For conditions of distribution and use, see copyright notice in zlib.h # For conditions of distribution and use, see copyright notice in zlib.h
# To compile and test, type:
# ./configure; make test
# The call of configure is optional if you don't have special requirements
# To install /usr/local/lib/libz.* and /usr/local/include/zlib.h, type:
# make install
# To install in $HOME instead of /usr/local, use:
# make install prefix=$HOME
CC=cc CC=cc
CFLAGS=-O CFLAGS=-O
#CFLAGS=-O -DMAX_WBITS=14 -DMAX_MEM_LEVEL=7 #use -O3 for gcc
#CFLAGS="-O -DMAX_WBITS=14 -DMAX_MEM_LEVEL=7"
#CFLAGS=-g -DDEBUG #CFLAGS=-g -DDEBUG
#CFLAGS=-O3 -Wall -Wwrite-strings -Wpointer-arith -Wconversion \
# -Wstrict-prototypes -Wmissing-prototypes
LDFLAGS=-L. -lz LDFLAGS=-L. -lz
LDSHARED=$(CC)
VER=1.0
LIBS=libz.a
AR=ar rc
RANLIB=ranlib RANLIB=ranlib
TAR=tar
prefix=/usr/local prefix=/usr/local
exec_prefix = $(prefix) exec_prefix = ${prefix}
OBJS = adler32.o compress.o crc32.o gzio.o uncompr.o deflate.o trees.o \ OBJS = adler32.o compress.o crc32.o gzio.o uncompr.o deflate.o trees.o \
zutil.o inflate.o infblock.o inftrees.o infcodes.o infutil.o inffast.o zutil.o inflate.o infblock.o inftrees.o infcodes.o infutil.o inffast.o
TEST_OBJS = example.o minigzip.o TEST_OBJS = example.o minigzip.o
DISTFILES = README ChangeLog configure Makefile.in Makefile Makefile.msc \
Makefile.bor Makefile.tc Make_vms.com descrip.mms *.[ch]
all: example minigzip all: example minigzip
test: all test: all
./example ./example
echo hello world | ./minigzip | ./minigzip -d echo hello world | ./minigzip | ./minigzip -d
libz.a: $(OBJS) install: libz.a
$(AR) $@ $(OBJS) -@mkdir $(prefix)/include
-@ ($(RANLIB) $@ || true) 2>/dev/null -@mkdir $(exec_prefix)/lib
libz.so.$(VER): $(OBJS)
$(LDSHARED) -o $@ $(OBJS)
rm -f libz.so; ln -s $@ libz.so
example: example.o $(LIBS)
$(CC) $(CFLAGS) -o $@ example.o $(LDFLAGS)
minigzip: minigzip.o $(LIBS)
$(CC) $(CFLAGS) -o $@ minigzip.o $(LDFLAGS)
install: $(LIBS)
-@if [ ! $(prefix)/include ]; then mkdir $(prefix)/include; fi
-@if [ ! $(exec_prefix)/lib ]; then mkdir $(exec_prefix)/lib; fi
cp zlib.h zconf.h $(prefix)/include cp zlib.h zconf.h $(prefix)/include
chmod 644 $(prefix)/include/zlib.h $(prefix)/include/zconf.h chmod 644 $(prefix)/include/zlib.h $(prefix)/include/zconf.h
cp $(LIBS) $(exec_prefix)/lib cp libz.a $(exec_prefix)/lib
cd $(exec_prefix)/lib; chmod 644 $(LIBS) chmod 644 $(exec_prefix)/lib/libz.a
-@(cd $(exec_prefix)/lib; $(RANLIB) libz.a || true) >/dev/null 2>&1 -@$(RANLIB) $(prefix)/lib/libz.a
cd $(exec_prefix)/lib; if test -f libz.so.$(VER); then \ # This second ranlib is needed on NeXTSTEP which checks file times
ln -s libz.so.$(VER) libz.so; \
fi
# The ranlib in install is needed on NeXTSTEP which checks file times
uninstall: libz.a: $(OBJS)
cd $(exec_prefix)/lib; rm -f $(LIBS); \ ar rc $@ $(OBJS)
if test -f libz.so; then \ -@$(RANLIB) $@
v=`sed -n '/VERSION "/s/.*"\(.*\)".*/\1/p'<$(prefix)/include/zlib.h`;\
rm -f libz.so.$$v libz.so; \ example: example.o libz.a
fi $(CC) $(CFLAGS) -o $@ example.o $(LDFLAGS)
cd $(prefix)/include; rm -f zlib.h zconf.h
minigzip: minigzip.o libz.a
$(CC) $(CFLAGS) -o $@ minigzip.o $(LDFLAGS)
clean: clean:
rm -f *.o *~ example minigzip libz.a libz.so* foo.gz rm -f *.o example minigzip libz.a foo.gz
zip: zip:
mv Makefile Makefile~; cp -p Makefile.in Makefile zip -ul9 zlib README ChangeLog Makefile Make????.??? Makefile.?? \
v=`sed -n -e 's/\./-/' -e '/VERSION "/s/.*"\(.*\)".*/\1/p' < zlib.h`;\ descrip.mms *.[ch]
zip -ul9 zlib-$$v $(DISTFILES)
mv Makefile~ Makefile
dist: tgz:
mv Makefile Makefile~; cp -p Makefile.in Makefile cd ..; tar cfz zlib/zlib.tgz zlib/README zlib/ChangeLog zlib/Makefile \
d=zlib-`sed -n '/VERSION "/s/.*"\(.*\)".*/\1/p' < zlib.h`;\ zlib/Make????.??? zlib/Makefile.?? zlib/descrip.mms zlib/*.[ch]
rm -f $$d.tar.gz; \
if test ! -d ../$$d; then rm -f ../$$d; ln -s `pwd` ../$$d; fi; \
files=""; \
for f in $(DISTFILES); do files="$$files $$d/$$f"; done; \
cd ..; \
GZIP=-9 $(TAR) chofz $$d/$$d.tar.gz $$files; \
if test ! -d $$d; then rm -f $$d; fi
mv Makefile~ Makefile
tags: TAGS:
etags *.[ch] etags *.[ch]
depend:
makedepend -- $(CFLAGS) -- *.[ch]
# DO NOT DELETE THIS LINE -- make depend depends on it. # DO NOT DELETE THIS LINE -- make depend depends on it.
adler32.o: zlib.h zconf.h adler32.o: zutil.h zlib.h zconf.h
compress.o: zlib.h zconf.h compress.o: zlib.h zconf.h
crc32.o: zlib.h zconf.h crc32.o: zutil.h zlib.h zconf.h
deflate.o: deflate.h zutil.h zlib.h zconf.h deflate.o: deflate.h zutil.h zlib.h zconf.h
example.o: zlib.h zconf.h example.o: zlib.h zconf.h
gzio.o: zutil.h zlib.h zconf.h gzio.o: zutil.h zlib.h zconf.h
infblock.o: infblock.h inftrees.h infcodes.h infutil.h zutil.h zlib.h zconf.h infblock.o: zutil.h zlib.h zconf.h infblock.h inftrees.h infcodes.h infutil.h
infcodes.o: zutil.h zlib.h zconf.h infcodes.o: zutil.h zlib.h zconf.h inftrees.h infutil.h infcodes.h inffast.h
infcodes.o: inftrees.h infblock.h infcodes.h infutil.h inffast.h inffast.o: zutil.h zlib.h zconf.h inftrees.h infutil.h inffast.h
inffast.o: zutil.h zlib.h zconf.h inftrees.h
inffast.o: infblock.h infcodes.h infutil.h inffast.h
inflate.o: zutil.h zlib.h zconf.h infblock.h inflate.o: zutil.h zlib.h zconf.h infblock.h
inftrees.o: zutil.h zlib.h zconf.h inftrees.h inftrees.o: zutil.h zlib.h zconf.h inftrees.h
infutil.o: zutil.h zlib.h zconf.h infblock.h inftrees.h infcodes.h infutil.h infutil.o: zutil.h zlib.h zconf.h inftrees.h infutil.h
minigzip.o: zlib.h zconf.h minigzip.o: zlib.h zconf.h
trees.o: deflate.h zutil.h zlib.h zconf.h trees.o: deflate.h zutil.h zlib.h zconf.h
uncompr.o: zlib.h zconf.h uncompr.o: zlib.h zconf.h
zutil.o: zutil.h zlib.h zconf.h zutil.o: zutil.h zlib.h zconf.h

View File

@ -18,7 +18,7 @@ CFLAGS=-O2 -Z $(MODEL)
CC=bcc CC=bcc
LD=bcc LD=bcc
LIB=tlib LIB=tlib
# replace bcc with tcc for Turbo C++ 1.0, with bcc32 for the 32 bit version # replace bcc with tcc for Turbo C++ 1.0
LDFLAGS=$(MODEL) LDFLAGS=$(MODEL)
O=.obj O=.obj

View File

@ -1,130 +0,0 @@
# Makefile for zlib
# Copyright (C) 1995-1996 Jean-loup Gailly.
# For conditions of distribution and use, see copyright notice in zlib.h
# To compile and test, type:
# ./configure; make test
# The call of configure is optional if you don't have special requirements
# To install /usr/local/lib/libz.* and /usr/local/include/zlib.h, type:
# make install
# To install in $HOME instead of /usr/local, use:
# make install prefix=$HOME
CC=cc
CFLAGS=-O
#CFLAGS=-O -DMAX_WBITS=14 -DMAX_MEM_LEVEL=7
#CFLAGS=-g -DDEBUG
#CFLAGS=-O3 -Wall -Wwrite-strings -Wpointer-arith -Wconversion \
# -Wstrict-prototypes -Wmissing-prototypes
LDFLAGS=-L. -lz
LDSHARED=$(CC)
VER=1.0
LIBS=libz.a
AR=ar rc
RANLIB=ranlib
TAR=tar
prefix=/usr/local
exec_prefix = $(prefix)
OBJS = adler32.o compress.o crc32.o gzio.o uncompr.o deflate.o trees.o \
zutil.o inflate.o infblock.o inftrees.o infcodes.o infutil.o inffast.o
TEST_OBJS = example.o minigzip.o
DISTFILES = README ChangeLog configure Makefile.in Makefile Makefile.msc \
Makefile.bor Makefile.tc Make_vms.com descrip.mms *.[ch]
all: example minigzip
test: all
./example
echo hello world | ./minigzip | ./minigzip -d
libz.a: $(OBJS)
$(AR) $@ $(OBJS)
-@ ($(RANLIB) $@ || true) 2>/dev/null
libz.so.$(VER): $(OBJS)
$(LDSHARED) -o $@ $(OBJS)
rm -f libz.so; ln -s $@ libz.so
example: example.o $(LIBS)
$(CC) $(CFLAGS) -o $@ example.o $(LDFLAGS)
minigzip: minigzip.o $(LIBS)
$(CC) $(CFLAGS) -o $@ minigzip.o $(LDFLAGS)
install: $(LIBS)
-@if [ ! $(prefix)/include ]; then mkdir $(prefix)/include; fi
-@if [ ! $(exec_prefix)/lib ]; then mkdir $(exec_prefix)/lib; fi
cp zlib.h zconf.h $(prefix)/include
chmod 644 $(prefix)/include/zlib.h $(prefix)/include/zconf.h
cp $(LIBS) $(exec_prefix)/lib
cd $(exec_prefix)/lib; chmod 644 $(LIBS)
-@(cd $(exec_prefix)/lib; $(RANLIB) libz.a || true) >/dev/null 2>&1
cd $(exec_prefix)/lib; if test -f libz.so.$(VER); then \
ln -s libz.so.$(VER) libz.so; \
fi
# The ranlib in install is needed on NeXTSTEP which checks file times
uninstall:
cd $(exec_prefix)/lib; rm -f $(LIBS); \
if test -f libz.so; then \
v=`sed -n '/VERSION "/s/.*"\(.*\)".*/\1/p'<$(prefix)/include/zlib.h`;\
rm -f libz.so.$$v libz.so; \
fi
cd $(prefix)/include; rm -f zlib.h zconf.h
clean:
rm -f *.o *~ example minigzip libz.a libz.so* foo.gz
zip:
mv Makefile Makefile~; cp -p Makefile.in Makefile
v=`sed -n -e 's/\./-/' -e '/VERSION "/s/.*"\(.*\)".*/\1/p' < zlib.h`;\
zip -ul9 zlib-$$v $(DISTFILES)
mv Makefile~ Makefile
dist:
mv Makefile Makefile~; cp -p Makefile.in Makefile
d=zlib-`sed -n '/VERSION "/s/.*"\(.*\)".*/\1/p' < zlib.h`;\
rm -f $$d.tar.gz; \
if test ! -d ../$$d; then rm -f ../$$d; ln -s `pwd` ../$$d; fi; \
files=""; \
for f in $(DISTFILES); do files="$$files $$d/$$f"; done; \
cd ..; \
GZIP=-9 $(TAR) chofz $$d/$$d.tar.gz $$files; \
if test ! -d $$d; then rm -f $$d; fi
mv Makefile~ Makefile
tags:
etags *.[ch]
depend:
makedepend -- $(CFLAGS) -- *.[ch]
# DO NOT DELETE THIS LINE -- make depend depends on it.
adler32.o: zlib.h zconf.h
compress.o: zlib.h zconf.h
crc32.o: zlib.h zconf.h
deflate.o: deflate.h zutil.h zlib.h zconf.h
example.o: zlib.h zconf.h
gzio.o: zutil.h zlib.h zconf.h
infblock.o: infblock.h inftrees.h infcodes.h infutil.h zutil.h zlib.h zconf.h
infcodes.o: zutil.h zlib.h zconf.h
infcodes.o: inftrees.h infblock.h infcodes.h infutil.h inffast.h
inffast.o: zutil.h zlib.h zconf.h inftrees.h
inffast.o: infblock.h infcodes.h infutil.h inffast.h
inflate.o: zutil.h zlib.h zconf.h infblock.h
inftrees.o: zutil.h zlib.h zconf.h inftrees.h
infutil.o: zutil.h zlib.h zconf.h infblock.h inftrees.h infcodes.h infutil.h
minigzip.o: zlib.h zconf.h
trees.o: deflate.h zutil.h zlib.h zconf.h
uncompr.o: zlib.h zconf.h
zutil.o: zutil.h zlib.h zconf.h

75
Makefile.qnx Normal file
View File

@ -0,0 +1,75 @@
# Makefile for zlib
# Copyright (C) 1995 Jean-loup Gailly.
# For conditions of distribution and use, see copyright notice in zlib.h
# Modified slightly for QNX by Chris Herborth (chrish@qnx.com)
CC=cc
CFLAGS=-4 -O -Q
#use -O3 for gcc to take advantage of inlining
#CFLAGS="-O -DMAX_WBITS=14 -DMAX_MEM_LEVEL=7"
#CFLAGS=-g -DDEBUG
LDFLAGS=-L. -lz
#RANLIB=ranlib
prefix=/usr/local
OBJS = adler32.o compress.o crc32.o gzio.o uncompr.o deflate.o trees.o \
zutil.o inflate.o infblock.o inftrees.o infcodes.o infutil.o inffast.o
TEST_OBJS = example.o minigzip.o
all: example minigzip
test: all
./example
echo hello world | ./minigzip | ./minigzip -d
install: zlib.lib
-@mkdir $(prefix)/include
-@mkdir $(prefix)/lib
cp zlib.h zconf.h $(prefix)/include
chmod 644 $(prefix)/include/zlib.h $(prefix)/include/zconf.h
cp zlib.lib $(prefix)/lib
chmod 644 $(prefix)/lib/zlib.lib
zlib.lib: $(OBJS)
cc -A $@ $(OBJS)
# ar rc $@ $(OBJS)
# $(RANLIB) $@
example: example.o zlib.lib
$(CC) $(CFLAGS) -o $@ example.o $(LDFLAGS)
minigzip: minigzip.o zlib.lib
$(CC) $(CFLAGS) -o $@ minigzip.o $(LDFLAGS)
clean:
rm -f *.o example minigzip zlib.lib foo.gz
zip:
zip -ul9 zlib README ChangeLog Makefile Makefile.??? Makefile.?? *.[ch]
tgz:
cd ..; tar cfz zlib/zlib.tgz zlib/README zlib/ChangeLog zlib/Makefile \
zlib/Makefile.??? zlib/Makefile.?? zlib/*.[ch]
# DO NOT DELETE THIS LINE -- make depend depends on it.
adler32.o: zutil.h zlib.h zconf.h
compress.o: zlib.h zconf.h
crc32.o: zutil.h zlib.h zconf.h
deflate.o: deflate.h zutil.h zlib.h zconf.h
example.o: zlib.h zconf.h
gzio.o: zutil.h zlib.h zconf.h
infblock.o: zutil.h zlib.h zconf.h infblock.h inftrees.h infcodes.h infutil.h
infcodes.o: zutil.h zlib.h zconf.h inftrees.h infutil.h infcodes.h inffast.h
inffast.o: zutil.h zlib.h zconf.h inftrees.h infutil.h inffast.h
inflate.o: zutil.h zlib.h zconf.h infblock.h
inftrees.o: zutil.h zlib.h zconf.h inftrees.h
infutil.o: zutil.h zlib.h zconf.h inftrees.h infutil.h
minigzip.o: zlib.h zconf.h
trees.o: deflate.h zutil.h zlib.h zconf.h
uncompr.o: zlib.h zconf.h
zutil.o: zutil.h zlib.h zconf.h

70
README
View File

@ -1,71 +1,55 @@
zlib 1.0 is a general purpose data compression library. All the code zlib 1.0 is a general purpose data compression library.
is reentrant (thread safe). The data format used by the zlib library All the code is reentrant (thread safe).
is described in the files zlib-3.3.doc, deflate-1.3.doc and
gzip-4.3.doc, available in ftp://ftp.uu.net/pub/archiving/zip/doc/ The data format used by the zlib library is described in the
files zlib-3.2.doc, deflate-1.2.doc and gzip-4.2.doc, available
in ftp://ftp.uu.net/pub/archiving/zip/doc
All functions of the compression library are documented in the file All functions of the compression library are documented in the file
zlib.h. A usage example of the library is given in the file example.c zlib.h. A usage example of the library is given in the file example.c
which also tests that the library is working correctly. Another which also tests that the library is working correctly. Another
example is given in the file minigzip.c. The compression library itself example is given in the file minigzip.c.
is composed of all source files except example.c and minigzip.c.
To compile all files and run the test program, follow the instructions To compile all files and run the test program, just type: make test
given at the top of Makefile. In short "make test; make install" (For MSDOS, use one of the special makefiles such as Makefile.msc;
should work for most machines. For MSDOS, use one of the special for VMS, use Make_vms.com or descrip.mms.)
makefiles such as Makefile.msc; for VMS, use Make_vms.com or descrip.mms. To install the zlib library (libz.a) in /usr/local/lib, type: make install
To install in a different directory, use for example:
make install prefix=$HOME
This will install in $HOME/lib instead of /usr/local/lib.
Questions about zlib should be sent to <zlib@quest.jpl.nasa.gov> or, Questions about zlib should be sent to <zlib@quest.jpl.nasa.gov>.
if this fails, to the addresses given below in the Copyright section.
The changes made in version 1.0 are documented in the file ChangeLog. The changes made in version 1.0 are documented in the file ChangeLog.
The main changes since 0.95 are: The main changes since 0.95 are:
- allow preset dictionary shared between compressor and decompressor
- allow compression level 0 (no compression) - allow compression level 0 (no compression)
- add deflateParams in zlib.h: allow dynamic change of compression level - add deflateParams in zlib.h: allow dynamic change of compression level
and compression strategy. and compression strategy.
- test large buffers and deflateParams in example.c - test large buffers and deflateParams in example.c
- add optional "configure" to build zlib as a shared library
- suppress Makefile.qnx, use configure instead
- fixes for 64-bit systems (needed for Alpha and Cray)
- declare Z_DEFLATED in zlib.h (possible parameter for deflateInit2) - declare Z_DEFLATED in zlib.h (possible parameter for deflateInit2)
- fixes for 64-bit systems (needed for Alpha and Cray)
- always return Z_BUF_ERROR when deflate() has nothing to do - always return Z_BUF_ERROR when deflate() has nothing to do
- deflateInit and inflateInit are now macros to allow version checking - fix some very unlikely race conditions.
- prefix all global functions and types with z_ with -DZ_PREFIX
- fix some very unlikely race conditions in multi-threaded environment
- several minor fixes for better portability - several minor fixes for better portability
- free in reverse order of allocation to help memory manager - free in reverse order of allocation to help memory manager
- use zlib-1.0/* instead of zlib/* inside the tar.gz
- make zlib warning-free with "gcc -O3 -Wall -Wwrite-strings -Wpointer-arith
-Wconversion -Wstrict-prototypes -Wmissing-prototypes"
- allow gzread on concatenated .gz files
- deflateEnd now returns Z_DATA_ERROR if it was premature
- deflate is finally (?) fully deterministic
Notes for some targets: Notes for some targets:
- For Turbo C the small model is supported only with reduced performance to - For MSDOS, the small and medium models have been tested only with
avoid any far allocation; it was tested with -DMAX_WBITS=11 -DMAX_MEM_LEVEL=3 Microsoft C. (This should work for Borland C also, but I don't have
a Borland compiler to test with.) The small model was tested with
Turbo C but only with reduced performance to avoid any far
allocation; it was tested with -DMAX_WBITS=11 -DMAX_MEM_LEVEL=3
MS Visual C++1.5 in far model gives:
warning C4746: 'z_errmsg' : unsized array treated as '__far'
warning C4746: 'inflate_mask' : unsized array treated as '__far'
Ignore those warnings.
- For 64-bit Iris, deflate.c must be compiled without any optimization. - For 64-bit Iris, deflate.c must be compiled without any optimization.
With -O, one libpng test fails. The test works in 32 bit mode (with the With -O, one libpng test fails. The test works in 32 bit mode (with the
-32 compiler flag). -32 compiler flag).
- zlib doesn't work with gcc 2.6.3 on a DEC 3000/300LX under OSF/1 2.1
it works when compiled with cc.
- zlib doesn't work on HP-UX 9.05 with one cc compiler (the one not
accepting the -O option). It works with the other cc compiler.
A Perl interface to zlib written by Paul Marquess <pmarquess@bfsec.bt.co.uk>
is in the CPAN (Comprehensive Perl Archive Network) sites, such as:
ftp://ftp.cis.ufl.edu/pub/perl/CPAN/modules/by-module/Compress/Compress-Zlib*
Acknowledgments:
The deflate format used by zlib was defined by Phil Katz. The deflate
and zlib specifications were written by Peter Deutsch. Thanks to all the
people who reported problems and suggested various improvements in zlib;
they are too numerous to cite here.
Copyright notice: Copyright notice:

View File

@ -1,5 +1,5 @@
/* adler32.c -- compute the Adler-32 checksum of a data stream /* adler32.c -- compute the Adler-32 checksum of a data stream
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -20,7 +20,7 @@
/* ========================================================================= */ /* ========================================================================= */
uLong adler32(adler, buf, len) uLong adler32(adler, buf, len)
uLong adler; uLong adler;
const Bytef *buf; Bytef *buf;
uInt len; uInt len;
{ {
unsigned long s1 = adler & 0xffff; unsigned long s1 = adler & 0xffff;

View File

@ -1,5 +1,5 @@
/* compress.c -- compress a memory buffer /* compress.c -- compress a memory buffer
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -22,13 +22,13 @@
int compress (dest, destLen, source, sourceLen) int compress (dest, destLen, source, sourceLen)
Bytef *dest; Bytef *dest;
uLongf *destLen; uLongf *destLen;
const Bytef *source; Bytef *source;
uLong sourceLen; uLong sourceLen;
{ {
z_stream stream; z_stream stream;
int err; int err;
stream.next_in = (Bytef*)source; stream.next_in = source;
stream.avail_in = (uInt)sourceLen; stream.avail_in = (uInt)sourceLen;
/* Check for source > 64K on 16-bit machine: */ /* Check for source > 64K on 16-bit machine: */
if ((uLong)stream.avail_in != sourceLen) return Z_BUF_ERROR; if ((uLong)stream.avail_in != sourceLen) return Z_BUF_ERROR;

81
configure vendored
View File

@ -1,81 +0,0 @@
#!/bin/sh
# configure script for zlib. This script is needed only if
# you wish to build a shared library and your system supports them,
# of if you need special compiler, flags or install directory.
# Otherwise, you can just use directly "make test; make install"
#
# To impose specific compiler or flags or install directory, use for example:
# prefix=$HOME CC=cc CFLAGS="-O4" ./configure
# or for csh/tcsh users:
# (setenv prefix $HOME; setenv CC cc; setenv CFLAGS "-O4"; ./configure)
# LDSHARED is the command to be used to create a shared library
LIBS=libz.a
VER=`sed -n -e '/VERSION "/s/.*"\(.*\)".*/\1/p' < zlib.h`
AR=${AR-"ar rc"}
prefix=${prefix-/usr/local}
exec_prefix=${exec_prefix-$prefix}
test -z "$CC" && echo Checking for gcc...
test=ztest$$
cat > $test.c <<EOF
int hello() { printf("hello\n"); }
EOF
if test -z "$CC" && (gcc -c -O3 $test.c) 2>/dev/null; then
CC=gcc
SFLAGS=${CFLAGS-"-fPIC -O3"}
CFLAGS=${CFLAGS-"-O3"}
LDSHARED=${LDSHARED-"gcc -shared"}
else
# find system name and corresponding cc options
CC=${CC-cc}
case `(uname -sr || echo unknown) 2>/dev/null` in
SunOS\ 5*) SFLAGS=${CFLAGS-"-fast -xcg89 -KPIC -R."}
CFLAGS=${CFLAGS-"-fast -xcg89"}
LDSHARED=${LDSHARED-"cc -G"};;
SunOS\ 4*) SFLAGS=${CFLAGS-"-O2 -PIC"}
CFLAGS=${CFLAGS-"-O2"}
LDSHARED=${LDSHARED-"ld"};;
IRIX*) SFLAGS=${CFLAGS-"-O2 -rpath ."}
CFLAGS=${CFLAGS-"-O2"}
LDSHARED=${LDSHARED-"cc -shared"};;
QNX*) SFLAGS=${CFLAGS-"-4 -O -Q"}
CFLAGS=${CFLAGS-"-4 -O -Q"}
LDSHARED=${LDSHARED-"cc"}
LIBS=zlib.lib
AR="cc -A";;
# send working options for other systems to gzip@prep.ai.mit.edu
*) SFLAGS=${CFLAGS-"-O"}
CFLAGS=${CFLAGS-"-O"}
LDSHARED=${LDSHARED-"-shared"};;
esac
fi
echo Checking for shared library support...
# we must test in two steps (cc then ld), required at least on SunOS 4.x
if test "`$CC -c $SFLAGS $test.c 2>&1`" = "" &&
test "`$LDSHARED -o $test.so $test.o 2>&1`" = ""; then
CFLAGS="$SFLAGS"
LIBS='libz.so.$(VER)'
echo Building shared library libz.so.$VER with $CC.
else
LDSHARED="$CC"
echo Building static library $LIBS version $VER with $CC.
fi
rm -f $test.[co] $test.so
# udpate Makefile
# ed -s Makefile <<EOF
sed < Makefile.in "
/^CC *=/s/=.*/=$CC/
/^CFLAGS *=/s/=.*/=$CFLAGS/
/^LDSHARED *=/s/=.*/=$LDSHARED/
/^LIBS *=/s,=.*,=$LIBS,
/^AR *=/s/=.*/=$AR/
/^VER *=/s/=.*/=$VER/
/^prefix *=/s,=.*,=$prefix,
/^exec_prefix *=/s,=.*,=$exec_prefix,
" > Makefile
#w
#q
#EOF

60
crc32.c
View File

@ -1,5 +1,5 @@
/* crc32.c -- compute the CRC-32 of a data stream /* crc32.c -- compute the CRC-32 of a data stream
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -10,53 +10,23 @@
#define local static #define local static
#ifdef DYNAMIC_CRC_TABLE #ifdef DYNAMIC_CRC_TABLE
/* =========================================================================
* Make the crc table. This function is needed only if you want to compute
* the table dynamically.
*/
local int crc_table_empty = 1; local int crc_table_empty = 1;
local uLongf crc_table[256]; local uLong crc_table[256];
local void make_crc_table OF((void));
/*
Generate a table for a byte-wise 32-bit CRC calculation on the polynomial:
x^32+x^26+x^23+x^22+x^16+x^12+x^11+x^10+x^8+x^7+x^5+x^4+x^2+x+1.
Polynomials over GF(2) are represented in binary, one bit per coefficient,
with the lowest powers in the most significant bit. Then adding polynomials
is just exclusive-or, and multiplying a polynomial by x is a right shift by
one. If we call the above polynomial p, and represent a byte as the
polynomial q, also with the lowest power in the most significant bit (so the
byte 0xb1 is the polynomial x^7+x^3+x+1), then the CRC is (q*x^32) mod p,
where a mod b means the remainder after dividing a by b.
This calculation is done using the shift-register method of multiplying and
taking the remainder. The register is initialized to zero, and for each
incoming bit, x^32 is added mod p to the register if the bit is a one (where
x^32 mod p is p+x^32 = x^26+...+1), and the register is multiplied mod p by
x (which is shifting right by one and adding x^32 mod p if the bit shifted
out is a one). We start with the highest power (least significant bit) of
q and repeat for all eight bits of q.
The table is simply the CRC of all possible eight bit values. This is all
the information needed to generate CRC's on data a byte at a time for all
combinations of CRC register values and incoming bytes.
*/
local void make_crc_table() local void make_crc_table()
{ {
uLong c; uLong c;
int n, k; int n, k;
uLong poly; /* polynomial exclusive-or pattern */
/* terms of polynomial defining this crc (except x^32): */
static Byte p[] = {0,1,2,4,5,7,8,10,11,12,16,22,23,26};
/* make exclusive-or pattern from polynomial (0xedb88320L) */
poly = 0L;
for (n = 0; n < sizeof(p)/sizeof(Byte); n++)
poly |= 1L << (31 - p[n]);
for (n = 0; n < 256; n++) for (n = 0; n < 256; n++)
{ {
c = (uLong)n; c = (uLong)n;
for (k = 0; k < 8; k++) for (k = 0; k < 8; k++)
c = c & 1 ? poly ^ (c >> 1) : c >> 1; c = c & 1 ? 0xedb88320L ^ (c >> 1) : c >> 1;
crc_table[n] = c; crc_table[n] = c;
} }
crc_table_empty = 0; crc_table_empty = 0;
@ -65,7 +35,7 @@ local void make_crc_table()
/* ======================================================================== /* ========================================================================
* Table of CRC-32's of all single-byte values (made by make_crc_table) * Table of CRC-32's of all single-byte values (made by make_crc_table)
*/ */
local uLongf crc_table[256] = { local uLong crc_table[] = {
0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L, 0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L,
0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L, 0x706af48fL, 0xe963a535L, 0x9e6495a3L, 0x0edb8832L, 0x79dcb8a4L,
0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L, 0xe0d5e91eL, 0x97d2d988L, 0x09b64c2bL, 0x7eb17cbdL, 0xe7b82d07L,
@ -121,18 +91,6 @@ local uLongf crc_table[256] = {
}; };
#endif #endif
/* =========================================================================
* This function can be used by asm versions of crc32()
*/
uLongf *get_crc_table()
{
#ifdef DYNAMIC_CRC_TABLE
if (crc_table_empty) make_crc_table();
#endif
return (uLongf *)crc_table;
}
/* ========================================================================= */
#define DO1(buf) crc = crc_table[((int)crc ^ (*buf++)) & 0xff] ^ (crc >> 8); #define DO1(buf) crc = crc_table[((int)crc ^ (*buf++)) & 0xff] ^ (crc >> 8);
#define DO2(buf) DO1(buf); DO1(buf); #define DO2(buf) DO1(buf); DO1(buf);
#define DO4(buf) DO2(buf); DO2(buf); #define DO4(buf) DO2(buf); DO2(buf);
@ -141,7 +99,7 @@ uLongf *get_crc_table()
/* ========================================================================= */ /* ========================================================================= */
uLong crc32(crc, buf, len) uLong crc32(crc, buf, len)
uLong crc; uLong crc;
const Bytef *buf; Bytef *buf;
uInt len; uInt len;
{ {
if (buf == Z_NULL) return 0L; if (buf == Z_NULL) return 0L;

194
deflate.c
View File

@ -1,5 +1,5 @@
/* deflate.c -- compress data using the deflation algorithm /* deflate.c -- compress data using the deflation algorithm
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -51,7 +51,7 @@
#include "deflate.h" #include "deflate.h"
char deflate_copyright[] = " deflate 1.0 Copyright 1995-1996 Jean-loup Gailly "; char deflate_copyright[] = " deflate 1.0 Copyright 1995 Jean-loup Gailly ";
/* /*
If you use the zlib library in a product, an acknowledgment is welcome If you use the zlib library in a product, an acknowledgment is welcome
in the documentation of your product. If for some reason you cannot in the documentation of your product. If for some reason you cannot
@ -60,8 +60,9 @@ char deflate_copyright[] = " deflate 1.0 Copyright 1995-1996 Jean-loup Gailly ";
*/ */
/* =========================================================================== /* ===========================================================================
* Function prototypes. * Prototypes for local functions.
*/ */
local void fill_window OF((deflate_state *s)); local void fill_window OF((deflate_state *s));
local int deflate_stored OF((deflate_state *s, int flush)); local int deflate_stored OF((deflate_state *s, int flush));
local int deflate_fast OF((deflate_state *s, int flush)); local int deflate_fast OF((deflate_state *s, int flush));
@ -168,36 +169,26 @@ struct static_tree_desc_s {int dummy;}; /* for buggy compilers */
zmemzero((charf *)s->head, (unsigned)(s->hash_size-1)*sizeof(*s->head)); zmemzero((charf *)s->head, (unsigned)(s->hash_size-1)*sizeof(*s->head));
/* ========================================================================= */ /* ========================================================================= */
int deflateInit_(strm, level, version, stream_size) int deflateInit (strm, level)
z_stream *strm; z_stream *strm;
int level; int level;
const char *version;
int stream_size;
{ {
return deflateInit2_(strm, level, Z_DEFLATED, MAX_WBITS, DEF_MEM_LEVEL, return deflateInit2 (strm, level, Z_DEFLATED, MAX_WBITS, DEF_MEM_LEVEL, 0);
Z_DEFAULT_STRATEGY, version, stream_size);
/* To do: ignore strm->next_in if we use it as window */ /* To do: ignore strm->next_in if we use it as window */
} }
/* ========================================================================= */ /* ========================================================================= */
int deflateInit2_(strm, level, method, windowBits, memLevel, strategy, int deflateInit2 (strm, level, method, windowBits, memLevel, strategy)
version, stream_size)
z_stream *strm; z_stream *strm;
int level; int level;
int method; int method;
int windowBits; int windowBits;
int memLevel; int memLevel;
int strategy; int strategy;
const char *version;
int stream_size;
{ {
deflate_state *s; deflate_state *s;
int noheader = 0; int noheader = 0;
if (version == Z_NULL || version[0] != ZLIB_VERSION[0] ||
stream_size != sizeof(z_stream)) {
return Z_VERSION_ERROR;
}
if (strm == Z_NULL) return Z_STREAM_ERROR; if (strm == Z_NULL) return Z_STREAM_ERROR;
strm->msg = Z_NULL; strm->msg = Z_NULL;
@ -243,7 +234,7 @@ int deflateInit2_(strm, level, method, windowBits, memLevel, strategy,
if (s->window == Z_NULL || s->prev == Z_NULL || s->head == Z_NULL || if (s->window == Z_NULL || s->prev == Z_NULL || s->head == Z_NULL ||
s->pending_buf == Z_NULL) { s->pending_buf == Z_NULL) {
strm->msg = ERR_MSG(Z_MEM_ERROR); strm->msg = z_errmsg[1-Z_MEM_ERROR];
deflateEnd (strm); deflateEnd (strm);
return Z_MEM_ERROR; return Z_MEM_ERROR;
} }
@ -261,41 +252,32 @@ int deflateInit2_(strm, level, method, windowBits, memLevel, strategy,
return deflateReset(strm); return deflateReset(strm);
} }
/* ========================================================================= */ /* =========================================================================
int deflateSetDictionary (strm, dictionary, dictLength) * Undocumented function to return the Adler32 of a stream. It can be
* called immediately after a flush with Z_SYNC_FLUSH, to allow later
* resumption of the compressor with deflateSetAdler32.
*/
uLong deflateGetAdler32 (strm)
z_stream *strm; z_stream *strm;
const Bytef *dictionary;
uInt dictLength;
{ {
deflate_state *s; if (strm == Z_NULL || strm->state == Z_NULL) return (uLong)Z_STREAM_ERROR;
uInt length = dictLength; /* Z_STREAM_ERROR happens to be an invalid Adler32 value. */
uInt n;
IPos hash_head;
if (strm == Z_NULL || strm->state == Z_NULL || dictionary == Z_NULL || return strm->state->adler;
strm->state->status != INIT_STATE) return Z_STREAM_ERROR; }
s = strm->state; /* =========================================================================
strm->adler = adler32(strm->adler, dictionary, dictLength); * Undocumented function to set the Adler32 of a stream. It can be called
* immediately after deflateInit to reset the Adler32 of a compression
* stream which had been interrupted.
*/
int deflateSetAdler32 (strm, adler)
z_stream *strm;
uLong adler;
{
if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR;
if (length < MIN_MATCH) return Z_OK; strm->state->adler = adler;
if (length > MAX_DIST(s)) {
length = MAX_DIST(s);
dictionary += dictLength - length;
}
zmemcpy((charf *)s->window, dictionary, length);
s->strstart = length;
s->block_start = (long)length;
/* Insert all strings in the hash table (except for the last two bytes).
* s->lookahead stays null, so s->ins_h will be recomputed at the next
* call of fill_window.
*/
s->ins_h = s->window[0];
UPDATE_HASH(s, s->ins_h, s->window[1]);
for (n = 0; n <= length - MIN_MATCH; n++) {
INSERT_STRING(s, n, hash_head);
}
return Z_OK; return Z_OK;
} }
@ -320,10 +302,10 @@ int deflateReset (strm)
s->noheader = 0; /* was set to -1 by deflate(..., Z_FINISH); */ s->noheader = 0; /* was set to -1 by deflate(..., Z_FINISH); */
} }
s->status = s->noheader ? BUSY_STATE : INIT_STATE; s->status = s->noheader ? BUSY_STATE : INIT_STATE;
strm->adler = 1; s->adler = 1;
s->last_flush = Z_NO_FLUSH; s->last_flush = Z_NO_FLUSH;
_tr_init(s); tr_init(s);
lm_init(s); lm_init(s);
return Z_OK; return Z_OK;
@ -410,47 +392,36 @@ int deflate (strm, flush)
int flush; int flush;
{ {
int old_flush; /* value of flush param for previous deflate call */ int old_flush; /* value of flush param for previous deflate call */
deflate_state *s;
if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR;
s = strm->state;
if (strm->next_out == Z_NULL || if (strm->next_out == Z_NULL ||
(strm->next_in == Z_NULL && strm->avail_in != 0) || (strm->next_in == Z_NULL && strm->avail_in != 0) ||
(s->status == FINISH_STATE && flush != Z_FINISH)) { (strm->state->status == FINISH_STATE && flush != Z_FINISH)) {
ERR_RETURN(strm, Z_STREAM_ERROR); ERR_RETURN(strm, Z_STREAM_ERROR);
} }
if (strm->avail_out == 0) ERR_RETURN(strm, Z_BUF_ERROR); if (strm->avail_out == 0) ERR_RETURN(strm, Z_BUF_ERROR);
s->strm = strm; /* just in case */ strm->state->strm = strm; /* just in case */
old_flush = s->last_flush; old_flush = strm->state->last_flush;
s->last_flush = flush; strm->state->last_flush = flush;
/* Write the zlib header */ /* Write the zlib header */
if (s->status == INIT_STATE) { if (strm->state->status == INIT_STATE) {
uInt header = (Z_DEFLATED + ((s->w_bits-8)<<4)) << 8; uInt header = (Z_DEFLATED + ((strm->state->w_bits-8)<<4)) << 8;
uInt level_flags = (s->level-1) >> 1; uInt level_flags = (strm->state->level-1) >> 1;
if (level_flags > 3) level_flags = 3; if (level_flags > 3) level_flags = 3;
header |= (level_flags << 6); header |= (level_flags << 6);
if (s->strstart != 0) header |= PRESET_DICT;
header += 31 - (header % 31); header += 31 - (header % 31);
s->status = BUSY_STATE; strm->state->status = BUSY_STATE;
putShortMSB(s, header); putShortMSB(strm->state, header);
/* Save the adler32 of the preset dictionary: */
if (s->strstart != 0) {
putShortMSB(s, (uInt)(strm->adler >> 16));
putShortMSB(s, (uInt)(strm->adler & 0xffff));
strm->adler = 1L;
}
} }
/* Flush as much pending output as possible */ /* Flush as much pending output as possible */
if (s->pending != 0) { if (strm->state->pending != 0) {
flush_pending(strm); flush_pending(strm);
if (strm->avail_out == 0) return Z_OK; if (strm->avail_out == 0) return Z_OK;
@ -464,20 +435,21 @@ int deflate (strm, flush)
} }
/* User must not provide more input after the first FINISH: */ /* User must not provide more input after the first FINISH: */
if (s->status == FINISH_STATE && strm->avail_in != 0) { if (strm->state->status == FINISH_STATE && strm->avail_in != 0) {
ERR_RETURN(strm, Z_BUF_ERROR); ERR_RETURN(strm, Z_BUF_ERROR);
} }
/* Start a new block or continue the current one. /* Start a new block or continue the current one.
*/ */
if (strm->avail_in != 0 || s->lookahead != 0 || if (strm->avail_in != 0 || strm->state->lookahead != 0 ||
(flush != Z_NO_FLUSH && s->status != FINISH_STATE)) { (flush != Z_NO_FLUSH && strm->state->status != FINISH_STATE)) {
int quit; int quit;
if (flush == Z_FINISH) { if (flush == Z_FINISH) {
s->status = FINISH_STATE; strm->state->status = FINISH_STATE;
} }
quit = (*(configuration_table[s->level].func))(s, flush); quit = (*(configuration_table[strm->state->level].func))
(strm->state, flush);
if (quit || strm->avail_out == 0) return Z_OK; if (quit || strm->avail_out == 0) return Z_OK;
/* If flush != Z_NO_FLUSH && avail_out == 0, the next call /* If flush != Z_NO_FLUSH && avail_out == 0, the next call
@ -489,14 +461,14 @@ int deflate (strm, flush)
*/ */
if (flush != Z_NO_FLUSH && flush != Z_FINISH) { if (flush != Z_NO_FLUSH && flush != Z_FINISH) {
if (flush == Z_PARTIAL_FLUSH) { if (flush == Z_PARTIAL_FLUSH) {
_tr_align(s); tr_align(strm->state);
} else { /* FULL_FLUSH or SYNC_FLUSH */ } else { /* FULL_FLUSH or SYNC_FLUSH */
_tr_stored_block(s, (char*)0, 0L, 0); tr_stored_block(strm->state, (char*)0, 0L, 0);
/* For a full flush, this empty block will be recognized /* For a full flush, this empty block will be recognized
* as a special marker by inflate_sync(). * as a special marker by inflate_sync().
*/ */
if (flush == Z_FULL_FLUSH) { if (flush == Z_FULL_FLUSH) {
CLEAR_HASH(s); /* forget history */ CLEAR_HASH(strm->state); /* forget history */
} }
} }
flush_pending(strm); flush_pending(strm);
@ -506,25 +478,23 @@ int deflate (strm, flush)
Assert(strm->avail_out > 0, "bug2"); Assert(strm->avail_out > 0, "bug2");
if (flush != Z_FINISH) return Z_OK; if (flush != Z_FINISH) return Z_OK;
if (s->noheader) return Z_STREAM_END; if (strm->state->noheader) return Z_STREAM_END;
/* Write the zlib trailer (adler32) */ /* Write the zlib trailer (adler32) */
putShortMSB(s, (uInt)(strm->adler >> 16)); putShortMSB(strm->state, (uInt)(strm->state->adler >> 16));
putShortMSB(s, (uInt)(strm->adler & 0xffff)); putShortMSB(strm->state, (uInt)(strm->state->adler & 0xffff));
flush_pending(strm); flush_pending(strm);
/* If avail_out is zero, the application will call deflate again /* If avail_out is zero, the application will call deflate again
* to flush the rest. * to flush the rest.
*/ */
s->noheader = -1; /* write the trailer only once! */ strm->state->noheader = -1; /* write the trailer only once! */
return s->pending != 0 ? Z_OK : Z_STREAM_END; return strm->state->pending != 0 ? Z_OK : Z_STREAM_END;
} }
/* ========================================================================= */ /* ========================================================================= */
int deflateEnd (strm) int deflateEnd (strm)
z_stream *strm; z_stream *strm;
{ {
int status;
if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR; if (strm == Z_NULL || strm->state == Z_NULL) return Z_STREAM_ERROR;
/* Deallocate in reverse order of allocations: */ /* Deallocate in reverse order of allocations: */
@ -533,11 +503,10 @@ int deflateEnd (strm)
TRY_FREE(strm, strm->state->prev); TRY_FREE(strm, strm->state->prev);
TRY_FREE(strm, strm->state->window); TRY_FREE(strm, strm->state->window);
status = strm->state->status;
ZFREE(strm, strm->state); ZFREE(strm, strm->state);
strm->state = Z_NULL; strm->state = Z_NULL;
return status == BUSY_STATE ? Z_DATA_ERROR : Z_OK; return Z_OK;
} }
/* ========================================================================= */ /* ========================================================================= */
@ -580,7 +549,7 @@ local int read_buf(strm, buf, size)
strm->avail_in -= len; strm->avail_in -= len;
if (!strm->state->noheader) { if (!strm->state->noheader) {
strm->adler = adler32(strm->adler, strm->next_in, len); strm->state->adler = adler32(strm->state->adler, strm->next_in, len);
} }
zmemcpy(buf, strm->next_in, len); zmemcpy(buf, strm->next_in, len);
strm->next_in += len; strm->next_in += len;
@ -624,7 +593,6 @@ local void lm_init (s)
* garbage. * garbage.
* IN assertions: cur_match is the head of the hash chain for the current * IN assertions: cur_match is the head of the hash chain for the current
* string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1 * string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1
* OUT assertion: the match length is not greater than s->lookahead.
*/ */
#ifndef ASMV #ifndef ASMV
/* For 80x86 and 680x0, an optimized version will be provided in match.asm or /* For 80x86 and 680x0, an optimized version will be provided in match.asm or
@ -639,7 +607,6 @@ local int longest_match(s, cur_match)
register Bytef *match; /* matched string */ register Bytef *match; /* matched string */
register int len; /* length of current match */ register int len; /* length of current match */
int best_len = s->prev_length; /* best match length so far */ int best_len = s->prev_length; /* best match length so far */
int nice_match = s->nice_match; /* stop if match long enough */
IPos limit = s->strstart > (IPos)MAX_DIST(s) ? IPos limit = s->strstart > (IPos)MAX_DIST(s) ?
s->strstart - (IPos)MAX_DIST(s) : NIL; s->strstart - (IPos)MAX_DIST(s) : NIL;
/* Stop when cur_match becomes <= limit. To simplify the code, /* Stop when cur_match becomes <= limit. To simplify the code,
@ -670,11 +637,6 @@ local int longest_match(s, cur_match)
if (s->prev_length >= s->good_match) { if (s->prev_length >= s->good_match) {
chain_length >>= 2; chain_length >>= 2;
} }
/* Do not look for matches beyond the end of the input. This is necessary
* to make deflate deterministic.
*/
if (nice_match > s->lookahead) nice_match = s->lookahead;
Assert((ulg)s->strstart <= s->window_size-MIN_LOOKAHEAD, "need lookahead"); Assert((ulg)s->strstart <= s->window_size-MIN_LOOKAHEAD, "need lookahead");
do { do {
@ -753,7 +715,7 @@ local int longest_match(s, cur_match)
if (len > best_len) { if (len > best_len) {
s->match_start = cur_match; s->match_start = cur_match;
best_len = len; best_len = len;
if (len >= nice_match) break; if (len >= s->nice_match) break;
#ifdef UNALIGNED_OK #ifdef UNALIGNED_OK
scan_end = *(ushf*)(scan+best_len-1); scan_end = *(ushf*)(scan+best_len-1);
#else #else
@ -764,8 +726,7 @@ local int longest_match(s, cur_match)
} while ((cur_match = prev[cur_match & wmask]) > limit } while ((cur_match = prev[cur_match & wmask]) > limit
&& --chain_length != 0); && --chain_length != 0);
if (best_len <= s->lookahead) return best_len; return best_len;
return s->lookahead;
} }
#endif /* ASMV */ #endif /* ASMV */
@ -779,13 +740,13 @@ local void check_match(s, start, match, length)
int length; int length;
{ {
/* check that the match is indeed a match */ /* check that the match is indeed a match */
if (zmemcmp((charf *)s->window + match, if (memcmp((charf *)s->window + match,
(charf *)s->window + start, length) != EQUAL) { (charf *)s->window + start, length) != EQUAL) {
fprintf(stderr, " start %u, match %u, length %d\n", fprintf(stderr,
start, match, length); " start %u, match %u, length %d\n",
do { start, match, length);
fprintf(stderr, "%c%c", s->window[match++], s->window[start++]); do { fprintf(stderr, "%c%c", s->window[match++],
} while (--length != 0); s->window[start++]); } while (--length != 0);
z_error("invalid match"); z_error("invalid match");
} }
if (verbose > 1) { if (verbose > 1) {
@ -901,11 +862,9 @@ local void fill_window(s)
* IN assertion: strstart is set to the end of the current match. * IN assertion: strstart is set to the end of the current match.
*/ */
#define FLUSH_BLOCK_ONLY(s, eof) { \ #define FLUSH_BLOCK_ONLY(s, eof) { \
_tr_flush_block(s, (s->block_start >= 0L ? \ tr_flush_block(s, (s->block_start >= 0L ? \
(charf *)&s->window[(unsigned)s->block_start] : \ (charf *)&s->window[(unsigned)s->block_start] : \
(charf *)Z_NULL), \ (charf *)Z_NULL), (long)s->strstart - s->block_start, (eof)); \
(ulg)((long)s->strstart - s->block_start), \
(eof)); \
s->block_start = s->strstart; \ s->block_start = s->strstart; \
flush_pending(s->strm); \ flush_pending(s->strm); \
Tracev((stderr,"[FLUSH]")); \ Tracev((stderr,"[FLUSH]")); \
@ -1008,12 +967,14 @@ local int deflate_fast(s, flush)
s->match_length = longest_match (s, hash_head); s->match_length = longest_match (s, hash_head);
} }
/* longest_match() sets match_start */ /* longest_match() sets match_start */
if (s->match_length > s->lookahead) s->match_length = s->lookahead;
} }
if (s->match_length >= MIN_MATCH) { if (s->match_length >= MIN_MATCH) {
check_match(s, s->strstart, s->match_start, s->match_length); check_match(s, s->strstart, s->match_start, s->match_length);
bflush = _tr_tally(s, s->strstart - s->match_start, bflush = tr_tally(s, s->strstart - s->match_start,
s->match_length - MIN_MATCH); s->match_length - MIN_MATCH);
s->lookahead -= s->match_length; s->lookahead -= s->match_length;
@ -1046,7 +1007,7 @@ local int deflate_fast(s, flush)
} else { } else {
/* No match, output a literal byte */ /* No match, output a literal byte */
Tracevv((stderr,"%c", s->window[s->strstart])); Tracevv((stderr,"%c", s->window[s->strstart]));
bflush = _tr_tally (s, 0, s->window[s->strstart]); bflush = tr_tally (s, 0, s->window[s->strstart]);
s->lookahead--; s->lookahead--;
s->strstart++; s->strstart++;
} }
@ -1104,6 +1065,7 @@ local int deflate_slow(s, flush)
s->match_length = longest_match (s, hash_head); s->match_length = longest_match (s, hash_head);
} }
/* longest_match() sets match_start */ /* longest_match() sets match_start */
if (s->match_length > s->lookahead) s->match_length = s->lookahead;
if (s->match_length <= 5 && (s->strategy == Z_FILTERED || if (s->match_length <= 5 && (s->strategy == Z_FILTERED ||
(s->match_length == MIN_MATCH && (s->match_length == MIN_MATCH &&
@ -1124,8 +1086,8 @@ local int deflate_slow(s, flush)
check_match(s, s->strstart-1, s->prev_match, s->prev_length); check_match(s, s->strstart-1, s->prev_match, s->prev_length);
bflush = _tr_tally(s, s->strstart -1 - s->prev_match, bflush = tr_tally(s, s->strstart -1 - s->prev_match,
s->prev_length - MIN_MATCH); s->prev_length - MIN_MATCH);
/* Insert in hash table all strings up to the end of the match. /* Insert in hash table all strings up to the end of the match.
* strstart-1 and strstart are already inserted. If there is not * strstart-1 and strstart are already inserted. If there is not
@ -1151,7 +1113,7 @@ local int deflate_slow(s, flush)
* is longer, truncate the previous match to a single literal. * is longer, truncate the previous match to a single literal.
*/ */
Tracevv((stderr,"%c", s->window[s->strstart-1])); Tracevv((stderr,"%c", s->window[s->strstart-1]));
if (_tr_tally (s, 0, s->window[s->strstart-1])) { if (tr_tally (s, 0, s->window[s->strstart-1])) {
FLUSH_BLOCK_ONLY(s, 0); FLUSH_BLOCK_ONLY(s, 0);
} }
s->strstart++; s->strstart++;
@ -1169,7 +1131,7 @@ local int deflate_slow(s, flush)
Assert (flush != Z_NO_FLUSH, "no flush?"); Assert (flush != Z_NO_FLUSH, "no flush?");
if (s->match_available) { if (s->match_available) {
Tracevv((stderr,"%c", s->window[s->strstart-1])); Tracevv((stderr,"%c", s->window[s->strstart-1]));
_tr_tally (s, 0, s->window[s->strstart-1]); tr_tally (s, 0, s->window[s->strstart-1]);
s->match_available = 0; s->match_available = 0;
} }
FLUSH_BLOCK(s, flush == Z_FINISH); FLUSH_BLOCK(s, flush == Z_FINISH);

View File

@ -1,5 +1,5 @@
/* deflate.h -- internal compression state /* deflate.h -- internal compression state
* Copyright (C) 1995-1996 Jean-loup Gailly * Copyright (C) 1995 Jean-loup Gailly
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -10,15 +10,17 @@
/* $Id: deflate.h,v 1.5 1995/05/03 17:27:09 jloup Exp $ */ /* $Id: deflate.h,v 1.5 1995/05/03 17:27:09 jloup Exp $ */
#ifndef _DEFLATE_H
#define _DEFLATE_H
#include "zutil.h" #include "zutil.h"
/* =========================================================================== /* ===========================================================================
* Internal compression state. * Internal compression state.
*/ */
/* Data type */
#define BINARY 0
#define ASCII 1
#define UNKNOWN 2
#define LENGTH_CODES 29 #define LENGTH_CODES 29
/* number of length codes, not counting the special END_BLOCK code */ /* number of length codes, not counting the special END_BLOCK code */
@ -85,6 +87,7 @@ typedef struct internal_state {
Bytef *pending_buf; /* output still pending */ Bytef *pending_buf; /* output still pending */
Bytef *pending_out; /* next pending byte to output to the stream */ Bytef *pending_out; /* next pending byte to output to the stream */
int pending; /* nb of bytes in the pending buffer */ int pending; /* nb of bytes in the pending buffer */
uLong adler; /* adler32 of uncompressed data */
int noheader; /* suppress zlib header and adler32 */ int noheader; /* suppress zlib header and adler32 */
Byte data_type; /* UNKNOWN, BINARY or ASCII */ Byte data_type; /* UNKNOWN, BINARY or ASCII */
Byte method; /* STORED (for zip only) or DEFLATED */ Byte method; /* STORED (for zip only) or DEFLATED */
@ -265,11 +268,9 @@ typedef struct internal_state {
*/ */
/* in trees.c */ /* in trees.c */
void _tr_init OF((deflate_state *s)); void tr_init OF((deflate_state *s));
int _tr_tally OF((deflate_state *s, unsigned dist, unsigned lc)); int tr_tally OF((deflate_state *s, int dist, int lc));
ulg _tr_flush_block OF((deflate_state *s, charf *buf, ulg stored_len, ulg tr_flush_block OF((deflate_state *s, charf *buf, ulg stored_len, int eof));
int eof)); void tr_align OF((deflate_state *s));
void _tr_align OF((deflate_state *s)); void tr_stored_block OF((deflate_state *s, charf *buf, ulg stored_len,
void _tr_stored_block OF((deflate_state *s, charf *buf, ulg stored_len, int eof));
int eof));
#endif

122
example.c
View File

@ -1,5 +1,5 @@
/* example.c -- usage example of the zlib compression library /* example.c -- usage example of the zlib compression library
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -22,17 +22,14 @@
} \ } \
} }
const char hello[] = "hello, hello!"; char *hello = "hello, hello!";
/* "hello world" would be more standard, but the repeated "hello" /* "hello world" would be more standard, but the repeated "hello"
* stresses the compression code better, sorry... * stresses the compression code better, sorry...
*/ */
const char dictionary[] = "hello";
uLong dictId; /* Adler32 value of the dictionary */
void test_compress OF((Bytef *compr, uLong comprLen, void test_compress OF((Bytef *compr, uLong comprLen,
Bytef *uncompr, uLong uncomprLen)); Bytef *uncompr, uLong uncomprLen));
void test_gzio OF((const char *out, const char *in, void test_gzio OF((char *out, char *in,
Bytef *uncompr, int uncomprLen)); Bytef *uncompr, int uncomprLen));
void test_deflate OF((Bytef *compr, uLong comprLen)); void test_deflate OF((Bytef *compr, uLong comprLen));
void test_inflate OF((Bytef *compr, uLong comprLen, void test_inflate OF((Bytef *compr, uLong comprLen,
@ -44,9 +41,6 @@ void test_large_inflate OF((Bytef *compr, uLong comprLen,
void test_flush OF((Bytef *compr, uLong comprLen)); void test_flush OF((Bytef *compr, uLong comprLen));
void test_sync OF((Bytef *compr, uLong comprLen, void test_sync OF((Bytef *compr, uLong comprLen,
Bytef *uncompr, uLong uncomprLen)); Bytef *uncompr, uLong uncomprLen));
void test_dict_deflate OF((Bytef *compr, uLong comprLen));
void test_dict_inflate OF((Bytef *compr, uLong comprLen,
Bytef *uncompr, uLong uncomprLen));
int main OF((int argc, char *argv[])); int main OF((int argc, char *argv[]));
/* =========================================================================== /* ===========================================================================
@ -59,7 +53,7 @@ void test_compress(compr, comprLen, uncompr, uncomprLen)
int err; int err;
uLong len = strlen(hello)+1; uLong len = strlen(hello)+1;
err = compress(compr, &comprLen, (const Bytef*)hello, len); err = compress(compr, &comprLen, (Byte*)hello, len);
CHECK_ERR(err, "compress"); CHECK_ERR(err, "compress");
strcpy((char*)uncompr, "garbage"); strcpy((char*)uncompr, "garbage");
@ -78,8 +72,8 @@ void test_compress(compr, comprLen, uncompr, uncomprLen)
* Test read/write of .gz files * Test read/write of .gz files
*/ */
void test_gzio(out, in, uncompr, uncomprLen) void test_gzio(out, in, uncompr, uncomprLen)
const char *out; /* output file */ char *out; /* output file */
const char *in; /* input file */ char *in; /* input file */
Bytef *uncompr; Bytef *uncompr;
int uncomprLen; int uncomprLen;
{ {
@ -93,7 +87,7 @@ void test_gzio(out, in, uncompr, uncomprLen)
exit(1); exit(1);
} }
if (gzwrite(file, (const voidp)hello, (unsigned)len) != len) { if (gzwrite(file, hello, len) != len) {
fprintf(stderr, "gzwrite err: %s\n", gzerror(file, &err)); fprintf(stderr, "gzwrite err: %s\n", gzerror(file, &err));
} }
gzclose(file); gzclose(file);
@ -104,7 +98,7 @@ void test_gzio(out, in, uncompr, uncomprLen)
} }
strcpy((char*)uncompr, "garbage"); strcpy((char*)uncompr, "garbage");
uncomprLen = gzread(file, uncompr, (unsigned)uncomprLen); uncomprLen = gzread(file, uncompr, uncomprLen);
if (uncomprLen != len) { if (uncomprLen != len) {
fprintf(stderr, "gzread err: %s\n", gzerror(file, &err)); fprintf(stderr, "gzread err: %s\n", gzerror(file, &err));
} }
@ -177,7 +171,7 @@ void test_inflate(compr, comprLen, uncompr, uncomprLen)
d_stream.next_in = compr; d_stream.next_in = compr;
d_stream.next_out = uncompr; d_stream.next_out = uncompr;
while (d_stream.total_out < uncomprLen && d_stream.total_in < comprLen) { while (d_stream.total_out < uncomprLen) {
d_stream.avail_in = d_stream.avail_out = 1; /* force small buffers */ d_stream.avail_in = d_stream.avail_out = 1; /* force small buffers */
err = inflate(&d_stream, Z_NO_FLUSH); err = inflate(&d_stream, Z_NO_FLUSH);
if (err == Z_STREAM_END) break; if (err == Z_STREAM_END) break;
@ -212,7 +206,7 @@ void test_large_deflate(compr, comprLen, uncompr, uncomprLen)
CHECK_ERR(err, "deflateInit"); CHECK_ERR(err, "deflateInit");
c_stream.next_out = compr; c_stream.next_out = compr;
c_stream.avail_out = (uInt)comprLen; c_stream.avail_out = comprLen;
/* At this point, uncompr is still mostly zeroes, so it should compress /* At this point, uncompr is still mostly zeroes, so it should compress
* very well: * very well:
@ -271,7 +265,7 @@ void test_large_inflate(compr, comprLen, uncompr, uncomprLen)
for (;;) { for (;;) {
d_stream.next_out = uncompr; /* discard the output */ d_stream.next_out = uncompr; /* discard the output */
d_stream.avail_out = (uInt)uncomprLen; d_stream.avail_out = uncomprLen;
err = inflate(&d_stream, Z_NO_FLUSH); err = inflate(&d_stream, Z_NO_FLUSH);
if (err == Z_STREAM_END) break; if (err == Z_STREAM_END) break;
CHECK_ERR(err, "large inflate"); CHECK_ERR(err, "large inflate");
@ -350,7 +344,7 @@ void test_sync(compr, comprLen, uncompr, uncomprLen)
inflate(&d_stream, Z_NO_FLUSH); inflate(&d_stream, Z_NO_FLUSH);
CHECK_ERR(err, "inflate"); CHECK_ERR(err, "inflate");
d_stream.avail_in = (uInt)comprLen-2; /* read all compressed data */ d_stream.avail_in = (uInt)uncomprLen-2; /* read all compressed data */
err = inflateSync(&d_stream); /* but skip the damaged part */ err = inflateSync(&d_stream); /* but skip the damaged part */
CHECK_ERR(err, "inflateSync"); CHECK_ERR(err, "inflateSync");
@ -365,91 +359,6 @@ void test_sync(compr, comprLen, uncompr, uncomprLen)
printf("after inflateSync(): hel%s\n", uncompr); printf("after inflateSync(): hel%s\n", uncompr);
} }
/* ===========================================================================
* Test deflate() with preset dictionary
*/
void test_dict_deflate(compr, comprLen)
Bytef *compr;
uLong comprLen;
{
z_stream c_stream; /* compression stream */
int err;
c_stream.zalloc = (alloc_func)0;
c_stream.zfree = (free_func)0;
c_stream.opaque = (voidpf)0;
err = deflateInit(&c_stream, Z_BEST_COMPRESSION);
CHECK_ERR(err, "deflateInit");
err = deflateSetDictionary(&c_stream,
(const Bytef*)dictionary, sizeof(dictionary));
CHECK_ERR(err, "deflateSetDictionary");
dictId = c_stream.adler;
c_stream.next_out = compr;
c_stream.avail_out = (uInt)comprLen;
c_stream.next_in = (Bytef*)hello;
c_stream.avail_in = (uInt)strlen(hello)+1;
err = deflate(&c_stream, Z_FINISH);
if (err != Z_STREAM_END) {
fprintf(stderr, "deflate should report Z_STREAM_END\n");
}
err = deflateEnd(&c_stream);
CHECK_ERR(err, "deflateEnd");
}
/* ===========================================================================
* Test inflate() with a preset dictionary
*/
void test_dict_inflate(compr, comprLen, uncompr, uncomprLen)
Bytef *compr, *uncompr;
uLong comprLen, uncomprLen;
{
int err;
z_stream d_stream; /* decompression stream */
strcpy((char*)uncompr, "garbage");
d_stream.zalloc = (alloc_func)0;
d_stream.zfree = (free_func)0;
d_stream.opaque = (voidpf)0;
err = inflateInit(&d_stream);
CHECK_ERR(err, "inflateInit");
d_stream.next_in = compr;
d_stream.avail_in = (uInt)comprLen;
d_stream.next_out = uncompr;
d_stream.avail_out = (uInt)uncomprLen;
for (;;) {
err = inflate(&d_stream, Z_NO_FLUSH);
if (err == Z_STREAM_END) break;
if (err == Z_NEED_DICT) {
if (d_stream.adler != dictId) {
fprintf(stderr, "unexpected dictionary");
exit(1);
}
err = inflateSetDictionary(&d_stream, (const Bytef*)dictionary,
sizeof(dictionary));
}
CHECK_ERR(err, "inflate with dict");
}
err = inflateEnd(&d_stream);
CHECK_ERR(err, "inflateEnd");
if (strcmp((char*)uncompr, hello)) {
fprintf(stderr, "bad inflate with dict\n");
} else {
printf("inflate with dictionary: %s\n", uncompr);
}
}
/* =========================================================================== /* ===========================================================================
* Usage: example [output.gz [input.gz]] * Usage: example [output.gz [input.gz]]
*/ */
@ -470,8 +379,8 @@ int main(argc, argv)
fprintf(stderr, "warning: different zlib version\n"); fprintf(stderr, "warning: different zlib version\n");
} }
compr = (Bytef*)malloc((uInt)comprLen); compr = (Bytef*)malloc(comprLen);
uncompr = (Bytef*)calloc((uInt)uncomprLen, 1); /* must be cleared */ uncompr = (Bytef*)calloc(uncomprLen, 1); /* must be cleared initially */
if (compr == Z_NULL || uncompr == Z_NULL) { if (compr == Z_NULL || uncompr == Z_NULL) {
printf("out of memory\n"); printf("out of memory\n");
exit(1); exit(1);
@ -492,9 +401,6 @@ int main(argc, argv)
test_flush(compr, comprLen); test_flush(compr, comprLen);
test_sync(compr, comprLen, uncompr, uncomprLen); test_sync(compr, comprLen, uncompr, uncomprLen);
test_dict_deflate(compr, comprLen);
test_dict_inflate(compr, comprLen, uncompr, uncomprLen);
exit(0); exit(0);
return 0; /* to avoid warning */ return 0; /* to avoid warning */
} }

361
gzio.c
View File

@ -1,5 +1,5 @@
/* gzio.c -- IO on .gz files /* gzio.c -- IO on .gz files
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -16,7 +16,8 @@ struct internal_state {int dummy;}; /* for buggy compilers */
#define ALLOC(size) malloc(size) #define ALLOC(size) malloc(size)
#define TRYFREE(p) {if (p) free(p);} #define TRYFREE(p) {if (p) free(p);}
static int gz_magic[2] = {0x1f, 0x8b}; /* gzip magic header */ #define GZ_MAGIC_1 0x1f
#define GZ_MAGIC_2 0x8b
/* gzip flag byte */ /* gzip flag byte */
#define ASCII_FLAG 0x01 /* bit 0 set: file probably ascii text */ #define ASCII_FLAG 0x01 /* bit 0 set: file probably ascii text */
@ -26,6 +27,10 @@ static int gz_magic[2] = {0x1f, 0x8b}; /* gzip magic header */
#define COMMENT 0x10 /* bit 4 set: file comment present */ #define COMMENT 0x10 /* bit 4 set: file comment present */
#define RESERVED 0xE0 /* bits 5..7: reserved */ #define RESERVED 0xE0 /* bits 5..7: reserved */
#ifndef SEEK_CUR
# define SEEK_CUR 1
#endif
typedef struct gz_stream { typedef struct gz_stream {
z_stream stream; z_stream stream;
int z_err; /* error code for last stream operation */ int z_err; /* error code for last stream operation */
@ -41,12 +46,40 @@ typedef struct gz_stream {
} gz_stream; } gz_stream;
local gzFile gz_open OF((const char *path, const char *mode, int fd)); local int destroy OF((gz_stream *s));
local int get_byte OF((gz_stream *s)); local gzFile gz_open OF((char *path, char *mode, int fd));
local void check_header OF((gz_stream *s)); local void putLong OF((FILE *file, uLong x));
local int destroy OF((gz_stream *s)); local uLong getLong OF((Bytef *buf));
local void putLong OF((FILE *file, uLong x));
local uLong getLong OF((gz_stream *s)); /* ===========================================================================
* Cleanup then free the given gz_stream. Return a zlib error code.
*/
local int destroy (s)
gz_stream *s;
{
int err = Z_OK;
if (!s) return Z_STREAM_ERROR;
TRYFREE(s->inbuf);
TRYFREE(s->outbuf);
TRYFREE(s->path);
TRYFREE(s->msg);
if (s->stream.state != NULL) {
if (s->mode == 'w') {
err = deflateEnd(&(s->stream));
} else if (s->mode == 'r') {
err = inflateEnd(&(s->stream));
}
}
if (s->file != NULL && fclose(s->file)) {
err = Z_ERRNO;
}
if (s->z_err < 0) err = s->z_err;
TRYFREE(s);
return err;
}
/* =========================================================================== /* ===========================================================================
Opens a gzip (.gz) file for reading or writing. The mode parameter Opens a gzip (.gz) file for reading or writing. The mode parameter
@ -58,20 +91,15 @@ local uLong getLong OF((gz_stream *s));
zlib error is Z_MEM_ERROR). zlib error is Z_MEM_ERROR).
*/ */
local gzFile gz_open (path, mode, fd) local gzFile gz_open (path, mode, fd)
const char *path; char *path;
const char *mode; char *mode;
int fd; int fd;
{ {
int err; int err;
int level = Z_DEFAULT_COMPRESSION; /* compression level */ int level = Z_DEFAULT_COMPRESSION; /* compression level */
char *p = (char*)mode; char *p = mode;
gz_stream *s; gz_stream *s = (gz_stream *)ALLOC(sizeof(gz_stream));
char fmode[80]; /* copy of mode, without the compression level */
char *m = fmode;
if (!path || !mode) return Z_NULL;
s = (gz_stream *)ALLOC(sizeof(gz_stream));
if (!s) return Z_NULL; if (!s) return Z_NULL;
s->stream.zalloc = (alloc_func)0; s->stream.zalloc = (alloc_func)0;
@ -96,13 +124,9 @@ local gzFile gz_open (path, mode, fd)
s->mode = '\0'; s->mode = '\0';
do { do {
if (*p == 'r') s->mode = 'r'; if (*p == 'r') s->mode = 'r';
if (*p == 'w' || *p == 'a') s->mode = 'w'; if (*p == 'w') s->mode = 'w';
if (*p >= '0' && *p <= '9') { if (*p >= '1' && *p <= '9') level = *p - '0';
level = *p - '0'; } while (*p++);
} else {
*m++ = *p; /* copy the mode */
}
} while (*p++ && m != fmode + sizeof(fmode));
if (s->mode == '\0') return destroy(s), (gzFile)Z_NULL; if (s->mode == '\0') return destroy(s), (gzFile)Z_NULL;
if (s->mode == 'w') { if (s->mode == 'w') {
@ -126,7 +150,7 @@ local gzFile gz_open (path, mode, fd)
s->stream.avail_out = Z_BUFSIZE; s->stream.avail_out = Z_BUFSIZE;
errno = 0; errno = 0;
s->file = fd < 0 ? FOPEN(path, fmode) : (FILE*)fdopen(fd, fmode); s->file = fd < 0 ? FOPEN(path, mode) : (FILE*)fdopen(fd, mode);
if (s->file == NULL) { if (s->file == NULL) {
return destroy(s), (gzFile)Z_NULL; return destroy(s), (gzFile)Z_NULL;
@ -134,10 +158,50 @@ local gzFile gz_open (path, mode, fd)
if (s->mode == 'w') { if (s->mode == 'w') {
/* Write a very simple .gz header: /* Write a very simple .gz header:
*/ */
fprintf(s->file, "%c%c%c%c%c%c%c%c%c%c", gz_magic[0], gz_magic[1], fprintf(s->file, "%c%c%c%c%c%c%c%c%c%c", GZ_MAGIC_1, GZ_MAGIC_2,
Z_DEFLATED, 0 /*flags*/, 0,0,0,0 /*time*/, 0 /*xflags*/, OS_CODE); Z_DEFLATED, 0 /*flags*/, 0,0,0,0 /*time*/, 0 /*xflags*/, OS_CODE);
} else { } else {
check_header(s); /* skip the .gz header */ /* Check and skip the header:
*/
Byte c1 = 0, c2 = 0;
Byte method = 0;
Byte flags = 0;
Byte xflags = 0;
Byte time[4];
Byte osCode;
int c;
s->stream.avail_in = fread(s->inbuf, 1, 2, s->file);
if (s->stream.avail_in != 2 || s->inbuf[0] != GZ_MAGIC_1
|| s->inbuf[1] != GZ_MAGIC_2) {
s->transparent = 1;
return (gzFile)s;
}
s->stream.avail_in = 0;
fscanf(s->file,"%c%c%4c%c%c", &method, &flags, time, &xflags, &osCode);
if (method != Z_DEFLATED || feof(s->file) || (flags & RESERVED) != 0) {
s->z_err = Z_DATA_ERROR;
return (gzFile)s;
}
if ((flags & EXTRA_FIELD) != 0) { /* skip the extra field */
long len;
fscanf(s->file, "%c%c", &c1, &c2);
len = c1 + ((long)c2<<8);
fseek(s->file, len, SEEK_CUR);
}
if ((flags & ORIG_NAME) != 0) { /* skip the original file name */
while ((c = getc(s->file)) != 0 && c != EOF) ;
}
if ((flags & COMMENT) != 0) { /* skip the .gz file comment */
while ((c = getc(s->file)) != 0 && c != EOF) ;
}
if ((flags & HEAD_CRC) != 0) { /* skip the header crc */
fscanf(s->file, "%c%c", &c1, &c2);
}
if (feof(s->file)) {
s->z_err = Z_DATA_ERROR;
}
} }
return (gzFile)s; return (gzFile)s;
} }
@ -146,138 +210,25 @@ local gzFile gz_open (path, mode, fd)
Opens a gzip (.gz) file for reading or writing. Opens a gzip (.gz) file for reading or writing.
*/ */
gzFile gzopen (path, mode) gzFile gzopen (path, mode)
const char *path; char *path;
const char *mode; char *mode;
{ {
return gz_open (path, mode, -1); return gz_open (path, mode, -1);
} }
/* =========================================================================== /* ===========================================================================
Associate a gzFile with the file descriptor fd. fd is not dup'ed here Associate a gzFile with the file descriptor fd.
to mimic the behavio(u)r of fdopen.
*/ */
gzFile gzdopen (fd, mode) gzFile gzdopen (fd, mode)
int fd; int fd;
const char *mode; char *mode;
{ {
char name[20]; char name[20];
if (fd < 0) return (gzFile)Z_NULL;
sprintf(name, "<fd:%d>", fd); /* for debugging */ sprintf(name, "<fd:%d>", fd); /* for debugging */
return gz_open (name, mode, fd); return gz_open (name, mode, fd);
} }
/* ===========================================================================
Read a byte from a gz_stream; update next_in and avail_in. Return EOF
for end of file.
IN assertion: the stream s has been sucessfully opened for reading.
*/
local int get_byte(s)
gz_stream *s;
{
if (s->z_eof) return EOF;
if (s->stream.avail_in == 0) {
errno = 0;
s->stream.avail_in = fread(s->inbuf, 1, Z_BUFSIZE, s->file);
if (s->stream.avail_in == 0) {
s->z_eof = 1;
if (ferror(s->file)) s->z_err = Z_ERRNO;
return EOF;
}
s->stream.next_in = s->inbuf;
}
s->stream.avail_in--;
return *(s->stream.next_in)++;
}
/* ===========================================================================
Check the gzip header of a gz_stream opened for reading. Set the stream
mode to transparent if the gzip magic header is not present; set s->err
to Z_DATA_ERROR if the magic header is present but the rest of the header
is incorrect.
IN assertion: the stream s has already been created sucessfully;
s->stream.avail_in is zero for the first time, but may be non-zero
for concatenated .gz files.
*/
local void check_header(s)
gz_stream *s;
{
int method = 0;
int flags = 0;
uInt len;
int c;
/* Check the gzip magic header */
for (len = 0; len < 2; len++) {
c = get_byte(s);
if (c != gz_magic[len]) {
s->transparent = 1;
if (c != EOF) s->stream.avail_in++, s->stream.next_in--;
s->z_err = s->stream.avail_in != 0 ? Z_OK : Z_STREAM_END;
return;
}
}
method = get_byte(s);
flags = get_byte(s);
if (method != Z_DEFLATED || (flags & RESERVED) != 0) {
s->z_err = Z_DATA_ERROR;
return;
}
/* Discard time, xflags and OS code: */
for (len = 0; len < 6; len++) (void)get_byte(s);
if ((flags & EXTRA_FIELD) != 0) { /* skip the extra field */
len = (uInt)get_byte(s);
len += ((uInt)get_byte(s))<<8;
/* len is garbage if EOF but the loop below will quit anyway */
while (len-- != 0 && get_byte(s) != EOF) ;
}
if ((flags & ORIG_NAME) != 0) { /* skip the original file name */
while ((c = get_byte(s)) != 0 && c != EOF) ;
}
if ((flags & COMMENT) != 0) { /* skip the .gz file comment */
while ((c = get_byte(s)) != 0 && c != EOF) ;
}
if ((flags & HEAD_CRC) != 0) { /* skip the header crc */
for (len = 0; len < 2; len++) (void)get_byte(s);
}
s->z_err = s->z_eof ? Z_DATA_ERROR : Z_OK;
}
/* ===========================================================================
* Cleanup then free the given gz_stream. Return a zlib error code.
Try freeing in the reverse order of allocations.
*/
local int destroy (s)
gz_stream *s;
{
int err = Z_OK;
if (!s) return Z_STREAM_ERROR;
TRYFREE(s->msg);
if (s->stream.state != NULL) {
if (s->mode == 'w') {
err = deflateEnd(&(s->stream));
} else if (s->mode == 'r') {
err = inflateEnd(&(s->stream));
}
}
if (s->file != NULL && fclose(s->file)) {
err = Z_ERRNO;
}
if (s->z_err < 0) err = s->z_err;
TRYFREE(s->inbuf);
TRYFREE(s->outbuf);
TRYFREE(s->path);
TRYFREE(s);
return err;
}
/* =========================================================================== /* ===========================================================================
Reads the given number of uncompressed bytes from the compressed file. Reads the given number of uncompressed bytes from the compressed file.
gzread returns the number of bytes actually read (0 for end of file). gzread returns the number of bytes actually read (0 for end of file).
@ -288,71 +239,52 @@ int gzread (file, buf, len)
unsigned len; unsigned len;
{ {
gz_stream *s = (gz_stream*)file; gz_stream *s = (gz_stream*)file;
Byte *start = buf; /* starting point for crc computation */
if (s == NULL || s->mode != 'r') return Z_STREAM_ERROR; if (s == NULL || s->mode != 'r') return Z_STREAM_ERROR;
if (s->z_err == Z_DATA_ERROR || s->z_err == Z_ERRNO) return -1; if (s->transparent) {
if (s->z_err == Z_STREAM_END) return 0; /* EOF */ int n = 0;
Byte *b = (Byte*)buf;
/* Copy the first two (non-magic) bytes if not done already */
while (s->stream.avail_in > 0 && len > 0) {
*b++ = *s->stream.next_in++;
s->stream.avail_in--;
len--; n++;
}
if (len == 0) return n;
return n + fread(b, 1, len, s->file);
}
if (s->z_err == Z_DATA_ERROR) return -1; /* bad .gz file */
if (s->z_err == Z_STREAM_END) return 0; /* don't read crc as data */
s->stream.next_out = buf; s->stream.next_out = buf;
s->stream.avail_out = len; s->stream.avail_out = len;
while (s->stream.avail_out != 0) { while (s->stream.avail_out != 0) {
if (s->transparent) {
/* Copy first the lookahead bytes: */
uInt n = s->stream.avail_in;
if (n > s->stream.avail_out) n = s->stream.avail_out;
if (n > 0) {
zmemcpy(s->stream.next_out, s->stream.next_in, n);
s->stream.next_out += n;
s->stream.next_in += n;
s->stream.avail_out -= n;
s->stream.avail_in -= n;
}
if (s->stream.avail_out > 0) {
s->stream.avail_out -= fread(s->stream.next_out,
1, s->stream.avail_out, s->file);
}
return (int)(len - s->stream.avail_out);
}
if (s->stream.avail_in == 0 && !s->z_eof) { if (s->stream.avail_in == 0 && !s->z_eof) {
errno = 0; errno = 0;
s->stream.avail_in = fread(s->inbuf, 1, Z_BUFSIZE, s->file); s->stream.avail_in =
fread(s->inbuf, 1, Z_BUFSIZE, s->file);
if (s->stream.avail_in == 0) { if (s->stream.avail_in == 0) {
s->z_eof = 1; s->z_eof = 1;
if (ferror(s->file)) { } else if (s->stream.avail_in == (uInt)EOF) {
s->z_err = Z_ERRNO; s->stream.avail_in = 0;
break; s->z_eof = 1;
} s->z_err = Z_ERRNO;
break;
} }
s->stream.next_in = s->inbuf; s->stream.next_in = s->inbuf;
} }
s->z_err = inflate(&(s->stream), Z_NO_FLUSH); s->z_err = inflate(&(s->stream), Z_NO_FLUSH);
if (s->z_err == Z_STREAM_END) { if (s->z_err == Z_STREAM_END ||
/* Check CRC and original size */ s->z_err != Z_OK || s->z_eof) break;
s->crc = crc32(s->crc, start, (uInt)(s->stream.next_out - start));
start = s->stream.next_out;
if (getLong(s) != s->crc || getLong(s) != s->stream.total_out) {
s->z_err = Z_DATA_ERROR;
} else {
/* Check for concatenated .gz files: */
check_header(s);
if (s->z_err == Z_OK) {
inflateReset(&(s->stream));
s->crc = crc32(0L, Z_NULL, 0);
}
}
}
if (s->z_err != Z_OK || s->z_eof) break;
} }
s->crc = crc32(s->crc, start, (uInt)(s->stream.next_out - start)); len -= s->stream.avail_out;
s->crc = crc32(s->crc, buf, len);
return (int)(len - s->stream.avail_out); return (int)len;
} }
/* =========================================================================== /* ===========================================================================
@ -361,7 +293,7 @@ int gzread (file, buf, len)
*/ */
int gzwrite (file, buf, len) int gzwrite (file, buf, len)
gzFile file; gzFile file;
const voidp buf; voidp buf;
unsigned len; unsigned len;
{ {
gz_stream *s = (gz_stream*)file; gz_stream *s = (gz_stream*)file;
@ -412,7 +344,7 @@ int gzflush (file, flush)
len = Z_BUFSIZE - s->stream.avail_out; len = Z_BUFSIZE - s->stream.avail_out;
if (len != 0) { if (len != 0) {
if ((uInt)fwrite(s->outbuf, 1, len, s->file) != len) { if (fwrite(s->outbuf, 1, len, s->file) != len) {
s->z_err = Z_ERRNO; s->z_err = Z_ERRNO;
return Z_ERRNO; return Z_ERRNO;
} }
@ -448,19 +380,18 @@ local void putLong (file, x)
} }
/* =========================================================================== /* ===========================================================================
Reads a long in LSB order from the given gz_stream. Sets Reads a long in LSB order from the given buffer
*/ */
local uLong getLong (s) local uLong getLong (buf)
gz_stream *s; Bytef *buf;
{ {
uLong x = (uLong)get_byte(s); uLong x = 0;
int c; Bytef *p = buf+4;
x += ((uLong)get_byte(s))<<8; do {
x += ((uLong)get_byte(s))<<16; x <<= 8;
c = get_byte(s); x |= *--p;
if (c == EOF) s->z_err = Z_DATA_ERROR; } while (p != buf);
x += ((uLong)c)<<24;
return x; return x;
} }
@ -471,6 +402,7 @@ local uLong getLong (s)
int gzclose (file) int gzclose (file)
gzFile file; gzFile file;
{ {
uInt n;
int err; int err;
gz_stream *s = (gz_stream*)file; gz_stream *s = (gz_stream*)file;
@ -483,6 +415,25 @@ int gzclose (file)
putLong (s->file, s->crc); putLong (s->file, s->crc);
putLong (s->file, s->stream.total_in); putLong (s->file, s->stream.total_in);
} else if (s->mode == 'r' && s->z_err == Z_STREAM_END) {
/* slide CRC and original size if they are at the end of inbuf */
if ((n = s->stream.avail_in) < 8 && !s->z_eof) {
Byte *p = s->inbuf;
Bytef *q = s->stream.next_in;
while (n--) { *p++ = *q++; };
n = s->stream.avail_in;
n += fread(p, 1, 8, s->file);
s->stream.next_in = s->inbuf;
}
/* check CRC and original size */
if (n < 8 ||
getLong(s->stream.next_in) != s->crc ||
getLong(s->stream.next_in + 4) != s->stream.total_out) {
s->z_err = Z_DATA_ERROR;
}
} }
return destroy(file); return destroy(file);
} }
@ -503,14 +454,14 @@ char* gzerror (file, errnum)
if (s == NULL) { if (s == NULL) {
*errnum = Z_STREAM_ERROR; *errnum = Z_STREAM_ERROR;
return ERR_MSG(Z_STREAM_ERROR); return z_errmsg[1-Z_STREAM_ERROR];
} }
*errnum = s->z_err; *errnum = s->z_err;
if (*errnum == Z_OK) return (char*)""; if (*errnum == Z_OK) return "";
m = (char*)(*errnum == Z_ERRNO ? zstrerror(errno) : s->stream.msg); m = *errnum == Z_ERRNO ? zstrerror(errno) : s->stream.msg;
if (m == NULL || *m == '\0') m = (char*)z_errmsg[1-s->z_err]; if (m == NULL || *m == '\0') m = z_errmsg[1-s->z_err];
TRYFREE(s->msg); TRYFREE(s->msg);
s->msg = (char*)ALLOC(strlen(s->path) + strlen(m) + 3); s->msg = (char*)ALLOC(strlen(s->path) + strlen(m) + 3);

View File

@ -1,5 +1,5 @@
/* infblock.c -- interpret and process block types to last block /* infblock.c -- interpret and process block types to last block
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -81,7 +81,7 @@ uLongf *c;
s->bitb = 0; s->bitb = 0;
s->read = s->write = s->window; s->read = s->write = s->window;
if (s->checkfn != Z_NULL) if (s->checkfn != Z_NULL)
z->adler = s->check = (*s->checkfn)(0L, Z_NULL, 0); s->check = (*s->checkfn)(0L, Z_NULL, 0);
Trace((stderr, "inflate: blocks reset\n")); Trace((stderr, "inflate: blocks reset\n"));
} }
@ -172,7 +172,7 @@ int r;
case 3: /* illegal */ case 3: /* illegal */
DUMPBITS(3) DUMPBITS(3)
s->mode = BAD; s->mode = BAD;
z->msg = (char*)"invalid block type"; z->msg = "invalid block type";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
LEAVE LEAVE
} }
@ -182,7 +182,7 @@ int r;
if ((((~b) >> 16) & 0xffff) != (b & 0xffff)) if ((((~b) >> 16) & 0xffff) != (b & 0xffff))
{ {
s->mode = BAD; s->mode = BAD;
z->msg = (char*)"invalid stored block lengths"; z->msg = "invalid stored block lengths";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
LEAVE LEAVE
} }
@ -215,7 +215,7 @@ int r;
if ((t & 0x1f) > 29 || ((t >> 5) & 0x1f) > 29) if ((t & 0x1f) > 29 || ((t >> 5) & 0x1f) > 29)
{ {
s->mode = BAD; s->mode = BAD;
z->msg = (char*)"too many length or distance symbols"; z->msg = "too many length or distance symbols";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
LEAVE LEAVE
} }
@ -285,7 +285,7 @@ int r;
(c == 16 && i < 1)) (c == 16 && i < 1))
{ {
s->mode = BAD; s->mode = BAD;
z->msg = (char*)"invalid bit length repeat"; z->msg = "invalid bit length repeat";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
LEAVE LEAVE
} }
@ -383,14 +383,3 @@ uLongf *c;
Trace((stderr, "inflate: blocks freed\n")); Trace((stderr, "inflate: blocks freed\n"));
return Z_OK; return Z_OK;
} }
void inflate_set_dictionary(s, z, d, n)
inflate_blocks_statef *s;
z_stream *z;
const Bytef *d;
uInt n;
{
zmemcpy((charf *)s->window, d, n);
s->read = s->write = s->window + n;
}

View File

@ -1,5 +1,5 @@
/* infblock.h -- header to use infblock.c /* infblock.h -- header to use infblock.c
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -30,9 +30,3 @@ extern int inflate_blocks_free OF((
inflate_blocks_statef *, inflate_blocks_statef *,
z_stream *, z_stream *,
uLongf *)); /* check value on output */ uLongf *)); /* check value on output */
extern void inflate_set_dictionary OF((
inflate_blocks_statef *s,
z_stream *z,
const Bytef *d, /* dictionary */
uInt n)); /* dictionary length */

View File

@ -1,5 +1,5 @@
/* infcodes.c -- process literals and length/distance pairs /* infcodes.c -- process literals and length/distance pairs
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -58,8 +58,7 @@ struct inflate_codes_state {
inflate_codes_statef *inflate_codes_new(bl, bd, tl, td, z) inflate_codes_statef *inflate_codes_new(bl, bd, tl, td, z)
uInt bl, bd; uInt bl, bd;
inflate_huft *tl; inflate_huft *tl, *td;
inflate_huft *td; /* need separate declaration for Borland C++ */
z_stream *z; z_stream *z;
{ {
inflate_codes_statef *c; inflate_codes_statef *c;
@ -153,7 +152,7 @@ int r;
break; break;
} }
c->mode = BADCODE; /* invalid code */ c->mode = BADCODE; /* invalid code */
z->msg = (char*)"invalid literal/length code"; z->msg = "invalid literal/length code";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
LEAVE LEAVE
case LENEXT: /* i: getting length extra (have base) */ case LENEXT: /* i: getting length extra (have base) */
@ -185,7 +184,7 @@ int r;
break; break;
} }
c->mode = BADCODE; /* invalid code */ c->mode = BADCODE; /* invalid code */
z->msg = (char*)"invalid distance code"; z->msg = "invalid distance code";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
LEAVE LEAVE
case DISTEXT: /* i: getting distance extra */ case DISTEXT: /* i: getting distance extra */

View File

@ -1,5 +1,5 @@
/* infcodes.h -- header to use infcodes.c /* infcodes.h -- header to use infcodes.c
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */

View File

@ -1,5 +1,5 @@
/* inffast.c -- process literals and length/distance pairs fast /* inffast.c -- process literals and length/distance pairs fast
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -29,8 +29,7 @@ struct inflate_codes_state {int dummy;}; /* for buggy compilers */
int inflate_fast(bl, bd, tl, td, s, z) int inflate_fast(bl, bd, tl, td, s, z)
uInt bl, bd; uInt bl, bd;
inflate_huft *tl; inflate_huft *tl, *td;
inflate_huft *td; /* need separate declaration for Borland C++ */
inflate_blocks_statef *s; inflate_blocks_statef *s;
z_stream *z; z_stream *z;
{ {
@ -123,7 +122,7 @@ z_stream *z;
e = (t = t->next + ((uInt)b & inflate_mask[e]))->exop; e = (t = t->next + ((uInt)b & inflate_mask[e]))->exop;
else else
{ {
z->msg = (char*)"invalid distance code"; z->msg = "invalid distance code";
UNGRAB UNGRAB
UPDATE UPDATE
return Z_DATA_ERROR; return Z_DATA_ERROR;
@ -153,7 +152,7 @@ z_stream *z;
} }
else else
{ {
z->msg = (char*)"invalid literal/length code"; z->msg = "invalid literal/length code";
UNGRAB UNGRAB
UPDATE UPDATE
return Z_DATA_ERROR; return Z_DATA_ERROR;

View File

@ -1,5 +1,5 @@
/* inffast.h -- header to use inffast.c /* inffast.h -- header to use inffast.c
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */

View File

@ -1,5 +1,5 @@
/* inflate.c -- zlib interface to inflate modules /* inflate.c -- zlib interface to inflate modules
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -15,11 +15,6 @@ struct internal_state {
enum { enum {
METHOD, /* waiting for method byte */ METHOD, /* waiting for method byte */
FLAG, /* waiting for flag byte */ FLAG, /* waiting for flag byte */
DICT4, /* four dictionary check bytes to go */
DICT3, /* three dictionary check bytes to go */
DICT2, /* two dictionary check bytes to go */
DICT1, /* one dictionary check byte to go */
DICT0, /* waiting for inflateSetDictionary */
BLOCKS, /* decompressing blocks */ BLOCKS, /* decompressing blocks */
CHECK4, /* four check bytes to go */ CHECK4, /* four check bytes to go */
CHECK3, /* three check bytes to go */ CHECK3, /* three check bytes to go */
@ -80,16 +75,10 @@ z_stream *z;
} }
int inflateInit2_(z, w, version, stream_size) int inflateInit2(z, w)
z_stream *z; z_stream *z;
int w; int w;
const char *version;
int stream_size;
{ {
if (version == Z_NULL || version[0] != ZLIB_VERSION[0] ||
stream_size != sizeof(z_stream))
return Z_VERSION_ERROR;
/* initialize state */ /* initialize state */
if (z == Z_NULL) if (z == Z_NULL)
return Z_STREAM_ERROR; return Z_STREAM_ERROR;
@ -123,7 +112,7 @@ int stream_size;
/* create inflate_blocks state */ /* create inflate_blocks state */
if ((z->state->blocks = if ((z->state->blocks =
inflate_blocks_new(z, z->state->nowrap ? Z_NULL : adler32, (uInt)1 << w)) inflate_blocks_new(z, z->state->nowrap ? Z_NULL : adler32, 1 << w))
== Z_NULL) == Z_NULL)
{ {
inflateEnd(z); inflateEnd(z);
@ -137,12 +126,10 @@ int stream_size;
} }
int inflateInit_(z, version, stream_size) int inflateInit(z)
z_stream *z; z_stream *z;
const char *version;
int stream_size;
{ {
return inflateInit2_(z, DEF_WBITS, version, stream_size); return inflateInit2(z, DEF_WBITS);
} }
@ -156,7 +143,7 @@ int f;
int r = f; /* to avoid warning about unused f */ int r = f; /* to avoid warning about unused f */
uInt b; uInt b;
if (z == Z_NULL || z->state == Z_NULL || z->next_in == Z_NULL) if (z == Z_NULL || z->next_in == Z_NULL)
return Z_STREAM_ERROR; return Z_STREAM_ERROR;
r = Z_BUF_ERROR; r = Z_BUF_ERROR;
while (1) switch (z->state->mode) while (1) switch (z->state->mode)
@ -166,58 +153,36 @@ int f;
if (((z->state->sub.method = NEXTBYTE) & 0xf) != Z_DEFLATED) if (((z->state->sub.method = NEXTBYTE) & 0xf) != Z_DEFLATED)
{ {
z->state->mode = BAD; z->state->mode = BAD;
z->msg = (char*)"unknown compression method"; z->msg = "unknown compression method";
z->state->sub.marker = 5; /* can't try inflateSync */ z->state->sub.marker = 5; /* can't try inflateSync */
break; break;
} }
if ((z->state->sub.method >> 4) + 8 > z->state->wbits) if ((z->state->sub.method >> 4) + 8 > z->state->wbits)
{ {
z->state->mode = BAD; z->state->mode = BAD;
z->msg = (char*)"invalid window size"; z->msg = "invalid window size";
z->state->sub.marker = 5; /* can't try inflateSync */ z->state->sub.marker = 5; /* can't try inflateSync */
break; break;
} }
z->state->mode = FLAG; z->state->mode = FLAG;
case FLAG: case FLAG:
NEEDBYTE NEEDBYTE
b = NEXTBYTE; if ((b = NEXTBYTE) & 0x20)
{
z->state->mode = BAD;
z->msg = "invalid reserved bit";
z->state->sub.marker = 5; /* can't try inflateSync */
break;
}
if (((z->state->sub.method << 8) + b) % 31) if (((z->state->sub.method << 8) + b) % 31)
{ {
z->state->mode = BAD; z->state->mode = BAD;
z->msg = (char*)"incorrect header check"; z->msg = "incorrect header check";
z->state->sub.marker = 5; /* can't try inflateSync */ z->state->sub.marker = 5; /* can't try inflateSync */
break; break;
} }
Trace((stderr, "inflate: zlib header ok\n")); Trace((stderr, "inflate: zlib header ok\n"));
if (!(b & PRESET_DICT)) z->state->mode = BLOCKS;
{
z->state->mode = BLOCKS;
break;
}
z->state->mode = DICT4;
case DICT4:
NEEDBYTE
z->state->sub.check.need = (uLong)NEXTBYTE << 24;
z->state->mode = DICT3;
case DICT3:
NEEDBYTE
z->state->sub.check.need += (uLong)NEXTBYTE << 16;
z->state->mode = DICT2;
case DICT2:
NEEDBYTE
z->state->sub.check.need += (uLong)NEXTBYTE << 8;
z->state->mode = DICT1;
case DICT1:
NEEDBYTE
z->state->sub.check.need += (uLong)NEXTBYTE;
z->adler = z->state->sub.check.need;
z->state->mode = DICT0;
return Z_NEED_DICT;
case DICT0:
z->state->mode = BAD;
z->msg = (char*)"need dictionary";
z->state->sub.marker = 0; /* can try inflateSync */
return Z_STREAM_ERROR;
case BLOCKS: case BLOCKS:
r = inflate_blocks(z->state->blocks, z, r); r = inflate_blocks(z->state->blocks, z, r);
if (r == Z_DATA_ERROR) if (r == Z_DATA_ERROR)
@ -255,7 +220,7 @@ int f;
if (z->state->sub.check.was != z->state->sub.check.need) if (z->state->sub.check.was != z->state->sub.check.need)
{ {
z->state->mode = BAD; z->state->mode = BAD;
z->msg = (char*)"incorrect data check"; z->msg = "incorrect data check";
z->state->sub.marker = 5; /* can't try inflateSync */ z->state->sub.marker = 5; /* can't try inflateSync */
break; break;
} }
@ -271,29 +236,6 @@ int f;
} }
int inflateSetDictionary(z, dictionary, dictLength)
z_stream *z;
const Bytef *dictionary;
uInt dictLength;
{
uInt length = dictLength;
if (z == Z_NULL || z->state == Z_NULL || z->state->mode != DICT0)
return Z_STREAM_ERROR;
if (adler32(1L, dictionary, dictLength) != z->adler) return Z_DATA_ERROR;
z->adler = 1L;
if (length >= (1<<z->state->wbits))
{
length = (1<<z->state->wbits)-1;
dictionary += dictLength - length;
}
inflate_set_dictionary(z->state->blocks, z, dictionary, length);
z->state->mode = BLOCKS;
return Z_OK;
}
int inflateSync(z) int inflateSync(z)
z_stream *z; z_stream *z;
{ {

View File

@ -1,12 +1,12 @@
/* inftrees.c -- generate Huffman trees for efficient decoding /* inftrees.c -- generate Huffman trees for efficient decoding
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
#include "zutil.h" #include "zutil.h"
#include "inftrees.h" #include "inftrees.h"
char inflate_copyright[] = " inflate 1.0 Copyright 1995-1996 Mark Adler "; char inflate_copyright[] = " inflate 1.0 Copyright 1995 Mark Adler ";
/* /*
If you use the zlib library in a product, an acknowledgment is welcome If you use the zlib library in a product, an acknowledgment is welcome
in the documentation of your product. If for some reason you cannot in the documentation of your product. If for some reason you cannot
@ -38,18 +38,18 @@ local voidpf falloc OF((
uInt)); /* size of item */ uInt)); /* size of item */
/* Tables for deflate from PKZIP's appnote.txt. */ /* Tables for deflate from PKZIP's appnote.txt. */
local uInt cplens[31] = { /* Copy lengths for literal codes 257..285 */ local uInt cplens[] = { /* Copy lengths for literal codes 257..285 */
3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 15, 17, 19, 23, 27, 31, 3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 15, 17, 19, 23, 27, 31,
35, 43, 51, 59, 67, 83, 99, 115, 131, 163, 195, 227, 258, 0, 0}; 35, 43, 51, 59, 67, 83, 99, 115, 131, 163, 195, 227, 258, 0, 0};
/* actually lengths - 2; also see note #13 above about 258 */ /* actually lengths - 2; also see note #13 above about 258 */
local uInt cplext[31] = { /* Extra bits for literal codes 257..285 */ local uInt cplext[] = { /* Extra bits for literal codes 257..285 */
0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 2,
3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0, 192, 192}; /* 192==invalid */ 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0, 192, 192}; /* 192==invalid */
local uInt cpdist[30] = { /* Copy offsets for distance codes 0..29 */ local uInt cpdist[] = { /* Copy offsets for distance codes 0..29 */
1, 2, 3, 4, 5, 7, 9, 13, 17, 25, 33, 49, 65, 97, 129, 193, 1, 2, 3, 4, 5, 7, 9, 13, 17, 25, 33, 49, 65, 97, 129, 193,
257, 385, 513, 769, 1025, 1537, 2049, 3073, 4097, 6145, 257, 385, 513, 769, 1025, 1537, 2049, 3073, 4097, 6145,
8193, 12289, 16385, 24577}; 8193, 12289, 16385, 24577};
local uInt cpdext[30] = { /* Extra bits for distance codes */ local uInt cpdext[] = { /* Extra bits for distance codes */
0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6, 0, 0, 0, 0, 1, 1, 2, 2, 3, 3, 4, 4, 5, 5, 6, 6,
7, 7, 8, 8, 9, 9, 10, 10, 11, 11, 7, 7, 8, 8, 9, 9, 10, 10, 11, 11,
12, 12, 13, 13}; 12, 12, 13, 13};
@ -307,11 +307,11 @@ z_stream *z; /* for zfree function */
r = huft_build(c, 19, 19, (uIntf*)Z_NULL, (uIntf*)Z_NULL, tb, bb, z); r = huft_build(c, 19, 19, (uIntf*)Z_NULL, (uIntf*)Z_NULL, tb, bb, z);
if (r == Z_DATA_ERROR) if (r == Z_DATA_ERROR)
z->msg = (char*)"oversubscribed dynamic bit lengths tree"; z->msg = "oversubscribed dynamic bit lengths tree";
else if (r == Z_BUF_ERROR) else if (r == Z_BUF_ERROR)
{ {
inflate_trees_free(*tb, z); inflate_trees_free(*tb, z);
z->msg = (char*)"incomplete dynamic bit lengths tree"; z->msg = "incomplete dynamic bit lengths tree";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
} }
return r; return r;
@ -334,11 +334,11 @@ z_stream *z; /* for zfree function */
if ((r = huft_build(c, nl, 257, cplens, cplext, tl, bl, z)) != Z_OK) if ((r = huft_build(c, nl, 257, cplens, cplext, tl, bl, z)) != Z_OK)
{ {
if (r == Z_DATA_ERROR) if (r == Z_DATA_ERROR)
z->msg = (char*)"oversubscribed literal/length tree"; z->msg = "oversubscribed literal/length tree";
else if (r == Z_BUF_ERROR) else if (r == Z_BUF_ERROR)
{ {
inflate_trees_free(*tl, z); inflate_trees_free(*tl, z);
z->msg = (char*)"incomplete literal/length tree"; z->msg = "incomplete literal/length tree";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
} }
return r; return r;
@ -348,14 +348,14 @@ z_stream *z; /* for zfree function */
if ((r = huft_build(c + nl, nd, 0, cpdist, cpdext, td, bd, z)) != Z_OK) if ((r = huft_build(c + nl, nd, 0, cpdist, cpdext, td, bd, z)) != Z_OK)
{ {
if (r == Z_DATA_ERROR) if (r == Z_DATA_ERROR)
z->msg = (char*)"oversubscribed literal/length tree"; z->msg = "oversubscribed literal/length tree";
else if (r == Z_BUF_ERROR) { else if (r == Z_BUF_ERROR) {
#ifdef PKZIP_BUG_WORKAROUND #ifdef PKZIP_BUG_WORKAROUND
r = Z_OK; r = Z_OK;
} }
#else #else
inflate_trees_free(*td, z); inflate_trees_free(*td, z);
z->msg = (char*)"incomplete literal/length tree"; z->msg = "incomplete literal/length tree";
r = Z_DATA_ERROR; r = Z_DATA_ERROR;
} }
inflate_trees_free(*tl, z); inflate_trees_free(*tl, z);
@ -385,7 +385,7 @@ uInt s; /* size of item */
{ {
Assert(s == sizeof(inflate_huft) && n <= *(intf *)q, Assert(s == sizeof(inflate_huft) && n <= *(intf *)q,
"inflate_trees falloc overflow"); "inflate_trees falloc overflow");
*(intf *)q -= n+s-s; /* s-s to avoid warning */ *(intf *)q -= n;
return (voidpf)(fixed_mem + *(intf *)q); return (voidpf)(fixed_mem + *(intf *)q);
} }

View File

@ -1,5 +1,5 @@
/* inftrees.h -- header to use inftrees.c /* inftrees.h -- header to use inftrees.c
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */

View File

@ -1,5 +1,5 @@
/* inflate_util.c -- data and routines common to blocks and codes /* inflate_util.c -- data and routines common to blocks and codes
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -12,7 +12,7 @@
struct inflate_codes_state {int dummy;}; /* for buggy compilers */ struct inflate_codes_state {int dummy;}; /* for buggy compilers */
/* And'ing with mask[n] masks the lower n bits */ /* And'ing with mask[n] masks the lower n bits */
uInt inflate_mask[17] = { uInt inflate_mask[] = {
0x0000, 0x0000,
0x0001, 0x0003, 0x0007, 0x000f, 0x001f, 0x003f, 0x007f, 0x00ff, 0x0001, 0x0003, 0x0007, 0x000f, 0x001f, 0x003f, 0x007f, 0x00ff,
0x01ff, 0x03ff, 0x07ff, 0x0fff, 0x1fff, 0x3fff, 0x7fff, 0xffff 0x01ff, 0x03ff, 0x07ff, 0x0fff, 0x1fff, 0x3fff, 0x7fff, 0xffff
@ -43,7 +43,7 @@ int r;
/* update check information */ /* update check information */
if (s->checkfn != Z_NULL) if (s->checkfn != Z_NULL)
z->adler = s->check = (*s->checkfn)(s->check, q, n); s->check = (*s->checkfn)(s->check, q, n);
/* copy as far as end of window */ /* copy as far as end of window */
zmemcpy(p, q, n); zmemcpy(p, q, n);
@ -69,7 +69,7 @@ int r;
/* update check information */ /* update check information */
if (s->checkfn != Z_NULL) if (s->checkfn != Z_NULL)
z->adler = s->check = (*s->checkfn)(s->check, q, n); s->check = (*s->checkfn)(s->check, q, n);
/* copy */ /* copy */
zmemcpy(p, q, n); zmemcpy(p, q, n);

View File

@ -1,5 +1,5 @@
/* infutil.h -- types and macros common to blocks and codes /* infutil.h -- types and macros common to blocks and codes
* Copyright (C) 1995-1996 Mark Adler * Copyright (C) 1995 Mark Adler
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -8,10 +8,11 @@
subject to change. Applications should only use zlib.h. subject to change. Applications should only use zlib.h.
*/ */
#ifndef _INFUTIL_H /* inflate blocks semi-private state */
#define _INFUTIL_H struct inflate_blocks_state {
typedef enum { /* mode */
enum {
TYPE, /* get type bits (3, including end bit) */ TYPE, /* get type bits (3, including end bit) */
LENS, /* get lengths for stored */ LENS, /* get lengths for stored */
STORED, /* processing stored block */ STORED, /* processing stored block */
@ -22,13 +23,7 @@ typedef enum {
DRY, /* output remaining window bytes */ DRY, /* output remaining window bytes */
DONE, /* finished last block, done */ DONE, /* finished last block, done */
BAD} /* got a data error--stuck here */ BAD} /* got a data error--stuck here */
inflate_block_mode; mode; /* current inflate_block mode */
/* inflate blocks semi-private state */
struct inflate_blocks_state {
/* mode */
inflate_block_mode mode; /* current inflate_block mode */
/* mode dependent information */ /* mode dependent information */
union { union {
@ -76,16 +71,16 @@ struct inflate_blocks_state {
#define DUMPBITS(j) {b>>=(j);k-=(j);} #define DUMPBITS(j) {b>>=(j);k-=(j);}
/* output bytes */ /* output bytes */
#define WAVAIL (uInt)(q<s->read?s->read-q-1:s->end-q) #define WAVAIL (uInt)(q<s->read?s->read-q-1:s->end-q)
#define LOADOUT {q=s->write;m=(uInt)WAVAIL;} #define LOADOUT {q=s->write;m=WAVAIL;}
#define WRAP {if(q==s->end&&s->read!=s->window){q=s->window;m=(uInt)WAVAIL;}} #define WRAP {if(q==s->end&&s->read!=s->window){q=s->window;m=WAVAIL;}}
#define FLUSH {UPDOUT r=inflate_flush(s,z,r); LOADOUT} #define FLUSH {UPDOUT r=inflate_flush(s,z,r); LOADOUT}
#define NEEDOUT {if(m==0){WRAP if(m==0){FLUSH WRAP if(m==0) LEAVE}}r=Z_OK;} #define NEEDOUT {if(m==0){WRAP if(m==0){FLUSH WRAP if(m==0) LEAVE}}r=Z_OK;}
#define OUTBYTE(a) {*q++=(Byte)(a);m--;} #define OUTBYTE(a) {*q++=(Byte)(a);m--;}
/* load local pointers */ /* load local pointers */
#define LOAD {LOADIN LOADOUT} #define LOAD {LOADIN LOADOUT}
/* masks for lower bits (size given to avoid silly warnings with Visual C++) */ /* masks for lower bits */
extern uInt inflate_mask[17]; extern uInt inflate_mask[];
/* copy as much as possible from the sliding window to the output area */ /* copy as much as possible from the sliding window to the output area */
extern int inflate_flush OF(( extern int inflate_flush OF((
@ -94,5 +89,3 @@ extern int inflate_flush OF((
int)); int));
struct internal_state {int dummy;}; /* for buggy compilers */ struct internal_state {int dummy;}; /* for buggy compilers */
#endif

View File

@ -1,5 +1,5 @@
/* minigzip.c -- simulate gzip using the zlib compression library /* minigzip.c -- simulate gzip using the zlib compression library
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -52,7 +52,7 @@ extern int unlink OF((const char *));
char *prog; char *prog;
void error OF((const char *msg)); void error OF((char *msg));
void gz_compress OF((FILE *in, gzFile out)); void gz_compress OF((FILE *in, gzFile out));
void gz_uncompress OF((gzFile in, FILE *out)); void gz_uncompress OF((gzFile in, FILE *out));
void file_compress OF((char *file)); void file_compress OF((char *file));
@ -63,7 +63,7 @@ int main OF((int argc, char *argv[]));
* Display error message and exit * Display error message and exit
*/ */
void error(msg) void error(msg)
const char *msg; char *msg;
{ {
fprintf(stderr, "%s: %s\n", prog, msg); fprintf(stderr, "%s: %s\n", prog, msg);
exit(1); exit(1);
@ -88,7 +88,7 @@ void gz_compress(in, out)
} }
if (len == 0) break; if (len == 0) break;
if (gzwrite(out, buf, (unsigned)len) != len) error(gzerror(out, &err)); if (gzwrite(out, buf, len) != len) error(gzerror(out, &err));
} }
fclose(in); fclose(in);
if (gzclose(out) != Z_OK) error("failed gzclose"); if (gzclose(out) != Z_OK) error("failed gzclose");
@ -110,9 +110,7 @@ void gz_uncompress(in, out)
if (len < 0) error (gzerror(in, &err)); if (len < 0) error (gzerror(in, &err));
if (len == 0) break; if (len == 0) break;
if ((int)fwrite(buf, 1, (unsigned)len, out) != len) { if (fwrite(buf, 1, len, out) != (uInt)len) error("failed fwrite");
error("failed fwrite");
}
} }
if (fclose(out)) error("failed fclose"); if (fclose(out)) error("failed fclose");

34
trees.c
View File

@ -1,5 +1,5 @@
/* trees.c -- output deflated data using Huffman coding /* trees.c -- output deflated data using Huffman coding
* Copyright (C) 1995-1996 Jean-loup Gailly * Copyright (C) 1995 Jean-loup Gailly
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -83,7 +83,7 @@ local uch bl_order[BL_CODES]
local ct_data static_ltree[L_CODES+2]; local ct_data static_ltree[L_CODES+2];
/* The static literal tree. Since the bit lengths are imposed, there is no /* The static literal tree. Since the bit lengths are imposed, there is no
* need for the L_CODES extra codes used during heap construction. However * need for the L_CODES extra codes used during heap construction. However
* The codes 286 and 287 are needed to build a canonical tree (see _tr_init * The codes 286 and 287 are needed to build a canonical tree (see tr_init
* below). * below).
*/ */
@ -292,7 +292,7 @@ local void tr_static_init()
/* The static distance tree is trivial: */ /* The static distance tree is trivial: */
for (n = 0; n < D_CODES; n++) { for (n = 0; n < D_CODES; n++) {
static_dtree[n].Len = 5; static_dtree[n].Len = 5;
static_dtree[n].Code = bi_reverse((unsigned)n, 5); static_dtree[n].Code = bi_reverse(n, 5);
} }
static_init_done = 1; static_init_done = 1;
} }
@ -300,7 +300,7 @@ local void tr_static_init()
/* =========================================================================== /* ===========================================================================
* Initialize the tree data structures for a new zlib stream. * Initialize the tree data structures for a new zlib stream.
*/ */
void _tr_init(s) void tr_init(s)
deflate_state *s; deflate_state *s;
{ {
tr_static_init(); tr_static_init();
@ -785,14 +785,14 @@ local void send_all_trees(s, lcodes, dcodes, blcodes)
/* =========================================================================== /* ===========================================================================
* Send a stored block * Send a stored block
*/ */
void _tr_stored_block(s, buf, stored_len, eof) void tr_stored_block(s, buf, stored_len, eof)
deflate_state *s; deflate_state *s;
charf *buf; /* input block */ charf *buf; /* input block */
ulg stored_len; /* length of input block */ ulg stored_len; /* length of input block */
int eof; /* true if this is the last block for a file */ int eof; /* true if this is the last block for a file */
{ {
send_bits(s, (STORED_BLOCK<<1)+eof, 3); /* send block type */ send_bits(s, (STORED_BLOCK<<1)+eof, 3); /* send block type */
s->compressed_len = (s->compressed_len + 3 + 7) & (ulg)~7L; s->compressed_len = (s->compressed_len + 3 + 7) & ~7L;
s->compressed_len += (stored_len + 4) << 3; s->compressed_len += (stored_len + 4) << 3;
copy_block(s, buf, (unsigned)stored_len, 1); /* with header */ copy_block(s, buf, (unsigned)stored_len, 1); /* with header */
@ -809,7 +809,7 @@ void _tr_stored_block(s, buf, stored_len, eof)
* To simplify the code, we assume the worst case of last real code encoded * To simplify the code, we assume the worst case of last real code encoded
* on one bit only. * on one bit only.
*/ */
void _tr_align(s) void tr_align(s)
deflate_state *s; deflate_state *s;
{ {
send_bits(s, STATIC_TREES<<1, 3); send_bits(s, STATIC_TREES<<1, 3);
@ -835,20 +835,20 @@ void _tr_align(s)
* trees or store, and output the encoded block to the zip file. This function * trees or store, and output the encoded block to the zip file. This function
* returns the total compressed length for the file so far. * returns the total compressed length for the file so far.
*/ */
ulg _tr_flush_block(s, buf, stored_len, eof) ulg tr_flush_block(s, buf, stored_len, eof)
deflate_state *s; deflate_state *s;
charf *buf; /* input block, or NULL if too old */ charf *buf; /* input block, or NULL if too old */
ulg stored_len; /* length of input block */ ulg stored_len; /* length of input block */
int eof; /* true if this is the last block for a file */ int eof; /* true if this is the last block for a file */
{ {
ulg opt_lenb, static_lenb; /* opt_len and static_len in bytes */ ulg opt_lenb, static_lenb; /* opt_len and static_len in bytes */
int max_blindex = 0; /* index of last bit length code of non zero freq */ int max_blindex; /* index of last bit length code of non zero freq */
/* Build the Huffman trees unless a stored block is forced */ /* Build the Huffman trees unless a stored block is forced */
if (s->level > 0) { if (s->level > 0) {
/* Check if the file is ascii or binary */ /* Check if the file is ascii or binary */
if (s->data_type == Z_UNKNOWN) set_data_type(s); if (s->data_type == UNKNOWN) set_data_type(s);
/* Construct the literal and distance trees */ /* Construct the literal and distance trees */
build_tree(s, (tree_desc *)(&(s->l_desc))); build_tree(s, (tree_desc *)(&(s->l_desc)));
@ -879,7 +879,7 @@ ulg _tr_flush_block(s, buf, stored_len, eof)
} else { } else {
Assert(buf != (char*)0, "lost buf"); Assert(buf != (char*)0, "lost buf");
opt_lenb = static_lenb = stored_len + 5; /* force a stored block */ opt_lenb = stored_len + 5; /* force a stored block */
} }
/* If compression failed and this is the first and last block, /* If compression failed and this is the first and last block,
@ -913,7 +913,7 @@ ulg _tr_flush_block(s, buf, stored_len, eof)
* successful. If LIT_BUFSIZE <= WSIZE, it is never too late to * successful. If LIT_BUFSIZE <= WSIZE, it is never too late to
* transform a block into a stored block. * transform a block into a stored block.
*/ */
_tr_stored_block(s, buf, stored_len, eof); tr_stored_block(s, buf, stored_len, eof);
#ifdef FORCE_STATIC #ifdef FORCE_STATIC
} else if (static_lenb >= 0) { /* force static trees */ } else if (static_lenb >= 0) { /* force static trees */
@ -947,10 +947,10 @@ ulg _tr_flush_block(s, buf, stored_len, eof)
* Save the match info and tally the frequency counts. Return true if * Save the match info and tally the frequency counts. Return true if
* the current block must be flushed. * the current block must be flushed.
*/ */
int _tr_tally (s, dist, lc) int tr_tally (s, dist, lc)
deflate_state *s; deflate_state *s;
unsigned dist; /* distance of matched string */ int dist; /* distance of matched string */
unsigned lc; /* match length-MIN_MATCH or unmatched char (if dist==0) */ int lc; /* match length-MIN_MATCH or unmatched char (if dist==0) */
{ {
s->d_buf[s->last_lit] = (ush)dist; s->d_buf[s->last_lit] = (ush)dist;
s->l_buf[s->last_lit++] = (uch)lc; s->l_buf[s->last_lit++] = (uch)lc;
@ -963,7 +963,7 @@ int _tr_tally (s, dist, lc)
dist--; /* dist = match distance - 1 */ dist--; /* dist = match distance - 1 */
Assert((ush)dist < (ush)MAX_DIST(s) && Assert((ush)dist < (ush)MAX_DIST(s) &&
(ush)lc <= (ush)(MAX_MATCH-MIN_MATCH) && (ush)lc <= (ush)(MAX_MATCH-MIN_MATCH) &&
(ush)d_code(dist) < (ush)D_CODES, "_tr_tally: bad match"); (ush)d_code(dist) < (ush)D_CODES, "tr_tally: bad match");
s->dyn_ltree[length_code[lc]+LITERALS+1].Freq++; s->dyn_ltree[length_code[lc]+LITERALS+1].Freq++;
s->dyn_dtree[d_code(dist)].Freq++; s->dyn_dtree[d_code(dist)].Freq++;
@ -1057,7 +1057,7 @@ local void set_data_type(s)
while (n < 7) bin_freq += s->dyn_ltree[n++].Freq; while (n < 7) bin_freq += s->dyn_ltree[n++].Freq;
while (n < 128) ascii_freq += s->dyn_ltree[n++].Freq; while (n < 128) ascii_freq += s->dyn_ltree[n++].Freq;
while (n < LITERALS) bin_freq += s->dyn_ltree[n++].Freq; while (n < LITERALS) bin_freq += s->dyn_ltree[n++].Freq;
s->data_type = (Byte)(bin_freq > (ascii_freq >> 2) ? Z_BINARY : Z_ASCII); s->data_type = (Byte)(bin_freq > (ascii_freq >> 2) ? BINARY : ASCII);
} }
/* =========================================================================== /* ===========================================================================

View File

@ -1,5 +1,5 @@
/* uncompr.c -- decompress a memory buffer /* uncompr.c -- decompress a memory buffer
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -25,13 +25,13 @@
int uncompress (dest, destLen, source, sourceLen) int uncompress (dest, destLen, source, sourceLen)
Bytef *dest; Bytef *dest;
uLongf *destLen; uLongf *destLen;
const Bytef *source; Bytef *source;
uLong sourceLen; uLong sourceLen;
{ {
z_stream stream; z_stream stream;
int err; int err;
stream.next_in = (Bytef*)source; stream.next_in = source;
stream.avail_in = (uInt)sourceLen; stream.avail_in = (uInt)sourceLen;
/* Check for source > 64K on 16-bit machine: */ /* Check for source > 64K on 16-bit machine: */
if ((uLong)stream.avail_in != sourceLen) return Z_BUF_ERROR; if ((uLong)stream.avail_in != sourceLen) return Z_BUF_ERROR;

57
zconf.h
View File

@ -1,5 +1,5 @@
/* zconf.h -- configuration of the zlib compression library /* zconf.h -- configuration of the zlib compression library
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -9,40 +9,11 @@
#define _ZCONF_H #define _ZCONF_H
/* /*
* People prefering a unique prefix for all types and library functions The library does not install any signal handler. It is recommended to
* should compile with -DZ_PREFIX add at least a handler for SIGSEGV when decompressing; the library checks
the consistency of the input data whenever possible but may go nuts
for some forms of corrupted input.
*/ */
#ifdef Z_PREFIX
# define deflateInit_ z_deflateInit_
# define deflate z_deflate
# define deflateEnd z_deflateEnd
# define inflateInit_ z_inflateInit_
# define inflate z_inflate
# define inflateEnd z_inflateEnd
# define deflateInit2_ z_deflateInit2_
# define deflateCopy z_deflateCopy
# define deflateReset z_deflateReset
# define deflateParams z_deflateParams
# define inflateInit2_ z_inflateInit2_
# define inflateSync z_inflateSync
# define inflateReset z_inflateReset
# define compress z_compress
# define uncompress z_uncompress
# define adler32 z_adler32
# define crc32 z_crc32
# define get_crc_table z_get_crc_table
# define Byte z_Byte
# define uInt z_uInt
# define uLong z_uLong
# define Bytef z_Bytef
# define charf z_charf
# define intf z_intf
# define uIntf z_uIntf
# define uLongf z_uLongf
# define voidpf z_voidpf
# define voidp z_voidp
#endif
#if (defined(_WIN32) || defined(__WIN32__)) && !defined(WIN32) #if (defined(_WIN32) || defined(__WIN32__)) && !defined(WIN32)
# define WIN32 # define WIN32
@ -78,7 +49,6 @@
#ifdef __MWERKS__ /* Metrowerks CodeWarrior declares fileno() in unix.h */ #ifdef __MWERKS__ /* Metrowerks CodeWarrior declares fileno() in unix.h */
# include <unix.h> # include <unix.h>
# define Byte _Byte /* Byte already used on Mac */
#endif #endif
/* Maximum value for memLevel in deflateInit2 */ /* Maximum value for memLevel in deflateInit2 */
@ -125,7 +95,6 @@
* just define FAR to be empty. * just define FAR to be empty.
*/ */
#if defined(M_I86SM) || defined(M_I86MM) /* MSC small or medium model */ #if defined(M_I86SM) || defined(M_I86MM) /* MSC small or medium model */
# define SMALL_MEDIUM
# ifdef _MSC_VER # ifdef _MSC_VER
# define FAR __far # define FAR __far
# else # else
@ -133,26 +102,20 @@
# endif # endif
#endif #endif
#if defined(__BORLANDC__) && (defined(__SMALL__) || defined(__MEDIUM__)) #if defined(__BORLANDC__) && (defined(__SMALL__) || defined(__MEDIUM__))
# define SMALL_MEDIUM # define FAR _far /* completely untested, just a best guess */
# define FAR __far
#endif #endif
#ifndef FAR #ifndef FAR
# define FAR # define FAR
#endif #endif
/* The Watcom compiler defines M_I86SM and __SMALL__ even in 32 bit mode */
#if defined(__WATCOMC__) && defined(__386__)
# undef FAR
# undef SMALL_MEDIUM
#endif
typedef unsigned char Byte; /* 8 bits */ typedef unsigned char Byte; /* 8 bits */
typedef unsigned int uInt; /* 16 bits or more */ typedef unsigned int uInt; /* 16 bits or more */
typedef unsigned long uLong; /* 32 bits or more */ typedef unsigned long uLong; /* 32 bits or more */
typedef Byte FAR Bytef; typedef Byte FAR Bytef;
typedef char FAR charf; typedef char FAR charf;
typedef int FAR intf; typedef int FAR intf;
typedef uInt FAR uIntf; typedef uInt FAR uIntf;
typedef uLong FAR uLongf; typedef uLong FAR uLongf;
#ifdef STDC #ifdef STDC

187
zlib.h
View File

@ -1,5 +1,5 @@
/* zlib.h -- interface of the 'zlib' general purpose compression library /* zlib.h -- interface of the 'zlib' general purpose compression library
version 1.0, Jan 27th, 1996. version 1.0, Jan 14th, 1996.
Copyright (C) 1995-1996 Jean-loup Gailly and Mark Adler Copyright (C) 1995-1996 Jean-loup Gailly and Mark Adler
@ -51,11 +51,6 @@ extern "C" {
repeated calls of the compression function. In the latter case, the repeated calls of the compression function. In the latter case, the
application must provide more input and/or consume the output application must provide more input and/or consume the output
(providing more output space) before each call. (providing more output space) before each call.
The library does not install any signal handler. It is recommended to
add at least a handler for SIGSEGV when decompressing; the library checks
the consistency of the input data whenever possible but may go nuts
for some forms of corrupted input.
*/ */
typedef voidpf (*alloc_func) OF((voidpf opaque, uInt items, uInt size)); typedef voidpf (*alloc_func) OF((voidpf opaque, uInt items, uInt size));
@ -79,9 +74,8 @@ typedef struct z_stream_s {
free_func zfree; /* used to free the internal state */ free_func zfree; /* used to free the internal state */
voidpf opaque; /* private data object passed to zalloc and zfree */ voidpf opaque; /* private data object passed to zalloc and zfree */
int data_type; /* best guess about the data type: ascii or binary */ Byte data_type; /* best guess about the data type: ascii or binary */
uLong adler; /* adler32 value of the uncompressed data */
uLong reserved; /* reserved for future use */
} z_stream; } z_stream;
/* /*
@ -124,16 +118,12 @@ typedef struct z_stream_s {
#define Z_OK 0 #define Z_OK 0
#define Z_STREAM_END 1 #define Z_STREAM_END 1
#define Z_NEED_DICT 2
#define Z_ERRNO (-1) #define Z_ERRNO (-1)
#define Z_STREAM_ERROR (-2) #define Z_STREAM_ERROR (-2)
#define Z_DATA_ERROR (-3) #define Z_DATA_ERROR (-3)
#define Z_MEM_ERROR (-4) #define Z_MEM_ERROR (-4)
#define Z_BUF_ERROR (-5) #define Z_BUF_ERROR (-5)
#define Z_VERSION_ERROR (-6) /* error codes for the compression/decompression functions */
/* Return codes for the compression/decompression functions. Negative
* values are errors, positive values are used for special but normal events.
*/
#define Z_NO_COMPRESSION 0 #define Z_NO_COMPRESSION 0
#define Z_BEST_SPEED 1 #define Z_BEST_SPEED 1
@ -144,19 +134,18 @@ typedef struct z_stream_s {
#define Z_FILTERED 1 #define Z_FILTERED 1
#define Z_HUFFMAN_ONLY 2 #define Z_HUFFMAN_ONLY 2
#define Z_DEFAULT_STRATEGY 0 #define Z_DEFAULT_STRATEGY 0
/* compression strategy; see deflateInit2() below for details */
#define Z_BINARY 0 #define Z_BINARY 0
#define Z_ASCII 1 #define Z_ASCII 1
#define Z_UNKNOWN 2 #define Z_UNKNOWN 2
/* Possible values of the data_type field */ /* Used to set the data_type field */
#define Z_DEFLATED 8 #define Z_DEFLATED 8
/* The deflate compression method (the only one supported in this version) */ /* The deflate compression method (the only one supported in this version) */
#define Z_NULL 0 /* for initializing zalloc, zfree, opaque */ #define Z_NULL 0 /* for initializing zalloc, zfree, opaque */
extern const char *zlib_version; extern char *zlib_version;
/* The application can compare zlib_version and ZLIB_VERSION for consistency. /* The application can compare zlib_version and ZLIB_VERSION for consistency.
If the first character differs, the library code actually used is If the first character differs, the library code actually used is
not compatible with the zlib.h header file used by the application. not compatible with the zlib.h header file used by the application.
@ -164,9 +153,8 @@ extern const char *zlib_version;
/* basic functions */ /* basic functions */
/*
extern int deflateInit OF((z_stream *strm, int level)); extern int deflateInit OF((z_stream *strm, int level));
/*
Initializes the internal stream state for compression. The fields Initializes the internal stream state for compression. The fields
zalloc, zfree and opaque must be initialized before by the caller. zalloc, zfree and opaque must be initialized before by the caller.
If zalloc and zfree are set to Z_NULL, deflateInit updates them to If zalloc and zfree are set to Z_NULL, deflateInit updates them to
@ -179,9 +167,7 @@ extern int deflateInit OF((z_stream *strm, int level));
compression (currently equivalent to level 6). compression (currently equivalent to level 6).
deflateInit returns Z_OK if success, Z_MEM_ERROR if there was not deflateInit returns Z_OK if success, Z_MEM_ERROR if there was not
enough memory, Z_STREAM_ERROR if level is not a valid compression level, enough memory, Z_STREAM_ERROR if level is not a valid compression level.
Z_VERSION_ERROR if the zlib library version (zlib_version) is incompatible
with the version assumed by the caller (ZLIB_VERSION).
msg is set to null if there is no error message. deflateInit does not msg is set to null if there is no error message. deflateInit does not
perform any compression: this will be done by deflate(). perform any compression: this will be done by deflate().
*/ */
@ -261,26 +247,22 @@ extern int deflateEnd OF((z_stream *strm));
pending output. pending output.
deflateEnd returns Z_OK if success, Z_STREAM_ERROR if the deflateEnd returns Z_OK if success, Z_STREAM_ERROR if the
stream state was inconsistent, Z_DATA_ERROR if the stream was freed stream state was inconsistent. In the error case, msg may be set
prematurely (some input or output was discarded). In the error case, but then points to a static string (which must not be deallocated).
msg may be set but then points to a static string (which must not be
deallocated).
*/ */
/*
extern int inflateInit OF((z_stream *strm)); extern int inflateInit OF((z_stream *strm));
/*
Initializes the internal stream state for decompression. The fields Initializes the internal stream state for decompression. The fields
zalloc, zfree and opaque must be initialized before by the caller. If zalloc, zfree and opaque must be initialized before by the caller. If
zalloc and zfree are set to Z_NULL, inflateInit updates them to use default zalloc and zfree are set to Z_NULL, inflateInit updates them to use default
allocation functions. allocation functions.
inflateInit returns Z_OK if success, Z_MEM_ERROR if there was not inflateInit returns Z_OK if success, Z_MEM_ERROR if there was not
enough memory, Z_VERSION_ERROR if the zlib library version is incompatible enough memory. msg is set to null if there is no error message.
with the version assumed by the caller. msg is set to null if there is no inflateInit does not perform any decompression: this will be done by
error message. inflateInit does not perform any decompression: this will be inflate().
done by inflate().
*/ */
@ -324,15 +306,12 @@ extern int inflate OF((z_stream *strm, int flush));
inflate() returns Z_OK if some progress has been made (more input inflate() returns Z_OK if some progress has been made (more input
processed or more output produced), Z_STREAM_END if the end of the processed or more output produced), Z_STREAM_END if the end of the
compressed data has been reached and all uncompressed output has been compressed data has been reached and all uncompressed output has been
produced, Z_NEED_DICT if a preset dictionary is needed at this point (see produced, Z_DATA_ERROR if the input data was corrupted, Z_STREAM_ERROR if
inflateSetDictionary below), Z_DATA_ERROR if the input data was corrupted, the stream structure was inconsistent (for example if next_in or next_out
Z_STREAM_ERROR if the stream structure was inconsistent (for example if was NULL), Z_MEM_ERROR if there was not enough memory, Z_BUF_ERROR if no
next_in or next_out was NULL), Z_MEM_ERROR if there was not enough memory, progress is possible or if there was not enough room in the output buffer
Z_BUF_ERROR if no progress is possible or if there was not enough room in when Z_FINISH is used. In the Z_DATA_ERROR case, the application may then
the output buffer when Z_FINISH is used. In the Z_DATA_ERROR case, the call inflateSync to look for a good compression block.
application may then call inflateSync to look for a good compression block.
In the Z_NEED_DICT case, strm->adler is set to the Adler32 value of the
dictionary chosen by the compressor.
*/ */
@ -347,20 +326,19 @@ extern int inflateEnd OF((z_stream *strm));
static string (which must not be deallocated). static string (which must not be deallocated).
*/ */
/* Advanced functions */ /* advanced functions */
/* /*
The following functions are needed only in some special applications. The following functions are needed only in some special applications.
*/ */
/*
extern int deflateInit2 OF((z_stream *strm, extern int deflateInit2 OF((z_stream *strm,
int level, int level,
int method, int method,
int windowBits, int windowBits,
int memLevel, int memLevel,
int strategy)); int strategy));
/*
This is another version of deflateInit with more compression options. The This is another version of deflateInit with more compression options. The
fields next_in, zalloc, zfree and opaque must be initialized before by fields next_in, zalloc, zfree and opaque must be initialized before by
the caller. the caller.
@ -375,22 +353,20 @@ extern int deflateInit2 OF((z_stream *strm,
values of this parameter result in better compression at the expense of values of this parameter result in better compression at the expense of
memory usage. The default value is 15 if deflateInit is used instead. memory usage. The default value is 15 if deflateInit is used instead.
The memLevel parameter specifies how much memory should be allocated The memLevel parameter specifies how much memory should be allocated
for the internal compression state. memLevel=1 uses minimum memory but for the internal compression state. memLevel=1 uses minimum memory but
is slow and reduces compression ratio; memLevel=9 uses maximum memory is slow and reduces compression ratio; memLevel=9 uses maximum memory
for optimal speed. The default value is 8. See zconf.h for total memory for optimal speed. The default value is 8. See zconf.h for total memory
usage as a function of windowBits and memLevel. usage as a function of windowBits and memLevel.
The strategy parameter is used to tune the compression algorithm. Use the The strategy parameter is used to tune the compression algorithm. Use
value Z_DEFAULT_STRATEGY for normal data, Z_FILTERED for data produced by a the value Z_DEFAULT_STRATEGY for normal data, Z_FILTERED for data
filter (or predictor), or Z_HUFFMAN_ONLY to force Huffman encoding only (no produced by a filter (or predictor), or Z_HUFFMAN_ONLY to force Huffman
string match). Filtered data consists mostly of small values with a encoding only (no string match). Filtered data consists mostly of small
somewhat random distribution. In this case, the compression algorithm is values with a somewhat random distribution. In this case, the
tuned to compress them better. The effect of Z_FILTERED is to force more compression algorithm is tuned to compress them better. The strategy
Huffman coding and less string matching; it is somewhat intermediate parameter only affects the compression ratio but not the correctness of
between Z_DEFAULT and Z_HUFFMAN_ONLY. The strategy parameter only affects the compressed output even if it is not set appropriately.
the compression ratio but not the correctness of the compressed output even
if it is not set appropriately.
If next_in is not null, the library will use this buffer to hold also If next_in is not null, the library will use this buffer to hold also
some history information; the buffer must either hold the entire input some history information; the buffer must either hold the entire input
@ -409,38 +385,9 @@ extern int deflateInit2 OF((z_stream *strm,
not enough memory, Z_STREAM_ERROR if a parameter is invalid (such as not enough memory, Z_STREAM_ERROR if a parameter is invalid (such as
an invalid method). msg is set to null if there is no error message. an invalid method). msg is set to null if there is no error message.
deflateInit2 does not perform any compression: this will be done by deflateInit2 does not perform any compression: this will be done by
deflate(). deflate().
*/ */
extern int deflateSetDictionary OF((z_stream *strm,
const Bytef *dictionary,
uInt dictLength));
/*
Initializes the compression dictionary (history buffer) from the given
byte sequence without producing any compressed output. This function must
be called immediately after deflateInit or deflateInit2, before any call
of deflate. The compressor and decompressor must use exactly the same
dictionary (see inflateSetDictionary).
The dictionary should consist of strings (byte sequences) that are likely
to be encountered later in the data to be compressed, with the most commonly
used strings preferably put towards the end of the dictionary. Using a
dictionary is most useful when the data to be compressed is short and
can be predicted with good accuracy; the data can then be compressed better
than with the default empty dictionary. In this version of the library,
only the last 32K bytes of the dictionary are used.
Upon return of this function, strm->adler is set to the Adler32 value
of the dictionary; the decompressor may later use this value to determine
which dictionary has been used by the compressor. (The Adler32 value
applies to the whole dictionary even if only a subset of the dictionary is
actually used by the compressor.)
deflateSetDictionary returns Z_OK if success, or Z_STREAM_ERROR if a
parameter is invalid (such as NULL dictionary) or the stream state
is inconsistent (for example if deflate has already been called for this
stream). deflateSetDictionary does not perform any compression: this will
be done by deflate().
*/
extern int deflateCopy OF((z_stream *dest, extern int deflateCopy OF((z_stream *dest,
z_stream *source)); z_stream *source));
/* /*
@ -451,14 +398,14 @@ extern int deflateCopy OF((z_stream *dest,
application to provide the correct values of next_out and avail_out for the application to provide the correct values of next_out and avail_out for the
next call of deflate. next call of deflate.
This function can be useful when several compression strategies will be This function is useful when several compression strategies will be
tried, for example when there are several ways of pre-processing the input tried, for example when there are several ways of pre-processing the input
data with a filter. The streams that will be discarded should then be freed data with a filter. The streams that will be discarded should then be freed
by calling deflateEnd. Note that deflateCopy duplicates the internal by calling deflateEnd. Note that deflateCopy duplicates the internal
compression state which can be quite large, so this strategy is slow and compression state which can be quite large, so this strategy is slow and
can consume lots of memory. can consume lots of memory.
deflateCopy returns Z_OK if success, Z_MEM_ERROR if there was not deflateCopy returns Z_OK if success, Z_MEM_ERROR if there was not
enough memory, Z_STREAM_ERROR if the source stream state was inconsistent enough memory, Z_STREAM_ERROR if the source stream state was inconsistent
(such as zalloc being NULL). msg is left unchanged in both source and (such as zalloc being NULL). msg is left unchanged in both source and
destination. destination.
@ -488,10 +435,9 @@ extern int deflateParams OF((z_stream *strm, int level, int strategy));
stream state was inconsistent or if a parameter was invalid. stream state was inconsistent or if a parameter was invalid.
*/ */
/*
extern int inflateInit2 OF((z_stream *strm, extern int inflateInit2 OF((z_stream *strm,
int windowBits)); int windowBits));
/*
This is another version of inflateInit with more compression options. The This is another version of inflateInit with more compression options. The
fields next_out, zalloc, zfree and opaque must be initialized before by fields next_out, zalloc, zfree and opaque must be initialized before by
the caller. the caller.
@ -523,25 +469,6 @@ extern int inflateInit2 OF((z_stream *strm,
inflate(). inflate().
*/ */
extern int inflateSetDictionary OF((z_stream *strm,
const Bytef *dictionary,
uInt dictLength));
/*
Initializes the decompression dictionary (history buffer) from the given
uncompressed byte sequence. This function must be called immediately after
a call of inflate if this call returned Z_NEED_DICT. The dictionary chosen
by the compressor can be determined from the Adler32 value returned by this
call of inflate. The compressor and decompressor must use exactly the same
dictionary (see deflateSetDictionary).
inflateSetDictionary returns Z_OK if success, Z_STREAM_ERROR if a
parameter is invalid (such as NULL dictionary) or the stream state is
inconsistent, Z_DATA_ERROR if the given dictionary doesn't match the
expected one (incorrect Adler32 value). inflateSetDictionary does not
perform any decompression: this will be done by subsequent calls of
inflate().
*/
extern int inflateSync OF((z_stream *strm)); extern int inflateSync OF((z_stream *strm));
/* /*
Skips invalid compressed data until the special marker (see deflate() Skips invalid compressed data until the special marker (see deflate()
@ -579,7 +506,7 @@ extern int inflateReset OF((z_stream *strm));
*/ */
extern int compress OF((Bytef *dest, uLongf *destLen, extern int compress OF((Bytef *dest, uLongf *destLen,
const Bytef *source, uLong sourceLen)); Bytef *source, uLong sourceLen));
/* /*
Compresses the source buffer into the destination buffer. sourceLen is Compresses the source buffer into the destination buffer. sourceLen is
the byte length of the source buffer. Upon entry, destLen is the total the byte length of the source buffer. Upon entry, destLen is the total
@ -594,7 +521,7 @@ extern int compress OF((Bytef *dest, uLongf *destLen,
*/ */
extern int uncompress OF((Bytef *dest, uLongf *destLen, extern int uncompress OF((Bytef *dest, uLongf *destLen,
const Bytef *source, uLong sourceLen)); Bytef *source, uLong sourceLen));
/* /*
Decompresses the source buffer into the destination buffer. sourceLen is Decompresses the source buffer into the destination buffer. sourceLen is
the byte length of the source buffer. Upon entry, destLen is the total the byte length of the source buffer. Upon entry, destLen is the total
@ -614,7 +541,7 @@ extern int uncompress OF((Bytef *dest, uLongf *destLen,
typedef voidp gzFile; typedef voidp gzFile;
extern gzFile gzopen OF((const char *path, const char *mode)); extern gzFile gzopen OF((char *path, char *mode));
/* /*
Opens a gzip (.gz) file for reading or writing. The mode parameter Opens a gzip (.gz) file for reading or writing. The mode parameter
is as in fopen ("rb" or "wb") but can also include a compression level is as in fopen ("rb" or "wb") but can also include a compression level
@ -626,15 +553,12 @@ extern gzFile gzopen OF((const char *path, const char *mode));
zlib error is Z_MEM_ERROR). zlib error is Z_MEM_ERROR).
*/ */
extern gzFile gzdopen OF((int fd, const char *mode)); extern gzFile gzdopen OF((int fd, char *mode));
/* /*
gzdopen() associates a gzFile with the file descriptor fd. File gzdopen() associates a gzFile with the file descriptor fd. File
descriptors are obtained from calls like open, dup, creat, pipe or descriptors are obtained from calls like open, dup, creat, pipe or
fileno (in the file has been previously opened with fopen). fileno (in the file has been previously opened with fopen).
The mode parameter is as in fopen ("rb" or "wb"). The mode parameter is as in fopen ("rb" or "wb").
The next call of gzclose on the returned gzFile will also close the
file descriptor fd, just like fclose(fdopen(fd), mode) closes the file
descriptor fd. If you want to keep fd open, use gzdopen(dup(fd), mode).
gzdopen returns NULL if there was insufficient memory to allocate gzdopen returns NULL if there was insufficient memory to allocate
the (de)compression state. the (de)compression state.
*/ */
@ -647,7 +571,7 @@ extern int gzread OF((gzFile file, voidp buf, unsigned len));
gzread returns the number of uncompressed bytes actually read (0 for gzread returns the number of uncompressed bytes actually read (0 for
end of file, -1 for error). */ end of file, -1 for error). */
extern int gzwrite OF((gzFile file, const voidp buf, unsigned len)); extern int gzwrite OF((gzFile file, voidp buf, unsigned len));
/* /*
Writes the given number of uncompressed bytes into the compressed file. Writes the given number of uncompressed bytes into the compressed file.
gzwrite returns the number of uncompressed bytes actually written gzwrite returns the number of uncompressed bytes actually written
@ -688,7 +612,7 @@ extern char* gzerror OF((gzFile file, int *errnum));
compression library. compression library.
*/ */
extern uLong adler32 OF((uLong adler, const Bytef *buf, uInt len)); extern uLong adler32 OF((uLong adler, Bytef *buf, uInt len));
/* /*
Update a running Adler-32 checksum with the bytes buf[0..len-1] and Update a running Adler-32 checksum with the bytes buf[0..len-1] and
@ -705,7 +629,7 @@ extern uLong adler32 OF((uLong adler, const Bytef *buf, uInt len));
if (adler != original_adler) error(); if (adler != original_adler) error();
*/ */
extern uLong crc32 OF((uLong crc, const Bytef *buf, uInt len)); extern uLong crc32 OF((uLong crc, Bytef *buf, uInt len));
/* /*
Update a running crc with the bytes buf[0..len-1] and return the updated Update a running crc with the bytes buf[0..len-1] and return the updated
crc. If buf is NULL, this function returns the required initial value crc. If buf is NULL, this function returns the required initial value
@ -721,37 +645,10 @@ extern uLong crc32 OF((uLong crc, const Bytef *buf, uInt len));
if (crc != original_crc) error(); if (crc != original_crc) error();
*/ */
/* various hacks, don't look :) */
/* deflateInit and inflateInit are macros to allow checking the zlib version
* and the compiler's view of z_stream:
*/
extern int deflateInit_ OF((z_stream *strm, int level,
const char *version, int stream_size));
extern int inflateInit_ OF((z_stream *strm,
const char *version, int stream_size));
extern int deflateInit2_ OF((z_stream *strm, int level, int method,
int windowBits, int memLevel, int strategy,
const char *version, int stream_size));
extern int inflateInit2_ OF((z_stream *strm, int windowBits,
const char *version, int stream_size));
#define deflateInit(strm, level) \
deflateInit_((strm), (level), ZLIB_VERSION, sizeof(z_stream))
#define inflateInit(strm) \
inflateInit_((strm), ZLIB_VERSION, sizeof(z_stream))
#define deflateInit2(strm, level, method, windowBits, memLevel, strategy) \
deflateInit2_((strm),(level),(method),(windowBits),(memLevel),\
(strategy), ZLIB_VERSION, sizeof(z_stream))
#define inflateInit2(strm, windowBits) \
inflateInit2_((strm), (windowBits), ZLIB_VERSION, sizeof(z_stream))
#ifndef _Z_UTIL_H #ifndef _Z_UTIL_H
struct internal_state {int dummy;}; /* hack for buggy compilers */ struct internal_state {int dummy;}; /* hack for buggy compilers */
#endif #endif
uLongf *get_crc_table OF((void)); /* can be used by asm versions of crc32() */
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

40
zutil.c
View File

@ -1,5 +1,5 @@
/* zutil.c -- target dependent utility functions for the compression library /* zutil.c -- target dependent utility functions for the compression library
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -15,18 +15,16 @@ struct internal_state {int dummy;}; /* for buggy compilers */
extern void exit OF((int)); extern void exit OF((int));
#endif #endif
const char *zlib_version = ZLIB_VERSION; char *zlib_version = ZLIB_VERSION;
const char *z_errmsg[10] = { char *z_errmsg[] = {
"need dictionary", /* Z_NEED_DICT 2 */ "stream end", /* Z_STREAM_END 1 */
"stream end", /* Z_STREAM_END 1 */ "", /* Z_OK 0 */
"", /* Z_OK 0 */ "file error", /* Z_ERRNO (-1) */
"file error", /* Z_ERRNO (-1) */ "stream error", /* Z_STREAM_ERROR (-2) */
"stream error", /* Z_STREAM_ERROR (-2) */ "data error", /* Z_DATA_ERROR (-3) */
"data error", /* Z_DATA_ERROR (-3) */ "insufficient memory", /* Z_MEM_ERROR (-4) */
"insufficient memory", /* Z_MEM_ERROR (-4) */ "buffer error", /* Z_BUF_ERROR (-5) */
"buffer error", /* Z_BUF_ERROR (-5) */
"incompatible version",/* Z_VERSION_ERROR (-6) */
""}; ""};
@ -62,9 +60,9 @@ void zmemzero(dest, len)
#endif #endif
#ifdef __TURBOC__ #ifdef __TURBOC__
#if (defined( __BORLANDC__) || !defined(SMALL_MEDIUM)) && !defined(__32BIT__) #if !defined(__SMALL__) && !defined(__MEDIUM__) && !defined(__32BIT__)
/* Small and medium model in Turbo C are for now limited to near allocation /* Small and medium model are for now limited to near allocation with
* with reduced MAX_WBITS and MAX_MEM_LEVEL * reduced MAX_WBITS and MAX_MEM_LEVEL
*/ */
# define MY_ZCALLOC # define MY_ZCALLOC
@ -102,6 +100,9 @@ voidpf zcalloc (voidpf opaque, unsigned items, unsigned size)
*/ */
if (bsize < 65520L) { if (bsize < 65520L) {
buf = farmalloc(bsize); buf = farmalloc(bsize);
#ifdef DEBUG
zmemzero(buf, (uInt)bsize);
#endif
if (*(ush*)&buf != 0) return buf; if (*(ush*)&buf != 0) return buf;
} else { } else {
buf = farmalloc(bsize + 16L); buf = farmalloc(bsize + 16L);
@ -113,6 +114,10 @@ voidpf zcalloc (voidpf opaque, unsigned items, unsigned size)
*((ush*)&buf+1) += ((ush)((uch*)buf-0) + 15) >> 4; *((ush*)&buf+1) += ((ush)((uch*)buf-0) + 15) >> 4;
*(ush*)&buf = 0; *(ush*)&buf = 0;
table[next_ptr++].new_ptr = buf; table[next_ptr++].new_ptr = buf;
#ifdef DEBUG
zmemzero(buf, (uInt)65535);
((uch*)buf)[65535] = 0;
#endif
return buf; return buf;
} }
@ -141,8 +146,7 @@ void zcfree (voidpf opaque, voidpf ptr)
#endif /* __TURBOC__ */ #endif /* __TURBOC__ */
#if defined(M_I86) && !(defined(__WATCOMC__) && defined(__386__)) #ifdef M_I86 /* Microsoft C */
/* Microsoft C */
# define MY_ZCALLOC # define MY_ZCALLOC
@ -178,7 +182,6 @@ voidpf zcalloc (opaque, items, size)
unsigned items; unsigned items;
unsigned size; unsigned size;
{ {
if (opaque) opaque = 0; /* to make compiler happy */
return (voidpf)calloc(items, size); return (voidpf)calloc(items, size);
} }
@ -186,7 +189,6 @@ void zcfree (opaque, ptr)
voidpf opaque; voidpf opaque;
voidpf ptr; voidpf ptr;
{ {
if (opaque) opaque = 0; /* to make compiler happy */
free(ptr); free(ptr);
} }

20
zutil.h
View File

@ -1,5 +1,5 @@
/* zutil.h -- internal interface and configuration of the compression library /* zutil.h -- internal interface and configuration of the compression library
* Copyright (C) 1995-1996 Jean-loup Gailly. * Copyright (C) 1995 Jean-loup Gailly.
* For conditions of distribution and use, see copyright notice in zlib.h * For conditions of distribution and use, see copyright notice in zlib.h
*/ */
@ -15,7 +15,7 @@
#include "zlib.h" #include "zlib.h"
#if defined(MSDOS) || defined(VMS) || defined(CRAY) || defined(WIN32) #if defined(MSDOS) || defined(VMS) || defined(CRAY)
# include <stddef.h> # include <stddef.h>
# include <errno.h> # include <errno.h>
#else #else
@ -37,13 +37,9 @@ typedef unsigned short ush;
typedef ush FAR ushf; typedef ush FAR ushf;
typedef unsigned long ulg; typedef unsigned long ulg;
extern const char *z_errmsg[10]; /* indexed by 2-zlib_error */ extern char *z_errmsg[]; /* indexed by 1-zlib_error */
/* (size given to avoid silly warnings with Visual C++) */
#define ERR_MSG(err) (char*)z_errmsg[Z_NEED_DICT-(err)] #define ERR_RETURN(strm,err) return (strm->msg = z_errmsg[1-(err)], (err))
#define ERR_RETURN(strm,err) \
return (strm->msg = ERR_MSG(err), (err))
/* To be used only when the state is known to be valid */ /* To be used only when the state is known to be valid */
/* common constants */ /* common constants */
@ -69,8 +65,6 @@ extern const char *z_errmsg[10]; /* indexed by 2-zlib_error */
#define MAX_MATCH 258 #define MAX_MATCH 258
/* The minimum and maximum match lengths */ /* The minimum and maximum match lengths */
#define PRESET_DICT 0x20 /* preset dictionary flag in zlib header */
/* target dependencies */ /* target dependencies */
#ifdef MSDOS #ifdef MSDOS
@ -148,13 +142,11 @@ extern const char *z_errmsg[10]; /* indexed by 2-zlib_error */
# define HAVE_MEMCPY # define HAVE_MEMCPY
#endif #endif
#ifdef HAVE_MEMCPY #ifdef HAVE_MEMCPY
# ifdef SMALL_MEDIUM /* MSDOS small or medium model */ # if defined(M_I86SM) || defined(M_I86MM) /* MSC small or medium model */
# define zmemcpy _fmemcpy # define zmemcpy _fmemcpy
# define zmemcmp _fmemcmp
# define zmemzero(dest, len) _fmemset(dest, 0, len) # define zmemzero(dest, len) _fmemset(dest, 0, len)
# else # else
# define zmemcpy memcpy # define zmemcpy memcpy
# define zmemcmp memcmp
# define zmemzero(dest, len) memset(dest, 0, len) # define zmemzero(dest, len) memset(dest, 0, len)
# endif # endif
#else #else
@ -184,7 +176,7 @@ extern const char *z_errmsg[10]; /* indexed by 2-zlib_error */
#endif #endif
typedef uLong (*check_func) OF((uLong check, const Bytef *buf, uInt len)); typedef uLong (*check_func) OF((uLong check, Bytef *buf, uInt len));
extern void z_error OF((char *m)); extern void z_error OF((char *m));