see also https://github.com/yacy/yacy_search_server/issues/491pull/594/head
parent
ff8fe7b6a4
commit
4a5820eb03
@ -1,2 +0,0 @@
|
|||||||
/build/
|
|
||||||
/dist/
|
|
@ -1,39 +0,0 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
|
||||||
<project name="J7Zip-modified" default="dist" basedir=".">
|
|
||||||
<description>
|
|
||||||
J7Zip library for YaCy sevenzipParser (not available in external repositories)
|
|
||||||
</description>
|
|
||||||
<!-- set global properties for this build -->
|
|
||||||
<property name="version" value="1.0.2" />
|
|
||||||
<property name="src" location="src"/>
|
|
||||||
<property name="build" location="build"/>
|
|
||||||
<property name="dist" location="dist"/>
|
|
||||||
|
|
||||||
<target name="init">
|
|
||||||
<loadproperties srcFile="../../build.properties" />
|
|
||||||
<!-- Create the build directory structure used by compile -->
|
|
||||||
<mkdir dir="${build}"/>
|
|
||||||
</target>
|
|
||||||
|
|
||||||
<target name="compile" depends="init"
|
|
||||||
description="compile the source">
|
|
||||||
<!-- Compile the Java code from ${src} into ${build} -->
|
|
||||||
<javac srcdir="${src}" destdir="${build}"/>
|
|
||||||
</target>
|
|
||||||
|
|
||||||
<target name="dist" depends="compile"
|
|
||||||
description="generate the distribution">
|
|
||||||
<!-- Create the distribution directory -->
|
|
||||||
<mkdir dir="${dist}"/>
|
|
||||||
|
|
||||||
<!-- Put everything in ${build} into the jar file -->
|
|
||||||
<jar jarfile="${dist}/J7Zip-modified-${version}.jar" basedir="${build}"/>
|
|
||||||
</target>
|
|
||||||
|
|
||||||
<target name="clean"
|
|
||||||
description="clean up">
|
|
||||||
<!-- Delete the ${build} and ${dist} directory trees -->
|
|
||||||
<delete dir="${build}"/>
|
|
||||||
<delete dir="${dist}"/>
|
|
||||||
</target>
|
|
||||||
</project>
|
|
@ -1,101 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
import java.util.Collection;
|
|
||||||
import java.util.Iterator;
|
|
||||||
|
|
||||||
public class BoolVector {
|
|
||||||
|
|
||||||
protected boolean[] data;
|
|
||||||
int capacityIncr = 10;
|
|
||||||
int elt = 0;
|
|
||||||
|
|
||||||
public BoolVector() {
|
|
||||||
this.data = new boolean[10];
|
|
||||||
}
|
|
||||||
|
|
||||||
public BoolVector(int size) {
|
|
||||||
this.data = new boolean[size];
|
|
||||||
}
|
|
||||||
|
|
||||||
public int size() {
|
|
||||||
return elt;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ensureAdditionalCapacity(int addCapacity) {
|
|
||||||
ensureCapacity(data.length + addCapacity);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ensureCapacity(int minCapacity) {
|
|
||||||
int oldCapacity = data.length;
|
|
||||||
if (minCapacity > oldCapacity) {
|
|
||||||
boolean [] oldData = data;
|
|
||||||
int newCapacity = oldCapacity + capacityIncr;
|
|
||||||
if (newCapacity < minCapacity) {
|
|
||||||
newCapacity = minCapacity;
|
|
||||||
}
|
|
||||||
data = new boolean[newCapacity];
|
|
||||||
System.arraycopy(oldData, 0, data, 0, elt);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean get(int index) {
|
|
||||||
if (index >= elt)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
|
|
||||||
return data[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Reserve(int s) {
|
|
||||||
ensureCapacity(s);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void add(boolean b) {
|
|
||||||
ensureCapacity(elt + 1);
|
|
||||||
data[elt++] = b;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addAll(Collection c) {
|
|
||||||
ensureCapacity(elt + c.size());
|
|
||||||
Iterator it = c.iterator();
|
|
||||||
while (it.hasNext())
|
|
||||||
data[elt++] = ((Boolean)it.next()).booleanValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addAll(Boolean[] b) {
|
|
||||||
ensureCapacity(elt + b.length);
|
|
||||||
for (int i=0; i<b.length; i++)
|
|
||||||
data[elt++] = ((Boolean)b[i]).booleanValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void set(int index, boolean value) {
|
|
||||||
if (index >= data.length)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
data[index] = value;
|
|
||||||
elt = index + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setRange(int start, boolean value) {
|
|
||||||
setRange(start, data.length - start, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setRange(int start, int length, boolean value) {
|
|
||||||
if (start + length > data.length)
|
|
||||||
throw new ArrayIndexOutOfBoundsException("start = " + start + ", length = " + length);
|
|
||||||
for (int i=0; i<length; i++)
|
|
||||||
data[start + i] = value;
|
|
||||||
elt = start + length;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setBoolVector(BoolVector v) {
|
|
||||||
this.data = v.data;
|
|
||||||
this.elt = v.elt;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void clear() {
|
|
||||||
elt = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isEmpty() {
|
|
||||||
return elt == 0;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,71 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
public class CRC {
|
|
||||||
public static final int[] Table = new int[256];
|
|
||||||
|
|
||||||
static {
|
|
||||||
for (int i = 0; i < 256; i++) {
|
|
||||||
int r = i;
|
|
||||||
for (int j = 0; j < 8; j++) {
|
|
||||||
if ((r & 1) != 0)
|
|
||||||
r = (r >>> 1) ^ 0xEDB88320;
|
|
||||||
else
|
|
||||||
r >>>= 1;
|
|
||||||
}
|
|
||||||
Table[i] = r;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int _value = -1;
|
|
||||||
|
|
||||||
public void Init() {
|
|
||||||
_value = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UpdateByte(int b) {
|
|
||||||
_value = Table[(_value ^ b) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UpdateUInt32(int v) {
|
|
||||||
for (int i = 0; i < 4; i++)
|
|
||||||
UpdateByte((v >> (8 * i)) & 0xFF );
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UpdateUInt64(long v) {
|
|
||||||
for (int i = 0; i < 8; i++)
|
|
||||||
UpdateByte((int)((v >> (8 * i))) & 0xFF);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetDigest() {
|
|
||||||
return _value ^ (-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Update(byte[] data, int size) {
|
|
||||||
for (int i = 0; i < size; i++)
|
|
||||||
_value = Table[(_value ^ data[i]) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Update(byte[] data) {
|
|
||||||
for (int i = 0; i < data.length; i++)
|
|
||||||
_value = Table[(_value ^ data[i]) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Update(byte[] data, int offset, int size) {
|
|
||||||
for (int i = 0; i < size; i++)
|
|
||||||
_value = Table[(_value ^ data[offset + i]) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int CalculateDigest(byte [] data, int size) {
|
|
||||||
CRC crc = new CRC();
|
|
||||||
crc.Update(data, size);
|
|
||||||
return crc.GetDigest();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static boolean VerifyDigest(int digest, byte [] data, int size) {
|
|
||||||
return (CalculateDigest(data, size) == digest);
|
|
||||||
}
|
|
||||||
|
|
||||||
public String toString() {
|
|
||||||
return Integer.toHexString(GetDigest());
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,129 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
import java.util.Collection;
|
|
||||||
import java.util.Iterator;
|
|
||||||
|
|
||||||
public class IntVector {
|
|
||||||
protected int[] data = new int[10];
|
|
||||||
int capacityIncr = 10;
|
|
||||||
int elt = 0;
|
|
||||||
|
|
||||||
public IntVector() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public IntVector(int size) {
|
|
||||||
this.data = new int[size];
|
|
||||||
}
|
|
||||||
|
|
||||||
public int size() {
|
|
||||||
return elt;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ensureAdditionalCapacity(int addCapacity) {
|
|
||||||
ensureCapacity(data.length + addCapacity);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ensureCapacity(int minCapacity) {
|
|
||||||
int oldCapacity = data.length;
|
|
||||||
if (minCapacity > oldCapacity) {
|
|
||||||
int [] oldData = data;
|
|
||||||
int newCapacity = oldCapacity + capacityIncr;
|
|
||||||
if (newCapacity < minCapacity) {
|
|
||||||
newCapacity = minCapacity;
|
|
||||||
}
|
|
||||||
data = new int[newCapacity];
|
|
||||||
System.arraycopy(oldData, 0, data, 0, elt);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int get(int index) {
|
|
||||||
if (index >= elt)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
|
|
||||||
return data[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Reserve(int s) {
|
|
||||||
ensureCapacity(s);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void add(int b) {
|
|
||||||
ensureCapacity(elt + 1);
|
|
||||||
data[elt++] = b;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addAll(Collection c) {
|
|
||||||
ensureCapacity(elt + c.size());
|
|
||||||
Iterator it = c.iterator();
|
|
||||||
while (it.hasNext())
|
|
||||||
data[elt++] = ((Integer)it.next()).intValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addAll(Integer[] b) {
|
|
||||||
ensureCapacity(elt + b.length);
|
|
||||||
for (int i=0; i<b.length; i++)
|
|
||||||
data[elt++] = ((Integer)b[i]).intValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void set(int index, int value) {
|
|
||||||
if (index >= data.length)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
data[index] = value;
|
|
||||||
elt = index + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setRange(int start, int value) {
|
|
||||||
setRange(start, data.length - start, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setRange(int start, int length, int value) {
|
|
||||||
if (start + length > data.length)
|
|
||||||
throw new ArrayIndexOutOfBoundsException("start = " + start + ", length = " + length);
|
|
||||||
for (int i=0; i<length; i++)
|
|
||||||
data[start + i] = value;
|
|
||||||
elt = start + length;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void clear() {
|
|
||||||
elt = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isEmpty() {
|
|
||||||
return elt == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int Back() {
|
|
||||||
if (elt < 1)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(0);
|
|
||||||
|
|
||||||
return data[elt-1];
|
|
||||||
}
|
|
||||||
|
|
||||||
public int Front() {
|
|
||||||
if (elt < 1)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(0);
|
|
||||||
|
|
||||||
return data[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void DeleteBack() {
|
|
||||||
// Delete(_size - 1);
|
|
||||||
remove(elt-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int remove(int index) {
|
|
||||||
if (index >= elt)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
int oldValue = data[index];
|
|
||||||
|
|
||||||
int numMoved = elt - index - 1;
|
|
||||||
Integer n = Integer.valueOf(elt);
|
|
||||||
if (numMoved > 0)
|
|
||||||
System.arraycopy(n, index+1, n, index,numMoved);
|
|
||||||
elt = n.intValue();
|
|
||||||
// data[--elt] = null; // Let gc do its work
|
|
||||||
|
|
||||||
return oldValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,54 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
import java.io.InputStream;
|
|
||||||
|
|
||||||
public class LimitedSequentialInStream extends InputStream {
|
|
||||||
final InputStream _stream; // ISequentialInStream
|
|
||||||
final long _size;
|
|
||||||
long _pos;
|
|
||||||
boolean _wasFinished;
|
|
||||||
|
|
||||||
public LimitedSequentialInStream(InputStream stream, long streamSize) {
|
|
||||||
_stream = stream;
|
|
||||||
_size = streamSize;
|
|
||||||
_pos = 0;
|
|
||||||
_wasFinished = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
public void SetStream(InputStream stream) { // ISequentialInStream
|
|
||||||
_stream = stream;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Init(long streamSize) {
|
|
||||||
_size = streamSize;
|
|
||||||
_pos = 0;
|
|
||||||
_wasFinished = false;
|
|
||||||
}*/
|
|
||||||
|
|
||||||
public int read() throws java.io.IOException {
|
|
||||||
int ret = _stream.read();
|
|
||||||
if (ret == -1) _wasFinished = true;
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read(byte [] data,int off, int size) throws java.io.IOException {
|
|
||||||
long sizeToRead2 = (_size - _pos);
|
|
||||||
if (size < sizeToRead2) sizeToRead2 = size;
|
|
||||||
|
|
||||||
int sizeToRead = (int)sizeToRead2;
|
|
||||||
|
|
||||||
if (sizeToRead > 0) {
|
|
||||||
int realProcessedSize = _stream.read(data, off, sizeToRead);
|
|
||||||
if (realProcessedSize == -1) {
|
|
||||||
_wasFinished = true;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
_pos += realProcessedSize;
|
|
||||||
return realProcessedSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
return -1; // EOF
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,38 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import SevenZip.IInStream;
|
|
||||||
|
|
||||||
public class LockedInStream {
|
|
||||||
|
|
||||||
final IInStream _stream;
|
|
||||||
|
|
||||||
public LockedInStream(IInStream stream) {
|
|
||||||
this._stream = stream;
|
|
||||||
}
|
|
||||||
/*
|
|
||||||
public void Init(IInStream stream) {
|
|
||||||
_stream = stream;
|
|
||||||
}*/
|
|
||||||
|
|
||||||
/* really too slow, don't use !
|
|
||||||
public synchronized int read(long startPos) throws java.io.IOException
|
|
||||||
{
|
|
||||||
// NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
|
|
||||||
_stream.Seek(startPos, IInStream.STREAM_SEEK_SET);
|
|
||||||
return _stream.read();
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
public synchronized int read(long startPos, byte [] data, int size) throws IOException {
|
|
||||||
// NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
|
|
||||||
_stream.Seek(startPos, IInStream.STREAM_SEEK_SET);
|
|
||||||
return _stream.read(data,0, size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public synchronized int read(long startPos, byte [] data, int off, int size) throws IOException {
|
|
||||||
// NWindows::NSynchronization::CCriticalSectionLock lock(_criticalSection);
|
|
||||||
_stream.Seek(startPos, IInStream.STREAM_SEEK_SET);
|
|
||||||
return _stream.read(data,off, size);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,41 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
import java.io.InputStream;
|
|
||||||
|
|
||||||
public class LockedSequentialInStreamImp extends InputStream {
|
|
||||||
final LockedInStream _lockedInStream;
|
|
||||||
long _pos;
|
|
||||||
|
|
||||||
public LockedSequentialInStreamImp(LockedInStream lockedInStream, long startPos) {
|
|
||||||
_lockedInStream = lockedInStream;
|
|
||||||
_pos = startPos;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
public void Init(LockedInStream lockedInStream, long startPos) {
|
|
||||||
_lockedInStream = lockedInStream;
|
|
||||||
_pos = startPos;
|
|
||||||
}*/
|
|
||||||
|
|
||||||
public int read() throws java.io.IOException {
|
|
||||||
throw new java.io.IOException("LockedSequentialInStreamImp : read() not implemented");
|
|
||||||
/*
|
|
||||||
int ret = _lockedInStream.read(_pos);
|
|
||||||
if (ret == -1) return -1; // EOF
|
|
||||||
|
|
||||||
_pos += 1;
|
|
||||||
|
|
||||||
return ret;
|
|
||||||
*/
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read(byte [] data, int off, int size) throws java.io.IOException {
|
|
||||||
int realProcessedSize = _lockedInStream.read(_pos, data,off, size);
|
|
||||||
if (realProcessedSize == -1) return -1; // EOF
|
|
||||||
|
|
||||||
_pos += realProcessedSize;
|
|
||||||
|
|
||||||
return realProcessedSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,126 +0,0 @@
|
|||||||
package Common;
|
|
||||||
|
|
||||||
import java.util.Collection;
|
|
||||||
import java.util.Iterator;
|
|
||||||
|
|
||||||
public class LongVector {
|
|
||||||
protected long[] data = new long[10];
|
|
||||||
int capacityIncr = 10;
|
|
||||||
int elt = 0;
|
|
||||||
|
|
||||||
public LongVector() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public int size() {
|
|
||||||
return elt;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ensureAdditionalCapacity(int addCapacity) {
|
|
||||||
ensureCapacity(data.length + addCapacity);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ensureCapacity(int minCapacity) {
|
|
||||||
int oldCapacity = data.length;
|
|
||||||
if (minCapacity > oldCapacity) {
|
|
||||||
long [] oldData = data;
|
|
||||||
int newCapacity = oldCapacity + capacityIncr;
|
|
||||||
if (newCapacity < minCapacity) {
|
|
||||||
newCapacity = minCapacity;
|
|
||||||
}
|
|
||||||
data = new long[newCapacity];
|
|
||||||
System.arraycopy(oldData, 0, data, 0, elt);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public long get(int index) {
|
|
||||||
if (index >= elt)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
|
|
||||||
return data[index];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Reserve(int s) {
|
|
||||||
ensureCapacity(s);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void add(long b) {
|
|
||||||
ensureCapacity(elt + 1);
|
|
||||||
data[elt++] = b;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addAll(Collection c) {
|
|
||||||
ensureCapacity(elt + c.size());
|
|
||||||
Iterator it = c.iterator();
|
|
||||||
while (it.hasNext())
|
|
||||||
data[elt++] = ((Long)it.next()).longValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void addAll(Long[] b) {
|
|
||||||
ensureCapacity(elt + b.length);
|
|
||||||
for (int i=0; i<b.length; i++)
|
|
||||||
data[elt++] = ((Long)b[i]).longValue();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void set(int index, long value) {
|
|
||||||
if (index >= data.length)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
data[index] = value;
|
|
||||||
elt = index + 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setRange(int start, long value) {
|
|
||||||
setRange(start, data.length - start, value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setRange(int start, int length, long value) {
|
|
||||||
if (start + length > data.length)
|
|
||||||
throw new ArrayIndexOutOfBoundsException("start = " + start + ", length = " + length);
|
|
||||||
for (int i=0; i<length; i++)
|
|
||||||
data[start + i] = value;
|
|
||||||
elt = start + length;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void clear() {
|
|
||||||
elt = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isEmpty() {
|
|
||||||
return elt == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long Back() {
|
|
||||||
if (elt < 1)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(0);
|
|
||||||
|
|
||||||
return data[elt-1];
|
|
||||||
}
|
|
||||||
|
|
||||||
public long Front() {
|
|
||||||
if (elt < 1)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(0);
|
|
||||||
|
|
||||||
return data[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void DeleteBack() {
|
|
||||||
// Delete(_size - 1);
|
|
||||||
remove(elt-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO
|
|
||||||
public long remove(int index) {
|
|
||||||
if (index >= elt)
|
|
||||||
throw new ArrayIndexOutOfBoundsException(index);
|
|
||||||
long oldValue = data[index];
|
|
||||||
|
|
||||||
int numMoved = elt - index - 1;
|
|
||||||
Integer n = Integer.valueOf(elt);
|
|
||||||
if (numMoved > 0)
|
|
||||||
System.arraycopy(n, index+1, n, index,numMoved);
|
|
||||||
elt = n.intValue();
|
|
||||||
// data[--elt] = null; // Let gc do its work
|
|
||||||
|
|
||||||
return oldValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,98 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import Common.IntVector;
|
|
||||||
|
|
||||||
public class BindInfo {
|
|
||||||
|
|
||||||
public Vector<CoderStreamsInfo> Coders = new Vector();
|
|
||||||
public Vector<BindPair> BindPairs = new Vector();
|
|
||||||
public IntVector InStreams = new IntVector();
|
|
||||||
public IntVector OutStreams = new IntVector();
|
|
||||||
|
|
||||||
public void Clear() {
|
|
||||||
Coders.clear();
|
|
||||||
BindPairs.clear();
|
|
||||||
InStreams.clear();
|
|
||||||
OutStreams.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
public int FindBinderForInStream(int inStream) {
|
|
||||||
for (int i = 0; i < BindPairs.size(); i++)
|
|
||||||
if (((BindPair)BindPairs.get(i)).InIndex == inStream)
|
|
||||||
return i;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int FindBinderForOutStream(int outStream) // const
|
|
||||||
{
|
|
||||||
for (int i = 0; i < BindPairs.size(); i++)
|
|
||||||
if (((BindPair)BindPairs.get(i)).OutIndex == outStream)
|
|
||||||
return i;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetCoderInStreamIndex(int coderIndex) // const
|
|
||||||
{
|
|
||||||
int streamIndex = 0;
|
|
||||||
for (int i = 0; i < coderIndex; i++)
|
|
||||||
streamIndex += ((CoderStreamsInfo)Coders.get(i)).NumInStreams;
|
|
||||||
return streamIndex;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetCoderOutStreamIndex(int coderIndex) // const
|
|
||||||
{
|
|
||||||
int streamIndex = 0;
|
|
||||||
for (int i = 0; i < coderIndex; i++)
|
|
||||||
streamIndex += ((CoderStreamsInfo)Coders.get(i)).NumOutStreams;
|
|
||||||
return streamIndex;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param streamIndex
|
|
||||||
* @return the coder index number
|
|
||||||
*/
|
|
||||||
public int FindInStream(int streamIndex) {
|
|
||||||
for (int i=0; i<Coders.size(); i++) {
|
|
||||||
int curSize = ((CoderStreamsInfo)Coders.get(i)).NumInStreams;
|
|
||||||
if (streamIndex < curSize) {
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
streamIndex -= curSize;
|
|
||||||
}
|
|
||||||
return -1; //throw new UnknownError("1");
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param streamIndex
|
|
||||||
* @return the coder index number
|
|
||||||
*/
|
|
||||||
public int FindOutStream(int streamIndex) {
|
|
||||||
for (int i=0; i<Coders.size(); i++) {
|
|
||||||
int curSize = ((CoderStreamsInfo)Coders.get(i)).NumOutStreams;
|
|
||||||
if (streamIndex < curSize)
|
|
||||||
return i;
|
|
||||||
streamIndex -= curSize;
|
|
||||||
}
|
|
||||||
return -1; //throw new UnknownError("1");
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean equals(Object obj) {
|
|
||||||
if (obj instanceof BindInfo) {
|
|
||||||
BindInfo arg = (BindInfo)obj;
|
|
||||||
if (this.Coders.size() != arg.Coders.size()) return false;
|
|
||||||
if (this.BindPairs.size() != arg.BindPairs.size()) return false;
|
|
||||||
if (this.InStreams.size() != arg.InStreams.size()) return false;
|
|
||||||
if (this.OutStreams.size() != arg.OutStreams.size()) return false;
|
|
||||||
int i;
|
|
||||||
for (i = 0; i < this.Coders.size(); i++)
|
|
||||||
if (!this.Coders.get(i).equals(arg.Coders.get(i))) return false;
|
|
||||||
for (i = 0; i < this.BindPairs.size(); i++)
|
|
||||||
if (!this.BindPairs.get(i).equals(arg.BindPairs.get(i))) return false;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return super.equals(obj);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,19 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
public class BindPair {
|
|
||||||
public int InIndex;
|
|
||||||
public int OutIndex;
|
|
||||||
|
|
||||||
public BindPair() {
|
|
||||||
InIndex = 0;
|
|
||||||
OutIndex = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean equals(Object obj) {
|
|
||||||
if (obj instanceof BindPair) {
|
|
||||||
BindPair arg = (BindPair)obj;
|
|
||||||
return (this.InIndex == arg.InIndex) && (this.OutIndex == arg.OutIndex);
|
|
||||||
}
|
|
||||||
return super.equals(obj);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,51 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
import SevenZip.ICompressCoder;
|
|
||||||
import SevenZip.ICompressCoder2;
|
|
||||||
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
public class CoderInfo {
|
|
||||||
ICompressCoder Coder;
|
|
||||||
ICompressCoder2 Coder2;
|
|
||||||
int NumInStreams;
|
|
||||||
int NumOutStreams;
|
|
||||||
|
|
||||||
LongVector InSizes = new LongVector();
|
|
||||||
LongVector OutSizes = new LongVector();
|
|
||||||
LongVector InSizePointers = new LongVector();
|
|
||||||
LongVector OutSizePointers = new LongVector();
|
|
||||||
|
|
||||||
public CoderInfo(int numInStreams, int numOutStreams) {
|
|
||||||
NumInStreams = numInStreams;
|
|
||||||
NumOutStreams = numOutStreams;
|
|
||||||
InSizes.Reserve(NumInStreams);
|
|
||||||
InSizePointers.Reserve(NumInStreams);
|
|
||||||
OutSizePointers.Reserve(NumOutStreams);
|
|
||||||
OutSizePointers.Reserve(NumOutStreams);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void SetSizes(
|
|
||||||
LongVector srcSizes,
|
|
||||||
LongVector sizes,
|
|
||||||
LongVector sizePointers,
|
|
||||||
int numItems) {
|
|
||||||
sizes.clear();
|
|
||||||
sizePointers.clear();
|
|
||||||
for(int i = 0; i < numItems; i++) {
|
|
||||||
if (srcSizes == null || srcSizes.get(i) == -1) // TBD null => -1
|
|
||||||
{
|
|
||||||
sizes.add(0L);
|
|
||||||
sizePointers.add(-1);
|
|
||||||
} else {
|
|
||||||
sizes.add(srcSizes.get(i)); // sizes.Add(*srcSizes[i]);
|
|
||||||
sizePointers.add(sizes.Back()); // sizePointers.Add(&sizes.Back());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetCoderInfo(LongVector inSizes, LongVector outSizes) {
|
|
||||||
SetSizes(inSizes, InSizes, InSizePointers, NumInStreams);
|
|
||||||
SetSizes(outSizes, OutSizes, OutSizePointers, NumOutStreams);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,12 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
public interface CoderMixer2 {
|
|
||||||
|
|
||||||
void ReInit();
|
|
||||||
|
|
||||||
// void setCoderInfos(Vector decoders, Folder folderInfo, LongVector packSizes);
|
|
||||||
|
|
||||||
void SetCoderInfo(int coderIndex,LongVector inSizes, LongVector outSizes);
|
|
||||||
}
|
|
@ -1,270 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
import SevenZip.HRESULT;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import Common.LongVector;
|
|
||||||
import SevenZip.ICompressCoder2;
|
|
||||||
import SevenZip.ICompressCoder;
|
|
||||||
import SevenZip.ICompressSetInStream;
|
|
||||||
import SevenZip.ICompressSetOutStream;
|
|
||||||
import SevenZip.ICompressSetOutStreamSize;
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
|
|
||||||
|
|
||||||
public class CoderMixer2ST implements ICompressCoder2 , CoderMixer2 {
|
|
||||||
|
|
||||||
BindInfo _bindInfo = new BindInfo();
|
|
||||||
Vector<STCoderInfo> _coders = new Vector<STCoderInfo>();
|
|
||||||
int _mainCoderIndex;
|
|
||||||
|
|
||||||
public CoderMixer2ST(BindInfo bindInfo) {
|
|
||||||
this._bindInfo = bindInfo;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddCoderCommon(boolean isMain) {
|
|
||||||
CoderStreamsInfo csi = _bindInfo.Coders.get(_coders.size());
|
|
||||||
_coders.add(new STCoderInfo(csi.NumInStreams, csi.NumOutStreams, isMain));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddCoder2(ICompressCoder2 coder, boolean isMain) {
|
|
||||||
AddCoderCommon(isMain);
|
|
||||||
_coders.lastElement().Coder2 = coder;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddCoder(ICompressCoder coder, boolean isMain) {
|
|
||||||
AddCoderCommon(isMain);
|
|
||||||
_coders.lastElement().Coder = coder;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void ReInit() {
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void SetCoderInfo(int coderIndex,LongVector inSizes, LongVector outSizes) {
|
|
||||||
// _coders[coderIndex].SetCoderInfo(inSizes, outSizes);
|
|
||||||
_coders.get(coderIndex).SetCoderInfo(inSizes, outSizes);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetInStream(
|
|
||||||
Vector<InputStream> inStreams,
|
|
||||||
//Object useless_inSizes, // const UInt64 **inSizes,
|
|
||||||
int streamIndex,
|
|
||||||
InputStream [] inStreamRes) {
|
|
||||||
InputStream seqInStream;
|
|
||||||
int i;
|
|
||||||
for(i = 0; i < _bindInfo.InStreams.size(); i++)
|
|
||||||
if (_bindInfo.InStreams.get(i) == streamIndex) {
|
|
||||||
seqInStream = inStreams.get(i);
|
|
||||||
inStreamRes[0] = seqInStream; // seqInStream.Detach();
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
int binderIndex = _bindInfo.FindBinderForInStream(streamIndex);
|
|
||||||
if (binderIndex < 0)
|
|
||||||
return HRESULT.E_INVALIDARG;
|
|
||||||
|
|
||||||
int coderIndex = _bindInfo.FindOutStream(_bindInfo.BindPairs.get(binderIndex).OutIndex);
|
|
||||||
if (coderIndex < 0)
|
|
||||||
return HRESULT.E_INVALIDARG;
|
|
||||||
|
|
||||||
CoderInfo coder = _coders.get(coderIndex);
|
|
||||||
if (coder.Coder == null)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
|
|
||||||
seqInStream = (InputStream)coder.Coder; // coder.Coder.QueryInterface(IID_ISequentialInStream, &seqInStream);
|
|
||||||
if (seqInStream == null)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
|
|
||||||
int startIndex = _bindInfo.GetCoderInStreamIndex(coderIndex);
|
|
||||||
|
|
||||||
if (coder.Coder == null)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
|
|
||||||
ICompressSetInStream setInStream = (ICompressSetInStream)coder.Coder; // coder.Coder.QueryInterface(IID_ICompressSetInStream, &setInStream);
|
|
||||||
if (setInStream == null)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
|
|
||||||
if (coder.NumInStreams > 1)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
for (i = 0; i < (int)coder.NumInStreams; i++) {
|
|
||||||
InputStream [] tmp = new InputStream[1];
|
|
||||||
int res = GetInStream(inStreams, /*useless_inSizes,*/ startIndex + i, tmp /* &seqInStream2 */ );
|
|
||||||
if (res != HRESULT.S_OK) return res;
|
|
||||||
InputStream seqInStream2 = tmp[0];
|
|
||||||
setInStream.SetInStream(seqInStream2);
|
|
||||||
//if (res != HRESULT.S_OK) return res;
|
|
||||||
}
|
|
||||||
inStreamRes[0] = seqInStream; // seqInStream.Detach();
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetOutStream(
|
|
||||||
Vector<OutputStream> outStreams,
|
|
||||||
//Object useless_outSizes, // const UInt64 **outSizes,
|
|
||||||
int streamIndex,
|
|
||||||
OutputStream [] outStreamRes) {
|
|
||||||
OutputStream seqOutStream;
|
|
||||||
int i;
|
|
||||||
for(i = 0; i < _bindInfo.OutStreams.size(); i++)
|
|
||||||
if (_bindInfo.OutStreams.get(i) == streamIndex) {
|
|
||||||
seqOutStream = outStreams.get(i);
|
|
||||||
outStreamRes[0] = seqOutStream; // seqOutStream.Detach();
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
int binderIndex = _bindInfo.FindBinderForOutStream(streamIndex);
|
|
||||||
if (binderIndex < 0)
|
|
||||||
return HRESULT.E_INVALIDARG;
|
|
||||||
|
|
||||||
int coderIndex = _bindInfo.FindInStream(_bindInfo.BindPairs.get(binderIndex).InIndex);
|
|
||||||
if (coderIndex < 0 )
|
|
||||||
return HRESULT.E_INVALIDARG;
|
|
||||||
|
|
||||||
CoderInfo coder = _coders.get(coderIndex);
|
|
||||||
if (coder.Coder == null)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
seqOutStream = (OutputStream)coder.Coder; // coder.Coder.QueryInterface(IID_ISequentialOutStream, &seqOutStream);
|
|
||||||
} catch (java.lang.ClassCastException e) {
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
}
|
|
||||||
|
|
||||||
int startIndex = _bindInfo.GetCoderOutStreamIndex(coderIndex);
|
|
||||||
|
|
||||||
if (coder.Coder == null)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
|
|
||||||
ICompressSetOutStream setOutStream = null;
|
|
||||||
try {
|
|
||||||
setOutStream = (ICompressSetOutStream)coder.Coder; // coder.Coder.QueryInterface(IID_ICompressSetOutStream, &setOutStream);
|
|
||||||
} catch (java.lang.ClassCastException e) {
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (coder.NumOutStreams > 1)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
for (i = 0; i < (int)coder.NumOutStreams; i++) {
|
|
||||||
OutputStream [] tmp = new OutputStream[1];
|
|
||||||
int res = GetOutStream(outStreams, /*useless_outSizes,*/ startIndex + i, tmp /* &seqOutStream2 */ );
|
|
||||||
if (res != HRESULT.S_OK) return res;
|
|
||||||
OutputStream seqOutStream2 = tmp[0];
|
|
||||||
res = setOutStream.SetOutStream(seqOutStream2);
|
|
||||||
if (res != HRESULT.S_OK) return res;
|
|
||||||
}
|
|
||||||
outStreamRes[0] = seqOutStream; // seqOutStream.Detach();
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int Code(
|
|
||||||
Vector<InputStream> inStreams,
|
|
||||||
//Object useless_inSizes, // const UInt64 ** inSizes ,
|
|
||||||
int numInStreams,
|
|
||||||
Vector<OutputStream> outStreams,
|
|
||||||
//Object useless_outSizes, // const UInt64 ** /* outSizes */,
|
|
||||||
int numOutStreams,
|
|
||||||
ICompressProgressInfo progress) throws IOException {
|
|
||||||
if (numInStreams != _bindInfo.InStreams.size() ||
|
|
||||||
numOutStreams != _bindInfo.OutStreams.size())
|
|
||||||
return HRESULT.E_INVALIDARG;
|
|
||||||
|
|
||||||
// Find main coder
|
|
||||||
int _mainCoderIndex = -1;
|
|
||||||
int i;
|
|
||||||
for (i = 0; i < _coders.size(); i++)
|
|
||||||
if (_coders.get(i).IsMain) {
|
|
||||||
_mainCoderIndex = i;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (_mainCoderIndex < 0)
|
|
||||||
for (i = 0; i < _coders.size(); i++)
|
|
||||||
if (_coders.get(i).NumInStreams > 1) {
|
|
||||||
if (_mainCoderIndex >= 0)
|
|
||||||
return HRESULT.E_NOTIMPL;
|
|
||||||
_mainCoderIndex = i;
|
|
||||||
}
|
|
||||||
if (_mainCoderIndex < 0)
|
|
||||||
_mainCoderIndex = 0;
|
|
||||||
|
|
||||||
// _mainCoderIndex = 0;
|
|
||||||
// _mainCoderIndex = _coders.Size() - 1;
|
|
||||||
CoderInfo mainCoder = _coders.get(_mainCoderIndex);
|
|
||||||
|
|
||||||
Vector<InputStream> seqInStreams = new Vector<InputStream>(); // CObjectVector< CMyComPtr<ISequentialInStream> >
|
|
||||||
Vector<OutputStream> seqOutStreams = new Vector<OutputStream>(); // CObjectVector< CMyComPtr<ISequentialOutStream> >
|
|
||||||
int startInIndex = _bindInfo.GetCoderInStreamIndex(_mainCoderIndex);
|
|
||||||
int startOutIndex = _bindInfo.GetCoderOutStreamIndex(_mainCoderIndex);
|
|
||||||
for (i = 0; i < (int)mainCoder.NumInStreams; i++) {
|
|
||||||
InputStream tmp [] = new InputStream[1];
|
|
||||||
int res = GetInStream(inStreams, /*useless_inSizes,*/ startInIndex + i, tmp /* &seqInStream */ );
|
|
||||||
if (res != HRESULT.S_OK) return res;
|
|
||||||
InputStream seqInStream = tmp[0];
|
|
||||||
seqInStreams.add(seqInStream);
|
|
||||||
}
|
|
||||||
for (i = 0; i < (int)mainCoder.NumOutStreams; i++) {
|
|
||||||
OutputStream tmp [] = new OutputStream[1];
|
|
||||||
int res = GetOutStream(outStreams, /*useless_outSizes,*/ startOutIndex + i, tmp);
|
|
||||||
if (res != HRESULT.S_OK) return res;
|
|
||||||
OutputStream seqOutStream = tmp[0];
|
|
||||||
seqOutStreams.add(seqOutStream);
|
|
||||||
}
|
|
||||||
Vector<InputStream> seqInStreamsSpec = new Vector<InputStream>();
|
|
||||||
Vector<OutputStream> seqOutStreamsSpec = new Vector<OutputStream>();
|
|
||||||
for (i = 0; i < (int)mainCoder.NumInStreams; i++)
|
|
||||||
seqInStreamsSpec.add(seqInStreams.get(i));
|
|
||||||
for (i = 0; i < (int)mainCoder.NumOutStreams; i++)
|
|
||||||
seqOutStreamsSpec.add(seqOutStreams.get(i));
|
|
||||||
|
|
||||||
for (i = 0; i < _coders.size(); i++) {
|
|
||||||
if (i == _mainCoderIndex)
|
|
||||||
continue;
|
|
||||||
CoderInfo coder = _coders.get(i);
|
|
||||||
|
|
||||||
ICompressSetOutStreamSize setOutStreamSize = null;
|
|
||||||
try
|
|
||||||
{
|
|
||||||
setOutStreamSize = (ICompressSetOutStreamSize)coder.Coder;
|
|
||||||
|
|
||||||
/*int res =*/ setOutStreamSize.SetOutStreamSize(coder.OutSizePointers.get(0));
|
|
||||||
//if (res != HRESULT.S_OK) return res;
|
|
||||||
} catch (java.lang.ClassCastException e) {
|
|
||||||
// nothing to do
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (mainCoder.Coder != null) {
|
|
||||||
/*int res =*/ mainCoder.Coder.Code(
|
|
||||||
seqInStreamsSpec.get(0),
|
|
||||||
seqOutStreamsSpec.get(0),
|
|
||||||
// TBD mainCoder.InSizePointers.get(0),
|
|
||||||
mainCoder.OutSizePointers.get(0),
|
|
||||||
progress);
|
|
||||||
//if (res != HRESULT.S_OK) return res;
|
|
||||||
} else {
|
|
||||||
/*int res =*/ mainCoder.Coder2.Code(
|
|
||||||
seqInStreamsSpec, // &seqInStreamsSpec.Front(
|
|
||||||
//mainCoder.InSizePointers.Front(), // &mainCoder.InSizePointers.Front()
|
|
||||||
mainCoder.NumInStreams,
|
|
||||||
seqOutStreamsSpec, // &seqOutStreamsSpec.Front()
|
|
||||||
//mainCoder.OutSizePointers.Front(), // &mainCoder.OutSizePointers.Front()
|
|
||||||
mainCoder.NumOutStreams,
|
|
||||||
progress);
|
|
||||||
//if (res != HRESULT.S_OK) return res;
|
|
||||||
}
|
|
||||||
|
|
||||||
OutputStream stream = seqOutStreams.firstElement();
|
|
||||||
stream.flush();
|
|
||||||
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void close() {
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,19 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
public class CoderStreamsInfo {
|
|
||||||
public int NumInStreams;
|
|
||||||
public int NumOutStreams;
|
|
||||||
|
|
||||||
public CoderStreamsInfo() {
|
|
||||||
NumInStreams = 0;
|
|
||||||
NumOutStreams = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean equals(Object obj) {
|
|
||||||
if (obj instanceof CoderStreamsInfo) {
|
|
||||||
CoderStreamsInfo arg = (CoderStreamsInfo)obj;
|
|
||||||
return (this.NumInStreams == arg.NumInStreams) && (this.NumOutStreams != arg.NumOutStreams);
|
|
||||||
}
|
|
||||||
return super.equals(obj);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,147 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
|
|
||||||
import SevenZip.HRESULT;
|
|
||||||
import java.io.IOException;
|
|
||||||
import SevenZip.ICompressCoder;
|
|
||||||
import SevenZip.ICompressSetOutStream;
|
|
||||||
|
|
||||||
/*
|
|
||||||
// #ifdef _ST_MODE
|
|
||||||
public ICompressSetInStream,
|
|
||||||
public ISequentialInStream,
|
|
||||||
public ICompressSetOutStream,
|
|
||||||
public ISequentialOutStream,
|
|
||||||
public IOutStreamFlush,
|
|
||||||
// #endif
|
|
||||||
*/
|
|
||||||
public class FilterCoder extends java.io.OutputStream implements ICompressCoder , ICompressSetOutStream {
|
|
||||||
|
|
||||||
public SevenZip.ICompressFilter Filter = null;
|
|
||||||
|
|
||||||
java.io.OutputStream _outStream = null;
|
|
||||||
int _bufferPos; // UInt32
|
|
||||||
|
|
||||||
boolean _outSizeIsDefined;
|
|
||||||
long _outSize;
|
|
||||||
long _nowPos64;
|
|
||||||
|
|
||||||
int Init() // HRESULT
|
|
||||||
{
|
|
||||||
_nowPos64 = 0;
|
|
||||||
_outSizeIsDefined = false;
|
|
||||||
return Filter.Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
// ICompressCoder
|
|
||||||
public void Code(
|
|
||||||
java.io.InputStream inStream, // , ISequentialInStream
|
|
||||||
java.io.OutputStream outStream, // ISequentialOutStream
|
|
||||||
long outSize, SevenZip.ICompressProgressInfo progress) throws java.io.IOException {
|
|
||||||
throw new java.io.IOException("Not implemented");
|
|
||||||
}
|
|
||||||
|
|
||||||
// java.io.OutputStream
|
|
||||||
public void write(int b) {
|
|
||||||
throw new UnknownError("FilterCoder write");
|
|
||||||
}
|
|
||||||
|
|
||||||
public void write(byte b[], int off, int size) throws IOException {
|
|
||||||
if (b == null) {
|
|
||||||
throw new NullPointerException();
|
|
||||||
} else if ((off < 0) || (off > b.length) || (size < 0) ||
|
|
||||||
((off + size) > b.length) || ((off + size) < 0)) {
|
|
||||||
throw new IndexOutOfBoundsException();
|
|
||||||
} else if (size == 0) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (off != 0) throw new IOException("FilterCoder - off <> 0");
|
|
||||||
|
|
||||||
byte [] cur_data = b;
|
|
||||||
int cur_off = 0;
|
|
||||||
while(size > 0) {
|
|
||||||
int sizeMax = kBufferSize - _bufferPos;
|
|
||||||
int sizeTemp = size;
|
|
||||||
if (sizeTemp > sizeMax)
|
|
||||||
sizeTemp = sizeMax;
|
|
||||||
System.arraycopy(cur_data, cur_off, _buffer, _bufferPos , sizeTemp); // memmove(_buffer + _bufferPos, data, sizeTemp);
|
|
||||||
size -= sizeTemp;
|
|
||||||
cur_off = cur_off + sizeTemp;
|
|
||||||
int endPos = _bufferPos + sizeTemp;
|
|
||||||
_bufferPos = Filter.Filter(_buffer, endPos);
|
|
||||||
if (_bufferPos == 0) {
|
|
||||||
_bufferPos = endPos;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (_bufferPos > endPos) {
|
|
||||||
if (size != 0)
|
|
||||||
throw new IOException("FilterCoder - write() : size <> 0"); // return HRESULT.E_FAIL;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
WriteWithLimit(_outStream, _bufferPos);
|
|
||||||
|
|
||||||
int i = 0;
|
|
||||||
while(_bufferPos < endPos)
|
|
||||||
_buffer[i++] = _buffer[_bufferPos++];
|
|
||||||
_bufferPos = i;
|
|
||||||
}
|
|
||||||
|
|
||||||
// return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
void WriteWithLimit(java.io.OutputStream outStream, int size) throws IOException {
|
|
||||||
if (_outSizeIsDefined) {
|
|
||||||
long remSize = _outSize - _nowPos64;
|
|
||||||
if (size > remSize)
|
|
||||||
size = (int)remSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
outStream.write(_buffer,0,size);
|
|
||||||
|
|
||||||
_nowPos64 += size;
|
|
||||||
}
|
|
||||||
|
|
||||||
byte [] _buffer;
|
|
||||||
|
|
||||||
static final int kBufferSize = 1 << 17;
|
|
||||||
public FilterCoder() {
|
|
||||||
_buffer = new byte[kBufferSize];
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// ICompressSetOutStream
|
|
||||||
public int SetOutStream(java.io.OutputStream outStream) {
|
|
||||||
_bufferPos = 0;
|
|
||||||
_outStream = outStream;
|
|
||||||
return Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReleaseOutStream() throws IOException {
|
|
||||||
if (_outStream != null) _outStream.close(); // Release()
|
|
||||||
_outStream = null;
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void flush() throws IOException {
|
|
||||||
if (_bufferPos != 0) {
|
|
||||||
int endPos = Filter.Filter(_buffer, _bufferPos);
|
|
||||||
if (endPos > _bufferPos) {
|
|
||||||
for (; _bufferPos < endPos; _bufferPos++)
|
|
||||||
_buffer[_bufferPos] = 0;
|
|
||||||
if (Filter.Filter(_buffer, endPos) != endPos)
|
|
||||||
throw new IOException("FilterCoder - flush() : E_FAIL"); // return HRESULT.E_FAIL;
|
|
||||||
}
|
|
||||||
_outStream.write(_buffer,0,_bufferPos);
|
|
||||||
_bufferPos = 0;
|
|
||||||
}
|
|
||||||
_outStream.flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() throws IOException {
|
|
||||||
if (_outStream != null) _outStream.close(); // Release()
|
|
||||||
_outStream = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,55 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
|
|
||||||
import Common.CRC;
|
|
||||||
|
|
||||||
public class OutStreamWithCRC extends OutputStream {
|
|
||||||
|
|
||||||
private OutputStream _stream;
|
|
||||||
private long _size;
|
|
||||||
private CRC _crc = new CRC();
|
|
||||||
private boolean _calculateCrc;
|
|
||||||
|
|
||||||
public void write(int b) throws IOException {
|
|
||||||
throw new IOException("OutStreamWithCRC - write() not implemented");
|
|
||||||
}
|
|
||||||
|
|
||||||
public void write(byte [] data,int off, int size) throws IOException {
|
|
||||||
if (_stream != null)
|
|
||||||
_stream.write(data, off,size);
|
|
||||||
if (_calculateCrc)
|
|
||||||
_crc.Update(data, off, size);
|
|
||||||
|
|
||||||
_size += size;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setStream(OutputStream stream) { _stream = stream; }
|
|
||||||
|
|
||||||
public void reset() { reset(true); }
|
|
||||||
|
|
||||||
public void reset(boolean calculateCrc) {
|
|
||||||
_size = 0;
|
|
||||||
_calculateCrc = calculateCrc;
|
|
||||||
_crc.Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void releaseStream() throws IOException {
|
|
||||||
// _stream.Release();
|
|
||||||
if (_stream != null) _stream.close();
|
|
||||||
_stream = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long getSize() {
|
|
||||||
return _size;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getCRC() {
|
|
||||||
return _crc.GetDigest();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void resetCRC() {
|
|
||||||
_crc.Init();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,10 +0,0 @@
|
|||||||
package SevenZip.Archive.Common;
|
|
||||||
|
|
||||||
public class STCoderInfo extends CoderInfo {
|
|
||||||
boolean IsMain;
|
|
||||||
|
|
||||||
public STCoderInfo(int numInStreams, int numOutStreams, boolean isMain) {
|
|
||||||
super(numInStreams, numOutStreams);
|
|
||||||
this.IsMain = isMain;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,12 +0,0 @@
|
|||||||
package SevenZip.Archive;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
|
|
||||||
public interface IArchiveExtractCallback extends SevenZip.IProgress {
|
|
||||||
|
|
||||||
OutputStream GetStream(int index, int askExtractMode) throws IOException;
|
|
||||||
|
|
||||||
void PrepareOperation(int askExtractMode);
|
|
||||||
void SetOperationResult(int resultEOperationResult) throws IOException;
|
|
||||||
}
|
|
@ -1,28 +0,0 @@
|
|||||||
package SevenZip.Archive;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public interface IInArchive {
|
|
||||||
public final static int NExtract_NAskMode_kExtract = 0;
|
|
||||||
public final static int NExtract_NAskMode_kTest = 1;
|
|
||||||
public final static int NExtract_NAskMode_kSkip = 2;
|
|
||||||
|
|
||||||
public final static int NExtract_NOperationResult_kOK = 0;
|
|
||||||
public final static int NExtract_NOperationResult_kUnSupportedMethod = 1;
|
|
||||||
public final static int NExtract_NOperationResult_kDataError = 2;
|
|
||||||
public final static int NExtract_NOperationResult_kCRCError = 3;
|
|
||||||
|
|
||||||
// Static-SFX (for Linux) can be big.
|
|
||||||
public final long kMaxCheckStartPosition = 1 << 22;
|
|
||||||
|
|
||||||
public SevenZipEntry getEntry(int index);
|
|
||||||
|
|
||||||
public int size();
|
|
||||||
|
|
||||||
public void close() throws IOException ;
|
|
||||||
|
|
||||||
public void Extract(int [] indices, int numItems,
|
|
||||||
int testModeSpec, IArchiveExtractCallback extractCallbackSpec) throws java.io.IOException;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
@ -1,18 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
|
|
||||||
public class AltCoderInfo {
|
|
||||||
public MethodID MethodID;
|
|
||||||
public ByteArrayOutputStream Properties;
|
|
||||||
|
|
||||||
public AltCoderInfo(int size) {
|
|
||||||
MethodID = new MethodID(null);
|
|
||||||
Properties = new ByteArrayOutputStream(size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public AltCoderInfo() {
|
|
||||||
MethodID = new MethodID(null);
|
|
||||||
Properties = new ByteArrayOutputStream();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,725 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import Common.BoolVector;
|
|
||||||
import Common.CRC;
|
|
||||||
import Common.IntVector;
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
import SevenZip.IInStream;
|
|
||||||
import SevenZip.Archive.Common.BindPair;
|
|
||||||
|
|
||||||
public class ArchiveDB {
|
|
||||||
|
|
||||||
public static final int kNumNoIndex = 0xFFFFFFFF;
|
|
||||||
|
|
||||||
public final LongVector PackSizes = new LongVector();
|
|
||||||
public final BoolVector PackCRCsDefined = new BoolVector();
|
|
||||||
public final IntVector PackCRCs = new IntVector();
|
|
||||||
public final IntVector NumUnPackStreamsVector = new IntVector();
|
|
||||||
public final Vector<FileItem> Files = new Vector();
|
|
||||||
public Vector<Folder> Folders = new Vector();
|
|
||||||
|
|
||||||
public final IntVector FolderStartPackStreamIndex = new IntVector();
|
|
||||||
public final IntVector FolderStartFileIndex = new IntVector();
|
|
||||||
public final IntVector FileIndexToFolderIndexMap = new IntVector();
|
|
||||||
|
|
||||||
private final InStream inStream;
|
|
||||||
private final InArchiveInfo ArchiveInfo = new InArchiveInfo();
|
|
||||||
private final LongVector PackStreamStartPositions = new LongVector();
|
|
||||||
|
|
||||||
public ArchiveDB(InStream inStream) throws IOException {
|
|
||||||
this.inStream = inStream;
|
|
||||||
this.ArchiveInfo.StartPosition = this.inStream.archiveBeginStreamPosition;
|
|
||||||
|
|
||||||
byte [] btmp = new byte[2];
|
|
||||||
int realProcessedSize = this.inStream.ReadDirect(btmp, 2);
|
|
||||||
if (realProcessedSize != 2)
|
|
||||||
throw new IOException("Unexpected End Of Archive"); // throw CInArchiveException(CInArchiveException::kUnexpectedEndOfArchive);
|
|
||||||
|
|
||||||
this.ArchiveInfo.ArchiveVersion_Major = btmp[0];
|
|
||||||
this.ArchiveInfo.ArchiveVersion_Minor = btmp[1];
|
|
||||||
|
|
||||||
if (this.ArchiveInfo.ArchiveVersion_Major != Header.kMajorVersion)
|
|
||||||
throw new IOException("Unsupported Version: " +
|
|
||||||
this.ArchiveInfo.ArchiveVersion_Major + "." +
|
|
||||||
this.ArchiveInfo.ArchiveVersion_Minor);
|
|
||||||
|
|
||||||
int crcFromArchive = this.inStream.SafeReadDirectUInt32();
|
|
||||||
long nextHeaderOffset = this.inStream.SafeReadDirectUInt64();
|
|
||||||
long nextHeaderSize = this.inStream.SafeReadDirectUInt64();
|
|
||||||
int nextHeaderCRC = this.inStream.SafeReadDirectUInt32();
|
|
||||||
|
|
||||||
this.ArchiveInfo.StartPositionAfterHeader = this.inStream.position;
|
|
||||||
|
|
||||||
CRC crc = new CRC();
|
|
||||||
crc.UpdateUInt64(nextHeaderOffset);
|
|
||||||
crc.UpdateUInt64(nextHeaderSize);
|
|
||||||
crc.UpdateUInt32(nextHeaderCRC);
|
|
||||||
|
|
||||||
if (crc.GetDigest() != crcFromArchive)
|
|
||||||
throw new IOException("Incorrect Header, CRCs don't match: archive: " +
|
|
||||||
Integer.toHexString(crcFromArchive) + ", calculated: " + crc); // CInArchiveException(CInArchiveException::kIncorrectHeader);
|
|
||||||
|
|
||||||
if (nextHeaderSize == 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (nextHeaderSize >= 0xFFFFFFFFL)
|
|
||||||
throw new IOException("second header too big: " + nextHeaderSize);
|
|
||||||
|
|
||||||
this.inStream.position = this.inStream.stream.Seek(nextHeaderOffset,IInStream.STREAM_SEEK_CUR);
|
|
||||||
|
|
||||||
this.readNextStreamHeaders((int)nextHeaderSize, nextHeaderCRC);
|
|
||||||
this.readHeader();
|
|
||||||
this.Fill();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void readNextStreamHeaders(int nextHeaderSize, int nextHeaderCRC) throws IOException {
|
|
||||||
byte[] buffer = new byte[nextHeaderSize];
|
|
||||||
|
|
||||||
// SafeReadDirect(buffer2.data(), (int)nextHeaderSize);
|
|
||||||
if (!this.inStream.SafeReadDirect(buffer, nextHeaderSize))
|
|
||||||
throw new IOException("Unexpected End Of Archive"); // throw CInArchiveException(CInArchiveException::kUnexpectedEndOfArchive);
|
|
||||||
|
|
||||||
if (!CRC.VerifyDigest(nextHeaderCRC, buffer, nextHeaderSize))
|
|
||||||
throw new IOException("Incorrect Header, CRCs don't match"); // CInArchiveException(CInArchiveException::kIncorrectHeader);
|
|
||||||
|
|
||||||
// TODO:
|
|
||||||
StreamSwitch streamSwitch = new StreamSwitch();
|
|
||||||
streamSwitch.Set(this.inStream, buffer);
|
|
||||||
|
|
||||||
long type;
|
|
||||||
while ((type = this.inStream.ReadID()) != Header.NID.kHeader) {
|
|
||||||
if (type != Header.NID.kEncodedHeader)
|
|
||||||
throw new IOException("Incorrect Header");
|
|
||||||
|
|
||||||
Vector dataVector = this.ReadAndDecodePackedStreams(
|
|
||||||
this.ArchiveInfo.StartPositionAfterHeader, 1);
|
|
||||||
|
|
||||||
if (dataVector.size() == 0) {
|
|
||||||
return;
|
|
||||||
} else if (dataVector.size() > 1) {
|
|
||||||
throw new IOException("Incorrect Header");
|
|
||||||
}
|
|
||||||
streamSwitch.Set(this.inStream, (byte[])dataVector.firstElement()); // dataVector.Front()
|
|
||||||
}
|
|
||||||
|
|
||||||
streamSwitch.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadArchiveProperties(InArchiveInfo archiveInfo) throws IOException {
|
|
||||||
while (this.inStream.ReadID() != Header.NID.kEnd)
|
|
||||||
this.inStream.SkeepData();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void readHeader() throws IOException {
|
|
||||||
long type = this.inStream.ReadID();
|
|
||||||
|
|
||||||
if (type == Header.NID.kArchiveProperties) {
|
|
||||||
this.ReadArchiveProperties(this.ArchiveInfo);
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
}
|
|
||||||
|
|
||||||
Vector dataVector = new Vector();
|
|
||||||
|
|
||||||
if (type == Header.NID.kAdditionalStreamsInfo) {
|
|
||||||
dataVector.addAll(ReadAndDecodePackedStreams(
|
|
||||||
this.ArchiveInfo.StartPositionAfterHeader, 1));
|
|
||||||
this.ArchiveInfo.DataStartPosition2 += this.ArchiveInfo.StartPositionAfterHeader;
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
}
|
|
||||||
|
|
||||||
LongVector unPackSizes = new LongVector();
|
|
||||||
BoolVector digestsDefined = new BoolVector();
|
|
||||||
IntVector digests = new IntVector();
|
|
||||||
|
|
||||||
if (type == Header.NID.kMainStreamsInfo) {
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kPackInfo);
|
|
||||||
this.ReadPackInfo(this.PackSizes, this.PackCRCsDefined, this.PackCRCs, 0);
|
|
||||||
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kUnPackInfo);
|
|
||||||
this.Folders = ReadUnPackInfo(dataVector);
|
|
||||||
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kSubStreamsInfo);
|
|
||||||
this.ReadSubStreamsInfo(this.Folders, this.NumUnPackStreamsVector, unPackSizes, digestsDefined, digests);
|
|
||||||
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kEnd);
|
|
||||||
|
|
||||||
this.ArchiveInfo.DataStartPosition += this.ArchiveInfo.StartPositionAfterHeader;
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
} else {
|
|
||||||
for(int i = 0; i < this.Folders.size(); i++) {
|
|
||||||
this.NumUnPackStreamsVector.add(1);
|
|
||||||
Folder folder = (Folder)this.Folders.get(i);
|
|
||||||
unPackSizes.add(folder.GetUnPackSize());
|
|
||||||
digestsDefined.add(folder.UnPackCRCDefined);
|
|
||||||
digests.add(folder.UnPackCRC);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (type == Header.NID.kEnd)
|
|
||||||
return;
|
|
||||||
if (type != Header.NID.kFilesInfo)
|
|
||||||
throw new IOException("Incorrect Header");
|
|
||||||
|
|
||||||
this.readFileDescriptions(dataVector, unPackSizes, digests, digestsDefined);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void readFileDescriptions(
|
|
||||||
Vector dataVector,
|
|
||||||
LongVector unPackSizes,
|
|
||||||
IntVector digests,
|
|
||||||
BoolVector digestsDefined) throws IOException {
|
|
||||||
|
|
||||||
int numFiles = this.inStream.ReadNum();
|
|
||||||
this.ArchiveInfo.FileInfoPopIDs.add(Header.NID.kSize);
|
|
||||||
if (!this.PackSizes.isEmpty())
|
|
||||||
this.ArchiveInfo.FileInfoPopIDs.add(Header.NID.kPackInfo);
|
|
||||||
if (numFiles > 0 && !digests.isEmpty())
|
|
||||||
this.ArchiveInfo.FileInfoPopIDs.add(Header.NID.kCRC);
|
|
||||||
|
|
||||||
this.Files.clear();
|
|
||||||
this.Files.ensureCapacity(numFiles);
|
|
||||||
for (int i=0; i<numFiles; i++)
|
|
||||||
this.Files.add(new FileItem());
|
|
||||||
|
|
||||||
BoolVector emptyStreamVector = new BoolVector();
|
|
||||||
emptyStreamVector.Reserve(numFiles);
|
|
||||||
for(int i = 0; i < numFiles; i++)
|
|
||||||
emptyStreamVector.add(false);
|
|
||||||
BoolVector emptyFileVector = new BoolVector();
|
|
||||||
BoolVector antiFileVector = new BoolVector();
|
|
||||||
int numEmptyStreams = 0;
|
|
||||||
|
|
||||||
long type;
|
|
||||||
while ((type = this.inStream.ReadID()) != Header.NID.kEnd) {
|
|
||||||
long size = this.inStream.ReadNumber();
|
|
||||||
this.ArchiveInfo.FileInfoPopIDs.add(type);
|
|
||||||
switch((int)type) {
|
|
||||||
case Header.NID.kEmptyStream:
|
|
||||||
emptyStreamVector.setBoolVector(this.inStream.ReadBoolVector(numFiles));
|
|
||||||
for (int i=0; i<emptyStreamVector.size(); i++)
|
|
||||||
if (emptyStreamVector.get(i))
|
|
||||||
numEmptyStreams++;
|
|
||||||
emptyFileVector.Reserve(numEmptyStreams);
|
|
||||||
antiFileVector.Reserve(numEmptyStreams);
|
|
||||||
for (int i = 0; i < numEmptyStreams; i++) {
|
|
||||||
emptyFileVector.add(false);
|
|
||||||
antiFileVector.add(false);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case Header.NID.kName: this.ReadFileNames(dataVector); break;
|
|
||||||
case Header.NID.kWinAttributes: this.ReadFileAttributes(dataVector); break;
|
|
||||||
case Header.NID.kStartPos: this.ReadFileStartPositions(dataVector); break;
|
|
||||||
case Header.NID.kEmptyFile: emptyFileVector.setBoolVector(this.inStream.ReadBoolVector(numEmptyStreams)); break;
|
|
||||||
case Header.NID.kAnti: antiFileVector.setBoolVector(this.inStream.ReadBoolVector(numEmptyStreams)); break;
|
|
||||||
case Header.NID.kCreationTime:
|
|
||||||
case Header.NID.kLastWriteTime:
|
|
||||||
case Header.NID.kLastAccessTime: this.ReadTime(dataVector, type); break;
|
|
||||||
default:
|
|
||||||
this.ArchiveInfo.FileInfoPopIDs.DeleteBack();
|
|
||||||
this.inStream.SkeepData(size);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int emptyFileIndex = 0;
|
|
||||||
int sizeIndex = 0;
|
|
||||||
for(int i = 0; i < numFiles; i++) {
|
|
||||||
FileItem file = (FileItem)this.Files.get(i);
|
|
||||||
file.HasStream = !emptyStreamVector.get(i);
|
|
||||||
if(file.HasStream) {
|
|
||||||
file.IsDirectory = false;
|
|
||||||
file.IsAnti = false;
|
|
||||||
file.UnPackSize = unPackSizes.get(sizeIndex);
|
|
||||||
file.FileCRC = digests.get(sizeIndex);
|
|
||||||
file.IsFileCRCDefined = digestsDefined.get(sizeIndex);
|
|
||||||
sizeIndex++;
|
|
||||||
} else {
|
|
||||||
file.IsDirectory = !emptyFileVector.get(emptyFileIndex);
|
|
||||||
file.IsAnti = antiFileVector.get(emptyFileIndex);
|
|
||||||
emptyFileIndex++;
|
|
||||||
file.UnPackSize = 0;
|
|
||||||
file.IsFileCRCDefined = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadSubStreamsInfo(
|
|
||||||
Vector<Folder> folders,
|
|
||||||
IntVector numUnPackStreamsInFolders,
|
|
||||||
LongVector unPackSizes,
|
|
||||||
BoolVector digestsDefined,
|
|
||||||
IntVector digests) throws IOException {
|
|
||||||
numUnPackStreamsInFolders.clear();
|
|
||||||
numUnPackStreamsInFolders.Reserve(folders.size());
|
|
||||||
long type;
|
|
||||||
|
|
||||||
while ((type = this.inStream.ReadID()) != Header.NID.kCRC &&
|
|
||||||
type != Header.NID.kSize &&
|
|
||||||
type != Header.NID.kEnd) {
|
|
||||||
if (type == Header.NID.kNumUnPackStream) {
|
|
||||||
for(int i = 0; i < folders.size(); i++) {
|
|
||||||
int value = this.inStream.ReadNum();
|
|
||||||
numUnPackStreamsInFolders.add(value);
|
|
||||||
}
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
this.inStream.SkeepData();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (numUnPackStreamsInFolders.isEmpty())
|
|
||||||
for (int i=0; i<folders.size(); i++)
|
|
||||||
numUnPackStreamsInFolders.add(1);
|
|
||||||
|
|
||||||
final ArrayList sizes = new ArrayList();
|
|
||||||
int numSubstreams;
|
|
||||||
long sum, size;
|
|
||||||
for (int i=0; i<numUnPackStreamsInFolders.size(); i++) {
|
|
||||||
numSubstreams = numUnPackStreamsInFolders.get(i);
|
|
||||||
if (numSubstreams < 1) continue;
|
|
||||||
sum = 0;
|
|
||||||
if (type == Header.NID.kSize)
|
|
||||||
for (int j=1; j<numSubstreams; j++) {
|
|
||||||
sum += size = this.inStream.ReadNumber();
|
|
||||||
sizes.add(new Long(size));
|
|
||||||
}
|
|
||||||
sizes.add(new Long((((Folder)folders.get(i)).GetUnPackSize() - sum)));
|
|
||||||
}
|
|
||||||
unPackSizes.addAll(sizes);
|
|
||||||
sizes.clear();
|
|
||||||
|
|
||||||
if (type == Header.NID.kSize)
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
|
|
||||||
int numDigests = 0;
|
|
||||||
int numDigestsTotal = 0;
|
|
||||||
for(int i = 0; i < folders.size(); i++) {
|
|
||||||
numSubstreams = numUnPackStreamsInFolders.get(i);
|
|
||||||
if (numSubstreams != 1 || !((Folder)folders.get(i)).UnPackCRCDefined)
|
|
||||||
numDigests += numSubstreams;
|
|
||||||
numDigestsTotal += numSubstreams;
|
|
||||||
}
|
|
||||||
|
|
||||||
final ArrayList bsizes = new ArrayList();
|
|
||||||
do {
|
|
||||||
if (type == Header.NID.kCRC) {
|
|
||||||
BoolVector digestsDefined2 = new BoolVector();
|
|
||||||
IntVector digests2 = new IntVector();
|
|
||||||
digests2 = this.inStream.ReadHashDigests(numDigests, digestsDefined2);
|
|
||||||
int digestIndex = 0;
|
|
||||||
|
|
||||||
for (int i=0; i<folders.size(); i++) {
|
|
||||||
numSubstreams = numUnPackStreamsInFolders.get(i);
|
|
||||||
Folder folder = (Folder)folders.get(i);
|
|
||||||
if (numSubstreams == 1 && folder.UnPackCRCDefined) {
|
|
||||||
bsizes.add(Boolean.TRUE);
|
|
||||||
sizes.add(Integer.valueOf(folder.UnPackCRC));
|
|
||||||
} else {
|
|
||||||
for (int j=0; j<numSubstreams; j++, digestIndex++) {
|
|
||||||
bsizes.add(Boolean.valueOf(digestsDefined2.get(digestIndex)));
|
|
||||||
sizes.add(Integer.valueOf(digests2.get(digestIndex)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
digestsDefined.addAll(bsizes);
|
|
||||||
bsizes.clear();
|
|
||||||
digests.addAll(sizes);
|
|
||||||
sizes.clear();
|
|
||||||
} else {
|
|
||||||
this.inStream.SkeepData();
|
|
||||||
}
|
|
||||||
} while ((type = this.inStream.ReadID()) != Header.NID.kEnd);
|
|
||||||
|
|
||||||
if (digestsDefined.isEmpty()) {
|
|
||||||
digests.clear();
|
|
||||||
for (int i=0; i<numDigestsTotal; i++) {
|
|
||||||
digestsDefined.add(false);
|
|
||||||
digests.add(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private Vector ReadAndDecodePackedStreams(long baseOffset, int dataStartPosIndex) throws IOException {
|
|
||||||
LongVector packSizes = new LongVector();
|
|
||||||
|
|
||||||
BoolVector packCRCsDefined = new BoolVector();
|
|
||||||
IntVector packCRCs = new IntVector();
|
|
||||||
|
|
||||||
long type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kPackInfo);
|
|
||||||
this.ReadPackInfo(packSizes, packCRCsDefined, packCRCs, dataStartPosIndex);
|
|
||||||
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kUnPackInfo);
|
|
||||||
Vector<Folder> folders = ReadUnPackInfo(null);
|
|
||||||
|
|
||||||
type = this.inStream.ReadID();
|
|
||||||
assert (type == Header.NID.kEnd);
|
|
||||||
|
|
||||||
int packIndex = 0;
|
|
||||||
Decoder decoder = new Decoder(false); // _ST_MODE
|
|
||||||
|
|
||||||
Vector dataVector = new Vector();
|
|
||||||
long dataStartPos = baseOffset + ((dataStartPosIndex == 0) ?
|
|
||||||
this.ArchiveInfo.DataStartPosition : this.ArchiveInfo.DataStartPosition2);
|
|
||||||
for(int i=0; i<folders.size(); i++) {
|
|
||||||
Folder folder = (Folder)folders.get(i);
|
|
||||||
long unPackSize = folder.GetUnPackSize();
|
|
||||||
if (unPackSize > InStream.kNumMax || unPackSize > 0xFFFFFFFFL)
|
|
||||||
throw new IOException("unPackSize too great: " + unPackSize);
|
|
||||||
|
|
||||||
ByteArrayOutputStream baos = new ByteArrayOutputStream((int)unPackSize);
|
|
||||||
decoder.Decode(
|
|
||||||
this.inStream.stream, dataStartPos,
|
|
||||||
packSizes, packIndex,
|
|
||||||
folder, baos, null);
|
|
||||||
byte[] data; // TODO: stream belassen!
|
|
||||||
dataVector.add(data = baos.toByteArray());
|
|
||||||
|
|
||||||
if (folder.UnPackCRCDefined)
|
|
||||||
if (!CRC.VerifyDigest(folder.UnPackCRC, data, (int)unPackSize))
|
|
||||||
throw new IOException("Incorrect Header, CRCs of packed folder don't match: archive: " +
|
|
||||||
Integer.toHexString(folder.UnPackCRC) + ", calculated: " +
|
|
||||||
Integer.toHexString(CRC.CalculateDigest(data, (int)unPackSize)) +
|
|
||||||
". Either is the archive corrupted or an internal error occured");
|
|
||||||
|
|
||||||
for (int j = 0; j < folder.PackStreams.size(); j++)
|
|
||||||
dataStartPos += packSizes.get(packIndex++);
|
|
||||||
}
|
|
||||||
|
|
||||||
return dataVector;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadPackInfo(
|
|
||||||
LongVector packSizes,
|
|
||||||
BoolVector packCRCsDefined,
|
|
||||||
IntVector packCRCs,
|
|
||||||
int dataStartPosIndex)
|
|
||||||
throws IOException {
|
|
||||||
if (dataStartPosIndex == 0) {
|
|
||||||
this.ArchiveInfo.DataStartPosition = this.inStream.ReadNumber();
|
|
||||||
} else {
|
|
||||||
this.ArchiveInfo.DataStartPosition2 = this.inStream.ReadNumber();
|
|
||||||
}
|
|
||||||
int numPackStreams = this.inStream.ReadNum();
|
|
||||||
|
|
||||||
this.inStream.skipToAttribute(Header.NID.kSize);
|
|
||||||
|
|
||||||
packSizes.clear();
|
|
||||||
packSizes.Reserve(numPackStreams);
|
|
||||||
for(int i = 0; i < numPackStreams; i++) {
|
|
||||||
long size = this.inStream.ReadNumber();
|
|
||||||
packSizes.add(size);
|
|
||||||
}
|
|
||||||
|
|
||||||
long type;
|
|
||||||
while ((type = this.inStream.ReadID()) != Header.NID.kEnd) {
|
|
||||||
if (type == Header.NID.kCRC) {
|
|
||||||
packCRCs = this.inStream.ReadHashDigests(numPackStreams, packCRCsDefined);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
this.inStream.SkeepData();
|
|
||||||
}
|
|
||||||
if (packCRCsDefined.isEmpty()) {
|
|
||||||
packCRCsDefined.Reserve(numPackStreams);
|
|
||||||
packCRCsDefined.clear();
|
|
||||||
packCRCs.Reserve(numPackStreams);
|
|
||||||
packCRCs.clear();
|
|
||||||
for(int i = 0; i < numPackStreams; i++) {
|
|
||||||
packCRCsDefined.add(false);
|
|
||||||
packCRCs.add(0);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadFileNames(Vector from) throws IOException {
|
|
||||||
StreamSwitch streamSwitch = new StreamSwitch();
|
|
||||||
streamSwitch.Set(this.inStream, from);
|
|
||||||
StringBuffer name = new StringBuffer(30);
|
|
||||||
char c;
|
|
||||||
for (int i=0; i<this.Files.size(); i++) {
|
|
||||||
while ((c = this.inStream.ReadWideCharLE()) != '\0')
|
|
||||||
name.append(c);
|
|
||||||
((FileItem)this.Files.get(i)).name = new String(name);
|
|
||||||
name.delete(0, name.length());
|
|
||||||
}
|
|
||||||
streamSwitch.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadFileAttributes(Vector from) throws IOException {
|
|
||||||
BoolVector boolVector = this.inStream.ReadBoolVector2(this.Files.size());
|
|
||||||
StreamSwitch streamSwitch = new StreamSwitch();
|
|
||||||
streamSwitch.Set(this.inStream, from);
|
|
||||||
for (int i=0; i<this.Files.size(); i++) {
|
|
||||||
FileItem file = (FileItem)this.Files.get(i);
|
|
||||||
file.AreAttributesDefined = boolVector.get(i);
|
|
||||||
if (file.AreAttributesDefined)
|
|
||||||
file.Attributes = this.inStream.ReadUInt32();
|
|
||||||
}
|
|
||||||
streamSwitch.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadFileStartPositions(Vector from) throws IOException {
|
|
||||||
BoolVector boolVector = this.inStream.ReadBoolVector2(this.Files.size());
|
|
||||||
StreamSwitch streamSwitch = new StreamSwitch();
|
|
||||||
streamSwitch.Set(this.inStream, from);
|
|
||||||
for(int i=0; i<this.Files.size(); i++) {
|
|
||||||
FileItem file = (FileItem)this.Files.get(i);
|
|
||||||
file.IsStartPosDefined = boolVector.get(i);
|
|
||||||
if (file.IsStartPosDefined)
|
|
||||||
file.StartPos = this.inStream.ReadUInt64();
|
|
||||||
}
|
|
||||||
streamSwitch.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReadTime(Vector dataVector, long type) throws IOException {
|
|
||||||
BoolVector boolVector = this.inStream.ReadBoolVector2(this.Files.size());
|
|
||||||
|
|
||||||
StreamSwitch streamSwitch = new StreamSwitch();
|
|
||||||
streamSwitch.Set(this.inStream, dataVector);
|
|
||||||
|
|
||||||
for (int i=0; i<this.Files.size(); i++) {
|
|
||||||
FileItem file = (FileItem)this.Files.get(i);
|
|
||||||
int low = 0;
|
|
||||||
int high = 0;
|
|
||||||
boolean defined = boolVector.get(i);
|
|
||||||
if (defined) {
|
|
||||||
low = this.inStream.ReadUInt32();
|
|
||||||
high = this.inStream.ReadUInt32();
|
|
||||||
}
|
|
||||||
switch((int)type) {
|
|
||||||
case Header.NID.kCreationTime:
|
|
||||||
// file.IsCreationTimeDefined = defined;
|
|
||||||
if (defined)
|
|
||||||
file.CreationTime = InStream.FileTimeToLong(high,low);
|
|
||||||
break;
|
|
||||||
case Header.NID.kLastWriteTime:
|
|
||||||
// file.IsLastWriteTimeDefined = defined;
|
|
||||||
if (defined)
|
|
||||||
file.LastWriteTime = InStream.FileTimeToLong(high,low);
|
|
||||||
break;
|
|
||||||
case Header.NID.kLastAccessTime:
|
|
||||||
// file.IsLastAccessTimeDefined = defined;
|
|
||||||
if (defined)
|
|
||||||
file.LastAccessTime = InStream.FileTimeToLong(high,low);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
streamSwitch.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
private Vector<Folder> ReadUnPackInfo(Vector dataVector) throws IOException {
|
|
||||||
this.inStream.skipToAttribute(Header.NID.kFolder);
|
|
||||||
|
|
||||||
int numFolders = this.inStream.ReadNum();
|
|
||||||
|
|
||||||
StreamSwitch streamSwitch = new StreamSwitch();
|
|
||||||
streamSwitch.Set(this.inStream, dataVector);
|
|
||||||
Vector<Folder> folders = new Vector(numFolders);
|
|
||||||
for (int i=0; i<numFolders; i++)
|
|
||||||
folders.add(GetNextFolderItem());
|
|
||||||
streamSwitch.close();
|
|
||||||
|
|
||||||
this.inStream.skipToAttribute(Header.NID.kCodersUnPackSize);
|
|
||||||
|
|
||||||
for (int i=0; i<numFolders; i++) {
|
|
||||||
Folder folder = folders.get(i);
|
|
||||||
int numOutStreams = folder.GetNumOutStreams();
|
|
||||||
folder.UnPackSizes.Reserve(numOutStreams);
|
|
||||||
for (int j=0; j<numOutStreams; j++) {
|
|
||||||
long unPackSize = this.inStream.ReadNumber();
|
|
||||||
folder.UnPackSizes.add(unPackSize);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
long type;
|
|
||||||
while ((type = this.inStream.ReadID()) != Header.NID.kEnd) {
|
|
||||||
if (type == Header.NID.kCRC) {
|
|
||||||
BoolVector crcsDefined = new BoolVector();
|
|
||||||
IntVector crcs = new IntVector();
|
|
||||||
crcs = this.inStream.ReadHashDigests(numFolders, crcsDefined);
|
|
||||||
for (int i=0; i<numFolders; i++) {
|
|
||||||
Folder folder = folders.get(i);
|
|
||||||
folder.UnPackCRCDefined = crcsDefined.get(i);
|
|
||||||
folder.UnPackCRC = crcs.get(i);
|
|
||||||
}
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
this.inStream.SkeepData();
|
|
||||||
}
|
|
||||||
return folders;
|
|
||||||
}
|
|
||||||
|
|
||||||
private Folder GetNextFolderItem() throws IOException {
|
|
||||||
int numCoders = this.inStream.ReadNum();
|
|
||||||
|
|
||||||
Folder folder = new Folder();
|
|
||||||
folder.Coders.clear();
|
|
||||||
folder.Coders.ensureCapacity(numCoders);
|
|
||||||
int numInStreams = 0;
|
|
||||||
int numOutStreams = 0;
|
|
||||||
for (int i=0; i<numCoders; i++) {
|
|
||||||
folder.Coders.add(new CoderInfo());
|
|
||||||
CoderInfo coder = folder.Coders.lastElement();
|
|
||||||
int mainByte;
|
|
||||||
do {
|
|
||||||
AltCoderInfo altCoder = new AltCoderInfo();
|
|
||||||
coder.AltCoders.add(altCoder);
|
|
||||||
mainByte = this.inStream.ReadByte();
|
|
||||||
altCoder.MethodID.IDSize = (byte)(mainByte & 0xF);
|
|
||||||
if (!this.inStream.ReadBytes(altCoder.MethodID.ID, altCoder.MethodID.IDSize))
|
|
||||||
throw new IOException("error reading properties for alternative decoder");
|
|
||||||
|
|
||||||
if ((mainByte & 0x10) != 0) {
|
|
||||||
coder.NumInStreams = this.inStream.ReadNum();
|
|
||||||
coder.NumOutStreams = this.inStream.ReadNum();
|
|
||||||
} else {
|
|
||||||
coder.NumInStreams = 1;
|
|
||||||
coder.NumOutStreams = 1;
|
|
||||||
}
|
|
||||||
if ((mainByte & 0x20) != 0) {
|
|
||||||
int propertiesSize = this.inStream.ReadNum();
|
|
||||||
if (!this.inStream.ReadBytes(altCoder.Properties, propertiesSize))
|
|
||||||
throw new IOException("error reading properties for alternative decoder");
|
|
||||||
}
|
|
||||||
} while ((mainByte & 0x80) != 0);
|
|
||||||
numInStreams += coder.NumInStreams;
|
|
||||||
numOutStreams += coder.NumOutStreams;
|
|
||||||
}
|
|
||||||
|
|
||||||
// RINOK(ReadNumber(numBindPairs));
|
|
||||||
int numBindPairs = numOutStreams - 1;
|
|
||||||
folder.BindPairs.clear();
|
|
||||||
folder.BindPairs.ensureCapacity(numBindPairs);
|
|
||||||
for (int i=0; i<numBindPairs; i++) {
|
|
||||||
BindPair bindPair = new BindPair();
|
|
||||||
bindPair.InIndex = this.inStream.ReadNum();
|
|
||||||
bindPair.OutIndex = this.inStream.ReadNum();
|
|
||||||
folder.BindPairs.add(bindPair);
|
|
||||||
}
|
|
||||||
|
|
||||||
int numPackedStreams = numInStreams - numBindPairs;
|
|
||||||
folder.PackStreams.Reserve(numPackedStreams);
|
|
||||||
if (numPackedStreams == 1) {
|
|
||||||
for (int j=0; j<numInStreams; j++)
|
|
||||||
if (folder.FindBindPairForInStream(j) < 0) {
|
|
||||||
folder.PackStreams.add(j);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
for (int i=0; i<numPackedStreams; i++) {
|
|
||||||
int packStreamInfo = this.inStream.ReadNum();
|
|
||||||
folder.PackStreams.add(packStreamInfo);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return folder;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void Fill() throws IOException {
|
|
||||||
FillFolderStartPackStream();
|
|
||||||
FillStartPos();
|
|
||||||
FillFolderStartFileIndex();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void FillFolderStartPackStream() {
|
|
||||||
this.FolderStartPackStreamIndex.clear();
|
|
||||||
this.FolderStartPackStreamIndex.Reserve(this.Folders.size());
|
|
||||||
int startPos = 0;
|
|
||||||
for(int i = 0; i < this.Folders.size(); i++) {
|
|
||||||
this.FolderStartPackStreamIndex.add(startPos);
|
|
||||||
startPos += ((Folder)this.Folders.get(i)).PackStreams.size();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void FillStartPos() {
|
|
||||||
this.PackStreamStartPositions.clear();
|
|
||||||
this.PackStreamStartPositions.Reserve(this.PackSizes.size());
|
|
||||||
long startPos = 0;
|
|
||||||
for(int i = 0; i < this.PackSizes.size(); i++) {
|
|
||||||
this.PackStreamStartPositions.add(startPos);
|
|
||||||
startPos += this.PackSizes.get(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void FillFolderStartFileIndex() throws IOException {
|
|
||||||
this.FolderStartFileIndex.clear();
|
|
||||||
this.FolderStartFileIndex.Reserve(this.Folders.size());
|
|
||||||
this.FileIndexToFolderIndexMap.clear();
|
|
||||||
this.FileIndexToFolderIndexMap.Reserve(this.Files.size());
|
|
||||||
|
|
||||||
int folderIndex = 0;
|
|
||||||
int indexInFolder = 0;
|
|
||||||
for (int i = 0; i < this.Files.size(); i++) {
|
|
||||||
FileItem file = (FileItem)this.Files.get(i);
|
|
||||||
boolean emptyStream = !file.HasStream;
|
|
||||||
if (emptyStream && indexInFolder == 0) {
|
|
||||||
this.FileIndexToFolderIndexMap.add(kNumNoIndex);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (indexInFolder == 0) {
|
|
||||||
// v3.13 incorrectly worked with empty folders
|
|
||||||
// v4.07: Loop for skipping empty folders
|
|
||||||
for (;;) {
|
|
||||||
if (folderIndex >= this.Folders.size())
|
|
||||||
throw new IOException("Incorrect Header");
|
|
||||||
this.FolderStartFileIndex.add(i); // check it
|
|
||||||
if (this.NumUnPackStreamsVector.get(folderIndex) != 0)
|
|
||||||
break;
|
|
||||||
folderIndex++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
this.FileIndexToFolderIndexMap.add(folderIndex);
|
|
||||||
if (emptyStream)
|
|
||||||
continue;
|
|
||||||
indexInFolder++;
|
|
||||||
if (indexInFolder >= this.NumUnPackStreamsVector.get(folderIndex)) {
|
|
||||||
folderIndex++;
|
|
||||||
indexInFolder = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/* ---------------------------------------------------------------------------------------------------
|
|
||||||
* public methods
|
|
||||||
* --------------------------------------------------------------------------------------------------- */
|
|
||||||
|
|
||||||
public void clear() {
|
|
||||||
this.ArchiveInfo.FileInfoPopIDs.clear();
|
|
||||||
this.PackStreamStartPositions.clear();
|
|
||||||
this.FolderStartPackStreamIndex.clear();
|
|
||||||
this.FolderStartFileIndex.clear();
|
|
||||||
this.FileIndexToFolderIndexMap.clear();
|
|
||||||
|
|
||||||
this.PackSizes.clear();
|
|
||||||
this.PackCRCsDefined.clear();
|
|
||||||
this.PackCRCs.clear();
|
|
||||||
this.Folders.clear();
|
|
||||||
this.NumUnPackStreamsVector.clear();
|
|
||||||
this.Files.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetFolderFullPackSize(int folderIndex) {
|
|
||||||
int packStreamIndex = this.FolderStartPackStreamIndex.get(folderIndex);
|
|
||||||
Folder folder = (Folder)this.Folders.get(folderIndex);
|
|
||||||
long size = 0;
|
|
||||||
for (int i = 0; i < folder.PackStreams.size(); i++)
|
|
||||||
size += this.PackSizes.get(packStreamIndex + i);
|
|
||||||
return size;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetFolderStreamPos(int folderIndex, int indexInFolder) {
|
|
||||||
return this.ArchiveInfo.DataStartPosition +
|
|
||||||
this.PackStreamStartPositions.get(this.FolderStartPackStreamIndex.get(folderIndex) +
|
|
||||||
indexInFolder);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,26 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import Common.BoolVector;
|
|
||||||
import Common.IntVector;
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
class ArchiveDatabase {
|
|
||||||
|
|
||||||
public LongVector PackSizes = new LongVector();
|
|
||||||
public BoolVector PackCRCsDefined = new BoolVector();
|
|
||||||
public IntVector PackCRCs = new IntVector();
|
|
||||||
public Vector<Folder> Folders = new Vector();
|
|
||||||
public IntVector NumUnPackStreamsVector = new IntVector();
|
|
||||||
public Vector<FileItem> Files = new Vector();
|
|
||||||
|
|
||||||
void Clear() {
|
|
||||||
PackSizes.clear();
|
|
||||||
PackCRCsDefined.clear();
|
|
||||||
PackCRCs.clear();
|
|
||||||
Folders.clear();
|
|
||||||
NumUnPackStreamsVector.clear();
|
|
||||||
Files.clear();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,107 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import Common.IntVector;
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
public class ArchiveDatabaseEx extends ArchiveDatabase {
|
|
||||||
public IntVector FolderStartPackStreamIndex = new IntVector();
|
|
||||||
public IntVector FolderStartFileIndex = new IntVector();
|
|
||||||
public IntVector FileIndexToFolderIndexMap = new IntVector();
|
|
||||||
|
|
||||||
InArchiveInfo ArchiveInfo = new InArchiveInfo();
|
|
||||||
LongVector PackStreamStartPositions = new LongVector();
|
|
||||||
|
|
||||||
public ArchiveDatabaseEx() {
|
|
||||||
super();
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
void Clear() {
|
|
||||||
ArchiveInfo.Clear();
|
|
||||||
PackStreamStartPositions.clear();
|
|
||||||
FolderStartPackStreamIndex.clear();
|
|
||||||
FolderStartFileIndex.clear();
|
|
||||||
FileIndexToFolderIndexMap.clear();
|
|
||||||
super.Clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
void FillFolderStartPackStream() {
|
|
||||||
FolderStartPackStreamIndex.clear();
|
|
||||||
FolderStartPackStreamIndex.Reserve(Folders.size());
|
|
||||||
int startPos = 0;
|
|
||||||
for(int i = 0; i < Folders.size(); i++) {
|
|
||||||
FolderStartPackStreamIndex.add(startPos);
|
|
||||||
startPos += ((Folder)Folders.get(i)).PackStreams.size();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void FillStartPos() {
|
|
||||||
PackStreamStartPositions.clear();
|
|
||||||
PackStreamStartPositions.Reserve(PackSizes.size());
|
|
||||||
long startPos = 0;
|
|
||||||
for(int i = 0; i < PackSizes.size(); i++) {
|
|
||||||
PackStreamStartPositions.add(startPos);
|
|
||||||
startPos += PackSizes.get(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Fill() throws java.io.IOException {
|
|
||||||
FillFolderStartPackStream();
|
|
||||||
FillStartPos();
|
|
||||||
FillFolderStartFileIndex();
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetFolderFullPackSize(int folderIndex) {
|
|
||||||
int packStreamIndex = FolderStartPackStreamIndex.get(folderIndex);
|
|
||||||
Folder folder = (Folder)Folders.get(folderIndex);
|
|
||||||
long size = 0;
|
|
||||||
for (int i = 0; i < folder.PackStreams.size(); i++)
|
|
||||||
size += PackSizes.get(packStreamIndex + i);
|
|
||||||
return size;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
void FillFolderStartFileIndex() throws java.io.IOException {
|
|
||||||
FolderStartFileIndex.clear();
|
|
||||||
FolderStartFileIndex.Reserve(Folders.size());
|
|
||||||
FileIndexToFolderIndexMap.clear();
|
|
||||||
FileIndexToFolderIndexMap.Reserve(Files.size());
|
|
||||||
|
|
||||||
int folderIndex = 0;
|
|
||||||
int indexInFolder = 0;
|
|
||||||
for (int i = 0; i < Files.size(); i++) {
|
|
||||||
FileItem file = (FileItem)Files.get(i);
|
|
||||||
boolean emptyStream = !file.HasStream;
|
|
||||||
if (emptyStream && indexInFolder == 0) {
|
|
||||||
FileIndexToFolderIndexMap.add(ArchiveDB.kNumNoIndex);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (indexInFolder == 0) {
|
|
||||||
// v3.13 incorrectly worked with empty folders
|
|
||||||
// v4.07: Loop for skipping empty folders
|
|
||||||
for (;;) {
|
|
||||||
if (folderIndex >= Folders.size())
|
|
||||||
throw new java.io.IOException("Incorrect Header"); // CInArchiveException(CInArchiveException::kIncorrectHeader);
|
|
||||||
FolderStartFileIndex.add(i); // check it
|
|
||||||
if (NumUnPackStreamsVector.get(folderIndex) != 0)
|
|
||||||
break;
|
|
||||||
folderIndex++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
FileIndexToFolderIndexMap.add(folderIndex);
|
|
||||||
if (emptyStream)
|
|
||||||
continue;
|
|
||||||
indexInFolder++;
|
|
||||||
if (indexInFolder >= NumUnPackStreamsVector.get(folderIndex)) {
|
|
||||||
folderIndex++;
|
|
||||||
indexInFolder = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetFolderStreamPos(int folderIndex, int indexInFolder) {
|
|
||||||
return ArchiveInfo.DataStartPosition +
|
|
||||||
PackStreamStartPositions.get(FolderStartPackStreamIndex.get(folderIndex) +
|
|
||||||
indexInFolder);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,25 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import SevenZip.Archive.Common.BindInfo;
|
|
||||||
|
|
||||||
class BindInfoEx extends BindInfo {
|
|
||||||
|
|
||||||
Vector CoderMethodIDs = new Vector();
|
|
||||||
|
|
||||||
public void Clear() {
|
|
||||||
super.Clear(); // CBindInfo::Clear();
|
|
||||||
CoderMethodIDs.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean equals(Object obj) {
|
|
||||||
if (obj instanceof BindInfoEx) {
|
|
||||||
BindInfoEx arg = (BindInfoEx)obj;
|
|
||||||
for (int i = 0; i < this.CoderMethodIDs.size(); i++)
|
|
||||||
if (this.CoderMethodIDs.get(i) != arg.CoderMethodIDs.get(i))
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return super.equals(obj);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,17 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
public class CoderInfo {
|
|
||||||
|
|
||||||
public int NumInStreams;
|
|
||||||
public int NumOutStreams;
|
|
||||||
public Vector AltCoders = new Vector();
|
|
||||||
|
|
||||||
boolean IsSimpleCoder() { return (NumInStreams == 1) && (NumOutStreams == 1); }
|
|
||||||
|
|
||||||
public CoderInfo() {
|
|
||||||
NumInStreams = 0;
|
|
||||||
NumOutStreams = 0;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,213 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import SevenZip.ICompressCoder2;
|
|
||||||
import SevenZip.ICompressCoder;
|
|
||||||
import SevenZip.ICompressFilter;
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
import SevenZip.IInStream;
|
|
||||||
|
|
||||||
import SevenZip.Archive.Common.CoderMixer2ST;
|
|
||||||
import SevenZip.Archive.Common.FilterCoder;
|
|
||||||
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
public class Decoder {
|
|
||||||
|
|
||||||
private boolean _bindInfoExPrevIsDefined;
|
|
||||||
private BindInfoEx _bindInfoExPrev;
|
|
||||||
|
|
||||||
private boolean _multiThread;
|
|
||||||
|
|
||||||
// CoderMixer2MT _mixerCoderMTSpec;
|
|
||||||
private CoderMixer2ST _mixerCoderSTSpec;
|
|
||||||
private final Vector _decoders;
|
|
||||||
|
|
||||||
public Decoder(boolean multiThread) {
|
|
||||||
this._multiThread = multiThread;
|
|
||||||
this._bindInfoExPrevIsDefined = false;
|
|
||||||
this._bindInfoExPrev = new BindInfoEx();
|
|
||||||
this._decoders = new Vector();
|
|
||||||
}
|
|
||||||
|
|
||||||
private static ICompressCoder getSimpleCoder(AltCoderInfo altCoderInfo) throws IOException {
|
|
||||||
ICompressCoder decoder = null;
|
|
||||||
ICompressFilter filter = null;
|
|
||||||
|
|
||||||
// #ifdef COMPRESS_LZMA
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_LZMA))
|
|
||||||
decoder = new SevenZip.Compression.LZMA.Decoder(altCoderInfo.Properties.toByteArray()); // NCompress::NLZMA::CDecoder;
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_PPMD))
|
|
||||||
throw new IOException("PPMD not implemented"); // decoder = new NCompress::NPPMD::CDecoder;
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_BCJ_X86))
|
|
||||||
filter = new SevenZip.Compression.Branch.BCJ_x86_Decoder();
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_Deflate))
|
|
||||||
throw new IOException("DEFLATE not implemented"); // decoder = new NCompress::NDeflate::NDecoder::CCOMCoder;
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_BZip2))
|
|
||||||
throw new IOException("BZIP2 not implemented"); // decoder = new NCompress::NBZip2::CDecoder;
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_Copy))
|
|
||||||
decoder = new SevenZip.Compression.Copy.Decoder(); // decoder = new NCompress::CCopyCoder;
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_7zAES))
|
|
||||||
throw new IOException("k_7zAES not implemented"); // filter = new NCrypto::NSevenZ::CDecoder;
|
|
||||||
|
|
||||||
if (filter != null) {
|
|
||||||
FilterCoder coderSpec = new FilterCoder();
|
|
||||||
coderSpec.Filter = filter;
|
|
||||||
decoder = coderSpec;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (decoder == null)
|
|
||||||
throw new IOException("decoder " + altCoderInfo.MethodID + " not implemented");
|
|
||||||
return decoder;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static ICompressCoder2 getComplexCoder(AltCoderInfo altCoderInfo) throws IOException {
|
|
||||||
ICompressCoder2 decoder = null;
|
|
||||||
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_BCJ2))
|
|
||||||
decoder = new SevenZip.Compression.Branch.BCJ2_x86_Decoder();
|
|
||||||
|
|
||||||
if (decoder == null)
|
|
||||||
throw new IOException("decoder " + altCoderInfo.MethodID + " not implemented");
|
|
||||||
return decoder;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void createNewCoders(
|
|
||||||
BindInfoEx bindInfo,
|
|
||||||
Folder folderInfo) throws IOException {
|
|
||||||
int i;
|
|
||||||
this._decoders.clear();
|
|
||||||
if (this._mixerCoderSTSpec != null) this._mixerCoderSTSpec.close(); // _mixerCoder.Release();
|
|
||||||
if (this._multiThread) {
|
|
||||||
/*
|
|
||||||
_mixerCoderMTSpec = new CoderMixer2MT();
|
|
||||||
_mixerCoder = _mixerCoderMTSpec;
|
|
||||||
_mixerCoderCommon = _mixerCoderMTSpec;
|
|
||||||
*/
|
|
||||||
throw new IOException("multithreaded decoder not implemented");
|
|
||||||
} else {
|
|
||||||
this._mixerCoderSTSpec = new CoderMixer2ST(bindInfo);
|
|
||||||
}
|
|
||||||
|
|
||||||
for (i=0; i<folderInfo.Coders.size(); i++) {
|
|
||||||
CoderInfo coderInfo = folderInfo.Coders.get(i);
|
|
||||||
AltCoderInfo altCoderInfo = (AltCoderInfo)coderInfo.AltCoders.firstElement();
|
|
||||||
|
|
||||||
if (coderInfo.IsSimpleCoder()) {
|
|
||||||
ICompressCoder decoder = getSimpleCoder(altCoderInfo);
|
|
||||||
this._decoders.add(decoder);
|
|
||||||
|
|
||||||
if (this._multiThread) {
|
|
||||||
// _mixerCoderMTSpec.AddCoder(decoder);
|
|
||||||
// has already ben checked above
|
|
||||||
// throw new IOException("Multithreaded decoder is not implemented");
|
|
||||||
} else {
|
|
||||||
this._mixerCoderSTSpec.AddCoder(decoder, false);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
ICompressCoder2 decoder = getComplexCoder(altCoderInfo);
|
|
||||||
this._decoders.add(decoder);
|
|
||||||
|
|
||||||
if (this._multiThread) {
|
|
||||||
// _mixerCoderMTSpec.AddCoder2(decoder);
|
|
||||||
// has already ben checked above
|
|
||||||
// throw new IOException("Multithreaded decoder is not implemented");
|
|
||||||
} else {
|
|
||||||
this._mixerCoderSTSpec.AddCoder2(decoder, false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
this._bindInfoExPrev = bindInfo;
|
|
||||||
this._bindInfoExPrevIsDefined = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
private void setCoderMixerCommonInfos(Folder folderInfo, LongVector packSizes) {
|
|
||||||
int packStreamIndex = 0, unPackStreamIndex = 0;
|
|
||||||
for (int i=0; i<folderInfo.Coders.size(); i++) {
|
|
||||||
CoderInfo coderInfo = folderInfo.Coders.get(i);
|
|
||||||
int numInStreams = coderInfo.NumInStreams;
|
|
||||||
int numOutStreams = coderInfo.NumOutStreams;
|
|
||||||
LongVector packSizesPointers = new LongVector(); // CRecordVector<const UInt64 *>
|
|
||||||
LongVector unPackSizesPointers = new LongVector(); // CRecordVector<const UInt64 *>
|
|
||||||
packSizesPointers.Reserve(numInStreams);
|
|
||||||
unPackSizesPointers.Reserve(numOutStreams);
|
|
||||||
int j;
|
|
||||||
|
|
||||||
for (j=0; j<numOutStreams; j++, unPackStreamIndex++)
|
|
||||||
unPackSizesPointers.add(folderInfo.UnPackSizes.get(unPackStreamIndex));
|
|
||||||
|
|
||||||
for (j=0; j<numInStreams; j++, packStreamIndex++) {
|
|
||||||
final long packSizesPointer;
|
|
||||||
final int bindPairIndex = folderInfo.FindBindPairForInStream(packStreamIndex);
|
|
||||||
final int index;
|
|
||||||
if (bindPairIndex >= 0) {
|
|
||||||
index = (folderInfo.BindPairs.get(bindPairIndex)).OutIndex;
|
|
||||||
packSizesPointer = folderInfo.UnPackSizes.get(index);
|
|
||||||
} else {
|
|
||||||
index = folderInfo.FindPackStreamArrayIndex(packStreamIndex);
|
|
||||||
if (index < 0)
|
|
||||||
throw new IndexOutOfBoundsException("PackStreamArrayIndex: " + index);
|
|
||||||
packSizesPointer = packSizes.get(index);
|
|
||||||
}
|
|
||||||
packSizesPointers.add(packSizesPointer);
|
|
||||||
}
|
|
||||||
|
|
||||||
this._mixerCoderSTSpec.SetCoderInfo(
|
|
||||||
i,
|
|
||||||
packSizesPointers, // &packSizesPointers.Front(),
|
|
||||||
unPackSizesPointers // &unPackSizesPointers.Front()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Decode(
|
|
||||||
IInStream inStream, long startPos,
|
|
||||||
LongVector packSizes, int packSizesOffset,
|
|
||||||
Folder folderInfo,
|
|
||||||
OutputStream outStream,
|
|
||||||
ICompressProgressInfo compressProgress
|
|
||||||
) throws IOException {
|
|
||||||
|
|
||||||
final Vector<InputStream> inStreams = folderInfo.getInStreams(
|
|
||||||
inStream,
|
|
||||||
startPos,
|
|
||||||
packSizes,
|
|
||||||
packSizesOffset);
|
|
||||||
|
|
||||||
final BindInfoEx bindInfo = folderInfo.toBindInfoEx();
|
|
||||||
|
|
||||||
if (!(this._bindInfoExPrevIsDefined && bindInfo.equals(this._bindInfoExPrev))) {
|
|
||||||
createNewCoders(bindInfo, folderInfo);
|
|
||||||
} else { /* should not happen, as far as I understood... */ }
|
|
||||||
|
|
||||||
this._mixerCoderSTSpec.ReInit();
|
|
||||||
// this._mixerCoderCommon.setCoderInfos(this._decoders, folderInfo, packSizes);
|
|
||||||
setCoderMixerCommonInfos(folderInfo, packSizes);
|
|
||||||
|
|
||||||
// int mainCoder = bindInfo.FindOutStream(bindInfo.OutStreams.get(0))[0];
|
|
||||||
|
|
||||||
if (this._multiThread) {
|
|
||||||
// _mixerCoderMTSpec.SetProgressCoderIndex(mainCoder);
|
|
||||||
throw new IOException("Multithreaded decoder is not implemented");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (folderInfo.Coders.size() == 0)
|
|
||||||
throw new IOException("no decoders available");
|
|
||||||
|
|
||||||
final Vector outStreams = new Vector(1);
|
|
||||||
outStreams.add(outStream);
|
|
||||||
|
|
||||||
this._mixerCoderSTSpec.Code(
|
|
||||||
inStreams,
|
|
||||||
//null,
|
|
||||||
inStreams.size(),
|
|
||||||
outStreams,
|
|
||||||
//null,
|
|
||||||
1,
|
|
||||||
compressProgress);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,33 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import Common.BoolVector;
|
|
||||||
|
|
||||||
public class ExtractFolderInfo {
|
|
||||||
/* #ifdef _7Z_VOL
|
|
||||||
int VolumeIndex;
|
|
||||||
#endif */
|
|
||||||
public int FileIndex;
|
|
||||||
public int FolderIndex;
|
|
||||||
public BoolVector ExtractStatuses = new BoolVector();
|
|
||||||
public long UnPackSize;
|
|
||||||
public ExtractFolderInfo(
|
|
||||||
/* #ifdef _7Z_VOL
|
|
||||||
int volumeIndex,
|
|
||||||
#endif */
|
|
||||||
int fileIndex, int folderIndex) // CNum fileIndex, CNum folderIndex
|
|
||||||
{
|
|
||||||
/* #ifdef _7Z_VOL
|
|
||||||
VolumeIndex(volumeIndex),
|
|
||||||
#endif */
|
|
||||||
FileIndex = fileIndex;
|
|
||||||
FolderIndex = folderIndex;
|
|
||||||
UnPackSize = 0;
|
|
||||||
|
|
||||||
if (fileIndex != ArchiveDB.kNumNoIndex)
|
|
||||||
{
|
|
||||||
ExtractStatuses.Reserve(1);
|
|
||||||
ExtractStatuses.add(true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,36 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
public class FileItem {
|
|
||||||
|
|
||||||
public long CreationTime;
|
|
||||||
public long LastWriteTime;
|
|
||||||
public long LastAccessTime;
|
|
||||||
|
|
||||||
public long UnPackSize;
|
|
||||||
public long StartPos;
|
|
||||||
public int Attributes;
|
|
||||||
public int FileCRC;
|
|
||||||
|
|
||||||
public boolean IsDirectory;
|
|
||||||
public boolean IsAnti;
|
|
||||||
public boolean IsFileCRCDefined;
|
|
||||||
public boolean AreAttributesDefined;
|
|
||||||
public boolean HasStream;
|
|
||||||
// public boolean IsCreationTimeDefined; replace by (CreationTime != 0)
|
|
||||||
// public boolean IsLastWriteTimeDefined; replace by (LastWriteTime != 0)
|
|
||||||
// public boolean IsLastAccessTimeDefined; replace by (LastAccessTime != 0)
|
|
||||||
public boolean IsStartPosDefined;
|
|
||||||
public String name;
|
|
||||||
|
|
||||||
public FileItem() {
|
|
||||||
HasStream = true;
|
|
||||||
IsDirectory = false;
|
|
||||||
IsAnti = false;
|
|
||||||
IsFileCRCDefined = false;
|
|
||||||
AreAttributesDefined = false;
|
|
||||||
CreationTime = 0; // IsCreationTimeDefined = false;
|
|
||||||
LastWriteTime = 0; // IsLastWriteTimeDefined = false;
|
|
||||||
LastAccessTime = 0; // IsLastAccessTimeDefined = false;
|
|
||||||
IsStartPosDefined = false;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,106 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import Common.IntVector;
|
|
||||||
import Common.LimitedSequentialInStream;
|
|
||||||
import Common.LockedInStream;
|
|
||||||
import Common.LockedSequentialInStreamImp;
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
import SevenZip.IInStream;
|
|
||||||
import SevenZip.Archive.Common.BindPair;
|
|
||||||
import SevenZip.Archive.Common.CoderStreamsInfo;
|
|
||||||
|
|
||||||
public class Folder {
|
|
||||||
|
|
||||||
public Vector<CoderInfo> Coders = new Vector();
|
|
||||||
public Vector<BindPair> BindPairs = new Vector();
|
|
||||||
public IntVector PackStreams = new IntVector();
|
|
||||||
public LongVector UnPackSizes = new LongVector();
|
|
||||||
int UnPackCRC;
|
|
||||||
boolean UnPackCRCDefined;
|
|
||||||
|
|
||||||
Folder() {
|
|
||||||
UnPackCRCDefined = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetUnPackSize() throws IOException {
|
|
||||||
if (UnPackSizes.isEmpty())
|
|
||||||
return 0;
|
|
||||||
for (int i = UnPackSizes.size() - 1; i >= 0; i--)
|
|
||||||
if (FindBindPairForOutStream(i) < 0)
|
|
||||||
return UnPackSizes.get(i);
|
|
||||||
throw new IOException("1"); // throw 1 // TBD
|
|
||||||
}
|
|
||||||
|
|
||||||
public int FindBindPairForInStream(int inStreamIndex) {
|
|
||||||
for(int i = 0; i < BindPairs.size(); i++)
|
|
||||||
if ((BindPairs.get(i)).InIndex == inStreamIndex)
|
|
||||||
return i;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int FindBindPairForOutStream(int outStreamIndex) {
|
|
||||||
for(int i = 0; i < BindPairs.size(); i++)
|
|
||||||
if ((BindPairs.get(i)).OutIndex == outStreamIndex)
|
|
||||||
return i;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int FindPackStreamArrayIndex(int inStreamIndex) {
|
|
||||||
for(int i = 0; i < PackStreams.size(); i++)
|
|
||||||
if (PackStreams.get(i) == inStreamIndex)
|
|
||||||
return i;
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetNumOutStreams() {
|
|
||||||
int result = 0;
|
|
||||||
for (int i = 0; i < Coders.size(); i++)
|
|
||||||
result += (Coders.get(i)).NumOutStreams;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Vector getInStreams(
|
|
||||||
IInStream inStream, long startPos,
|
|
||||||
LongVector packSizes, int packSizesOffset) {
|
|
||||||
final Vector inStreams = new Vector(this.PackStreams.size());
|
|
||||||
final LockedInStream lockedInStream = new LockedInStream(inStream);
|
|
||||||
for (int j = 0; j < this.PackStreams.size(); j++) {
|
|
||||||
inStreams.add(new LimitedSequentialInStream(
|
|
||||||
new LockedSequentialInStreamImp(lockedInStream, startPos),
|
|
||||||
packSizes.get(j + packSizesOffset)));
|
|
||||||
startPos += packSizes.get(j + packSizesOffset);
|
|
||||||
}
|
|
||||||
return inStreams;
|
|
||||||
}
|
|
||||||
|
|
||||||
public BindInfoEx toBindInfoEx() {
|
|
||||||
BindInfoEx bindInfo = new BindInfoEx();
|
|
||||||
|
|
||||||
for (int i = 0; i < this.BindPairs.size(); i++) {
|
|
||||||
BindPair bindPair = new BindPair();
|
|
||||||
bindPair.InIndex = (this.BindPairs.get(i)).InIndex;
|
|
||||||
bindPair.OutIndex = (this.BindPairs.get(i)).OutIndex;
|
|
||||||
bindInfo.BindPairs.add(bindPair);
|
|
||||||
}
|
|
||||||
int outStreamIndex = 0;
|
|
||||||
for (int i = 0; i < this.Coders.size(); i++) {
|
|
||||||
CoderStreamsInfo coderStreamsInfo = new CoderStreamsInfo();
|
|
||||||
CoderInfo coderInfo = this.Coders.get(i);
|
|
||||||
coderStreamsInfo.NumInStreams = coderInfo.NumInStreams;
|
|
||||||
coderStreamsInfo.NumOutStreams = coderInfo.NumOutStreams;
|
|
||||||
bindInfo.Coders.add(coderStreamsInfo);
|
|
||||||
AltCoderInfo altCoderInfo = (AltCoderInfo)coderInfo.AltCoders.firstElement();
|
|
||||||
bindInfo.CoderMethodIDs.add(altCoderInfo.MethodID);
|
|
||||||
for (int j = 0; j < coderStreamsInfo.NumOutStreams; j++, outStreamIndex++)
|
|
||||||
if (this.FindBindPairForOutStream(outStreamIndex) < 0)
|
|
||||||
bindInfo.OutStreams.add(outStreamIndex);
|
|
||||||
}
|
|
||||||
for (int i = 0; i < this.PackStreams.size(); i++)
|
|
||||||
bindInfo.InStreams.add(this.PackStreams.get(i));
|
|
||||||
return bindInfo;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,161 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
|
|
||||||
import SevenZip.Archive.Common.OutStreamWithCRC;
|
|
||||||
import SevenZip.Archive.IArchiveExtractCallback;
|
|
||||||
import SevenZip.Archive.IInArchive;
|
|
||||||
|
|
||||||
import Common.BoolVector;
|
|
||||||
|
|
||||||
public class FolderOutStream extends OutputStream {
|
|
||||||
|
|
||||||
private OutStreamWithCRC outStreamWithHashSpec;
|
|
||||||
private ArchiveDB archiveDatabase;
|
|
||||||
private BoolVector extractStatuses;
|
|
||||||
private int startIndex;
|
|
||||||
private int ref2Offset;
|
|
||||||
private IArchiveExtractCallback extractCallback;
|
|
||||||
private boolean testMode;
|
|
||||||
private int currentIndex;
|
|
||||||
private boolean fileIsOpen;
|
|
||||||
private long filePos;
|
|
||||||
|
|
||||||
public FolderOutStream(
|
|
||||||
ArchiveDB archiveDatabase,
|
|
||||||
int ref2Offset,
|
|
||||||
int startIndex,
|
|
||||||
BoolVector extractStatuses,
|
|
||||||
IArchiveExtractCallback extractCallback,
|
|
||||||
boolean testMode) throws IOException {
|
|
||||||
this(new OutStreamWithCRC(), archiveDatabase, ref2Offset, startIndex, extractStatuses, extractCallback, testMode);
|
|
||||||
}
|
|
||||||
|
|
||||||
public FolderOutStream(OutStreamWithCRC os,
|
|
||||||
ArchiveDB archiveDatabase,
|
|
||||||
int ref2Offset,
|
|
||||||
int startIndex,
|
|
||||||
BoolVector extractStatuses,
|
|
||||||
IArchiveExtractCallback extractCallback,
|
|
||||||
boolean testMode) throws IOException {
|
|
||||||
if (os == null) throw new NullPointerException();
|
|
||||||
this.outStreamWithHashSpec = os;
|
|
||||||
this.archiveDatabase = archiveDatabase;
|
|
||||||
this.ref2Offset = ref2Offset;
|
|
||||||
this.startIndex = startIndex;
|
|
||||||
|
|
||||||
this.extractStatuses = extractStatuses;
|
|
||||||
this.extractCallback = extractCallback;
|
|
||||||
this.testMode = testMode;
|
|
||||||
|
|
||||||
this.currentIndex = 0;
|
|
||||||
this.fileIsOpen = false;
|
|
||||||
WriteEmptyFiles();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void OpenFile() throws IOException {
|
|
||||||
int askMode;
|
|
||||||
if (this.extractStatuses.get(this.currentIndex)) {
|
|
||||||
askMode = this.testMode
|
|
||||||
? IInArchive.NExtract_NAskMode_kTest
|
|
||||||
: IInArchive.NExtract_NAskMode_kExtract;
|
|
||||||
} else {
|
|
||||||
askMode = IInArchive.NExtract_NAskMode_kSkip;
|
|
||||||
}
|
|
||||||
|
|
||||||
int index = this.startIndex + this.currentIndex;
|
|
||||||
|
|
||||||
OutputStream realOutStream = this.extractCallback.GetStream(this.ref2Offset + index, askMode);
|
|
||||||
this.outStreamWithHashSpec.setStream(realOutStream);
|
|
||||||
this.outStreamWithHashSpec.reset();
|
|
||||||
if (realOutStream == null && askMode == IInArchive.NExtract_NAskMode_kExtract) {
|
|
||||||
FileItem fileInfo = (FileItem)this.archiveDatabase.Files.get(index);
|
|
||||||
if (!fileInfo.IsAnti && !fileInfo.IsDirectory)
|
|
||||||
askMode = IInArchive.NExtract_NAskMode_kSkip;
|
|
||||||
}
|
|
||||||
this.extractCallback.PrepareOperation(askMode);
|
|
||||||
}
|
|
||||||
|
|
||||||
private int WriteEmptyFiles() throws IOException {
|
|
||||||
int begin = this.currentIndex;
|
|
||||||
for(;this.currentIndex < this.extractStatuses.size(); this.currentIndex++) {
|
|
||||||
int index = this.startIndex + this.currentIndex;
|
|
||||||
FileItem fileInfo = (FileItem)this.archiveDatabase.Files.get(index);
|
|
||||||
if (!fileInfo.IsAnti && !fileInfo.IsDirectory && fileInfo.UnPackSize != 0)
|
|
||||||
return -1; // return HRESULT.S_OK;
|
|
||||||
OpenFile();
|
|
||||||
|
|
||||||
this.extractCallback.SetOperationResult(IInArchive.NExtract_NOperationResult_kOK);
|
|
||||||
this.outStreamWithHashSpec.releaseStream();
|
|
||||||
}
|
|
||||||
return this.extractStatuses.size() - begin;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void write(int b) throws IOException {
|
|
||||||
throw new IOException("FolderOutStream - write() not implemented");
|
|
||||||
}
|
|
||||||
|
|
||||||
public void /* UInt32 *processedSize */ write(byte[] data, int off, int size) throws IOException {
|
|
||||||
int realProcessedSize = 0;
|
|
||||||
while(this.currentIndex < this.extractStatuses.size()) {
|
|
||||||
if (this.fileIsOpen) {
|
|
||||||
int index = this.startIndex + this.currentIndex;
|
|
||||||
FileItem fileInfo = (FileItem)this.archiveDatabase.Files.get(index);
|
|
||||||
long fileSize = fileInfo.UnPackSize;
|
|
||||||
|
|
||||||
long numBytesToWrite2 = fileSize - this.filePos;
|
|
||||||
int tmp = size - realProcessedSize;
|
|
||||||
if (tmp < numBytesToWrite2) numBytesToWrite2 = tmp;
|
|
||||||
|
|
||||||
int processedSizeLocal;
|
|
||||||
// int res = _outStreamWithHash.Write((const Byte *)data + realProcessedSize,numBytesToWrite, &processedSizeLocal));
|
|
||||||
// if (res != HRESULT.S_OK) throw new java.io.IOException("_outStreamWithHash.Write : " + res); // return res;
|
|
||||||
processedSizeLocal = (int)numBytesToWrite2;
|
|
||||||
this.outStreamWithHashSpec.write(data, realProcessedSize + off, (int)numBytesToWrite2);
|
|
||||||
|
|
||||||
this.filePos += processedSizeLocal;
|
|
||||||
realProcessedSize += processedSizeLocal;
|
|
||||||
|
|
||||||
if (this.filePos == fileSize) {
|
|
||||||
boolean digestsAreEqual = !fileInfo.IsFileCRCDefined || (fileInfo.FileCRC == this.outStreamWithHashSpec.getCRC());
|
|
||||||
this.extractCallback.SetOperationResult(digestsAreEqual ?
|
|
||||||
IInArchive.NExtract_NOperationResult_kOK :
|
|
||||||
IInArchive.NExtract_NOperationResult_kCRCError);
|
|
||||||
|
|
||||||
this.outStreamWithHashSpec.releaseStream();
|
|
||||||
this.fileIsOpen = false;
|
|
||||||
this.currentIndex++;
|
|
||||||
}
|
|
||||||
if (realProcessedSize == size) {
|
|
||||||
WriteEmptyFiles();
|
|
||||||
return ;// return realProcessedSize;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
OpenFile();
|
|
||||||
this.fileIsOpen = true;
|
|
||||||
this.filePos = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void FlushCorrupted(int resultEOperationResult) throws IOException {
|
|
||||||
while(this.currentIndex < this.extractStatuses.size()) {
|
|
||||||
if (this.fileIsOpen) {
|
|
||||||
this.extractCallback.SetOperationResult(resultEOperationResult);
|
|
||||||
|
|
||||||
this.outStreamWithHashSpec.releaseStream();
|
|
||||||
this.fileIsOpen = false;
|
|
||||||
this.currentIndex++;
|
|
||||||
} else {
|
|
||||||
OpenFile();
|
|
||||||
this.fileIsOpen = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean IsWritingFinished() {
|
|
||||||
return this.currentIndex == this.extractStatuses.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,281 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import SevenZip.HRESULT;
|
|
||||||
import SevenZip.IInStream;
|
|
||||||
import SevenZip.MyRandomAccessFile;
|
|
||||||
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
import SevenZip.Common.LocalProgress;
|
|
||||||
import SevenZip.Common.LocalCompressProgressInfo;
|
|
||||||
import SevenZip.Archive.IInArchive;
|
|
||||||
import SevenZip.Archive.IArchiveExtractCallback;
|
|
||||||
import SevenZip.Archive.SevenZipEntry;
|
|
||||||
|
|
||||||
public class Handler implements IInArchive {
|
|
||||||
|
|
||||||
public IInStream _inStream;
|
|
||||||
public ArchiveDB _database;
|
|
||||||
int _numThreads = 1; // XXX: configurable
|
|
||||||
|
|
||||||
public Handler(File archive) throws IOException {
|
|
||||||
this(new MyRandomAccessFile(archive, "r"), kMaxCheckStartPosition);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Handler(IInStream stream) throws IOException {
|
|
||||||
this(stream, kMaxCheckStartPosition);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Handler(IInStream stream, long maxCheckStartPosition) throws IOException {
|
|
||||||
InStream archive = new InStream(stream, maxCheckStartPosition);
|
|
||||||
this._database = new ArchiveDB(archive);
|
|
||||||
this._inStream = stream;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Extract(int [] indices, int numItems,
|
|
||||||
int testModeSpec, IArchiveExtractCallback extractCallback) throws IOException {
|
|
||||||
|
|
||||||
boolean testMode = (testModeSpec != 0);
|
|
||||||
long importantTotalUnPacked = 0;
|
|
||||||
|
|
||||||
boolean allFilesMode = (numItems == -1);
|
|
||||||
if (allFilesMode)
|
|
||||||
numItems = this._database.Files.size();
|
|
||||||
|
|
||||||
if (numItems == 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
Vector<ExtractFolderInfo> extractFolderInfoVector = new Vector();
|
|
||||||
for (int ii = 0; ii < numItems; ii++) {
|
|
||||||
int ref2Index = allFilesMode ? ii : indices[ii];
|
|
||||||
|
|
||||||
ArchiveDB database = _database;
|
|
||||||
int fileIndex = ref2Index;
|
|
||||||
|
|
||||||
int folderIndex = database.FileIndexToFolderIndexMap.get(fileIndex);
|
|
||||||
if (folderIndex == ArchiveDB.kNumNoIndex) {
|
|
||||||
extractFolderInfoVector.add( new ExtractFolderInfo(fileIndex, ArchiveDB.kNumNoIndex));
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (extractFolderInfoVector.isEmpty() ||
|
|
||||||
folderIndex != (extractFolderInfoVector.lastElement()).FolderIndex) {
|
|
||||||
extractFolderInfoVector.add(new ExtractFolderInfo(ArchiveDB.kNumNoIndex, folderIndex));
|
|
||||||
Folder folderInfo = database.Folders.get(folderIndex);
|
|
||||||
long unPackSize = folderInfo.GetUnPackSize();
|
|
||||||
importantTotalUnPacked += unPackSize;
|
|
||||||
extractFolderInfoVector.lastElement().UnPackSize = unPackSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
ExtractFolderInfo efi = extractFolderInfoVector.lastElement();
|
|
||||||
|
|
||||||
int startIndex = database.FolderStartFileIndex.get(folderIndex); // CNum
|
|
||||||
for (int index = efi.ExtractStatuses.size(); index <= fileIndex - startIndex; index++)
|
|
||||||
efi.ExtractStatuses.add(index == fileIndex - startIndex);
|
|
||||||
}
|
|
||||||
|
|
||||||
extractCallback.SetTotal(importantTotalUnPacked);
|
|
||||||
|
|
||||||
Decoder decoder = new Decoder(false);
|
|
||||||
|
|
||||||
long currentImportantTotalUnPacked = 0;
|
|
||||||
long totalFolderUnPacked;
|
|
||||||
|
|
||||||
for (int i = 0; i < extractFolderInfoVector.size(); i++, currentImportantTotalUnPacked += totalFolderUnPacked) {
|
|
||||||
ExtractFolderInfo efi = extractFolderInfoVector.get(i);
|
|
||||||
totalFolderUnPacked = efi.UnPackSize;
|
|
||||||
|
|
||||||
extractCallback.SetCompleted(currentImportantTotalUnPacked);
|
|
||||||
|
|
||||||
int startIndex; // CNum
|
|
||||||
if (efi.FileIndex != ArchiveDB.kNumNoIndex)
|
|
||||||
startIndex = efi.FileIndex;
|
|
||||||
else
|
|
||||||
startIndex = this._database.FolderStartFileIndex.get(efi.FolderIndex);
|
|
||||||
|
|
||||||
|
|
||||||
FolderOutStream folderOutStream = new FolderOutStream(this._database, 0, startIndex, efi.ExtractStatuses, extractCallback, testMode);
|
|
||||||
int result = HRESULT.S_OK;
|
|
||||||
|
|
||||||
if (efi.FileIndex != ArchiveDB.kNumNoIndex)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
int folderIndex = efi.FolderIndex; // CNum
|
|
||||||
Folder folderInfo = this._database.Folders.get(folderIndex);
|
|
||||||
|
|
||||||
LocalProgress localProgressSpec = new LocalProgress(extractCallback, false);
|
|
||||||
|
|
||||||
ICompressProgressInfo compressProgress = new LocalCompressProgressInfo(
|
|
||||||
localProgressSpec,
|
|
||||||
ICompressProgressInfo.INVALID,
|
|
||||||
currentImportantTotalUnPacked);
|
|
||||||
|
|
||||||
int packStreamIndex = this._database.FolderStartPackStreamIndex.get(folderIndex); // CNum
|
|
||||||
long folderStartPackPos = this._database.GetFolderStreamPos(folderIndex, 0);
|
|
||||||
|
|
||||||
try {
|
|
||||||
/* TODO: result = */ decoder.Decode(
|
|
||||||
this._inStream,
|
|
||||||
folderStartPackPos,
|
|
||||||
this._database.PackSizes,
|
|
||||||
packStreamIndex,
|
|
||||||
folderInfo,
|
|
||||||
folderOutStream,
|
|
||||||
compressProgress);
|
|
||||||
|
|
||||||
if (result == HRESULT.S_FALSE) {
|
|
||||||
folderOutStream.FlushCorrupted(IInArchive.NExtract_NOperationResult_kDataError);
|
|
||||||
// if (result != HRESULT.S_OK) return result;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (result == HRESULT.E_NOTIMPL) {
|
|
||||||
folderOutStream.FlushCorrupted(IInArchive.NExtract_NOperationResult_kUnSupportedMethod);
|
|
||||||
// if (result != HRESULT.S_OK) return result;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (folderOutStream.IsWritingFinished()) {
|
|
||||||
folderOutStream.FlushCorrupted(IInArchive.NExtract_NOperationResult_kDataError);
|
|
||||||
// if (result != HRESULT.S_OK) return result;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
} catch(Exception e) {
|
|
||||||
System.out.println("IOException : " + e);
|
|
||||||
e.printStackTrace();
|
|
||||||
folderOutStream.FlushCorrupted(IInArchive.NExtract_NOperationResult_kDataError);
|
|
||||||
// if (result != HRESULT.S_OK) return result;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() throws IOException {
|
|
||||||
if (_inStream != null) _inStream.close();
|
|
||||||
_inStream = null;
|
|
||||||
_database.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
public int size() {
|
|
||||||
return _database.Files.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
private long getPackSize(int index2) {
|
|
||||||
long packSize = 0;
|
|
||||||
int folderIndex = _database.FileIndexToFolderIndexMap.get(index2);
|
|
||||||
if (folderIndex != ArchiveDB.kNumNoIndex) {
|
|
||||||
if (_database.FolderStartFileIndex.get(folderIndex) == index2)
|
|
||||||
packSize = _database.GetFolderFullPackSize(folderIndex);
|
|
||||||
}
|
|
||||||
return packSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
private static int GetUInt32FromMemLE(byte [] p , int off) {
|
|
||||||
return p[off]
|
|
||||||
| (((int)p[off + 1]) << 8)
|
|
||||||
| (((int)p[off + 2]) << 16)
|
|
||||||
| (((int)p[off + 3]) << 24);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static String GetStringForSizeValue(int value) {
|
|
||||||
for (int i = 31; i >= 0; i--)
|
|
||||||
if ((1 << i) == value)
|
|
||||||
return Integer.toString(i);
|
|
||||||
StringBuffer result = new StringBuffer();
|
|
||||||
if (value % (1 << 20) == 0) {
|
|
||||||
result.append(value >> 20);
|
|
||||||
result.append('m');
|
|
||||||
} else if (value % (1 << 10) == 0) {
|
|
||||||
result.append(value >> 10);
|
|
||||||
result.append('k');
|
|
||||||
} else {
|
|
||||||
result.append(value);
|
|
||||||
result.append('b');
|
|
||||||
}
|
|
||||||
return result.toString();
|
|
||||||
}
|
|
||||||
|
|
||||||
private String getMethods(int index2) {
|
|
||||||
int folderIndex = _database.FileIndexToFolderIndexMap.get(index2);
|
|
||||||
if (folderIndex != ArchiveDB.kNumNoIndex) {
|
|
||||||
Folder folderInfo = _database.Folders.get(folderIndex);
|
|
||||||
StringBuffer methodsString = new StringBuffer();
|
|
||||||
for (int i = folderInfo.Coders.size() - 1; i >= 0; i--) {
|
|
||||||
CoderInfo coderInfo = folderInfo.Coders.get(i);
|
|
||||||
if (methodsString.length() > 0)
|
|
||||||
methodsString.append(' ');
|
|
||||||
|
|
||||||
// MethodInfo methodInfo;
|
|
||||||
|
|
||||||
for (int j = 0; j < coderInfo.AltCoders.size(); j++) {
|
|
||||||
if (j > 0) methodsString.append('|');
|
|
||||||
AltCoderInfo altCoderInfo = (AltCoderInfo)coderInfo.AltCoders.get(j);
|
|
||||||
|
|
||||||
if (altCoderInfo.MethodID.getName() == null) {
|
|
||||||
// TBD methodsString += altCoderInfo.MethodID.ConvertToString();
|
|
||||||
} else {
|
|
||||||
methodsString.append(altCoderInfo.MethodID.getName());
|
|
||||||
|
|
||||||
if (altCoderInfo.MethodID.equals(MethodID.k_LZMA)) {
|
|
||||||
if (altCoderInfo.Properties.size() >= 5) {
|
|
||||||
methodsString.append(':');
|
|
||||||
int dicSize = GetUInt32FromMemLE(altCoderInfo.Properties.toByteArray(), 1);
|
|
||||||
methodsString.append(GetStringForSizeValue(dicSize));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
/* else if (altCoderInfo.MethodID == k_PPMD) {
|
|
||||||
if (altCoderInfo.Properties.GetCapacity() >= 5) {
|
|
||||||
Byte order = *(const Byte *)altCoderInfo.Properties;
|
|
||||||
methodsString += ":o";
|
|
||||||
methodsString += ConvertUInt32ToString(order);
|
|
||||||
methodsString += ":mem";
|
|
||||||
UInt32 dicSize = GetUInt32FromMemLE(
|
|
||||||
((const Byte *)altCoderInfo.Properties + 1));
|
|
||||||
methodsString += GetStringForSizeValue(dicSize);
|
|
||||||
}
|
|
||||||
} else if (altCoderInfo.MethodID == k_AES) {
|
|
||||||
if (altCoderInfo.Properties.GetCapacity() >= 1) {
|
|
||||||
methodsString += ":";
|
|
||||||
const Byte *data = (const Byte *)altCoderInfo.Properties;
|
|
||||||
Byte firstByte = *data++;
|
|
||||||
UInt32 numCyclesPower = firstByte & 0x3F;
|
|
||||||
methodsString += ConvertUInt32ToString(numCyclesPower);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if (altCoderInfo.Properties.GetCapacity() > 0) {
|
|
||||||
methodsString += ":[";
|
|
||||||
for (size_t bi = 0; bi < altCoderInfo.Properties.GetCapacity(); bi++) {
|
|
||||||
if (bi > 5 && bi + 1 < altCoderInfo.Properties.GetCapacity()) {
|
|
||||||
methodsString += "..";
|
|
||||||
break;
|
|
||||||
} else
|
|
||||||
methodsString += GetHex2(altCoderInfo.Properties[bi]);
|
|
||||||
}
|
|
||||||
methodsString += "]";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return methodsString.toString();
|
|
||||||
}
|
|
||||||
|
|
||||||
return new String();
|
|
||||||
}
|
|
||||||
|
|
||||||
public SevenZipEntry getEntry(int index) {
|
|
||||||
SevenZip.Archive.SevenZip.FileItem item = (FileItem)_database.Files.get(index);
|
|
||||||
return new SevenZipEntry(
|
|
||||||
item.name,
|
|
||||||
getPackSize(index),
|
|
||||||
item.UnPackSize,
|
|
||||||
(item.IsFileCRCDefined) ? item.FileCRC & 0xFFFFFFFFL : -1,
|
|
||||||
item.LastWriteTime,
|
|
||||||
(item.IsStartPosDefined) ? item.StartPos : -1,
|
|
||||||
item.IsDirectory,
|
|
||||||
item.Attributes,
|
|
||||||
getMethods(index));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,43 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
class Header {
|
|
||||||
|
|
||||||
public static final int kSignatureSize = 6;
|
|
||||||
public static final byte [] kSignature= { '7', 'z', (byte)0xBC, (byte)0xAF, 0x27, 0x1C };
|
|
||||||
public static final byte kMajorVersion = 0;
|
|
||||||
|
|
||||||
public static class NID {
|
|
||||||
public static final int kEnd = 0;
|
|
||||||
public static final int kHeader = 1;
|
|
||||||
public static final int kArchiveProperties = 2;
|
|
||||||
public static final int kAdditionalStreamsInfo = 3;
|
|
||||||
public static final int kMainStreamsInfo = 4;
|
|
||||||
public static final int kFilesInfo = 5;
|
|
||||||
|
|
||||||
public static final int kPackInfo = 6;
|
|
||||||
public static final int kUnPackInfo = 7;
|
|
||||||
public static final int kSubStreamsInfo = 8;
|
|
||||||
|
|
||||||
public static final int kSize = 9;
|
|
||||||
public static final int kCRC = 10;
|
|
||||||
|
|
||||||
public static final int kFolder = 11;
|
|
||||||
public static final int kCodersUnPackSize = 12;
|
|
||||||
public static final int kNumUnPackStream = 13;
|
|
||||||
|
|
||||||
public static final int kEmptyStream = 14;
|
|
||||||
public static final int kEmptyFile = 15;
|
|
||||||
public static final int kAnti = 16;
|
|
||||||
|
|
||||||
public static final int kName = 17;
|
|
||||||
public static final int kCreationTime = 18;
|
|
||||||
public static final int kLastAccessTime = 19;
|
|
||||||
public static final int kLastWriteTime = 20;
|
|
||||||
public static final int kWinAttributes = 21;
|
|
||||||
public static final int kComment = 22;
|
|
||||||
|
|
||||||
public static final int kEncodedHeader = 23;
|
|
||||||
|
|
||||||
public static final int kStartPos = 24;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,18 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import Common.LongVector;
|
|
||||||
|
|
||||||
class InArchiveInfo {
|
|
||||||
public byte ArchiveVersion_Major;
|
|
||||||
public byte ArchiveVersion_Minor;
|
|
||||||
|
|
||||||
public long StartPosition;
|
|
||||||
public long StartPositionAfterHeader;
|
|
||||||
public long DataStartPosition;
|
|
||||||
public long DataStartPosition2;
|
|
||||||
LongVector FileInfoPopIDs = new LongVector();
|
|
||||||
|
|
||||||
void Clear() {
|
|
||||||
FileInfoPopIDs.clear();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,45 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
class InByte2 {
|
|
||||||
byte [] _buffer;
|
|
||||||
int _size;
|
|
||||||
int _pos;
|
|
||||||
|
|
||||||
public InByte2() {
|
|
||||||
}
|
|
||||||
|
|
||||||
public InByte2(byte [] buffer, int size) {
|
|
||||||
_buffer = buffer;
|
|
||||||
_size = size;
|
|
||||||
_pos = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadByte() throws IOException {
|
|
||||||
if(_pos >= _size)
|
|
||||||
throw new IOException("CInByte2 - Can't read stream");
|
|
||||||
return (_buffer[_pos++] & 0xFF);
|
|
||||||
}
|
|
||||||
|
|
||||||
int ReadBytes2(byte[] data, int size) {
|
|
||||||
int processedSize;
|
|
||||||
for(processedSize = 0; processedSize < size && _pos < _size; processedSize++)
|
|
||||||
data[processedSize] = _buffer[_pos++];
|
|
||||||
return processedSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean ReadBytes(byte[] data, int size) {
|
|
||||||
int processedSize = ReadBytes2(data, size);
|
|
||||||
return (processedSize == size);
|
|
||||||
}
|
|
||||||
|
|
||||||
int readBytes(ByteArrayOutputStream baos, int size) {
|
|
||||||
int processedSize;
|
|
||||||
for (processedSize = 0; processedSize < size && _pos < _size; processedSize++)
|
|
||||||
baos.write(_buffer[_pos++]);
|
|
||||||
return processedSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GetProcessedSize() { return _pos; }
|
|
||||||
}
|
|
@ -1,292 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import Common.BoolVector;
|
|
||||||
import Common.IntVector;
|
|
||||||
|
|
||||||
import SevenZip.IInStream;
|
|
||||||
import SevenZip.Common.StreamUtils;
|
|
||||||
|
|
||||||
public class InStream {
|
|
||||||
|
|
||||||
public static final int kNumMax = 0x7FFFFFFF;
|
|
||||||
|
|
||||||
final IInStream stream;
|
|
||||||
|
|
||||||
private final Vector _inByteVector = new Vector();
|
|
||||||
private /* TODO: final */ InByte2 _inByteBack = null;
|
|
||||||
|
|
||||||
final long archiveBeginStreamPosition;
|
|
||||||
long position;
|
|
||||||
|
|
||||||
public InStream(IInStream stream, long searchHeaderSizeLimit) throws IOException {
|
|
||||||
this.stream = stream;
|
|
||||||
this.position = stream.Seek(0, IInStream.STREAM_SEEK_CUR);
|
|
||||||
this.archiveBeginStreamPosition = FindAndReadSignature(searchHeaderSizeLimit);
|
|
||||||
}
|
|
||||||
|
|
||||||
private long FindAndReadSignature(
|
|
||||||
long searchHeaderSizeLimit) throws IOException {
|
|
||||||
|
|
||||||
this.stream.Seek(this.position, IInStream.STREAM_SEEK_SET);
|
|
||||||
|
|
||||||
byte[] signature = new byte[Header.kSignatureSize];
|
|
||||||
|
|
||||||
int processedSize = ReadDirect(this.stream, signature, 0, Header.kSignatureSize);
|
|
||||||
if (processedSize != Header.kSignatureSize)
|
|
||||||
throw new IOException("detected illegal signature length: " + processedSize + " at byte " + this.position);
|
|
||||||
|
|
||||||
if (TestSignatureCandidate(signature, 0))
|
|
||||||
return this.position;
|
|
||||||
|
|
||||||
// SFX support
|
|
||||||
final int kBufferSize = 1 << 16;
|
|
||||||
byte [] buffer = new byte[kBufferSize];
|
|
||||||
int numPrevBytes = Header.kSignatureSize - 1;
|
|
||||||
|
|
||||||
System.arraycopy(signature, 1, buffer, 0, numPrevBytes);
|
|
||||||
|
|
||||||
long curTestPos = this.position + 1;
|
|
||||||
while (searchHeaderSizeLimit == -1 ||
|
|
||||||
curTestPos - this.position <= searchHeaderSizeLimit) {
|
|
||||||
|
|
||||||
int numReadBytes = kBufferSize - numPrevBytes;
|
|
||||||
processedSize = ReadDirect(this.stream, buffer, numPrevBytes, numReadBytes);
|
|
||||||
if (processedSize == -1)
|
|
||||||
throw new IOException("unexpected EOF during search for signature");
|
|
||||||
|
|
||||||
int numBytesInBuffer = numPrevBytes + processedSize;
|
|
||||||
if (numBytesInBuffer < Header.kSignatureSize)
|
|
||||||
throw new IOException("detected illegal signature length: " + numBytesInBuffer + " at byte " + this.position);
|
|
||||||
|
|
||||||
int numTests = numBytesInBuffer - Header.kSignatureSize + 1;
|
|
||||||
for (int pos=0; pos<numTests; pos++, curTestPos++) {
|
|
||||||
if (TestSignatureCandidate(buffer, pos)) {
|
|
||||||
this.position = curTestPos + Header.kSignatureSize;
|
|
||||||
this.stream.Seek(this.position, IInStream.STREAM_SEEK_SET);
|
|
||||||
return curTestPos;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
numPrevBytes = numBytesInBuffer - numTests;
|
|
||||||
System.arraycopy(buffer, numTests, buffer, 0, numPrevBytes);
|
|
||||||
}
|
|
||||||
|
|
||||||
throw new IOException("signature not found within the given " + searchHeaderSizeLimit + " bytes");
|
|
||||||
}
|
|
||||||
|
|
||||||
public void AddByteStream(byte [] buffer, int size) {
|
|
||||||
this._inByteVector.add(this._inByteBack = new InByte2(buffer, size));
|
|
||||||
}
|
|
||||||
|
|
||||||
public void DeleteByteStream() {
|
|
||||||
this._inByteVector.removeElementAt(this._inByteVector.size() - 1);
|
|
||||||
if (!this._inByteVector.isEmpty())
|
|
||||||
this._inByteBack = (InByte2)this._inByteVector.lastElement();
|
|
||||||
}
|
|
||||||
|
|
||||||
public static boolean TestSignatureCandidate(byte[] testBytes, int off) {
|
|
||||||
if (off == 0)
|
|
||||||
return Arrays.equals(testBytes, Header.kSignature);
|
|
||||||
for (int i=0; i<Header.kSignatureSize; i++) {
|
|
||||||
// System.out.println(" " + i + ":" + testBytes[i] + " " + kSignature[i]);
|
|
||||||
if (testBytes[i + off] != Header.kSignature[i])
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadDirect(
|
|
||||||
IInStream stream,
|
|
||||||
byte[] data,
|
|
||||||
int off,
|
|
||||||
int size) throws IOException {
|
|
||||||
int realProcessedSize = StreamUtils.ReadStream(stream, data, off, size);
|
|
||||||
if (realProcessedSize != -1)
|
|
||||||
this.position += realProcessedSize;
|
|
||||||
return realProcessedSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadDirect(byte[] data, int size) throws IOException {
|
|
||||||
return ReadDirect(this.stream, data, 0, size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean SafeReadDirect(byte[] data, int size) throws IOException {
|
|
||||||
return (ReadDirect(data, size) == size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int SafeReadDirectUInt32() throws IOException {
|
|
||||||
int val = 0;
|
|
||||||
byte[] b = new byte[4];
|
|
||||||
|
|
||||||
int realProcessedSize = ReadDirect(b, 4);
|
|
||||||
if (realProcessedSize != 4)
|
|
||||||
throw new IOException("Unexpected End Of Archive"); // throw CInArchiveException(CInArchiveException::kUnexpectedEndOfArchive);
|
|
||||||
|
|
||||||
for (int i = 0; i < 4; i++)
|
|
||||||
val |= (b[i] & 0xFF) << (8 * i);
|
|
||||||
return val;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadUInt32() throws IOException {
|
|
||||||
int value = 0;
|
|
||||||
for (int i = 0; i < 4; i++) {
|
|
||||||
int b = ReadByte();
|
|
||||||
value |= ((b) << (8 * i));
|
|
||||||
}
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long ReadUInt64() throws IOException {
|
|
||||||
long value = 0;
|
|
||||||
for (int i = 0; i < 8; i++) {
|
|
||||||
int b = ReadByte();
|
|
||||||
value |= (((long)b) << (8 * i));
|
|
||||||
}
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean ReadBytes(byte data[], int size) throws IOException {
|
|
||||||
return this._inByteBack.ReadBytes(data, size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean ReadBytes(ByteArrayOutputStream baos, int size) throws IOException {
|
|
||||||
return this._inByteBack.readBytes(baos, size) == size;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadByte() throws IOException {
|
|
||||||
return this._inByteBack.ReadByte();
|
|
||||||
}
|
|
||||||
|
|
||||||
public long SafeReadDirectUInt64() throws IOException {
|
|
||||||
long val = 0;
|
|
||||||
byte [] b = new byte[8];
|
|
||||||
|
|
||||||
int realProcessedSize = ReadDirect(b, 8);
|
|
||||||
if (realProcessedSize != 8)
|
|
||||||
throw new IOException("Unexpected End Of Archive"); // throw CInArchiveException(CInArchiveException::kUnexpectedEndOfArchive);
|
|
||||||
|
|
||||||
for (int i = 0; i < 8; i++) {
|
|
||||||
val |= ((long)(b[i] & 0xFF) << (8 * i));
|
|
||||||
}
|
|
||||||
return val;
|
|
||||||
}
|
|
||||||
|
|
||||||
public char ReadWideCharLE() throws IOException {
|
|
||||||
int b1 = this._inByteBack.ReadByte();
|
|
||||||
int b2 = this._inByteBack.ReadByte();
|
|
||||||
char c = (char)(((char)(b2) << 8) + b1);
|
|
||||||
return c;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long ReadNumber() throws IOException {
|
|
||||||
int firstByte = ReadByte();
|
|
||||||
|
|
||||||
int mask = 0x80;
|
|
||||||
long value = 0;
|
|
||||||
for (int i = 0; i < 8; i++) {
|
|
||||||
if ((firstByte & mask) == 0) {
|
|
||||||
long highPart = firstByte & (mask - 1);
|
|
||||||
value += (highPart << (i * 8));
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
int b = ReadByte();
|
|
||||||
if (b < 0)
|
|
||||||
throw new IOException("ReadNumber - Can't read stream");
|
|
||||||
|
|
||||||
value |= (((long)b) << (8 * i));
|
|
||||||
mask >>= 1;
|
|
||||||
}
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadNum() throws IOException { // CNum
|
|
||||||
long value64 = ReadNumber();
|
|
||||||
if (value64 > InStream.kNumMax)
|
|
||||||
throw new IOException("ReadNum - value > CNum.kNumMax"); // return E_FAIL;
|
|
||||||
|
|
||||||
return (int)value64;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long ReadID() throws IOException {
|
|
||||||
return ReadNumber();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SkeepData(long size) throws IOException {
|
|
||||||
for (long i = 0; i < size; i++)
|
|
||||||
ReadByte();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SkeepData() throws IOException {
|
|
||||||
long size = ReadNumber();
|
|
||||||
SkeepData(size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void skipToAttribute(long attribute) throws IOException {
|
|
||||||
long type;
|
|
||||||
while ((type = ReadID()) != attribute) {
|
|
||||||
if (type == Header.NID.kEnd)
|
|
||||||
throw new IOException("unexpected end of archive");
|
|
||||||
SkeepData();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() throws IOException {
|
|
||||||
if (this.stream != null) this.stream.close(); // _stream.Release();
|
|
||||||
}
|
|
||||||
|
|
||||||
public BoolVector ReadBoolVector(int numItems) throws IOException {
|
|
||||||
BoolVector v = new BoolVector(numItems);
|
|
||||||
int b = 0;
|
|
||||||
int mask = 0;
|
|
||||||
for (int i=0; i<numItems; i++) {
|
|
||||||
if (mask == 0) {
|
|
||||||
b = ReadByte();
|
|
||||||
mask = 0x80;
|
|
||||||
}
|
|
||||||
v.add((b & mask) != 0);
|
|
||||||
mask >>= 1;
|
|
||||||
}
|
|
||||||
return v;
|
|
||||||
}
|
|
||||||
|
|
||||||
public BoolVector ReadBoolVector2(int numItems) throws IOException { // CBoolVector
|
|
||||||
int allAreDefined = ReadByte();
|
|
||||||
if (allAreDefined == 0)
|
|
||||||
return ReadBoolVector(numItems);
|
|
||||||
BoolVector v = new BoolVector(numItems);
|
|
||||||
for (int i = 0; i < numItems; i++)
|
|
||||||
v.add(true);
|
|
||||||
return v;
|
|
||||||
}
|
|
||||||
|
|
||||||
public IntVector ReadHashDigests(
|
|
||||||
int numItems,
|
|
||||||
BoolVector digestsDefined) throws IOException {
|
|
||||||
digestsDefined.setBoolVector(ReadBoolVector2(numItems));
|
|
||||||
final IntVector digests = new IntVector(numItems);
|
|
||||||
digests.clear();
|
|
||||||
digests.Reserve(numItems);
|
|
||||||
for (int i=0; i<numItems; i++) {
|
|
||||||
int crc = 0;
|
|
||||||
if (digestsDefined.get(i))
|
|
||||||
crc = ReadUInt32();
|
|
||||||
digests.add(crc);
|
|
||||||
}
|
|
||||||
return digests;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final long SECS_BETWEEN_EPOCHS = 11644473600L;
|
|
||||||
public static final long SECS_TO_100NS = 10000000L; /* 10^7 */
|
|
||||||
|
|
||||||
public static long FileTimeToLong(int dwHighDateTime, int dwLowDateTime) {
|
|
||||||
// The FILETIME structure is a 64-bit value representing the number of 100-nanosecond intervals since January 1
|
|
||||||
long tm = dwHighDateTime;
|
|
||||||
tm <<=32;
|
|
||||||
tm |= (dwLowDateTime & 0xFFFFFFFFL);
|
|
||||||
return (tm - (SECS_BETWEEN_EPOCHS * SECS_TO_100NS)) / (10000L); /* now convert to milliseconds */
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,83 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
public class MethodID implements Comparable {
|
|
||||||
|
|
||||||
public static final MethodID k_LZMA = new MethodID(0x3, 0x1, 0x1, "LZMA");
|
|
||||||
public static final MethodID k_PPMD = new MethodID(0x3, 0x4, 0x1, "PPMD");
|
|
||||||
public static final MethodID k_BCJ_X86 = new MethodID(0x3, 0x3, 0x1, 0x3, "BCJ_x86");
|
|
||||||
public static final MethodID k_BCJ = new MethodID(0x3, 0x3, 0x1, 0x3, "BCJ");
|
|
||||||
public static final MethodID k_BCJ2 = new MethodID(0x3, 0x3, 0x1, 0x1B, "BCJ2");
|
|
||||||
public static final MethodID k_Deflate = new MethodID(0x4, 0x1, 0x8, "Deflate");
|
|
||||||
public static final MethodID k_Deflate64 = new MethodID(0x4, 0x1, 0x9, "Defalte64");
|
|
||||||
public static final MethodID k_BZip2 = new MethodID(0x4, 0x2, 0x2, "BZip2");
|
|
||||||
public static final MethodID k_Copy = new MethodID(0x0, "Copy");
|
|
||||||
public static final MethodID k_7zAES = new MethodID(0x6, 0xF1, 0x07, 0x01, "7zAES");
|
|
||||||
|
|
||||||
public byte[] ID;
|
|
||||||
public byte IDSize;
|
|
||||||
|
|
||||||
private static final int kMethodIDSize = 15;
|
|
||||||
private final String name;
|
|
||||||
|
|
||||||
public MethodID(String name) {
|
|
||||||
this.ID = new byte[kMethodIDSize];
|
|
||||||
this.IDSize = 0;
|
|
||||||
this.name = name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public MethodID(int a, String name) {
|
|
||||||
int size = 1;
|
|
||||||
this.ID = new byte[size];
|
|
||||||
this.IDSize = (byte)size;
|
|
||||||
this.ID[0] = (byte)a;
|
|
||||||
this.name = name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public MethodID(int a, int b, int c, String name) {
|
|
||||||
int size = 3;
|
|
||||||
this.ID = new byte[size];
|
|
||||||
this.IDSize = (byte)size;
|
|
||||||
this.ID[0] = (byte)a;
|
|
||||||
this.ID[1] = (byte)b;
|
|
||||||
this.ID[2] = (byte)c;
|
|
||||||
this.name = name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public MethodID(int a, int b, int c, int d, String name) {
|
|
||||||
int size = 4;
|
|
||||||
this.ID = new byte[size];
|
|
||||||
this.IDSize = (byte)size;
|
|
||||||
this.ID[0] = (byte)a;
|
|
||||||
this.ID[1] = (byte)b;
|
|
||||||
this.ID[2] = (byte)c;
|
|
||||||
this.ID[3] = (byte)d;
|
|
||||||
this.name = name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int compareTo(Object arg) {
|
|
||||||
MethodID o = (MethodID)arg;
|
|
||||||
if (this.IDSize != o.IDSize) return (int)(this.IDSize - o.IDSize);
|
|
||||||
for (int i=0; i<this.IDSize; i++)
|
|
||||||
if (this.ID[i] != o.ID[i]) return (int)(this.ID[i] - o.ID[i]);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean equals(Object anObject) {
|
|
||||||
if (anObject instanceof MethodID) {
|
|
||||||
MethodID m = (MethodID)anObject;
|
|
||||||
if (this.IDSize != m.IDSize) return false;
|
|
||||||
for(int i = 0; i < this.IDSize ; i++)
|
|
||||||
if (this.ID[i] != m.ID[i]) return false;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
return super.equals(anObject);
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getName() {
|
|
||||||
return this.name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String toString() {
|
|
||||||
return (this.name == null) ? "undefined" : this.name;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,45 +0,0 @@
|
|||||||
package SevenZip.Archive.SevenZip;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
class StreamSwitch {
|
|
||||||
|
|
||||||
InStream _archive;
|
|
||||||
boolean _needRemove;
|
|
||||||
|
|
||||||
public StreamSwitch() {
|
|
||||||
_needRemove = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() {
|
|
||||||
Remove();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Remove() {
|
|
||||||
if (_needRemove) {
|
|
||||||
_archive.DeleteByteStream();
|
|
||||||
_needRemove = false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Set(InStream archive, byte[] data) {
|
|
||||||
Set(archive, data, data.length);
|
|
||||||
}
|
|
||||||
|
|
||||||
void Set(InStream archive, byte[] data, int size) {
|
|
||||||
Remove();
|
|
||||||
_archive = archive;
|
|
||||||
_archive.AddByteStream(data, size);
|
|
||||||
_needRemove = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Set(InStream archive, Vector dataVector) throws IOException {
|
|
||||||
Remove();
|
|
||||||
int external = archive.ReadByte();
|
|
||||||
if (external != 0) {
|
|
||||||
int dataIndex = archive.ReadNum();
|
|
||||||
Set(archive, (byte[])dataVector.get(dataIndex));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,132 +0,0 @@
|
|||||||
package SevenZip.Archive;
|
|
||||||
|
|
||||||
import SevenZip.Archive.SevenZip.MethodID;
|
|
||||||
|
|
||||||
public class SevenZipEntry {
|
|
||||||
|
|
||||||
protected long LastWriteTime;
|
|
||||||
|
|
||||||
protected long UnPackSize;
|
|
||||||
protected long PackSize;
|
|
||||||
|
|
||||||
protected int Attributes;
|
|
||||||
protected long FileCRC;
|
|
||||||
|
|
||||||
protected boolean IsDirectory;
|
|
||||||
|
|
||||||
protected String Name;
|
|
||||||
protected String Methods;
|
|
||||||
|
|
||||||
protected long Position;
|
|
||||||
|
|
||||||
public SevenZipEntry(
|
|
||||||
String name,
|
|
||||||
long packSize,
|
|
||||||
long unPackSize,
|
|
||||||
long crc,
|
|
||||||
long lastWriteTime,
|
|
||||||
long position,
|
|
||||||
boolean isDir,
|
|
||||||
int att,
|
|
||||||
String methods) {
|
|
||||||
|
|
||||||
this.Name = name;
|
|
||||||
this.PackSize = packSize;
|
|
||||||
this.UnPackSize = unPackSize;
|
|
||||||
this.FileCRC = crc;
|
|
||||||
this.LastWriteTime = lastWriteTime;
|
|
||||||
this.Position = position;
|
|
||||||
this.IsDirectory = isDir;
|
|
||||||
this.Attributes = att;
|
|
||||||
this.Methods = methods;
|
|
||||||
}
|
|
||||||
|
|
||||||
public SevenZipEntry(
|
|
||||||
String name,
|
|
||||||
long packSize,
|
|
||||||
long unPackSize,
|
|
||||||
long crc,
|
|
||||||
long lastWriteTime,
|
|
||||||
long position,
|
|
||||||
boolean isDir,
|
|
||||||
int att,
|
|
||||||
MethodID[] methods) {
|
|
||||||
|
|
||||||
this.Name = name;
|
|
||||||
this.PackSize = packSize;
|
|
||||||
this.UnPackSize = unPackSize;
|
|
||||||
this.FileCRC = crc;
|
|
||||||
this.LastWriteTime = lastWriteTime;
|
|
||||||
this.Position = position;
|
|
||||||
this.IsDirectory = isDir;
|
|
||||||
this.Attributes = att;
|
|
||||||
|
|
||||||
StringBuffer methodNames = new StringBuffer();
|
|
||||||
for (int i=0; i<methods.length; i++)
|
|
||||||
if (methods[i].getName() != null) {
|
|
||||||
if (methodNames.length() > 0)
|
|
||||||
methodNames.append(' ');
|
|
||||||
methodNames.append(methods[i].getName());
|
|
||||||
}
|
|
||||||
this.Methods = methodNames.toString();
|
|
||||||
}
|
|
||||||
|
|
||||||
public long getCompressedSize() {
|
|
||||||
return PackSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long getSize() {
|
|
||||||
return UnPackSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long getCrc() {
|
|
||||||
return FileCRC;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getName() {
|
|
||||||
return Name;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long getTime() {
|
|
||||||
return LastWriteTime;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long getPosition() {
|
|
||||||
return Position;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean isDirectory() {
|
|
||||||
return IsDirectory;
|
|
||||||
}
|
|
||||||
|
|
||||||
static final String kEmptyAttributeChar = ".";
|
|
||||||
static final String kDirectoryAttributeChar = "D";
|
|
||||||
static final String kReadonlyAttributeChar = "R";
|
|
||||||
static final String kHiddenAttributeChar = "H";
|
|
||||||
static final String kSystemAttributeChar = "S";
|
|
||||||
static final String kArchiveAttributeChar = "A";
|
|
||||||
static public final int FILE_ATTRIBUTE_READONLY = 0x00000001 ;
|
|
||||||
static public final int FILE_ATTRIBUTE_HIDDEN = 0x00000002 ;
|
|
||||||
static public final int FILE_ATTRIBUTE_SYSTEM = 0x00000004 ;
|
|
||||||
static public final int FILE_ATTRIBUTE_DIRECTORY = 0x00000010;
|
|
||||||
static public final int FILE_ATTRIBUTE_ARCHIVE = 0x00000020 ;
|
|
||||||
|
|
||||||
public String getAttributesString() {
|
|
||||||
String ret = "";
|
|
||||||
ret += ((Attributes & FILE_ATTRIBUTE_DIRECTORY) != 0 || IsDirectory) ?
|
|
||||||
kDirectoryAttributeChar: kEmptyAttributeChar;
|
|
||||||
ret += ((Attributes & FILE_ATTRIBUTE_READONLY) != 0)?
|
|
||||||
kReadonlyAttributeChar: kEmptyAttributeChar;
|
|
||||||
ret += ((Attributes & FILE_ATTRIBUTE_HIDDEN) != 0) ?
|
|
||||||
kHiddenAttributeChar: kEmptyAttributeChar;
|
|
||||||
ret += ((Attributes & FILE_ATTRIBUTE_SYSTEM) != 0) ?
|
|
||||||
kSystemAttributeChar: kEmptyAttributeChar;
|
|
||||||
ret += ((Attributes & FILE_ATTRIBUTE_ARCHIVE) != 0) ?
|
|
||||||
kArchiveAttributeChar: kEmptyAttributeChar;
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getMethods() {
|
|
||||||
return Methods;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,148 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import SevenZip.Archive.IArchiveExtractCallback;
|
|
||||||
import SevenZip.Archive.IInArchive;
|
|
||||||
import SevenZip.Archive.SevenZipEntry;
|
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.io.RandomAccessFile;
|
|
||||||
|
|
||||||
public class ArchiveExtractCallback implements IArchiveExtractCallback // , ICryptoGetTextPassword,
|
|
||||||
{
|
|
||||||
|
|
||||||
protected IInArchive archiveHandler; // IInArchive
|
|
||||||
protected String filePath; // name inside arcvhive
|
|
||||||
protected String diskFilePath; // full path to file on disk
|
|
||||||
|
|
||||||
public long NumErrors;
|
|
||||||
public boolean PasswordIsDefined;
|
|
||||||
protected String Password;
|
|
||||||
protected boolean extractMode;
|
|
||||||
|
|
||||||
protected boolean isDirectory;
|
|
||||||
protected final File exractPath;
|
|
||||||
|
|
||||||
public ArchiveExtractCallback(File extractPath) {
|
|
||||||
this.PasswordIsDefined = false;
|
|
||||||
this.exractPath = extractPath;
|
|
||||||
}
|
|
||||||
|
|
||||||
public ArchiveExtractCallback() {
|
|
||||||
this(null);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Init(IInArchive archiveHandler) {
|
|
||||||
this.NumErrors = 0;
|
|
||||||
this.archiveHandler = archiveHandler;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetTotal(long size) { }
|
|
||||||
public void SetCompleted(long completeValue) { }
|
|
||||||
|
|
||||||
public void PrepareOperation(int askExtractMode) {
|
|
||||||
this.extractMode = (askExtractMode == IInArchive.NExtract_NAskMode_kExtract);
|
|
||||||
switch (askExtractMode) {
|
|
||||||
case IInArchive.NExtract_NAskMode_kExtract:
|
|
||||||
System.out.print("Extracting ");
|
|
||||||
break;
|
|
||||||
case IInArchive.NExtract_NAskMode_kTest:
|
|
||||||
System.out.print("Testing ");
|
|
||||||
break;
|
|
||||||
case IInArchive.NExtract_NAskMode_kSkip:
|
|
||||||
System.out.print("Skipping ");
|
|
||||||
break;
|
|
||||||
};
|
|
||||||
System.out.print(this.filePath);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetOperationResult(int operationResult) throws IOException {
|
|
||||||
if (operationResult != IInArchive.NExtract_NOperationResult_kOK) {
|
|
||||||
this.NumErrors++;
|
|
||||||
System.out.print(" ");
|
|
||||||
switch(operationResult) {
|
|
||||||
case IInArchive.NExtract_NOperationResult_kUnSupportedMethod:
|
|
||||||
throw new IOException("Unsupported Method");
|
|
||||||
case IInArchive.NExtract_NOperationResult_kCRCError:
|
|
||||||
throw new IOException("CRC Failed");
|
|
||||||
case IInArchive.NExtract_NOperationResult_kDataError:
|
|
||||||
throw new IOException("Data Error");
|
|
||||||
default:
|
|
||||||
// throw new IOException("Unknown Error");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
System.out.println();
|
|
||||||
}
|
|
||||||
|
|
||||||
public OutputStream GetStream(int index, int askExtractMode) throws IOException {
|
|
||||||
RAOutputStream r = null;
|
|
||||||
SevenZipEntry item = this.archiveHandler.getEntry(index);
|
|
||||||
this.filePath = item.getName();
|
|
||||||
|
|
||||||
File file;
|
|
||||||
if (this.exractPath == null) {
|
|
||||||
file = new File(this.filePath);
|
|
||||||
} else {
|
|
||||||
file = new File(this.exractPath, this.filePath);
|
|
||||||
}
|
|
||||||
this.diskFilePath = file.getAbsolutePath();
|
|
||||||
|
|
||||||
if (askExtractMode == IInArchive.NExtract_NAskMode_kExtract) {
|
|
||||||
if (this.isDirectory = item.isDirectory()) {
|
|
||||||
if (!file.isDirectory() && !file.mkdirs())
|
|
||||||
throw new IOException("failed to make directories: " + file);
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
File dirs = file.getParentFile();
|
|
||||||
if (dirs != null && !dirs.isDirectory() && !dirs.mkdirs()) {
|
|
||||||
throw new IOException("failed to make directories: " + dirs);
|
|
||||||
}
|
|
||||||
|
|
||||||
long pos = item.getPosition();
|
|
||||||
if (pos == -1) {
|
|
||||||
file.delete();
|
|
||||||
}
|
|
||||||
|
|
||||||
RandomAccessFile outStr = new RandomAccessFile(file, "rw");
|
|
||||||
|
|
||||||
if (pos != -1)
|
|
||||||
outStr.seek(pos);
|
|
||||||
|
|
||||||
r = new RAOutputStream(outStr);
|
|
||||||
}
|
|
||||||
|
|
||||||
// other case : skip ...
|
|
||||||
return r;
|
|
||||||
}
|
|
||||||
|
|
||||||
private class RAOutputStream extends OutputStream {
|
|
||||||
RandomAccessFile file;
|
|
||||||
|
|
||||||
public RAOutputStream(RandomAccessFile f) {
|
|
||||||
this.file = f;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() throws IOException {
|
|
||||||
this.file.close();
|
|
||||||
this.file = null;
|
|
||||||
}
|
|
||||||
/*
|
|
||||||
public void flush() throws IOException {
|
|
||||||
file.flush();
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
public void write(byte[] b) throws IOException {
|
|
||||||
this.file.write(b);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void write(byte[] b, int off, int len) throws IOException {
|
|
||||||
this.file.write(b,off,len);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void write(int b) throws IOException {
|
|
||||||
this.file.write(b);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,52 +0,0 @@
|
|||||||
// SevenZip/CRC.java
|
|
||||||
|
|
||||||
package SevenZip;
|
|
||||||
|
|
||||||
public class CRC
|
|
||||||
{
|
|
||||||
static public int[] Table = new int[256];
|
|
||||||
|
|
||||||
static
|
|
||||||
{
|
|
||||||
for (int i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
int r = i;
|
|
||||||
for (int j = 0; j < 8; j++)
|
|
||||||
if ((r & 1) != 0)
|
|
||||||
r = (r >>> 1) ^ 0xEDB88320;
|
|
||||||
else
|
|
||||||
r >>>= 1;
|
|
||||||
Table[i] = r;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int _value = -1;
|
|
||||||
|
|
||||||
public void Init()
|
|
||||||
{
|
|
||||||
_value = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Update(byte[] data, int offset, int size)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < size; i++)
|
|
||||||
_value = Table[(_value ^ data[offset + i]) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Update(byte[] data)
|
|
||||||
{
|
|
||||||
int size = data.length;
|
|
||||||
for (int i = 0; i < size; i++)
|
|
||||||
_value = Table[(_value ^ data[i]) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void UpdateByte(int b)
|
|
||||||
{
|
|
||||||
_value = Table[(_value ^ b) & 0xFF] ^ (_value >>> 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetDigest()
|
|
||||||
{
|
|
||||||
return _value ^ (-1);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,77 +0,0 @@
|
|||||||
package SevenZip.Common;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
|
|
||||||
public class InBuffer {
|
|
||||||
|
|
||||||
int _bufferPos;
|
|
||||||
int _bufferLimit;
|
|
||||||
byte [] _bufferBase;
|
|
||||||
InputStream _stream = null; // CMyComPtr<ISequentialInStream>
|
|
||||||
long _processedSize;
|
|
||||||
int _bufferSize;
|
|
||||||
boolean _wasFinished;
|
|
||||||
|
|
||||||
public InBuffer() {
|
|
||||||
|
|
||||||
}
|
|
||||||
// ~CInBuffer() { Free(); }
|
|
||||||
|
|
||||||
public void Create(int bufferSize) {
|
|
||||||
final int kMinBlockSize = 1;
|
|
||||||
if (bufferSize < kMinBlockSize)
|
|
||||||
bufferSize = kMinBlockSize;
|
|
||||||
if (_bufferBase != null && _bufferSize == bufferSize)
|
|
||||||
return ;
|
|
||||||
Free();
|
|
||||||
_bufferSize = bufferSize;
|
|
||||||
_bufferBase = new byte[bufferSize];
|
|
||||||
}
|
|
||||||
void Free() {
|
|
||||||
_bufferBase = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetStream(InputStream stream) { // ISequentialInStream
|
|
||||||
_stream = stream;
|
|
||||||
}
|
|
||||||
public void Init() {
|
|
||||||
_processedSize = 0;
|
|
||||||
_bufferPos = 0; // = _bufferBase;
|
|
||||||
_bufferLimit = 0; // _buffer;
|
|
||||||
_wasFinished = false;
|
|
||||||
}
|
|
||||||
public void ReleaseStream() throws IOException {
|
|
||||||
if (_stream != null) _stream.close(); // _stream.Release();
|
|
||||||
_stream = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read() throws IOException {
|
|
||||||
if(_bufferPos >= _bufferLimit)
|
|
||||||
return ReadBlock2();
|
|
||||||
return _bufferBase[_bufferPos++] & 0xFF;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean ReadBlock() throws IOException {
|
|
||||||
if (_wasFinished)
|
|
||||||
return false;
|
|
||||||
_processedSize += _bufferPos; // (_buffer - _bufferBase);
|
|
||||||
|
|
||||||
int numProcessedBytes = _stream.read(_bufferBase, 0,_bufferSize);
|
|
||||||
if (numProcessedBytes == -1) numProcessedBytes = 0; // EOF
|
|
||||||
|
|
||||||
_bufferPos = 0; // _bufferBase;
|
|
||||||
_bufferLimit = numProcessedBytes; // _buffer + numProcessedBytes;
|
|
||||||
_wasFinished = (numProcessedBytes == 0);
|
|
||||||
return (!_wasFinished);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReadBlock2() throws IOException {
|
|
||||||
if(!ReadBlock())
|
|
||||||
return -1; // 0xFF;
|
|
||||||
return _bufferBase[_bufferPos++] & 0xFF;
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetProcessedSize() { return _processedSize + (_bufferPos); }
|
|
||||||
public boolean WasFinished() { return _wasFinished; }
|
|
||||||
}
|
|
@ -1,44 +0,0 @@
|
|||||||
package SevenZip.Common;
|
|
||||||
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
|
|
||||||
public class LocalCompressProgressInfo implements ICompressProgressInfo {
|
|
||||||
final ICompressProgressInfo _progress;
|
|
||||||
|
|
||||||
final boolean _inStartValueIsAssigned;
|
|
||||||
final boolean _outStartValueIsAssigned;
|
|
||||||
final long _inStartValue;
|
|
||||||
final long _outStartValue;
|
|
||||||
|
|
||||||
public LocalCompressProgressInfo(
|
|
||||||
ICompressProgressInfo progress,
|
|
||||||
long inStartValue,
|
|
||||||
long outStartValue) {
|
|
||||||
_progress = progress;
|
|
||||||
_inStartValueIsAssigned = (inStartValue != ICompressProgressInfo.INVALID);
|
|
||||||
_inStartValue = inStartValue;
|
|
||||||
_outStartValueIsAssigned = (outStartValue != ICompressProgressInfo.INVALID);
|
|
||||||
_outStartValue = outStartValue;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetRatioInfo(long inSize, long outSize) {
|
|
||||||
long inSizeNew, outSizeNew;
|
|
||||||
long inSizeNewPointer;
|
|
||||||
long outSizeNewPointer;
|
|
||||||
if (_inStartValueIsAssigned && inSize != ICompressProgressInfo.INVALID) {
|
|
||||||
inSizeNew = _inStartValue + (inSize); // *inSize
|
|
||||||
inSizeNewPointer = inSizeNew;
|
|
||||||
} else {
|
|
||||||
inSizeNewPointer = ICompressProgressInfo.INVALID;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_outStartValueIsAssigned && outSize != ICompressProgressInfo.INVALID) {
|
|
||||||
outSizeNew = _outStartValue + (outSize);
|
|
||||||
outSizeNewPointer = outSizeNew;
|
|
||||||
} else {
|
|
||||||
outSizeNewPointer = ICompressProgressInfo.INVALID;
|
|
||||||
}
|
|
||||||
_progress.SetRatioInfo(inSizeNewPointer, outSizeNewPointer);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,19 +0,0 @@
|
|||||||
package SevenZip.Common;
|
|
||||||
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
import SevenZip.IProgress;
|
|
||||||
|
|
||||||
public class LocalProgress implements ICompressProgressInfo {
|
|
||||||
private final IProgress _progress;
|
|
||||||
private final boolean _inSizeIsMain;
|
|
||||||
|
|
||||||
public LocalProgress(IProgress progress, boolean inSizeIsMain) {
|
|
||||||
this._progress = progress;
|
|
||||||
this._inSizeIsMain = inSizeIsMain;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetRatioInfo(long inSize, long outSize) {
|
|
||||||
_progress.SetCompleted(_inSizeIsMain ? inSize : outSize);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,27 +0,0 @@
|
|||||||
package SevenZip.Common;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
|
|
||||||
public class StreamUtils {
|
|
||||||
|
|
||||||
static public int ReadStream(InputStream stream, byte[] data, int off, int size) throws IOException {
|
|
||||||
int processedSize = 0;
|
|
||||||
|
|
||||||
while(size != 0) {
|
|
||||||
int processedSizeLoc = stream.read(data,off + processedSize,size);
|
|
||||||
if (processedSizeLoc > 0)
|
|
||||||
{
|
|
||||||
processedSize += processedSizeLoc;
|
|
||||||
size -= processedSizeLoc;
|
|
||||||
}
|
|
||||||
if (processedSizeLoc == -1) {
|
|
||||||
if (processedSize > 0) return processedSize;
|
|
||||||
return -1; // EOF
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return processedSize;
|
|
||||||
}
|
|
||||||
|
|
||||||
// HRESULT WriteStream(ISequentialOutStream *stream, const void *data, UInt32 size, UInt32 *processedSize);
|
|
||||||
}
|
|
@ -1,189 +0,0 @@
|
|||||||
|
|
||||||
package SevenZip.Compression.Branch;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
import SevenZip.Compression.LZ.OutWindow;
|
|
||||||
import SevenZip.ICompressCoder2;
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
import SevenZip.Common.InBuffer;
|
|
||||||
import SevenZip.HRESULT;
|
|
||||||
|
|
||||||
public class BCJ2_x86_Decoder implements ICompressCoder2 {
|
|
||||||
|
|
||||||
public static final int kNumMoveBits = 5;
|
|
||||||
|
|
||||||
InBuffer _mainInStream = new InBuffer();
|
|
||||||
InBuffer _callStream = new InBuffer();
|
|
||||||
InBuffer _jumpStream = new InBuffer();
|
|
||||||
|
|
||||||
SevenZip.Compression.RangeCoder.BitDecoder _statusE8Decoder[] = new SevenZip.Compression.RangeCoder.BitDecoder[256];
|
|
||||||
SevenZip.Compression.RangeCoder.BitDecoder _statusE9Decoder = new SevenZip.Compression.RangeCoder.BitDecoder(kNumMoveBits);
|
|
||||||
SevenZip.Compression.RangeCoder.BitDecoder _statusJccDecoder = new SevenZip.Compression.RangeCoder.BitDecoder(kNumMoveBits);
|
|
||||||
|
|
||||||
OutWindow _outStream = new OutWindow();
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder _rangeDecoder = new SevenZip.Compression.RangeCoder.Decoder();
|
|
||||||
|
|
||||||
|
|
||||||
// static final boolean IsJcc(int b0, int b1) {
|
|
||||||
// return ((b0 == 0x0F) && ((b1 & 0xF0) == 0x80));
|
|
||||||
// }
|
|
||||||
|
|
||||||
int CodeReal(
|
|
||||||
Vector<InputStream> inStreams,
|
|
||||||
//Object useless1, // const UInt64 ** /* inSizes */,
|
|
||||||
int numInStreams,
|
|
||||||
Vector<OutputStream> outStreams,
|
|
||||||
//Object useless2, // const UInt64 ** /* outSizes */,
|
|
||||||
int numOutStreams,
|
|
||||||
ICompressProgressInfo progress) throws java.io.IOException {
|
|
||||||
|
|
||||||
if (numInStreams != 4 || numOutStreams != 1)
|
|
||||||
throw new IllegalArgumentException("numInStreams != 4 || numOutStreams != 1");
|
|
||||||
|
|
||||||
_mainInStream.Create(1 << 16);
|
|
||||||
_callStream.Create(1 << 20);
|
|
||||||
_jumpStream.Create(1 << 16);
|
|
||||||
_rangeDecoder.Create(1 << 20);
|
|
||||||
_outStream.Create(1 << 16);
|
|
||||||
|
|
||||||
_mainInStream.SetStream(inStreams.get(0));
|
|
||||||
_callStream.SetStream(inStreams.get(1));
|
|
||||||
_jumpStream.SetStream(inStreams.get(2));
|
|
||||||
_rangeDecoder.SetStream(inStreams.get(3));
|
|
||||||
_outStream.SetStream(outStreams.get(0));
|
|
||||||
|
|
||||||
_mainInStream.Init();
|
|
||||||
_callStream.Init();
|
|
||||||
_jumpStream.Init();
|
|
||||||
_rangeDecoder.Init();
|
|
||||||
_outStream.Init();
|
|
||||||
|
|
||||||
for (int i = 0; i < 256; i++) {
|
|
||||||
_statusE8Decoder[i] = new SevenZip.Compression.RangeCoder.BitDecoder(kNumMoveBits);
|
|
||||||
_statusE8Decoder[i].Init();
|
|
||||||
}
|
|
||||||
_statusE9Decoder.Init();
|
|
||||||
_statusJccDecoder.Init();
|
|
||||||
|
|
||||||
int prevByte = 0;
|
|
||||||
int processedBytes = 0;
|
|
||||||
for (;;) {
|
|
||||||
|
|
||||||
if (processedBytes > (1 << 20) && progress != null) {
|
|
||||||
long nowPos64 = _outStream.GetProcessedSize();
|
|
||||||
progress.SetRatioInfo(ICompressProgressInfo.INVALID, nowPos64);
|
|
||||||
processedBytes = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
processedBytes++;
|
|
||||||
int b = _mainInStream.read();
|
|
||||||
if (b == -1) {
|
|
||||||
Flush();
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
_outStream.WriteByte(b); // System.out.println("0:"+b);
|
|
||||||
// if ((b != 0xE8) && (b != 0xE9) && (!IsJcc(prevByte, b))) {
|
|
||||||
if ((b != 0xE8) && (b != 0xE9) && (!((prevByte == 0x0F) && ((b & 0xF0) == 0x80)))) {
|
|
||||||
prevByte = b;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
boolean status;
|
|
||||||
if (b == 0xE8)
|
|
||||||
status = (_statusE8Decoder[prevByte].Decode(_rangeDecoder) == 1);
|
|
||||||
else if (b == 0xE9)
|
|
||||||
status = (_statusE9Decoder.Decode(_rangeDecoder) == 1);
|
|
||||||
else
|
|
||||||
status = (_statusJccDecoder.Decode(_rangeDecoder) == 1);
|
|
||||||
|
|
||||||
if (status) {
|
|
||||||
int src;
|
|
||||||
if (b == 0xE8) {
|
|
||||||
int b0 = _callStream.read();
|
|
||||||
// if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src = ((int)b0) << 24;
|
|
||||||
|
|
||||||
b0 = _callStream.read();
|
|
||||||
// if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src |= ((int)b0) << 16;
|
|
||||||
|
|
||||||
b0 = _callStream.read();
|
|
||||||
// if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src |= ((int)b0) << 8;
|
|
||||||
|
|
||||||
b0 = _callStream.read();
|
|
||||||
if (b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src |= ((int)b0);
|
|
||||||
|
|
||||||
} else {
|
|
||||||
int b0 = _jumpStream.read();
|
|
||||||
// if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src = ((int)b0) << 24;
|
|
||||||
|
|
||||||
b0 = _jumpStream.read();
|
|
||||||
// if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src |= ((int)b0) << 16;
|
|
||||||
|
|
||||||
b0 = _jumpStream.read();
|
|
||||||
// if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src |= ((int)b0) << 8;
|
|
||||||
|
|
||||||
b0 = _jumpStream.read();
|
|
||||||
if(b0 == -1) return HRESULT.S_FALSE;
|
|
||||||
src |= ((int)b0);
|
|
||||||
|
|
||||||
}
|
|
||||||
int dest = src - ((int)_outStream.GetProcessedSize() + 4) ;
|
|
||||||
_outStream.WriteByte(dest);
|
|
||||||
_outStream.WriteByte((dest >> 8));
|
|
||||||
_outStream.WriteByte((dest >> 16));
|
|
||||||
_outStream.WriteByte((dest >> 24));
|
|
||||||
prevByte = (int)(dest >> 24) & 0xFF;
|
|
||||||
processedBytes += 4;
|
|
||||||
} else
|
|
||||||
prevByte = b;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Flush() throws IOException {
|
|
||||||
_outStream.Flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public int Code(
|
|
||||||
Vector<InputStream> inStreams, // ISequentialInStream **inStreams,
|
|
||||||
//Object useless_inSizes, // const UInt64 ** /* inSizes */,
|
|
||||||
int numInStreams,
|
|
||||||
Vector<OutputStream> outStreams, // ISequentialOutStream **outStreams
|
|
||||||
//Object useless_outSizes, // const UInt64 ** /* outSizes */,
|
|
||||||
int numOutStreams,
|
|
||||||
ICompressProgressInfo progress) throws java.io.IOException {
|
|
||||||
|
|
||||||
try {
|
|
||||||
return CodeReal(inStreams, /*useless_inSizes,*/ numInStreams,
|
|
||||||
outStreams, /*useless_outSizes,*/ numOutStreams, progress);
|
|
||||||
} catch(java.io.IOException e) {
|
|
||||||
throw e;
|
|
||||||
} finally {
|
|
||||||
ReleaseStreams();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void ReleaseStreams() throws java.io.IOException {
|
|
||||||
_mainInStream.ReleaseStream();
|
|
||||||
_callStream.ReleaseStream();
|
|
||||||
_jumpStream.ReleaseStream();
|
|
||||||
_rangeDecoder.ReleaseStream();
|
|
||||||
_outStream.ReleaseStream();
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void close() throws java.io.IOException {
|
|
||||||
ReleaseStreams();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
@ -1,114 +0,0 @@
|
|||||||
package SevenZip.Compression.Branch;
|
|
||||||
|
|
||||||
import SevenZip.HRESULT;
|
|
||||||
import SevenZip.ICompressFilter;
|
|
||||||
|
|
||||||
public class BCJ_x86_Decoder implements ICompressFilter {
|
|
||||||
|
|
||||||
// struct CBranch86 - begin
|
|
||||||
int [] _prevMask = new int[1]; // UInt32
|
|
||||||
int [] _prevPos = new int[1]; // UInt32
|
|
||||||
void x86Init() {
|
|
||||||
_prevMask[0] = 0;
|
|
||||||
_prevPos[0] = -5;
|
|
||||||
}
|
|
||||||
// struct CBranch86 - end
|
|
||||||
|
|
||||||
static final boolean [] kMaskToAllowedStatus = {true, true, true, false, true, false, false, false };
|
|
||||||
|
|
||||||
static final int [] kMaskToBitNumber = {0, 1, 2, 2, 3, 3, 3, 3};
|
|
||||||
|
|
||||||
static final boolean Test86MSByte(int b) { return ((b) == 0 || (b) == 0xFF); }
|
|
||||||
|
|
||||||
static final int x86_Convert(byte [] buffer, int endPos, int nowPos,
|
|
||||||
int [] prevMask, int [] prevPos, boolean encoding) {
|
|
||||||
int bufferPos = 0;
|
|
||||||
int limit;
|
|
||||||
|
|
||||||
if (endPos < 5)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if (nowPos - prevPos[0] > 5)
|
|
||||||
prevPos[0] = nowPos - 5;
|
|
||||||
|
|
||||||
limit = endPos - 5;
|
|
||||||
while(bufferPos <= limit) {
|
|
||||||
int b = (buffer[bufferPos] & 0xFF);
|
|
||||||
int offset;
|
|
||||||
if (b != 0xE8 && b != 0xE9) {
|
|
||||||
bufferPos++;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
offset = (nowPos + bufferPos - prevPos[0]);
|
|
||||||
prevPos[0] = (nowPos + bufferPos);
|
|
||||||
if (offset > 5)
|
|
||||||
prevMask[0] = 0;
|
|
||||||
else {
|
|
||||||
for (int i = 0; i < offset; i++) {
|
|
||||||
prevMask[0] &= 0x77;
|
|
||||||
prevMask[0] <<= 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
b = (buffer[bufferPos + 4] & 0xFF);
|
|
||||||
if (Test86MSByte(b) && kMaskToAllowedStatus[(prevMask[0] >> 1) & 0x7] &&
|
|
||||||
(prevMask[0] >>> 1) < 0x10) {
|
|
||||||
int src =
|
|
||||||
((int)(b) << 24) |
|
|
||||||
((int)(buffer[bufferPos + 3] & 0xFF) << 16) |
|
|
||||||
((int)(buffer[bufferPos + 2] & 0xFF) << 8) |
|
|
||||||
(buffer[bufferPos + 1] & 0xFF);
|
|
||||||
|
|
||||||
int dest;
|
|
||||||
for (;;) {
|
|
||||||
int index;
|
|
||||||
if (encoding)
|
|
||||||
dest = (nowPos + bufferPos + 5) + src;
|
|
||||||
else
|
|
||||||
dest = src - (nowPos + bufferPos + 5);
|
|
||||||
if (prevMask[0] == 0)
|
|
||||||
break;
|
|
||||||
index = kMaskToBitNumber[prevMask[0] >>> 1];
|
|
||||||
b = (int)((dest >> (24 - index * 8)) & 0xFF);
|
|
||||||
if (!Test86MSByte(b))
|
|
||||||
break;
|
|
||||||
src = dest ^ ((1 << (32 - index * 8)) - 1);
|
|
||||||
}
|
|
||||||
buffer[bufferPos + 4] = (byte)(~(((dest >> 24) & 1) - 1));
|
|
||||||
buffer[bufferPos + 3] = (byte)(dest >> 16);
|
|
||||||
buffer[bufferPos + 2] = (byte)(dest >> 8);
|
|
||||||
buffer[bufferPos + 1] = (byte)dest;
|
|
||||||
bufferPos += 5;
|
|
||||||
prevMask[0] = 0;
|
|
||||||
} else {
|
|
||||||
bufferPos++;
|
|
||||||
prevMask[0] |= 1;
|
|
||||||
if (Test86MSByte(b))
|
|
||||||
prevMask[0] |= 0x10;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return bufferPos;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int SubFilter(byte [] data, int size) {
|
|
||||||
return x86_Convert(data, size, _bufferPos, _prevMask, _prevPos, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SubInit() {
|
|
||||||
x86Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
int _bufferPos; // UInt32
|
|
||||||
|
|
||||||
// ICompressFilter interface
|
|
||||||
public int Init() {
|
|
||||||
_bufferPos = 0;
|
|
||||||
SubInit();
|
|
||||||
return HRESULT.S_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int Filter(byte [] data, int size) {
|
|
||||||
int processedSize = SubFilter(data, size);
|
|
||||||
_bufferPos += processedSize;
|
|
||||||
return processedSize;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,36 +0,0 @@
|
|||||||
|
|
||||||
package SevenZip.Compression.Copy;
|
|
||||||
|
|
||||||
import SevenZip.ICompressCoder;
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
|
|
||||||
public class Decoder implements ICompressCoder {
|
|
||||||
|
|
||||||
static final int kBufferSize = 1 << 17;
|
|
||||||
|
|
||||||
public void Code(
|
|
||||||
java.io.InputStream inStream, // , ISequentialInStream
|
|
||||||
java.io.OutputStream outStream, // ISequentialOutStream
|
|
||||||
long outSize, ICompressProgressInfo progress) throws java.io.IOException {
|
|
||||||
|
|
||||||
byte [] _buffer = new byte[kBufferSize];
|
|
||||||
long TotalSize = 0;
|
|
||||||
|
|
||||||
for (;;) {
|
|
||||||
int realProcessedSize;
|
|
||||||
int size = kBufferSize;
|
|
||||||
|
|
||||||
if (outSize != -1) // NULL
|
|
||||||
if (size > (outSize - TotalSize))
|
|
||||||
size = (int)(outSize - TotalSize);
|
|
||||||
|
|
||||||
realProcessedSize = inStream.read(_buffer, 0,size);
|
|
||||||
if(realProcessedSize == -1) // EOF
|
|
||||||
break;
|
|
||||||
outStream.write(_buffer,0,realProcessedSize);
|
|
||||||
TotalSize += realProcessedSize;
|
|
||||||
if (progress != null)
|
|
||||||
progress.SetRatioInfo(TotalSize, TotalSize);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,383 +0,0 @@
|
|||||||
// LZ.BinTree
|
|
||||||
|
|
||||||
package SevenZip.Compression.LZ;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public class BinTree extends InWindow
|
|
||||||
{
|
|
||||||
int _cyclicBufferPos;
|
|
||||||
int _cyclicBufferSize = 0;
|
|
||||||
int _matchMaxLen;
|
|
||||||
|
|
||||||
int[] _son;
|
|
||||||
int[] _hash;
|
|
||||||
|
|
||||||
int _cutValue = 0xFF;
|
|
||||||
int _hashMask;
|
|
||||||
int _hashSizeSum = 0;
|
|
||||||
|
|
||||||
boolean HASH_ARRAY = true;
|
|
||||||
|
|
||||||
static final int kHash2Size = 1 << 10;
|
|
||||||
static final int kHash3Size = 1 << 16;
|
|
||||||
static final int kBT2HashSize = 1 << 16;
|
|
||||||
static final int kStartMaxLen = 1;
|
|
||||||
static final int kHash3Offset = kHash2Size;
|
|
||||||
static final int kEmptyHashValue = 0;
|
|
||||||
static final int kMaxValForNormalize = (1 << 30) - 1;
|
|
||||||
|
|
||||||
int kNumHashDirectBytes = 0;
|
|
||||||
int kMinMatchCheck = 4;
|
|
||||||
int kFixHashSize = kHash2Size + kHash3Size;
|
|
||||||
|
|
||||||
public void SetType(int numHashBytes)
|
|
||||||
{
|
|
||||||
HASH_ARRAY = (numHashBytes > 2);
|
|
||||||
if (HASH_ARRAY)
|
|
||||||
{
|
|
||||||
kNumHashDirectBytes = 0;
|
|
||||||
kMinMatchCheck = 4;
|
|
||||||
kFixHashSize = kHash2Size + kHash3Size;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
kNumHashDirectBytes = 2;
|
|
||||||
kMinMatchCheck = 2 + 1;
|
|
||||||
kFixHashSize = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public void Init() throws IOException
|
|
||||||
{
|
|
||||||
super.Init();
|
|
||||||
for (int i = 0; i < _hashSizeSum; i++)
|
|
||||||
_hash[i] = kEmptyHashValue;
|
|
||||||
_cyclicBufferPos = 0;
|
|
||||||
ReduceOffsets(-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void MovePos() throws IOException
|
|
||||||
{
|
|
||||||
if (++_cyclicBufferPos >= _cyclicBufferSize)
|
|
||||||
_cyclicBufferPos = 0;
|
|
||||||
super.MovePos();
|
|
||||||
if (_pos == kMaxValForNormalize)
|
|
||||||
Normalize();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public boolean Create(int historySize, int keepAddBufferBefore,
|
|
||||||
int matchMaxLen, int keepAddBufferAfter)
|
|
||||||
{
|
|
||||||
if (historySize > kMaxValForNormalize - 256)
|
|
||||||
return false;
|
|
||||||
_cutValue = 16 + (matchMaxLen >> 1);
|
|
||||||
|
|
||||||
int windowReservSize = (historySize + keepAddBufferBefore +
|
|
||||||
matchMaxLen + keepAddBufferAfter) / 2 + 256;
|
|
||||||
|
|
||||||
super.Create(historySize + keepAddBufferBefore, matchMaxLen + keepAddBufferAfter, windowReservSize);
|
|
||||||
|
|
||||||
_matchMaxLen = matchMaxLen;
|
|
||||||
|
|
||||||
int cyclicBufferSize = historySize + 1;
|
|
||||||
if (_cyclicBufferSize != cyclicBufferSize)
|
|
||||||
_son = new int[(_cyclicBufferSize = cyclicBufferSize) * 2];
|
|
||||||
|
|
||||||
int hs = kBT2HashSize;
|
|
||||||
|
|
||||||
if (HASH_ARRAY)
|
|
||||||
{
|
|
||||||
hs = historySize - 1;
|
|
||||||
hs |= (hs >> 1);
|
|
||||||
hs |= (hs >> 2);
|
|
||||||
hs |= (hs >> 4);
|
|
||||||
hs |= (hs >> 8);
|
|
||||||
hs >>= 1;
|
|
||||||
hs |= 0xFFFF;
|
|
||||||
if (hs > (1 << 24))
|
|
||||||
hs >>= 1;
|
|
||||||
_hashMask = hs;
|
|
||||||
hs++;
|
|
||||||
hs += kFixHashSize;
|
|
||||||
}
|
|
||||||
if (hs != _hashSizeSum)
|
|
||||||
_hash = new int [_hashSizeSum = hs];
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
public int GetMatches(int[] distances) throws IOException
|
|
||||||
{
|
|
||||||
int lenLimit;
|
|
||||||
if (_pos + _matchMaxLen <= _streamPos)
|
|
||||||
lenLimit = _matchMaxLen;
|
|
||||||
else
|
|
||||||
{
|
|
||||||
lenLimit = _streamPos - _pos;
|
|
||||||
if (lenLimit < kMinMatchCheck)
|
|
||||||
{
|
|
||||||
MovePos();
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int offset = 0;
|
|
||||||
int matchMinPos = (_pos > _cyclicBufferSize) ? (_pos - _cyclicBufferSize) : 0;
|
|
||||||
int cur = _bufferOffset + _pos;
|
|
||||||
int maxLen = kStartMaxLen; // to avoid items for len < hashSize;
|
|
||||||
int hashValue, hash2Value = 0, hash3Value = 0;
|
|
||||||
|
|
||||||
if (HASH_ARRAY)
|
|
||||||
{
|
|
||||||
int temp = CrcTable[_bufferBase[cur] & 0xFF] ^ (_bufferBase[cur + 1] & 0xFF);
|
|
||||||
hash2Value = temp & (kHash2Size - 1);
|
|
||||||
temp ^= ((int)(_bufferBase[cur + 2] & 0xFF) << 8);
|
|
||||||
hash3Value = temp & (kHash3Size - 1);
|
|
||||||
hashValue = (temp ^ (CrcTable[_bufferBase[cur + 3] & 0xFF] << 5)) & _hashMask;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
hashValue = ((_bufferBase[cur] & 0xFF) ^ ((int)(_bufferBase[cur + 1] & 0xFF) << 8));
|
|
||||||
|
|
||||||
int curMatch = _hash[kFixHashSize + hashValue];
|
|
||||||
if (HASH_ARRAY)
|
|
||||||
{
|
|
||||||
int curMatch2 = _hash[hash2Value];
|
|
||||||
int curMatch3 = _hash[kHash3Offset + hash3Value];
|
|
||||||
_hash[hash2Value] = _pos;
|
|
||||||
_hash[kHash3Offset + hash3Value] = _pos;
|
|
||||||
if (curMatch2 > matchMinPos)
|
|
||||||
if (_bufferBase[_bufferOffset + curMatch2] == _bufferBase[cur])
|
|
||||||
{
|
|
||||||
distances[offset++] = maxLen = 2;
|
|
||||||
distances[offset++] = _pos - curMatch2 - 1;
|
|
||||||
}
|
|
||||||
if (curMatch3 > matchMinPos)
|
|
||||||
if (_bufferBase[_bufferOffset + curMatch3] == _bufferBase[cur])
|
|
||||||
{
|
|
||||||
if (curMatch3 == curMatch2)
|
|
||||||
offset -= 2;
|
|
||||||
distances[offset++] = maxLen = 3;
|
|
||||||
distances[offset++] = _pos - curMatch3 - 1;
|
|
||||||
curMatch2 = curMatch3;
|
|
||||||
}
|
|
||||||
if (offset != 0 && curMatch2 == curMatch)
|
|
||||||
{
|
|
||||||
offset -= 2;
|
|
||||||
maxLen = kStartMaxLen;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
_hash[kFixHashSize + hashValue] = _pos;
|
|
||||||
|
|
||||||
int ptr0 = (_cyclicBufferPos << 1) + 1;
|
|
||||||
int ptr1 = (_cyclicBufferPos << 1);
|
|
||||||
|
|
||||||
int len0, len1;
|
|
||||||
len0 = len1 = kNumHashDirectBytes;
|
|
||||||
|
|
||||||
if (kNumHashDirectBytes != 0)
|
|
||||||
{
|
|
||||||
if (curMatch > matchMinPos)
|
|
||||||
{
|
|
||||||
if (_bufferBase[_bufferOffset + curMatch + kNumHashDirectBytes] !=
|
|
||||||
_bufferBase[cur + kNumHashDirectBytes])
|
|
||||||
{
|
|
||||||
distances[offset++] = maxLen = kNumHashDirectBytes;
|
|
||||||
distances[offset++] = _pos - curMatch - 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int count = _cutValue;
|
|
||||||
|
|
||||||
while (true)
|
|
||||||
{
|
|
||||||
if (curMatch <= matchMinPos || count-- == 0)
|
|
||||||
{
|
|
||||||
_son[ptr0] = _son[ptr1] = kEmptyHashValue;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
int delta = _pos - curMatch;
|
|
||||||
int cyclicPos = ((delta <= _cyclicBufferPos) ?
|
|
||||||
(_cyclicBufferPos - delta) :
|
|
||||||
(_cyclicBufferPos - delta + _cyclicBufferSize)) << 1;
|
|
||||||
|
|
||||||
int pby1 = _bufferOffset + curMatch;
|
|
||||||
int len = Math.min(len0, len1);
|
|
||||||
if (_bufferBase[pby1 + len] == _bufferBase[cur + len])
|
|
||||||
{
|
|
||||||
while(++len != lenLimit)
|
|
||||||
if (_bufferBase[pby1 + len] != _bufferBase[cur + len])
|
|
||||||
break;
|
|
||||||
if (maxLen < len)
|
|
||||||
{
|
|
||||||
distances[offset++] = maxLen = len;
|
|
||||||
distances[offset++] = delta - 1;
|
|
||||||
if (len == lenLimit)
|
|
||||||
{
|
|
||||||
_son[ptr1] = _son[cyclicPos];
|
|
||||||
_son[ptr0] = _son[cyclicPos + 1];
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if ((_bufferBase[pby1 + len] & 0xFF) < (_bufferBase[cur + len] & 0xFF))
|
|
||||||
{
|
|
||||||
_son[ptr1] = curMatch;
|
|
||||||
ptr1 = cyclicPos + 1;
|
|
||||||
curMatch = _son[ptr1];
|
|
||||||
len1 = len;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_son[ptr0] = curMatch;
|
|
||||||
ptr0 = cyclicPos;
|
|
||||||
curMatch = _son[ptr0];
|
|
||||||
len0 = len;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
MovePos();
|
|
||||||
return offset;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Skip(int num) throws IOException
|
|
||||||
{
|
|
||||||
do
|
|
||||||
{
|
|
||||||
int lenLimit;
|
|
||||||
if (_pos + _matchMaxLen <= _streamPos)
|
|
||||||
lenLimit = _matchMaxLen;
|
|
||||||
else
|
|
||||||
{
|
|
||||||
lenLimit = _streamPos - _pos;
|
|
||||||
if (lenLimit < kMinMatchCheck)
|
|
||||||
{
|
|
||||||
MovePos();
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int matchMinPos = (_pos > _cyclicBufferSize) ? (_pos - _cyclicBufferSize) : 0;
|
|
||||||
int cur = _bufferOffset + _pos;
|
|
||||||
|
|
||||||
int hashValue;
|
|
||||||
|
|
||||||
if (HASH_ARRAY)
|
|
||||||
{
|
|
||||||
int temp = CrcTable[_bufferBase[cur] & 0xFF] ^ (_bufferBase[cur + 1] & 0xFF);
|
|
||||||
int hash2Value = temp & (kHash2Size - 1);
|
|
||||||
_hash[hash2Value] = _pos;
|
|
||||||
temp ^= ((int)(_bufferBase[cur + 2] & 0xFF) << 8);
|
|
||||||
int hash3Value = temp & (kHash3Size - 1);
|
|
||||||
_hash[kHash3Offset + hash3Value] = _pos;
|
|
||||||
hashValue = (temp ^ (CrcTable[_bufferBase[cur + 3] & 0xFF] << 5)) & _hashMask;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
hashValue = ((_bufferBase[cur] & 0xFF) ^ ((int)(_bufferBase[cur + 1] & 0xFF) << 8));
|
|
||||||
|
|
||||||
int curMatch = _hash[kFixHashSize + hashValue];
|
|
||||||
_hash[kFixHashSize + hashValue] = _pos;
|
|
||||||
|
|
||||||
int ptr0 = (_cyclicBufferPos << 1) + 1;
|
|
||||||
int ptr1 = (_cyclicBufferPos << 1);
|
|
||||||
|
|
||||||
int len0, len1;
|
|
||||||
len0 = len1 = kNumHashDirectBytes;
|
|
||||||
|
|
||||||
int count = _cutValue;
|
|
||||||
while (true)
|
|
||||||
{
|
|
||||||
if (curMatch <= matchMinPos || count-- == 0)
|
|
||||||
{
|
|
||||||
_son[ptr0] = _son[ptr1] = kEmptyHashValue;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
int delta = _pos - curMatch;
|
|
||||||
int cyclicPos = ((delta <= _cyclicBufferPos) ?
|
|
||||||
(_cyclicBufferPos - delta) :
|
|
||||||
(_cyclicBufferPos - delta + _cyclicBufferSize)) << 1;
|
|
||||||
|
|
||||||
int pby1 = _bufferOffset + curMatch;
|
|
||||||
int len = Math.min(len0, len1);
|
|
||||||
if (_bufferBase[pby1 + len] == _bufferBase[cur + len])
|
|
||||||
{
|
|
||||||
while (++len != lenLimit)
|
|
||||||
if (_bufferBase[pby1 + len] != _bufferBase[cur + len])
|
|
||||||
break;
|
|
||||||
if (len == lenLimit)
|
|
||||||
{
|
|
||||||
_son[ptr1] = _son[cyclicPos];
|
|
||||||
_son[ptr0] = _son[cyclicPos + 1];
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if ((_bufferBase[pby1 + len] & 0xFF) < (_bufferBase[cur + len] & 0xFF))
|
|
||||||
{
|
|
||||||
_son[ptr1] = curMatch;
|
|
||||||
ptr1 = cyclicPos + 1;
|
|
||||||
curMatch = _son[ptr1];
|
|
||||||
len1 = len;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_son[ptr0] = curMatch;
|
|
||||||
ptr0 = cyclicPos;
|
|
||||||
curMatch = _son[ptr0];
|
|
||||||
len0 = len;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
MovePos();
|
|
||||||
}
|
|
||||||
while (--num != 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
void NormalizeLinks(int[] items, int numItems, int subValue)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < numItems; i++)
|
|
||||||
{
|
|
||||||
int value = items[i];
|
|
||||||
if (value <= subValue)
|
|
||||||
value = kEmptyHashValue;
|
|
||||||
else
|
|
||||||
value -= subValue;
|
|
||||||
items[i] = value;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Normalize()
|
|
||||||
{
|
|
||||||
int subValue = _pos - _cyclicBufferSize;
|
|
||||||
NormalizeLinks(_son, _cyclicBufferSize * 2, subValue);
|
|
||||||
NormalizeLinks(_hash, _hashSizeSum, subValue);
|
|
||||||
ReduceOffsets(subValue);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetCutValue(int cutValue) { _cutValue = cutValue; }
|
|
||||||
|
|
||||||
private static final int[] CrcTable = new int[256];
|
|
||||||
|
|
||||||
static
|
|
||||||
{
|
|
||||||
for (int i = 0; i < 256; i++)
|
|
||||||
{
|
|
||||||
int r = i;
|
|
||||||
for (int j = 0; j < 8; j++)
|
|
||||||
if ((r & 1) != 0)
|
|
||||||
r = (r >>> 1) ^ 0xEDB88320;
|
|
||||||
else
|
|
||||||
r >>>= 1;
|
|
||||||
CrcTable[i] = r;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,131 +0,0 @@
|
|||||||
// LZ.InWindow
|
|
||||||
|
|
||||||
package SevenZip.Compression.LZ;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public class InWindow
|
|
||||||
{
|
|
||||||
public byte[] _bufferBase; // pointer to buffer with data
|
|
||||||
java.io.InputStream _stream;
|
|
||||||
int _posLimit; // offset (from _buffer) of first byte when new block reading must be done
|
|
||||||
boolean _streamEndWasReached; // if (true) then _streamPos shows real end of stream
|
|
||||||
|
|
||||||
int _pointerToLastSafePosition;
|
|
||||||
|
|
||||||
public int _bufferOffset;
|
|
||||||
|
|
||||||
public int _blockSize; // Size of Allocated memory block
|
|
||||||
public int _pos; // offset (from _buffer) of curent byte
|
|
||||||
int _keepSizeBefore; // how many BYTEs must be kept in buffer before _pos
|
|
||||||
int _keepSizeAfter; // how many BYTEs must be kept buffer after _pos
|
|
||||||
public int _streamPos; // offset (from _buffer) of first not read byte from Stream
|
|
||||||
|
|
||||||
public void MoveBlock()
|
|
||||||
{
|
|
||||||
int offset = _bufferOffset + _pos - _keepSizeBefore;
|
|
||||||
// we need one additional byte, since MovePos moves on 1 byte.
|
|
||||||
if (offset > 0)
|
|
||||||
offset--;
|
|
||||||
|
|
||||||
int numBytes = _bufferOffset + _streamPos - offset;
|
|
||||||
|
|
||||||
// check negative offset ????
|
|
||||||
for (int i = 0; i < numBytes; i++)
|
|
||||||
_bufferBase[i] = _bufferBase[offset + i];
|
|
||||||
_bufferOffset -= offset;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ReadBlock() throws IOException
|
|
||||||
{
|
|
||||||
if (_streamEndWasReached)
|
|
||||||
return;
|
|
||||||
while (true)
|
|
||||||
{
|
|
||||||
int size = (0 - _bufferOffset) + _blockSize - _streamPos;
|
|
||||||
if (size == 0)
|
|
||||||
return;
|
|
||||||
int numReadBytes = _stream.read(_bufferBase, _bufferOffset + _streamPos, size);
|
|
||||||
if (numReadBytes == -1)
|
|
||||||
{
|
|
||||||
_posLimit = _streamPos;
|
|
||||||
int pointerToPostion = _bufferOffset + _posLimit;
|
|
||||||
if (pointerToPostion > _pointerToLastSafePosition)
|
|
||||||
_posLimit = _pointerToLastSafePosition - _bufferOffset;
|
|
||||||
|
|
||||||
_streamEndWasReached = true;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
_streamPos += numReadBytes;
|
|
||||||
if (_streamPos >= _pos + _keepSizeAfter)
|
|
||||||
_posLimit = _streamPos - _keepSizeAfter;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void Free() { _bufferBase = null; }
|
|
||||||
|
|
||||||
public void Create(int keepSizeBefore, int keepSizeAfter, int keepSizeReserv)
|
|
||||||
{
|
|
||||||
_keepSizeBefore = keepSizeBefore;
|
|
||||||
_keepSizeAfter = keepSizeAfter;
|
|
||||||
int blockSize = keepSizeBefore + keepSizeAfter + keepSizeReserv;
|
|
||||||
if (_bufferBase == null || _blockSize != blockSize)
|
|
||||||
{
|
|
||||||
Free();
|
|
||||||
_blockSize = blockSize;
|
|
||||||
_bufferBase = new byte[_blockSize];
|
|
||||||
}
|
|
||||||
_pointerToLastSafePosition = _blockSize - keepSizeAfter;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetStream(java.io.InputStream stream) { _stream = stream; }
|
|
||||||
public void ReleaseStream() { _stream = null; }
|
|
||||||
|
|
||||||
public void Init() throws IOException
|
|
||||||
{
|
|
||||||
_bufferOffset = 0;
|
|
||||||
_pos = 0;
|
|
||||||
_streamPos = 0;
|
|
||||||
_streamEndWasReached = false;
|
|
||||||
ReadBlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void MovePos() throws IOException
|
|
||||||
{
|
|
||||||
_pos++;
|
|
||||||
if (_pos > _posLimit)
|
|
||||||
{
|
|
||||||
int pointerToPostion = _bufferOffset + _pos;
|
|
||||||
if (pointerToPostion > _pointerToLastSafePosition)
|
|
||||||
MoveBlock();
|
|
||||||
ReadBlock();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public byte GetIndexByte(int index) { return _bufferBase[_bufferOffset + _pos + index]; }
|
|
||||||
|
|
||||||
// index + limit have not to exceed _keepSizeAfter;
|
|
||||||
public int GetMatchLen(int index, int distance, int limit)
|
|
||||||
{
|
|
||||||
if (_streamEndWasReached)
|
|
||||||
if ((_pos + index) + limit > _streamPos)
|
|
||||||
limit = _streamPos - (_pos + index);
|
|
||||||
distance++;
|
|
||||||
// Byte *pby = _buffer + (size_t)_pos + index;
|
|
||||||
int pby = _bufferOffset + _pos + index;
|
|
||||||
|
|
||||||
int i;
|
|
||||||
for (i = 0; i < limit && _bufferBase[pby + i] == _bufferBase[pby + i - distance]; i++);
|
|
||||||
return i;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetNumAvailableBytes() { return _streamPos - _pos; }
|
|
||||||
|
|
||||||
public void ReduceOffsets(int subValue)
|
|
||||||
{
|
|
||||||
_bufferOffset += subValue;
|
|
||||||
_posLimit -= subValue;
|
|
||||||
_pos -= subValue;
|
|
||||||
_streamPos -= subValue;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,107 +0,0 @@
|
|||||||
// LZ.OutWindow
|
|
||||||
|
|
||||||
package SevenZip.Compression.LZ;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public class OutWindow {
|
|
||||||
byte[] _buffer;
|
|
||||||
byte[] _buffer2 = null;
|
|
||||||
int _bufferPos2 = 0;
|
|
||||||
int _pos;
|
|
||||||
int _windowSize = 0;
|
|
||||||
int _streamPos;
|
|
||||||
java.io.OutputStream _stream;
|
|
||||||
long _processedSize;
|
|
||||||
|
|
||||||
public void Create(int windowSize) {
|
|
||||||
final int kMinBlockSize = 1;
|
|
||||||
if (windowSize < kMinBlockSize)
|
|
||||||
windowSize = kMinBlockSize;
|
|
||||||
|
|
||||||
if (_buffer == null || _windowSize != windowSize)
|
|
||||||
_buffer = new byte[windowSize];
|
|
||||||
_windowSize = windowSize;
|
|
||||||
_pos = 0;
|
|
||||||
_streamPos = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetStream(java.io.OutputStream stream) throws IOException {
|
|
||||||
ReleaseStream();
|
|
||||||
_stream = stream;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ReleaseStream() throws IOException {
|
|
||||||
Flush();
|
|
||||||
_stream = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetMemStream(byte [] d) {
|
|
||||||
_buffer2 = d;
|
|
||||||
_bufferPos2 = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Init() {
|
|
||||||
Init(false);
|
|
||||||
}
|
|
||||||
public void Init(boolean solid) {
|
|
||||||
_processedSize = 0;
|
|
||||||
if (!solid) {
|
|
||||||
_streamPos = 0;
|
|
||||||
_pos = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Flush() throws IOException {
|
|
||||||
int size = _pos - _streamPos;
|
|
||||||
if (size == 0)
|
|
||||||
return;
|
|
||||||
if (_stream != null) _stream.write(_buffer, _streamPos, size);
|
|
||||||
if (_buffer2 != null) {
|
|
||||||
System.arraycopy(_buffer, _streamPos, _buffer2, _bufferPos2, size);
|
|
||||||
_bufferPos2 += size;
|
|
||||||
}
|
|
||||||
if (_pos >= _windowSize)
|
|
||||||
_pos = 0;
|
|
||||||
_streamPos = _pos;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void CopyBlock(int distance, int len) throws IOException {
|
|
||||||
int pos = _pos - distance - 1;
|
|
||||||
if (pos < 0)
|
|
||||||
pos += _windowSize;
|
|
||||||
for (; len != 0; len--) {
|
|
||||||
if (pos >= _windowSize)
|
|
||||||
pos = 0;
|
|
||||||
_buffer[_pos++] = _buffer[pos++];
|
|
||||||
_processedSize++;
|
|
||||||
if (_pos >= _windowSize)
|
|
||||||
Flush();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void PutByte(byte b) throws IOException {
|
|
||||||
_buffer[_pos++] = b;
|
|
||||||
_processedSize++;
|
|
||||||
if (_pos >= _windowSize)
|
|
||||||
Flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void WriteByte(int b) throws IOException {
|
|
||||||
_buffer[_pos++] = (byte)b;
|
|
||||||
_processedSize++;
|
|
||||||
if (_pos >= _windowSize)
|
|
||||||
Flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
public byte GetByte(int distance) {
|
|
||||||
int pos = _pos - distance - 1;
|
|
||||||
if (pos < 0)
|
|
||||||
pos += _windowSize;
|
|
||||||
return _buffer[pos];
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetProcessedSize() {
|
|
||||||
return _processedSize;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,88 +0,0 @@
|
|||||||
// Base.java
|
|
||||||
|
|
||||||
package SevenZip.Compression.LZMA;
|
|
||||||
|
|
||||||
public class Base
|
|
||||||
{
|
|
||||||
public static final int kNumRepDistances = 4;
|
|
||||||
public static final int kNumStates = 12;
|
|
||||||
|
|
||||||
public static final int StateInit()
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final int StateUpdateChar(int index)
|
|
||||||
{
|
|
||||||
if (index < 4)
|
|
||||||
return 0;
|
|
||||||
if (index < 10)
|
|
||||||
return index - 3;
|
|
||||||
return index - 6;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final int StateUpdateMatch(int index)
|
|
||||||
{
|
|
||||||
return (index < 7 ? 7 : 10);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final int StateUpdateRep(int index)
|
|
||||||
{
|
|
||||||
return (index < 7 ? 8 : 11);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final int StateUpdateShortRep(int index)
|
|
||||||
{
|
|
||||||
return (index < 7 ? 9 : 11);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final boolean StateIsCharState(int index)
|
|
||||||
{
|
|
||||||
return index < 7;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final int kNumPosSlotBits = 6;
|
|
||||||
public static final int kDicLogSizeMin = 0;
|
|
||||||
// public static final int kDicLogSizeMax = 28;
|
|
||||||
// public static final int kDistTableSizeMax = kDicLogSizeMax * 2;
|
|
||||||
|
|
||||||
public static final int kNumLenToPosStatesBits = 2; // it's for speed optimization
|
|
||||||
public static final int kNumLenToPosStates = 1 << kNumLenToPosStatesBits;
|
|
||||||
|
|
||||||
public static final int kMatchMinLen = 2;
|
|
||||||
|
|
||||||
public static final int GetLenToPosState(int len)
|
|
||||||
{
|
|
||||||
len -= kMatchMinLen;
|
|
||||||
if (len < kNumLenToPosStates)
|
|
||||||
return len;
|
|
||||||
return (int)(kNumLenToPosStates - 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static final int kNumAlignBits = 4;
|
|
||||||
public static final int kAlignTableSize = 1 << kNumAlignBits;
|
|
||||||
public static final int kAlignMask = (kAlignTableSize - 1);
|
|
||||||
|
|
||||||
public static final int kStartPosModelIndex = 4;
|
|
||||||
public static final int kEndPosModelIndex = 14;
|
|
||||||
public static final int kNumPosModels = kEndPosModelIndex - kStartPosModelIndex;
|
|
||||||
|
|
||||||
public static final int kNumFullDistances = 1 << (kEndPosModelIndex / 2);
|
|
||||||
|
|
||||||
public static final int kNumLitPosStatesBitsEncodingMax = 4;
|
|
||||||
public static final int kNumLitContextBitsMax = 8;
|
|
||||||
|
|
||||||
public static final int kNumPosStatesBitsMax = 4;
|
|
||||||
public static final int kNumPosStatesMax = (1 << kNumPosStatesBitsMax);
|
|
||||||
public static final int kNumPosStatesBitsEncodingMax = 4;
|
|
||||||
public static final int kNumPosStatesEncodingMax = (1 << kNumPosStatesBitsEncodingMax);
|
|
||||||
|
|
||||||
public static final int kNumLowLenBits = 3;
|
|
||||||
public static final int kNumMidLenBits = 3;
|
|
||||||
public static final int kNumHighLenBits = 8;
|
|
||||||
public static final int kNumLowLenSymbols = 1 << kNumLowLenBits;
|
|
||||||
public static final int kNumMidLenSymbols = 1 << kNumMidLenBits;
|
|
||||||
public static final int kNumLenSymbols = kNumLowLenSymbols + kNumMidLenSymbols +
|
|
||||||
(1 << kNumHighLenBits);
|
|
||||||
public static final int kMatchMaxLen = kMatchMinLen + kNumLenSymbols - 1;
|
|
||||||
}
|
|
@ -1,437 +0,0 @@
|
|||||||
package SevenZip.Compression.LZMA;
|
|
||||||
|
|
||||||
import SevenZip.ICompressCoder;
|
|
||||||
import SevenZip.ICompressGetInStreamProcessedSize;
|
|
||||||
import SevenZip.ICompressProgressInfo;
|
|
||||||
import SevenZip.ICompressSetInStream;
|
|
||||||
import SevenZip.ICompressSetOutStreamSize;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
|
|
||||||
import SevenZip.Compression.LZ.OutWindow;
|
|
||||||
import SevenZip.Compression.RangeCoder.BitTreeDecoder;
|
|
||||||
|
|
||||||
public class Decoder extends InputStream implements ICompressCoder, ICompressGetInStreamProcessedSize,
|
|
||||||
ICompressSetInStream, ICompressSetOutStreamSize {
|
|
||||||
|
|
||||||
private static final int kLenIdFinished = -1;
|
|
||||||
private static final int kLenIdNeedInit = -2;
|
|
||||||
|
|
||||||
private final SevenZip.Compression.RangeCoder.Decoder m_RangeDecoder = new SevenZip.Compression.RangeCoder.Decoder();
|
|
||||||
private final OutWindow m_OutWindow = new OutWindow();
|
|
||||||
|
|
||||||
private final short[] m_IsMatchDecoders = new short[Base.kNumStates << Base.kNumPosStatesBitsMax];
|
|
||||||
private final short[] m_IsRepDecoders = new short[Base.kNumStates];
|
|
||||||
private final short[] m_IsRepG0Decoders = new short[Base.kNumStates];
|
|
||||||
private final short[] m_IsRepG1Decoders = new short[Base.kNumStates];
|
|
||||||
private final short[] m_IsRepG2Decoders = new short[Base.kNumStates];
|
|
||||||
private final short[] m_IsRep0LongDecoders = new short[Base.kNumStates << Base.kNumPosStatesBitsMax];
|
|
||||||
private final short[] m_PosDecoders = new short[Base.kNumFullDistances - Base.kEndPosModelIndex];
|
|
||||||
|
|
||||||
private final BitTreeDecoder[] m_PosSlotDecoder = new BitTreeDecoder[Base.kNumLenToPosStates];
|
|
||||||
private final BitTreeDecoder m_PosAlignDecoder = new BitTreeDecoder(Base.kNumAlignBits);
|
|
||||||
|
|
||||||
private final LenDecoder m_LenDecoder;
|
|
||||||
private final LenDecoder m_RepLenDecoder;
|
|
||||||
|
|
||||||
private final LiteralDecoder m_LiteralDecoder;
|
|
||||||
|
|
||||||
private final int m_DictionarySize;
|
|
||||||
private final int m_DictionarySizeCheck;
|
|
||||||
|
|
||||||
private int m_posStateMask;
|
|
||||||
|
|
||||||
private long _outSize = 0;
|
|
||||||
private boolean _outSizeDefined = false;
|
|
||||||
private int _remainLen; // -1 means end of stream. // -2 means need Init
|
|
||||||
private int _rep0;
|
|
||||||
private int _rep1;
|
|
||||||
private int _rep2;
|
|
||||||
private int _rep3;
|
|
||||||
private int _state;
|
|
||||||
|
|
||||||
public Decoder(byte[] properties) {
|
|
||||||
for (int i = 0; i < Base.kNumLenToPosStates; i++)
|
|
||||||
this.m_PosSlotDecoder[i] = new BitTreeDecoder(Base.kNumPosSlotBits);
|
|
||||||
|
|
||||||
if (properties.length < 5)
|
|
||||||
throw new IllegalArgumentException("properties.length < 5");
|
|
||||||
int val = properties[0] & 0xFF;
|
|
||||||
int lc = val % 9;
|
|
||||||
int remainder = val / 9;
|
|
||||||
int lp = remainder % 5;
|
|
||||||
int pb = remainder / 5;
|
|
||||||
int dictionarySize = 0;
|
|
||||||
for (int i = 0; i < 4; i++)
|
|
||||||
dictionarySize += ((int)(properties[1 + i]) & 0xFF) << (i * 8);
|
|
||||||
|
|
||||||
// Set lc, lp, pb
|
|
||||||
if (lc > Base.kNumLitContextBitsMax || lp > 4 || pb > Base.kNumPosStatesBitsMax)
|
|
||||||
throw new IllegalArgumentException("lc > Base.kNumLitContextBitsMax || lp > 4 || pb > Base.kNumPosStatesBitsMax");
|
|
||||||
// if (this.m_LiteralDecoder != null) throw new NullPointerException("LiteralDecoder != null, WTF?!"); // hint: skip use of not initialized static variable
|
|
||||||
this.m_LiteralDecoder = new LiteralDecoder(lp, lc);
|
|
||||||
int numPosStates = 1 << pb;
|
|
||||||
this.m_LenDecoder = new LenDecoder(numPosStates);
|
|
||||||
this.m_RepLenDecoder = new LenDecoder(numPosStates);
|
|
||||||
this.m_posStateMask = numPosStates - 1;
|
|
||||||
|
|
||||||
// set dictionary size
|
|
||||||
if (dictionarySize < 0)
|
|
||||||
throw new IllegalArgumentException("dictionarySize must not be smaller than 0");
|
|
||||||
this.m_DictionarySize = dictionarySize;
|
|
||||||
this.m_DictionarySizeCheck = Math.max(this.m_DictionarySize, 1);
|
|
||||||
this.m_OutWindow.Create(Math.max(this.m_DictionarySizeCheck, (1 << 12)));
|
|
||||||
this.m_RangeDecoder.Create(1 << 20);
|
|
||||||
}
|
|
||||||
|
|
||||||
public long GetInStreamProcessedSize() {
|
|
||||||
throw new UnknownError("GetInStreamProcessedSize");
|
|
||||||
// return m_RangeDecoder.GetProcessedSize();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ReleaseInStream() throws IOException {
|
|
||||||
this.m_RangeDecoder.ReleaseStream();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetInStream(InputStream inStream) { // Common.ISequentialInStream
|
|
||||||
this.m_RangeDecoder.SetStream(inStream);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void SetOutStreamSize(long outSize /* const UInt64 *outSize*/ ) {
|
|
||||||
this._outSizeDefined = (outSize != ICompressSetOutStreamSize.INVALID_OUTSIZE);
|
|
||||||
if (this._outSizeDefined)
|
|
||||||
this._outSize = outSize;
|
|
||||||
this._remainLen = kLenIdNeedInit;
|
|
||||||
this.m_OutWindow.Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
// #ifdef _ST_MODE
|
|
||||||
public int read() throws IOException {
|
|
||||||
throw new IOException("LZMA Decoder - read() not implemented");
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read(byte [] data, int off, int size) throws IOException {
|
|
||||||
if (off != 0) throw new IOException("LZMA Decoder - read(byte [] data, int off != 0, int size)) not implemented");
|
|
||||||
|
|
||||||
long startPos = this.m_OutWindow.GetProcessedSize();
|
|
||||||
this.m_OutWindow.SetMemStream(data);
|
|
||||||
CodeSpec(size);
|
|
||||||
Flush();
|
|
||||||
int ret = (int)(this.m_OutWindow.GetProcessedSize() - startPos);
|
|
||||||
if (ret == 0) ret = -1;
|
|
||||||
return ret;
|
|
||||||
}
|
|
||||||
|
|
||||||
// #endif // _ST_MODE
|
|
||||||
|
|
||||||
private void Init() throws IOException {
|
|
||||||
this.m_OutWindow.Init(false);
|
|
||||||
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_IsMatchDecoders);
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_IsRep0LongDecoders);
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_IsRepDecoders);
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_IsRepG0Decoders);
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_IsRepG1Decoders);
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_IsRepG2Decoders);
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_PosDecoders);
|
|
||||||
|
|
||||||
this._rep0 = this._rep1 = this._rep2 = this._rep3 = 0;
|
|
||||||
this._state = Base.StateInit();
|
|
||||||
|
|
||||||
// this.m_LiteralDecoder.Init();
|
|
||||||
for (int i = 0; i < Base.kNumLenToPosStates; i++)
|
|
||||||
this.m_PosSlotDecoder[i].Init();
|
|
||||||
// this.m_LenDecoder.Init();
|
|
||||||
// this.m_RepLenDecoder.Init();
|
|
||||||
this.m_PosAlignDecoder.Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Flush() throws IOException {
|
|
||||||
this.m_OutWindow.Flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
private void ReleaseStreams() throws IOException {
|
|
||||||
this.m_OutWindow.ReleaseStream();
|
|
||||||
ReleaseInStream();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void CodeReal(
|
|
||||||
InputStream inStream, // , ISequentialInStream
|
|
||||||
OutputStream outStream, // ISequentialOutStream
|
|
||||||
long outSize,
|
|
||||||
ICompressProgressInfo progress // useless_progress
|
|
||||||
) throws IOException {
|
|
||||||
SetInStream(inStream);
|
|
||||||
this.m_OutWindow.SetStream(outStream);
|
|
||||||
SetOutStreamSize(outSize);
|
|
||||||
|
|
||||||
do {
|
|
||||||
int curSize = 1 << 18;
|
|
||||||
CodeSpec(curSize);
|
|
||||||
if (this._remainLen == kLenIdFinished)
|
|
||||||
break;
|
|
||||||
|
|
||||||
if (progress != null) {
|
|
||||||
long inSize = this.m_RangeDecoder.GetProcessedSize();
|
|
||||||
long nowPos64 = this.m_OutWindow.GetProcessedSize();
|
|
||||||
progress.SetRatioInfo(inSize, nowPos64);
|
|
||||||
}
|
|
||||||
} while (!this._outSizeDefined || this.m_OutWindow.GetProcessedSize() < this._outSize);
|
|
||||||
Flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Code(
|
|
||||||
InputStream inStream, // , ISequentialInStream
|
|
||||||
OutputStream outStream, // ISequentialOutStream
|
|
||||||
long outSize,
|
|
||||||
ICompressProgressInfo progress // useless_progress
|
|
||||||
) throws IOException {
|
|
||||||
try {
|
|
||||||
CodeReal(inStream,outStream,outSize,progress);
|
|
||||||
} finally {
|
|
||||||
Flush();
|
|
||||||
ReleaseStreams();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void CodeSpec(int curSize) throws IOException {
|
|
||||||
if (this._outSizeDefined) {
|
|
||||||
long rem = this._outSize - this.m_OutWindow.GetProcessedSize();
|
|
||||||
if (curSize > rem)
|
|
||||||
curSize = (int)rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this._remainLen == kLenIdFinished)
|
|
||||||
return;
|
|
||||||
if (this._remainLen == kLenIdNeedInit) {
|
|
||||||
this.m_RangeDecoder.Init();
|
|
||||||
Init();
|
|
||||||
this._remainLen = 0;
|
|
||||||
}
|
|
||||||
if (curSize == 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
int rep0 = this._rep0;
|
|
||||||
int rep1 = this._rep1;
|
|
||||||
int rep2 = this._rep2;
|
|
||||||
int rep3 = this._rep3;
|
|
||||||
int state = this._state;
|
|
||||||
byte prevByte;
|
|
||||||
|
|
||||||
while(this._remainLen > 0 && curSize > 0) {
|
|
||||||
prevByte = this.m_OutWindow.GetByte(rep0);
|
|
||||||
this.m_OutWindow.PutByte(prevByte);
|
|
||||||
this._remainLen--;
|
|
||||||
curSize--;
|
|
||||||
}
|
|
||||||
long nowPos64 = this.m_OutWindow.GetProcessedSize();
|
|
||||||
if (nowPos64 == 0) {
|
|
||||||
prevByte = 0;
|
|
||||||
} else {
|
|
||||||
prevByte = this.m_OutWindow.GetByte(0);
|
|
||||||
}
|
|
||||||
|
|
||||||
while(curSize > 0) {
|
|
||||||
if (this.m_RangeDecoder.bufferedStream.WasFinished())
|
|
||||||
throw new IOException("m_RangeDecoder.bufferedStream was finised");
|
|
||||||
// return HRESULT.S_FALSE;
|
|
||||||
int posState = (int)nowPos64 & this.m_posStateMask;
|
|
||||||
|
|
||||||
if (this.m_RangeDecoder.DecodeBit(this.m_IsMatchDecoders, (state << Base.kNumPosStatesBitsMax) + posState) == 0) {
|
|
||||||
LiteralDecoder.Decoder2 decoder2 = this.m_LiteralDecoder.GetDecoder((int)nowPos64, prevByte);
|
|
||||||
if (!Base.StateIsCharState(state)) {
|
|
||||||
prevByte = decoder2.DecodeWithMatchByte(this.m_RangeDecoder, this.m_OutWindow.GetByte(rep0));
|
|
||||||
} else {
|
|
||||||
prevByte = decoder2.DecodeNormal(this.m_RangeDecoder);
|
|
||||||
}
|
|
||||||
this.m_OutWindow.PutByte(prevByte);
|
|
||||||
state = Base.StateUpdateChar(state);
|
|
||||||
curSize--;
|
|
||||||
nowPos64++;
|
|
||||||
} else {
|
|
||||||
int len;
|
|
||||||
if (this.m_RangeDecoder.DecodeBit(this.m_IsRepDecoders, state) == 1) {
|
|
||||||
len = 0;
|
|
||||||
if (this.m_RangeDecoder.DecodeBit(this.m_IsRepG0Decoders, state) == 0) {
|
|
||||||
if (this.m_RangeDecoder.DecodeBit(this.m_IsRep0LongDecoders, (state << Base.kNumPosStatesBitsMax) + posState) == 0) {
|
|
||||||
state = Base.StateUpdateShortRep(state);
|
|
||||||
len = 1;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
int distance;
|
|
||||||
if (this.m_RangeDecoder.DecodeBit(this.m_IsRepG1Decoders, state) == 0) {
|
|
||||||
distance = rep1;
|
|
||||||
} else {
|
|
||||||
if (this.m_RangeDecoder.DecodeBit(this.m_IsRepG2Decoders, state) == 0) {
|
|
||||||
distance = rep2;
|
|
||||||
} else {
|
|
||||||
distance = rep3;
|
|
||||||
rep3 = rep2;
|
|
||||||
}
|
|
||||||
rep2 = rep1;
|
|
||||||
}
|
|
||||||
rep1 = rep0;
|
|
||||||
rep0 = distance;
|
|
||||||
}
|
|
||||||
if (len == 0) {
|
|
||||||
len = this.m_RepLenDecoder.Decode(this.m_RangeDecoder, posState) + Base.kMatchMinLen;
|
|
||||||
state = Base.StateUpdateRep(state);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
rep3 = rep2;
|
|
||||||
rep2 = rep1;
|
|
||||||
rep1 = rep0;
|
|
||||||
len = Base.kMatchMinLen + this.m_LenDecoder.Decode(this.m_RangeDecoder, posState);
|
|
||||||
state = Base.StateUpdateMatch(state);
|
|
||||||
int posSlot = this.m_PosSlotDecoder[Base.GetLenToPosState(len)].Decode(this.m_RangeDecoder);
|
|
||||||
if (posSlot >= Base.kStartPosModelIndex) {
|
|
||||||
int numDirectBits = (posSlot >> 1) - 1;
|
|
||||||
rep0 = ((2 | (posSlot & 1)) << numDirectBits);
|
|
||||||
if (posSlot < Base.kEndPosModelIndex) {
|
|
||||||
rep0 += BitTreeDecoder.ReverseDecode(
|
|
||||||
this.m_PosDecoders,
|
|
||||||
rep0 - posSlot - 1,
|
|
||||||
this.m_RangeDecoder,
|
|
||||||
numDirectBits);
|
|
||||||
} else {
|
|
||||||
rep0 += (this.m_RangeDecoder.DecodeDirectBits(numDirectBits - Base.kNumAlignBits) << Base.kNumAlignBits);
|
|
||||||
rep0 += this.m_PosAlignDecoder.ReverseDecode(this.m_RangeDecoder);
|
|
||||||
if (rep0 < 0) {
|
|
||||||
if (rep0 == -1)
|
|
||||||
break;
|
|
||||||
throw new IOException("rep0 == -1");
|
|
||||||
// return HRESULT.S_FALSE;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
rep0 = posSlot;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (rep0 >= nowPos64 || rep0 >= this.m_DictionarySizeCheck) {
|
|
||||||
// m_OutWindow.Flush();
|
|
||||||
this._remainLen = kLenIdFinished;
|
|
||||||
throw new IOException("rep0 >= nowPos64 || rep0 >= m_DictionarySizeCheck");
|
|
||||||
// return HRESULT.S_FALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int locLen = len;
|
|
||||||
if (len > curSize)
|
|
||||||
locLen = curSize;
|
|
||||||
// if (!m_OutWindow.CopyBlock(rep0, locLen))
|
|
||||||
// return HRESULT.S_FALSE;
|
|
||||||
this.m_OutWindow.CopyBlock(rep0, locLen);
|
|
||||||
prevByte = this.m_OutWindow.GetByte(0);
|
|
||||||
curSize -= locLen;
|
|
||||||
nowPos64 += locLen;
|
|
||||||
len -= locLen;
|
|
||||||
if (len != 0) {
|
|
||||||
this._remainLen = len;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.m_RangeDecoder.bufferedStream.WasFinished())
|
|
||||||
throw new IOException("m_RangeDecoder.bufferedStream was finised");
|
|
||||||
|
|
||||||
this._rep0 = rep0;
|
|
||||||
this._rep1 = rep1;
|
|
||||||
this._rep2 = rep2;
|
|
||||||
this._rep3 = rep3;
|
|
||||||
this._state = state;
|
|
||||||
}
|
|
||||||
|
|
||||||
private class LenDecoder {
|
|
||||||
|
|
||||||
private final short[] m_Choice = new short[2];
|
|
||||||
private final BitTreeDecoder[] m_LowCoder = new BitTreeDecoder[Base.kNumPosStatesMax];
|
|
||||||
private final BitTreeDecoder[] m_MidCoder = new BitTreeDecoder[Base.kNumPosStatesMax];
|
|
||||||
private final BitTreeDecoder m_HighCoder = new BitTreeDecoder(Base.kNumHighLenBits);
|
|
||||||
private int m_NumPosStates = 0;
|
|
||||||
|
|
||||||
public LenDecoder(int numPosStates) {
|
|
||||||
while (this.m_NumPosStates < numPosStates) {
|
|
||||||
this.m_LowCoder[this.m_NumPosStates] = new BitTreeDecoder(Base.kNumLowLenBits);
|
|
||||||
this.m_MidCoder[this.m_NumPosStates] = new BitTreeDecoder(Base.kNumMidLenBits);
|
|
||||||
this.m_NumPosStates++;
|
|
||||||
}
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_Choice);
|
|
||||||
for (int posState = 0; posState < this.m_NumPosStates; posState++) {
|
|
||||||
this.m_LowCoder[posState].Init();
|
|
||||||
this.m_MidCoder[posState].Init();
|
|
||||||
}
|
|
||||||
this.m_HighCoder.Init();
|
|
||||||
}
|
|
||||||
|
|
||||||
public int Decode(SevenZip.Compression.RangeCoder.Decoder rangeDecoder, int posState) throws IOException {
|
|
||||||
if (rangeDecoder.DecodeBit(this.m_Choice, 0) == 0)
|
|
||||||
return this.m_LowCoder[posState].Decode(rangeDecoder);
|
|
||||||
int symbol = Base.kNumLowLenSymbols;
|
|
||||||
if (rangeDecoder.DecodeBit(this.m_Choice, 1) == 0)
|
|
||||||
symbol += this.m_MidCoder[posState].Decode(rangeDecoder);
|
|
||||||
else
|
|
||||||
symbol += Base.kNumMidLenSymbols + this.m_HighCoder.Decode(rangeDecoder);
|
|
||||||
return symbol;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private static class LiteralDecoder {
|
|
||||||
|
|
||||||
private final Decoder2[] m_Coders;
|
|
||||||
private final int m_NumPrevBits;
|
|
||||||
private final int m_NumPosBits;
|
|
||||||
private final int m_PosMask;
|
|
||||||
|
|
||||||
public LiteralDecoder(int numPosBits, int numPrevBits) {
|
|
||||||
this.m_NumPrevBits = numPrevBits;
|
|
||||||
this.m_NumPosBits = numPosBits;
|
|
||||||
this.m_PosMask = (1 << numPosBits) - 1;
|
|
||||||
final int numStates = 1 << (this.m_NumPrevBits + this.m_NumPosBits);
|
|
||||||
this.m_Coders = new Decoder2[numStates];
|
|
||||||
for (int i = 0; i < numStates; i++)
|
|
||||||
this.m_Coders[i] = new Decoder2();
|
|
||||||
}
|
|
||||||
|
|
||||||
private Decoder2 GetDecoder(int pos, byte prevByte) {
|
|
||||||
final int indexHigh = (pos & this.m_PosMask) << this.m_NumPrevBits;
|
|
||||||
final int indexLow = (prevByte & 0xFF) >>> (8 - this.m_NumPrevBits);
|
|
||||||
return this.m_Coders[indexHigh + indexLow];
|
|
||||||
}
|
|
||||||
|
|
||||||
private static class Decoder2 {
|
|
||||||
final short[] m_Decoders = new short[0x300];
|
|
||||||
|
|
||||||
public Decoder2() {
|
|
||||||
SevenZip.Compression.RangeCoder.Decoder.InitBitModels(this.m_Decoders);
|
|
||||||
}
|
|
||||||
|
|
||||||
public byte DecodeNormal(SevenZip.Compression.RangeCoder.Decoder rangeDecoder) throws IOException {
|
|
||||||
int symbol = 1;
|
|
||||||
do {
|
|
||||||
symbol = (symbol << 1) | rangeDecoder.DecodeBit(this.m_Decoders, symbol);
|
|
||||||
} while (symbol < 0x100);
|
|
||||||
return (byte)symbol;
|
|
||||||
}
|
|
||||||
|
|
||||||
public byte DecodeWithMatchByte(SevenZip.Compression.RangeCoder.Decoder rangeDecoder, byte matchByte) throws IOException {
|
|
||||||
int symbol = 1, matchBit, bit;
|
|
||||||
do {
|
|
||||||
matchBit = (matchByte >> 7) & 1;
|
|
||||||
matchByte <<= 1;
|
|
||||||
bit = rangeDecoder.DecodeBit(this.m_Decoders, ((1 + matchBit) << 8) + symbol);
|
|
||||||
symbol = (symbol << 1) | bit;
|
|
||||||
if (matchBit != bit) {
|
|
||||||
while (symbol < 0x100)
|
|
||||||
symbol = (symbol << 1) | rangeDecoder.DecodeBit(this.m_Decoders, symbol);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
} while (symbol < 0x100);
|
|
||||||
return (byte)symbol;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
File diff suppressed because it is too large
Load Diff
@ -1,38 +0,0 @@
|
|||||||
package SevenZip.Compression.RangeCoder;
|
|
||||||
|
|
||||||
import SevenZip.Compression.RangeCoder.Decoder;
|
|
||||||
|
|
||||||
|
|
||||||
public class BitDecoder extends BitModel
|
|
||||||
{
|
|
||||||
public BitDecoder(int num) {
|
|
||||||
super(num);
|
|
||||||
}
|
|
||||||
public int Decode(Decoder decoder) throws java.io.IOException
|
|
||||||
{
|
|
||||||
int newBound = (decoder.Range >>> kNumBitModelTotalBits) * this.Prob;
|
|
||||||
if ((decoder.Code ^ 0x80000000) < (newBound ^ 0x80000000))
|
|
||||||
{
|
|
||||||
decoder.Range = newBound;
|
|
||||||
this.Prob += (kBitModelTotal - this.Prob) >>> numMoveBits;
|
|
||||||
if ((decoder.Range & kTopMask) == 0)
|
|
||||||
{
|
|
||||||
decoder.Code = (decoder.Code << 8) | decoder.bufferedStream.read();
|
|
||||||
decoder.Range <<= 8;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
decoder.Range -= newBound;
|
|
||||||
decoder.Code -= newBound;
|
|
||||||
this.Prob -= (this.Prob) >>> numMoveBits;
|
|
||||||
if ((decoder.Range & kTopMask) == 0)
|
|
||||||
{
|
|
||||||
decoder.Code = (decoder.Code << 8) | decoder.bufferedStream.read();
|
|
||||||
decoder.Range <<= 8;
|
|
||||||
}
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,29 +0,0 @@
|
|||||||
package SevenZip.Compression.RangeCoder;
|
|
||||||
|
|
||||||
|
|
||||||
public class BitModel
|
|
||||||
{
|
|
||||||
|
|
||||||
public static final int kTopMask = ~((1 << 24) - 1);
|
|
||||||
public static final int kNumBitModelTotalBits = 11;
|
|
||||||
public static final int kBitModelTotal = (1 << kNumBitModelTotalBits);
|
|
||||||
|
|
||||||
int numMoveBits;
|
|
||||||
|
|
||||||
int Prob;
|
|
||||||
|
|
||||||
public BitModel(int num) {
|
|
||||||
numMoveBits = num;
|
|
||||||
}
|
|
||||||
/*
|
|
||||||
public void UpdateModel(UInt32 symbol)
|
|
||||||
{
|
|
||||||
if (symbol == 0)
|
|
||||||
Prob += (kBitModelTotal - Prob) >> numMoveBits;
|
|
||||||
else
|
|
||||||
Prob -= (Prob) >> numMoveBits;
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
public void Init() { Prob = kBitModelTotal / 2; }
|
|
||||||
|
|
||||||
}
|
|
@ -1,57 +0,0 @@
|
|||||||
package SevenZip.Compression.RangeCoder;
|
|
||||||
|
|
||||||
import SevenZip.Compression.RangeCoder.Decoder;
|
|
||||||
|
|
||||||
public class BitTreeDecoder
|
|
||||||
{
|
|
||||||
short[] Models;
|
|
||||||
int NumBitLevels;
|
|
||||||
|
|
||||||
public BitTreeDecoder(int numBitLevels)
|
|
||||||
{
|
|
||||||
NumBitLevels = numBitLevels;
|
|
||||||
Models = new short[1 << numBitLevels];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Init()
|
|
||||||
{
|
|
||||||
Decoder.InitBitModels(Models);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int Decode(Decoder rangeDecoder) throws java.io.IOException
|
|
||||||
{
|
|
||||||
int m = 1;
|
|
||||||
for (int bitIndex = NumBitLevels; bitIndex != 0; bitIndex--)
|
|
||||||
m = (m << 1) + rangeDecoder.DecodeBit(Models, m);
|
|
||||||
return m - (1 << NumBitLevels);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReverseDecode(Decoder rangeDecoder) throws java.io.IOException
|
|
||||||
{
|
|
||||||
int m = 1;
|
|
||||||
int symbol = 0;
|
|
||||||
for (int bitIndex = 0; bitIndex < NumBitLevels; bitIndex++)
|
|
||||||
{
|
|
||||||
int bit = rangeDecoder.DecodeBit(Models, m);
|
|
||||||
m <<= 1;
|
|
||||||
m += bit;
|
|
||||||
symbol |= (bit << bitIndex);
|
|
||||||
}
|
|
||||||
return symbol;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int ReverseDecode(short[] Models, int startIndex,
|
|
||||||
Decoder rangeDecoder, int NumBitLevels) throws java.io.IOException
|
|
||||||
{
|
|
||||||
int m = 1;
|
|
||||||
int symbol = 0;
|
|
||||||
for (int bitIndex = 0; bitIndex < NumBitLevels; bitIndex++)
|
|
||||||
{
|
|
||||||
int bit = rangeDecoder.DecodeBit(Models, startIndex + m);
|
|
||||||
m <<= 1;
|
|
||||||
m += bit;
|
|
||||||
symbol |= (bit << bitIndex);
|
|
||||||
}
|
|
||||||
return symbol;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,102 +0,0 @@
|
|||||||
package SevenZip.Compression.RangeCoder;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
import SevenZip.Compression.RangeCoder.Decoder;
|
|
||||||
import SevenZip.Compression.RangeCoder.Encoder;
|
|
||||||
|
|
||||||
public class BitTreeEncoder
|
|
||||||
{
|
|
||||||
short[] Models;
|
|
||||||
int NumBitLevels;
|
|
||||||
|
|
||||||
public BitTreeEncoder(int numBitLevels)
|
|
||||||
{
|
|
||||||
NumBitLevels = numBitLevels;
|
|
||||||
Models = new short[1 << numBitLevels];
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Init()
|
|
||||||
{
|
|
||||||
Decoder.InitBitModels(Models);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Encode(Encoder rangeEncoder, int symbol) throws IOException
|
|
||||||
{
|
|
||||||
int m = 1;
|
|
||||||
for (int bitIndex = NumBitLevels; bitIndex != 0; )
|
|
||||||
{
|
|
||||||
bitIndex--;
|
|
||||||
int bit = (symbol >>> bitIndex) & 1;
|
|
||||||
rangeEncoder.Encode(Models, m, bit);
|
|
||||||
m = (m << 1) | bit;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ReverseEncode(Encoder rangeEncoder, int symbol) throws IOException
|
|
||||||
{
|
|
||||||
int m = 1;
|
|
||||||
for (int i = 0; i < NumBitLevels; i++)
|
|
||||||
{
|
|
||||||
int bit = symbol & 1;
|
|
||||||
rangeEncoder.Encode(Models, m, bit);
|
|
||||||
m = (m << 1) | bit;
|
|
||||||
symbol >>= 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public int GetPrice(int symbol)
|
|
||||||
{
|
|
||||||
int price = 0;
|
|
||||||
int m = 1;
|
|
||||||
for (int bitIndex = NumBitLevels; bitIndex != 0; )
|
|
||||||
{
|
|
||||||
bitIndex--;
|
|
||||||
int bit = (symbol >>> bitIndex) & 1;
|
|
||||||
price += Encoder.GetPrice(Models[m], bit);
|
|
||||||
m = (m << 1) + bit;
|
|
||||||
}
|
|
||||||
return price;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int ReverseGetPrice(int symbol)
|
|
||||||
{
|
|
||||||
int price = 0;
|
|
||||||
int m = 1;
|
|
||||||
for (int i = NumBitLevels; i != 0; i--)
|
|
||||||
{
|
|
||||||
int bit = symbol & 1;
|
|
||||||
symbol >>>= 1;
|
|
||||||
price += Encoder.GetPrice(Models[m], bit);
|
|
||||||
m = (m << 1) | bit;
|
|
||||||
}
|
|
||||||
return price;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static int ReverseGetPrice(short[] Models, int startIndex,
|
|
||||||
int NumBitLevels, int symbol)
|
|
||||||
{
|
|
||||||
int price = 0;
|
|
||||||
int m = 1;
|
|
||||||
for (int i = NumBitLevels; i != 0; i--)
|
|
||||||
{
|
|
||||||
int bit = symbol & 1;
|
|
||||||
symbol >>>= 1;
|
|
||||||
price += Encoder.GetPrice(Models[startIndex + m], bit);
|
|
||||||
m = (m << 1) | bit;
|
|
||||||
}
|
|
||||||
return price;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void ReverseEncode(short[] Models, int startIndex,
|
|
||||||
Encoder rangeEncoder, int NumBitLevels, int symbol) throws IOException
|
|
||||||
{
|
|
||||||
int m = 1;
|
|
||||||
for (int i = 0; i < NumBitLevels; i++)
|
|
||||||
{
|
|
||||||
int bit = symbol & 1;
|
|
||||||
rangeEncoder.Encode(Models, startIndex + m, bit);
|
|
||||||
m = (m << 1) | bit;
|
|
||||||
symbol >>= 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,101 +0,0 @@
|
|||||||
package SevenZip.Compression.RangeCoder;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public class Decoder
|
|
||||||
{
|
|
||||||
static final int kTopMask = ~((1 << 24) - 1);
|
|
||||||
|
|
||||||
static final int kNumBitModelTotalBits = 11;
|
|
||||||
static final int kBitModelTotal = (1 << kNumBitModelTotalBits);
|
|
||||||
static final int kNumMoveBits = 5;
|
|
||||||
|
|
||||||
int Range;
|
|
||||||
int Code;
|
|
||||||
|
|
||||||
// boolean _wasFinished;
|
|
||||||
// long _processedSize;
|
|
||||||
|
|
||||||
// public boolean WasFinished() { return _wasFinished; }
|
|
||||||
|
|
||||||
// public java.io.InputStream Stream;
|
|
||||||
|
|
||||||
public SevenZip.Common.InBuffer bufferedStream = new SevenZip.Common.InBuffer();
|
|
||||||
|
|
||||||
int read() throws IOException {
|
|
||||||
return bufferedStream.read();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Create(int bufferSize) { bufferedStream.Create(bufferSize); }
|
|
||||||
|
|
||||||
public long GetProcessedSize() {
|
|
||||||
return bufferedStream.GetProcessedSize();
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void SetStream(java.io.InputStream stream)
|
|
||||||
{
|
|
||||||
bufferedStream.SetStream(stream);
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void ReleaseStream() throws IOException
|
|
||||||
{
|
|
||||||
bufferedStream.ReleaseStream();
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void Init() throws IOException
|
|
||||||
{
|
|
||||||
bufferedStream.Init();
|
|
||||||
Code = 0;
|
|
||||||
Range = -1;
|
|
||||||
for (int i = 0; i < 5; i++) {
|
|
||||||
Code = (Code << 8) | this.read();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
public final int DecodeDirectBits(int numTotalBits) throws IOException
|
|
||||||
{
|
|
||||||
int result = 0;
|
|
||||||
for (int i = numTotalBits; i != 0; i--)
|
|
||||||
{
|
|
||||||
Range >>>= 1;
|
|
||||||
int t = ((Code - Range) >>> 31);
|
|
||||||
Code -= Range & (t - 1);
|
|
||||||
result = (result << 1) | (1 - t);
|
|
||||||
|
|
||||||
if ((Range & kTopMask) == 0)
|
|
||||||
{
|
|
||||||
Code = (Code << 8) | this.read();
|
|
||||||
Range <<= 8;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int DecodeBit(short []probs, int index) throws IOException {
|
|
||||||
int prob = probs[index];
|
|
||||||
int newBound = (Range >>> kNumBitModelTotalBits) * prob;
|
|
||||||
if ((Code ^ 0x80000000) < (newBound ^ 0x80000000)) {
|
|
||||||
Range = newBound;
|
|
||||||
probs[index] = (short)(prob + ((kBitModelTotal - prob) >>> kNumMoveBits));
|
|
||||||
if ((Range & kTopMask) == 0) {
|
|
||||||
Code = (Code << 8) | this.read();
|
|
||||||
Range <<= 8;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
} else {
|
|
||||||
Range -= newBound;
|
|
||||||
Code -= newBound;
|
|
||||||
probs[index] = (short)(prob - ((prob) >>> kNumMoveBits));
|
|
||||||
if ((Range & kTopMask) == 0) {
|
|
||||||
Code = (Code << 8) | this.read();
|
|
||||||
Range <<= 8;
|
|
||||||
}
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void InitBitModels(short[] probs) {
|
|
||||||
for (int i = 0; i < probs.length; i++)
|
|
||||||
probs[i] = (kBitModelTotal >>> 1);
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,153 +0,0 @@
|
|||||||
package SevenZip.Compression.RangeCoder;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
import SevenZip.Compression.RangeCoder.Encoder;
|
|
||||||
|
|
||||||
public class Encoder
|
|
||||||
{
|
|
||||||
static final int kTopMask = ~((1 << 24) - 1);
|
|
||||||
|
|
||||||
static final int kNumBitModelTotalBits = 11;
|
|
||||||
static final int kBitModelTotal = (1 << kNumBitModelTotalBits);
|
|
||||||
static final int kNumMoveBits = 5;
|
|
||||||
|
|
||||||
java.io.OutputStream Stream;
|
|
||||||
|
|
||||||
long Low;
|
|
||||||
int Range;
|
|
||||||
int _cacheSize;
|
|
||||||
int _cache;
|
|
||||||
|
|
||||||
long _position;
|
|
||||||
|
|
||||||
public void SetStream(java.io.OutputStream stream)
|
|
||||||
{
|
|
||||||
Stream = stream;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ReleaseStream()
|
|
||||||
{
|
|
||||||
Stream = null;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Init()
|
|
||||||
{
|
|
||||||
_position = 0;
|
|
||||||
Low = 0;
|
|
||||||
Range = -1;
|
|
||||||
_cacheSize = 1;
|
|
||||||
_cache = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void FlushData() throws IOException
|
|
||||||
{
|
|
||||||
for (int i = 0; i < 5; i++)
|
|
||||||
ShiftLow();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void FlushStream() throws IOException
|
|
||||||
{
|
|
||||||
Stream.flush();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void ShiftLow() throws IOException
|
|
||||||
{
|
|
||||||
int LowHi = (int)(Low >>> 32);
|
|
||||||
if (LowHi != 0 || Low < 0xFF000000L)
|
|
||||||
{
|
|
||||||
_position += _cacheSize;
|
|
||||||
int temp = _cache;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
Stream.write(temp + LowHi);
|
|
||||||
temp = 0xFF;
|
|
||||||
}
|
|
||||||
while(--_cacheSize != 0);
|
|
||||||
_cache = (((int)Low) >>> 24);
|
|
||||||
}
|
|
||||||
_cacheSize++;
|
|
||||||
Low = (Low & 0xFFFFFF) << 8;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void EncodeDirectBits(int v, int numTotalBits) throws IOException
|
|
||||||
{
|
|
||||||
for (int i = numTotalBits - 1; i >= 0; i--)
|
|
||||||
{
|
|
||||||
Range >>>= 1;
|
|
||||||
if (((v >>> i) & 1) == 1)
|
|
||||||
Low += Range;
|
|
||||||
if ((Range & Encoder.kTopMask) == 0)
|
|
||||||
{
|
|
||||||
Range <<= 8;
|
|
||||||
ShiftLow();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
public long GetProcessedSizeAdd()
|
|
||||||
{
|
|
||||||
return _cacheSize + _position + 4;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
static final int kNumMoveReducingBits = 2;
|
|
||||||
public static final int kNumBitPriceShiftBits = 6;
|
|
||||||
|
|
||||||
public static void InitBitModels(short []probs)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < probs.length; i++)
|
|
||||||
probs[i] = (kBitModelTotal >>> 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Encode(short []probs, int index, int symbol) throws IOException
|
|
||||||
{
|
|
||||||
int prob = probs[index];
|
|
||||||
int newBound = (Range >>> kNumBitModelTotalBits) * prob;
|
|
||||||
if (symbol == 0)
|
|
||||||
{
|
|
||||||
Range = newBound;
|
|
||||||
probs[index] = (short)(prob + ((kBitModelTotal - prob) >>> kNumMoveBits));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
Low += (newBound & 0xFFFFFFFFL);
|
|
||||||
Range -= newBound;
|
|
||||||
probs[index] = (short)(prob - ((prob) >>> kNumMoveBits));
|
|
||||||
}
|
|
||||||
if ((Range & kTopMask) == 0)
|
|
||||||
{
|
|
||||||
Range <<= 8;
|
|
||||||
ShiftLow();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private static int[] ProbPrices = new int[kBitModelTotal >>> kNumMoveReducingBits];
|
|
||||||
|
|
||||||
static
|
|
||||||
{
|
|
||||||
int kNumBits = (kNumBitModelTotalBits - kNumMoveReducingBits);
|
|
||||||
for (int i = kNumBits - 1; i >= 0; i--)
|
|
||||||
{
|
|
||||||
int start = 1 << (kNumBits - i - 1);
|
|
||||||
int end = 1 << (kNumBits - i);
|
|
||||||
for (int j = start; j < end; j++)
|
|
||||||
ProbPrices[j] = (i << kNumBitPriceShiftBits) +
|
|
||||||
(((end - j) << kNumBitPriceShiftBits) >>> (kNumBits - i - 1));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static public int GetPrice(int Prob, int symbol)
|
|
||||||
{
|
|
||||||
return ProbPrices[(((Prob - symbol) ^ ((-symbol))) & (kBitModelTotal - 1)) >>> kNumMoveReducingBits];
|
|
||||||
}
|
|
||||||
static public int GetPrice0(int Prob)
|
|
||||||
{
|
|
||||||
return ProbPrices[Prob >>> kNumMoveReducingBits];
|
|
||||||
}
|
|
||||||
static public int GetPrice1(int Prob)
|
|
||||||
{
|
|
||||||
return ProbPrices[(kBitModelTotal - Prob) >>> kNumMoveReducingBits];
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,11 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public class HRESULT {
|
|
||||||
public static final int S_OK = 0;
|
|
||||||
public static final int S_FALSE = 1;
|
|
||||||
|
|
||||||
public static final int E_NOTIMPL = 0x80004001;
|
|
||||||
public static final int E_FAIL = 0x80004005;
|
|
||||||
public static final int E_INVALIDARG = 0x80070057;
|
|
||||||
}
|
|
||||||
|
|
@ -1,6 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface ICodeProgress
|
|
||||||
{
|
|
||||||
public void SetProgress(long inSize, long outSize);
|
|
||||||
}
|
|
@ -1,13 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
|
|
||||||
public interface ICompressCoder {
|
|
||||||
|
|
||||||
void Code(
|
|
||||||
InputStream inStream, // , ISequentialInStream
|
|
||||||
OutputStream outStream, // ISequentialOutStream
|
|
||||||
long outSize, ICompressProgressInfo progress) throws IOException;
|
|
||||||
}
|
|
@ -1,20 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.io.OutputStream;
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
public interface ICompressCoder2 {
|
|
||||||
|
|
||||||
public int Code(
|
|
||||||
Vector<InputStream> inStreams,
|
|
||||||
//Object useless1, // const UInt64 ** /* inSizes */,
|
|
||||||
int numInStreams,
|
|
||||||
Vector<OutputStream> outStreams,
|
|
||||||
//Object useless2, // const UInt64 ** /* outSizes */,
|
|
||||||
int numOutStreams,
|
|
||||||
ICompressProgressInfo progress) throws IOException;
|
|
||||||
|
|
||||||
public void close() throws java.io.IOException ; // destructor
|
|
||||||
}
|
|
@ -1,12 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface ICompressFilter {
|
|
||||||
int Init();
|
|
||||||
int Filter(byte [] data, int size);
|
|
||||||
// Filter return outSize (UInt32)
|
|
||||||
// if (outSize <= size): Filter have converted outSize bytes
|
|
||||||
// if (outSize > size): Filter have not converted anything.
|
|
||||||
// and it needs at least outSize bytes to convert one block
|
|
||||||
// (it's for crypto block algorithms).
|
|
||||||
|
|
||||||
}
|
|
@ -1,6 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface ICompressGetInStreamProcessedSize {
|
|
||||||
public long GetInStreamProcessedSize();
|
|
||||||
}
|
|
||||||
|
|
@ -1,6 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface ICompressProgressInfo {
|
|
||||||
public static final long INVALID = -1;
|
|
||||||
void SetRatioInfo(long inSize, long outSize);
|
|
||||||
}
|
|
@ -1,9 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import java.io.InputStream;
|
|
||||||
|
|
||||||
public interface ICompressSetInStream {
|
|
||||||
public void SetInStream(InputStream inStream);
|
|
||||||
public void ReleaseInStream() throws java.io.IOException ;
|
|
||||||
}
|
|
||||||
|
|
@ -1,7 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface ICompressSetOutStream {
|
|
||||||
public int SetOutStream(java.io.OutputStream inStream);
|
|
||||||
public int ReleaseOutStream() throws java.io.IOException;
|
|
||||||
}
|
|
||||||
|
|
@ -1,7 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface ICompressSetOutStreamSize {
|
|
||||||
public static final int INVALID_OUTSIZE=-1;
|
|
||||||
public void SetOutStreamSize(long outSize);
|
|
||||||
}
|
|
||||||
|
|
@ -1,11 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public abstract class IInStream extends java.io.InputStream
|
|
||||||
{
|
|
||||||
static public final int STREAM_SEEK_SET = 0;
|
|
||||||
static public final int STREAM_SEEK_CUR = 1;
|
|
||||||
// static public final int STREAM_SEEK_END = 2;
|
|
||||||
public abstract long Seek(long offset, int seekOrigin) throws java.io.IOException ;
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
@ -1,7 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public interface IProgress {
|
|
||||||
public void SetTotal(long total);
|
|
||||||
public void SetCompleted(long completeValue);
|
|
||||||
}
|
|
||||||
|
|
@ -1,162 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import SevenZip.Archive.SevenZip.Handler;
|
|
||||||
import SevenZip.Archive.SevenZipEntry;
|
|
||||||
import SevenZip.Archive.IArchiveExtractCallback;
|
|
||||||
import SevenZip.Archive.IInArchive;
|
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.text.DateFormat;
|
|
||||||
|
|
||||||
import java.util.Vector;
|
|
||||||
|
|
||||||
public class J7zip {
|
|
||||||
|
|
||||||
static void PrintHelp() {
|
|
||||||
System.out.println(
|
|
||||||
"\nUsage: JZip <l|t|x> <archive_name> [<file_names>...]\n" +
|
|
||||||
" l : Lists files\n" +
|
|
||||||
" t : Tests archive.7z\n" +
|
|
||||||
" x : eXtracts files\n");
|
|
||||||
}
|
|
||||||
|
|
||||||
static void listing(IInArchive archive,Vector listOfNames,boolean techMode) {
|
|
||||||
|
|
||||||
if (!techMode) {
|
|
||||||
System.out.println(" Date Time Attr Size Compressed Name");
|
|
||||||
System.out.println("-------------- ----- ------------ ------------ ------------");
|
|
||||||
}
|
|
||||||
|
|
||||||
long size = 0;
|
|
||||||
long packSize = 0;
|
|
||||||
long nbFiles = 0;
|
|
||||||
|
|
||||||
for(int i = 0; i < archive.size() ; i++) {
|
|
||||||
SevenZipEntry item = archive.getEntry(i);
|
|
||||||
|
|
||||||
DateFormat formatter = DateFormat.getDateTimeInstance(DateFormat.SHORT , DateFormat.SHORT );
|
|
||||||
String str_tm = formatter.format(new java.util.Date(item.getTime()));
|
|
||||||
|
|
||||||
if (listOfNames.contains(item.getName())) {
|
|
||||||
if (techMode) {
|
|
||||||
System.out.println("Path = " + item.getName());
|
|
||||||
System.out.println("Size = " + item.getSize());
|
|
||||||
System.out.println("Packed Size = " + item.getCompressedSize());
|
|
||||||
System.out.println("Modified = " + str_tm);
|
|
||||||
System.out.println(" Attributes : " + item.getAttributesString());
|
|
||||||
long crc = item.getCrc();
|
|
||||||
if (crc != -1)
|
|
||||||
System.out.println("CRC = " + Long.toHexString(crc).toUpperCase());
|
|
||||||
else
|
|
||||||
System.out.println("CRC =");
|
|
||||||
System.out.println("Method = " + item.getMethods() );
|
|
||||||
System.out.println("" );
|
|
||||||
|
|
||||||
} else {
|
|
||||||
System.out.print(str_tm + " " + item.getAttributesString());
|
|
||||||
|
|
||||||
System.out.print(item.getSize());
|
|
||||||
|
|
||||||
System.out.print(item.getCompressedSize());
|
|
||||||
|
|
||||||
System.out.println(" " + item.getName());
|
|
||||||
}
|
|
||||||
|
|
||||||
size += item.getSize();
|
|
||||||
packSize += item.getCompressedSize();
|
|
||||||
nbFiles ++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!techMode) {
|
|
||||||
System.out.println("-------------- ----- ------------ ------------ ------------");
|
|
||||||
System.out.print(" " + size + packSize + " " + nbFiles);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static void testOrExtract(IInArchive archive, Vector listOfNames,int mode) throws Exception {
|
|
||||||
|
|
||||||
ArchiveExtractCallback extractCallbackSpec = new ArchiveExtractCallback();
|
|
||||||
IArchiveExtractCallback extractCallback = extractCallbackSpec;
|
|
||||||
extractCallbackSpec.Init(archive);
|
|
||||||
extractCallbackSpec.PasswordIsDefined = false;
|
|
||||||
|
|
||||||
try {
|
|
||||||
int len = 0;
|
|
||||||
int arrays [] = null;
|
|
||||||
|
|
||||||
if (listOfNames.size() >= 1) {
|
|
||||||
arrays = new int[listOfNames.size()];
|
|
||||||
for(int i = 0 ; i < archive.size() ; i++) {
|
|
||||||
if (listOfNames.contains(archive.getEntry(i).getName())) {
|
|
||||||
arrays[len++] = i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (len == 0) {
|
|
||||||
archive.Extract(null, -1, mode , extractCallback);
|
|
||||||
} else {
|
|
||||||
archive.Extract(arrays, len, mode, extractCallback);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (extractCallbackSpec.NumErrors == 0)
|
|
||||||
System.out.println("Ok Done");
|
|
||||||
else
|
|
||||||
System.out.println(" " + extractCallbackSpec.NumErrors + " errors");
|
|
||||||
} catch (IOException e) {
|
|
||||||
System.out.println("IO error : " + e.getLocalizedMessage());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void main(String[] args) throws Exception {
|
|
||||||
System.out.println("\nJ7zip 4.43 ALPHA 2 (" + Runtime.getRuntime().availableProcessors() + " CPUs)");
|
|
||||||
|
|
||||||
if (args.length < 2) {
|
|
||||||
PrintHelp();
|
|
||||||
return ;
|
|
||||||
}
|
|
||||||
|
|
||||||
final int MODE_LISTING = 0;
|
|
||||||
final int MODE_TESTING = 1;
|
|
||||||
final int MODE_EXTRACT = 2;
|
|
||||||
|
|
||||||
int mode = -1;
|
|
||||||
|
|
||||||
Vector listOfNames = new Vector();
|
|
||||||
for (int i = 2;i < args.length ; i++)
|
|
||||||
listOfNames.add(args[i]);
|
|
||||||
|
|
||||||
if (args[0].equals("l")) {
|
|
||||||
mode = MODE_LISTING;
|
|
||||||
} else if (args[0].equals("t")) {
|
|
||||||
mode = MODE_TESTING;
|
|
||||||
} else if (args[0].equals("x")) {
|
|
||||||
mode = MODE_EXTRACT;
|
|
||||||
} else {
|
|
||||||
PrintHelp();
|
|
||||||
return ;
|
|
||||||
}
|
|
||||||
|
|
||||||
String filename = args[1];
|
|
||||||
|
|
||||||
MyRandomAccessFile istream = new MyRandomAccessFile(filename,"r");
|
|
||||||
|
|
||||||
IInArchive archive = new Handler(istream);
|
|
||||||
|
|
||||||
|
|
||||||
switch(mode) {
|
|
||||||
case MODE_LISTING:
|
|
||||||
listing(archive,listOfNames,false);
|
|
||||||
break;
|
|
||||||
case MODE_TESTING:
|
|
||||||
testOrExtract(archive,listOfNames,IInArchive.NExtract_NAskMode_kTest);
|
|
||||||
break;
|
|
||||||
case MODE_EXTRACT:
|
|
||||||
testOrExtract(archive,listOfNames,IInArchive.NExtract_NAskMode_kExtract);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
archive.close();
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,250 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
public class LzmaAlone
|
|
||||||
{
|
|
||||||
static public class CommandLine
|
|
||||||
{
|
|
||||||
public static final int kEncode = 0;
|
|
||||||
public static final int kDecode = 1;
|
|
||||||
public static final int kBenchmak = 2;
|
|
||||||
|
|
||||||
public int Command = -1;
|
|
||||||
public int NumBenchmarkPasses = 10;
|
|
||||||
|
|
||||||
public int DictionarySize = 1 << 23;
|
|
||||||
public boolean DictionarySizeIsDefined = false;
|
|
||||||
|
|
||||||
public int Lc = 3;
|
|
||||||
public int Lp = 0;
|
|
||||||
public int Pb = 2;
|
|
||||||
|
|
||||||
public int Fb = 128;
|
|
||||||
public boolean FbIsDefined = false;
|
|
||||||
|
|
||||||
public boolean Eos = false;
|
|
||||||
|
|
||||||
public int Algorithm = 2;
|
|
||||||
public int MatchFinder = 1;
|
|
||||||
|
|
||||||
public String InFile;
|
|
||||||
public String OutFile;
|
|
||||||
|
|
||||||
boolean ParseSwitch(String s)
|
|
||||||
{
|
|
||||||
if (s.startsWith("d"))
|
|
||||||
{
|
|
||||||
DictionarySize = 1 << Integer.parseInt(s.substring(1));
|
|
||||||
DictionarySizeIsDefined = true;
|
|
||||||
}
|
|
||||||
else if (s.startsWith("fb"))
|
|
||||||
{
|
|
||||||
Fb = Integer.parseInt(s.substring(2));
|
|
||||||
FbIsDefined = true;
|
|
||||||
}
|
|
||||||
else if (s.startsWith("a"))
|
|
||||||
Algorithm = Integer.parseInt(s.substring(1));
|
|
||||||
else if (s.startsWith("lc"))
|
|
||||||
Lc = Integer.parseInt(s.substring(2));
|
|
||||||
else if (s.startsWith("lp"))
|
|
||||||
Lp = Integer.parseInt(s.substring(2));
|
|
||||||
else if (s.startsWith("pb"))
|
|
||||||
Pb = Integer.parseInt(s.substring(2));
|
|
||||||
else if (s.startsWith("eos"))
|
|
||||||
Eos = true;
|
|
||||||
else if (s.startsWith("mf"))
|
|
||||||
{
|
|
||||||
String mfs = s.substring(2);
|
|
||||||
if (mfs.equals("bt2"))
|
|
||||||
MatchFinder = 0;
|
|
||||||
else if (mfs.equals("bt4"))
|
|
||||||
MatchFinder = 1;
|
|
||||||
else if (mfs.equals("bt4b"))
|
|
||||||
MatchFinder = 2;
|
|
||||||
else
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
return false;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean Parse(String[] args) throws Exception
|
|
||||||
{
|
|
||||||
int pos = 0;
|
|
||||||
boolean switchMode = true;
|
|
||||||
for (int i = 0; i < args.length; i++)
|
|
||||||
{
|
|
||||||
String s = args[i];
|
|
||||||
if (s.length() == 0)
|
|
||||||
return false;
|
|
||||||
if (switchMode)
|
|
||||||
{
|
|
||||||
if (s.compareTo("--") == 0)
|
|
||||||
{
|
|
||||||
switchMode = false;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (s.charAt(0) == '-')
|
|
||||||
{
|
|
||||||
String sw = s.substring(1).toLowerCase();
|
|
||||||
if (sw.length() == 0)
|
|
||||||
return false;
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (!ParseSwitch(sw))
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
catch (NumberFormatException e)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (pos == 0)
|
|
||||||
{
|
|
||||||
if (s.equalsIgnoreCase("e"))
|
|
||||||
Command = kEncode;
|
|
||||||
else if (s.equalsIgnoreCase("d"))
|
|
||||||
Command = kDecode;
|
|
||||||
else if (s.equalsIgnoreCase("b"))
|
|
||||||
Command = kBenchmak;
|
|
||||||
else
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
else if(pos == 1)
|
|
||||||
{
|
|
||||||
if (Command == kBenchmak)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
NumBenchmarkPasses = Integer.parseInt(s);
|
|
||||||
if (NumBenchmarkPasses < 1)
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
catch (NumberFormatException e)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
InFile = s;
|
|
||||||
}
|
|
||||||
else if(pos == 2)
|
|
||||||
OutFile = s;
|
|
||||||
else
|
|
||||||
return false;
|
|
||||||
pos++;
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
static void PrintHelp()
|
|
||||||
{
|
|
||||||
System.out.println(
|
|
||||||
"\nUsage: LZMA <e|d> [<switches>...] inputFile outputFile\n" +
|
|
||||||
" e: encode file\n" +
|
|
||||||
" d: decode file\n" +
|
|
||||||
" b: Benchmark\n" +
|
|
||||||
"<Switches>\n" +
|
|
||||||
// " -a{N}: set compression mode - [0, 1], default: 1 (max)\n" +
|
|
||||||
" -d{N}: set dictionary - [0,28], default: 23 (8MB)\n" +
|
|
||||||
" -fb{N}: set number of fast bytes - [5, 273], default: 128\n" +
|
|
||||||
" -lc{N}: set number of literal context bits - [0, 8], default: 3\n" +
|
|
||||||
" -lp{N}: set number of literal pos bits - [0, 4], default: 0\n" +
|
|
||||||
" -pb{N}: set number of pos bits - [0, 4], default: 2\n" +
|
|
||||||
" -mf{MF_ID}: set Match Finder: [bt2, bt4], default: bt4\n" +
|
|
||||||
" -eos: write End Of Stream marker\n"
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void main(String[] args) throws Exception
|
|
||||||
{
|
|
||||||
System.out.println("\nLZMA (Java) 4.42 Copyright (c) 1999-2006 Igor Pavlov 2006-05-15\n");
|
|
||||||
|
|
||||||
if (args.length < 1)
|
|
||||||
{
|
|
||||||
PrintHelp();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
CommandLine params = new CommandLine();
|
|
||||||
if (!params.Parse(args))
|
|
||||||
{
|
|
||||||
System.out.println("\nIncorrect command");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (params.Command == CommandLine.kBenchmak)
|
|
||||||
{
|
|
||||||
int dictionary = (1 << 21);
|
|
||||||
if (params.DictionarySizeIsDefined)
|
|
||||||
dictionary = params.DictionarySize;
|
|
||||||
if (params.MatchFinder > 1)
|
|
||||||
throw new Exception("Unsupported match finder");
|
|
||||||
SevenZip.LzmaBench.LzmaBenchmark(params.NumBenchmarkPasses, dictionary);
|
|
||||||
}
|
|
||||||
else if (params.Command == CommandLine.kEncode || params.Command == CommandLine.kDecode)
|
|
||||||
{
|
|
||||||
java.io.File inFile = new java.io.File(params.InFile);
|
|
||||||
java.io.File outFile = new java.io.File(params.OutFile);
|
|
||||||
|
|
||||||
java.io.BufferedInputStream inStream = new java.io.BufferedInputStream(new java.io.FileInputStream(inFile));
|
|
||||||
java.io.BufferedOutputStream outStream = new java.io.BufferedOutputStream(new java.io.FileOutputStream(outFile));
|
|
||||||
|
|
||||||
boolean eos = false;
|
|
||||||
if (params.Eos)
|
|
||||||
eos = true;
|
|
||||||
if (params.Command == CommandLine.kEncode)
|
|
||||||
{
|
|
||||||
SevenZip.Compression.LZMA.Encoder encoder = new SevenZip.Compression.LZMA.Encoder();
|
|
||||||
if (!encoder.SetAlgorithm(params.Algorithm))
|
|
||||||
throw new Exception("Incorrect compression mode");
|
|
||||||
if (!encoder.SetDictionarySize(params.DictionarySize))
|
|
||||||
throw new Exception("Incorrect dictionary size");
|
|
||||||
if (!encoder.SetNumFastBytes(params.Fb))
|
|
||||||
throw new Exception("Incorrect -fb value");
|
|
||||||
if (!encoder.SetMatchFinder(params.MatchFinder))
|
|
||||||
throw new Exception("Incorrect -mf value");
|
|
||||||
if (!encoder.SetLcLpPb(params.Lc, params.Lp, params.Pb))
|
|
||||||
throw new Exception("Incorrect -lc or -lp or -pb value");
|
|
||||||
encoder.SetEndMarkerMode(eos);
|
|
||||||
encoder.WriteCoderProperties(outStream);
|
|
||||||
long fileSize;
|
|
||||||
if (eos)
|
|
||||||
fileSize = -1;
|
|
||||||
else
|
|
||||||
fileSize = inFile.length();
|
|
||||||
for (int i = 0; i < 8; i++)
|
|
||||||
outStream.write((int)(fileSize >>> (8 * i)) & 0xFF);
|
|
||||||
encoder.Code(inStream, outStream, -1, -1, null);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
int propertiesSize = 5;
|
|
||||||
byte[] properties = new byte[propertiesSize];
|
|
||||||
if (inStream.read(properties, 0, propertiesSize) != propertiesSize)
|
|
||||||
throw new Exception("input .lzma file is too short");
|
|
||||||
SevenZip.Compression.LZMA.Decoder decoder = new SevenZip.Compression.LZMA.Decoder(properties);
|
|
||||||
long outSize = 0;
|
|
||||||
for (int i = 0; i < 8; i++)
|
|
||||||
{
|
|
||||||
int v = inStream.read();
|
|
||||||
if (v < 0)
|
|
||||||
throw new Exception("Can't read stream size");
|
|
||||||
outSize |= ((long)v) << (8 * i);
|
|
||||||
}
|
|
||||||
decoder.Code(inStream, outStream, outSize, null);
|
|
||||||
}
|
|
||||||
outStream.flush();
|
|
||||||
outStream.close();
|
|
||||||
inStream.close();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
throw new Exception("Incorrect command");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,388 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import java.io.ByteArrayOutputStream;
|
|
||||||
import java.io.IOException;
|
|
||||||
|
|
||||||
public class LzmaBench
|
|
||||||
{
|
|
||||||
static final int kAdditionalSize = (1 << 21);
|
|
||||||
static final int kCompressedAdditionalSize = (1 << 10);
|
|
||||||
|
|
||||||
static class CRandomGenerator
|
|
||||||
{
|
|
||||||
int A1;
|
|
||||||
int A2;
|
|
||||||
public CRandomGenerator() { Init(); }
|
|
||||||
public void Init() { A1 = 362436069; A2 = 521288629; }
|
|
||||||
public int GetRnd()
|
|
||||||
{
|
|
||||||
return
|
|
||||||
((A1 = 36969 * (A1 & 0xffff) + (A1 >>> 16)) << 16) ^
|
|
||||||
((A2 = 18000 * (A2 & 0xffff) + (A2 >>> 16)));
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
static class CBitRandomGenerator
|
|
||||||
{
|
|
||||||
CRandomGenerator RG = new CRandomGenerator();
|
|
||||||
int Value;
|
|
||||||
int NumBits;
|
|
||||||
public void Init()
|
|
||||||
{
|
|
||||||
Value = 0;
|
|
||||||
NumBits = 0;
|
|
||||||
}
|
|
||||||
public int GetRnd(int numBits)
|
|
||||||
{
|
|
||||||
int result;
|
|
||||||
if (NumBits > numBits)
|
|
||||||
{
|
|
||||||
result = Value & ((1 << numBits) - 1);
|
|
||||||
Value >>>= numBits;
|
|
||||||
NumBits -= numBits;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
numBits -= NumBits;
|
|
||||||
result = (Value << numBits);
|
|
||||||
Value = RG.GetRnd();
|
|
||||||
result |= Value & (((int)1 << numBits) - 1);
|
|
||||||
Value >>>= numBits;
|
|
||||||
NumBits = 32 - numBits;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
static class CBenchRandomGenerator
|
|
||||||
{
|
|
||||||
CBitRandomGenerator RG = new CBitRandomGenerator();
|
|
||||||
int Pos;
|
|
||||||
int Rep0;
|
|
||||||
|
|
||||||
public int BufferSize;
|
|
||||||
public byte[] Buffer = null;
|
|
||||||
|
|
||||||
public CBenchRandomGenerator() { }
|
|
||||||
public void Set(int bufferSize)
|
|
||||||
{
|
|
||||||
Buffer = new byte[bufferSize];
|
|
||||||
Pos = 0;
|
|
||||||
BufferSize = bufferSize;
|
|
||||||
}
|
|
||||||
int GetRndBit() { return RG.GetRnd(1); }
|
|
||||||
int GetLogRandBits(int numBits)
|
|
||||||
{
|
|
||||||
int len = RG.GetRnd(numBits);
|
|
||||||
return RG.GetRnd((int)len);
|
|
||||||
}
|
|
||||||
int GetOffset()
|
|
||||||
{
|
|
||||||
if (GetRndBit() == 0)
|
|
||||||
return GetLogRandBits(4);
|
|
||||||
return (GetLogRandBits(4) << 10) | RG.GetRnd(10);
|
|
||||||
}
|
|
||||||
int GetLen1() { return RG.GetRnd(1 + (int)RG.GetRnd(2)); }
|
|
||||||
int GetLen2() { return RG.GetRnd(2 + (int)RG.GetRnd(2)); }
|
|
||||||
public void Generate()
|
|
||||||
{
|
|
||||||
RG.Init();
|
|
||||||
Rep0 = 1;
|
|
||||||
while (Pos < BufferSize)
|
|
||||||
{
|
|
||||||
if (GetRndBit() == 0 || Pos < 1)
|
|
||||||
Buffer[Pos++] = (byte)(RG.GetRnd(8));
|
|
||||||
else
|
|
||||||
{
|
|
||||||
int len;
|
|
||||||
if (RG.GetRnd(3) == 0)
|
|
||||||
len = 1 + GetLen1();
|
|
||||||
else
|
|
||||||
{
|
|
||||||
do
|
|
||||||
Rep0 = GetOffset();
|
|
||||||
while (Rep0 >= Pos);
|
|
||||||
Rep0++;
|
|
||||||
len = 2 + GetLen2();
|
|
||||||
}
|
|
||||||
for (int i = 0; i < len && Pos < BufferSize; i++, Pos++)
|
|
||||||
Buffer[Pos] = Buffer[Pos - Rep0];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
static class CrcOutStream extends java.io.OutputStream
|
|
||||||
{
|
|
||||||
public CRC CRC = new CRC();
|
|
||||||
|
|
||||||
public void Init()
|
|
||||||
{
|
|
||||||
CRC.Init();
|
|
||||||
}
|
|
||||||
public int GetDigest()
|
|
||||||
{
|
|
||||||
return CRC.GetDigest();
|
|
||||||
}
|
|
||||||
public void write(byte[] b)
|
|
||||||
{
|
|
||||||
CRC.Update(b);
|
|
||||||
}
|
|
||||||
public void write(byte[] b, int off, int len)
|
|
||||||
{
|
|
||||||
CRC.Update(b, off, len);
|
|
||||||
}
|
|
||||||
public void write(int b)
|
|
||||||
{
|
|
||||||
CRC.UpdateByte(b);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
static class MyOutputStream extends java.io.OutputStream
|
|
||||||
{
|
|
||||||
byte[] _buffer;
|
|
||||||
int _size;
|
|
||||||
int _pos;
|
|
||||||
|
|
||||||
public MyOutputStream(byte[] buffer)
|
|
||||||
{
|
|
||||||
_buffer = buffer;
|
|
||||||
_size = _buffer.length;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void reset()
|
|
||||||
{
|
|
||||||
_pos = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void write(int b) throws IOException
|
|
||||||
{
|
|
||||||
if (_pos >= _size)
|
|
||||||
throw new IOException("Error");
|
|
||||||
_buffer[_pos++] = (byte)b;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int size()
|
|
||||||
{
|
|
||||||
return _pos;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
static class MyInputStream extends java.io.InputStream
|
|
||||||
{
|
|
||||||
byte[] _buffer;
|
|
||||||
int _size;
|
|
||||||
int _pos;
|
|
||||||
|
|
||||||
public MyInputStream(byte[] buffer, int size)
|
|
||||||
{
|
|
||||||
_buffer = buffer;
|
|
||||||
_size = size;
|
|
||||||
}
|
|
||||||
|
|
||||||
public void reset()
|
|
||||||
{
|
|
||||||
_pos = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read()
|
|
||||||
{
|
|
||||||
if (_pos >= _size)
|
|
||||||
return -1;
|
|
||||||
return _buffer[_pos++] & 0xFF;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
static class CProgressInfo implements ICodeProgress
|
|
||||||
{
|
|
||||||
public long ApprovedStart;
|
|
||||||
public long InSize;
|
|
||||||
public long Time;
|
|
||||||
public void Init()
|
|
||||||
{ InSize = 0; }
|
|
||||||
public void SetProgress(long inSize, long outSize)
|
|
||||||
{
|
|
||||||
if (inSize >= ApprovedStart && InSize == 0)
|
|
||||||
{
|
|
||||||
Time = System.currentTimeMillis();
|
|
||||||
InSize = inSize;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
static final int kSubBits = 8;
|
|
||||||
|
|
||||||
static int GetLogSize(int size)
|
|
||||||
{
|
|
||||||
for (int i = kSubBits; i < 32; i++)
|
|
||||||
for (int j = 0; j < (1 << kSubBits); j++)
|
|
||||||
if (size <= ((1) << i) + (j << (i - kSubBits)))
|
|
||||||
return (i << kSubBits) + j;
|
|
||||||
return (32 << kSubBits);
|
|
||||||
}
|
|
||||||
|
|
||||||
static long MyMultDiv64(long value, long elapsedTime)
|
|
||||||
{
|
|
||||||
long freq = 1000; // ms
|
|
||||||
long elTime = elapsedTime;
|
|
||||||
while (freq > 1000000)
|
|
||||||
{
|
|
||||||
freq >>>= 1;
|
|
||||||
elTime >>>= 1;
|
|
||||||
}
|
|
||||||
if (elTime == 0)
|
|
||||||
elTime = 1;
|
|
||||||
return value * freq / elTime;
|
|
||||||
}
|
|
||||||
|
|
||||||
static long GetCompressRating(int dictionarySize, long elapsedTime, long size)
|
|
||||||
{
|
|
||||||
long t = GetLogSize(dictionarySize) - (18 << kSubBits);
|
|
||||||
long numCommandsForOne = 1060 + ((t * t * 10) >> (2 * kSubBits));
|
|
||||||
long numCommands = (long)(size) * numCommandsForOne;
|
|
||||||
return MyMultDiv64(numCommands, elapsedTime);
|
|
||||||
}
|
|
||||||
|
|
||||||
static long GetDecompressRating(long elapsedTime, long outSize, long inSize)
|
|
||||||
{
|
|
||||||
long numCommands = inSize * 220 + outSize * 20;
|
|
||||||
return MyMultDiv64(numCommands, elapsedTime);
|
|
||||||
}
|
|
||||||
|
|
||||||
static long GetTotalRating(
|
|
||||||
int dictionarySize,
|
|
||||||
long elapsedTimeEn, long sizeEn,
|
|
||||||
long elapsedTimeDe,
|
|
||||||
long inSizeDe, long outSizeDe)
|
|
||||||
{
|
|
||||||
return (GetCompressRating(dictionarySize, elapsedTimeEn, sizeEn) +
|
|
||||||
GetDecompressRating(elapsedTimeDe, inSizeDe, outSizeDe)) / 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void PrintValue(long v)
|
|
||||||
{
|
|
||||||
String s = "";
|
|
||||||
s += v;
|
|
||||||
for (int i = 0; i + s.length() < 6; i++)
|
|
||||||
System.out.print(" ");
|
|
||||||
System.out.print(s);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void PrintRating(long rating)
|
|
||||||
{
|
|
||||||
PrintValue(rating / 1000000);
|
|
||||||
System.out.print(" MIPS");
|
|
||||||
}
|
|
||||||
|
|
||||||
static void PrintResults(
|
|
||||||
int dictionarySize,
|
|
||||||
long elapsedTime,
|
|
||||||
long size,
|
|
||||||
boolean decompressMode, long secondSize)
|
|
||||||
{
|
|
||||||
long speed = MyMultDiv64(size, elapsedTime);
|
|
||||||
PrintValue(speed / 1024);
|
|
||||||
System.out.print(" KB/s ");
|
|
||||||
long rating;
|
|
||||||
if (decompressMode)
|
|
||||||
rating = GetDecompressRating(elapsedTime, size, secondSize);
|
|
||||||
else
|
|
||||||
rating = GetCompressRating(dictionarySize, elapsedTime, size);
|
|
||||||
PrintRating(rating);
|
|
||||||
}
|
|
||||||
|
|
||||||
static public int LzmaBenchmark(int numIterations, int dictionarySize) throws Exception
|
|
||||||
{
|
|
||||||
if (numIterations <= 0)
|
|
||||||
return 0;
|
|
||||||
if (dictionarySize < (1 << 18))
|
|
||||||
{
|
|
||||||
System.out.println("\nError: dictionary size for benchmark must be >= 18 (256 KB)");
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
System.out.print("\n Compressing Decompressing\n\n");
|
|
||||||
|
|
||||||
SevenZip.Compression.LZMA.Encoder encoder = new SevenZip.Compression.LZMA.Encoder();
|
|
||||||
|
|
||||||
if (!encoder.SetDictionarySize(dictionarySize))
|
|
||||||
throw new Exception("Incorrect dictionary size");
|
|
||||||
|
|
||||||
int kBufferSize = dictionarySize + kAdditionalSize;
|
|
||||||
int kCompressedBufferSize = (kBufferSize / 2) + kCompressedAdditionalSize;
|
|
||||||
|
|
||||||
ByteArrayOutputStream propStream = new ByteArrayOutputStream();
|
|
||||||
encoder.WriteCoderProperties(propStream);
|
|
||||||
SevenZip.Compression.LZMA.Decoder decoder = new SevenZip.Compression.LZMA.Decoder(propStream.toByteArray());
|
|
||||||
|
|
||||||
CBenchRandomGenerator rg = new CBenchRandomGenerator();
|
|
||||||
|
|
||||||
rg.Set(kBufferSize);
|
|
||||||
rg.Generate();
|
|
||||||
CRC crc = new CRC();
|
|
||||||
crc.Init();
|
|
||||||
crc.Update(rg.Buffer, 0, rg.BufferSize);
|
|
||||||
|
|
||||||
CProgressInfo progressInfo = new CProgressInfo();
|
|
||||||
progressInfo.ApprovedStart = dictionarySize;
|
|
||||||
|
|
||||||
long totalBenchSize = 0;
|
|
||||||
long totalEncodeTime = 0;
|
|
||||||
long totalDecodeTime = 0;
|
|
||||||
long totalCompressedSize = 0;
|
|
||||||
|
|
||||||
MyInputStream inStream = new MyInputStream(rg.Buffer, rg.BufferSize);
|
|
||||||
|
|
||||||
byte[] compressedBuffer = new byte[kCompressedBufferSize];
|
|
||||||
MyOutputStream compressedStream = new MyOutputStream(compressedBuffer);
|
|
||||||
CrcOutStream crcOutStream = new CrcOutStream();
|
|
||||||
MyInputStream inputCompressedStream = null;
|
|
||||||
int compressedSize = 0;
|
|
||||||
for (int i = 0; i < numIterations; i++)
|
|
||||||
{
|
|
||||||
progressInfo.Init();
|
|
||||||
inStream.reset();
|
|
||||||
compressedStream.reset();
|
|
||||||
encoder.Code(inStream, compressedStream, -1, -1, progressInfo);
|
|
||||||
long encodeTime = System.currentTimeMillis() - progressInfo.Time;
|
|
||||||
|
|
||||||
if (i == 0)
|
|
||||||
{
|
|
||||||
compressedSize = compressedStream.size();
|
|
||||||
inputCompressedStream = new MyInputStream(compressedBuffer, compressedSize);
|
|
||||||
}
|
|
||||||
else if (compressedSize != compressedStream.size())
|
|
||||||
throw (new Exception("Encoding error"));
|
|
||||||
|
|
||||||
if (progressInfo.InSize == 0)
|
|
||||||
throw (new Exception("Internal ERROR 1282"));
|
|
||||||
|
|
||||||
long decodeTime = 0;
|
|
||||||
for (int j = 0; j < 2; j++)
|
|
||||||
{
|
|
||||||
inputCompressedStream.reset();
|
|
||||||
crcOutStream.Init();
|
|
||||||
|
|
||||||
long outSize = kBufferSize;
|
|
||||||
long startTime = System.currentTimeMillis();
|
|
||||||
decoder.Code(inputCompressedStream, crcOutStream, outSize, null);
|
|
||||||
decodeTime = System.currentTimeMillis() - startTime;
|
|
||||||
if (crcOutStream.GetDigest() != crc.GetDigest())
|
|
||||||
throw (new Exception("CRC Error"));
|
|
||||||
}
|
|
||||||
long benchSize = kBufferSize - (long)progressInfo.InSize;
|
|
||||||
PrintResults(dictionarySize, encodeTime, benchSize, false, 0);
|
|
||||||
System.out.print(" ");
|
|
||||||
PrintResults(dictionarySize, decodeTime, kBufferSize, true, compressedSize);
|
|
||||||
System.out.println();
|
|
||||||
|
|
||||||
totalBenchSize += benchSize;
|
|
||||||
totalEncodeTime += encodeTime;
|
|
||||||
totalDecodeTime += decodeTime;
|
|
||||||
totalCompressedSize += compressedSize;
|
|
||||||
}
|
|
||||||
System.out.println("---------------------------------------------------");
|
|
||||||
PrintResults(dictionarySize, totalEncodeTime, totalBenchSize, false, 0);
|
|
||||||
System.out.print(" ");
|
|
||||||
PrintResults(dictionarySize, totalDecodeTime,
|
|
||||||
kBufferSize * (long)numIterations, true, totalCompressedSize);
|
|
||||||
System.out.println(" Average");
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,45 +0,0 @@
|
|||||||
package SevenZip;
|
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.io.RandomAccessFile;
|
|
||||||
|
|
||||||
public class MyRandomAccessFile extends SevenZip.IInStream {
|
|
||||||
|
|
||||||
RandomAccessFile _file;
|
|
||||||
|
|
||||||
public MyRandomAccessFile(File file, String mode) throws IOException {
|
|
||||||
this(file.getAbsolutePath(), mode);
|
|
||||||
}
|
|
||||||
|
|
||||||
public MyRandomAccessFile(String filename,String mode) throws IOException {
|
|
||||||
_file = new RandomAccessFile(filename,mode);
|
|
||||||
}
|
|
||||||
|
|
||||||
public long Seek(long offset, int seekOrigin) throws IOException {
|
|
||||||
if (seekOrigin == STREAM_SEEK_SET) {
|
|
||||||
_file.seek(offset);
|
|
||||||
}
|
|
||||||
else if (seekOrigin == STREAM_SEEK_CUR) {
|
|
||||||
_file.seek(offset + _file.getFilePointer());
|
|
||||||
}
|
|
||||||
return _file.getFilePointer();
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read() throws IOException {
|
|
||||||
return _file.read();
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read(byte [] data, int off, int size) throws IOException {
|
|
||||||
return _file.read(data,off,size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public int read(byte [] data, int size) throws IOException {
|
|
||||||
return _file.read(data,0,size);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void close() throws IOException {
|
|
||||||
_file.close();
|
|
||||||
_file = null;
|
|
||||||
}
|
|
||||||
}
|
|
Loading…
Reference in new issue