001    /** 
002     * 
003     * Copyright 2004 Protique Ltd
004     * 
005     * Licensed under the Apache License, Version 2.0 (the "License"); 
006     * you may not use this file except in compliance with the License. 
007     * You may obtain a copy of the License at 
008     * 
009     * http://www.apache.org/licenses/LICENSE-2.0
010     * 
011     * Unless required by applicable law or agreed to in writing, software
012     * distributed under the License is distributed on an "AS IS" BASIS, 
013     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
014     * See the License for the specific language governing permissions and 
015     * limitations under the License. 
016     * 
017     **/
018    
019    package org.activemq.io.util;
020    import java.io.ByteArrayOutputStream;
021    
022    /**
023     * Optimized ByteArrayOutputStream
024     * 
025     * @version $Revision: 1.1.1.1 $
026     */
027    public class WireByteArrayOutputStream extends ByteArrayOutputStream {
028        /**
029         * Creates a new byte array output stream. The buffer capacity is initially 32 bytes, though its size increases if
030         * necessary.
031         */
032        public WireByteArrayOutputStream() {
033            super(32);
034        }
035    
036        /**
037         * Creates a new byte array output stream, with a buffer capacity of the specified size, in bytes.
038         * 
039         * @param size the initial size.
040         * @exception IllegalArgumentException if size is negative.
041         */
042        public WireByteArrayOutputStream(int size) {
043            super(size);
044        }
045    
046        /**
047         * start using a fresh byte array
048         * 
049         * @param size
050         */
051        public void restart(int size) {
052            buf = new byte[size];
053            count = 0;
054        }
055    
056        /**
057         * start using a fresh byte array
058         */
059        public void restart() {
060            restart(32);
061        }
062    
063        /**
064         * Writes the specified byte to this byte array output stream.
065         * 
066         * @param b the byte to be written.
067         */
068        public void write(int b) {
069            int newcount = count + 1;
070            if (newcount > buf.length) {
071                byte newbuf[] = new byte[Math.max(buf.length << 1, newcount)];
072                System.arraycopy(buf, 0, newbuf, 0, count);
073                buf = newbuf;
074            }
075            buf[count] = (byte) b;
076            count = newcount;
077        }
078    
079        /**
080         * Writes <code>len</code> bytes from the specified byte array starting at offset <code>off</code> to this byte
081         * array output stream.
082         * 
083         * @param b the data.
084         * @param off the start offset in the data.
085         * @param len the number of bytes to write.
086         */
087        public void write(byte b[], int off, int len) {
088            if ((off < 0) || (off > b.length) || (len < 0) || ((off + len) > b.length) || ((off + len) < 0)) {
089                throw new IndexOutOfBoundsException();
090            }
091            else if (len == 0) {
092                return;
093            }
094            int newcount = count + len;
095            if (newcount > buf.length) {
096                byte newbuf[] = new byte[Math.max(buf.length << 1, newcount)];
097                System.arraycopy(buf, 0, newbuf, 0, count);
098                buf = newbuf;
099            }
100            System.arraycopy(b, off, buf, count, len);
101            count = newcount;
102        }
103    
104        /**
105         * @return the underlying byte[] buffer
106         */
107        public byte[] getData() {
108            return buf;
109        }
110        
111        /**
112         * reset the output stream
113         */
114        public void reset(){
115            count = 0;
116        }
117    }