diff options
| author | Mark Adler <madler@alumni.caltech.edu> | 2011-10-07 01:57:07 -0700 |
|---|---|---|
| committer | Mark Adler <madler@alumni.caltech.edu> | 2011-10-07 02:11:56 -0700 |
| commit | f442c1e89e99ae5a0068a2d32e7284c2623f09fd (patch) | |
| tree | 1bc659f486af707673c36916c4d75ef7f517dece /minigzip.c | |
| parent | 518ad0177ae2f1aaefc49285b3536a6bd8d9973c (diff) | |
| download | zlib-f442c1e89e99ae5a0068a2d32e7284c2623f09fd.tar.gz zlib-f442c1e89e99ae5a0068a2d32e7284c2623f09fd.tar.bz2 zlib-f442c1e89e99ae5a0068a2d32e7284c2623f09fd.zip | |
Add a ./config --solo option to make zlib subset with no libary use
A common request has been the ability to compile zlib to require no
other libraries. This --solo option provides that ability. The price
is that the gz*, compress*, and uncompress functions are eliminated,
and that the user must provide memory allocation and free routines to
deflate and inflate when initializing.
Diffstat (limited to 'minigzip.c')
| -rw-r--r-- | minigzip.c | 193 |
1 files changed, 192 insertions, 1 deletions
| @@ -1,5 +1,5 @@ | |||
| 1 | /* minigzip.c -- simulate gzip using the zlib compression library | 1 | /* minigzip.c -- simulate gzip using the zlib compression library |
| 2 | * Copyright (C) 1995-2006, 2010 Jean-loup Gailly. | 2 | * Copyright (C) 1995-2006, 2010, 2011 Jean-loup Gailly. |
| 3 | * For conditions of distribution and use, see copyright notice in zlib.h | 3 | * For conditions of distribution and use, see copyright notice in zlib.h |
| 4 | */ | 4 | */ |
| 5 | 5 | ||
| @@ -138,6 +138,197 @@ static void pwinerror (s) | |||
| 138 | # define local | 138 | # define local |
| 139 | #endif | 139 | #endif |
| 140 | 140 | ||
| 141 | #ifdef Z_SOLO | ||
| 142 | /* for Z_SOLO, create simplified gz* functions using deflate and inflate */ | ||
| 143 | |||
| 144 | #if defined(Z_HAVE_UNISTD_H) || defined(Z_LARGE) | ||
| 145 | # include <unistd.h> /* for unlink() */ | ||
| 146 | #endif | ||
| 147 | |||
| 148 | void *myalloc OF((void *, unsigned, unsigned)); | ||
| 149 | void myfree OF((void *, void *)); | ||
| 150 | |||
| 151 | void *myalloc(q, n, m) | ||
| 152 | void *q; | ||
| 153 | unsigned n, m; | ||
| 154 | { | ||
| 155 | q = Z_NULL; | ||
| 156 | return calloc(n, m); | ||
| 157 | } | ||
| 158 | |||
| 159 | void myfree(q, p) | ||
| 160 | void *q, *p; | ||
| 161 | { | ||
| 162 | q = Z_NULL; | ||
| 163 | free(p); | ||
| 164 | } | ||
| 165 | |||
| 166 | typedef struct gzFile_s { | ||
| 167 | FILE *file; | ||
| 168 | int write; | ||
| 169 | int err; | ||
| 170 | char *msg; | ||
| 171 | z_stream strm; | ||
| 172 | } *gzFile; | ||
| 173 | |||
| 174 | gzFile gzopen OF((const char *, const char *)); | ||
| 175 | gzFile gzdopen OF((int, const char *)); | ||
| 176 | gzFile gz_open OF((const char *, int, const char *)); | ||
| 177 | |||
| 178 | gzFile gzopen(path, mode) | ||
| 179 | const char *path; | ||
| 180 | const char *mode; | ||
| 181 | { | ||
| 182 | return gz_open(path, -1, mode); | ||
| 183 | } | ||
| 184 | |||
| 185 | gzFile gzdopen(fd, mode) | ||
| 186 | int fd; | ||
| 187 | const char *mode; | ||
| 188 | { | ||
| 189 | return gz_open(NULL, fd, mode); | ||
| 190 | } | ||
| 191 | |||
| 192 | gzFile gz_open(path, fd, mode) | ||
| 193 | const char *path; | ||
| 194 | int fd; | ||
| 195 | const char *mode; | ||
| 196 | { | ||
| 197 | gzFile gz; | ||
| 198 | int ret; | ||
| 199 | |||
| 200 | gz = malloc(sizeof(gzFile)); | ||
| 201 | if (gz == NULL) | ||
| 202 | return NULL; | ||
| 203 | gz->write = strchr(mode, 'w') != NULL; | ||
| 204 | gz->strm.zalloc = myalloc; | ||
| 205 | gz->strm.zfree = myfree; | ||
| 206 | gz->strm.opaque = Z_NULL; | ||
| 207 | if (gz->write) | ||
| 208 | ret = deflateInit2(&(gz->strm), -1, 8, 15 + 16, 8, 0); | ||
| 209 | else { | ||
| 210 | gz->strm.next_in = 0; | ||
| 211 | gz->strm.avail_in = Z_NULL; | ||
| 212 | ret = inflateInit2(&(gz->strm), 15 + 16); | ||
| 213 | } | ||
| 214 | if (ret != Z_OK) { | ||
| 215 | free(gz); | ||
| 216 | return NULL; | ||
| 217 | } | ||
| 218 | gz->file = path == NULL ? fdopen(fd, gz->write ? "wb" : "rb") : | ||
| 219 | fopen(path, gz->write ? "wb" : "rb"); | ||
| 220 | if (gz->file == NULL) { | ||
| 221 | gz->write ? deflateEnd(&(gz->strm)) : inflateEnd(&(gz->strm)); | ||
| 222 | free(gz); | ||
| 223 | return NULL; | ||
| 224 | } | ||
| 225 | gz->err = 0; | ||
| 226 | gz->msg = ""; | ||
| 227 | return gz; | ||
| 228 | } | ||
| 229 | |||
| 230 | int gzwrite OF((gzFile, const void *, unsigned)); | ||
| 231 | |||
| 232 | int gzwrite(gz, buf, len) | ||
| 233 | gzFile gz; | ||
| 234 | const void *buf; | ||
| 235 | unsigned len; | ||
| 236 | { | ||
| 237 | z_stream *strm; | ||
| 238 | unsigned char out[BUFLEN]; | ||
| 239 | |||
| 240 | if (gz == NULL || !gz->write) | ||
| 241 | return 0; | ||
| 242 | strm = &(gz->strm); | ||
| 243 | strm->next_in = (void *)buf; | ||
| 244 | strm->avail_in = len; | ||
| 245 | do { | ||
| 246 | strm->next_out = out; | ||
| 247 | strm->avail_out = BUFLEN; | ||
| 248 | (void)deflate(strm, Z_NO_FLUSH); | ||
| 249 | fwrite(out, 1, BUFLEN - strm->avail_out, gz->file); | ||
| 250 | } while (strm->avail_out == 0); | ||
| 251 | return len; | ||
| 252 | } | ||
| 253 | |||
| 254 | int gzread OF((gzFile, void *, unsigned)); | ||
| 255 | |||
| 256 | int gzread(gz, buf, len) | ||
| 257 | gzFile gz; | ||
| 258 | void *buf; | ||
| 259 | unsigned len; | ||
| 260 | { | ||
| 261 | int ret; | ||
| 262 | unsigned got; | ||
| 263 | unsigned char in[1]; | ||
| 264 | z_stream *strm; | ||
| 265 | |||
| 266 | if (gz == NULL || gz->write) | ||
| 267 | return 0; | ||
| 268 | if (gz->err) | ||
| 269 | return 0; | ||
| 270 | strm = &(gz->strm); | ||
| 271 | strm->next_out = (void *)buf; | ||
| 272 | strm->avail_out = len; | ||
| 273 | do { | ||
| 274 | got = fread(in, 1, 1, gz->file); | ||
| 275 | if (got == 0) | ||
| 276 | break; | ||
| 277 | strm->next_in = in; | ||
| 278 | strm->avail_in = 1; | ||
| 279 | ret = inflate(strm, Z_NO_FLUSH); | ||
| 280 | if (ret == Z_DATA_ERROR) { | ||
| 281 | gz->err = Z_DATA_ERROR; | ||
| 282 | gz->msg = strm->msg; | ||
| 283 | return 0; | ||
| 284 | } | ||
| 285 | if (ret == Z_STREAM_END) | ||
| 286 | inflateReset(strm); | ||
| 287 | } while (strm->avail_out); | ||
| 288 | return len - strm->avail_out; | ||
| 289 | } | ||
| 290 | |||
| 291 | int gzclose OF((gzFile)); | ||
| 292 | |||
| 293 | int gzclose(gz) | ||
| 294 | gzFile gz; | ||
| 295 | { | ||
| 296 | z_stream *strm; | ||
| 297 | unsigned char out[BUFLEN]; | ||
| 298 | |||
| 299 | if (gz == NULL) | ||
| 300 | return Z_STREAM_ERROR; | ||
| 301 | strm = &(gz->strm); | ||
| 302 | if (gz->write) { | ||
| 303 | strm->next_in = Z_NULL; | ||
| 304 | strm->avail_in = 0; | ||
| 305 | do { | ||
| 306 | strm->next_out = out; | ||
| 307 | strm->avail_out = BUFLEN; | ||
| 308 | (void)deflate(strm, Z_FINISH); | ||
| 309 | fwrite(out, 1, BUFLEN - strm->avail_out, gz->file); | ||
| 310 | } while (strm->avail_out == 0); | ||
| 311 | deflateEnd(strm); | ||
| 312 | } | ||
| 313 | else | ||
| 314 | inflateEnd(strm); | ||
| 315 | fclose(gz->file); | ||
| 316 | free(gz); | ||
| 317 | return Z_OK; | ||
| 318 | } | ||
| 319 | |||
| 320 | const char *gzerror OF((gzFile, int *)); | ||
| 321 | |||
| 322 | const char *gzerror(gz, err) | ||
| 323 | gzFile gz; | ||
| 324 | int *err; | ||
| 325 | { | ||
| 326 | *err = gz->err; | ||
| 327 | return gz->msg; | ||
| 328 | } | ||
| 329 | |||
| 330 | #endif | ||
| 331 | |||
| 141 | char *prog; | 332 | char *prog; |
| 142 | 333 | ||
| 143 | void error OF((const char *msg)); | 334 | void error OF((const char *msg)); |
