blob: d79da41859aa00502f0d9deef5a7b730ec14bbee [file] [log] [blame]
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -07001/*
2 * Licensed to the Apache Software Foundation (ASF) under one or more
3 * contributor license agreements. See the NOTICE file distributed with
4 * this work for additional information regarding copyright ownership.
5 * The ASF licenses this file to You under the Apache License, Version 2.0
6 * (the "License"); you may not use this file except in compliance with
7 * the License. You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17/**
18 * @author Rustem V. Rafikov
19 * @version $Revision: 1.3 $
20 */
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080021
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070022package javax.imageio.stream;
23
24import java.io.EOFException;
25import java.io.IOException;
26import java.nio.ByteOrder;
27
28/**
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080029 * The ImageInputStreamImpl abstract class implements the ImageInputStream
30 * interface.
31 *
32 * @since Android 1.0
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070033 */
34public abstract class ImageInputStreamImpl implements ImageInputStream {
35
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080036 /**
37 * The byte order.
38 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070039 protected ByteOrder byteOrder = ByteOrder.BIG_ENDIAN;
40
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080041 /**
42 * The stream position.
43 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070044 protected long streamPos = 0;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080045
46 /**
47 * The flushed position.
48 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070049 protected long flushedPos = 0;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080050
51 /**
52 * The bit offset.
53 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070054 protected int bitOffset = 0;
55
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080056 /**
57 * The closed.
58 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070059 private boolean closed = false;
60
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080061 /**
62 * The position stack.
63 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070064 private final PositionStack posStack = new PositionStack();
65
66 /**
67 * Instantiates a new ImageInputStreamImpl.
68 */
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080069 public ImageInputStreamImpl() {
70 }
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070071
72 /**
73 * Check if the stream is closed and if true, throws an IOException.
74 *
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -080075 * @throws IOException
76 * if the stream is closed.
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -070077 */
78 protected final void checkClosed() throws IOException {
79 if (closed) {
80 throw new IOException("stream is closed");
81 }
82 }
83
84 public void setByteOrder(ByteOrder byteOrder) {
85 this.byteOrder = byteOrder;
86 }
87
88 public ByteOrder getByteOrder() {
89 return byteOrder;
90 }
91
92 public abstract int read() throws IOException;
93
94 public int read(byte[] b) throws IOException {
95 return read(b, 0, b.length);
96 }
97
98 public abstract int read(byte[] b, int off, int len) throws IOException;
99
100 public void readBytes(IIOByteBuffer buf, int len) throws IOException {
101 if (buf == null) {
102 throw new NullPointerException("buffer is NULL");
103 }
104
105 byte[] b = new byte[len];
106 len = read(b, 0, b.length);
107
108 buf.setData(b);
109 buf.setOffset(0);
110 buf.setLength(len);
111 }
112
113 public boolean readBoolean() throws IOException {
114 int b = read();
115 if (b < 0) {
116 throw new EOFException("EOF reached");
117 }
118 return b != 0;
119 }
120
121 public byte readByte() throws IOException {
122 int b = read();
123 if (b < 0) {
124 throw new EOFException("EOF reached");
125 }
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800126 return (byte)b;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700127 }
128
129 public int readUnsignedByte() throws IOException {
130 int b = read();
131 if (b < 0) {
132 throw new EOFException("EOF reached");
133 }
134 return b;
135 }
136
137 public short readShort() throws IOException {
138 int b1 = read();
139 int b2 = read();
140
141 if (b1 < 0 || b2 < 0) {
142 throw new EOFException("EOF reached");
143 }
144
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800145 return byteOrder == ByteOrder.BIG_ENDIAN ? (short)((b1 << 8) | (b2 & 0xff))
146 : (short)((b2 << 8) | (b1 & 0xff));
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700147 }
148
149 public int readUnsignedShort() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800150 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700151 throw new UnsupportedOperationException("Not implemented yet");
152 }
153
154 public char readChar() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800155 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700156 throw new UnsupportedOperationException("Not implemented yet");
157 }
158
159 public int readInt() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800160 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700161 throw new UnsupportedOperationException("Not implemented yet");
162 }
163
164 public long readUnsignedInt() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800165 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700166 throw new UnsupportedOperationException("Not implemented yet");
167 }
168
169 public long readLong() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800170 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700171 throw new UnsupportedOperationException("Not implemented yet");
172 }
173
174 public float readFloat() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800175 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700176 throw new UnsupportedOperationException("Not implemented yet");
177 }
178
179 public double readDouble() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800180 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700181 throw new UnsupportedOperationException("Not implemented yet");
182 }
183
184 public String readLine() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800185 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700186 throw new UnsupportedOperationException("Not implemented yet");
187 }
188
189 public String readUTF() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800190 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700191 throw new UnsupportedOperationException("Not implemented yet");
192 }
193
194 public void readFully(byte[] b, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800195 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700196 throw new UnsupportedOperationException("Not implemented yet");
197 }
198
199 public void readFully(byte[] b) throws IOException {
200 readFully(b, 0, b.length);
201 }
202
203 public void readFully(short[] s, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800204 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700205 throw new UnsupportedOperationException("Not implemented yet");
206 }
207
208 public void readFully(char[] c, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800209 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700210 throw new UnsupportedOperationException("Not implemented yet");
211 }
212
213 public void readFully(int[] i, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800214 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700215 throw new UnsupportedOperationException("Not implemented yet");
216 }
217
218 public void readFully(long[] l, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800219 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700220 throw new UnsupportedOperationException("Not implemented yet");
221 }
222
223 public void readFully(float[] f, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800224 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700225 throw new UnsupportedOperationException("Not implemented yet");
226 }
227
228 public void readFully(double[] d, int off, int len) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800229 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700230 throw new UnsupportedOperationException("Not implemented yet");
231 }
232
233 public long getStreamPosition() throws IOException {
234 checkClosed();
235 return streamPos;
236 }
237
238 public int getBitOffset() throws IOException {
239 checkClosed();
240 return bitOffset;
241 }
242
243 public void setBitOffset(int bitOffset) throws IOException {
244 checkClosed();
245 this.bitOffset = bitOffset;
246 }
247
248 public int readBit() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800249 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700250 throw new UnsupportedOperationException("Not implemented yet");
251 }
252
253 public long readBits(int numBits) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800254 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700255 throw new UnsupportedOperationException("Not implemented yet");
256 }
257
258 public long length() {
259 return -1L;
260 }
261
262 public int skipBytes(int n) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800263 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700264 throw new UnsupportedOperationException("Not implemented yet");
265 }
266
267 public long skipBytes(long n) throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800268 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700269 throw new UnsupportedOperationException("Not implemented yet");
270 }
271
272 public void seek(long pos) throws IOException {
273 checkClosed();
274 if (pos < getFlushedPosition()) {
275 throw new IllegalArgumentException("trying to seek before flushed pos");
276 }
277 bitOffset = 0;
278 streamPos = pos;
279 }
280
281 public void mark() {
282 try {
283 posStack.push(getStreamPosition());
284 } catch (IOException e) {
285 e.printStackTrace();
286 throw new RuntimeException("Stream marking error");
287 }
288 }
289
290 public void reset() throws IOException {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800291 // -- TODO bit pos
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700292 if (!posStack.isEmpty()) {
293 long p = posStack.pop();
294 if (p < flushedPos) {
295 throw new IOException("marked position lies in the flushed portion of the stream");
296 }
297 seek(p);
298 }
299 }
300
301 public void flushBefore(long pos) throws IOException {
302 if (pos > getStreamPosition()) {
303 throw new IndexOutOfBoundsException("Trying to flush outside of current position");
304 }
305 if (pos < flushedPos) {
306 throw new IndexOutOfBoundsException("Trying to flush within already flushed portion");
307 }
308 flushedPos = pos;
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800309 // -- TODO implement
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700310 }
311
312 public void flush() throws IOException {
313 flushBefore(getStreamPosition());
314 }
315
316 public long getFlushedPosition() {
317 return flushedPos;
318 }
319
320 public boolean isCached() {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800321 return false; // def
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700322 }
323
324 public boolean isCachedMemory() {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800325 return false; // def
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700326 }
327
328 public boolean isCachedFile() {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800329 return false; // def
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700330 }
331
332 public void close() throws IOException {
333 checkClosed();
334 closed = true;
335
336 }
337
338 /**
339 * Finalizes this object.
340 *
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800341 * @throws Throwable
342 * if an error occurs.
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700343 */
344 @Override
345 protected void finalize() throws Throwable {
346 if (!closed) {
347 try {
348 close();
349 } finally {
350 super.finalize();
351 }
352 }
353 }
354
355 /**
356 * The Class PositionStack.
357 */
358 private static class PositionStack {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800359
360 /**
361 * The Constant SIZE.
362 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700363 private static final int SIZE = 10;
364
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800365 /**
366 * The values.
367 */
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700368 private long[] values = new long[SIZE];
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700369
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800370 /**
371 * The pos.
372 */
373 private int pos = 0;
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700374
375 /**
376 * Push.
377 *
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800378 * @param v
379 * the v.
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700380 */
381 void push(long v) {
382 if (pos >= values.length) {
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800383 ensure(pos + 1);
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700384 }
385 values[pos++] = v;
386 }
387
388 /**
389 * Pop.
390 *
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800391 * @return the long.
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700392 */
393 long pop() {
394 return values[--pos];
395 }
396
397 /**
398 * Checks if is empty.
399 *
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800400 * @return true, if is empty.
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700401 */
402 boolean isEmpty() {
403 return pos == 0;
404 }
405
406 /**
407 * Ensure.
408 *
The Android Open Source Projecte09fd9e2008-12-17 18:05:43 -0800409 * @param size
410 * the size.
The Android Open Source Project7c1b96a2008-10-21 07:00:00 -0700411 */
412 private void ensure(int size) {
413 long[] arr = new long[Math.max(2 * values.length, size)];
414 System.arraycopy(values, 0, arr, 0, values.length);
415 values = arr;
416 }
417 }
418}