From 417b4381dda4b88a1e382f821c8964cf8954307e Mon Sep 17 00:00:00 2001 From: David Monniaux Date: Tue, 29 Jan 2019 22:31:50 +0100 Subject: https://github.com/pfalcon/uzlib --- test/monniaux/uzlib/src/adler32.c | 78 ++++ test/monniaux/uzlib/src/crc32.c | 63 +++ test/monniaux/uzlib/src/defl_static.c | 305 ++++++++++++++ test/monniaux/uzlib/src/defl_static.h | 45 ++ test/monniaux/uzlib/src/genlz77.c | 124 ++++++ test/monniaux/uzlib/src/makefile | 36 ++ test/monniaux/uzlib/src/makefile.b32 | 34 ++ test/monniaux/uzlib/src/makefile.dj2 | 33 ++ test/monniaux/uzlib/src/makefile.dmc | 32 ++ test/monniaux/uzlib/src/makefile.mgw | 31 ++ test/monniaux/uzlib/src/makefile.vc | 30 ++ test/monniaux/uzlib/src/makefile.wat | 35 ++ test/monniaux/uzlib/src/nasm/crc32.nas | 118 ++++++ test/monniaux/uzlib/src/nasm/nasmlcm.inc | 326 +++++++++++++++ test/monniaux/uzlib/src/nasm/tinfzlib.nas | 160 ++++++++ test/monniaux/uzlib/src/tinf.h | 3 + test/monniaux/uzlib/src/tinf_compat.h | 9 + test/monniaux/uzlib/src/tinfgzip.c | 110 +++++ test/monniaux/uzlib/src/tinflate.c | 661 ++++++++++++++++++++++++++++++ test/monniaux/uzlib/src/tinfzlib.c | 66 +++ test/monniaux/uzlib/src/uzlib.h | 169 ++++++++ test/monniaux/uzlib/src/uzlib_conf.h | 22 + 22 files changed, 2490 insertions(+) create mode 100644 test/monniaux/uzlib/src/adler32.c create mode 100644 test/monniaux/uzlib/src/crc32.c create mode 100644 test/monniaux/uzlib/src/defl_static.c create mode 100644 test/monniaux/uzlib/src/defl_static.h create mode 100644 test/monniaux/uzlib/src/genlz77.c create mode 100644 test/monniaux/uzlib/src/makefile create mode 100644 test/monniaux/uzlib/src/makefile.b32 create mode 100644 test/monniaux/uzlib/src/makefile.dj2 create mode 100644 test/monniaux/uzlib/src/makefile.dmc create mode 100644 test/monniaux/uzlib/src/makefile.mgw create mode 100644 test/monniaux/uzlib/src/makefile.vc create mode 100644 test/monniaux/uzlib/src/makefile.wat create mode 100644 test/monniaux/uzlib/src/nasm/crc32.nas create mode 100644 test/monniaux/uzlib/src/nasm/nasmlcm.inc create mode 100644 test/monniaux/uzlib/src/nasm/tinfzlib.nas create mode 100644 test/monniaux/uzlib/src/tinf.h create mode 100644 test/monniaux/uzlib/src/tinf_compat.h create mode 100644 test/monniaux/uzlib/src/tinfgzip.c create mode 100644 test/monniaux/uzlib/src/tinflate.c create mode 100644 test/monniaux/uzlib/src/tinfzlib.c create mode 100644 test/monniaux/uzlib/src/uzlib.h create mode 100644 test/monniaux/uzlib/src/uzlib_conf.h (limited to 'test/monniaux/uzlib/src') diff --git a/test/monniaux/uzlib/src/adler32.c b/test/monniaux/uzlib/src/adler32.c new file mode 100644 index 00000000..1f175949 --- /dev/null +++ b/test/monniaux/uzlib/src/adler32.c @@ -0,0 +1,78 @@ +/* + * Adler-32 checksum + * + * Copyright (c) 2003 by Joergen Ibsen / Jibz + * All Rights Reserved + * + * http://www.ibsensoftware.com/ + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +/* + * Adler-32 algorithm taken from the zlib source, which is + * Copyright (C) 1995-1998 Jean-loup Gailly and Mark Adler + */ + +#include "tinf.h" + +#define A32_BASE 65521 +#define A32_NMAX 5552 + +uint32_t uzlib_adler32(const void *data, unsigned int length, uint32_t prev_sum /* 1 */) +{ + const unsigned char *buf = (const unsigned char *)data; + + unsigned int s1 = prev_sum & 0xffff; + unsigned int s2 = prev_sum >> 16; + + while (length > 0) + { + int k = length < A32_NMAX ? length : A32_NMAX; + int i; + + for (i = k / 16; i; --i, buf += 16) + { + s1 += buf[0]; s2 += s1; s1 += buf[1]; s2 += s1; + s1 += buf[2]; s2 += s1; s1 += buf[3]; s2 += s1; + s1 += buf[4]; s2 += s1; s1 += buf[5]; s2 += s1; + s1 += buf[6]; s2 += s1; s1 += buf[7]; s2 += s1; + + s1 += buf[8]; s2 += s1; s1 += buf[9]; s2 += s1; + s1 += buf[10]; s2 += s1; s1 += buf[11]; s2 += s1; + s1 += buf[12]; s2 += s1; s1 += buf[13]; s2 += s1; + s1 += buf[14]; s2 += s1; s1 += buf[15]; s2 += s1; + } + + for (i = k % 16; i; --i) { s1 += *buf++; s2 += s1; } + + s1 %= A32_BASE; + s2 %= A32_BASE; + + length -= k; + } + + return (s2 << 16) | s1; +} diff --git a/test/monniaux/uzlib/src/crc32.c b/test/monniaux/uzlib/src/crc32.c new file mode 100644 index 00000000..e24c643b --- /dev/null +++ b/test/monniaux/uzlib/src/crc32.c @@ -0,0 +1,63 @@ +/* + * CRC32 checksum + * + * Copyright (c) 1998-2003 by Joergen Ibsen / Jibz + * All Rights Reserved + * + * http://www.ibsensoftware.com/ + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +/* + * CRC32 algorithm taken from the zlib source, which is + * Copyright (C) 1995-1998 Jean-loup Gailly and Mark Adler + */ + +#include "tinf.h" + +static const unsigned int tinf_crc32tab[16] = { + 0x00000000, 0x1db71064, 0x3b6e20c8, 0x26d930ac, 0x76dc4190, + 0x6b6b51f4, 0x4db26158, 0x5005713c, 0xedb88320, 0xf00f9344, + 0xd6d6a3e8, 0xcb61b38c, 0x9b64c2b0, 0x86d3d2d4, 0xa00ae278, + 0xbdbdf21c +}; + +/* crc is previous value for incremental computation, 0xffffffff initially */ +uint32_t uzlib_crc32(const void *data, unsigned int length, uint32_t crc) +{ + const unsigned char *buf = (const unsigned char *)data; + unsigned int i; + + for (i = 0; i < length; ++i) + { + crc ^= buf[i]; + crc = tinf_crc32tab[crc & 0x0f] ^ (crc >> 4); + crc = tinf_crc32tab[crc & 0x0f] ^ (crc >> 4); + } + + // return value suitable for passing in next time, for final value invert it + return crc/* ^ 0xffffffff*/; +} diff --git a/test/monniaux/uzlib/src/defl_static.c b/test/monniaux/uzlib/src/defl_static.c new file mode 100644 index 00000000..80ea1977 --- /dev/null +++ b/test/monniaux/uzlib/src/defl_static.c @@ -0,0 +1,305 @@ +/* + +Routines in this file are based on: +Zlib (RFC1950 / RFC1951) compression for PuTTY. + +PuTTY is copyright 1997-2014 Simon Tatham. + +Portions copyright Robert de Bath, Joris van Rantwijk, Delian +Delchev, Andreas Schultz, Jeroen Massar, Wez Furlong, Nicolas Barry, +Justin Bradford, Ben Harris, Malcolm Smith, Ahmad Khalifa, Markus +Kuhn, Colin Watson, and CORE SDI S.A. + +Permission is hereby granted, free of charge, to any person +obtaining a copy of this software and associated documentation files +(the "Software"), to deal in the Software without restriction, +including without limitation the rights to use, copy, modify, merge, +publish, distribute, sublicense, and/or sell copies of the Software, +and to permit persons to whom the Software is furnished to do so, +subject to the following conditions: + +The above copyright notice and this permission notice shall be +included in all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +NONINFRINGEMENT. IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE +FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +*/ + +#include +#include +#include +#include +#include "defl_static.h" + +#define snew(type) ( (type *) malloc(sizeof(type)) ) +#define snewn(n, type) ( (type *) malloc((n) * sizeof(type)) ) +#define sresize(x, n, type) ( (type *) realloc((x), (n) * sizeof(type)) ) +#define sfree(x) ( free((x)) ) + +#ifndef FALSE +#define FALSE 0 +#define TRUE (!FALSE) +#endif + +/* ---------------------------------------------------------------------- + * Zlib compression. We always use the static Huffman tree option. + * Mostly this is because it's hard to scan a block in advance to + * work out better trees; dynamic trees are great when you're + * compressing a large file under no significant time constraint, + * but when you're compressing little bits in real time, things get + * hairier. + * + * I suppose it's possible that I could compute Huffman trees based + * on the frequencies in the _previous_ block, as a sort of + * heuristic, but I'm not confident that the gain would balance out + * having to transmit the trees. + */ + +void outbits(struct Outbuf *out, unsigned long bits, int nbits) +{ + assert(out->noutbits + nbits <= 32); + out->outbits |= bits << out->noutbits; + out->noutbits += nbits; + while (out->noutbits >= 8) { + if (out->outlen >= out->outsize) { + out->outsize = out->outlen + 64; + out->outbuf = sresize(out->outbuf, out->outsize, unsigned char); + } + out->outbuf[out->outlen++] = (unsigned char) (out->outbits & 0xFF); + out->outbits >>= 8; + out->noutbits -= 8; + } +} + +static const unsigned char mirrorbytes[256] = { + 0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0, + 0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0, + 0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8, + 0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8, + 0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4, + 0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4, + 0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec, + 0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc, + 0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2, + 0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2, + 0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea, + 0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa, + 0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6, + 0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6, + 0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee, + 0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe, + 0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1, + 0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1, + 0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9, + 0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9, + 0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5, + 0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5, + 0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed, + 0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd, + 0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3, + 0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3, + 0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb, + 0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb, + 0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7, + 0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7, + 0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef, + 0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff, +}; + +typedef struct { + short code, extrabits; + uint16_t min, max; +} coderecord; + +static const coderecord lencodes[] = { + {257, 0, 3, 3}, + {258, 0, 4, 4}, + {259, 0, 5, 5}, + {260, 0, 6, 6}, + {261, 0, 7, 7}, + {262, 0, 8, 8}, + {263, 0, 9, 9}, + {264, 0, 10, 10}, + {265, 1, 11, 12}, + {266, 1, 13, 14}, + {267, 1, 15, 16}, + {268, 1, 17, 18}, + {269, 2, 19, 22}, + {270, 2, 23, 26}, + {271, 2, 27, 30}, + {272, 2, 31, 34}, + {273, 3, 35, 42}, + {274, 3, 43, 50}, + {275, 3, 51, 58}, + {276, 3, 59, 66}, + {277, 4, 67, 82}, + {278, 4, 83, 98}, + {279, 4, 99, 114}, + {280, 4, 115, 130}, + {281, 5, 131, 162}, + {282, 5, 163, 194}, + {283, 5, 195, 226}, + {284, 5, 227, 257}, + {285, 0, 258, 258}, +}; + +static const coderecord distcodes[] = { + {0, 0, 1, 1}, + {1, 0, 2, 2}, + {2, 0, 3, 3}, + {3, 0, 4, 4}, + {4, 1, 5, 6}, + {5, 1, 7, 8}, + {6, 2, 9, 12}, + {7, 2, 13, 16}, + {8, 3, 17, 24}, + {9, 3, 25, 32}, + {10, 4, 33, 48}, + {11, 4, 49, 64}, + {12, 5, 65, 96}, + {13, 5, 97, 128}, + {14, 6, 129, 192}, + {15, 6, 193, 256}, + {16, 7, 257, 384}, + {17, 7, 385, 512}, + {18, 8, 513, 768}, + {19, 8, 769, 1024}, + {20, 9, 1025, 1536}, + {21, 9, 1537, 2048}, + {22, 10, 2049, 3072}, + {23, 10, 3073, 4096}, + {24, 11, 4097, 6144}, + {25, 11, 6145, 8192}, + {26, 12, 8193, 12288}, + {27, 12, 12289, 16384}, + {28, 13, 16385, 24576}, + {29, 13, 24577, 32768}, +}; + +void zlib_literal(struct Outbuf *out, unsigned char c) +{ + if (out->comp_disabled) { + /* + * We're in an uncompressed block, so just output the byte. + */ + outbits(out, c, 8); + return; + } + + if (c <= 143) { + /* 0 through 143 are 8 bits long starting at 00110000. */ + outbits(out, mirrorbytes[0x30 + c], 8); + } else { + /* 144 through 255 are 9 bits long starting at 110010000. */ + outbits(out, 1 + 2 * mirrorbytes[0x90 - 144 + c], 9); + } +} + +void zlib_match(struct Outbuf *out, int distance, int len) +{ + const coderecord *d, *l; + int i, j, k; + + assert(!out->comp_disabled); + + while (len > 0) { + int thislen; + + /* + * We can transmit matches of lengths 3 through 258 + * inclusive. So if len exceeds 258, we must transmit in + * several steps, with 258 or less in each step. + * + * Specifically: if len >= 261, we can transmit 258 and be + * sure of having at least 3 left for the next step. And if + * len <= 258, we can just transmit len. But if len == 259 + * or 260, we must transmit len-3. + */ + thislen = (len > 260 ? 258 : len <= 258 ? len : len - 3); + len -= thislen; + + /* + * Binary-search to find which length code we're + * transmitting. + */ + i = -1; + j = sizeof(lencodes) / sizeof(*lencodes); + while (1) { + assert(j - i >= 2); + k = (j + i) / 2; + if (thislen < lencodes[k].min) + j = k; + else if (thislen > lencodes[k].max) + i = k; + else { + l = &lencodes[k]; + break; /* found it! */ + } + } + + /* + * Transmit the length code. 256-279 are seven bits + * starting at 0000000; 280-287 are eight bits starting at + * 11000000. + */ + if (l->code <= 279) { + outbits(out, mirrorbytes[(l->code - 256) * 2], 7); + } else { + outbits(out, mirrorbytes[0xc0 - 280 + l->code], 8); + } + + /* + * Transmit the extra bits. + */ + if (l->extrabits) + outbits(out, thislen - l->min, l->extrabits); + + /* + * Binary-search to find which distance code we're + * transmitting. + */ + i = -1; + j = sizeof(distcodes) / sizeof(*distcodes); + while (1) { + assert(j - i >= 2); + k = (j + i) / 2; + if (distance < distcodes[k].min) + j = k; + else if (distance > distcodes[k].max) + i = k; + else { + d = &distcodes[k]; + break; /* found it! */ + } + } + + /* + * Transmit the distance code. Five bits starting at 00000. + */ + outbits(out, mirrorbytes[d->code * 8], 5); + + /* + * Transmit the extra bits. + */ + if (d->extrabits) + outbits(out, distance - d->min, d->extrabits); + } +} + +void zlib_start_block(struct Outbuf *out) +{ +// outbits(out, 0x9C78, 16); + outbits(out, 1, 1); /* Final block */ + outbits(out, 1, 2); /* Static huffman block */ +} + +void zlib_finish_block(struct Outbuf *out) +{ + outbits(out, 0, 7); /* close block */ + outbits(out, 0, 7); /* Make sure all bits are flushed */ +} diff --git a/test/monniaux/uzlib/src/defl_static.h b/test/monniaux/uzlib/src/defl_static.h new file mode 100644 index 00000000..292734d7 --- /dev/null +++ b/test/monniaux/uzlib/src/defl_static.h @@ -0,0 +1,45 @@ +/* + * Copyright (c) uzlib authors + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +/* This files contains type declaration and prototypes for defl_static.c. + They may be altered/distinct from the originals used in PuTTY source + code. */ + +struct Outbuf { + unsigned char *outbuf; + int outlen, outsize; + unsigned long outbits; + int noutbits; + int comp_disabled; +}; + +void outbits(struct Outbuf *out, unsigned long bits, int nbits); +void zlib_start_block(struct Outbuf *ctx); +void zlib_finish_block(struct Outbuf *ctx); +void zlib_literal(struct Outbuf *ectx, unsigned char c); +void zlib_match(struct Outbuf *ectx, int distance, int len); diff --git a/test/monniaux/uzlib/src/genlz77.c b/test/monniaux/uzlib/src/genlz77.c new file mode 100644 index 00000000..ede1fc9e --- /dev/null +++ b/test/monniaux/uzlib/src/genlz77.c @@ -0,0 +1,124 @@ +/* + * genlz77 - Generic LZ77 compressor + * + * Copyright (c) 2014 by Paul Sokolovsky + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ +#include +#include +#include +#include "uzlib.h" + +#if 0 +#define HASH_BITS 12 +#else +#define HASH_BITS data->hash_bits +#endif + +#define HASH_SIZE (1<dict_size +#endif + +/* Hash function can be defined as macro or as inline function */ + +/*#define HASH(p) (p[0] + p[1] + p[2])*/ + +/* This is hash function from liblzf */ +static inline int HASH(struct uzlib_comp *data, const uint8_t *p) { + int v = (p[0] << 16) | (p[1] << 8) | p[2]; + int hash = ((v >> (3*8 - HASH_BITS)) - v) & (HASH_SIZE - 1); + return hash; +} + +#ifdef DUMP_LZTXT + +/* Counter for approximate compressed length in LZTXT mode. */ +/* Literal is counted as 1, copy as 2 bytes. */ +unsigned approx_compressed_len; + +void literal(void *data, uint8_t val) +{ + printf("L%02x # %c\n", val, (val >= 0x20 && val <= 0x7e) ? val : '?'); + approx_compressed_len++; +} + +void copy(void *data, unsigned offset, unsigned len) +{ + printf("C-%u,%u\n", offset, len); + approx_compressed_len += 2; +} + +#else + +static inline void literal(void *data, uint8_t val) +{ + zlib_literal(data, val); +} + +static inline void copy(void *data, unsigned offset, unsigned len) +{ + zlib_match(data, offset, len); +} + +#endif + + +void uzlib_compress(struct uzlib_comp *data, const uint8_t *src, unsigned slen) +{ + const uint8_t *top = src + slen - MIN_MATCH; + while (src < top) { + int h = HASH(data, src); + const uint8_t **bucket = &data->hash_table[h & (HASH_SIZE - 1)]; + const uint8_t *subs = *bucket; + *bucket = src; + if (subs && src > subs && (src - subs) <= MAX_OFFSET && !memcmp(src, subs, MIN_MATCH)) { + src += MIN_MATCH; + const uint8_t *m = subs + MIN_MATCH; + int len = MIN_MATCH; + while (*src == *m && len < MAX_MATCH && src < top) { + src++; m++; len++; + } + copy(data, src - len - subs, len); + } else { + literal(data, *src++); + } + } + // Process buffer tail, which is less than MIN_MATCH + // (and so it doesn't make sense to look for matches there) + top += MIN_MATCH; + while (src < top) { + literal(data, *src++); + } +} diff --git a/test/monniaux/uzlib/src/makefile b/test/monniaux/uzlib/src/makefile new file mode 100644 index 00000000..3ced616f --- /dev/null +++ b/test/monniaux/uzlib/src/makefile @@ -0,0 +1,36 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## GCC makefile (Linux, FreeBSD, BeOS and QNX) +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## +## http://www.ibsensoftware.com/ +## + +target = ../lib/libtinf.a +objects = tinflate.o tinfgzip.o tinfzlib.o adler32.o crc32.o \ + defl_static.o genlz77.o + +COPT = -Os +CFLAGS = -Wall $(COPT) +LDFLAGS = $(CFLAGS) -s + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + ar -frs $@ $^ + ranlib $@ + +%.o : %.c + $(CC) $(CFLAGS) -o $@ -c $< + +%.o : %.nas + nasm -o $@ -f elf -D_ELF_ -O3 -Inasm/ $< + +clean: + $(RM) $(objects) $(target) diff --git a/test/monniaux/uzlib/src/makefile.b32 b/test/monniaux/uzlib/src/makefile.b32 new file mode 100644 index 00000000..52e17162 --- /dev/null +++ b/test/monniaux/uzlib/src/makefile.b32 @@ -0,0 +1,34 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## Borland C/C++ makefile (GNU Make) +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## +## http://www.ibsensoftware.com/ +## + +target = ..\lib\tinf.lib +objects = tinflate.obj tinfgzip.obj tinfzlib.obj adler32.obj crc32.obj + +cflags = -a16 -K -O2 -OS + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + echo $(patsubst %,+%,$(objects)) >> lib.cmd + tlib $@ /C @lib.cmd + $(RM) lib.cmd + +%.obj : %.c + bcc32 $(cflags) -c $< + +%.obj : %.nas + nasm -o $@ -f obj -D_OBJ_ -O3 -Inasm/ $< + +clean: + $(RM) $(objects) $(target) $(temps) diff --git a/test/monniaux/uzlib/src/makefile.dj2 b/test/monniaux/uzlib/src/makefile.dj2 new file mode 100644 index 00000000..856ecfd6 --- /dev/null +++ b/test/monniaux/uzlib/src/makefile.dj2 @@ -0,0 +1,33 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## DJGPP makefile +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## +## http://www.ibsensoftware.com/ +## + +target = ../lib/libtinf.a +objects = tinflate.o tinfgzip.o tinfzlib.o adler32.o crc32.o + +cflags = -s -Wall -Os -fomit-frame-pointer + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + ar -frsv $@ $^ + ranlib $@ + +%.o : %.c + gcc $(cflags) -o $@ -c $< + +%.o : %.nas + nasm -o $@ -f coff -O3 -Inasm/ $< + +clean: + $(RM) $(objects) $(target) diff --git a/test/monniaux/uzlib/src/makefile.dmc b/test/monniaux/uzlib/src/makefile.dmc new file mode 100644 index 00000000..7629b8f3 --- /dev/null +++ b/test/monniaux/uzlib/src/makefile.dmc @@ -0,0 +1,32 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## Digital Mars C/C++ makefile (GNU Make) +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## +## http://www.ibsensoftware.com/ +## + +target = ..\lib\tinf.lib +objects = tinflate.obj tinfgzip.obj tinfzlib.obj adler32.obj crc32.obj + +cflags = -s -mn -o+all + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + lib -c $@ $^ + +%.obj : %.c + dmc $(cflags) -c $< + +%.obj : %.nas + nasm -o $@ -f obj -D_OBJ_ -O3 $< + +clean: + $(RM) $(objects) $(target) $(temps) diff --git a/test/monniaux/uzlib/src/makefile.mgw b/test/monniaux/uzlib/src/makefile.mgw new file mode 100644 index 00000000..020f1853 --- /dev/null +++ b/test/monniaux/uzlib/src/makefile.mgw @@ -0,0 +1,31 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## MinGW / Cygwin makefile +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## + +target = ../lib/libtinf.a +objects = tinflate.o tinfgzip.o tinfzlib.o adler32.o crc32.o + +cflags = -s -Wall -Os -fomit-frame-pointer + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + ar -frsv $@ $^ + ranlib $@ + +%.o : %.c + gcc $(cflags) -o $@ -c $< + +%.o : %.nas + nasm -o $@ -f win32 -O3 -Inasm/ $< + +clean: + $(RM) $(target) $(objects) diff --git a/test/monniaux/uzlib/src/makefile.vc b/test/monniaux/uzlib/src/makefile.vc new file mode 100644 index 00000000..de37a20d --- /dev/null +++ b/test/monniaux/uzlib/src/makefile.vc @@ -0,0 +1,30 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## Visual C++ Makefile (GNU Make) +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## + +target = ../lib/tinf.lib +objects = tinflate.obj tinfgzip.obj tinfzlib.obj adler32.obj crc32.obj + +cflags = /nologo /W3 /O1 /G6 /W3 /Gy /GF + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + lib /OUT:$@ $^ + +%.obj : %.c + cl $(cflags) -c $< + +%.obj : %.nas + nasm -o $@ -f win32 -O3 -Inasm/ $< + +clean: + $(RM) $(target) $(objects) diff --git a/test/monniaux/uzlib/src/makefile.wat b/test/monniaux/uzlib/src/makefile.wat new file mode 100644 index 00000000..573fb2d4 --- /dev/null +++ b/test/monniaux/uzlib/src/makefile.wat @@ -0,0 +1,35 @@ +## +## tinflib - tiny inflate library (inflate, gzip, zlib) +## +## Watcom / OpenWatcom C/C++ makefile (GNU Make) +## +## Copyright (c) 2003 by Joergen Ibsen / Jibz +## All Rights Reserved +## +## http://www.ibsensoftware.com/ +## + +target = ..\lib\tinf.lib +objects = tinflate.obj tinfgzip.obj tinfzlib.obj adler32.obj crc32.obj +system = nt + +cflags = -bt=$(system) -d0 -obmlrs -s -zl + +.PHONY: all clean + +all: $(target) + +$(target): $(objects) + $(RM) $@ + echo $(patsubst %,+%,$(objects)) >> lib.cmd + wlib -c -n -q -s -fo -io $@ @lib.cmd + $(RM) lib.cmd + +%.obj : %.c + wcc386 $(cflags) $< + +%.obj : %.nas + nasm -o $@ -f obj -D_OBJ_ -O3 -Inasm/ $< + +clean: + $(RM) $(objects) $(target) diff --git a/test/monniaux/uzlib/src/nasm/crc32.nas b/test/monniaux/uzlib/src/nasm/crc32.nas new file mode 100644 index 00000000..bd91692b --- /dev/null +++ b/test/monniaux/uzlib/src/nasm/crc32.nas @@ -0,0 +1,118 @@ +;; +;; NASM assembler crc32 +;; +;; Copyright (c) 1998-2003 by Joergen Ibsen / Jibz +;; All Rights Reserved +;; +;; http://www.ibsensoftware.com/ +;; +;; This software is provided 'as-is', without any express +;; or implied warranty. In no event will the authors be +;; held liable for any damages arising from the use of +;; this software. +;; +;; Permission is granted to anyone to use this software +;; for any purpose, including commercial applications, +;; and to alter it and redistribute it freely, subject to +;; the following restrictions: +;; +;; 1. The origin of this software must not be +;; misrepresented; you must not claim that you +;; wrote the original software. If you use this +;; software in a product, an acknowledgment in +;; the product documentation would be appreciated +;; but is not required. +;; +;; 2. Altered source versions must be plainly marked +;; as such, and must not be misrepresented as +;; being the original software. +;; +;; 3. This notice may not be removed or altered from +;; any source distribution. +;; + +; CRC32 algorithm taken from the zlib source, which is +; Copyright (C) 1995-1998 Jean-loup Gailly and Mark Adler + +cpu 386 + +bits 32 + +%include "nasmlcm.inc" + +section lcmtext + +lcmglobal tinf_crc32,8 + +lcmexport tinf_crc32,8 + +; ============================================================= + +lcmlabel tinf_crc32,8 + ; tinf_crc32(const void *data, + ; unsigned int length); + + .len$ equ 2*4 + 4 + 4 + .dat$ equ 2*4 + 4 + + push esi + push edi + + mov esi, [esp + .dat$] ; esi -> buffer + mov ecx, [esp + .len$] ; ecx = length + + sub eax, eax ; crc = 0 + + test esi, esi + jz short .c_exit + + test ecx, ecx + jz short .c_exit + + dec eax ; crc = 0xffffffff + +%ifdef _OBJ_ + mov edi, tinf_crc32tab wrt FLAT ; edi -> crctab +%else + mov edi, tinf_crc32tab ; edi -> crctab +%endif + + .c_next_byte: + xor al, [esi] + inc esi + + mov edx, 0x0f + and edx, eax + + shr eax, 4 + + xor eax, [edi + edx*4] + + mov edx, 0x0f + and edx, eax + + shr eax, 4 + + xor eax, [edi + edx*4] + + dec ecx + jnz short .c_next_byte + + not eax + + .c_exit: + pop edi + pop esi + + lcmret 8 + +; ============================================================= + +section lcmdata + +tinf_crc32tab dd 0x00000000, 0x1db71064, 0x3b6e20c8, 0x26d930ac, 0x76dc4190 + dd 0x6b6b51f4, 0x4db26158, 0x5005713c, 0xedb88320, 0xf00f9344 + dd 0xd6d6a3e8, 0xcb61b38c, 0x9b64c2b0, 0x86d3d2d4, 0xa00ae278 + dd 0xbdbdf21c + +; ============================================================= diff --git a/test/monniaux/uzlib/src/nasm/nasmlcm.inc b/test/monniaux/uzlib/src/nasm/nasmlcm.inc new file mode 100644 index 00000000..5cbe7e0d --- /dev/null +++ b/test/monniaux/uzlib/src/nasm/nasmlcm.inc @@ -0,0 +1,326 @@ +;; +;; NASM linker compatibility macros 2002.07.24 +;; +;; Copyright (c) 2001-2003 by Joergen Ibsen / Jibz +;; All Rights Reserved +;; +;; http://www.ibsensoftware.com/ +;; + +; define _ELF_ for ELF32 object files +; define _OBJ_ for OMF object files +; define _OBJ_ and _DLL_ for OMF object files for a dll (stdcall) +; define _MSLIBS_ for MS style Win32 import libs (lcmwinextern) +; default is DJGPP/WIN32 COFF object files + +; remember to do lcm*extern before lcmimport + +; ==================================================================== +; +; There are differences between how the object formats that NASM +; supports work, and what features they support. Similarly there +; are differences between how complete and standard compliant the +; support for these formats are in linkers. +; +; The NASM linker compatibility macros (nasmlcm) were put together +; to ease my work by allowing a single source file to be assembled +; for use with a number of compilers/linkers. +; +; Currently obj/omf, win32/coff, djgpp/coff and elf32 output formats +; are supported. The following macros are available: +; +; lcmtext - section name for the code section +; lcmdata - section name for the initialized data section +; lcmbss - section name for the uninitialized data section +; +; lcmglobal - declare a function (two arguments) or data (one +; argument) as global in the current format +; lcmcglobal - same as lcmglobal, but uses C name decoration +; +; lcmextern - declare a function (two arguments) or data (one +; argument) as extern in the current format +; lcmcextern - same as lcmextern, but uses C name decoration +; lcmdllextern - same as lcmextern, but uses dll name decoration +; lcmwinextern - same as lcmextern, but uses name decoration for +; calling Win32 Api functions (see _MSLIBS_) +; +; lcmimport - declares a function (two arguments) or data (one +; argument) as imported in the current format +; lcmexport - declares a function (two arguments) or data (one +; argument) as exported in the current format +; +; lcmlabel - start label for a function in the current format +; lcmclabel - start label for a function with C name decoration +; lcmadjust - adjust stack after a function call in the current +; format +; lcmret - return from a function in the current format +; lcmcret - return from a C function +; +; The following defines change the format and behaviour: +; +; _ELF_ - the lcm*global macro adds :function and :data type +; specifiers +; +; _OBJ_ - section names are similar to those produced by +; Borland tools to increase compatibility with +; various OMF compatible linkers +; +; _DLL_ - functions are exported and imported with added +; size specifiers (_SomeFunction@12), lcmret adjusts +; stack (stdcall) +; +; _MSLIBS_ - the lcmwinextern macro prepends an underscore and +; adds size specification for functions, allowing +; the object file to be linked with MS libraries. +; +; ==================================================================== + +%ifndef NASMLCM_INC_INCLUDED +%define NASMLCM_INC_INCLUDED + +%ifdef _DLL_ + %ifndef _OBJ_ + %error "_DLL_ needs _OBJ_ defined!" + %endif +%endif + +; --- define lcm- section names --- +; +; a number of linkers require omf objects where the section +; names are equal to those produces by tasm. + +%ifdef _OBJ_ + + %define lcmtext _TEXT class=CODE public use32 align=4 FLAT + %define lcmdata _DATA class=DATA public use32 align=4 + %define lcmbss _BSS class=BSS public use32 align=4 FLAT + + group FLAT + group DGROUP _DATA + +%else ; _OBJ_ + + %define lcmtext .text + %define lcmdata .data + %define lcmbss .bss + +%endif ; _OBJ_ + +; --- define lcmglobal and lcm*extern macros --- +; +; special handling of functions and data for ELF32 + +%ifdef _ELF_ + + %macro lcmglobal 2 + global %{1}:function + %endmacro + %macro lcmglobal 1 + global %{1}:data + %endmacro + + %define lcmcglobal lcmglobal + + %macro lcmextern 1-2 + extern %1 + %endmacro + + %macro lcmcextern 0 + %error lcmcextern not supported in ELF format + %endmacro + + %macro lcmdllextern 0 + %error lcmdllextern not supported in ELF format + %endmacro + +%else ; _ELF_ + + %ifdef _DLL_ + + %macro lcmglobal 2 + global _%1 + global _%1@%2 + %endmacro + %macro lcmglobal 1 + global _%1 + %define %1 _%1 + %endmacro + + %macro lcmcglobal 2 + global _%1 + %endmacro + %macro lcmcglobal 1 + global _%1 + %define %1 _%1 + %endmacro + + %macro lcmextern 2 + extern _%1@%2 + %define %1 _%1@%2 + %endmacro + %macro lcmextern 1 + extern _%1 + %define %1 _%1 + %endmacro + + %else + + %macro lcmglobal 2 + global _%1 + %endmacro + %macro lcmglobal 1 + global _%1 + %define %1 _%1 + %endmacro + + %define lcmcglobal lcmglobal + + %macro lcmextern 1-2 + extern _%1 + %define %1 _%1 + %endmacro + + %endif + + %macro lcmcextern 1-2 + extern _%1 + %define %1 _%1 + %endmacro + + %macro lcmdllextern 2 + extern _%1@%2 + %define %1 _%1@%2 + %endmacro + %macro lcmdllextern 1 + extern _%1 + %define %1 _%1 + %endmacro + + %macro lcmwinextern 2 + %ifdef _MSLIBS_ + extern _%1@%2 + %define %1 _%1@%2 + %else + extern %1 + %endif + %endmacro + +%endif ; _ELF_ + +; --- define lcmimport and lcmexport --- +; + +%ifdef _OBJ_ + + %macro lcmimport 2-3 + import %1 %2 %3 + %rotate 1 + %endmacro + + %ifdef _DLL_ + + %macro lcmexport 2 + export _%1 + export _%1@%2 + %endmacro + %macro lcmexport 1 + export _%1 + %endmacro + + %else + + %macro lcmexport 1-2 + %endmacro + + %endif + +%else ; _OBJ_ + + %macro lcmimport 2-3 + %endmacro + + %macro lcmexport 1-2 + %endmacro + +%endif ; _OBJ_ + +; --- define lcmlabel, lcmadjust and lcmret macros --- +; +; we need special labels and stdcall calling convention when +; assembling for a dll + +%ifdef _ELF_ + + %macro lcmlabel 2 + %1: + %endmacro + + %define lcmclabel lcmlabel + + %macro lcmadjust 1 + %if %1 < 128 + add esp, byte %1 + %else + add esp, %1 + %endif + %endmacro + + %macro lcmret 1 + ret + %endmacro + + %define lcmcret lcmret + +%else ; _ELF_ + + %ifdef _DLL_ + %macro lcmlabel 2 + _%1: + _%1@%2: + %endmacro + + %macro lcmclabel 2 + _%1: + %endmacro + + %macro lcmadjust 1 + %endmacro + + %macro lcmret 1 + %if %1 > 0 + ret %1 + %else + ret + %endif + %endmacro + + %macro lcmcret 1 + ret + %endmacro + + %else + + %macro lcmlabel 2 + _%1: + %endmacro + + %define lcmclabel lcmlabel + + %macro lcmadjust 1 + %if %1 < 128 + add esp, byte %1 + %else + add esp, %1 + %endif + %endmacro + + %macro lcmret 1 + ret + %endmacro + + %define lcmcret lcmret + %endif + +%endif ; _ELF_ + +%endif ; NASMLCM_INC_INCLUDED diff --git a/test/monniaux/uzlib/src/nasm/tinfzlib.nas b/test/monniaux/uzlib/src/nasm/tinfzlib.nas new file mode 100644 index 00000000..1f9519eb --- /dev/null +++ b/test/monniaux/uzlib/src/nasm/tinfzlib.nas @@ -0,0 +1,160 @@ +;; +;; tinfzlib - tiny zlib uncompress +;; +;; Copyright (c) 2003 by Joergen Ibsen / Jibz +;; All Rights Reserved +;; +;; http://www.ibsensoftware.com/ +;; +;; This software is provided 'as-is', without any express +;; or implied warranty. In no event will the authors be +;; held liable for any damages arising from the use of +;; this software. +;; +;; Permission is granted to anyone to use this software +;; for any purpose, including commercial applications, +;; and to alter it and redistribute it freely, subject to +;; the following restrictions: +;; +;; 1. The origin of this software must not be +;; misrepresented; you must not claim that you +;; wrote the original software. If you use this +;; software in a product, an acknowledgment in +;; the product documentation would be appreciated +;; but is not required. +;; +;; 2. Altered source versions must be plainly marked +;; as such, and must not be misrepresented as +;; being the original software. +;; +;; 3. This notice may not be removed or altered from +;; any source distribution. +;; + +TINF_OK equ 0 +TINF_DATA_ERROR equ (-3) + +cpu 386 + +bits 32 + +%include "nasmlcm.inc" + +section lcmtext + +lcmglobal tinf_zlib_uncompress,16 + +lcmexport tinf_zlib_uncompress,16 + +lcmextern tinf_uncompress,16 +lcmextern tinf_adler32,8 + +; ============================================================= + +lcmlabel tinf_zlib_uncompress,16 + ; tinf_zlib_uncompress(void *dest, + ; unsigned int *destLen, + ; const void *source, + ; unsigned int sourceLen) + + .slen$ equ 2*4 + 4 + 12 + .src$ equ 2*4 + 4 + 8 + .dlen$ equ 2*4 + 4 + 4 + .dst$ equ 2*4 + 4 + + push esi + push ebx + + mov esi, [esp + .src$] ; esi -> source + + ; -- get header bytes -- + + movzx eax, word [esi] ; al = cmf, ah = flg, + + ; -- check format -- + + ; check method is deflate + ; if ((cmf & 0x0f) != 8) return TINF_DATA_ERROR; + mov cl, 0x0f + and cl, al + cmp cl, 8 + jne short .return_error + + ; check window size is valid + ; if ((cmf >> 4) > 7) return TINF_DATA_ERROR; + mov ch, al + shr ch, 4 + cmp ch, cl ; cl = 8 from above + jae short .return_error + + ; check there is no preset dictionary + ; if (flg & 0x20) return TINF_DATA_ERROR; + test ah, 0x20 + jnz short .return_error + + ; check checksum + ; if ((256*cmf + flg) % 31) return TINF_DATA_ERROR; + xchg al, ah + xor edx, edx + lea ebx, [edx + 31] + div ebx + test edx, edx + jnz short .return_error + + ; -- get adler32 checksum -- + + mov ecx, [esp + .slen$] ; ecx = sourceLen + mov ebx, [esi + ecx - 4] + + %ifdef BSWAP_OK + bswap ebx + %else ; BSWAP_OK + xchg bl, bh + rol ebx, 16 + xchg bl, bh + %endif ; BSWAP_OK + + ; -- inflate -- + + ; res = tinf_uncompress(dst, destLen, src + 2, sourceLen - 6); + lea eax, [ecx - 6] + push eax + lea eax, [esi + 2] + push eax + push dword [esp + 8 + .dlen$] + push dword [esp + 12 + .dst$] + call tinf_uncompress + add esp, byte 16 + + ; if (res != TINF_OK) return TINF_DATA_ERROR; + test eax, eax + jnz short .return_error + + ; -- check adler32 checksum -- + + ; if (a32 != tinf_adler32(dst, *destLen)) return TINF_DATA_ERROR; + mov eax, [esp + .dlen$]; + push dword [eax] + push dword [esp + 4 + .dst$] + call tinf_adler32 + add esp, byte 8 + + sub eax, ebx + jz short .return_eax + + .return_error: + mov eax, TINF_DATA_ERROR + + .return_eax: + pop ebx + pop esi + + lcmret 16 + +; ============================================================= + +%ifdef _OBJ_ + section lcmdata +%endif + +; ============================================================= diff --git a/test/monniaux/uzlib/src/tinf.h b/test/monniaux/uzlib/src/tinf.h new file mode 100644 index 00000000..ae6e1c40 --- /dev/null +++ b/test/monniaux/uzlib/src/tinf.h @@ -0,0 +1,3 @@ +/* Compatibility header for the original tinf lib/older versions of uzlib. + Note: may be removed in the future, please migrate to uzlib.h. */ +#include "uzlib.h" diff --git a/test/monniaux/uzlib/src/tinf_compat.h b/test/monniaux/uzlib/src/tinf_compat.h new file mode 100644 index 00000000..f763804b --- /dev/null +++ b/test/monniaux/uzlib/src/tinf_compat.h @@ -0,0 +1,9 @@ +/* This header contains compatibility defines for the original tinf API + and uzlib 2.x and below API. These defines are deprecated and going + to be removed in the future, so applications should migrate to new + uzlib API. */ +#define TINF_DATA struct uzlib_uncomp + +#define destSize dest_size +#define destStart dest_start +#define readSource source_read_cb diff --git a/test/monniaux/uzlib/src/tinfgzip.c b/test/monniaux/uzlib/src/tinfgzip.c new file mode 100644 index 00000000..22b000df --- /dev/null +++ b/test/monniaux/uzlib/src/tinfgzip.c @@ -0,0 +1,110 @@ +/* + * uzlib - tiny deflate/inflate library (deflate, gzip, zlib) + * + * Copyright (c) 2003 by Joergen Ibsen / Jibz + * All Rights Reserved + * + * http://www.ibsensoftware.com/ + * + * Copyright (c) 2014-2018 by Paul Sokolovsky + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +#include "tinf.h" + +#define FTEXT 1 +#define FHCRC 2 +#define FEXTRA 4 +#define FNAME 8 +#define FCOMMENT 16 + +void tinf_skip_bytes(TINF_DATA *d, int num); +uint16_t tinf_get_uint16(TINF_DATA *d); + +void tinf_skip_bytes(TINF_DATA *d, int num) +{ + while (num--) uzlib_get_byte(d); +} + +uint16_t tinf_get_uint16(TINF_DATA *d) +{ + unsigned int v = uzlib_get_byte(d); + v = (uzlib_get_byte(d) << 8) | v; + return v; +} + +int uzlib_gzip_parse_header(TINF_DATA *d) +{ + unsigned char flg; + + /* -- check format -- */ + + /* check id bytes */ + if (uzlib_get_byte(d) != 0x1f || uzlib_get_byte(d) != 0x8b) return TINF_DATA_ERROR; + + /* check method is deflate */ + if (uzlib_get_byte(d) != 8) return TINF_DATA_ERROR; + + /* get flag byte */ + flg = uzlib_get_byte(d); + + /* check that reserved bits are zero */ + if (flg & 0xe0) return TINF_DATA_ERROR; + + /* -- find start of compressed data -- */ + + /* skip rest of base header of 10 bytes */ + tinf_skip_bytes(d, 6); + + /* skip extra data if present */ + if (flg & FEXTRA) + { + unsigned int xlen = tinf_get_uint16(d); + tinf_skip_bytes(d, xlen); + } + + /* skip file name if present */ + if (flg & FNAME) { while (uzlib_get_byte(d)); } + + /* skip file comment if present */ + if (flg & FCOMMENT) { while (uzlib_get_byte(d)); } + + /* check header crc if present */ + if (flg & FHCRC) + { + /*unsigned int hcrc =*/ tinf_get_uint16(d); + + // TODO: Check! +// if (hcrc != (tinf_crc32(src, start - src) & 0x0000ffff)) +// return TINF_DATA_ERROR; + } + + /* initialize for crc32 checksum */ + d->checksum_type = TINF_CHKSUM_CRC; + d->checksum = ~0; + + return TINF_OK; +} diff --git a/test/monniaux/uzlib/src/tinflate.c b/test/monniaux/uzlib/src/tinflate.c new file mode 100644 index 00000000..cfb9b4c5 --- /dev/null +++ b/test/monniaux/uzlib/src/tinflate.c @@ -0,0 +1,661 @@ +/* + * uzlib - tiny deflate/inflate library (deflate, gzip, zlib) + * + * Copyright (c) 2003 by Joergen Ibsen / Jibz + * All Rights Reserved + * http://www.ibsensoftware.com/ + * + * Copyright (c) 2014-2018 by Paul Sokolovsky + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +#include +#include "tinf.h" + +#define UZLIB_DUMP_ARRAY(heading, arr, size) \ + { \ + printf("%s", heading); \ + for (int i = 0; i < size; ++i) { \ + printf(" %d", (arr)[i]); \ + } \ + printf("\n"); \ + } + +uint32_t tinf_get_le_uint32(TINF_DATA *d); +uint32_t tinf_get_be_uint32(TINF_DATA *d); + +/* --------------------------------------------------- * + * -- uninitialized global data (static structures) -- * + * --------------------------------------------------- */ + +#ifdef RUNTIME_BITS_TABLES + +/* extra bits and base tables for length codes */ +unsigned char length_bits[30]; +unsigned short length_base[30]; + +/* extra bits and base tables for distance codes */ +unsigned char dist_bits[30]; +unsigned short dist_base[30]; + +#else + +const unsigned char length_bits[30] = { + 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 +}; +const unsigned short length_base[30] = { + 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 +}; + +const unsigned char dist_bits[30] = { + 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, 12, 12, 13, 13 +}; +const unsigned short dist_base[30] = { + 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, 8193, 12289, 16385, 24577 +}; + +#endif + +/* special ordering of code length codes */ +const unsigned char clcidx[] = { + 16, 17, 18, 0, 8, 7, 9, 6, + 10, 5, 11, 4, 12, 3, 13, 2, + 14, 1, 15 +}; + +/* ----------------------- * + * -- utility functions -- * + * ----------------------- */ + +#ifdef RUNTIME_BITS_TABLES +/* build extra bits and base tables */ +static void tinf_build_bits_base(unsigned char *bits, unsigned short *base, int delta, int first) +{ + int i, sum; + + /* build bits table */ + for (i = 0; i < delta; ++i) bits[i] = 0; + for (i = 0; i < 30 - delta; ++i) bits[i + delta] = i / delta; + + /* build base table */ + for (sum = first, i = 0; i < 30; ++i) + { + base[i] = sum; + sum += 1 << bits[i]; + } +} +#endif + +/* build the fixed huffman trees */ +static void tinf_build_fixed_trees(TINF_TREE *lt, TINF_TREE *dt) +{ + int i; + + /* build fixed length tree */ + for (i = 0; i < 7; ++i) lt->table[i] = 0; + + lt->table[7] = 24; + lt->table[8] = 152; + lt->table[9] = 112; + + for (i = 0; i < 24; ++i) lt->trans[i] = 256 + i; + for (i = 0; i < 144; ++i) lt->trans[24 + i] = i; + for (i = 0; i < 8; ++i) lt->trans[24 + 144 + i] = 280 + i; + for (i = 0; i < 112; ++i) lt->trans[24 + 144 + 8 + i] = 144 + i; + + /* build fixed distance tree */ + for (i = 0; i < 5; ++i) dt->table[i] = 0; + + dt->table[5] = 32; + + for (i = 0; i < 32; ++i) dt->trans[i] = i; +} + +/* given an array of code lengths, build a tree */ +static void tinf_build_tree(TINF_TREE *t, const unsigned char *lengths, unsigned int num) +{ + unsigned short offs[16]; + unsigned int i, sum; + + /* clear code length count table */ + for (i = 0; i < 16; ++i) t->table[i] = 0; + + /* scan symbol lengths, and sum code length counts */ + for (i = 0; i < num; ++i) t->table[lengths[i]]++; + + #if UZLIB_CONF_DEBUG_LOG >= 2 + UZLIB_DUMP_ARRAY("codelen counts:", t->table, TINF_ARRAY_SIZE(t->table)); + #endif + + /* In the lengths array, 0 means unused code. So, t->table[0] now contains + number of unused codes. But table's purpose is to contain # of codes of + particular length, and there're 0 codes of length 0. */ + t->table[0] = 0; + + /* compute offset table for distribution sort */ + for (sum = 0, i = 0; i < 16; ++i) + { + offs[i] = sum; + sum += t->table[i]; + } + + #if UZLIB_CONF_DEBUG_LOG >= 2 + UZLIB_DUMP_ARRAY("codelen offsets:", offs, TINF_ARRAY_SIZE(offs)); + #endif + + /* create code->symbol translation table (symbols sorted by code) */ + for (i = 0; i < num; ++i) + { + if (lengths[i]) t->trans[offs[lengths[i]]++] = i; + } +} + +/* ---------------------- * + * -- decode functions -- * + * ---------------------- */ + +unsigned char uzlib_get_byte(TINF_DATA *d) +{ + /* If end of source buffer is not reached, return next byte from source + buffer. */ + if (d->source < d->source_limit) { + return *d->source++; + } + +#ifndef UZLIB_NO_CALLBACK + /* Otherwise if there's callback and we haven't seen EOF yet, try to + read next byte using it. (Note: the callback can also update ->source + and ->source_limit). */ + if (d->readSource && !d->eof) { + int val = d->readSource(d); + if (val >= 0) { + return (unsigned char)val; + } + } +#endif + + /* Otherwise, we hit EOF (either from ->readSource() or from exhaustion + of the buffer), and it will be "sticky", i.e. further calls to this + function will end up here too. */ + d->eof = true; + + return 0; +} + +uint32_t tinf_get_le_uint32(TINF_DATA *d) +{ + uint32_t val = 0; + int i; + for (i = 4; i--;) { + val = val >> 8 | ((uint32_t)uzlib_get_byte(d)) << 24; + } + return val; +} + +uint32_t tinf_get_be_uint32(TINF_DATA *d) +{ + uint32_t val = 0; + int i; + for (i = 4; i--;) { + val = val << 8 | uzlib_get_byte(d); + } + return val; +} + +/* get one bit from source stream */ +static int tinf_getbit(TINF_DATA *d) +{ + unsigned int bit; + + /* check if tag is empty */ + if (!d->bitcount--) + { + /* load next tag */ + d->tag = uzlib_get_byte(d); + d->bitcount = 7; + } + + /* shift bit out of tag */ + bit = d->tag & 0x01; + d->tag >>= 1; + + return bit; +} + +/* read a num bit value from a stream and add base */ +static unsigned int tinf_read_bits(TINF_DATA *d, int num, int base) +{ + unsigned int val = 0; + + /* read num bits */ + if (num) + { + unsigned int limit = 1 << (num); + unsigned int mask; + + for (mask = 1; mask < limit; mask *= 2) + if (tinf_getbit(d)) val += mask; + } + + return val + base; +} + +/* given a data stream and a tree, decode a symbol */ +static int tinf_decode_symbol(TINF_DATA *d, TINF_TREE *t) +{ + int sum = 0, cur = 0, len = 0; + + /* get more bits while code value is above sum */ + do { + + cur = 2*cur + tinf_getbit(d); + + if (++len == TINF_ARRAY_SIZE(t->table)) { + return TINF_DATA_ERROR; + } + + sum += t->table[len]; + cur -= t->table[len]; + + } while (cur >= 0); + + sum += cur; + #if UZLIB_CONF_PARANOID_CHECKS + if (sum < 0 || sum >= TINF_ARRAY_SIZE(t->trans)) { + return TINF_DATA_ERROR; + } + #endif + + return t->trans[sum]; +} + +/* given a data stream, decode dynamic trees from it */ +static int tinf_decode_trees(TINF_DATA *d, TINF_TREE *lt, TINF_TREE *dt) +{ + /* code lengths for 288 literal/len symbols and 32 dist symbols */ + unsigned char lengths[288+32]; + unsigned int hlit, hdist, hclen, hlimit; + unsigned int i, num, length; + + /* get 5 bits HLIT (257-286) */ + hlit = tinf_read_bits(d, 5, 257); + + /* get 5 bits HDIST (1-32) */ + hdist = tinf_read_bits(d, 5, 1); + + /* get 4 bits HCLEN (4-19) */ + hclen = tinf_read_bits(d, 4, 4); + + for (i = 0; i < 19; ++i) lengths[i] = 0; + + /* read code lengths for code length alphabet */ + for (i = 0; i < hclen; ++i) + { + /* get 3 bits code length (0-7) */ + unsigned int clen = tinf_read_bits(d, 3, 0); + + lengths[clcidx[i]] = clen; + } + + /* build code length tree, temporarily use length tree */ + tinf_build_tree(lt, lengths, 19); + + /* decode code lengths for the dynamic trees */ + hlimit = hlit + hdist; + for (num = 0; num < hlimit; ) + { + int sym = tinf_decode_symbol(d, lt); + unsigned char fill_value = 0; + int lbits, lbase = 3; + + /* error decoding */ + if (sym < 0) return sym; + + switch (sym) + { + case 16: + /* copy previous code length 3-6 times (read 2 bits) */ + if (num == 0) return TINF_DATA_ERROR; + fill_value = lengths[num - 1]; + lbits = 2; + break; + case 17: + /* repeat code length 0 for 3-10 times (read 3 bits) */ + lbits = 3; + break; + case 18: + /* repeat code length 0 for 11-138 times (read 7 bits) */ + lbits = 7; + lbase = 11; + break; + default: + /* values 0-15 represent the actual code lengths */ + lengths[num++] = sym; + /* continue the for loop */ + continue; + } + + /* special code length 16-18 are handled here */ + length = tinf_read_bits(d, lbits, lbase); + if (num + length > hlimit) return TINF_DATA_ERROR; + for (; length; --length) + { + lengths[num++] = fill_value; + } + } + + #if UZLIB_CONF_DEBUG_LOG >= 2 + printf("lit code lengths (%d):", hlit); + UZLIB_DUMP_ARRAY("", lengths, hlit); + printf("dist code lengths (%d):", hdist); + UZLIB_DUMP_ARRAY("", lengths + hlit, hdist); + #endif + + #if UZLIB_CONF_PARANOID_CHECKS + /* Check that there's "end of block" symbol */ + if (lengths[256] == 0) { + return TINF_DATA_ERROR; + } + #endif + + /* build dynamic trees */ + tinf_build_tree(lt, lengths, hlit); + tinf_build_tree(dt, lengths + hlit, hdist); + + return TINF_OK; +} + +/* ----------------------------- * + * -- block inflate functions -- * + * ----------------------------- */ + +/* given a stream and two trees, inflate next byte of output */ +static int tinf_inflate_block_data(TINF_DATA *d, TINF_TREE *lt, TINF_TREE *dt) +{ + if (d->curlen == 0) { + unsigned int offs; + int dist; + int sym = tinf_decode_symbol(d, lt); + //printf("huff sym: %02x\n", sym); + + if (d->eof) { + return TINF_DATA_ERROR; + } + + /* literal byte */ + if (sym < 256) { + TINF_PUT(d, sym); + return TINF_OK; + } + + /* end of block */ + if (sym == 256) { + return TINF_DONE; + } + + /* substring from sliding dictionary */ + sym -= 257; + if (sym >= 29) { + return TINF_DATA_ERROR; + } + + /* possibly get more bits from length code */ + d->curlen = tinf_read_bits(d, length_bits[sym], length_base[sym]); + + dist = tinf_decode_symbol(d, dt); + if (dist >= 30) { + return TINF_DATA_ERROR; + } + + /* possibly get more bits from distance code */ + offs = tinf_read_bits(d, dist_bits[dist], dist_base[dist]); + + /* calculate and validate actual LZ offset to use */ + if (d->dict_ring) { + if (offs > d->dict_size) { + return TINF_DICT_ERROR; + } + /* Note: unlike full-dest-in-memory case below, we don't + try to catch offset which points to not yet filled + part of the dictionary here. Doing so would require + keeping another variable to track "filled in" size + of the dictionary. Appearance of such an offset cannot + lead to accessing memory outside of the dictionary + buffer, and clients which don't want to leak unrelated + information, should explicitly initialize dictionary + buffer passed to uzlib. */ + + d->lzOff = d->dict_idx - offs; + if (d->lzOff < 0) { + d->lzOff += d->dict_size; + } + } else { + /* catch trying to point before the start of dest buffer */ + if (offs > d->dest - d->destStart) { + return TINF_DATA_ERROR; + } + d->lzOff = -offs; + } + } + + /* copy next byte from dict substring */ + if (d->dict_ring) { + TINF_PUT(d, d->dict_ring[d->lzOff]); + if ((unsigned)++d->lzOff == d->dict_size) { + d->lzOff = 0; + } + } else { + d->dest[0] = d->dest[d->lzOff]; + d->dest++; + } + d->curlen--; + return TINF_OK; +} + +/* inflate next byte from uncompressed block of data */ +static int tinf_inflate_uncompressed_block(TINF_DATA *d) +{ + if (d->curlen == 0) { + unsigned int length, invlength; + + /* get length */ + length = uzlib_get_byte(d); + length += 256 * uzlib_get_byte(d); + /* get one's complement of length */ + invlength = uzlib_get_byte(d); + invlength += 256 * uzlib_get_byte(d); + /* check length */ + if (length != (~invlength & 0x0000ffff)) return TINF_DATA_ERROR; + + /* increment length to properly return TINF_DONE below, without + producing data at the same time */ + d->curlen = length + 1; + + /* make sure we start next block on a byte boundary */ + d->bitcount = 0; + } + + if (--d->curlen == 0) { + return TINF_DONE; + } + + unsigned char c = uzlib_get_byte(d); + TINF_PUT(d, c); + return TINF_OK; +} + +/* ---------------------- * + * -- public functions -- * + * ---------------------- */ + +/* initialize global (static) data */ +void uzlib_init(void) +{ +#ifdef RUNTIME_BITS_TABLES + /* build extra bits and base tables */ + tinf_build_bits_base(length_bits, length_base, 4, 3); + tinf_build_bits_base(dist_bits, dist_base, 2, 1); + + /* fix a special case */ + length_bits[28] = 0; + length_base[28] = 258; +#endif +} + +/* initialize decompression structure */ +void uzlib_uncompress_init(TINF_DATA *d, void *dict, unsigned int dictLen) +{ + d->eof = 0; + d->bitcount = 0; + d->bfinal = 0; + d->btype = -1; + d->dict_size = dictLen; + d->dict_ring = dict; + d->dict_idx = 0; + d->curlen = 0; +} + +/* inflate next output bytes from compressed stream */ +int uzlib_uncompress(TINF_DATA *d) +{ + do { + int res; + + /* start a new block */ + if (d->btype == -1) { +next_blk: + /* read final block flag */ + d->bfinal = tinf_getbit(d); + /* read block type (2 bits) */ + d->btype = tinf_read_bits(d, 2, 0); + + #if UZLIB_CONF_DEBUG_LOG >= 1 + printf("Started new block: type=%d final=%d\n", d->btype, d->bfinal); + #endif + + if (d->btype == 1) { + /* build fixed huffman trees */ + tinf_build_fixed_trees(&d->ltree, &d->dtree); + } else if (d->btype == 2) { + /* decode trees from stream */ + res = tinf_decode_trees(d, &d->ltree, &d->dtree); + if (res != TINF_OK) { + return res; + } + } + } + + /* process current block */ + switch (d->btype) + { + case 0: + /* decompress uncompressed block */ + res = tinf_inflate_uncompressed_block(d); + break; + case 1: + case 2: + /* decompress block with fixed/dynamic huffman trees */ + /* trees were decoded previously, so it's the same routine for both */ + res = tinf_inflate_block_data(d, &d->ltree, &d->dtree); + break; + default: + return TINF_DATA_ERROR; + } + + if (res == TINF_DONE && !d->bfinal) { + /* the block has ended (without producing more data), but we + can't return without data, so start procesing next block */ + goto next_blk; + } + + if (res != TINF_OK) { + return res; + } + + } while (d->dest < d->dest_limit); + + return TINF_OK; +} + +/* inflate next output bytes from compressed stream, updating + checksum, and at the end of stream, verify it */ +int uzlib_uncompress_chksum(TINF_DATA *d) +{ + int res; + unsigned char *data = d->dest; + + res = uzlib_uncompress(d); + + if (res < 0) return res; + + switch (d->checksum_type) { + + case TINF_CHKSUM_ADLER: + d->checksum = uzlib_adler32(data, d->dest - data, d->checksum); + break; + + case TINF_CHKSUM_CRC: + d->checksum = uzlib_crc32(data, d->dest - data, d->checksum); + break; + } + + if (res == TINF_DONE) { + unsigned int val; + + switch (d->checksum_type) { + + case TINF_CHKSUM_ADLER: + val = tinf_get_be_uint32(d); + if (d->checksum != val) { + return TINF_CHKSUM_ERROR; + } + break; + + case TINF_CHKSUM_CRC: + val = tinf_get_le_uint32(d); + if (~d->checksum != val) { + return TINF_CHKSUM_ERROR; + } + // Uncompressed size. TODO: Check + val = tinf_get_le_uint32(d); + break; + } + } + + return res; +} diff --git a/test/monniaux/uzlib/src/tinfzlib.c b/test/monniaux/uzlib/src/tinfzlib.c new file mode 100644 index 00000000..5cb8852f --- /dev/null +++ b/test/monniaux/uzlib/src/tinfzlib.c @@ -0,0 +1,66 @@ +/* + * uzlib - tiny deflate/inflate library (deflate, gzip, zlib) + * + * Copyright (c) 2003 by Joergen Ibsen / Jibz + * All Rights Reserved + * + * http://www.ibsensoftware.com/ + * + * Copyright (c) 2014-2018 by Paul Sokolovsky + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +#include "tinf.h" + +int uzlib_zlib_parse_header(TINF_DATA *d) +{ + unsigned char cmf, flg; + + /* -- get header bytes -- */ + + cmf = uzlib_get_byte(d); + flg = uzlib_get_byte(d); + + /* -- check format -- */ + + /* check checksum */ + if ((256*cmf + flg) % 31) return TINF_DATA_ERROR; + + /* check method is deflate */ + if ((cmf & 0x0f) != 8) return TINF_DATA_ERROR; + + /* check window size is valid */ + if ((cmf >> 4) > 7) return TINF_DATA_ERROR; + + /* check there is no preset dictionary */ + if (flg & 0x20) return TINF_DATA_ERROR; + + /* initialize for adler32 checksum */ + d->checksum_type = TINF_CHKSUM_ADLER; + d->checksum = 1; + + return cmf >> 4; +} diff --git a/test/monniaux/uzlib/src/uzlib.h b/test/monniaux/uzlib/src/uzlib.h new file mode 100644 index 00000000..3a4a1ad1 --- /dev/null +++ b/test/monniaux/uzlib/src/uzlib.h @@ -0,0 +1,169 @@ +/* + * uzlib - tiny deflate/inflate library (deflate, gzip, zlib) + * + * Copyright (c) 2003 by Joergen Ibsen / Jibz + * All Rights Reserved + * http://www.ibsensoftware.com/ + * + * Copyright (c) 2014-2018 by Paul Sokolovsky + * + * This software is provided 'as-is', without any express + * or implied warranty. In no event will the authors be + * held liable for any damages arising from the use of + * this software. + * + * Permission is granted to anyone to use this software + * for any purpose, including commercial applications, + * and to alter it and redistribute it freely, subject to + * the following restrictions: + * + * 1. The origin of this software must not be + * misrepresented; you must not claim that you + * wrote the original software. If you use this + * software in a product, an acknowledgment in + * the product documentation would be appreciated + * but is not required. + * + * 2. Altered source versions must be plainly marked + * as such, and must not be misrepresented as + * being the original software. + * + * 3. This notice may not be removed or altered from + * any source distribution. + */ + +#ifndef UZLIB_H_INCLUDED +#define UZLIB_H_INCLUDED + +#include +#include +#include + +#include "defl_static.h" + +#include "uzlib_conf.h" +#if UZLIB_CONF_DEBUG_LOG +#include +#endif + +/* calling convention */ +#ifndef TINFCC + #ifdef __WATCOMC__ + #define TINFCC __cdecl + #else + #define TINFCC + #endif +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/* ok status, more data produced */ +#define TINF_OK 0 +/* end of compressed stream reached */ +#define TINF_DONE 1 +#define TINF_DATA_ERROR (-3) +#define TINF_CHKSUM_ERROR (-4) +#define TINF_DICT_ERROR (-5) + +/* checksum types */ +#define TINF_CHKSUM_NONE 0 +#define TINF_CHKSUM_ADLER 1 +#define TINF_CHKSUM_CRC 2 + +/* helper macros */ +#define TINF_ARRAY_SIZE(arr) (sizeof(arr) / sizeof(*(arr))) + +/* data structures */ + +typedef struct { + unsigned short table[16]; /* table of code length counts */ + unsigned short trans[288]; /* code -> symbol translation table */ +} TINF_TREE; + +struct uzlib_uncomp { + /* Pointer to the next byte in the input buffer */ + const unsigned char *source; + /* Pointer to the next byte past the input buffer (source_limit = source + len) */ + const unsigned char *source_limit; + /* If source_limit == NULL, or source >= source_limit, this function + will be used to read next byte from source stream. The function may + also return -1 in case of EOF (or irrecoverable error). Note that + besides returning the next byte, it may also update source and + source_limit fields, thus allowing for buffered operation. */ + int (*source_read_cb)(struct uzlib_uncomp *uncomp); + + unsigned int tag; + unsigned int bitcount; + + /* Destination (output) buffer start */ + unsigned char *dest_start; + /* Current pointer in dest buffer */ + unsigned char *dest; + /* Pointer past the end of the dest buffer, similar to source_limit */ + unsigned char *dest_limit; + + /* Accumulating checksum */ + unsigned int checksum; + char checksum_type; + bool eof; + + int btype; + int bfinal; + unsigned int curlen; + int lzOff; + unsigned char *dict_ring; + unsigned int dict_size; + unsigned int dict_idx; + + TINF_TREE ltree; /* dynamic length/symbol tree */ + TINF_TREE dtree; /* dynamic distance tree */ +}; + +#include "tinf_compat.h" + +#define TINF_PUT(d, c) \ + { \ + *d->dest++ = c; \ + if (d->dict_ring) { d->dict_ring[d->dict_idx++] = c; if (d->dict_idx == d->dict_size) d->dict_idx = 0; } \ + } + +unsigned char TINFCC uzlib_get_byte(TINF_DATA *d); + +/* Decompression API */ + +void TINFCC uzlib_init(void); +void TINFCC uzlib_uncompress_init(TINF_DATA *d, void *dict, unsigned int dictLen); +int TINFCC uzlib_uncompress(TINF_DATA *d); +int TINFCC uzlib_uncompress_chksum(TINF_DATA *d); + +int TINFCC uzlib_zlib_parse_header(TINF_DATA *d); +int TINFCC uzlib_gzip_parse_header(TINF_DATA *d); + +/* Compression API */ + +typedef const uint8_t *uzlib_hash_entry_t; + +struct uzlib_comp { + struct Outbuf out; + + uzlib_hash_entry_t *hash_table; + unsigned int hash_bits; + unsigned int dict_size; +}; + +void TINFCC uzlib_compress(struct uzlib_comp *c, const uint8_t *src, unsigned slen); + +/* Checksum API */ + +/* prev_sum is previous value for incremental computation, 1 initially */ +uint32_t TINFCC uzlib_adler32(const void *data, unsigned int length, uint32_t prev_sum); +/* crc is previous value for incremental computation, 0xffffffff initially */ +uint32_t TINFCC uzlib_crc32(const void *data, unsigned int length, uint32_t crc); + +#ifdef __cplusplus +} /* extern "C" */ +#endif + +#endif /* UZLIB_H_INCLUDED */ diff --git a/test/monniaux/uzlib/src/uzlib_conf.h b/test/monniaux/uzlib/src/uzlib_conf.h new file mode 100644 index 00000000..d6c94071 --- /dev/null +++ b/test/monniaux/uzlib/src/uzlib_conf.h @@ -0,0 +1,22 @@ +/* + * uzlib - tiny deflate/inflate library (deflate, gzip, zlib) + * + * Copyright (c) 2014-2018 by Paul Sokolovsky + */ + +#ifndef UZLIB_CONF_H_INCLUDED +#define UZLIB_CONF_H_INCLUDED + +#ifndef UZLIB_CONF_DEBUG_LOG +/* Debug logging level 0, 1, 2, etc. */ +#define UZLIB_CONF_DEBUG_LOG 0 +#endif + +#ifndef UZLIB_CONF_PARANOID_CHECKS +/* Perform extra checks on the input stream, even if they aren't proven + to be strictly required (== lack of them wasn't proven to lead to + crashes). */ +#define UZLIB_CONF_PARANOID_CHECKS 0 +#endif + +#endif /* UZLIB_CONF_H_INCLUDED */ -- cgit From 258b99426446ac7b12b6f5736362a9f7daa979de Mon Sep 17 00:00:00 2001 From: David Monniaux Date: Tue, 29 Jan 2019 22:41:27 +0100 Subject: no need for this anymore --- test/monniaux/uzlib/src/tinflate.c | 2 -- 1 file changed, 2 deletions(-) (limited to 'test/monniaux/uzlib/src') diff --git a/test/monniaux/uzlib/src/tinflate.c b/test/monniaux/uzlib/src/tinflate.c index cfb9b4c5..b93bc1fa 100644 --- a/test/monniaux/uzlib/src/tinflate.c +++ b/test/monniaux/uzlib/src/tinflate.c @@ -197,7 +197,6 @@ unsigned char uzlib_get_byte(TINF_DATA *d) return *d->source++; } -#ifndef UZLIB_NO_CALLBACK /* Otherwise if there's callback and we haven't seen EOF yet, try to read next byte using it. (Note: the callback can also update ->source and ->source_limit). */ @@ -207,7 +206,6 @@ unsigned char uzlib_get_byte(TINF_DATA *d) return (unsigned char)val; } } -#endif /* Otherwise, we hit EOF (either from ->readSource() or from exhaustion of the buffer), and it will be "sticky", i.e. further calls to this -- cgit