Mercurial > 510Connectbot
comparison src/com/jcraft/jzlib/InflaterInputStream.java @ 357:46c2115ae1c8
update jzlib to a21be20213d66eff15904d925e9b721956a01ef7
author | Carl Byington <carl@five-ten-sg.com> |
---|---|
date | Fri, 01 Aug 2014 13:34:58 -0700 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
356:5e91b559b5fe | 357:46c2115ae1c8 |
---|---|
1 /* -*-mode:java; c-basic-offset:2; indent-tabs-mode:nil -*- */ | |
2 /* | |
3 Copyright (c) 2011 ymnk, JCraft,Inc. All rights reserved. | |
4 | |
5 Redistribution and use in source and binary forms, with or without | |
6 modification, are permitted provided that the following conditions are met: | |
7 | |
8 1. Redistributions of source code must retain the above copyright notice, | |
9 this list of conditions and the following disclaimer. | |
10 | |
11 2. Redistributions in binary form must reproduce the above copyright | |
12 notice, this list of conditions and the following disclaimer in | |
13 the documentation and/or other materials provided with the distribution. | |
14 | |
15 3. The names of the authors may not be used to endorse or promote products | |
16 derived from this software without specific prior written permission. | |
17 | |
18 THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, | |
19 INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND | |
20 FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT, | |
21 INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT, | |
22 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT | |
23 LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, | |
24 OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF | |
25 LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING | |
26 NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, | |
27 EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | |
28 */ | |
29 | |
30 package com.jcraft.jzlib; | |
31 import java.io.*; | |
32 | |
33 public class InflaterInputStream extends FilterInputStream { | |
34 protected final Inflater inflater; | |
35 protected byte[] buf; | |
36 | |
37 private boolean closed = false; | |
38 | |
39 private boolean eof = false; | |
40 | |
41 private boolean close_in = true; | |
42 | |
43 protected static final int DEFAULT_BUFSIZE = 512; | |
44 | |
45 public InflaterInputStream(InputStream in) throws IOException { | |
46 this(in, false); | |
47 } | |
48 | |
49 public InflaterInputStream(InputStream in, boolean nowrap) throws IOException { | |
50 this(in, new Inflater(nowrap)); | |
51 myinflater = true; | |
52 } | |
53 | |
54 public InflaterInputStream(InputStream in, Inflater inflater) throws IOException { | |
55 this(in, inflater, DEFAULT_BUFSIZE); | |
56 } | |
57 | |
58 public InflaterInputStream(InputStream in, | |
59 Inflater inflater, int size) throws IOException { | |
60 this(in, inflater, size, true); | |
61 } | |
62 | |
63 public InflaterInputStream(InputStream in, | |
64 Inflater inflater, | |
65 int size, boolean close_in) throws IOException { | |
66 super(in); | |
67 if (in == null || inflater == null) { | |
68 throw new NullPointerException(); | |
69 } | |
70 else if (size <= 0) { | |
71 throw new IllegalArgumentException("buffer size must be greater than 0"); | |
72 } | |
73 this.inflater = inflater; | |
74 buf = new byte[size]; | |
75 this.close_in = close_in; | |
76 } | |
77 | |
78 protected boolean myinflater = false; | |
79 | |
80 private byte[] byte1 = new byte[1]; | |
81 | |
82 public int read() throws IOException { | |
83 if (closed) { throw new IOException("Stream closed"); } | |
84 return read(byte1, 0, 1) == -1 ? -1 : byte1[0] & 0xff; | |
85 } | |
86 | |
87 public int read(byte[] b, int off, int len) throws IOException { | |
88 if (closed) { throw new IOException("Stream closed"); } | |
89 if (b == null) { | |
90 throw new NullPointerException(); | |
91 } | |
92 else if (off < 0 || len < 0 || len > b.length - off) { | |
93 throw new IndexOutOfBoundsException(); | |
94 } | |
95 else if (len == 0) { | |
96 return 0; | |
97 } | |
98 else if (eof) { | |
99 return -1; | |
100 } | |
101 | |
102 int n = 0; | |
103 inflater.setOutput(b, off, len); | |
104 while(!eof) { | |
105 if(inflater.avail_in==0) | |
106 fill(); | |
107 int err = inflater.inflate(JZlib.Z_NO_FLUSH); | |
108 n += inflater.next_out_index - off; | |
109 off = inflater.next_out_index; | |
110 switch(err) { | |
111 case JZlib.Z_DATA_ERROR: | |
112 throw new IOException(inflater.msg); | |
113 case JZlib.Z_STREAM_END: | |
114 case JZlib.Z_NEED_DICT: | |
115 eof = true; | |
116 if(err == JZlib.Z_NEED_DICT) | |
117 return -1; | |
118 break; | |
119 default: | |
120 } | |
121 if(inflater.avail_out==0) | |
122 break; | |
123 } | |
124 return n; | |
125 } | |
126 | |
127 public int available() throws IOException { | |
128 if (closed) { throw new IOException("Stream closed"); } | |
129 if (eof) { | |
130 return 0; | |
131 } | |
132 else { | |
133 return 1; | |
134 } | |
135 } | |
136 | |
137 private byte[] b = new byte[512]; | |
138 | |
139 public long skip(long n) throws IOException { | |
140 if (n < 0) { | |
141 throw new IllegalArgumentException("negative skip length"); | |
142 } | |
143 | |
144 if (closed) { throw new IOException("Stream closed"); } | |
145 | |
146 int max = (int)Math.min(n, Integer.MAX_VALUE); | |
147 int total = 0; | |
148 while (total < max) { | |
149 int len = max - total; | |
150 if (len > b.length) { | |
151 len = b.length; | |
152 } | |
153 len = read(b, 0, len); | |
154 if (len == -1) { | |
155 eof = true; | |
156 break; | |
157 } | |
158 total += len; | |
159 } | |
160 return total; | |
161 } | |
162 | |
163 public void close() throws IOException { | |
164 if (!closed) { | |
165 if (myinflater) | |
166 inflater.end(); | |
167 if(close_in) | |
168 in.close(); | |
169 closed = true; | |
170 } | |
171 } | |
172 | |
173 protected void fill() throws IOException { | |
174 if (closed) { throw new IOException("Stream closed"); } | |
175 int len = in.read(buf, 0, buf.length); | |
176 if (len == -1) { | |
177 if(inflater.istate.wrap == 0 && | |
178 !inflater.finished()){ | |
179 buf[0]=0; | |
180 len=1; | |
181 } | |
182 else if(inflater.istate.was != -1){ // in reading trailer | |
183 throw new IOException("footer is not found"); | |
184 } | |
185 else{ | |
186 throw new EOFException("Unexpected end of ZLIB input stream"); | |
187 } | |
188 } | |
189 inflater.setInput(buf, 0, len, true); | |
190 } | |
191 | |
192 public boolean markSupported() { | |
193 return false; | |
194 } | |
195 | |
196 public synchronized void mark(int readlimit) { | |
197 } | |
198 | |
199 public synchronized void reset() throws IOException { | |
200 throw new IOException("mark/reset not supported"); | |
201 } | |
202 | |
203 public long getTotalIn() { | |
204 return inflater.getTotalIn(); | |
205 } | |
206 | |
207 public long getTotalOut() { | |
208 return inflater.getTotalOut(); | |
209 } | |
210 | |
211 public byte[] getAvailIn() { | |
212 if(inflater.avail_in<=0) | |
213 return null; | |
214 byte[] tmp = new byte[inflater.avail_in]; | |
215 System.arraycopy(inflater.next_in, inflater.next_in_index, | |
216 tmp, 0, inflater.avail_in); | |
217 return tmp; | |
218 } | |
219 | |
220 public void readHeader() throws IOException { | |
221 | |
222 byte[] empty = "".getBytes(); | |
223 inflater.setInput(empty, 0, 0, false); | |
224 inflater.setOutput(empty, 0, 0); | |
225 | |
226 int err = inflater.inflate(JZlib.Z_NO_FLUSH); | |
227 if(!inflater.istate.inParsingHeader()){ | |
228 return; | |
229 } | |
230 | |
231 byte[] b1 = new byte[1]; | |
232 do{ | |
233 int i = in.read(b1); | |
234 if(i<=0) | |
235 throw new IOException("no input"); | |
236 inflater.setInput(b1); | |
237 err = inflater.inflate(JZlib.Z_NO_FLUSH); | |
238 if(err!=0/*Z_OK*/) | |
239 throw new IOException(inflater.msg); | |
240 } | |
241 while(inflater.istate.inParsingHeader()); | |
242 } | |
243 | |
244 public Inflater getInflater(){ | |
245 return inflater; | |
246 } | |
247 } |