org.freehep.util.io.ASCII85InputStream Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of freehep-io Show documentation
Show all versions of freehep-io Show documentation
FreeHEP extension to the java.io library
// Copyright 2001-2009, FreeHEP.
package org.freehep.util.io;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
/**
* The ASCII85InputStream decodes ASCII base-85 encoded data. The exact
* definition of ASCII base-85 encoding can be found in the PostScript Language
* Reference (3rd ed.) chapter 3.13.3. More info also on
* http://en.wikipedia.org/wiki/Ascii85
*
* @author Mark Donszelmann
*/
public class ASCII85InputStream extends DecodingInputStream implements ASCII85 {
private boolean endReached;
private int b[] = new int[4];
private int bIndex;
private int bLength;
private int c[] = new int[5];
private int lineNo;
private int prev;
private InputStream in;
/**
* Create an ASCII85 Input Stream from given stream.
*
* @param input
* input to use
*/
public ASCII85InputStream(InputStream input) {
super();
in = input;
bIndex = 0;
bLength = 0;
endReached = false;
prev = -1;
lineNo = 1;
}
@Override
public int read() throws IOException {
if (bIndex >= bLength) {
if (endReached) {
return -1;
}
bLength = readTuple();
if (bLength < 0) {
return -1;
}
bIndex = 0;
}
int a = b[bIndex];
bIndex++;
return a;
}
/**
* @return current line number
*/
public int getLineNo() {
return lineNo;
}
private int readTuple() throws IOException, EncodingException {
int cIndex = 0;
int ch = -1;
while ((!endReached) && (cIndex < 5)) {
prev = ch;
ch = in.read();
switch (ch) {
case -1:
throw new EncodingException(
"ASCII85InputStream: missing '~>' at end of stream");
case 'z':
if (cIndex != 0) {
throw new EncodingException(
"ASCII85InputStream: 'z' encoding can only appear at the start of a group, cIndex: "
+ cIndex);
}
b[0] = b[1] = b[2] = b[3] = 0;
return 4;
case '~':
ch = in.read();
while ((ch >= 0) && (ch != '>') && Character.isWhitespace(ch)) {
ch = in.read();
}
if (ch != '>') {
throw new EncodingException(
"ASCII85InputStream: Invalid EOD, expected '>', found "
+ ch);
}
endReached = true;
break;
case '\r':
lineNo++;
break;
case '\n':
if (prev != '\r') {
lineNo++;
}
break;
case ' ':
case '\t':
case '\f':
case 0:
// ignored
break;
default:
c[cIndex] = ch;
cIndex++;
break;
}
}
if (cIndex > 0) {
// fill the rest, avoid rounding by padding with "u" characters.
for (int i = 0; i < c.length; i++) {
if (i >= cIndex) {
c[i] = 'u';
} else {
c[i] -= '!';
}
}
// convert
long d = ((c[0] * a85p4) + (c[1] * a85p3) + (c[2] * a85p2)
+ (c[3] * a85p1) + c[4]) & 0x00000000FFFFFFFFL;
b[0] = (int) ((d >> 24) & 0x00FF);
b[1] = (int) ((d >> 16) & 0x00FF);
b[2] = (int) ((d >> 8) & 0x00FF);
b[3] = (int) (d & 0x00FF);
}
return cIndex - 1;
}
/**
* Print out ASCII85 of a file
*
* @param args
* filename
* @throws Exception
* when file does not exist
*/
public static void main(String[] args) throws Exception {
if (args.length < 1) {
System.err.println("Usage: ASCII85InputStream filename");
System.exit(1);
}
ASCII85InputStream in = new ASCII85InputStream(new FileInputStream(
args[0]));
int b = in.read();
while (b != -1) {
System.out.write(b);
b = in.read();
}
in.close();
System.out.flush();
}
}
© 2015 - 2024 Weber Informatics LLC | Privacy Policy