ChunkedInflaterInputStream.java 3.88 KB
/*
 * Decompiled with CFR 0_118.
 */
package com.day.io;

import java.io.EOFException;
import java.io.FilterInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.zip.DataFormatException;
import java.util.zip.Inflater;
import java.util.zip.ZipException;

public class ChunkedInflaterInputStream
extends FilterInputStream {
    protected Inflater inf;
    protected byte[] buf;
    protected int len;
    private boolean closed = false;
    private boolean reachEOF = false;
    boolean usesDefaultInflater = false;
    private byte[] singleByteBuf = new byte[1];
    private byte[] b = new byte[512];

    private void ensureOpen() throws IOException {
        if (this.closed) {
            throw new IOException("Stream closed");
        }
    }

    public ChunkedInflaterInputStream(InputStream in, Inflater inf, int size) {
        super(in);
        if (in == null || inf == null) {
            throw new NullPointerException();
        }
        if (size <= 0) {
            throw new IllegalArgumentException("buffer size <= 0");
        }
        this.inf = inf;
        this.buf = new byte[size];
    }

    public ChunkedInflaterInputStream(InputStream in, Inflater inf) {
        this(in, inf, 8192);
    }

    public ChunkedInflaterInputStream(InputStream in) {
        this(in, new Inflater());
        this.usesDefaultInflater = true;
    }

    public int read() throws IOException {
        this.ensureOpen();
        return this.read(this.singleByteBuf, 0, 1) == -1 ? -1 : this.singleByteBuf[0] & 255;
    }

    public int read(byte[] b, int off, int len) throws IOException {
        this.ensureOpen();
        if ((off | len | off + len | b.length - (off + len)) < 0) {
            throw new IndexOutOfBoundsException();
        }
        if (len == 0) {
            return 0;
        }
        try {
            int n;
            while ((n = this.inf.inflate(b, off, len)) == 0) {
                if (this.inf.finished() || this.inf.needsDictionary()) {
                    int r = this.inf.getRemaining();
                    if (r == 0 && this.in.available() <= 0) {
                        this.reachEOF = true;
                        return -1;
                    }
                    this.inf.reset();
                    this.inf.setInput(this.buf, this.len - r, r);
                }
                if (!this.inf.needsInput()) continue;
                this.fill();
            }
            return n;
        }
        catch (DataFormatException e) {
            String s = e.getMessage();
            throw new ZipException(s != null ? s : "Invalid ZLIB data format");
        }
    }

    public int available() throws IOException {
        this.ensureOpen();
        if (this.reachEOF) {
            return 0;
        }
        return 1;
    }

    public long skip(long n) throws IOException {
        int len;
        int total;
        if (n < 0) {
            throw new IllegalArgumentException("negative skip length");
        }
        this.ensureOpen();
        int max = (int)Math.min(n, Integer.MAX_VALUE);
        for (total = 0; total < max; total += len) {
            len = max - total;
            if (len > this.b.length) {
                len = this.b.length;
            }
            if ((len = this.read(this.b, 0, len)) != -1) continue;
            this.reachEOF = true;
            break;
        }
        return total;
    }

    public void close() throws IOException {
        if (!this.closed) {
            if (this.usesDefaultInflater) {
                this.inf.end();
            }
            this.in.close();
            this.closed = true;
        }
    }

    protected void fill() throws IOException {
        this.ensureOpen();
        this.len = this.in.read(this.buf, 0, this.buf.length);
        if (this.len == -1) {
            throw new EOFException("Unexpected end of ZLIB input stream");
        }
        this.inf.setInput(this.buf, 0, this.len);
    }
}