Edit

kc3-lang/freetype/src/gzip/inflate.c

Branch :

  • Show log

    Commit

  • Author : David Turner
    Date : 2003-01-30 23:24:18
    Hash : 4bdf4350
    Message : various improvements for 2.1.4. see ChangeLog, I've got problems with copy & paste on my desktop !!

  • src/gzip/inflate.c
  • /* inflate.c -- zlib interface to inflate modules
     * Copyright (C) 1995-2002 Mark Adler
     * For conditions of distribution and use, see copyright notice in zlib.h
     */
    
    #include "zutil.h"
    #include "infblock.h"
    
    #define  DONE  INFLATE_DONE
    #define  BAD   INFLATE_BAD
    
    typedef enum {
          METHOD,   /* waiting for method byte */
          FLAG,     /* waiting for flag byte */
          DICT4,    /* four dictionary check bytes to go */
          DICT3,    /* three dictionary check bytes to go */
          DICT2,    /* two dictionary check bytes to go */
          DICT1,    /* one dictionary check byte to go */
          DICT0,    /* waiting for inflateSetDictionary */
          BLOCKS,   /* decompressing blocks */
          CHECK4,   /* four check bytes to go */
          CHECK3,   /* three check bytes to go */
          CHECK2,   /* two check bytes to go */
          CHECK1,   /* one check byte to go */
          DONE,     /* finished check, done */
          BAD}      /* got an error--stay here */
    inflate_mode;
    
    /* inflate private state */
    struct internal_state {
    
      /* mode */
      inflate_mode  mode;   /* current inflate mode */
    
      /* mode dependent information */
      union {
        uInt method;        /* if FLAGS, method byte */
        struct {
          uLong was;                /* computed check value */
          uLong need;               /* stream check value */
        } check;            /* if CHECK, check values to compare */
        uInt marker;        /* if BAD, inflateSync's marker bytes count */
      } sub;        /* submode */
    
      /* mode independent information */
      int  nowrap;          /* flag for no wrapper */
      uInt wbits;           /* log2(window size)  (8..15, defaults to 15) */
      inflate_blocks_statef
        *blocks;            /* current inflate_blocks state */
    
    };
    
    
    ZEXPORT(int) inflateReset( /* z) */
    z_streamp z )
    {
      if (z == Z_NULL || z->state == Z_NULL)
        return Z_STREAM_ERROR;
      z->total_in = z->total_out = 0;
      z->msg = Z_NULL;
      z->state->mode = z->state->nowrap ? BLOCKS : METHOD;
      inflate_blocks_reset(z->state->blocks, z, Z_NULL);
      Tracev((stderr, "inflate: reset\n"));
      return Z_OK;
    }
    
    
    ZEXPORT(int) inflateEnd( /* z) */
    z_streamp z )
    {
      if (z == Z_NULL || z->state == Z_NULL || z->zfree == Z_NULL)
        return Z_STREAM_ERROR;
      if (z->state->blocks != Z_NULL)
        inflate_blocks_free(z->state->blocks, z);
      ZFREE(z, z->state);
      z->state = Z_NULL;
      Tracev((stderr, "inflate: end\n"));
      return Z_OK;
    }
    
    
    ZEXPORT(int) inflateInit2_( /* z, w, version, stream_size) */
    z_streamp z,
    int w,
    const char *version,
    int stream_size )
    {
      if (version == Z_NULL || version[0] != ZLIB_VERSION[0] ||
          stream_size != sizeof(z_stream))
          return Z_VERSION_ERROR;
    
      /* initialize state */
      if (z == Z_NULL)
        return Z_STREAM_ERROR;
      z->msg = Z_NULL;
      if (z->zalloc == Z_NULL)
      {
        z->zalloc = zcalloc;
        z->opaque = (voidpf)0;
      }
      if (z->zfree == Z_NULL) z->zfree = zcfree;
      if ((z->state = (struct internal_state FAR *)
           ZALLOC(z,1,sizeof(struct internal_state))) == Z_NULL)
        return Z_MEM_ERROR;
      z->state->blocks = Z_NULL;
    
      /* handle undocumented nowrap option (no zlib header or check) */
      z->state->nowrap = 0;
      if (w < 0)
      {
        w = - w;
        z->state->nowrap = 1;
      }
    
      /* set window size */
      if (w < 8 || w > 15)
      {
        inflateEnd(z);
        return Z_STREAM_ERROR;
      }
      z->state->wbits = (uInt)w;
    
      /* create inflate_blocks state */
      if ((z->state->blocks =
          inflate_blocks_new(z, z->state->nowrap ? Z_NULL : adler32, (uInt)1 << w))
          == Z_NULL)
      {
        inflateEnd(z);
        return Z_MEM_ERROR;
      }
      Tracev((stderr, "inflate: allocated\n"));
    
      /* reset state */
      inflateReset(z);
      return Z_OK;
    }
    
    
    
    #undef  NEEDBYTE
    #define NEEDBYTE {if(z->avail_in==0)return r;r=f;}
    
    #undef  NEXTBYTE
    #define NEXTBYTE (z->avail_in--,z->total_in++,*z->next_in++)
    
    
    ZEXPORT(int) inflate( /* z, f) */
    z_streamp z,
    int f )
    {
      int r;
      uInt b;
    
      if (z == Z_NULL || z->state == Z_NULL || z->next_in == Z_NULL)
        return Z_STREAM_ERROR;
      f = f == Z_FINISH ? Z_BUF_ERROR : Z_OK;
      r = Z_BUF_ERROR;
      while (1) switch (z->state->mode)
      {
        case METHOD:
          NEEDBYTE
          if (((z->state->sub.method = NEXTBYTE) & 0xf) != Z_DEFLATED)
          {
            z->state->mode = BAD;
            z->msg = (char*)"unknown compression method";
            z->state->sub.marker = 5;       /* can't try inflateSync */
            break;
          }
          if ((z->state->sub.method >> 4) + 8 > z->state->wbits)
          {
            z->state->mode = BAD;
            z->msg = (char*)"invalid window size";
            z->state->sub.marker = 5;       /* can't try inflateSync */
            break;
          }
          z->state->mode = FLAG;
        case FLAG:
          NEEDBYTE
          b = NEXTBYTE;
          if (((z->state->sub.method << 8) + b) % 31)
          {
            z->state->mode = BAD;
            z->msg = (char*)"incorrect header check";
            z->state->sub.marker = 5;       /* can't try inflateSync */
            break;
          }
          Tracev((stderr, "inflate: zlib header ok\n"));
          if (!(b & PRESET_DICT))
          {
            z->state->mode = BLOCKS;
            break;
          }
          z->state->mode = DICT4;
        case DICT4:
          NEEDBYTE
          z->state->sub.check.need = (uLong)NEXTBYTE << 24;
          z->state->mode = DICT3;
        case DICT3:
          NEEDBYTE
          z->state->sub.check.need += (uLong)NEXTBYTE << 16;
          z->state->mode = DICT2;
        case DICT2:
          NEEDBYTE
          z->state->sub.check.need += (uLong)NEXTBYTE << 8;
          z->state->mode = DICT1;
        case DICT1:
          NEEDBYTE
          z->state->sub.check.need += (uLong)NEXTBYTE;
          z->adler = z->state->sub.check.need;
          z->state->mode = DICT0;
          return Z_NEED_DICT;
        case DICT0:
          z->state->mode = BAD;
          z->msg = (char*)"need dictionary";
          z->state->sub.marker = 0;       /* can try inflateSync */
          return Z_STREAM_ERROR;
        case BLOCKS:
          r = inflate_blocks(z->state->blocks, z, r);
          if (r == Z_DATA_ERROR)
          {
            z->state->mode = BAD;
            z->state->sub.marker = 0;       /* can try inflateSync */
            break;
          }
          if (r == Z_OK)
            r = f;
          if (r != Z_STREAM_END)
            return r;
          r = f;
          inflate_blocks_reset(z->state->blocks, z, &z->state->sub.check.was);
          if (z->state->nowrap)
          {
            z->state->mode = DONE;
            break;
          }
          z->state->mode = CHECK4;
        case CHECK4:
          NEEDBYTE
          z->state->sub.check.need = (uLong)NEXTBYTE << 24;
          z->state->mode = CHECK3;
        case CHECK3:
          NEEDBYTE
          z->state->sub.check.need += (uLong)NEXTBYTE << 16;
          z->state->mode = CHECK2;
        case CHECK2:
          NEEDBYTE
          z->state->sub.check.need += (uLong)NEXTBYTE << 8;
          z->state->mode = CHECK1;
        case CHECK1:
          NEEDBYTE
          z->state->sub.check.need += (uLong)NEXTBYTE;
    
          if (z->state->sub.check.was != z->state->sub.check.need)
          {
            z->state->mode = BAD;
            z->msg = (char*)"incorrect data check";
            z->state->sub.marker = 5;       /* can't try inflateSync */
            break;
          }
          Tracev((stderr, "inflate: zlib check ok\n"));
          z->state->mode = DONE;
        case DONE:
          return Z_STREAM_END;
        case BAD:
          return Z_DATA_ERROR;
        default:
          return Z_STREAM_ERROR;
      }
    #ifdef NEED_DUMMY_RETURN
      return Z_STREAM_ERROR;  /* Some dumb compilers complain without this */
    #endif
    }