001: /*
002: * $RCSfile: ByteInputBuffer.java,v $
003: * $Revision: 1.1 $
004: * $Date: 2005/02/11 05:02:05 $
005: * $State: Exp $
006: *
007: * Class: ByteInputBuffer
008: *
009: * Description: Provides buffering for byte based input, similar
010: * to the standard class ByteArrayInputStream
011: *
012: * the old jj2000.j2k.io.ByteArrayInput class by
013: * Diego SANTA CRUZ, Apr-26-1999
014: *
015: *
016: * COPYRIGHT:
017: *
018: * This software module was originally developed by Raphaël Grosbois and
019: * Diego Santa Cruz (Swiss Federal Institute of Technology-EPFL); Joel
020: * Askelöf (Ericsson Radio Systems AB); and Bertrand Berthelot, David
021: * Bouchard, Félix Henry, Gerard Mozelle and Patrice Onno (Canon Research
022: * Centre France S.A) in the course of development of the JPEG2000
023: * standard as specified by ISO/IEC 15444 (JPEG 2000 Standard). This
024: * software module is an implementation of a part of the JPEG 2000
025: * Standard. Swiss Federal Institute of Technology-EPFL, Ericsson Radio
026: * Systems AB and Canon Research Centre France S.A (collectively JJ2000
027: * Partners) agree not to assert against ISO/IEC and users of the JPEG
028: * 2000 Standard (Users) any of their rights under the copyright, not
029: * including other intellectual property rights, for this software module
030: * with respect to the usage by ISO/IEC and Users of this software module
031: * or modifications thereof for use in hardware or software products
032: * claiming conformance to the JPEG 2000 Standard. Those intending to use
033: * this software module in hardware or software products are advised that
034: * their use may infringe existing patents. The original developers of
035: * this software module, JJ2000 Partners and ISO/IEC assume no liability
036: * for use of this software module or modifications thereof. No license
037: * or right to this software module is granted for non JPEG 2000 Standard
038: * conforming products. JJ2000 Partners have full right to use this
039: * software module for his/her own purpose, assign or donate this
040: * software module to any third party and to inhibit third parties from
041: * using this software module for non JPEG 2000 Standard conforming
042: * products. This copyright notice must be included in all copies or
043: * derivative works of this software module.
044: *
045: * Copyright (c) 1999/2000 JJ2000 Partners.
046: *
047: *
048: *
049: */
050:
051: package jj2000.j2k.entropy.decoder;
052:
053: import java.io.*;
054:
055: /**
056: * This class provides a byte input facility from byte buffers. It is similar
057: * to the ByteArrayInputStream class, but adds the possibility to add data to
058: * the stream after the creation of the object.
059: *
060: * <P>Unlike the ByteArrayInputStream this class is not thread safe (i.e. no
061: * two threads can use the same object at the same time, but different objects
062: * may be used in different threads).
063: *
064: * <P>This class can modify the contents of the buffer given to the
065: * constructor, when the addByteArray() method is called.
066: *
067: * @see InputStream
068: * */
069: public class ByteInputBuffer {
070:
071: /** The byte array containing the data */
072: private byte buf[];
073:
074: /** The index one greater than the last valid character in the input
075: * stream buffer */
076: private int count;
077:
078: /** The index of the next character to read from the input stream buffer
079: * */
080: private int pos;
081:
082: /**
083: * Creates a new byte array input stream that reads data from the
084: * specified byte array. The byte array is not copied.
085: *
086: * @param buf the input buffer.
087: */
088: public ByteInputBuffer(byte buf[]) {
089: this .buf = buf;
090: count = buf.length;
091: }
092:
093: /**
094: * Creates a new byte array input stream that reads data from the
095: * specified byte array. Up to length characters are to be read
096: * from the byte array, starting at the indicated offset.
097: *
098: * <P>The byte array is not copied.
099: *
100: * @param buf the input buffer.
101: *
102: * @param offset the offset in the buffer of the first byte to
103: * read.
104: *
105: * @param length the maximum number of bytes to read from the
106: * buffer.
107: */
108: public ByteInputBuffer(byte buf[], int offset, int length) {
109: this .buf = buf;
110: pos = offset;
111: count = offset + length;
112: }
113:
114: /**
115: * Sets the underlying buffer byte array to the given one, with the given
116: * offset and length. If 'buf' is null then the current byte buffer is
117: * assumed. If 'offset' is negative, then it will be assumed to be
118: * 'off+len', where 'off' and 'len' are the offset and length of the
119: * current byte buffer.
120: *
121: * <P>The byte array is not copied.
122: *
123: * @param buf the input buffer. If null it is the current input buffer.
124: *
125: * @param offset the offset in the buffer of the first byte to read. If
126: * negative it is assumed to be the byte just after the end of the current
127: * input buffer, only permitted if 'buf' is null.
128: *
129: * @param length the maximum number of bytes to read frmo the buffer.
130: */
131: public void setByteArray(byte buf[], int offset, int length) {
132: // In same buffer?
133: if (buf == null) {
134: if (length < 0 || count + length > this .buf.length) {
135: throw new IllegalArgumentException();
136: }
137: if (offset < 0) {
138: pos = count;
139: count += length;
140: } else {
141: count = offset + length;
142: pos = offset;
143: }
144: } else { // New input buffer
145: if (offset < 0 || length < 0
146: || offset + length > buf.length) {
147: throw new IllegalArgumentException();
148: }
149: this .buf = buf;
150: count = offset + length;
151: pos = offset;
152: }
153: }
154:
155: /**
156: * Adds the specified data to the end of the byte array stream. This
157: * method modifies the byte array buffer. It can also discard the already
158: * read input.
159: *
160: * @param data The data to add. The data is copied.
161: *
162: * @param off The index, in data, of the first element to add to
163: * the stream.
164: *
165: * @param len The number of elements to add to the array.
166: *
167: *
168: * */
169: public synchronized void addByteArray(byte data[], int off, int len) {
170: // Check integrity
171: if (len < 0 || off < 0 || len + off > buf.length) {
172: throw new IllegalArgumentException();
173: }
174: // Copy new data
175: if (count + len <= buf.length) { // Enough place in 'buf'
176: System.arraycopy(data, off, buf, count, len);
177: count += len;
178: } else {
179: if (count - pos + len <= buf.length) {
180: // Enough place in 'buf' if we move input data
181: // Move buffer
182: System.arraycopy(buf, pos, buf, 0, count - pos);
183: } else { // Not enough place in 'buf', use new buffer
184: byte[] oldbuf = buf;
185: buf = new byte[count - pos + len];
186: // Copy buffer
187: System.arraycopy(oldbuf, count, buf, 0, count - pos);
188: }
189: count -= pos;
190: pos = 0;
191: // Copy new data
192: System.arraycopy(data, off, buf, count, len);
193: count += len;
194: }
195: }
196:
197: /**
198: * Reads the next byte of data from this input stream. The value
199: * byte is returned as an int in the range 0 to 255. If no byte is
200: * available because the end of the stream has been reached, the
201: * EOFException exception is thrown.
202: *
203: * <P>This method is not synchronized, so it is not thread safe.
204: *
205: * @return The byte read in the range 0-255.
206: *
207: * @exception EOFException If the end of the stream is reached.
208: *
209: *
210: * */
211: public int readChecked() throws IOException {
212: if (pos < count) {
213: return (int) buf[pos++] & 0xFF;
214: } else {
215: throw new EOFException();
216: }
217: }
218:
219: /**
220: * Reads the next byte of data from this input stream. The value byte is
221: * returned as an int in the range 0 to 255. If no byte is available
222: * because the end of the stream has been reached, -1 is returned.
223: *
224: * <P>This method is not synchronized, so it is not thread safe.
225: *
226: * @return The byte read in the range 0-255, or -1 if the end of stream
227: * has been reached.
228: *
229: *
230: * */
231: public int read() {
232: if (pos < count) {
233: return (int) buf[pos++] & 0xFF;
234: } else {
235: return -1;
236: }
237: }
238:
239: }
|