org.eclipse.mat.parser.io.BitOutputStream Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of haha Show documentation
Show all versions of haha Show documentation
Java library to automate the analysis of Android heap dumps.
/**
* ****************************************************************************
* Copyright (c) 2008 SAP AG.
* All rights reserved. This program and the accompanying materials
* are made available under the terms of the Eclipse Public License v1.0
* which accompanies this distribution, and is available at
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* SAP AG - initial API and implementation
* *****************************************************************************
*/
package org.eclipse.mat.parser.io;
import java.io.Closeable;
import java.io.Flushable;
import java.io.IOException;
import java.io.OutputStream;
import org.eclipse.mat.hprof.Messages;
public class BitOutputStream implements Flushable, Closeable {
public final static int DEFAULT_BUFFER_SIZE = 16 * 1024;
private OutputStream os;
private int current;
private byte[] buffer;
private int free;
private int pos;
private int avail;
final static int TEMP_BUFFER_SIZE = 128;
private byte[] tempBuffer = new byte[TEMP_BUFFER_SIZE];
public BitOutputStream(final OutputStream os) {
this.os = os;
this.buffer = new byte[DEFAULT_BUFFER_SIZE];
avail = DEFAULT_BUFFER_SIZE;
free = 8;
}
public void flush() throws IOException {
align();
os.write(buffer, 0, pos);
pos = 0;
avail = buffer.length;
os.flush();
}
public void close() throws IOException {
flush();
os.close();
os = null;
buffer = null;
tempBuffer = null;
}
private void write(final int b) throws IOException {
if (avail-- == 0) {
if (os == null) {
avail = 0;
throw new IOException(Messages.BitOutputStream_Error_ArrayFull.pattern);
}
if (buffer == null) {
os.write(b);
avail = 0;
return;
}
os.write(buffer);
avail = buffer.length - 1;
pos = 0;
}
buffer[pos++] = (byte) b;
}
private int writeInCurrent(final int b, final int len) throws IOException {
current |= (b & ((1 << len) - 1)) << (free -= len);
if (free == 0) {
write(current);
free = 8;
current = 0;
}
return len;
}
private int align() throws IOException {
if (free != 8) {
return writeInCurrent(0, free);
} else {
return 0;
}
}
public int writeBit(final int bit) throws IOException {
return writeInCurrent(bit, 1);
}
public int writeInt(int x, final int len) throws IOException {
if (len <= free) return writeInCurrent(x, len);
final int queue = (len - free) & 7, blocks = (len - free) >> 3;
int i = blocks;
if (queue != 0) {
tempBuffer[blocks] = (byte) x;
x >>= queue;
}
while (i-- != 0) {
tempBuffer[i] = (byte) x;
x >>>= 8;
}
writeInCurrent(x, free);
for (i = 0; i < blocks; i++)
write(tempBuffer[i]);
if (queue != 0) writeInCurrent(tempBuffer[blocks], queue);
return len;
}
}