--- old/src/java.base/share/classes/java/lang/String.java 2014-09-14 16:37:10.716014834 +0100 +++ new/src/java.base/share/classes/java/lang/String.java 2014-09-14 16:37:10.604014839 +0100 @@ -28,6 +28,7 @@ import java.io.ObjectStreamField; import java.io.UnsupportedEncodingException; import java.nio.charset.Charset; +import java.nio.ByteBuffer; import java.util.ArrayList; import java.util.Arrays; import java.util.Comparator; @@ -360,16 +361,24 @@ this(ascii, hibyte, 0, ascii.length); } + private static void checkBounds(byte[] bytes, int offset, int length) { + checkBounds(bytes.length, offset, length); + } + + private static void checkBounds(ByteBuffer bytes, int offset, int length) { + checkBounds(bytes.capacity(), offset, length); + } + /* Common private utility method used to bounds check the byte array * and requested offset & length values used by the String(byte[],..) * constructors. */ - private static void checkBounds(byte[] bytes, int offset, int length) { + private static void checkBounds(int lengthOfBuffer, int offset, int length) { if (length < 0) throw new StringIndexOutOfBoundsException(length); if (offset < 0) throw new StringIndexOutOfBoundsException(offset); - if (offset > bytes.length - length) + if (offset > lengthOfBuffer - length) throw new StringIndexOutOfBoundsException(offset + length); } @@ -448,7 +457,45 @@ if (charset == null) throw new NullPointerException("charset"); checkBounds(bytes, offset, length); - this.value = StringCoding.decode(charset, bytes, offset, length); + this.value = StringCoding.decode(charset, bytes, offset, length); + } + + /** + * Constructs a new {@code String} by decoding the specified + * {@linkplain java.nio.ByteBuffer byte buffer} using the specified + * {@linkplain java.nio.charset.Charset charset}. + * The length of the new {@code String} is a function of the charset, and + * hence may not be equal to the length of the subarray. + * + *

This method always replaces malformed-input and unmappable-character + * sequences with this charset's default replacement string. The {@link + * java.nio.charset.CharsetDecoder} class should be used when more control + * over the decoding process is required. + * + * @param bytes + * The bytes to be decoded into characters + * + * @param offset + * The index of the first byte to decode + * + * @param length + * The number of bytes to decode + * + * @param charset + * The {@linkplain java.nio.charset.Charset charset} to be used to + * decode the {@code bytes} + * + * @throws IndexOutOfBoundsException + * If the {@code offset} and {@code length} arguments index + * characters outside the bounds of the {@code bytes} array + * + * @since 1.9 + */ + public String(ByteBuffer bytes, int offset, int length, Charset charset) { + if (charset == null) + throw new NullPointerException("charset"); + checkBounds(bytes, offset, length); + this.value = StringCoding.decode(charset, bytes, offset, length); } /** @@ -925,9 +972,59 @@ * @since 1.6 */ public byte[] getBytes(Charset charset) { - if (charset == null) throw new NullPointerException(); + Objects.requireNonNull(charset); return StringCoding.encode(charset, value, 0, value.length); } + + /** + *

Encodes this {@code String} into a sequence of bytes using the given + * {@linkplain java.nio.charset.Charset charset}, storing the result into a + * byte array that has been passed as an argument. + * + * @param destBuffer + * The destination array + * + * @param destOffset + * The start offset in the destination array + * + * @param charset + * The {@linkplain java.nio.charset.Charset} to be used to encode + * the {@code String} + * + * @return the number of bytes copied + * + * @since 1.9 + */ + public int getBytes(final byte[] destBuffer, final int destOffset, final Charset charset) { + Objects.requireNonNull(destBuffer); + Objects.requireNonNull(charset); + return StringCoding.encode(charset, value, 0, value.length, destBuffer, destOffset); + } + + /** + *

Encodes this {@code String} into a sequence of bytes using the given + * {@linkplain java.nio.charset.Charset charset}, storing the result into a + * {@linkplain java.nio.ByteBuffer byte buffer} that has been passed as an argument. + * + * @param destBuffer + * The destination {@linkplain java.nio.ByteBuffer} + * + * @param destOffset + * The start offset in the destination array + * + * @param charset + * The {@linkplain java.nio.charset.Charset} to be used to encode + * the {@code String} + * + * @return the number of bytes copied + * + * @since 1.9 + */ + public int getBytes(final ByteBuffer destBuffer, final int destOffset, final Charset charset) { + Objects.requireNonNull(destBuffer); + Objects.requireNonNull(charset); + return StringCoding.encode(charset, value, 0, value.length, destBuffer, destOffset); + } /** * Encodes this {@code String} into a sequence of bytes using the