HBASE-23892 SecureTestCluster should allow its subclasses to pass their Class referen...
[hbase.git] / hbase-common / src / main / java / org / apache / hadoop / hbase / io / ByteArrayOutputStream.java
blob77dd3b82c425b0a4e1d9b45ea43786bc2e69ae02
1 /**
2 * Licensed to the Apache Software Foundation (ASF) under one
3 * or more contributor license agreements. See the NOTICE file
4 * distributed with this work for additional information
5 * regarding copyright ownership. The ASF licenses this file
6 * to you under the Apache License, Version 2.0 (the
7 * "License"); you may not use this file except in compliance
8 * with the License. You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
18 package org.apache.hadoop.hbase.io;
20 import java.io.OutputStream;
21 import java.nio.BufferOverflowException;
22 import java.nio.ByteBuffer;
23 import java.util.Arrays;
25 import org.apache.hadoop.hbase.nio.ByteBuff;
26 import org.apache.hadoop.hbase.util.ByteBufferUtils;
27 import org.apache.hadoop.hbase.util.Bytes;
28 import org.apache.yetus.audience.InterfaceAudience;
30 /**
31 * Our own implementation of ByteArrayOutputStream where all methods are NOT synchronized and
32 * supports writing ByteBuffer directly to it.
34 @InterfaceAudience.Private
35 public class ByteArrayOutputStream extends OutputStream implements ByteBufferWriter {
37 // Borrowed from openJDK:
38 // http://grepcode.com/file/repository.grepcode.com/java/root/jdk/openjdk/8-b132/java/util/ArrayList.java#221
39 private static final int MAX_ARRAY_SIZE = Integer.MAX_VALUE - 8;
41 private byte[] buf;
42 private int pos = 0;
44 public ByteArrayOutputStream() {
45 this(32);
48 public ByteArrayOutputStream(int capacity) {
49 this.buf = new byte[capacity];
52 @Override
53 public void write(ByteBuffer b, int off, int len) {
54 checkSizeAndGrow(len);
55 ByteBufferUtils.copyFromBufferToArray(this.buf, b, off, this.pos, len);
56 this.pos += len;
59 @Override
60 public void writeInt(int i) {
61 checkSizeAndGrow(Bytes.SIZEOF_INT);
62 Bytes.putInt(this.buf, this.pos, i);
63 this.pos += Bytes.SIZEOF_INT;
66 @Override
67 public void write(int b) {
68 checkSizeAndGrow(Bytes.SIZEOF_BYTE);
69 buf[this.pos] = (byte) b;
70 this.pos++;
73 @Override
74 public void write(byte[] b, int off, int len) {
75 checkSizeAndGrow(len);
76 System.arraycopy(b, off, this.buf, this.pos, len);
77 this.pos += len;
80 private void checkSizeAndGrow(int extra) {
81 long capacityNeeded = this.pos + (long) extra;
82 if (capacityNeeded > this.buf.length) {
83 // guarantee it's possible to fit
84 if (capacityNeeded > MAX_ARRAY_SIZE) {
85 throw new BufferOverflowException();
87 // double until hit the cap
88 long nextCapacity = Math.min(this.buf.length << 1, MAX_ARRAY_SIZE);
89 // but make sure there is enough if twice the existing capacity is still too small
90 nextCapacity = Math.max(nextCapacity, capacityNeeded);
91 if (nextCapacity > MAX_ARRAY_SIZE) {
92 throw new BufferOverflowException();
94 byte[] newBuf = new byte[(int) nextCapacity];
95 System.arraycopy(buf, 0, newBuf, 0, buf.length);
96 buf = newBuf;
101 * Resets the <code>pos</code> field of this byte array output stream to zero. The output stream
102 * can be used again.
104 public void reset() {
105 this.pos = 0;
109 * Copies the content of this Stream into a new byte array.
110 * @return the contents of this output stream, as new byte array.
112 public byte[] toByteArray() {
113 return Arrays.copyOf(buf, pos);
116 public void toByteBuff(ByteBuff buff) {
117 buff.put(buf, 0, pos);
121 * @return the underlying array where the data gets accumulated
123 public byte[] getBuffer() {
124 return this.buf;
128 * @return The current size of the buffer.
130 public int size() {
131 return this.pos;