⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 inflate.c

📁 Lib files of linux kernel
💻 C
📖 第 1 页 / 共 3 页
字号:
                DROPBITS(state->extra);            }            state->mode = DIST;        case DIST:            for (;;) {                this = state->distcode[BITS(state->distbits)];                if ((unsigned)(this.bits) <= bits) break;                PULLBYTE();            }            if ((this.op & 0xf0) == 0) {                last = this;                for (;;) {                    this = state->distcode[last.val +                            (BITS(last.bits + last.op) >> last.bits)];                    if ((unsigned)(last.bits + this.bits) <= bits) break;                    PULLBYTE();                }                DROPBITS(last.bits);            }            DROPBITS(this.bits);            if (this.op & 64) {                strm->msg = (char *)"invalid distance code";                state->mode = BAD;                break;            }            state->offset = (unsigned)this.val;            state->extra = (unsigned)(this.op) & 15;            state->mode = DISTEXT;        case DISTEXT:            if (state->extra) {                NEEDBITS(state->extra);                state->offset += BITS(state->extra);                DROPBITS(state->extra);            }#ifdef INFLATE_STRICT            if (state->offset > state->dmax) {                strm->msg = (char *)"invalid distance too far back";                state->mode = BAD;                break;            }#endif            if (state->offset > state->whave + out - left) {                strm->msg = (char *)"invalid distance too far back";                state->mode = BAD;                break;            }            state->mode = MATCH;        case MATCH:            if (left == 0) goto inf_leave;            copy = out - left;            if (state->offset > copy) {         /* copy from window */                copy = state->offset - copy;                if (copy > state->write) {                    copy -= state->write;                    from = state->window + (state->wsize - copy);                }                else                    from = state->window + (state->write - copy);                if (copy > state->length) copy = state->length;            }            else {                              /* copy from output */                from = put - state->offset;                copy = state->length;            }            if (copy > left) copy = left;            left -= copy;            state->length -= copy;            do {                *put++ = *from++;            } while (--copy);            if (state->length == 0) state->mode = LEN;            break;        case LIT:            if (left == 0) goto inf_leave;            *put++ = (unsigned char)(state->length);            left--;            state->mode = LEN;            break;        case CHECK:            if (state->wrap) {                NEEDBITS(32);                out -= left;                strm->total_out += out;                state->total += out;                if (out)                    strm->adler = state->check =                        UPDATE(state->check, put - out, out);                out = left;                if ((                     REVERSE(hold)) != state->check) {                    strm->msg = (char *)"incorrect data check";                    state->mode = BAD;                    break;                }                INITBITS();            }            state->mode = DONE;        case DONE:            ret = Z_STREAM_END;            goto inf_leave;        case BAD:            ret = Z_DATA_ERROR;            goto inf_leave;        case MEM:            return Z_MEM_ERROR;        case SYNC:        default:            return Z_STREAM_ERROR;        }    /*       Return from inflate(), updating the total counts and the check value.       If there was no progress during the inflate() call, return a buffer       error.  Call zlib_updatewindow() to create and/or update the window state.     */  inf_leave:    RESTORE();    if (state->wsize || (state->mode < CHECK && out != strm->avail_out))        zlib_updatewindow(strm, out);    in -= strm->avail_in;    out -= strm->avail_out;    strm->total_in += in;    strm->total_out += out;    state->total += out;    if (state->wrap && out)        strm->adler = state->check =            UPDATE(state->check, strm->next_out - out, out);    strm->data_type = state->bits + (state->last ? 64 : 0) +                      (state->mode == TYPE ? 128 : 0);    if (flush == Z_PACKET_FLUSH && ret == Z_OK &&            strm->avail_out != 0 && strm->avail_in == 0)		return zlib_inflateSyncPacket(strm);    if (((in == 0 && out == 0) || flush == Z_FINISH) && ret == Z_OK)        ret = Z_BUF_ERROR;    return ret;}int zlib_inflateEnd(z_streamp strm){    if (strm == NULL || strm->state == NULL)        return Z_STREAM_ERROR;    return Z_OK;}#if 0int zlib_inflateSetDictionary(z_streamp strm, const Byte *dictionary,        uInt dictLength){    struct inflate_state *state;    unsigned long id;    /* check state */    if (strm == NULL || strm->state == NULL) return Z_STREAM_ERROR;    state = (struct inflate_state *)strm->state;    if (state->wrap != 0 && state->mode != DICT)        return Z_STREAM_ERROR;    /* check for correct dictionary id */    if (state->mode == DICT) {        id = zlib_adler32(0L, NULL, 0);        id = zlib_adler32(id, dictionary, dictLength);        if (id != state->check)            return Z_DATA_ERROR;    }    /* copy dictionary to window */    zlib_updatewindow(strm, strm->avail_out);    if (dictLength > state->wsize) {        memcpy(state->window, dictionary + dictLength - state->wsize,                state->wsize);        state->whave = state->wsize;    }    else {        memcpy(state->window + state->wsize - dictLength, dictionary,                dictLength);        state->whave = dictLength;    }    state->havedict = 1;    return Z_OK;}#endif#if 0/*   Search buf[0..len-1] for the pattern: 0, 0, 0xff, 0xff.  Return when found   or when out of input.  When called, *have is the number of pattern bytes   found in order so far, in 0..3.  On return *have is updated to the new   state.  If on return *have equals four, then the pattern was found and the   return value is how many bytes were read including the last byte of the   pattern.  If *have is less than four, then the pattern has not been found   yet and the return value is len.  In the latter case, zlib_syncsearch() can be   called again with more data and the *have state.  *have is initialized to   zero for the first call. */static unsigned zlib_syncsearch(unsigned *have, unsigned char *buf,        unsigned len){    unsigned got;    unsigned next;    got = *have;    next = 0;    while (next < len && got < 4) {        if ((int)(buf[next]) == (got < 2 ? 0 : 0xff))            got++;        else if (buf[next])            got = 0;        else            got = 4 - got;        next++;    }    *have = got;    return next;}#endif#if 0int zlib_inflateSync(z_streamp strm){    unsigned len;               /* number of bytes to look at or looked at */    unsigned long in, out;      /* temporary to save total_in and total_out */    unsigned char buf[4];       /* to restore bit buffer to byte string */    struct inflate_state *state;    /* check parameters */    if (strm == NULL || strm->state == NULL) return Z_STREAM_ERROR;    state = (struct inflate_state *)strm->state;    if (strm->avail_in == 0 && state->bits < 8) return Z_BUF_ERROR;    /* if first time, start search in bit buffer */    if (state->mode != SYNC) {        state->mode = SYNC;        state->hold <<= state->bits & 7;        state->bits -= state->bits & 7;        len = 0;        while (state->bits >= 8) {            buf[len++] = (unsigned char)(state->hold);            state->hold >>= 8;            state->bits -= 8;        }        state->have = 0;        zlib_syncsearch(&(state->have), buf, len);    }    /* search available input */    len = zlib_syncsearch(&(state->have), strm->next_in, strm->avail_in);    strm->avail_in -= len;    strm->next_in += len;    strm->total_in += len;    /* return no joy or set up to restart inflate() on a new block */    if (state->have != 4) return Z_DATA_ERROR;    in = strm->total_in;  out = strm->total_out;    zlib_inflateReset(strm);    strm->total_in = in;  strm->total_out = out;    state->mode = TYPE;    return Z_OK;}#endif/* * This subroutine adds the data at next_in/avail_in to the output history * without performing any output.  The output buffer must be "caught up"; * i.e. no pending output but this should always be the case. The state must * be waiting on the start of a block (i.e. mode == TYPE or HEAD).  On exit, * the output will also be caught up, and the checksum will have been updated * if need be. */int zlib_inflateIncomp(z_stream *z){    struct inflate_state *state = (struct inflate_state *)z->state;    Byte *saved_no = z->next_out;    uInt saved_ao = z->avail_out;    if (state->mode != TYPE && state->mode != HEAD)	return Z_DATA_ERROR;    /* Setup some variables to allow misuse of updateWindow */    z->avail_out = 0;    z->next_out = (unsigned char*)z->next_in + z->avail_in;    zlib_updatewindow(z, z->avail_in);    /* Restore saved variables */    z->avail_out = saved_ao;    z->next_out = saved_no;    z->adler = state->check =        UPDATE(state->check, z->next_in, z->avail_in);    z->total_out += z->avail_in;    z->total_in += z->avail_in;    z->next_in += z->avail_in;    state->total += z->avail_in;    z->avail_in = 0;    return Z_OK;}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -