--- old/src/java.base/share/classes/java/io/InputStream.java 2018-01-17 08:15:49.000000000 -0800 +++ new/src/java.base/share/classes/java/io/InputStream.java 2018-01-17 08:15:48.000000000 -0800 @@ -63,7 +63,8 @@ * *

While the stream is open, the {@code available()}, {@code read()}, * {@code read(byte[])}, {@code read(byte[], int, int)}, - * {@code readAllBytes()}, {@code readNBytes()}, {@code skip()}, and + * {@code readAllBytes()}, {@code readNBytes(byte[], int, int)}, + * {@code readNBytes(int)}, {@code skip()}, and * {@code transferTo()} methods all behave as if end of stream has been * reached. After the stream has been closed, these methods all throw * {@code IOException}. @@ -123,6 +124,16 @@ } @Override + public byte[] readNBytes(int len) + throws IOException { + if (len < 0) { + throw new IllegalArgumentException("len < 0"); + } + ensureOpen(); + return new byte[0]; + } + + @Override public long skip(long n) throws IOException { ensureOpen(); return 0L; @@ -233,8 +244,8 @@ * b and the number of bytes read before the exception * occurred is returned. The default implementation of this method blocks * until the requested amount of input data len has been read, - * end of file is detected, or an exception is thrown. Subclasses are encouraged - * to provide a more efficient implementation of this method. + * end of file is detected, or an exception is thrown. Subclasses are + * encouraged to provide a more efficient implementation of this method. * * @param b the buffer into which the data is read. * @param off the start offset in array b @@ -287,16 +298,22 @@ private static final int MAX_BUFFER_SIZE = Integer.MAX_VALUE - 8; /** - * Reads all remaining bytes from the input stream. This method blocks until - * all remaining bytes have been read and end of stream is detected, or an - * exception is thrown. This method does not close the input stream. + * Reads a number of bytes from the input stream. The number of bytes to + * read is specified by the {@code len} parameter which is interpreted as + * an inclusive upper bound on the number to read. This method blocks + * until the requested number of bytes have been read, end of stream is + * detected, or an exception is thrown. This method does not close the + * input stream. + * + *

If {@code len} is zero, then no bytes are read and an empty byte + * array is returned. * *

When this stream reaches end of stream, further invocations of this * method will return an empty byte array. * *

Note that this method is intended for simple cases where it is - * convenient to read all bytes into a byte array. It is not intended for - * reading input streams with large amounts of data. + * convenient to read the specified number of bytes into a byte array. It + * is not intended for reading large amounts of data. * *

The behavior for the case where the input stream is asynchronously * closed, or the thread interrupted during the read, is highly input @@ -308,26 +325,36 @@ * It is strongly recommended that the stream be promptly closed if an I/O * error occurs. * + * @param len the maximum number of bytes to read * @return a byte array containing the bytes read from this input stream + * @throws IllegalArgumentException if {@code len} is negative * @throws IOException if an I/O error occurs * @throws OutOfMemoryError if an array of the required size cannot be * allocated. For example, if an array larger than {@code 2GB} would * be required to store the bytes. * - * @since 9 + * @since 11 */ - public byte[] readAllBytes() throws IOException { + private byte[] readAtMostNBytes(int len) + throws IOException { + if (len < 0) { + throw new IllegalArgumentException("len < 0"); + } + List bufs = null; byte[] result = null; int total = 0; + int remaining = len; int n; do { - byte[] buf = new byte[DEFAULT_BUFFER_SIZE]; + byte[] buf = new byte[Math.min(len, DEFAULT_BUFFER_SIZE)]; int nread = 0; // read to EOF which may read more or less than buffer size - while ((n = read(buf, nread, buf.length - nread)) > 0) { + while ((n = read(buf, nread, + Math.min(buf.length - nread, remaining))) > 0) { nread += n; + remaining -= n; } if (nread > 0) { @@ -345,7 +372,9 @@ bufs.add(buf); } } - } while (n >= 0); // if the last call to read returned -1, then break + // if the last call to read returned -1 or the number of bytes + // requested have been read then break + } while (n >= 0 && remaining > 0); if (bufs == null) { if (result == null) { @@ -357,18 +386,95 @@ result = new byte[total]; int offset = 0; - int remaining = total; + remaining = total; for (byte[] b : bufs) { - int len = Math.min(b.length, remaining); - System.arraycopy(b, 0, result, offset, len); - offset += len; - remaining -= len; + int count = Math.min(b.length, remaining); + System.arraycopy(b, 0, result, offset, count); + offset += count; + remaining -= count; } return result; } /** + * Reads all remaining bytes from the input stream. This method blocks until + * all remaining bytes have been read and end of stream is detected, or an + * exception is thrown. This method does not close the input stream. + * + *

When this stream reaches end of stream, further invocations of this + * method will return an empty byte array. + * + *

Note that this method is intended for simple cases where it is + * convenient to read all bytes into a byte array. It is not intended for + * reading input streams with large amounts of data. + * + *

The behavior for the case where the input stream is asynchronously + * closed, or the thread interrupted during the read, is highly input + * stream specific, and therefore not specified. + * + *

If an I/O error occurs reading from the input stream, then it may do + * so after some, but not all, bytes have been read. Consequently the input + * stream may not be at end of stream and may be in an inconsistent state. + * It is strongly recommended that the stream be promptly closed if an I/O + * error occurs. + * + * @return a byte array containing the bytes read from this input stream + * @throws IOException if an I/O error occurs + * @throws OutOfMemoryError if an array of the required size cannot be + * allocated. For example, if an array larger than {@code 2GB} would + * be required to store the bytes. + * + * @since 9 + */ + public byte[] readAllBytes() throws IOException { + return readAtMostNBytes(Integer.MAX_VALUE); + } + + /** + * Reads up to a specified number of bytes from the input stream. This + * method blocks until the requested number of bytes have been read, end + * of stream is detected, or an exception is thrown. This method does not + * close the input stream. + * + *

The length of the returned array equals the number of bytes read + * from the stream. If {@code len} is zero, then no bytes are read and + * an empty byte array is returned. Otherwise, up to {@code len} bytes + * are read from the stream. Fewer than {@code len} bytes may be read if + * end of stream is encountered. + * + *

When this stream reaches end of stream, further invocations of this + * method will return an empty byte array. + * + *

Note that this method is intended for simple cases where it is + * convenient to read the specified number of bytes into a byte array. It + * is not intended for reading large amounts of data. + * + *

The behavior for the case where the input stream is asynchronously + * closed, or the thread interrupted during the read, is highly input + * stream specific, and therefore not specified. + * + *

If an I/O error occurs reading from the input stream, then it may do + * so after some, but not all, bytes have been read. Consequently the input + * stream may not be at end of stream and may be in an inconsistent state. + * It is strongly recommended that the stream be promptly closed if an I/O + * error occurs. + * + * @param len the maximum number of bytes to read + * @return a byte array containing the bytes read from this input stream + * @throws IllegalArgumentException if {@code length} is negative + * @throws IOException if an I/O error occurs + * @throws OutOfMemoryError if an array of the required size cannot be + * allocated. For example, if an array larger than {@code 2GB} would + * be required to store the bytes. + * + * @since 11 + */ + public byte[] readNBytes(int len) throws IOException { + return readAtMostNBytes(len); + } + + /** * Reads the requested number of bytes from the input stream into the given * byte array. This method blocks until {@code len} bytes of input data have * been read, end of stream is detected, or an exception is thrown. The