⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 unzip.c

📁 这是一个SIGMA方案的PMP播放器的UCLINUX程序,可播放DVD,VCD,CD MP3...有很好的参考价值.
💻 C
📖 第 1 页 / 共 2 页
字号:
    8193, 12289, 16385, 24577};static const extra_bits_t cpdext[] = {  /* Extra bits for distance codes */    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};/* Tables for deflate from PKZIP's appnote.txt. */static const extra_bits_t border[] = {  /* Order of the bit length code lengths */    16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15};/* * decompress an inflated block * e: last block flag * * GLOBAL VARIABLES: bb, kk, */static int inflate_block(int *e){	unsigned t;			/* block type */	register unsigned long b;			/* bit buffer */	register unsigned k;		/* number of bits in bit buffer */	/* make local bit buffer */	b = bb;	k = bk;	/* read in last block bit */	while (k < 1) {		b |= ((unsigned long)fgetc(in_file)) << k;		k += 8;	}	*e = (int) b & 1;	b >>= 1;	k -= 1;	/* read in block type */	while (k < 2) {		b |= ((unsigned long)fgetc(in_file)) << k;		k += 8;	}	t = (unsigned) b & 3;	b >>= 2;	k -= 2;	/* restore the global bit buffer */	bb = b;	bk = k;	/* inflate that block type */	switch (t) {	case 0:	/* Inflate stored */		{			unsigned long n;			/* number of bytes in block */			unsigned long w;			/* current window position */			register unsigned long b_stored;			/* bit buffer */			register unsigned long k_stored;		/* number of bits in bit buffer */			/* make local copies of globals */			b_stored = bb;				/* initialize bit buffer */			k_stored = bk;			w = outcnt;			/* initialize window position */			/* go to byte boundary */			n = k_stored & 7;			b_stored >>= n;			k_stored -= n;			/* get the length and its complement */			while (k_stored < 16) {				b_stored |= ((unsigned long)fgetc(in_file)) << k_stored;				k_stored += 8;			}			n = ((unsigned) b_stored & 0xffff);			b_stored >>= 16;			k_stored -= 16;			while (k_stored < 16) {				b_stored |= ((unsigned long)fgetc(in_file)) << k_stored;				k_stored += 8;			}			if (n != (unsigned) ((~b_stored) & 0xffff)) {				return 1;		/* error in compressed data */			}			b_stored >>= 16;			k_stored -= 16;			/* read and output the compressed data */			while (n--) {				while (k_stored < 8) {					b_stored |= ((unsigned long)fgetc(in_file)) << k_stored;					k_stored += 8;				}				window[w++] = (unsigned char) b_stored;				if (w == (unsigned long)WSIZE) {					outcnt=(w),					flush_window();					w = 0;				}				b_stored >>= 8;				k_stored -= 8;			}			/* restore the globals from the locals */			outcnt = w;			/* restore global window pointer */			bb = b_stored;				/* restore global bit buffer */			bk = k_stored;			return 0;		}	case 1:	/* Inflate fixed 			 * decompress an inflated type 1 (fixed Huffman codes) block.  We should			 * either replace this with a custom decoder, or at least precompute the			 * Huffman tables.			 */		{			int i;					/* temporary variable */			huft_t *tl;				/* literal/length code table */			huft_t *td;				/* distance code table */			int bl;					/* lookup bits for tl */			int bd;					/* lookup bits for td */			unsigned int l[288];	/* length list for huft_build */			/* set up literal table */			for (i = 0; i < 144; i++) {				l[i] = 8;			}			for (; i < 256; i++) {				l[i] = 9;			}			for (; i < 280; i++) {				l[i] = 7;			}			for (; i < 288; i++) {	/* make a complete, but wrong code set */				l[i] = 8;			}			bl = 7;			if ((i = huft_build(l, 288, 257, cplens, cplext, &tl, &bl)) != 0) {				return i;			}			/* set up distance table */			for (i = 0; i < 30; i++) {	/* make an incomplete code set */				l[i] = 5;			}			bd = 5;			if ((i = huft_build(l, 30, 0, cpdist, cpdext, &td, &bd)) > 1) {				huft_free(tl);				return i;			}			/* decompress until an end-of-block code */			if (inflate_codes(tl, td, bl, bd))				return 1;			/* free the decoding tables, return */			huft_free(tl);			huft_free(td);			return 0;		}	case 2:	/* Inflate dynamic */		{			const int dbits = 6;					/* bits in base distance lookup table */			const int lbits = 9;					/* bits in base literal/length lookup table */			int i;						/* temporary variables */			unsigned j;			unsigned l;					/* last length */			unsigned m;					/* mask for bit lengths table */			unsigned n;					/* number of lengths to get */			huft_t *tl;			/* literal/length code table */			huft_t *td;			/* distance code table */			int bl;						/* lookup bits for tl */			int bd;						/* lookup bits for td */			unsigned nb;				/* number of bit length codes */			unsigned nl;				/* number of literal/length codes */			unsigned nd;				/* number of distance codes */			unsigned ll[286 + 30];		/* literal/length and distance code lengths */			register unsigned long b_dynamic;	/* bit buffer */			register unsigned k_dynamic;		/* number of bits in bit buffer */			/* make local bit buffer */			b_dynamic = bb;			k_dynamic = bk;			/* read in table lengths */			while (k_dynamic < 5) {				b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;				k_dynamic += 8;			}			nl = 257 + ((unsigned) b_dynamic & 0x1f);	/* number of literal/length codes */			b_dynamic >>= 5;			k_dynamic -= 5;			while (k_dynamic < 5) {				b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;				k_dynamic += 8;			}			nd = 1 + ((unsigned) b_dynamic & 0x1f);	/* number of distance codes */			b_dynamic >>= 5;			k_dynamic -= 5;			while (k_dynamic < 4) {				b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;				k_dynamic += 8;			}			nb = 4 + ((unsigned) b_dynamic & 0xf);	/* number of bit length codes */			b_dynamic >>= 4;			k_dynamic -= 4;			if (nl > 286 || nd > 30) {				return 1;	/* bad lengths */			}			/* read in bit-length-code lengths */			for (j = 0; j < nb; j++) {				while (k_dynamic < 3) {					b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;					k_dynamic += 8;				}				ll[border[j]] = (unsigned) b_dynamic & 7;				b_dynamic >>= 3;				k_dynamic -= 3;			}			for (; j < 19; j++) {				ll[border[j]] = 0;			}			/* build decoding table for trees--single level, 7 bit lookup */			bl = 7;			if ((i = huft_build(ll, 19, 19, NULL, NULL, &tl, &bl)) != 0) {				if (i == 1) {					huft_free(tl);				}				return i;			/* incomplete code set */			}			/* read in literal and distance code lengths */			n = nl + nd;			m = mask_bits[bl];			i = l = 0;			while ((unsigned) i < n) {				while (k_dynamic < (unsigned) bl) {					b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;					k_dynamic += 8;				}				j = (td = tl + ((unsigned) b_dynamic & m))->b;				b_dynamic >>= j;				k_dynamic -= j;				j = td->v.n;				if (j < 16) {			/* length of code in bits (0..15) */					ll[i++] = l = j;	/* save last length in l */				}				else if (j == 16) {		/* repeat last length 3 to 6 times */					while (k_dynamic < 2) {						b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;						k_dynamic += 8;					}					j = 3 + ((unsigned) b_dynamic & 3);					b_dynamic >>= 2;					k_dynamic -= 2;					if ((unsigned) i + j > n) {						return 1;					}					while (j--) {						ll[i++] = l;					}				} else if (j == 17) {	/* 3 to 10 zero length codes */					while (k_dynamic < 3) {						b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;						k_dynamic += 8;					}					j = 3 + ((unsigned) b_dynamic & 7);					b_dynamic >>= 3;					k_dynamic -= 3;					if ((unsigned) i + j > n) {						return 1;					}					while (j--) {						ll[i++] = 0;					}					l = 0;				} else {		/* j == 18: 11 to 138 zero length codes */					while (k_dynamic < 7) {						b_dynamic |= ((unsigned long)fgetc(in_file)) << k_dynamic;						k_dynamic += 8;					}					j = 11 + ((unsigned) b_dynamic & 0x7f);					b_dynamic >>= 7;					k_dynamic -= 7;					if ((unsigned) i + j > n) {						return 1;					}					while (j--) {						ll[i++] = 0;					}					l = 0;				}			}			/* free decoding table for trees */			huft_free(tl);			/* restore the global bit buffer */			bb = b_dynamic;			bk = k_dynamic;			/* build the decoding tables for literal/length and distance codes */			bl = lbits;			if ((i = huft_build(ll, nl, 257, cplens, cplext, &tl, &bl)) != 0) {				if (i == 1) {					error_msg("Incomplete literal tree");					huft_free(tl);				}				return i;			/* incomplete code set */			}			bd = dbits;			if ((i = huft_build(ll + nl, nd, 0, cpdist, cpdext, &td, &bd)) != 0) {				if (i == 1) {					error_msg("incomplete distance tree");					huft_free(td);				}				huft_free(tl);				return i;			/* incomplete code set */			}			/* decompress until an end-of-block code */			if (inflate_codes(tl, td, bl, bd))				return 1;			/* free the decoding tables, return */			huft_free(tl);			huft_free(td);			return 0;		}	default:		/* bad block type */		return 2;	}}/* * decompress an inflated entry * * GLOBAL VARIABLES: outcnt, bk, bb, hufts, inptr */extern int inflate(FILE *in, FILE *out){	int e;				/* last block flag */	int r;				/* result code */	unsigned h = 0;		/* maximum struct huft's malloc'ed */	/* initialize window, bit buffer */	outcnt = 0;	bk = 0;	bb = 0;	in_file = in;	out_file = out;	/* Allocate all global buffers (for DYN_ALLOC option) */	window = xmalloc((size_t)(((2L*WSIZE)+1L)*sizeof(unsigned char)));	bytes_out = 0L;	/* Create the crc table */	make_crc_table();	/* decompress until the last block */	do {		hufts = 0;		if ((r = inflate_block(&e)) != 0) {			return r;		}		if (hufts > h) {			h = hufts;		}	} while (!e);	/* Undo too much lookahead. The next read will be byte aligned so we	 * can discard unused bits in the last meaningful byte.	 */	while (bk >= 8) {		bk -= 8;		ungetc((bb << bk), in_file);	}	/* flush out window */	flush_window();	free(window);	free(crc_table);	/* return success */	return 0;}/* =========================================================================== * Unzip in to out.  This routine works on gzip files only. * * IN assertions: the buffer inbuf contains already the beginning of *   the compressed data, from offsets inptr to insize-1 included. *   The magic header has already been checked. The output buffer is cleared. * in, out: input and output file descriptors */extern int unzip(FILE *l_in_file, FILE *l_out_file){	unsigned char buf[8];	/* extended local header */	unsigned char flags;	/* compression flags */	typedef void (*sig_type) (int);	unsigned short i;	unsigned char magic [2];	if (signal(SIGINT, SIG_IGN) != SIG_IGN) {		(void) signal(SIGINT, (sig_type) abort_gzip);	}#ifdef SIGTERM//	if (signal(SIGTERM, SIG_IGN) != SIG_IGN) {//		(void) signal(SIGTERM, (sig_type) abort_gzip);//	}#endif#ifdef SIGHUP	if (signal(SIGHUP, SIG_IGN) != SIG_IGN) {		(void) signal(SIGHUP, (sig_type) abort_gzip);	}#endif	magic [0] = fgetc(l_in_file);	magic [1] = fgetc(l_in_file);	#ifdef CONFIG_FEATURE_UNCOMPRESS	/* Magic header for compress files, 1F 9d = \037\235 */	if (( magic [0] == 0x1F ) && ( magic [1] == 0x9d)) {		return uncompress ( l_in_file, l_out_file );	}#endif	/* Magic header for gzip files, 1F 8B = \037\213 */	if (( magic [0] != 0x1F ) || ( magic [1] != 0x8b)) {		error_msg("Invalid gzip magic");		return EXIT_FAILURE;	}	/* Check the compression method */	if (fgetc(l_in_file) != 8) {		error_msg("Unknown compression method");		return(-1);	}	flags = (unsigned char) fgetc(l_in_file);	/* Ignore time stamp(4), extra flags(1), OS type(1) */	for (i = 0; i < 6; i++) {		fgetc(l_in_file);	}	if (flags & 0x04) {		/* bit 2 set: extra field present */		const unsigned short extra = fgetc(l_in_file) + (fgetc(l_in_file) << 8);		for (i = 0; i < extra; i++) {			fgetc(l_in_file);		}	}	/* Discard original name if any */	if (flags & 0x08) {		/* bit 3 set: original file name present */		while (fgetc(l_in_file) != 0);	/* null */	}	/* Discard file comment if any */	if (flags & 0x10) {		/* bit 4 set: file comment present */		while (fgetc(l_in_file) != 0);	/* null */	}	/* Decompress */	if (inflate(l_in_file, l_out_file) != 0) {		error_msg("invalid compressed data--format violated");	}	/* Get the crc and original length	 * crc32  (see algorithm.doc)	 * uncompressed input size modulo 2^32	 */	fread(buf, 1, 8, l_in_file);	/* Validate decompression - crc */	if ((unsigned int)((buf[0] | (buf[1] << 8)) |((buf[2] | (buf[3] << 8)) << 16)) != (crc ^ 0xffffffffL)) {		error_msg("invalid compressed data--crc error");	}	/* Validate decompression - size */	if (((buf[4] | (buf[5] << 8)) |((buf[6] | (buf[7] << 8)) << 16)) != (unsigned long) bytes_out) {		error_msg("invalid compressed data--length error");	}	return 0;}/* * This needs access to global variables window and crc_table, so its not in its own file. */extern void gz_close(int gunzip_pid){	if (kill(gunzip_pid, SIGTERM) == -1) {		error_msg_and_die("***  Couldnt kill old gunzip process *** aborting");	}	if (waitpid(gunzip_pid, NULL, 0) == -1) {		printf("Couldnt wait ?");	}	free(window);	free(crc_table);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -