1 /* 2 * Copyright (c) 1994, 2016, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package java.io; 27 28 /** 29 * A <code>PushbackInputStream</code> adds 30 * functionality to another input stream, namely 31 * the ability to "push back" or "unread" bytes, 32 * by storing pushed-back bytes in an internal buffer. 33 * This is useful in situations where 34 * it is convenient for a fragment of code 35 * to read an indefinite number of data bytes 36 * that are delimited by a particular byte 37 * value; after reading the terminating byte, 38 * the code fragment can "unread" it, so that 39 * the next read operation on the input stream 40 * will reread the byte that was pushed back. 41 * For example, bytes representing the characters 42 * constituting an identifier might be terminated 43 * by a byte representing an operator character; 44 * a method whose job is to read just an identifier 45 * can read until it sees the operator and 46 * then push the operator back to be re-read. 47 * 48 * @author David Connelly 49 * @author Jonathan Payne 50 * @since 1.0 51 */ 52 public 53 class PushbackInputStream extends FilterInputStream { 54 /** 55 * The pushback buffer. 56 * @since 1.1 57 */ 58 protected byte[] buf; 59 60 /** 61 * The position within the pushback buffer from which the next byte will 62 * be read. When the buffer is empty, <code>pos</code> is equal to 63 * <code>buf.length</code>; when the buffer is full, <code>pos</code> is 64 * equal to zero. 65 * 66 * @since 1.1 67 */ 68 protected int pos; 69 70 /** 71 * Check to make sure that this stream has not been closed 72 */ 73 private void ensureOpen() throws IOException { 74 if (in == null) 75 throw new IOException("Stream closed"); 76 } 77 78 /** 79 * Creates a <code>PushbackInputStream</code> 80 * with a pushback buffer of the specified <code>size</code>, 81 * and saves its argument, the input stream 82 * <code>in</code>, for later use. Initially, 83 * the pushback buffer is empty. 84 * 85 * @param in the input stream from which bytes will be read. 86 * @param size the size of the pushback buffer. 87 * @exception IllegalArgumentException if {@code size <= 0} 88 * @since 1.1 89 */ 90 public PushbackInputStream(InputStream in, int size) { 91 super(in); 92 if (size <= 0) { 93 throw new IllegalArgumentException("size <= 0"); 94 } 95 this.buf = new byte[size]; 96 this.pos = size; 97 } 98 99 /** 100 * Creates a <code>PushbackInputStream</code> 101 * with a 1-byte pushback buffer, and saves its argument, the input stream 102 * <code>in</code>, for later use. Initially, 103 * the pushback buffer is empty. 104 * 105 * @param in the input stream from which bytes will be read. 106 */ 107 public PushbackInputStream(InputStream in) { 108 this(in, 1); 109 } 110 111 /** 112 * Reads the next byte of data from this input stream. The value 113 * byte is returned as an <code>int</code> in the range 114 * <code>0</code> to <code>255</code>. If no byte is available 115 * because the end of the stream has been reached, the value 116 * <code>-1</code> is returned. This method blocks until input data 117 * is available, the end of the stream is detected, or an exception 118 * is thrown. 119 * 120 * <p> This method returns the most recently pushed-back byte, if there is 121 * one, and otherwise calls the <code>read</code> method of its underlying 122 * input stream and returns whatever value that method returns. 123 * 124 * @return the next byte of data, or <code>-1</code> if the end of the 125 * stream has been reached. 126 * @exception IOException if this input stream has been closed by 127 * invoking its {@link #close()} method, 128 * or an I/O error occurs. 129 * @see java.io.InputStream#read() 130 */ 131 public int read() throws IOException { 132 ensureOpen(); 133 if (pos < buf.length) { 134 return buf[pos++] & 0xff; 135 } 136 return super.read(); 137 } 138 139 /** 140 * Reads up to <code>len</code> bytes of data from this input stream into 141 * an array of bytes. This method first reads any pushed-back bytes; after 142 * that, if fewer than <code>len</code> bytes have been read then it 143 * reads from the underlying input stream. If <code>len</code> is not zero, the method 144 * blocks until at least 1 byte of input is available; otherwise, no 145 * bytes are read and <code>0</code> is returned. 146 * 147 * @param b the buffer into which the data is read. 148 * @param off the start offset in the destination array <code>b</code> 149 * @param len the maximum number of bytes read. 150 * @return the total number of bytes read into the buffer, or 151 * <code>-1</code> if there is no more data because the end of 152 * the stream has been reached. 153 * @exception NullPointerException If <code>b</code> is <code>null</code>. 154 * @exception IndexOutOfBoundsException If <code>off</code> is negative, 155 * <code>len</code> is negative, or <code>len</code> is greater than 156 * <code>b.length - off</code> 157 * @exception IOException if this input stream has been closed by 158 * invoking its {@link #close()} method, 159 * or an I/O error occurs. 160 * @see java.io.InputStream#read(byte[], int, int) 161 */ 162 public int read(byte[] b, int off, int len) throws IOException { 163 ensureOpen(); 164 if (b == null) { 165 throw new NullPointerException(); 166 } else if (off < 0 || len < 0 || len > b.length - off) { 167 throw new IndexOutOfBoundsException(); 168 } else if (len == 0) { 169 return 0; 170 } 171 172 int avail = buf.length - pos; 173 if (avail > 0) { 174 if (len < avail) { 175 avail = len; 176 } 177 System.arraycopy(buf, pos, b, off, avail); 178 pos += avail; 179 off += avail; 180 len -= avail; 181 } 182 if (len > 0) { 183 len = super.read(b, off, len); 184 if (len == -1) { 185 return avail == 0 ? -1 : avail; 186 } 187 return avail + len; 188 } 189 return avail; 190 } 191 192 /** 193 * Pushes back a byte by copying it to the front of the pushback buffer. 194 * After this method returns, the next byte to be read will have the value 195 * <code>(byte)b</code>. 196 * 197 * @param b the <code>int</code> value whose low-order 198 * byte is to be pushed back. 199 * @exception IOException If there is not enough room in the pushback 200 * buffer for the byte, or this input stream has been closed by 201 * invoking its {@link #close()} method. 202 */ 203 public void unread(int b) throws IOException { 204 ensureOpen(); 205 if (pos == 0) { 206 throw new IOException("Push back buffer is full"); 207 } 208 buf[--pos] = (byte)b; 209 } 210 211 /** 212 * Pushes back a portion of an array of bytes by copying it to the front 213 * of the pushback buffer. After this method returns, the next byte to be 214 * read will have the value <code>b[off]</code>, the byte after that will 215 * have the value <code>b[off+1]</code>, and so forth. 216 * 217 * @param b the byte array to push back. 218 * @param off the start offset of the data. 219 * @param len the number of bytes to push back. 220 * @exception IOException If there is not enough room in the pushback 221 * buffer for the specified number of bytes, 222 * or this input stream has been closed by 223 * invoking its {@link #close()} method. 224 * @since 1.1 225 */ 226 public void unread(byte[] b, int off, int len) throws IOException { 227 ensureOpen(); 228 if (len > pos) { 229 throw new IOException("Push back buffer is full"); 230 } 231 pos -= len; 232 System.arraycopy(b, off, buf, pos, len); 233 } 234 235 /** 236 * Pushes back an array of bytes by copying it to the front of the 237 * pushback buffer. After this method returns, the next byte to be read 238 * will have the value <code>b[0]</code>, the byte after that will have the 239 * value <code>b[1]</code>, and so forth. 240 * 241 * @param b the byte array to push back 242 * @exception IOException If there is not enough room in the pushback 243 * buffer for the specified number of bytes, 244 * or this input stream has been closed by 245 * invoking its {@link #close()} method. 246 * @since 1.1 247 */ 248 public void unread(byte[] b) throws IOException { 249 unread(b, 0, b.length); 250 } 251 252 /** 253 * Returns an estimate of the number of bytes that can be read (or 254 * skipped over) from this input stream without blocking by the next 255 * invocation of a method for this input stream. The next invocation might be 256 * the same thread or another thread. A single read or skip of this 257 * many bytes will not block, but may read or skip fewer bytes. 258 * 259 * <p> The method returns the sum of the number of bytes that have been 260 * pushed back and the value returned by {@link 261 * java.io.FilterInputStream#available available}. 262 * 263 * @return the number of bytes that can be read (or skipped over) from 264 * the input stream without blocking. 265 * @exception IOException if this input stream has been closed by 266 * invoking its {@link #close()} method, 267 * or an I/O error occurs. 268 * @see java.io.FilterInputStream#in 269 * @see java.io.InputStream#available() 270 */ 271 public int available() throws IOException { 272 ensureOpen(); 273 int n = buf.length - pos; 274 int avail = super.available(); 275 return n > (Integer.MAX_VALUE - avail) 276 ? Integer.MAX_VALUE 277 : n + avail; 278 } 279 280 /** 281 * Skips over and discards <code>n</code> bytes of data from this 282 * input stream. The <code>skip</code> method may, for a variety of 283 * reasons, end up skipping over some smaller number of bytes, 284 * possibly zero. If <code>n</code> is negative, no bytes are skipped. 285 * 286 * <p> The <code>skip</code> method of <code>PushbackInputStream</code> 287 * first skips over the bytes in the pushback buffer, if any. It then 288 * calls the <code>skip</code> method of the underlying input stream if 289 * more bytes need to be skipped. The actual number of bytes skipped 290 * is returned. 291 * 292 * @param n {@inheritDoc} 293 * @return {@inheritDoc} 294 * @throws IOException if the stream has been closed by 295 * invoking its {@link #close()} method, 296 * {@code in.skip(n)} throws an IOException, 297 * or an I/O error occurs. 298 * @see java.io.FilterInputStream#in 299 * @see java.io.InputStream#skip(long n) 300 * @since 1.2 301 */ 302 public long skip(long n) throws IOException { 303 ensureOpen(); 304 if (n <= 0) { 305 return 0; 306 } 307 308 long pskip = buf.length - pos; 309 if (pskip > 0) { 310 if (n < pskip) { 311 pskip = n; 312 } 313 pos += pskip; 314 n -= pskip; 315 } 316 if (n > 0) { 317 pskip += super.skip(n); 318 } 319 return pskip; 320 } 321 322 /** 323 * Tests if this input stream supports the <code>mark</code> and 324 * <code>reset</code> methods, which it does not. 325 * 326 * @return <code>false</code>, since this class does not support the 327 * <code>mark</code> and <code>reset</code> methods. 328 * @see java.io.InputStream#mark(int) 329 * @see java.io.InputStream#reset() 330 */ 331 public boolean markSupported() { 332 return false; 333 } 334 335 /** 336 * Marks the current position in this input stream. 337 * 338 * <p> The <code>mark</code> method of <code>PushbackInputStream</code> 339 * does nothing. 340 * 341 * @param readlimit the maximum limit of bytes that can be read before 342 * the mark position becomes invalid. 343 * @see java.io.InputStream#reset() 344 */ 345 public synchronized void mark(int readlimit) { 346 } 347 348 /** 349 * Repositions this stream to the position at the time the 350 * <code>mark</code> method was last called on this input stream. 351 * 352 * <p> The method <code>reset</code> for class 353 * <code>PushbackInputStream</code> does nothing except throw an 354 * <code>IOException</code>. 355 * 356 * @exception IOException if this method is invoked. 357 * @see java.io.InputStream#mark(int) 358 * @see java.io.IOException 359 */ 360 public synchronized void reset() throws IOException { 361 throw new IOException("mark/reset not supported"); 362 } 363 364 /** 365 * Closes this input stream and releases any system resources 366 * associated with the stream. 367 * Once the stream has been closed, further read(), unread(), 368 * available(), reset(), or skip() invocations will throw an IOException. 369 * Closing a previously closed stream has no effect. 370 * 371 * @exception IOException if an I/O error occurs. 372 */ 373 public synchronized void close() throws IOException { 374 if (in == null) 375 return; 376 in.close(); 377 in = null; 378 buf = null; 379 } 380 } | 1 /* 2 * Copyright (c) 1994, 2019, Oracle and/or its affiliates. All rights reserved. 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * This code is free software; you can redistribute it and/or modify it 6 * under the terms of the GNU General Public License version 2 only, as 7 * published by the Free Software Foundation. Oracle designates this 8 * particular file as subject to the "Classpath" exception as provided 9 * by Oracle in the LICENSE file that accompanied this code. 10 * 11 * This code is distributed in the hope that it will be useful, but WITHOUT 12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 * version 2 for more details (a copy is included in the LICENSE file that 15 * accompanied this code). 16 * 17 * You should have received a copy of the GNU General Public License version 18 * 2 along with this work; if not, write to the Free Software Foundation, 19 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. 20 * 21 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA 22 * or visit www.oracle.com if you need additional information or have any 23 * questions. 24 */ 25 26 package java.io; 27 28 /** 29 * A {@code PushbackInputStream} adds 30 * functionality to another input stream, namely 31 * the ability to "push back" or "unread" bytes, 32 * by storing pushed-back bytes in an internal buffer. 33 * This is useful in situations where 34 * it is convenient for a fragment of code 35 * to read an indefinite number of data bytes 36 * that are delimited by a particular byte 37 * value; after reading the terminating byte, 38 * the code fragment can "unread" it, so that 39 * the next read operation on the input stream 40 * will reread the byte that was pushed back. 41 * For example, bytes representing the characters 42 * constituting an identifier might be terminated 43 * by a byte representing an operator character; 44 * a method whose job is to read just an identifier 45 * can read until it sees the operator and 46 * then push the operator back to be re-read. 47 * 48 * @author David Connelly 49 * @author Jonathan Payne 50 * @since 1.0 51 */ 52 public 53 class PushbackInputStream extends FilterInputStream { 54 /** 55 * The pushback buffer. 56 * @since 1.1 57 */ 58 protected byte[] buf; 59 60 /** 61 * The position within the pushback buffer from which the next byte will 62 * be read. When the buffer is empty, {@code pos} is equal to 63 * {@code buf.length}; when the buffer is full, {@code pos} is 64 * equal to zero. 65 * 66 * @since 1.1 67 */ 68 protected int pos; 69 70 /** 71 * Check to make sure that this stream has not been closed 72 */ 73 private void ensureOpen() throws IOException { 74 if (in == null) 75 throw new IOException("Stream closed"); 76 } 77 78 /** 79 * Creates a {@code PushbackInputStream} 80 * with a pushback buffer of the specified {@code size}, 81 * and saves its argument, the input stream 82 * {@code in}, for later use. Initially, 83 * the pushback buffer is empty. 84 * 85 * @param in the input stream from which bytes will be read. 86 * @param size the size of the pushback buffer. 87 * @throws IllegalArgumentException if {@code size <= 0} 88 * @since 1.1 89 */ 90 public PushbackInputStream(InputStream in, int size) { 91 super(in); 92 if (size <= 0) { 93 throw new IllegalArgumentException("size <= 0"); 94 } 95 this.buf = new byte[size]; 96 this.pos = size; 97 } 98 99 /** 100 * Creates a {@code PushbackInputStream} 101 * with a 1-byte pushback buffer, and saves its argument, the input stream 102 * {@code in}, for later use. Initially, 103 * the pushback buffer is empty. 104 * 105 * @param in the input stream from which bytes will be read. 106 */ 107 public PushbackInputStream(InputStream in) { 108 this(in, 1); 109 } 110 111 /** 112 * Reads the next byte of data from this input stream. The value 113 * byte is returned as an {@code int} in the range 114 * {@code 0} to {@code 255}. If no byte is available 115 * because the end of the stream has been reached, the value 116 * {@code -1} is returned. This method blocks until input data 117 * is available, the end of the stream is detected, or an exception 118 * is thrown. 119 * 120 * <p> This method returns the most recently pushed-back byte, if there is 121 * one, and otherwise calls the {@code read} method of its underlying 122 * input stream and returns whatever value that method returns. 123 * 124 * @return the next byte of data, or {@code -1} if the end of the 125 * stream has been reached. 126 * @throws IOException if this input stream has been closed by 127 * invoking its {@link #close()} method, 128 * or an I/O error occurs. 129 * @see java.io.InputStream#read() 130 */ 131 public int read() throws IOException { 132 ensureOpen(); 133 if (pos < buf.length) { 134 return buf[pos++] & 0xff; 135 } 136 return super.read(); 137 } 138 139 /** 140 * Reads up to {@code len} bytes of data from this input stream into 141 * an array of bytes. This method first reads any pushed-back bytes; after 142 * that, if fewer than {@code len} bytes have been read then it 143 * reads from the underlying input stream. If {@code len} is not zero, the method 144 * blocks until at least 1 byte of input is available; otherwise, no 145 * bytes are read and {@code 0} is returned. 146 * 147 * @param b the buffer into which the data is read. 148 * @param off the start offset in the destination array {@code b} 149 * @param len the maximum number of bytes read. 150 * @return the total number of bytes read into the buffer, or 151 * {@code -1} if there is no more data because the end of 152 * the stream has been reached. 153 * @throws NullPointerException If {@code b} is {@code null}. 154 * @throws IndexOutOfBoundsException If {@code off} is negative, 155 * {@code len} is negative, or {@code len} is greater than 156 * {@code b.length - off} 157 * @throws IOException if this input stream has been closed by 158 * invoking its {@link #close()} method, 159 * or an I/O error occurs. 160 * @see java.io.InputStream#read(byte[], int, int) 161 */ 162 public int read(byte[] b, int off, int len) throws IOException { 163 ensureOpen(); 164 if (b == null) { 165 throw new NullPointerException(); 166 } else if (off < 0 || len < 0 || len > b.length - off) { 167 throw new IndexOutOfBoundsException(); 168 } else if (len == 0) { 169 return 0; 170 } 171 172 int avail = buf.length - pos; 173 if (avail > 0) { 174 if (len < avail) { 175 avail = len; 176 } 177 System.arraycopy(buf, pos, b, off, avail); 178 pos += avail; 179 off += avail; 180 len -= avail; 181 } 182 if (len > 0) { 183 len = super.read(b, off, len); 184 if (len == -1) { 185 return avail == 0 ? -1 : avail; 186 } 187 return avail + len; 188 } 189 return avail; 190 } 191 192 /** 193 * Pushes back a byte by copying it to the front of the pushback buffer. 194 * After this method returns, the next byte to be read will have the value 195 * {@code (byte)b}. 196 * 197 * @param b the {@code int} value whose low-order 198 * byte is to be pushed back. 199 * @throws IOException If there is not enough room in the pushback 200 * buffer for the byte, or this input stream has been closed by 201 * invoking its {@link #close()} method. 202 */ 203 public void unread(int b) throws IOException { 204 ensureOpen(); 205 if (pos == 0) { 206 throw new IOException("Push back buffer is full"); 207 } 208 buf[--pos] = (byte)b; 209 } 210 211 /** 212 * Pushes back a portion of an array of bytes by copying it to the front 213 * of the pushback buffer. After this method returns, the next byte to be 214 * read will have the value {@code b[off]}, the byte after that will 215 * have the value {@code b[off+1]}, and so forth. 216 * 217 * @param b the byte array to push back. 218 * @param off the start offset of the data. 219 * @param len the number of bytes to push back. 220 * @throws NullPointerException If {@code b} is {@code null}. 221 * @throws IOException If there is not enough room in the pushback 222 * buffer for the specified number of bytes, 223 * or this input stream has been closed by 224 * invoking its {@link #close()} method. 225 * @since 1.1 226 */ 227 public void unread(byte[] b, int off, int len) throws IOException { 228 ensureOpen(); 229 if (len > pos) { 230 throw new IOException("Push back buffer is full"); 231 } 232 pos -= len; 233 System.arraycopy(b, off, buf, pos, len); 234 } 235 236 /** 237 * Pushes back an array of bytes by copying it to the front of the 238 * pushback buffer. After this method returns, the next byte to be read 239 * will have the value {@code b[0]}, the byte after that will have the 240 * value {@code b[1]}, and so forth. 241 * 242 * @param b the byte array to push back 243 * @throws NullPointerException If {@code b} is {@code null}. 244 * @throws IOException If there is not enough room in the pushback 245 * buffer for the specified number of bytes, 246 * or this input stream has been closed by 247 * invoking its {@link #close()} method. 248 * @since 1.1 249 */ 250 public void unread(byte[] b) throws IOException { 251 unread(b, 0, b.length); 252 } 253 254 /** 255 * Returns an estimate of the number of bytes that can be read (or 256 * skipped over) from this input stream without blocking by the next 257 * invocation of a method for this input stream. The next invocation might be 258 * the same thread or another thread. A single read or skip of this 259 * many bytes will not block, but may read or skip fewer bytes. 260 * 261 * <p> The method returns the sum of the number of bytes that have been 262 * pushed back and the value returned by {@link 263 * java.io.FilterInputStream#available available}. 264 * 265 * @return the number of bytes that can be read (or skipped over) from 266 * the input stream without blocking. 267 * @throws IOException if this input stream has been closed by 268 * invoking its {@link #close()} method, 269 * or an I/O error occurs. 270 * @see java.io.FilterInputStream#in 271 * @see java.io.InputStream#available() 272 */ 273 public int available() throws IOException { 274 ensureOpen(); 275 int n = buf.length - pos; 276 int avail = super.available(); 277 return n > (Integer.MAX_VALUE - avail) 278 ? Integer.MAX_VALUE 279 : n + avail; 280 } 281 282 /** 283 * Skips over and discards {@code n} bytes of data from this 284 * input stream. The {@code skip} method may, for a variety of 285 * reasons, end up skipping over some smaller number of bytes, 286 * possibly zero. If {@code n} is negative, no bytes are skipped. 287 * 288 * <p> The {@code skip} method of {@code PushbackInputStream} 289 * first skips over the bytes in the pushback buffer, if any. It then 290 * calls the {@code skip} method of the underlying input stream if 291 * more bytes need to be skipped. The actual number of bytes skipped 292 * is returned. 293 * 294 * @param n {@inheritDoc} 295 * @return {@inheritDoc} 296 * @throws IOException if the stream has been closed by 297 * invoking its {@link #close()} method, 298 * {@code in.skip(n)} throws an IOException, 299 * or an I/O error occurs. 300 * @see java.io.FilterInputStream#in 301 * @see java.io.InputStream#skip(long n) 302 * @since 1.2 303 */ 304 public long skip(long n) throws IOException { 305 ensureOpen(); 306 if (n <= 0) { 307 return 0; 308 } 309 310 long pskip = buf.length - pos; 311 if (pskip > 0) { 312 if (n < pskip) { 313 pskip = n; 314 } 315 pos += pskip; 316 n -= pskip; 317 } 318 if (n > 0) { 319 pskip += super.skip(n); 320 } 321 return pskip; 322 } 323 324 /** 325 * Tests if this input stream supports the {@code mark} and 326 * {@code reset} methods, which it does not. 327 * 328 * @return {@code false}, since this class does not support the 329 * {@code mark} and {@code reset} methods. 330 * @see java.io.InputStream#mark(int) 331 * @see java.io.InputStream#reset() 332 */ 333 public boolean markSupported() { 334 return false; 335 } 336 337 /** 338 * Marks the current position in this input stream. 339 * 340 * <p> The {@code mark} method of {@code PushbackInputStream} 341 * does nothing. 342 * 343 * @param readlimit the maximum limit of bytes that can be read before 344 * the mark position becomes invalid. 345 * @see java.io.InputStream#reset() 346 */ 347 public synchronized void mark(int readlimit) { 348 } 349 350 /** 351 * Repositions this stream to the position at the time the 352 * {@code mark} method was last called on this input stream. 353 * 354 * <p> The method {@code reset} for class 355 * {@code PushbackInputStream} does nothing except throw an 356 * {@code IOException}. 357 * 358 * @throws IOException if this method is invoked. 359 * @see java.io.InputStream#mark(int) 360 * @see java.io.IOException 361 */ 362 public synchronized void reset() throws IOException { 363 throw new IOException("mark/reset not supported"); 364 } 365 366 /** 367 * Closes this input stream and releases any system resources 368 * associated with the stream. 369 * Once the stream has been closed, further read(), unread(), 370 * available(), reset(), or skip() invocations will throw an IOException. 371 * Closing a previously closed stream has no effect. 372 * 373 * @throws IOException if an I/O error occurs. 374 */ 375 public synchronized void close() throws IOException { 376 if (in == null) 377 return; 378 in.close(); 379 in = null; 380 buf = null; 381 } 382 } |