📄 compress.c
字号:
unmake_z_name(ofname); /* strip off Z or .Z */
}
else { /* COMPRESSION */
if (*inpath){ /* adjust for inpath name */
strcpy(ifname,inpath); /* and copy into ifname */
strcat(ifname,name_index(*fileptr));
}
else
strcpy(ifname,*fileptr);
if (is_z_name(ifname)) {
fprintf(stderr, "%s: already has %s suffix -- no change\n",
ifname,suffix);
continue;
}
/* Open input file */
if ((freopen(ifname,READ_FILE_TYPE, stdin)) == NULL) {
perror(ifname);
continue;
}
else
setvbuf(stdin,xbuf,_IOFBF,XBUFSIZE);
/* Generate output filename */
if (*outpath){ /* adjust for outpath name */
strcpy(ofname,outpath); /* and copy into ofname */
strcat(ofname,name_index(ifname));
}
else /* place it in directory of input file */
strcpy(ofname,ifname); /* DjG may screw up the placement */
/* of the outfile */
if (!(make_z_name(ofname)))
continue;
} /* end else compression we now have the files set up */
/* Check for overwrite of existing file */
if (!overwrite && !zcat_flg) {
if (!stat(ofname, &statbuf)) {
response = 'n';
fprintf(stderr, "%s already exists;", ofname);
#ifndef NOSIGNAL
if (foreground()) {
#else
if (TRUE) {
#endif
fprintf(stderr, "\ndo you wish to overwrite %s (y or n)? ",
ofname);
fflush(stderr);
response = get_one();
}
if ((response != 'y') && (response != 'Y')){
fprintf(stderr, "\tnot overwritten\n");
continue;
}
} /* end if stat */
} /* end if overwrite */
/* Output file is opened in compress/decompress routines */
if (!zcat_flg)
if(test_file(ifname)){
putc('\n',stderr);
continue; /* either linked or not a regular file */
}
/* Actually do the compression/decompression on files */
if (!do_decomp){
compress();
check_error();
}
else{
decompress();
check_error();
}
if(!zcat_flg) {
copystat(ifname, ofname); /* Copy stats */
if((exit_stat ) || (!quiet))
putc('\n', stderr);
} /* end if zcat */
} /*end for loop */
} /* end if filelist */
else { /* it is standard input to standard output*/
#if (FILTER == FALSE) /* filter is defined as true or false */
/* DjG added to make more sense. The following tests for standard
input being a character device. If so, there is no use in MsDos
for the program, as that will compress from the keyboard to the
console. Sure not what is needed. Instead, the usage function
is called. In Xenix/Unix systems, there is a need for this type
of pipe as the input may be from a char dev, remote station.
*/
/* check if input is unredirected */
if ( isatty(fileno(stdin)) ){
Usage(1);
exit(NORMAL);
}
#endif
/* filter */
if (do_decomp){
setvbuf(stdin,zbuf,_IOFBF,ZBUFSIZE); /* make the buffers larger */
setvbuf(stdout,xbuf,_IOFBF,XBUFSIZE);
}
else{
setvbuf(stdin,xbuf,_IOFBF,XBUFSIZE); /* make the buffers larger */
setvbuf(stdout,zbuf,_IOFBF,ZBUFSIZE);
}
if (!do_decomp) { /* compress stdin to stdout */
compress();
check_error();
if(!quiet)
putc('\n', stderr);
} /* end compress stdio */
else { /* decompress stdin to stdout */
/* Check the magic number */
if (!nomagic) {
if ((getchar()!=(magic_header[0] & 0xFF))
|| (getchar()!=(magic_header[1] & 0xFF))) {
fprintf(stderr, "stdin: not in compressed format\n");
exit(ERROR);
}
maxbits = getchar(); /* set -b from file */
block_compress = maxbits & BLOCK_MASK;
maxbits &= BIT_MASK;
if(maxbits > MAXBITS) {
fprintf(stderr,
"stdin: compressed with %d bits, can only handle %d bits\n",
maxbits, MAXBITS);
exit(ERROR);
}
}
decompress();
check_error();
} /* end else decomp stdio */
} /* end else standard input */
exit(exit_stat);
}
void Usage(flag)
int flag;
{
static char *keep2 = "keep";
static char *keep3 = "kill (erase)";
static char *on = "on";
static char *off = "off";
#ifdef DEBUG
fprintf(stderr,"Usage: %s [-cCdDf?hkKvV][-b maxbits][-Iinpath][-Ooutpath][filenames...]\n",
prog_name);
#else
fprintf(stderr,"Usage: %s [-cCdf?hkKvV][-b maxbits][-Iinpath][-Ooutpath][filenames...]\n",
prog_name);
#endif
if (flag)
return;
fprintf(stderr,"Argument Processing..case is significant:\n");
fprintf(stderr," MUST use '-' for switch character\nAll flags are optional.\n");
#ifdef DEBUG
fprintf(stderr," -D => debug; Keep file on error.\n");
fprintf(stderr," -V => print Version; debug verbose\n");
#else
fprintf(stderr," -V => print Version\n");
#endif
fprintf(stderr," -d => do_decomp default = %s\n",(do_decomp)?on:off);
fprintf(stderr," -v => verbose\n");
fprintf(stderr," -f => force overwrite of output file default = %s\n",
(force)?on:off);
fprintf(stderr," -n => no header: useful to uncompress old files\n");
fprintf(stderr," -c => cat all output to stdout default = %s\n",
(zcat_flg)?on:off);
fprintf(stderr," -C => generate output compatible with compress 2.0.\n");
fprintf(stderr," -k => %s input file, default == %s\n",(keep)?keep3:keep2,
(keep)?keep2:keep3);
fprintf(stderr," -K => %s output file on error, default == %s\n",
(keep_error)?keep3:keep2,(keep_error)?keep2:keep3);
fprintf(stderr," -b maxbits => default == %d bits, max == %d bits\n",maxbits,MAXBITS);
fprintf(stderr," -I pathname => infile path == %s\n",inpath);
fprintf(stderr," -O pathname => outfile path == %s\n",outpath);
fprintf(stderr," -? -h => help usage.\n");
}
/*
* All previous #ifdef'ed code should return() a value.
* If no other option is available, the following is the original code.
* It not only reads from stderr (not a defined operation)
* but it does so via an explicit read() call on file descriptor 2!
* So much for portability. -Dal
*/
/* Dal included code to use the MSC getche() but it crashes because of
the freopening of stdin. Have to use the cludge for MSC. This function is
included so that others who have problems with the keyboard read can
change this function for their system. DjG
*/
char get_one()
/*
* get a single character, with echo.
*/
{
char tmp[2];
int fd;
#ifdef SOZOBON
return(0x7F & getche());
}
#else
# ifdef MINIX
fd = open("/dev/tty", 0); /* open the tty directly */
# else
fd = fileno(stderr); /* read from stderr */
# endif
read(fd, tmp, 2);
while (tmp[1] != '\n') {
if (read(fd, tmp+1, 1) < 0) { /* Ack! */
perror("stderr");
break;
}
}
return(tmp[0]);
}
#endif
void writeerr()
{
perror ( ofname );
if (!zcat_flg && !keep_error){
fclose(stdout);
unlink ( ofname );
}
exit ( 1 );
}
#ifndef NOSIGNAL
/*
* This routine returns 1 if we are running in the foreground and stderr
* is a tty.
*/
int foreground()
{
if(bgnd_flag) { /* background? */
return(0);
}
else { /* foreground */
if(isatty(2)) { /* and stderr is a tty */
return(1);
} else {
return(0);
}
}
}
#endif
void prratio(stream, num, den)
FILE *stream;
long int num, den;
{
register int q; /* Doesn't need to be long */
if(num > 214748L) { /* 2147483647/10000 */
q = (int) (num / (den / 10000L));
}
else {
q = (int) (10000L * num / den); /* Long calculations, though */
}
if (q < 0) {
putc('-', stream);
q = -q;
}
fprintf(stream, "%d.%02d%%", q / 100, q % 100);
}
int check_error() /* returning OK continues with processing next file */
{
switch(exit_stat) {
case OK:
return (OK);
case NOMEM:
if (do_decomp)
fprintf(stderr,"%s: not enough memory to decompress '%s'.\n", prog_name, ifname);
else
fprintf(stderr,"%s: not enough memory to compress '%s'.\n", prog_name, ifname);
break;
/* return(OK); */ /* DjG removed causes problems */
case SIGNAL_ERROR:
fprintf(stderr,"%s: error setting signal interupt.\n",prog_name);
exit(ERROR);
break;
case READERR:
fprintf(stderr,"%s: read error on input '%s'.\n", prog_name, ifname);
break;
case WRITEERR:
fprintf(stderr,"%s: write error on output '%s'.\n", prog_name, ofname);
break;
case TOKTOOBIG:
fprintf(stderr,"%s: token too long in '%s'. Failed on realloc().\n", prog_name, ifname);
break;
case INFILEBAD:
fprintf(stderr, "%s: '%s' in unknown compressed format.\n", prog_name, ifname);
break;
case CODEBAD:
fprintf(stderr,"%s: file token bad in '%s'.\n", prog_name,ifname);
break;
case TABLEBAD:
fprintf(stderr,"%s: internal error -- tables corrupted.\n", prog_name);
break;
case NOTOPENED:
fprintf(stderr,"%s: could not open output file %s\n",prog_name,ofname);
exit(ERROR);
break;
case NOSAVING:
if (force)
exit_stat = OK;
return (OK);
default:
fprintf(stderr,"%s: internal error -- illegal return value = %d.\n", prog_name,exit_stat);
}
if (!zcat_flg && !keep_error){
fclose(stdout); /* won't get here without an error */
unlink ( ofname );
}
exit(exit_stat);
return(ERROR);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -