modules/zlib/src/gzlib.c

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/modules/zlib/src/gzlib.c	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,634 @@
     1.4 +/* gzlib.c -- zlib functions common to reading and writing gzip files
     1.5 + * Copyright (C) 2004, 2010, 2011, 2012, 2013 Mark Adler
     1.6 + * For conditions of distribution and use, see copyright notice in zlib.h
     1.7 + */
     1.8 +
     1.9 +#include "gzguts.h"
    1.10 +
    1.11 +#if defined(_WIN32) && !defined(__BORLANDC__)
    1.12 +#  define LSEEK _lseeki64
    1.13 +#else
    1.14 +#if defined(_LARGEFILE64_SOURCE) && _LFS64_LARGEFILE-0
    1.15 +#  define LSEEK lseek64
    1.16 +#else
    1.17 +#  define LSEEK lseek
    1.18 +#endif
    1.19 +#endif
    1.20 +
    1.21 +/* Local functions */
    1.22 +local void gz_reset OF((gz_statep));
    1.23 +local gzFile gz_open OF((const void *, int, const char *));
    1.24 +
    1.25 +#if defined UNDER_CE
    1.26 +
    1.27 +/* Map the Windows error number in ERROR to a locale-dependent error message
    1.28 +   string and return a pointer to it.  Typically, the values for ERROR come
    1.29 +   from GetLastError.
    1.30 +
    1.31 +   The string pointed to shall not be modified by the application, but may be
    1.32 +   overwritten by a subsequent call to gz_strwinerror
    1.33 +
    1.34 +   The gz_strwinerror function does not change the current setting of
    1.35 +   GetLastError. */
    1.36 +char ZLIB_INTERNAL *gz_strwinerror (error)
    1.37 +     DWORD error;
    1.38 +{
    1.39 +    static char buf[1024];
    1.40 +
    1.41 +    wchar_t *msgbuf;
    1.42 +    DWORD lasterr = GetLastError();
    1.43 +    DWORD chars = FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM
    1.44 +        | FORMAT_MESSAGE_ALLOCATE_BUFFER,
    1.45 +        NULL,
    1.46 +        error,
    1.47 +        0, /* Default language */
    1.48 +        (LPVOID)&msgbuf,
    1.49 +        0,
    1.50 +        NULL);
    1.51 +    if (chars != 0) {
    1.52 +        /* If there is an \r\n appended, zap it.  */
    1.53 +        if (chars >= 2
    1.54 +            && msgbuf[chars - 2] == '\r' && msgbuf[chars - 1] == '\n') {
    1.55 +            chars -= 2;
    1.56 +            msgbuf[chars] = 0;
    1.57 +        }
    1.58 +
    1.59 +        if (chars > sizeof (buf) - 1) {
    1.60 +            chars = sizeof (buf) - 1;
    1.61 +            msgbuf[chars] = 0;
    1.62 +        }
    1.63 +
    1.64 +        wcstombs(buf, msgbuf, chars + 1);
    1.65 +        LocalFree(msgbuf);
    1.66 +    }
    1.67 +    else {
    1.68 +        sprintf(buf, "unknown win32 error (%ld)", error);
    1.69 +    }
    1.70 +
    1.71 +    SetLastError(lasterr);
    1.72 +    return buf;
    1.73 +}
    1.74 +
    1.75 +#endif /* UNDER_CE */
    1.76 +
    1.77 +/* Reset gzip file state */
    1.78 +local void gz_reset(state)
    1.79 +    gz_statep state;
    1.80 +{
    1.81 +    state->x.have = 0;              /* no output data available */
    1.82 +    if (state->mode == GZ_READ) {   /* for reading ... */
    1.83 +        state->eof = 0;             /* not at end of file */
    1.84 +        state->past = 0;            /* have not read past end yet */
    1.85 +        state->how = LOOK;          /* look for gzip header */
    1.86 +    }
    1.87 +    state->seek = 0;                /* no seek request pending */
    1.88 +    gz_error(state, Z_OK, NULL);    /* clear error */
    1.89 +    state->x.pos = 0;               /* no uncompressed data yet */
    1.90 +    state->strm.avail_in = 0;       /* no input data yet */
    1.91 +}
    1.92 +
    1.93 +/* Open a gzip file either by name or file descriptor. */
    1.94 +local gzFile gz_open(path, fd, mode)
    1.95 +    const void *path;
    1.96 +    int fd;
    1.97 +    const char *mode;
    1.98 +{
    1.99 +    gz_statep state;
   1.100 +    size_t len;
   1.101 +    int oflag;
   1.102 +#ifdef O_CLOEXEC
   1.103 +    int cloexec = 0;
   1.104 +#endif
   1.105 +#ifdef O_EXCL
   1.106 +    int exclusive = 0;
   1.107 +#endif
   1.108 +
   1.109 +    /* check input */
   1.110 +    if (path == NULL)
   1.111 +        return NULL;
   1.112 +
   1.113 +    /* allocate gzFile structure to return */
   1.114 +    state = (gz_statep)malloc(sizeof(gz_state));
   1.115 +    if (state == NULL)
   1.116 +        return NULL;
   1.117 +    state->size = 0;            /* no buffers allocated yet */
   1.118 +    state->want = GZBUFSIZE;    /* requested buffer size */
   1.119 +    state->msg = NULL;          /* no error message yet */
   1.120 +
   1.121 +    /* interpret mode */
   1.122 +    state->mode = GZ_NONE;
   1.123 +    state->level = Z_DEFAULT_COMPRESSION;
   1.124 +    state->strategy = Z_DEFAULT_STRATEGY;
   1.125 +    state->direct = 0;
   1.126 +    while (*mode) {
   1.127 +        if (*mode >= '0' && *mode <= '9')
   1.128 +            state->level = *mode - '0';
   1.129 +        else
   1.130 +            switch (*mode) {
   1.131 +            case 'r':
   1.132 +                state->mode = GZ_READ;
   1.133 +                break;
   1.134 +#ifndef NO_GZCOMPRESS
   1.135 +            case 'w':
   1.136 +                state->mode = GZ_WRITE;
   1.137 +                break;
   1.138 +            case 'a':
   1.139 +                state->mode = GZ_APPEND;
   1.140 +                break;
   1.141 +#endif
   1.142 +            case '+':       /* can't read and write at the same time */
   1.143 +                free(state);
   1.144 +                return NULL;
   1.145 +            case 'b':       /* ignore -- will request binary anyway */
   1.146 +                break;
   1.147 +#ifdef O_CLOEXEC
   1.148 +            case 'e':
   1.149 +                cloexec = 1;
   1.150 +                break;
   1.151 +#endif
   1.152 +#ifdef O_EXCL
   1.153 +            case 'x':
   1.154 +                exclusive = 1;
   1.155 +                break;
   1.156 +#endif
   1.157 +            case 'f':
   1.158 +                state->strategy = Z_FILTERED;
   1.159 +                break;
   1.160 +            case 'h':
   1.161 +                state->strategy = Z_HUFFMAN_ONLY;
   1.162 +                break;
   1.163 +            case 'R':
   1.164 +                state->strategy = Z_RLE;
   1.165 +                break;
   1.166 +            case 'F':
   1.167 +                state->strategy = Z_FIXED;
   1.168 +                break;
   1.169 +            case 'T':
   1.170 +                state->direct = 1;
   1.171 +                break;
   1.172 +            default:        /* could consider as an error, but just ignore */
   1.173 +                ;
   1.174 +            }
   1.175 +        mode++;
   1.176 +    }
   1.177 +
   1.178 +    /* must provide an "r", "w", or "a" */
   1.179 +    if (state->mode == GZ_NONE) {
   1.180 +        free(state);
   1.181 +        return NULL;
   1.182 +    }
   1.183 +
   1.184 +    /* can't force transparent read */
   1.185 +    if (state->mode == GZ_READ) {
   1.186 +        if (state->direct) {
   1.187 +            free(state);
   1.188 +            return NULL;
   1.189 +        }
   1.190 +        state->direct = 1;      /* for empty file */
   1.191 +    }
   1.192 +
   1.193 +    /* save the path name for error messages */
   1.194 +#ifdef _WIN32
   1.195 +    if (fd == -2) {
   1.196 +        len = wcstombs(NULL, path, 0);
   1.197 +        if (len == (size_t)-1)
   1.198 +            len = 0;
   1.199 +    }
   1.200 +    else
   1.201 +#endif
   1.202 +        len = strlen((const char *)path);
   1.203 +    state->path = (char *)malloc(len + 1);
   1.204 +    if (state->path == NULL) {
   1.205 +        free(state);
   1.206 +        return NULL;
   1.207 +    }
   1.208 +#ifdef _WIN32
   1.209 +    if (fd == -2)
   1.210 +        if (len)
   1.211 +            wcstombs(state->path, path, len + 1);
   1.212 +        else
   1.213 +            *(state->path) = 0;
   1.214 +    else
   1.215 +#endif
   1.216 +#if !defined(NO_snprintf) && !defined(NO_vsnprintf)
   1.217 +        snprintf(state->path, len + 1, "%s", (const char *)path);
   1.218 +#else
   1.219 +        strcpy(state->path, path);
   1.220 +#endif
   1.221 +
   1.222 +    /* compute the flags for open() */
   1.223 +    oflag =
   1.224 +#ifdef O_LARGEFILE
   1.225 +        O_LARGEFILE |
   1.226 +#endif
   1.227 +#ifdef O_BINARY
   1.228 +        O_BINARY |
   1.229 +#endif
   1.230 +#ifdef O_CLOEXEC
   1.231 +        (cloexec ? O_CLOEXEC : 0) |
   1.232 +#endif
   1.233 +        (state->mode == GZ_READ ?
   1.234 +         O_RDONLY :
   1.235 +         (O_WRONLY | O_CREAT |
   1.236 +#ifdef O_EXCL
   1.237 +          (exclusive ? O_EXCL : 0) |
   1.238 +#endif
   1.239 +          (state->mode == GZ_WRITE ?
   1.240 +           O_TRUNC :
   1.241 +           O_APPEND)));
   1.242 +
   1.243 +    /* open the file with the appropriate flags (or just use fd) */
   1.244 +    state->fd = fd > -1 ? fd : (
   1.245 +#ifdef _WIN32
   1.246 +        fd == -2 ? _wopen(path, oflag, 0666) :
   1.247 +#endif
   1.248 +        open((const char *)path, oflag, 0666));
   1.249 +    if (state->fd == -1) {
   1.250 +        free(state->path);
   1.251 +        free(state);
   1.252 +        return NULL;
   1.253 +    }
   1.254 +    if (state->mode == GZ_APPEND)
   1.255 +        state->mode = GZ_WRITE;         /* simplify later checks */
   1.256 +
   1.257 +    /* save the current position for rewinding (only if reading) */
   1.258 +    if (state->mode == GZ_READ) {
   1.259 +        state->start = LSEEK(state->fd, 0, SEEK_CUR);
   1.260 +        if (state->start == -1) state->start = 0;
   1.261 +    }
   1.262 +
   1.263 +    /* initialize stream */
   1.264 +    gz_reset(state);
   1.265 +
   1.266 +    /* return stream */
   1.267 +    return (gzFile)state;
   1.268 +}
   1.269 +
   1.270 +/* -- see zlib.h -- */
   1.271 +gzFile ZEXPORT gzopen(path, mode)
   1.272 +    const char *path;
   1.273 +    const char *mode;
   1.274 +{
   1.275 +    return gz_open(path, -1, mode);
   1.276 +}
   1.277 +
   1.278 +/* -- see zlib.h -- */
   1.279 +gzFile ZEXPORT gzopen64(path, mode)
   1.280 +    const char *path;
   1.281 +    const char *mode;
   1.282 +{
   1.283 +    return gz_open(path, -1, mode);
   1.284 +}
   1.285 +
   1.286 +/* -- see zlib.h -- */
   1.287 +gzFile ZEXPORT gzdopen(fd, mode)
   1.288 +    int fd;
   1.289 +    const char *mode;
   1.290 +{
   1.291 +    char *path;         /* identifier for error messages */
   1.292 +    gzFile gz;
   1.293 +
   1.294 +    if (fd == -1 || (path = (char *)malloc(7 + 3 * sizeof(int))) == NULL)
   1.295 +        return NULL;
   1.296 +#if !defined(NO_snprintf) && !defined(NO_vsnprintf)
   1.297 +    snprintf(path, 7 + 3 * sizeof(int), "<fd:%d>", fd); /* for debugging */
   1.298 +#else
   1.299 +    sprintf(path, "<fd:%d>", fd);   /* for debugging */
   1.300 +#endif
   1.301 +    gz = gz_open(path, fd, mode);
   1.302 +    free(path);
   1.303 +    return gz;
   1.304 +}
   1.305 +
   1.306 +/* -- see zlib.h -- */
   1.307 +#ifdef _WIN32
   1.308 +gzFile ZEXPORT gzopen_w(path, mode)
   1.309 +    const wchar_t *path;
   1.310 +    const char *mode;
   1.311 +{
   1.312 +    return gz_open(path, -2, mode);
   1.313 +}
   1.314 +#endif
   1.315 +
   1.316 +/* -- see zlib.h -- */
   1.317 +int ZEXPORT gzbuffer(file, size)
   1.318 +    gzFile file;
   1.319 +    unsigned size;
   1.320 +{
   1.321 +    gz_statep state;
   1.322 +
   1.323 +    /* get internal structure and check integrity */
   1.324 +    if (file == NULL)
   1.325 +        return -1;
   1.326 +    state = (gz_statep)file;
   1.327 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.328 +        return -1;
   1.329 +
   1.330 +    /* make sure we haven't already allocated memory */
   1.331 +    if (state->size != 0)
   1.332 +        return -1;
   1.333 +
   1.334 +    /* check and set requested size */
   1.335 +    if (size < 2)
   1.336 +        size = 2;               /* need two bytes to check magic header */
   1.337 +    state->want = size;
   1.338 +    return 0;
   1.339 +}
   1.340 +
   1.341 +/* -- see zlib.h -- */
   1.342 +int ZEXPORT gzrewind(file)
   1.343 +    gzFile file;
   1.344 +{
   1.345 +    gz_statep state;
   1.346 +
   1.347 +    /* get internal structure */
   1.348 +    if (file == NULL)
   1.349 +        return -1;
   1.350 +    state = (gz_statep)file;
   1.351 +
   1.352 +    /* check that we're reading and that there's no error */
   1.353 +    if (state->mode != GZ_READ ||
   1.354 +            (state->err != Z_OK && state->err != Z_BUF_ERROR))
   1.355 +        return -1;
   1.356 +
   1.357 +    /* back up and start over */
   1.358 +    if (LSEEK(state->fd, state->start, SEEK_SET) == -1)
   1.359 +        return -1;
   1.360 +    gz_reset(state);
   1.361 +    return 0;
   1.362 +}
   1.363 +
   1.364 +/* -- see zlib.h -- */
   1.365 +z_off64_t ZEXPORT gzseek64(file, offset, whence)
   1.366 +    gzFile file;
   1.367 +    z_off64_t offset;
   1.368 +    int whence;
   1.369 +{
   1.370 +    unsigned n;
   1.371 +    z_off64_t ret;
   1.372 +    gz_statep state;
   1.373 +
   1.374 +    /* get internal structure and check integrity */
   1.375 +    if (file == NULL)
   1.376 +        return -1;
   1.377 +    state = (gz_statep)file;
   1.378 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.379 +        return -1;
   1.380 +
   1.381 +    /* check that there's no error */
   1.382 +    if (state->err != Z_OK && state->err != Z_BUF_ERROR)
   1.383 +        return -1;
   1.384 +
   1.385 +    /* can only seek from start or relative to current position */
   1.386 +    if (whence != SEEK_SET && whence != SEEK_CUR)
   1.387 +        return -1;
   1.388 +
   1.389 +    /* normalize offset to a SEEK_CUR specification */
   1.390 +    if (whence == SEEK_SET)
   1.391 +        offset -= state->x.pos;
   1.392 +    else if (state->seek)
   1.393 +        offset += state->skip;
   1.394 +    state->seek = 0;
   1.395 +
   1.396 +    /* if within raw area while reading, just go there */
   1.397 +    if (state->mode == GZ_READ && state->how == COPY &&
   1.398 +            state->x.pos + offset >= 0) {
   1.399 +        ret = LSEEK(state->fd, offset - state->x.have, SEEK_CUR);
   1.400 +        if (ret == -1)
   1.401 +            return -1;
   1.402 +        state->x.have = 0;
   1.403 +        state->eof = 0;
   1.404 +        state->past = 0;
   1.405 +        state->seek = 0;
   1.406 +        gz_error(state, Z_OK, NULL);
   1.407 +        state->strm.avail_in = 0;
   1.408 +        state->x.pos += offset;
   1.409 +        return state->x.pos;
   1.410 +    }
   1.411 +
   1.412 +    /* calculate skip amount, rewinding if needed for back seek when reading */
   1.413 +    if (offset < 0) {
   1.414 +        if (state->mode != GZ_READ)         /* writing -- can't go backwards */
   1.415 +            return -1;
   1.416 +        offset += state->x.pos;
   1.417 +        if (offset < 0)                     /* before start of file! */
   1.418 +            return -1;
   1.419 +        if (gzrewind(file) == -1)           /* rewind, then skip to offset */
   1.420 +            return -1;
   1.421 +    }
   1.422 +
   1.423 +    /* if reading, skip what's in output buffer (one less gzgetc() check) */
   1.424 +    if (state->mode == GZ_READ) {
   1.425 +        n = GT_OFF(state->x.have) || (z_off64_t)state->x.have > offset ?
   1.426 +            (unsigned)offset : state->x.have;
   1.427 +        state->x.have -= n;
   1.428 +        state->x.next += n;
   1.429 +        state->x.pos += n;
   1.430 +        offset -= n;
   1.431 +    }
   1.432 +
   1.433 +    /* request skip (if not zero) */
   1.434 +    if (offset) {
   1.435 +        state->seek = 1;
   1.436 +        state->skip = offset;
   1.437 +    }
   1.438 +    return state->x.pos + offset;
   1.439 +}
   1.440 +
   1.441 +/* -- see zlib.h -- */
   1.442 +z_off_t ZEXPORT gzseek(file, offset, whence)
   1.443 +    gzFile file;
   1.444 +    z_off_t offset;
   1.445 +    int whence;
   1.446 +{
   1.447 +    z_off64_t ret;
   1.448 +
   1.449 +    ret = gzseek64(file, (z_off64_t)offset, whence);
   1.450 +    return ret == (z_off_t)ret ? (z_off_t)ret : -1;
   1.451 +}
   1.452 +
   1.453 +/* -- see zlib.h -- */
   1.454 +z_off64_t ZEXPORT gztell64(file)
   1.455 +    gzFile file;
   1.456 +{
   1.457 +    gz_statep state;
   1.458 +
   1.459 +    /* get internal structure and check integrity */
   1.460 +    if (file == NULL)
   1.461 +        return -1;
   1.462 +    state = (gz_statep)file;
   1.463 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.464 +        return -1;
   1.465 +
   1.466 +    /* return position */
   1.467 +    return state->x.pos + (state->seek ? state->skip : 0);
   1.468 +}
   1.469 +
   1.470 +/* -- see zlib.h -- */
   1.471 +z_off_t ZEXPORT gztell(file)
   1.472 +    gzFile file;
   1.473 +{
   1.474 +    z_off64_t ret;
   1.475 +
   1.476 +    ret = gztell64(file);
   1.477 +    return ret == (z_off_t)ret ? (z_off_t)ret : -1;
   1.478 +}
   1.479 +
   1.480 +/* -- see zlib.h -- */
   1.481 +z_off64_t ZEXPORT gzoffset64(file)
   1.482 +    gzFile file;
   1.483 +{
   1.484 +    z_off64_t offset;
   1.485 +    gz_statep state;
   1.486 +
   1.487 +    /* get internal structure and check integrity */
   1.488 +    if (file == NULL)
   1.489 +        return -1;
   1.490 +    state = (gz_statep)file;
   1.491 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.492 +        return -1;
   1.493 +
   1.494 +    /* compute and return effective offset in file */
   1.495 +    offset = LSEEK(state->fd, 0, SEEK_CUR);
   1.496 +    if (offset == -1)
   1.497 +        return -1;
   1.498 +    if (state->mode == GZ_READ)             /* reading */
   1.499 +        offset -= state->strm.avail_in;     /* don't count buffered input */
   1.500 +    return offset;
   1.501 +}
   1.502 +
   1.503 +/* -- see zlib.h -- */
   1.504 +z_off_t ZEXPORT gzoffset(file)
   1.505 +    gzFile file;
   1.506 +{
   1.507 +    z_off64_t ret;
   1.508 +
   1.509 +    ret = gzoffset64(file);
   1.510 +    return ret == (z_off_t)ret ? (z_off_t)ret : -1;
   1.511 +}
   1.512 +
   1.513 +/* -- see zlib.h -- */
   1.514 +int ZEXPORT gzeof(file)
   1.515 +    gzFile file;
   1.516 +{
   1.517 +    gz_statep state;
   1.518 +
   1.519 +    /* get internal structure and check integrity */
   1.520 +    if (file == NULL)
   1.521 +        return 0;
   1.522 +    state = (gz_statep)file;
   1.523 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.524 +        return 0;
   1.525 +
   1.526 +    /* return end-of-file state */
   1.527 +    return state->mode == GZ_READ ? state->past : 0;
   1.528 +}
   1.529 +
   1.530 +/* -- see zlib.h -- */
   1.531 +const char * ZEXPORT gzerror(file, errnum)
   1.532 +    gzFile file;
   1.533 +    int *errnum;
   1.534 +{
   1.535 +    gz_statep state;
   1.536 +
   1.537 +    /* get internal structure and check integrity */
   1.538 +    if (file == NULL)
   1.539 +        return NULL;
   1.540 +    state = (gz_statep)file;
   1.541 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.542 +        return NULL;
   1.543 +
   1.544 +    /* return error information */
   1.545 +    if (errnum != NULL)
   1.546 +        *errnum = state->err;
   1.547 +    return state->err == Z_MEM_ERROR ? "out of memory" :
   1.548 +                                       (state->msg == NULL ? "" : state->msg);
   1.549 +}
   1.550 +
   1.551 +/* -- see zlib.h -- */
   1.552 +void ZEXPORT gzclearerr(file)
   1.553 +    gzFile file;
   1.554 +{
   1.555 +    gz_statep state;
   1.556 +
   1.557 +    /* get internal structure and check integrity */
   1.558 +    if (file == NULL)
   1.559 +        return;
   1.560 +    state = (gz_statep)file;
   1.561 +    if (state->mode != GZ_READ && state->mode != GZ_WRITE)
   1.562 +        return;
   1.563 +
   1.564 +    /* clear error and end-of-file */
   1.565 +    if (state->mode == GZ_READ) {
   1.566 +        state->eof = 0;
   1.567 +        state->past = 0;
   1.568 +    }
   1.569 +    gz_error(state, Z_OK, NULL);
   1.570 +}
   1.571 +
   1.572 +/* Create an error message in allocated memory and set state->err and
   1.573 +   state->msg accordingly.  Free any previous error message already there.  Do
   1.574 +   not try to free or allocate space if the error is Z_MEM_ERROR (out of
   1.575 +   memory).  Simply save the error message as a static string.  If there is an
   1.576 +   allocation failure constructing the error message, then convert the error to
   1.577 +   out of memory. */
   1.578 +void ZLIB_INTERNAL gz_error(state, err, msg)
   1.579 +    gz_statep state;
   1.580 +    int err;
   1.581 +    const char *msg;
   1.582 +{
   1.583 +    /* free previously allocated message and clear */
   1.584 +    if (state->msg != NULL) {
   1.585 +        if (state->err != Z_MEM_ERROR)
   1.586 +            free(state->msg);
   1.587 +        state->msg = NULL;
   1.588 +    }
   1.589 +
   1.590 +    /* if fatal, set state->x.have to 0 so that the gzgetc() macro fails */
   1.591 +    if (err != Z_OK && err != Z_BUF_ERROR)
   1.592 +        state->x.have = 0;
   1.593 +
   1.594 +    /* set error code, and if no message, then done */
   1.595 +    state->err = err;
   1.596 +    if (msg == NULL)
   1.597 +        return;
   1.598 +
   1.599 +    /* for an out of memory error, return literal string when requested */
   1.600 +    if (err == Z_MEM_ERROR)
   1.601 +        return;
   1.602 +
   1.603 +    /* construct error message with path */
   1.604 +    if ((state->msg = (char *)malloc(strlen(state->path) + strlen(msg) + 3)) ==
   1.605 +            NULL) {
   1.606 +        state->err = Z_MEM_ERROR;
   1.607 +        return;
   1.608 +    }
   1.609 +#if !defined(NO_snprintf) && !defined(NO_vsnprintf)
   1.610 +    snprintf(state->msg, strlen(state->path) + strlen(msg) + 3,
   1.611 +             "%s%s%s", state->path, ": ", msg);
   1.612 +#else
   1.613 +    strcpy(state->msg, state->path);
   1.614 +    strcat(state->msg, ": ");
   1.615 +    strcat(state->msg, msg);
   1.616 +#endif
   1.617 +    return;
   1.618 +}
   1.619 +
   1.620 +#ifndef INT_MAX
   1.621 +/* portably return maximum value for an int (when limits.h presumed not
   1.622 +   available) -- we need to do this to cover cases where 2's complement not
   1.623 +   used, since C standard permits 1's complement and sign-bit representations,
   1.624 +   otherwise we could just use ((unsigned)-1) >> 1 */
   1.625 +unsigned ZLIB_INTERNAL gz_intmax()
   1.626 +{
   1.627 +    unsigned p, q;
   1.628 +
   1.629 +    p = 1;
   1.630 +    do {
   1.631 +        q = p;
   1.632 +        p <<= 1;
   1.633 +        p++;
   1.634 +    } while (p > q);
   1.635 +    return q >> 1;
   1.636 +}
   1.637 +#endif

mercurial