xref: /original-bsd/usr.bin/compress/compress.c (revision c829ecf6)
1 /*
2  * Copyright (c) 1985, 1986 The Regents of the University of California.
3  * All rights reserved.
4  *
5  * This code is derived from software contributed to Berkeley by
6  * James A. Woods, derived from original work by Spencer Thomas
7  * and Joseph Orost.
8  *
9  * %sccs.include.redist.c%
10  */
11 
12 #ifndef lint
13 char copyright[] =
14 "@(#) Copyright (c) 1985, 1986 The Regents of the University of California.\n\
15  All rights reserved.\n";
16 #endif /* not lint */
17 
18 #ifndef lint
19 static char sccsid[] = "@(#)compress.c	5.12 (Berkeley) 06/01/90";
20 #endif /* not lint */
21 
22 /*
23  * Compress - data compression program
24  */
25 #define	min(a,b)	((a>b) ? b : a)
26 
27 /*
28  * machine variants which require cc -Dmachine:  pdp11, z8000, pcxt
29  */
30 
31 /*
32  * Set USERMEM to the maximum amount of physical user memory available
33  * in bytes.  USERMEM is used to determine the maximum BITS that can be used
34  * for compression.
35  *
36  * SACREDMEM is the amount of physical memory saved for others; compress
37  * will hog the rest.
38  */
39 #ifndef SACREDMEM
40 #define SACREDMEM	0
41 #endif
42 
43 #ifndef USERMEM
44 # define USERMEM 	450000	/* default user memory */
45 #endif
46 
47 #ifdef interdata		/* (Perkin-Elmer) */
48 #define SIGNED_COMPARE_SLOW	/* signed compare is slower than unsigned */
49 #endif
50 
51 #ifdef pdp11
52 # define BITS 	12	/* max bits/code for 16-bit machine */
53 # define NO_UCHAR	/* also if "unsigned char" functions as signed char */
54 # undef USERMEM
55 #endif /* pdp11 */	/* don't forget to compile with -i */
56 
57 #ifdef z8000
58 # define BITS 	12
59 # undef vax		/* weird preprocessor */
60 # undef USERMEM
61 #endif /* z8000 */
62 
63 #ifdef pcxt
64 # define BITS   12
65 # undef USERMEM
66 #endif /* pcxt */
67 
68 #ifdef USERMEM
69 # if USERMEM >= (433484+SACREDMEM)
70 #  define PBITS	16
71 # else
72 #  if USERMEM >= (229600+SACREDMEM)
73 #   define PBITS	15
74 #  else
75 #   if USERMEM >= (127536+SACREDMEM)
76 #    define PBITS	14
77 #   else
78 #    if USERMEM >= (73464+SACREDMEM)
79 #     define PBITS	13
80 #    else
81 #     define PBITS	12
82 #    endif
83 #   endif
84 #  endif
85 # endif
86 # undef USERMEM
87 #endif /* USERMEM */
88 
89 #ifdef PBITS		/* Preferred BITS for this memory size */
90 # ifndef BITS
91 #  define BITS PBITS
92 # endif BITS
93 #endif /* PBITS */
94 
95 #if BITS == 16
96 # define HSIZE	69001		/* 95% occupancy */
97 #endif
98 #if BITS == 15
99 # define HSIZE	35023		/* 94% occupancy */
100 #endif
101 #if BITS == 14
102 # define HSIZE	18013		/* 91% occupancy */
103 #endif
104 #if BITS == 13
105 # define HSIZE	9001		/* 91% occupancy */
106 #endif
107 #if BITS <= 12
108 # define HSIZE	5003		/* 80% occupancy */
109 #endif
110 
111 #ifdef M_XENIX			/* Stupid compiler can't handle arrays with */
112 # if BITS == 16			/* more than 65535 bytes - so we fake it */
113 #  define XENIX_16
114 # else
115 #  if BITS > 13			/* Code only handles BITS = 12, 13, or 16 */
116 #   define BITS	13
117 #  endif
118 # endif
119 #endif
120 
121 /*
122  * a code_int must be able to hold 2**BITS values of type int, and also -1
123  */
124 #if BITS > 15
125 typedef long int	code_int;
126 #else
127 typedef int		code_int;
128 #endif
129 
130 #ifdef SIGNED_COMPARE_SLOW
131 typedef unsigned long int count_int;
132 typedef unsigned short int count_short;
133 #else
134 typedef long int	  count_int;
135 #endif
136 
137 #ifdef NO_UCHAR
138  typedef char	char_type;
139 #else
140  typedef	unsigned char	char_type;
141 #endif /* UCHAR */
142 char_type magic_header[] = { "\037\235" };	/* 1F 9D */
143 
144 /* Defines for third byte of header */
145 #define BIT_MASK	0x1f
146 #define BLOCK_MASK	0x80
147 /* Masks 0x40 and 0x20 are free.  I think 0x20 should mean that there is
148    a fourth header byte (for expansion).
149 */
150 #define INIT_BITS 9			/* initial number of bits/code */
151 
152 /*
153  * compress.c - File compression ala IEEE Computer, June 1984.
154  *
155  * Authors:	Spencer W. Thomas	(decvax!utah-cs!thomas)
156  *		Jim McKie		(decvax!mcvax!jim)
157  *		Steve Davies		(decvax!vax135!petsd!peora!srd)
158  *		Ken Turkowski		(decvax!decwrl!turtlevax!ken)
159  *		James A. Woods		(decvax!ihnp4!ames!jaw)
160  *		Joe Orost		(decvax!vax135!petsd!joe)
161  *
162  * $Header: compress.c,v 4.0 85/07/30 12:50:00 joe Release $
163  * $Log:	compress.c,v $
164  * Revision 4.0  85/07/30  12:50:00  joe
165  * Removed ferror() calls in output routine on every output except first.
166  * Prepared for release to the world.
167  *
168  * Revision 3.6  85/07/04  01:22:21  joe
169  * Remove much wasted storage by overlaying hash table with the tables
170  * used by decompress: tab_suffix[1<<BITS], stack[8000].  Updated USERMEM
171  * computations.  Fixed dump_tab() DEBUG routine.
172  *
173  * Revision 3.5  85/06/30  20:47:21  jaw
174  * Change hash function to use exclusive-or.  Rip out hash cache.  These
175  * speedups render the megamemory version defunct, for now.  Make decoder
176  * stack global.  Parts of the RCS trunks 2.7, 2.6, and 2.1 no longer apply.
177  *
178  * Revision 3.4  85/06/27  12:00:00  ken
179  * Get rid of all floating-point calculations by doing all compression ratio
180  * calculations in fixed point.
181  *
182  * Revision 3.3  85/06/24  21:53:24  joe
183  * Incorporate portability suggestion for M_XENIX.  Got rid of text on #else
184  * and #endif lines.  Cleaned up #ifdefs for vax and interdata.
185  *
186  * Revision 3.2  85/06/06  21:53:24  jaw
187  * Incorporate portability suggestions for Z8000, IBM PC/XT from mailing list.
188  * Default to "quiet" output (no compression statistics).
189  *
190  * Revision 3.1  85/05/12  18:56:13  jaw
191  * Integrate decompress() stack speedups (from early pointer mods by McKie).
192  * Repair multi-file USERMEM gaffe.  Unify 'force' flags to mimic semantics
193  * of SVR2 'pack'.  Streamline block-compress table clear logic.  Increase
194  * output byte count by magic number size.
195  *
196  * Revision 3.0   84/11/27  11:50:00  petsd!joe
197  * Set HSIZE depending on BITS.  Set BITS depending on USERMEM.  Unrolled
198  * loops in clear routines.  Added "-C" flag for 2.0 compatibility.  Used
199  * unsigned compares on Perkin-Elmer.  Fixed foreground check.
200  *
201  * Revision 2.7   84/11/16  19:35:39  ames!jaw
202  * Cache common hash codes based on input statistics; this improves
203  * performance for low-density raster images.  Pass on #ifdef bundle
204  * from Turkowski.
205  *
206  * Revision 2.6   84/11/05  19:18:21  ames!jaw
207  * Vary size of hash tables to reduce time for small files.
208  * Tune PDP-11 hash function.
209  *
210  * Revision 2.5   84/10/30  20:15:14  ames!jaw
211  * Junk chaining; replace with the simpler (and, on the VAX, faster)
212  * double hashing, discussed within.  Make block compression standard.
213  *
214  * Revision 2.4   84/10/16  11:11:11  ames!jaw
215  * Introduce adaptive reset for block compression, to boost the rate
216  * another several percent.  (See mailing list notes.)
217  *
218  * Revision 2.3   84/09/22  22:00:00  petsd!joe
219  * Implemented "-B" block compress.  Implemented REVERSE sorting of tab_next.
220  * Bug fix for last bits.  Changed fwrite to putchar loop everywhere.
221  *
222  * Revision 2.2   84/09/18  14:12:21  ames!jaw
223  * Fold in news changes, small machine typedef from thomas,
224  * #ifdef interdata from joe.
225  *
226  * Revision 2.1   84/09/10  12:34:56  ames!jaw
227  * Configured fast table lookup for 32-bit machines.
228  * This cuts user time in half for b <= FBITS, and is useful for news batching
229  * from VAX to PDP sites.  Also sped up decompress() [fwrite->putc] and
230  * added signal catcher [plus beef in writeerr()] to delete effluvia.
231  *
232  * Revision 2.0   84/08/28  22:00:00  petsd!joe
233  * Add check for foreground before prompting user.  Insert maxbits into
234  * compressed file.  Force file being uncompressed to end with ".Z".
235  * Added "-c" flag and "zcat".  Prepared for release.
236  *
237  * Revision 1.10  84/08/24  18:28:00  turtlevax!ken
238  * Will only compress regular files (no directories), added a magic number
239  * header (plus an undocumented -n flag to handle old files without headers),
240  * added -f flag to force overwriting of possibly existing destination file,
241  * otherwise the user is prompted for a response.  Will tack on a .Z to a
242  * filename if it doesn't have one when decompressing.  Will only replace
243  * file if it was compressed.
244  *
245  * Revision 1.9  84/08/16  17:28:00  turtlevax!ken
246  * Removed scanargs(), getopt(), added .Z extension and unlimited number of
247  * filenames to compress.  Flags may be clustered (-Ddvb12) or separated
248  * (-D -d -v -b 12), or combination thereof.  Modes and other status is
249  * copied with copystat().  -O bug for 4.2 seems to have disappeared with
250  * 1.8.
251  *
252  * Revision 1.8  84/08/09  23:15:00  joe
253  * Made it compatible with vax version, installed jim's fixes/enhancements
254  *
255  * Revision 1.6  84/08/01  22:08:00  joe
256  * Sped up algorithm significantly by sorting the compress chain.
257  *
258  * Revision 1.5  84/07/13  13:11:00  srd
259  * Added C version of vax asm routines.  Changed structure to arrays to
260  * save much memory.  Do unsigned compares where possible (faster on
261  * Perkin-Elmer)
262  *
263  * Revision 1.4  84/07/05  03:11:11  thomas
264  * Clean up the code a little and lint it.  (Lint complains about all
265  * the regs used in the asm, but I'm not going to "fix" this.)
266  *
267  * Revision 1.3  84/07/05  02:06:54  thomas
268  * Minor fixes.
269  *
270  * Revision 1.2  84/07/05  00:27:27  thomas
271  * Add variable bit length output.
272  *
273  */
274 static char rcs_ident[] = "$Header: compress.c,v 4.0 85/07/30 12:50:00 joe Release $";
275 
276 #include <stdio.h>
277 #include <ctype.h>
278 #include <signal.h>
279 #include <sys/types.h>
280 #include <sys/stat.h>
281 #ifdef notdef
282 #include <sys/ioctl.h>
283 #endif
284 
285 #define ARGVAL() (*++(*argv) || (--argc && *++argv))
286 
287 int n_bits;				/* number of bits/code */
288 int maxbits = BITS;			/* user settable max # bits/code */
289 code_int maxcode;			/* maximum code, given n_bits */
290 code_int maxmaxcode = 1 << BITS;	/* should NEVER generate this code */
291 #ifdef COMPATIBLE		/* But wrong! */
292 # define MAXCODE(n_bits)	(1 << (n_bits) - 1)
293 #else
294 # define MAXCODE(n_bits)	((1 << (n_bits)) - 1)
295 #endif /* COMPATIBLE */
296 
297 #ifdef XENIX_16
298 count_int htab0[8192];
299 count_int htab1[8192];
300 count_int htab2[8192];
301 count_int htab3[8192];
302 count_int htab4[8192];
303 count_int htab5[8192];
304 count_int htab6[8192];
305 count_int htab7[8192];
306 count_int htab8[HSIZE-65536];
307 count_int * htab[9] = {
308 	htab0, htab1, htab2, htab3, htab4, htab5, htab6, htab7, htab8 };
309 
310 #define htabof(i)	(htab[(i) >> 13][(i) & 0x1fff])
311 unsigned short code0tab[16384];
312 unsigned short code1tab[16384];
313 unsigned short code2tab[16384];
314 unsigned short code3tab[16384];
315 unsigned short code4tab[16384];
316 unsigned short * codetab[5] = {
317 	code0tab, code1tab, code2tab, code3tab, code4tab };
318 
319 #define codetabof(i)	(codetab[(i) >> 14][(i) & 0x3fff])
320 
321 #else	/* Normal machine */
322 
323 #ifdef sel	/* gould base register braindamage */
324 /*NOBASE*/
325 count_int htab [HSIZE];
326 unsigned short codetab [HSIZE];
327 /*NOBASE*/
328 #else
329 count_int htab [HSIZE];
330 unsigned short codetab [HSIZE];
331 #endif sel
332 
333 #define htabof(i)	htab[i]
334 #define codetabof(i)	codetab[i]
335 #endif	/* XENIX_16 */
336 code_int hsize = HSIZE;			/* for dynamic table sizing */
337 count_int fsize;
338 
339 /*
340  * To save much memory, we overlay the table used by compress() with those
341  * used by decompress().  The tab_prefix table is the same size and type
342  * as the codetab.  The tab_suffix table needs 2**BITS characters.  We
343  * get this from the beginning of htab.  The output stack uses the rest
344  * of htab, and contains characters.  There is plenty of room for any
345  * possible stack (stack used to be 8000 characters).
346  */
347 
348 #define tab_prefixof(i)	codetabof(i)
349 #ifdef XENIX_16
350 # define tab_suffixof(i)	((char_type *)htab[(i)>>15])[(i) & 0x7fff]
351 # define de_stack		((char_type *)(htab2))
352 #else	/* Normal machine */
353 # define tab_suffixof(i)	((char_type *)(htab))[i]
354 # define de_stack		((char_type *)&tab_suffixof(1<<BITS))
355 #endif	/* XENIX_16 */
356 
357 code_int free_ent = 0;			/* first unused entry */
358 int exit_stat = 0;			/* per-file status */
359 int perm_stat = 0;			/* permanent status */
360 
361 code_int getcode();
362 
363 Usage() {
364 #ifdef DEBUG
365 fprintf(stderr,"Usage: compress [-dDVfc] [-b maxbits] [file ...]\n");
366 }
367 int debug = 0;
368 #else
369 fprintf(stderr,"Usage: compress [-fvc] [-b maxbits] [file ...]\n");
370 }
371 #endif /* DEBUG */
372 int nomagic = 0;	/* Use a 3-byte magic number header, unless old file */
373 int zcat_flg = 0;	/* Write output on stdout, suppress messages */
374 int precious = 1;	/* Don't unlink output file on interrupt */
375 int quiet = 1;		/* don't tell me about compression */
376 
377 /*
378  * block compression parameters -- after all codes are used up,
379  * and compression rate changes, start over.
380  */
381 int block_compress = BLOCK_MASK;
382 int clear_flg = 0;
383 long int ratio = 0;
384 #define CHECK_GAP 10000	/* ratio check interval */
385 count_int checkpoint = CHECK_GAP;
386 /*
387  * the next two codes should not be changed lightly, as they must not
388  * lie within the contiguous general code space.
389  */
390 #define FIRST	257	/* first free entry */
391 #define	CLEAR	256	/* table clear output code */
392 
393 int force = 0;
394 char ofname [100];
395 #ifdef DEBUG
396 int verbose = 0;
397 #endif /* DEBUG */
398 sig_t oldint;
399 int bgnd_flag;
400 
401 int do_decomp = 0;
402 
403 /*****************************************************************
404  * TAG( main )
405  *
406  * Algorithm from "A Technique for High Performance Data Compression",
407  * Terry A. Welch, IEEE Computer Vol 17, No 6 (June 1984), pp 8-19.
408  *
409  * Usage: compress [-dfvc] [-b bits] [file ...]
410  * Inputs:
411  *	-d:	    If given, decompression is done instead.
412  *
413  *      -c:         Write output on stdout, don't remove original.
414  *
415  *      -b:         Parameter limits the max number of bits/code.
416  *
417  *	-f:	    Forces output file to be generated, even if one already
418  *		    exists, and even if no space is saved by compressing.
419  *		    If -f is not used, the user will be prompted if stdin is
420  *		    a tty, otherwise, the output file will not be overwritten.
421  *
422  *      -v:	    Write compression statistics
423  *
424  * 	file ...:   Files to be compressed.  If none specified, stdin
425  *		    is used.
426  * Outputs:
427  *	file.Z:	    Compressed form of file with same mode, owner, and utimes
428  * 	or stdout   (if stdin used as input)
429  *
430  * Assumptions:
431  *	When filenames are given, replaces with the compressed version
432  *	(.Z suffix) only if the file decreases in size.
433  * Algorithm:
434  * 	Modified Lempel-Ziv method (LZW).  Basically finds common
435  * substrings and replaces them with a variable size code.  This is
436  * deterministic, and can be done on the fly.  Thus, the decompression
437  * procedure needs no input table, but tracks the way the table was built.
438  */
439 
440 main( argc, argv )
441 register int argc; char **argv;
442 {
443     int overwrite = 0;	/* Do not overwrite unless given -f flag */
444     char tempname[100];
445     char **filelist, **fileptr;
446     char *cp, *rindex(), *malloc();
447     struct stat statbuf;
448     void onintr(), oops();
449 
450     /* This bg check only works for sh. */
451     if ( (oldint = signal ( SIGINT, SIG_IGN )) != SIG_IGN ) {
452 	signal ( SIGINT, onintr );
453 	signal ( SIGSEGV, oops );
454     }
455     bgnd_flag = oldint != SIG_DFL;
456 #ifdef notdef     /* This works for csh but we don't want it. */
457     { int tgrp;
458     if (bgnd_flag == 0 && ioctl(2, TIOCGPGRP, (char *)&tgrp) == 0 &&
459       getpgrp(0) != tgrp)
460 	bgnd_flag = 1;
461     }
462 #endif
463 
464 #ifdef COMPATIBLE
465     nomagic = 1;	/* Original didn't have a magic number */
466 #endif /* COMPATIBLE */
467 
468     filelist = fileptr = (char **)(malloc(argc * sizeof(*argv)));
469     *filelist = NULL;
470 
471     if((cp = rindex(argv[0], '/')) != 0) {
472 	cp++;
473     } else {
474 	cp = argv[0];
475     }
476     if(strcmp(cp, "uncompress") == 0) {
477 	do_decomp = 1;
478     } else if(strcmp(cp, "zcat") == 0) {
479 	do_decomp = 1;
480 	zcat_flg = 1;
481     }
482 
483 #ifdef BSD4_2
484     /* 4.2BSD dependent - take it out if not */
485     setlinebuf( stderr );
486 #endif /* BSD4_2 */
487 
488     /* Argument Processing
489      * All flags are optional.
490      * -D => debug
491      * -V => print Version; debug verbose
492      * -d => do_decomp
493      * -v => unquiet
494      * -f => force overwrite of output file
495      * -n => no header: useful to uncompress old files
496      * -b maxbits => maxbits.  If -b is specified, then maxbits MUST be
497      *	    given also.
498      * -c => cat all output to stdout
499      * -C => generate output compatible with compress 2.0.
500      * if a string is left, must be an input filename.
501      */
502     for (argc--, argv++; argc > 0; argc--, argv++) {
503 	if (**argv == '-') {	/* A flag argument */
504 	    while (*++(*argv)) {	/* Process all flags in this arg */
505 		switch (**argv) {
506 #ifdef DEBUG
507 		    case 'D':
508 			debug = 1;
509 			break;
510 		    case 'V':
511 			verbose = 1;
512 			version();
513 			break;
514 #else
515 		    case 'V':
516 			version();
517 			break;
518 #endif /* DEBUG */
519 		    case 'v':
520 			quiet = 0;
521 			break;
522 		    case 'd':
523 			do_decomp = 1;
524 			break;
525 		    case 'f':
526 		    case 'F':
527 			overwrite = 1;
528 			force = 1;
529 			break;
530 		    case 'n':
531 			nomagic = 1;
532 			break;
533 		    case 'C':
534 			block_compress = 0;
535 			break;
536 		    case 'b':
537 			if (!ARGVAL()) {
538 			    fprintf(stderr, "Missing maxbits\n");
539 			    Usage();
540 			    exit(1);
541 			}
542 			maxbits = atoi(*argv);
543 			goto nextarg;
544 		    case 'c':
545 			zcat_flg = 1;
546 			break;
547 		    case 'q':
548 			quiet = 1;
549 			break;
550 		    default:
551 			fprintf(stderr, "Unknown flag: '%c'; ", **argv);
552 			Usage();
553 			exit(1);
554 		}
555 	    }
556 	}
557 	else {		/* Input file name */
558 	    *fileptr++ = *argv;	/* Build input file list */
559 	    *fileptr = NULL;
560 	    /* process nextarg; */
561 	}
562 	nextarg: continue;
563     }
564 
565     if(maxbits < INIT_BITS) maxbits = INIT_BITS;
566     if (maxbits > BITS) maxbits = BITS;
567     maxmaxcode = 1 << maxbits;
568 
569     if (*filelist != NULL) {
570 	for (fileptr = filelist; *fileptr; fileptr++) {
571 	    exit_stat = 0;
572 	    if (do_decomp) {			/* DECOMPRESSION */
573 		/* Check for .Z suffix */
574 		if (strcmp(*fileptr + strlen(*fileptr) - 2, ".Z") != 0) {
575 		    /* No .Z: tack one on */
576 		    strcpy(tempname, *fileptr);
577 		    strcat(tempname, ".Z");
578 		    *fileptr = tempname;
579 		}
580 		/* Open input file */
581 		if ((freopen(*fileptr, "r", stdin)) == NULL) {
582 		    perror(*fileptr);
583 		    perm_stat = 1;
584 		    continue;
585 		}
586 		/* Check the magic number */
587 		if (nomagic == 0) {
588 		    if ((getchar() != (magic_header[0] & 0xFF))
589 		     || (getchar() != (magic_header[1] & 0xFF))) {
590 			fprintf(stderr, "%s: not in compressed format\n",
591 			    *fileptr);
592 		    continue;
593 		    }
594 		    maxbits = getchar();	/* set -b from file */
595 		    block_compress = maxbits & BLOCK_MASK;
596 		    maxbits &= BIT_MASK;
597 		    maxmaxcode = 1 << maxbits;
598 		    if(maxbits > BITS) {
599 			fprintf(stderr,
600 			"%s: compressed with %d bits, can only handle %d bits\n",
601 			*fileptr, maxbits, BITS);
602 			continue;
603 		    }
604 		}
605 		/* Generate output filename */
606 		strcpy(ofname, *fileptr);
607 		ofname[strlen(*fileptr) - 2] = '\0';  /* Strip off .Z */
608 	    } else {					/* COMPRESSION */
609 		if (strcmp(*fileptr + strlen(*fileptr) - 2, ".Z") == 0) {
610 		    	fprintf(stderr, "%s: already has .Z suffix -- no change\n",
611 			    *fileptr);
612 		    continue;
613 		}
614 		/* Open input file */
615 		if ((freopen(*fileptr, "r", stdin)) == NULL) {
616 		    perror(*fileptr);
617 		    perm_stat = 1;
618 		    continue;
619 		}
620 		stat ( *fileptr, &statbuf );
621 		fsize = (long) statbuf.st_size;
622 		/*
623 		 * tune hash table size for small files -- ad hoc,
624 		 * but the sizes match earlier #defines, which
625 		 * serve as upper bounds on the number of output codes.
626 		 */
627 		hsize = HSIZE;
628 		if ( fsize < (1 << 12) )
629 		    hsize = min ( 5003, HSIZE );
630 		else if ( fsize < (1 << 13) )
631 		    hsize = min ( 9001, HSIZE );
632 		else if ( fsize < (1 << 14) )
633 		    hsize = min ( 18013, HSIZE );
634 		else if ( fsize < (1 << 15) )
635 		    hsize = min ( 35023, HSIZE );
636 		else if ( fsize < 47000 )
637 		    hsize = min ( 50021, HSIZE );
638 
639 		/* Generate output filename */
640 		strcpy(ofname, *fileptr);
641 #ifndef BSD4_2		/* Short filenames */
642 		if ((cp=rindex(ofname,'/')) != NULL)	cp++;
643 		else					cp = ofname;
644 		if (strlen(cp) > 12) {
645 		    fprintf(stderr,"%s: filename too long to tack on .Z\n",cp);
646 		    continue;
647 		}
648 #endif  /* BSD4_2		Long filenames allowed */
649 		strcat(ofname, ".Z");
650 	    }
651 	    /* Check for overwrite of existing file */
652 	    if (overwrite == 0 && zcat_flg == 0) {
653 		if (stat(ofname, &statbuf) == 0) {
654 		    char response[2];
655 		    response[0] = 'n';
656 		    fprintf(stderr, "%s already exists;", ofname);
657 		    if (bgnd_flag == 0 && isatty(2)) {
658 			fprintf(stderr, " do you wish to overwrite %s (y or n)? ",
659 			ofname);
660 			fflush(stderr);
661 			read(2, response, 2);
662 			while (response[1] != '\n') {
663 			    if (read(2, response+1, 1) < 0) {	/* Ack! */
664 				perror("stderr"); break;
665 			    }
666 			}
667 		    }
668 		    if (response[0] != 'y') {
669 			fprintf(stderr, "\tnot overwritten\n");
670 			continue;
671 		    }
672 		}
673 	    }
674 	    if(zcat_flg == 0) {		/* Open output file */
675 		if (freopen(ofname, "w", stdout) == NULL) {
676 		    perror(ofname);
677 		    perm_stat = 1;
678 		    continue;
679 		}
680 		precious = 0;
681 		if(!quiet)
682 			fprintf(stderr, "%s: ", *fileptr);
683 	    }
684 
685 	    /* Actually do the compression/decompression */
686 	    if (do_decomp == 0)	compress();
687 #ifndef DEBUG
688 	    else			decompress();
689 #else
690 	    else if (debug == 0)	decompress();
691 	    else			printcodes();
692 	    if (verbose)		dump_tab();
693 #endif /* DEBUG */
694 	    if(zcat_flg == 0) {
695 		copystat(*fileptr, ofname);	/* Copy stats */
696 		precious = 1;
697 		if((exit_stat == 1) || (!quiet))
698 			putc('\n', stderr);
699 	    }
700 	}
701     } else {		/* Standard input */
702 	if (do_decomp == 0) {
703 		compress();
704 #ifdef DEBUG
705 		if(verbose)		dump_tab();
706 #endif /* DEBUG */
707 		if(!quiet)
708 			putc('\n', stderr);
709 	} else {
710 	    /* Check the magic number */
711 	    if (nomagic == 0) {
712 		if ((getchar()!=(magic_header[0] & 0xFF))
713 		 || (getchar()!=(magic_header[1] & 0xFF))) {
714 		    fprintf(stderr, "stdin: not in compressed format\n");
715 		    exit(1);
716 		}
717 		maxbits = getchar();	/* set -b from file */
718 		block_compress = maxbits & BLOCK_MASK;
719 		maxbits &= BIT_MASK;
720 		maxmaxcode = 1 << maxbits;
721 		fsize = 100000;		/* assume stdin large for USERMEM */
722 		if(maxbits > BITS) {
723 			fprintf(stderr,
724 			"stdin: compressed with %d bits, can only handle %d bits\n",
725 			maxbits, BITS);
726 			exit(1);
727 		}
728 	    }
729 #ifndef DEBUG
730 	    decompress();
731 #else
732 	    if (debug == 0)	decompress();
733 	    else		printcodes();
734 	    if (verbose)	dump_tab();
735 #endif /* DEBUG */
736 	}
737     }
738     exit(perm_stat ? perm_stat : exit_stat);
739 }
740 
741 static int offset;
742 long int in_count = 1;			/* length of input */
743 long int bytes_out;			/* length of compressed output */
744 long int out_count = 0;			/* # of codes output (for debugging) */
745 
746 /*
747  * compress stdin to stdout
748  *
749  * Algorithm:  use open addressing double hashing (no chaining) on the
750  * prefix code / next character combination.  We do a variant of Knuth's
751  * algorithm D (vol. 3, sec. 6.4) along with G. Knott's relatively-prime
752  * secondary probe.  Here, the modular division first probe is gives way
753  * to a faster exclusive-or manipulation.  Also do block compression with
754  * an adaptive reset, whereby the code table is cleared when the compression
755  * ratio decreases, but after the table fills.  The variable-length output
756  * codes are re-sized at this point, and a special CLEAR code is generated
757  * for the decompressor.  Late addition:  construct the table according to
758  * file size for noticeable speed improvement on small files.  Please direct
759  * questions about this implementation to ames!jaw.
760  */
761 
762 compress() {
763     register long fcode;
764     register code_int i = 0;
765     register int c;
766     register code_int ent;
767 #ifdef XENIX_16
768     register code_int disp;
769 #else	/* Normal machine */
770     register int disp;
771 #endif
772     register code_int hsize_reg;
773     register int hshift;
774 
775 #ifndef COMPATIBLE
776     if (nomagic == 0) {
777 	putchar(magic_header[0]); putchar(magic_header[1]);
778 	putchar((char)(maxbits | block_compress));
779 	if(ferror(stdout))
780 		writeerr();
781     }
782 #endif /* COMPATIBLE */
783 
784     offset = 0;
785     bytes_out = 3;		/* includes 3-byte header mojo */
786     out_count = 0;
787     clear_flg = 0;
788     ratio = 0;
789     in_count = 1;
790     checkpoint = CHECK_GAP;
791     maxcode = MAXCODE(n_bits = INIT_BITS);
792     free_ent = ((block_compress) ? FIRST : 256 );
793 
794     ent = getchar ();
795 
796     hshift = 0;
797     for ( fcode = (long) hsize;  fcode < 65536L; fcode *= 2L )
798     	hshift++;
799     hshift = 8 - hshift;		/* set hash code range bound */
800 
801     hsize_reg = hsize;
802     cl_hash( (count_int) hsize_reg);		/* clear hash table */
803 
804 #ifdef SIGNED_COMPARE_SLOW
805     while ( (c = getchar()) != (unsigned) EOF ) {
806 #else
807     while ( (c = getchar()) != EOF ) {
808 #endif
809 	in_count++;
810 	fcode = (long) (((long) c << maxbits) + ent);
811  	i = ((c << hshift) ^ ent);	/* xor hashing */
812 
813 	if ( htabof (i) == fcode ) {
814 	    ent = codetabof (i);
815 	    continue;
816 	} else if ( (long)htabof (i) < 0 )	/* empty slot */
817 	    goto nomatch;
818  	disp = hsize_reg - i;		/* secondary hash (after G. Knott) */
819 	if ( i == 0 )
820 	    disp = 1;
821 probe:
822 	if ( (i -= disp) < 0 )
823 	    i += hsize_reg;
824 
825 	if ( htabof (i) == fcode ) {
826 	    ent = codetabof (i);
827 	    continue;
828 	}
829 	if ( (long)htabof (i) > 0 )
830 	    goto probe;
831 nomatch:
832 	output ( (code_int) ent );
833 	out_count++;
834  	ent = c;
835 #ifdef SIGNED_COMPARE_SLOW
836 	if ( (unsigned) free_ent < (unsigned) maxmaxcode) {
837 #else
838 	if ( free_ent < maxmaxcode ) {
839 #endif
840  	    codetabof (i) = free_ent++;	/* code -> hashtable */
841 	    htabof (i) = fcode;
842 	}
843 	else if ( (count_int)in_count >= checkpoint && block_compress )
844 	    cl_block ();
845     }
846     /*
847      * Put out the final code.
848      */
849     output( (code_int)ent );
850     out_count++;
851     output( (code_int)-1 );
852 
853     /*
854      * Print out stats on stderr
855      */
856     if(zcat_flg == 0 && !quiet) {
857 #ifdef DEBUG
858 	fprintf( stderr,
859 		"%ld chars in, %ld codes (%ld bytes) out, compression factor: ",
860 		in_count, out_count, bytes_out );
861 	prratio( stderr, in_count, bytes_out );
862 	fprintf( stderr, "\n");
863 	fprintf( stderr, "\tCompression as in compact: " );
864 	prratio( stderr, in_count-bytes_out, in_count );
865 	fprintf( stderr, "\n");
866 	fprintf( stderr, "\tLargest code (of last block) was %d (%d bits)\n",
867 		free_ent - 1, n_bits );
868 #else /* !DEBUG */
869 	fprintf( stderr, "Compression: " );
870 	prratio( stderr, in_count-bytes_out, in_count );
871 #endif /* DEBUG */
872     }
873     if(bytes_out > in_count)	/* exit(2) if no savings */
874 	exit_stat = 2;
875     return;
876 }
877 
878 /*****************************************************************
879  * TAG( output )
880  *
881  * Output the given code.
882  * Inputs:
883  * 	code:	A n_bits-bit integer.  If == -1, then EOF.  This assumes
884  *		that n_bits =< (long)wordsize - 1.
885  * Outputs:
886  * 	Outputs code to the file.
887  * Assumptions:
888  *	Chars are 8 bits long.
889  * Algorithm:
890  * 	Maintain a BITS character long buffer (so that 8 codes will
891  * fit in it exactly).  Use the VAX insv instruction to insert each
892  * code in turn.  When the buffer fills up empty it and start over.
893  */
894 
895 static char buf[BITS];
896 
897 #ifndef vax
898 char_type lmask[9] = {0xff, 0xfe, 0xfc, 0xf8, 0xf0, 0xe0, 0xc0, 0x80, 0x00};
899 char_type rmask[9] = {0x00, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x7f, 0xff};
900 #endif /* vax */
901 
902 output( code )
903 code_int  code;
904 {
905 #ifdef DEBUG
906     static int col = 0;
907 #endif /* DEBUG */
908 
909     /*
910      * On the VAX, it is important to have the register declarations
911      * in exactly the order given, or the asm will break.
912      */
913     register int r_off = offset, bits= n_bits;
914     register char * bp = buf;
915 
916 #ifdef DEBUG
917 	if ( verbose )
918 	    fprintf( stderr, "%5d%c", code,
919 		    (col+=6) >= 74 ? (col = 0, '\n') : ' ' );
920 #endif /* DEBUG */
921     if ( code >= 0 ) {
922 #ifdef vax
923 	/* VAX DEPENDENT!! Implementation on other machines is below.
924 	 *
925 	 * Translation: Insert BITS bits from the argument starting at
926 	 * offset bits from the beginning of buf.
927 	 */
928 	0;	/* Work around for pcc -O bug with asm and if stmt */
929 	asm( "insv	4(ap),r11,r10,(r9)" );
930 #else /* not a vax */
931 /*
932  * byte/bit numbering on the VAX is simulated by the following code
933  */
934 	/*
935 	 * Get to the first byte.
936 	 */
937 	bp += (r_off >> 3);
938 	r_off &= 7;
939 	/*
940 	 * Since code is always >= 8 bits, only need to mask the first
941 	 * hunk on the left.
942 	 */
943 	*bp = (*bp & rmask[r_off]) | (code << r_off) & lmask[r_off];
944 	bp++;
945 	bits -= (8 - r_off);
946 	code >>= 8 - r_off;
947 	/* Get any 8 bit parts in the middle (<=1 for up to 16 bits). */
948 	if ( bits >= 8 ) {
949 	    *bp++ = code;
950 	    code >>= 8;
951 	    bits -= 8;
952 	}
953 	/* Last bits. */
954 	if(bits)
955 	    *bp = code;
956 #endif /* vax */
957 	offset += n_bits;
958 	if ( offset == (n_bits << 3) ) {
959 	    bp = buf;
960 	    bits = n_bits;
961 	    bytes_out += bits;
962 	    do
963 		putchar(*bp++);
964 	    while(--bits);
965 	    offset = 0;
966 	}
967 
968 	/*
969 	 * If the next entry is going to be too big for the code size,
970 	 * then increase it, if possible.
971 	 */
972 	if ( free_ent > maxcode || (clear_flg > 0))
973 	{
974 	    /*
975 	     * Write the whole buffer, because the input side won't
976 	     * discover the size increase until after it has read it.
977 	     */
978 	    if ( offset > 0 ) {
979 		if( fwrite( buf, 1, n_bits, stdout ) != n_bits)
980 			writeerr();
981 		bytes_out += n_bits;
982 	    }
983 	    offset = 0;
984 
985 	    if ( clear_flg ) {
986     	        maxcode = MAXCODE (n_bits = INIT_BITS);
987 	        clear_flg = 0;
988 	    }
989 	    else {
990 	    	n_bits++;
991 	    	if ( n_bits == maxbits )
992 		    maxcode = maxmaxcode;
993 	    	else
994 		    maxcode = MAXCODE(n_bits);
995 	    }
996 #ifdef DEBUG
997 	    if ( debug ) {
998 		fprintf( stderr, "\nChange to %d bits\n", n_bits );
999 		col = 0;
1000 	    }
1001 #endif /* DEBUG */
1002 	}
1003     } else {
1004 	/*
1005 	 * At EOF, write the rest of the buffer.
1006 	 */
1007 	if ( offset > 0 )
1008 	    fwrite( buf, 1, (offset + 7) / 8, stdout );
1009 	bytes_out += (offset + 7) / 8;
1010 	offset = 0;
1011 	fflush( stdout );
1012 #ifdef DEBUG
1013 	if ( verbose )
1014 	    fprintf( stderr, "\n" );
1015 #endif /* DEBUG */
1016 	if( ferror( stdout ) )
1017 		writeerr();
1018     }
1019 }
1020 
1021 /*
1022  * Decompress stdin to stdout.  This routine adapts to the codes in the
1023  * file building the "string" table on-the-fly; requiring no table to
1024  * be stored in the compressed file.  The tables used herein are shared
1025  * with those of the compress() routine.  See the definitions above.
1026  */
1027 
1028 decompress() {
1029     register char_type *stackp;
1030     register int finchar;
1031     register code_int code, oldcode, incode;
1032 
1033     /*
1034      * As above, initialize the first 256 entries in the table.
1035      */
1036     maxcode = MAXCODE(n_bits = INIT_BITS);
1037     for ( code = 255; code >= 0; code-- ) {
1038 	tab_prefixof(code) = 0;
1039 	tab_suffixof(code) = (char_type)code;
1040     }
1041     free_ent = ((block_compress) ? FIRST : 256 );
1042 
1043     finchar = oldcode = getcode();
1044     if(oldcode == -1)	/* EOF already? */
1045 	return;			/* Get out of here */
1046     putchar( (char)finchar );		/* first code must be 8 bits = char */
1047     if(ferror(stdout))		/* Crash if can't write */
1048 	writeerr();
1049     stackp = de_stack;
1050 
1051     while ( (code = getcode()) > -1 ) {
1052 
1053 	if ( (code == CLEAR) && block_compress ) {
1054 	    for ( code = 255; code >= 0; code-- )
1055 		tab_prefixof(code) = 0;
1056 	    clear_flg = 1;
1057 	    free_ent = FIRST - 1;
1058 	    if ( (code = getcode ()) == -1 )	/* O, untimely death! */
1059 		break;
1060 	}
1061 	incode = code;
1062 	/*
1063 	 * Special case for KwKwK string.
1064 	 */
1065 	if ( code >= free_ent ) {
1066             *stackp++ = finchar;
1067 	    code = oldcode;
1068 	}
1069 
1070 	/*
1071 	 * Generate output characters in reverse order
1072 	 */
1073 #ifdef SIGNED_COMPARE_SLOW
1074 	while ( ((unsigned long)code) >= ((unsigned long)256) ) {
1075 #else
1076 	while ( code >= 256 ) {
1077 #endif
1078 	    *stackp++ = tab_suffixof(code);
1079 	    code = tab_prefixof(code);
1080 	}
1081 	*stackp++ = finchar = tab_suffixof(code);
1082 
1083 	/*
1084 	 * And put them out in forward order
1085 	 */
1086 	do
1087 	    putchar ( *--stackp );
1088 	while ( stackp > de_stack );
1089 
1090 	/*
1091 	 * Generate the new entry.
1092 	 */
1093 	if ( (code=free_ent) < maxmaxcode ) {
1094 	    tab_prefixof(code) = (unsigned short)oldcode;
1095 	    tab_suffixof(code) = finchar;
1096 	    free_ent = code+1;
1097 	}
1098 	/*
1099 	 * Remember previous code.
1100 	 */
1101 	oldcode = incode;
1102     }
1103     fflush( stdout );
1104     if(ferror(stdout))
1105 	writeerr();
1106 }
1107 
1108 /*****************************************************************
1109  * TAG( getcode )
1110  *
1111  * Read one code from the standard input.  If EOF, return -1.
1112  * Inputs:
1113  * 	stdin
1114  * Outputs:
1115  * 	code or -1 is returned.
1116  */
1117 
1118 code_int
1119 getcode() {
1120     /*
1121      * On the VAX, it is important to have the register declarations
1122      * in exactly the order given, or the asm will break.
1123      */
1124     register code_int code;
1125     static int offset = 0, size = 0;
1126     static char_type buf[BITS];
1127     register int r_off, bits;
1128     register char_type *bp = buf;
1129 
1130     if ( clear_flg > 0 || offset >= size || free_ent > maxcode ) {
1131 	/*
1132 	 * If the next entry will be too big for the current code
1133 	 * size, then we must increase the size.  This implies reading
1134 	 * a new buffer full, too.
1135 	 */
1136 	if ( free_ent > maxcode ) {
1137 	    n_bits++;
1138 	    if ( n_bits == maxbits )
1139 		maxcode = maxmaxcode;	/* won't get any bigger now */
1140 	    else
1141 		maxcode = MAXCODE(n_bits);
1142 	}
1143 	if ( clear_flg > 0) {
1144     	    maxcode = MAXCODE (n_bits = INIT_BITS);
1145 	    clear_flg = 0;
1146 	}
1147 	size = fread( buf, 1, n_bits, stdin );
1148 	if ( size <= 0 )
1149 	    return -1;			/* end of file */
1150 	offset = 0;
1151 	/* Round size down to integral number of codes */
1152 	size = (size << 3) - (n_bits - 1);
1153     }
1154     r_off = offset;
1155     bits = n_bits;
1156 #ifdef vax
1157     asm( "extzv   r10,r9,(r8),r11" );
1158 #else /* not a vax */
1159 	/*
1160 	 * Get to the first byte.
1161 	 */
1162 	bp += (r_off >> 3);
1163 	r_off &= 7;
1164 	/* Get first part (low order bits) */
1165 #ifdef NO_UCHAR
1166 	code = ((*bp++ >> r_off) & rmask[8 - r_off]) & 0xff;
1167 #else
1168 	code = (*bp++ >> r_off);
1169 #endif /* NO_UCHAR */
1170 	bits -= (8 - r_off);
1171 	r_off = 8 - r_off;		/* now, offset into code word */
1172 	/* Get any 8 bit parts in the middle (<=1 for up to 16 bits). */
1173 	if ( bits >= 8 ) {
1174 #ifdef NO_UCHAR
1175 	    code |= (*bp++ & 0xff) << r_off;
1176 #else
1177 	    code |= *bp++ << r_off;
1178 #endif /* NO_UCHAR */
1179 	    r_off += 8;
1180 	    bits -= 8;
1181 	}
1182 	/* high order bits. */
1183 	code |= (*bp & rmask[bits]) << r_off;
1184 #endif /* vax */
1185     offset += n_bits;
1186 
1187     return code;
1188 }
1189 
1190 char *
1191 rindex(s, c)		/* For those who don't have it in libc.a */
1192 register char *s, c;
1193 {
1194 	char *p;
1195 	for (p = NULL; *s; s++)
1196 	    if (*s == c)
1197 		p = s;
1198 	return(p);
1199 }
1200 
1201 #ifdef DEBUG
1202 printcodes()
1203 {
1204     /*
1205      * Just print out codes from input file.  For debugging.
1206      */
1207     code_int code;
1208     int col = 0, bits;
1209 
1210     bits = n_bits = INIT_BITS;
1211     maxcode = MAXCODE(n_bits);
1212     free_ent = ((block_compress) ? FIRST : 256 );
1213     while ( ( code = getcode() ) >= 0 ) {
1214 	if ( (code == CLEAR) && block_compress ) {
1215    	    free_ent = FIRST - 1;
1216    	    clear_flg = 1;
1217 	}
1218 	else if ( free_ent < maxmaxcode )
1219 	    free_ent++;
1220 	if ( bits != n_bits ) {
1221 	    fprintf(stderr, "\nChange to %d bits\n", n_bits );
1222 	    bits = n_bits;
1223 	    col = 0;
1224 	}
1225 	fprintf(stderr, "%5d%c", code, (col+=6) >= 74 ? (col = 0, '\n') : ' ' );
1226     }
1227     putc( '\n', stderr );
1228     exit( 0 );
1229 }
1230 
1231 code_int sorttab[1<<BITS];	/* sorted pointers into htab */
1232 
1233 dump_tab()	/* dump string table */
1234 {
1235     register int i, first;
1236     register ent;
1237 #define STACK_SIZE	15000
1238     int stack_top = STACK_SIZE;
1239     register c;
1240 
1241     if(do_decomp == 0) {	/* compressing */
1242 	register int flag = 1;
1243 
1244 	for(i=0; i<hsize; i++) {	/* build sort pointers */
1245 		if((long)htabof(i) >= 0) {
1246 			sorttab[codetabof(i)] = i;
1247 		}
1248 	}
1249 	first = block_compress ? FIRST : 256;
1250 	for(i = first; i < free_ent; i++) {
1251 		fprintf(stderr, "%5d: \"", i);
1252 		de_stack[--stack_top] = '\n';
1253 		de_stack[--stack_top] = '"';
1254 		stack_top = in_stack((htabof(sorttab[i])>>maxbits)&0xff,
1255                                      stack_top);
1256 		for(ent=htabof(sorttab[i]) & ((1<<maxbits)-1);
1257 		    ent > 256;
1258 		    ent=htabof(sorttab[ent]) & ((1<<maxbits)-1)) {
1259 			stack_top = in_stack(htabof(sorttab[ent]) >> maxbits,
1260 						stack_top);
1261 		}
1262 		stack_top = in_stack(ent, stack_top);
1263 		fwrite( &de_stack[stack_top], 1, STACK_SIZE-stack_top, stderr);
1264 	   	stack_top = STACK_SIZE;
1265 	}
1266    } else if(!debug) {	/* decompressing */
1267 
1268        for ( i = 0; i < free_ent; i++ ) {
1269 	   ent = i;
1270 	   c = tab_suffixof(ent);
1271 	   if ( isascii(c) && isprint(c) )
1272 	       fprintf( stderr, "%5d: %5d/'%c'  \"",
1273 			   ent, tab_prefixof(ent), c );
1274 	   else
1275 	       fprintf( stderr, "%5d: %5d/\\%03o \"",
1276 			   ent, tab_prefixof(ent), c );
1277 	   de_stack[--stack_top] = '\n';
1278 	   de_stack[--stack_top] = '"';
1279 	   for ( ; ent != NULL;
1280 		   ent = (ent >= FIRST ? tab_prefixof(ent) : NULL) ) {
1281 	       stack_top = in_stack(tab_suffixof(ent), stack_top);
1282 	   }
1283 	   fwrite( &de_stack[stack_top], 1, STACK_SIZE - stack_top, stderr );
1284 	   stack_top = STACK_SIZE;
1285        }
1286     }
1287 }
1288 
1289 int
1290 in_stack(c, stack_top)
1291 	register c, stack_top;
1292 {
1293 	if ( (isascii(c) && isprint(c) && c != '\\') || c == ' ' ) {
1294 	    de_stack[--stack_top] = c;
1295 	} else {
1296 	    switch( c ) {
1297 	    case '\n': de_stack[--stack_top] = 'n'; break;
1298 	    case '\t': de_stack[--stack_top] = 't'; break;
1299 	    case '\b': de_stack[--stack_top] = 'b'; break;
1300 	    case '\f': de_stack[--stack_top] = 'f'; break;
1301 	    case '\r': de_stack[--stack_top] = 'r'; break;
1302 	    case '\\': de_stack[--stack_top] = '\\'; break;
1303 	    default:
1304 	 	de_stack[--stack_top] = '0' + c % 8;
1305 	 	de_stack[--stack_top] = '0' + (c / 8) % 8;
1306 	 	de_stack[--stack_top] = '0' + c / 64;
1307 	 	break;
1308 	    }
1309 	    de_stack[--stack_top] = '\\';
1310 	}
1311 	return stack_top;
1312 }
1313 #endif /* DEBUG */
1314 
1315 writeerr()
1316 {
1317     perror ( ofname );
1318     unlink ( ofname );
1319     exit ( 1 );
1320 }
1321 
1322 copystat(ifname, ofname)
1323 char *ifname, *ofname;
1324 {
1325     struct stat statbuf;
1326     int mode;
1327     time_t timep[2];
1328 
1329     fclose(stdout);
1330     if (stat(ifname, &statbuf)) {		/* Get stat on input file */
1331 	perror(ifname);
1332 	return;
1333     }
1334     if ((statbuf.st_mode & S_IFMT/*0170000*/) != S_IFREG/*0100000*/) {
1335 	if(quiet)
1336 	    	fprintf(stderr, "%s: ", ifname);
1337 	fprintf(stderr, " -- not a regular file: unchanged");
1338 	exit_stat = 1;
1339 	perm_stat = 1;
1340     } else if (statbuf.st_nlink > 1) {
1341 	if(quiet)
1342 	    	fprintf(stderr, "%s: ", ifname);
1343 	fprintf(stderr, " -- has %d other links: unchanged",
1344 		statbuf.st_nlink - 1);
1345 	exit_stat = 1;
1346 	perm_stat = 1;
1347     } else if (exit_stat == 2 && (!force)) { /* No compression: remove file.Z */
1348 	if(!quiet)
1349 		fprintf(stderr, " -- file unchanged");
1350     } else {			/* ***** Successful Compression ***** */
1351 	exit_stat = 0;
1352 	mode = statbuf.st_mode & 07777;
1353 	if (chmod(ofname, mode))		/* Copy modes */
1354 	    perror(ofname);
1355 	chown(ofname, statbuf.st_uid, statbuf.st_gid);	/* Copy ownership */
1356 	timep[0] = statbuf.st_atime;
1357 	timep[1] = statbuf.st_mtime;
1358 	utime(ofname, timep);	/* Update last accessed and modified times */
1359 	if (unlink(ifname))	/* Remove input file */
1360 	    perror(ifname);
1361 	if(!quiet)
1362 		fprintf(stderr, " -- replaced with %s", ofname);
1363 	return;		/* Successful return */
1364     }
1365 
1366     /* Unsuccessful return -- one of the tests failed */
1367     if (unlink(ofname))
1368 	perror(ofname);
1369 }
1370 
1371 void
1372 onintr ( )
1373 {
1374     if (!precious)
1375 	unlink ( ofname );
1376     exit ( 1 );
1377 }
1378 
1379 void
1380 oops ( )	/* wild pointer -- assume bad input */
1381 {
1382     if ( do_decomp )
1383     	fprintf ( stderr, "uncompress: corrupt input\n" );
1384     unlink ( ofname );
1385     exit ( 1 );
1386 }
1387 
1388 cl_block ()		/* table clear for block compress */
1389 {
1390     register long int rat;
1391 
1392     checkpoint = in_count + CHECK_GAP;
1393 #ifdef DEBUG
1394 	if ( debug ) {
1395     		fprintf ( stderr, "count: %ld, ratio: ", in_count );
1396      		prratio ( stderr, in_count, bytes_out );
1397 		fprintf ( stderr, "\n");
1398 	}
1399 #endif /* DEBUG */
1400 
1401     if(in_count > 0x007fffff) {	/* shift will overflow */
1402 	rat = bytes_out >> 8;
1403 	if(rat == 0) {		/* Don't divide by zero */
1404 	    rat = 0x7fffffff;
1405 	} else {
1406 	    rat = in_count / rat;
1407 	}
1408     } else {
1409 	rat = (in_count << 8) / bytes_out;	/* 8 fractional bits */
1410     }
1411     if ( rat > ratio ) {
1412 	ratio = rat;
1413     } else {
1414 	ratio = 0;
1415 #ifdef DEBUG
1416 	if(verbose)
1417 		dump_tab();	/* dump string table */
1418 #endif
1419  	cl_hash ( (count_int) hsize );
1420 	free_ent = FIRST;
1421 	clear_flg = 1;
1422 	output ( (code_int) CLEAR );
1423 #ifdef DEBUG
1424 	if(debug)
1425     		fprintf ( stderr, "clear\n" );
1426 #endif /* DEBUG */
1427     }
1428 }
1429 
1430 cl_hash(hsize)		/* reset code table */
1431 	register count_int hsize;
1432 {
1433 #ifndef XENIX_16	/* Normal machine */
1434 	register count_int *htab_p = htab+hsize;
1435 #else
1436 	register j;
1437 	register long k = hsize;
1438 	register count_int *htab_p;
1439 #endif
1440 	register long i;
1441 	register long m1 = -1;
1442 
1443 #ifdef XENIX_16
1444     for(j=0; j<=8 && k>=0; j++,k-=8192) {
1445 	i = 8192;
1446 	if(k < 8192) {
1447 		i = k;
1448 	}
1449 	htab_p = &(htab[j][i]);
1450 	i -= 16;
1451 	if(i > 0) {
1452 #else
1453 	i = hsize - 16;
1454 #endif
1455  	do {				/* might use Sys V memset(3) here */
1456 		*(htab_p-16) = m1;
1457 		*(htab_p-15) = m1;
1458 		*(htab_p-14) = m1;
1459 		*(htab_p-13) = m1;
1460 		*(htab_p-12) = m1;
1461 		*(htab_p-11) = m1;
1462 		*(htab_p-10) = m1;
1463 		*(htab_p-9) = m1;
1464 		*(htab_p-8) = m1;
1465 		*(htab_p-7) = m1;
1466 		*(htab_p-6) = m1;
1467 		*(htab_p-5) = m1;
1468 		*(htab_p-4) = m1;
1469 		*(htab_p-3) = m1;
1470 		*(htab_p-2) = m1;
1471 		*(htab_p-1) = m1;
1472 		htab_p -= 16;
1473 	} while ((i -= 16) >= 0);
1474 #ifdef XENIX_16
1475 	}
1476     }
1477 #endif
1478     	for ( i += 16; i > 0; i-- )
1479 		*--htab_p = m1;
1480 }
1481 
1482 prratio(stream, num, den)
1483 FILE *stream;
1484 long int num, den;
1485 {
1486 	register int q;			/* Doesn't need to be long */
1487 
1488 	if(num > 214748L) {		/* 2147483647/10000 */
1489 		q = num / (den / 10000L);
1490 	} else {
1491 		q = 10000L * num / den;		/* Long calculations, though */
1492 	}
1493 	if (q < 0) {
1494 		putc('-', stream);
1495 		q = -q;
1496 	}
1497 	fprintf(stream, "%d.%02d%%", q / 100, q % 100);
1498 }
1499 
1500 version()
1501 {
1502 	fprintf(stderr, "%s, Berkeley 5.12 06/01/90\n", rcs_ident);
1503 	fprintf(stderr, "Options: ");
1504 #ifdef vax
1505 	fprintf(stderr, "vax, ");
1506 #endif
1507 #ifdef NO_UCHAR
1508 	fprintf(stderr, "NO_UCHAR, ");
1509 #endif
1510 #ifdef SIGNED_COMPARE_SLOW
1511 	fprintf(stderr, "SIGNED_COMPARE_SLOW, ");
1512 #endif
1513 #ifdef XENIX_16
1514 	fprintf(stderr, "XENIX_16, ");
1515 #endif
1516 #ifdef COMPATIBLE
1517 	fprintf(stderr, "COMPATIBLE, ");
1518 #endif
1519 #ifdef DEBUG
1520 	fprintf(stderr, "DEBUG, ");
1521 #endif
1522 #ifdef BSD4_2
1523 	fprintf(stderr, "BSD4_2, ");
1524 #endif
1525 	fprintf(stderr, "BITS = %d\n", BITS);
1526 }
1527