diff options
Diffstat (limited to '')
| -rw-r--r-- | minigzip.c | 210 |
1 files changed, 210 insertions, 0 deletions
diff --git a/minigzip.c b/minigzip.c new file mode 100644 index 0000000..688b3a1 --- /dev/null +++ b/minigzip.c | |||
| @@ -0,0 +1,210 @@ | |||
| 1 | /* minigzip.c -- simulate gzip using the zlib compression library | ||
| 2 | * Copyright (C) 1995 Jean-loup Gailly. | ||
| 3 | * For conditions of distribution and use, see copyright notice in zlib.h | ||
| 4 | */ | ||
| 5 | |||
| 6 | /* | ||
| 7 | * minigzip is a minimal implementation of the gzip utility. This is | ||
| 8 | * only an example of using zlib and isn't meant to replace the | ||
| 9 | * full-featured gzip. No attempt is made to deal with file systems | ||
| 10 | * limiting names to 14 or 8+3 characters, etc... Error checking is | ||
| 11 | * very limited. So use minigzip only for testing; use gzip for the | ||
| 12 | * real thing. On MSDOS, use only on file names without extension | ||
| 13 | * or in pipe mode. | ||
| 14 | */ | ||
| 15 | |||
| 16 | /* $Id: minigzip.c,v 1.1 1995/04/14 13:35:59 jloup Exp $ */ | ||
| 17 | |||
| 18 | #include <stdio.h> | ||
| 19 | #include "zlib.h" | ||
| 20 | |||
| 21 | #ifdef MSDOS | ||
| 22 | # include <fcntl.h> | ||
| 23 | # define SET_BINARY_MODE(file) setmode(fileno(file), O_BINARY) | ||
| 24 | #else | ||
| 25 | # define SET_BINARY_MODE(file) | ||
| 26 | #endif | ||
| 27 | |||
| 28 | #define BUFLEN 4096 | ||
| 29 | #define MAX_NAME_LEN 1024 | ||
| 30 | |||
| 31 | #define local static | ||
| 32 | /* For MSDOS and other systems with limitation on stack size. For Unix, | ||
| 33 | #define local | ||
| 34 | works also. | ||
| 35 | */ | ||
| 36 | |||
| 37 | char *prog; | ||
| 38 | |||
| 39 | /* =========================================================================== | ||
| 40 | * Display error message and exit | ||
| 41 | */ | ||
| 42 | void error(msg) | ||
| 43 | char *msg; | ||
| 44 | { | ||
| 45 | fprintf(stderr, "%s: %s\n", prog, msg); | ||
| 46 | exit(1); | ||
| 47 | } | ||
| 48 | |||
| 49 | /* =========================================================================== | ||
| 50 | * Compress input to output then close both files. | ||
| 51 | */ | ||
| 52 | void gz_compress(in, out) | ||
| 53 | FILE *in; | ||
| 54 | gzFile out; | ||
| 55 | { | ||
| 56 | local char buf[BUFLEN]; | ||
| 57 | int len; | ||
| 58 | int err; | ||
| 59 | |||
| 60 | for (;;) { | ||
| 61 | len = fread(buf, 1, sizeof(buf), in); | ||
| 62 | if (ferror(in)) { | ||
| 63 | perror("fread"); | ||
| 64 | exit(1); | ||
| 65 | } | ||
| 66 | if (len == 0) break; | ||
| 67 | |||
| 68 | if (gzwrite(out, buf, len) != len) error(gzerror(out, &err)); | ||
| 69 | } | ||
| 70 | fclose(in); | ||
| 71 | if (gzclose(out) != Z_OK) error("failed gzclose"); | ||
| 72 | } | ||
| 73 | |||
| 74 | /* =========================================================================== | ||
| 75 | * Uncompress input to output then close both files. | ||
| 76 | */ | ||
| 77 | void gz_uncompress(in, out) | ||
| 78 | gzFile in; | ||
| 79 | FILE *out; | ||
| 80 | { | ||
| 81 | local char buf[BUFLEN]; | ||
| 82 | int len; | ||
| 83 | int err; | ||
| 84 | |||
| 85 | for (;;) { | ||
| 86 | len = gzread(in, buf, sizeof(buf)); | ||
| 87 | if (len < 0) error (gzerror(in, &err)); | ||
| 88 | if (len == 0) break; | ||
| 89 | |||
| 90 | if (fwrite(buf, 1, len, out) != len) error("failed fwrite"); | ||
| 91 | } | ||
| 92 | if (fclose(out)) error("failed fclose"); | ||
| 93 | |||
| 94 | if (gzclose(in) != Z_OK) error("failed gzclose"); | ||
| 95 | } | ||
| 96 | |||
| 97 | |||
| 98 | /* =========================================================================== | ||
| 99 | * Compress the given file: create a corresponding .gz file and remove the | ||
| 100 | * original. | ||
| 101 | */ | ||
| 102 | void file_compress(file) | ||
| 103 | char *file; | ||
| 104 | { | ||
| 105 | local char outfile[MAX_NAME_LEN]; | ||
| 106 | FILE *in; | ||
| 107 | gzFile out; | ||
| 108 | |||
| 109 | strcpy(outfile, file); | ||
| 110 | strcat(outfile, ".gz"); | ||
| 111 | |||
| 112 | in = fopen(file, "rb"); | ||
| 113 | if (in == NULL) { | ||
| 114 | perror(file); | ||
| 115 | exit(1); | ||
| 116 | } | ||
| 117 | out = gzopen(outfile, "wb"); | ||
| 118 | if (out == NULL) { | ||
| 119 | fprintf(stderr, "%s: can't gzopen %s\n", prog, outfile); | ||
| 120 | exit(1); | ||
| 121 | } | ||
| 122 | gz_compress(in, out); | ||
| 123 | |||
| 124 | unlink(file); | ||
| 125 | } | ||
| 126 | |||
| 127 | |||
| 128 | /* =========================================================================== | ||
| 129 | * Uncompress the given file and remove the original. | ||
| 130 | */ | ||
| 131 | void file_uncompress(file) | ||
| 132 | char *file; | ||
| 133 | { | ||
| 134 | local char buf[MAX_NAME_LEN]; | ||
| 135 | char *infile, *outfile; | ||
| 136 | FILE *out; | ||
| 137 | gzFile in; | ||
| 138 | int len = strlen(file); | ||
| 139 | |||
| 140 | strcpy(buf, file); | ||
| 141 | |||
| 142 | if (len > 3 && strcmp(file+len-3, ".gz") == 0) { | ||
| 143 | infile = file; | ||
| 144 | outfile = buf; | ||
| 145 | outfile[len-3] = '\0'; | ||
| 146 | } else { | ||
| 147 | outfile = file; | ||
| 148 | infile = buf; | ||
| 149 | strcat(infile, ".gz"); | ||
| 150 | } | ||
| 151 | in = gzopen(infile, "rb"); | ||
| 152 | if (in == NULL) { | ||
| 153 | fprintf(stderr, "%s: can't gzopen %s\n", prog, infile); | ||
| 154 | exit(1); | ||
| 155 | } | ||
| 156 | out = fopen(outfile, "wb"); | ||
| 157 | if (out == NULL) { | ||
| 158 | perror(file); | ||
| 159 | exit(1); | ||
| 160 | } | ||
| 161 | |||
| 162 | gz_uncompress(in, out); | ||
| 163 | |||
| 164 | unlink(infile); | ||
| 165 | } | ||
| 166 | |||
| 167 | |||
| 168 | /* =========================================================================== | ||
| 169 | * Usage: minigzip [-d] [files...] | ||
| 170 | */ | ||
| 171 | |||
| 172 | void main(argc, argv) | ||
| 173 | int argc; | ||
| 174 | char *argv[]; | ||
| 175 | { | ||
| 176 | int uncompr = 0; | ||
| 177 | gzFile file; | ||
| 178 | |||
| 179 | prog = argv[0]; | ||
| 180 | argc--, argv++; | ||
| 181 | |||
| 182 | if (argc > 0) { | ||
| 183 | uncompr = (strcmp(*argv, "-d") == 0); | ||
| 184 | if (uncompr) { | ||
| 185 | argc--, argv++; | ||
| 186 | } | ||
| 187 | } | ||
| 188 | if (argc == 0) { | ||
| 189 | SET_BINARY_MODE(stdin); | ||
| 190 | SET_BINARY_MODE(stdout); | ||
| 191 | if (uncompr) { | ||
| 192 | file = gzdopen(fileno(stdin), "rb"); | ||
| 193 | if (file == NULL) error("can't gzdopen stdin"); | ||
| 194 | gz_uncompress(file, stdout); | ||
| 195 | } else { | ||
| 196 | file = gzdopen(fileno(stdout), "wb"); | ||
| 197 | if (file == NULL) error("can't gzdopen stdout"); | ||
| 198 | gz_compress(stdin, file); | ||
| 199 | } | ||
| 200 | } else { | ||
| 201 | do { | ||
| 202 | if (uncompr) { | ||
| 203 | file_uncompress(*argv); | ||
| 204 | } else { | ||
| 205 | file_compress(*argv); | ||
| 206 | } | ||
| 207 | } while (argv++, --argc); | ||
| 208 | } | ||
| 209 | exit(0); | ||
| 210 | } | ||
