// Translated by Nina
// This source code is under public domain

package net.morilib.lisp.nano;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.List;
import java.util.Stack;
import net.morilib.lisp.nano.util.PeekableReader;

public  class NanoParser   {

	static class TokenException extends RuntimeException {
	}

	static abstract class Engine {
		abstract int step(java.io.Reader __rd, int c) throws java.io.IOException;
		abstract boolean accepted();
		abstract int execaction(int c);
		abstract boolean isend();
		abstract int recover(Exception e);
		abstract int deadState();
		abstract int stateSize();
		abstract int finallyState();
	}

	static class Continuation {

		private int STATE;
		private int[] __sts;
		private Engine[] __stk;
		private Object[][] __stv;

		Continuation(int s, int[] sts, Engine[] stk, Object[][] stv,
				int len) {
			STATE = s;
			__sts = new int[len];
			__stk = new Engine[len];
			__stv = new Object[len][];
			System.arraycopy(sts, 0, __sts, 0, len);
			System.arraycopy(stk, 0, __stk, 0, len);
			System.arraycopy(stv, 0, __stv, 0, len);
		}

	}

	private static final int NINA_ACCEPT = -1;
	private static final int NINA_FAIL = -9;
	private static final int NINA_HALT_ACCEPT = -91;
	private static final int NINA_HALT_REJECT = -72;
	private static final int NINA_BEGIN = -2;
	private static final int NINA_STACKLEN = 72;
	static final int INITIAL = 0;

	private int STATE;
	private int[] __sts = new int[NINA_STACKLEN];
	private Engine[] __stk = new Engine[NINA_STACKLEN];
	private Object[][] __stv = new Object[NINA_STACKLEN][];
	private int __slen = 0;

	Throwable exception;

	private int unread = -1;
	private int[] __backtrack = null;
	private int __backtrack_ptr = -1;
	private int __backtrack_len = -1;
	private int __backtrack_wptr = -1;
	private int __backtrack_sym = -1;
	private int[] __backtrack_state = null;
	private int[] __backtrack_wsym = null;
	private int[] __backtrack_ptrs = null;
	private Continuation[] __backtrack_cont = null;
	private int __backtrack_sptr = -1;
	private boolean __backtrack_flg = false;

private static final Symbol QUT = Symbol.getSymbol("quote");
private static final Symbol QQT = Symbol.getSymbol("quasiquote");
private static final Symbol UQT = Symbol.getSymbol("unquote");
private static final Symbol UQS = Symbol.getSymbol("unquote-splicing");
private static final int EXACT = 1;
private static final int INEXACT = 2;

private StringBuffer nbf, dbf, fbf, ybf, bbf, obf, zbf, xbf, cbf;
private Stack<List<Datum>> lst;
private LispReal real;
private LispNumber num;
private Datum dtm;
private int chr;
private int exactness;
Datum res;

private String prompt1;
//private String prompt2;
private Scheme scheme;

public NanoParser(Scheme scheme, String prompt1, String prompt2) {
	this.scheme  = scheme;
	this.prompt1 = prompt1;
//	this.prompt2 = prompt2;
}

public NanoParser(Scheme scheme) {
	this.scheme  = scheme;
	this.prompt1 = null;
//	this.prompt2 = null;
}

public NanoParser() {
	this.scheme = Scheme.newInstance();
}

public Datum readExpr(PeekableReader p) throws java.io.IOException {
	parse(p);
	p.unget(unread);
	return res;
}

private void putprompt1() {
	if(prompt1 != null) {
		System.out.print(prompt1);
	}
}

//private void putprompt2() {
//	if(prompt2 != null) {
//		System.out.print(prompt2);
//	}
//}

private void putresult(Datum res) {
	if(prompt1 != null && scheme != null && res != null) {
		System.out.println(scheme.input(res));
	} else if(scheme != null && res != null) {
		scheme.input(res);
	}
}

private void init() {
	ybf = bbf = obf = zbf = xbf = cbf = null;
	chr = -1;
	dtm = null;
	exactness = 0;
}

private void l2d() {
	dtm = LispUtils.listToCons(lst.pop(), get());
}

private void adl(int c) {
	if(c == '(')  lst.push(new ArrayList<Datum>());
}

private void adg(int c) {
	lst.peek().add(get());
}

private LispNumber toExactness(LispNumber n) {
	switch(exactness) {
	case EXACT:    return n.toExact();
	case INEXACT:  return n.toInexact();
	default:       return n;
	}
}

private Datum get() {
	LispNumber n;
	String s;
	Datum r;

	if(dtm != null) {
		return dtm;
	} else if(ybf != null) {
	    if((s = ybf.toString()).equals("+inf.0")) {
	    	return LispDouble.POSITIVE_INFINITY;
	    } else if(s.equals("-inf.0")) {
	    	return LispDouble.NEGATIVE_INFINITY;
	    } else if(s.equals("+nan.0")) {
	    	return LispDouble.NaN;
	    } else {
			return Symbol.getSymbol(s);
		}
	} else if(bbf != null) {
		try {
			n = LispInteger.valueOf(new BigInteger(bbf.toString(), 2));
			return toExactness(n);
		} catch(NumberFormatException e) {
			throw LispMessage.getInstance().getError("err.read.number.invalid");
		}
	} else if(obf != null) {
		try {
			n = LispInteger.valueOf(new BigInteger(obf.toString(), 8));
			return toExactness(n);
		} catch(NumberFormatException e) {
			throw LispMessage.getInstance().getError("err.read.number.invalid");
		}
	} else if(zbf != null) {
		try {
			n = LispInteger.valueOf(new BigInteger(zbf.toString(), 10));
			return toExactness(n);
		} catch(NumberFormatException e) {
			throw LispMessage.getInstance().getError("err.read.number.invalid");
		}
	} else if(xbf != null) {
		try {
			n = LispInteger.valueOf(new BigInteger(xbf.toString(), 16));
			return toExactness(n);
		} catch(NumberFormatException e) {
			throw LispMessage.getInstance().getError("err.read.number.invalid");
		}
	} else if(cbf != null) {
		if((r = LispCharacter.getByName(cbf.toString())) != null) {
			return r;
		} else {
			throw LispMessage.getInstance().getError("err.read.character.unknown");
		}
	} else if(chr >= 0) {
		return new LispCharacter(chr);
	} else {
		return null;
	}
}

private void ay(int c) {
	if(ybf == null)  ybf = new StringBuffer();
	if(c > 0)  ybf.appendCodePoint(c);
}

private void ayn() {
	ay('\n');
}

private void ayq() {
	ay('\\');
}

private void ab(int c) {
	if(bbf == null)  bbf = new StringBuffer();
	bbf.appendCodePoint(c);
}

private void ao(int c) {
	if(obf == null)  obf = new StringBuffer();
	obf.appendCodePoint(c);
}

private void az(int c) {
	if(zbf == null)  zbf = new StringBuffer();
	zbf.appendCodePoint(c);
}

private void ax(int c) {
	if(xbf == null)  xbf = new StringBuffer();
	xbf.appendCodePoint(c);
}

private void ac(int c) {
	if(cbf == null) {
		cbf = new StringBuffer();
		cbf.appendCodePoint(chr);
	}
	cbf.appendCodePoint(c);
}

private void ib() {
	real = LispInteger.ONE;
	num = null;
}

private void ia() {
	nbf = new StringBuffer();
	dbf = fbf = null;
}

private void an(int c) {
	if(c != '+')  nbf.append((char)c);
}

private void ad(int c) {
	dbf.append((char)c);
}

private void af(int c) {
	if(fbf == null)  fbf = nbf;
	fbf.append((char)c);
}

private LispReal getr() {
	if(dbf != null) {
		return LispRational.newRational(new BigInteger(nbf.toString()),
				new BigInteger(dbf.toString()));
	} else if(fbf != null) {
		return new LispDouble(Double.parseDouble(fbf.toString()));
	} else {
		return LispInteger.valueOf(new BigInteger(nbf.toString()));
	}
}

public static Datum exec(String s) {
	NanoParser r;

	try {
		r = new NanoParser(null);
		r.parse(new java.io.StringReader(s));
		return r.res;
	} catch(java.io.IOException e) {
		throw new RuntimeException();
	}
}

public static Datum read(
		PeekableReader rd) throws java.io.IOException {
	NanoParser r;

	r = new NanoParser(null);
	r.parse(rd, r.ENGINE_read);
	if(r.unread >= 0)  rd.unget(r.unread);
	return r.res;
}

public static void read(Scheme sch,
		java.io.InputStream rd) throws java.io.IOException {
	NanoParser r;

	r = new NanoParser(sch);
	r.parse(rd);
}

public Datum read(String s) {
	try {
		parse(new java.io.StringReader(s), ENGINE_read);
		return res;
	} catch(TokenException e) {
		throw LispMessage.getInstance().getError("err.read");
	} catch(java.io.IOException e) {
		throw new RuntimeException(e);
	}
}

public static void repl(Scheme scheme, PeekableReader rd,
		LispMessage msg) throws java.io.IOException {
	NanoParser r;

	try {
		r = new NanoParser(scheme, " >", ">>");
		r.parse(rd);
	} catch(ReadException e) {
		System.err.println(msg.get("err.repl.read") +
				e.getMessage());
	} catch(LispException e) {
		System.err.println(msg.get("err.repl.err") +
				e.getMessage());
		if(scheme.stackTrace != null && !scheme.stackTrace.equals("")) {
			System.err.println(msg.get("err.stacktrace"));
			System.err.print(scheme.stackTrace);
		}

		if(e.getException() != null) {
			e.getException().printStackTrace();
		}
	}
}


	private int _read(java.io.Reader rd) throws java.io.IOException {
		int c;

		if(__backtrack_sym >= 0) {
			c = __backtrack_sym;
			__backtrack_sym = -1;
			__logprint("Read Backtracking: ", c);
		} else if(unread >= 0) {
			c = unread;
			unread = -1;
			__logprint("Read unread: ", c);
		} else if(__backtrack_ptr >= 0) {
			if(__backtrack_ptr < __backtrack_len) {
				c = __backtrack[__backtrack_ptr++];
			} else {
				__backtrack = null;
				__backtrack_ptr = __backtrack_wptr = -1;
				c = _read(rd);
			}
			__logprint("Read Backtracking: ", c);
		} else if((c = rd.read()) >= 0) {
			__write_backtrack(c);
			__logprint("Read: ", c);
		} else {
			__logprint("Read end-of-file");
		}
		return c;
	}

	void UNGET(int c) {
		unread = c;
		__logprint("Set unread: ", c);
	}

	private void __logprint(String s, int c) {
	}

	private void __logopen() {
	}

	private void __logprint(String s) {
	}

	private void __logclose() {
	}

	private void __puttrace() {
	}

	void SET_BACKTRACK(int c) {
		int[] a;
		int[] b;

		if(__backtrack_sym != c) {
			if(__backtrack_ptr < 0) {
				__backtrack = new int[1024];
				__backtrack_wptr = 0;
			} else {
				__backtrack_wptr = __backtrack_ptr;
			}

			if(__backtrack_wsym == null) {
				__backtrack_state = new int[72];
				__backtrack_wsym = new int[72];
				__backtrack_ptrs = new int[72];
				__backtrack_cont = new Continuation[72];
				__backtrack_sptr = 0;
			} else if(__backtrack_sptr >= __backtrack_wsym.length) {
				a = __backtrack_wsym;
				b = __backtrack_ptrs;
				__backtrack_wsym = new int[a.length];
				__backtrack_ptrs = new int[b.length];
				System.arraycopy(a, 0, __backtrack_wsym, 0, a.length);
				System.arraycopy(b, 0, __backtrack_ptrs, 0, b.length);
			}
			__backtrack_state[__backtrack_sptr] = STATE;
			__backtrack_wsym[__backtrack_sptr] = c;
			__backtrack_ptrs[__backtrack_sptr] = __backtrack_wptr;
			__backtrack_cont[__backtrack_sptr] = GETCC();
			__backtrack_sptr++;
			__backtrack_flg = true;
			__logprint("Set Backtrack: ", c);
		}
	}

	private void __write_backtrack(int c) {
		int[] a;

		if(__backtrack_wptr < 0) {
			// do nothing
		} else if(__backtrack_wptr < __backtrack.length) {
			__backtrack[__backtrack_wptr++] = c;
		} else {
			a = new int[__backtrack.length * 2];
			System.arraycopy(__backtrack, 0, a, 0,
					__backtrack.length);
			__backtrack = a;
			__backtrack[__backtrack_wptr++] = c;
		}
	}

	void BACKTRACK_COMMIT() {
		if(--__backtrack_sptr <= 0) {
			__backtrack_state = null;
			__backtrack_wsym = null;
			__backtrack_ptrs = null;
			__backtrack_cont = null;
			__backtrack_sptr = -1;
			__backtrack_wptr = -1;
			__logprint("Commit Backtracking");
		}
	}

	boolean BACKTRACK(int c) {
		if(__backtrack_wptr >= 0) {
			__backtrack_len = __backtrack_wptr;
			__backtrack_wptr = -1;
			__backtrack_sptr--;
			STATE = __backtrack_state[__backtrack_sptr];
			__backtrack_ptr = __backtrack_ptrs[__backtrack_sptr];
			__backtrack_sym = __backtrack_wsym[__backtrack_sptr];
			SETCC(__backtrack_cont[__backtrack_sptr]);
			__logprint("Rollback Backtracking");
			return true;
		} else {
			return false;
		}
	}

	Continuation GETCC() {
		return new Continuation(STATE, __sts, __stk, __stv, __slen);
	}

	void SETCC(Continuation c) {
		int l;

		STATE = c.STATE;
		l = c.__stk.length;
		l = __stk.length > l ? __stk.length : l * 2;
		__sts = new int[l];
		__stk = new Engine[l];
		System.arraycopy(c.__sts, 0, __sts, 0, c.__sts.length);
		System.arraycopy(c.__stk, 0, __stk, 0, c.__stk.length);
		__slen = c.__sts.length;
	}


	private int real_step(java.io.Reader __rd,
			int  $c) throws java.io.IOException {
		boolean __g = true;

		switch(STATE) {
		case 0:
			if(__g && $c == '+') {
				STATE = 1;
				return 1;
			} else if(__g && $c == '-') {
				STATE = 1;
				return 1;
			} else if(__g && $c == '.') {
				STATE = 2;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 3;
				return 1;
			}
			return 0;
		case 3:
			if(__g && $c == '.') {
				STATE = 2;
				return 1;
			} else if(__g && $c == '/') {
				STATE = 4;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 3;
				return 1;
			} else if(__g && $c == 'E') {
				STATE = 5;
				return 1;
			} else if(__g && $c == 'F') {
				STATE = 5;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 5;
				return 1;
			} else if(__g && $c == 'f') {
				STATE = 5;
				return 1;
			}
			return 0;
		case 5:
			if(__g && $c == '+') {
				STATE = 6;
				return 1;
			} else if(__g && $c == '-') {
				STATE = 6;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 7;
				return 1;
			}
			return 0;
		case 7:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 7;
				return 1;
			}
			return 0;
		case 6:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 7;
				return 1;
			}
			return 0;
		case 4:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 8;
				return 1;
			}
			return 0;
		case 8:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 8;
				return 1;
			}
			return 0;
		case 2:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 9;
				return 1;
			}
			return 0;
		case 9:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 9;
				return 1;
			} else if(__g && $c == 'E') {
				STATE = 5;
				return 1;
			} else if(__g && $c == 'F') {
				STATE = 5;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 5;
				return 1;
			} else if(__g && $c == 'f') {
				STATE = 5;
				return 1;
			}
			return 0;
		case 1:
			if(__g && $c == '.') {
				STATE = 2;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 3;
				return 1;
			}
			return 0;
		}
		return 0;
	}
	private boolean real_accepted() {
		return (STATE == 3 ||
				STATE == 7 ||
				STATE == 8 ||
				STATE == 9);
	}

	int real_execaction(int  $c) {
		switch(STATE) {
		case 9:
			af($c);
			break;
		case 6:
			af($c);
			break;
		case 3:
			an($c);
			break;
		case 8:
			ad($c);
			break;
		case 1:
			an($c);
			break;
		case 7:
			af($c);
			break;
		case 4:
			dbf = new StringBuffer();
			break;
		case 0:
			ia();
			break;
		case 2:
			af($c);
			break;
		case 5:
			af($c);
			break;
		}
		return 1;
	}

	boolean real_isend() {
		return false;
	}

	private final Engine ENGINE_real = new Engine() {

		int step(java.io.Reader __rd,
				int c) throws java.io.IOException {
			return real_step(__rd, c);
		}

		boolean accepted() {
			return real_accepted();
		}

		int execaction(int c) {
			return real_execaction(c);
		}

		boolean isend() {
			return real_isend();
		}

		int recover(Exception e) {
			return -1;
		}

		int deadState() {
			return -1;
		}

		int stateSize() {
			return 10;
		}

		int finallyState() {
			return -1;
		}

		public String toString() {
			return "real";
		}

	};

	private int read_step(java.io.Reader __rd,
			int  $c) throws java.io.IOException {
		switch(STATE) {
		case 0:
			__stkpush(1, ENGINE_sexp);
			STATE = 0;
			return -1;
		case 1:
			return 0;
		}
		return 0;
	}
	private boolean read_accepted() {
		return (STATE == 0 ||
				STATE == 1);
	}

	int read_execaction(int  $c) {
		switch(STATE) {
		case 0:
			lst = new Stack<List<Datum>>();
			break;
		case 1:
			res = get();
			break;
		}
		return 1;
	}

	boolean read_isend() {
		return false;
	}

	private final Engine ENGINE_read = new Engine() {

		int step(java.io.Reader __rd,
				int c) throws java.io.IOException {
			return read_step(__rd, c);
		}

		boolean accepted() {
			return read_accepted();
		}

		int execaction(int c) {
			return read_execaction(c);
		}

		boolean isend() {
			return read_isend();
		}

		int recover(Exception e) {
			return -1;
		}

		int deadState() {
			return -1;
		}

		int stateSize() {
			return 2;
		}

		int finallyState() {
			return -1;
		}

		public String toString() {
			return "read";
		}

	};

	private int number_step(java.io.Reader __rd,
			int  $c) throws java.io.IOException {
		boolean __g = true;

		switch(STATE) {
		case 0:
			__stkpush(1, ENGINE_real);
			STATE = 0;
			return -1;
		case 1:
			if(__g && $c == '+') {
				STATE = 2;
				return 1;
			} else if(__g && $c == '-') {
				UNGET($c);
				STATE = 2;
				return 1;
			} else if(__g && $c == '@') {
				STATE = 3;
				return 1;
			} else if(__g && $c == 'i') {
				STATE = 4;
				return 1;
			}
			return 0;
		case 4:
			return 0;
		case 3:
			__stkpush(5, ENGINE_real);
			STATE = 0;
			return -1;
		case 5:
			return 0;
		case 2:
			if(__g && $c == 'i') {
				STATE = 6;
				return 1;
			} else {
				__stkpush(7, ENGINE_real);
				STATE = 0;
				return -1;
			}
		case 7:
			if(__g && $c == 'i') {
				STATE = 8;
				return 1;
			}
			return 0;
		case 8:
			return 0;
		case 6:
			return 0;
		}
		return 0;
	}
	private boolean number_accepted() {
		return (STATE == 1 ||
				STATE == 4 ||
				STATE == 5 ||
				STATE == 6 ||
				STATE == 8);
	}

	int number_execaction(int  $c) {
		switch(STATE) {
		case 2:
			break;
		case 5:
			num = LispComplex.newPolar(real.getRealDouble(), getr().getRealDouble());
			break;
		case 0:
			ib();
			break;
		case 8:
			num = LispComplex.newComplex(real, getr());
			break;
		case 3:
			break;
		case 7:
			break;
		case 1:
			real = getr();
			break;
		case 6:
			num = LispComplex.newComplex(real, LispInteger.ONE);
			break;
		case 4:
			num = LispComplex.newComplex(LispInteger.ZERO, getr());
			break;
		}
		return 1;
	}

	boolean number_isend() {
		return false;
	}

	private final Engine ENGINE_number = new Engine() {

		int step(java.io.Reader __rd,
				int c) throws java.io.IOException {
			return number_step(__rd, c);
		}

		boolean accepted() {
			return number_accepted();
		}

		int execaction(int c) {
			return number_execaction(c);
		}

		boolean isend() {
			return number_isend();
		}

		int recover(Exception e) {
			return -1;
		}

		int deadState() {
			return -1;
		}

		int stateSize() {
			return 9;
		}

		int finallyState() {
			return -1;
		}

		public String toString() {
			return "number";
		}

	};

	private int sexp_step(java.io.Reader __rd,
			int  $c) throws java.io.IOException {
		boolean __g = true;

		switch(STATE) {
		case 0:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 0;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 0;
				return 1;
			} else if(__g && $c == '"') {
				STATE = 1;
				return 1;
			} else if(__g && $c == '#') {
				STATE = 2;
				return 1;
			} else if(__g && $c == '\'') {
				STATE = 3;
				return 1;
			} else if(__g && $c == '(') {
				STATE = 4;
				return 1;
			} else if(__g && $c == '+') {
				UNGET($c);
				STATE = 5;
				return 1;
			} else if(__g && $c == ',') {
				STATE = 6;
				return 1;
			} else if(__g && $c == '-') {
				UNGET($c);
				STATE = 5;
				return 1;
			} else if(__g && $c == '.') {
				UNGET($c);
				STATE = 5;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				UNGET($c);
				STATE = 5;
				return 1;
			} else if(__g && $c == ';') {
				STATE = 7;
				return 1;
			} else if(__g && $c == '`') {
				STATE = 8;
				return 1;
			} else {
				STATE = 9;
				return 1;
			}
		case 9:
			if(__g && $c >= 0 && $c <= 8) {
				STATE = 9;
				return 1;
			} else if(__g && $c >= 14 && $c <= 31) {
				STATE = 9;
				return 1;
			} else if(__g && $c == '!') {
				STATE = 9;
				return 1;
			} else if(__g && $c >= '$' && $c <= '\'') {
				STATE = 9;
				return 1;
			} else if(__g && $c >= '*' && $c <= ':') {
				STATE = 9;
				return 1;
			} else if(__g && $c >= '<' && $c <= 2147483647) {
				STATE = 9;
				return 1;
			}
			return 0;
		case 8:
			__stkpush(10, ENGINE_sexp);
			STATE = 0;
			return -1;
		case 10:
			return 0;
		case 7:
			if(__g && $c == '\n') {
				STATE = 0;
				return 1;
			} else {
				STATE = 7;
				return 1;
			}
		case 6:
			if(__g && $c == '@') {
				STATE = 11;
				return 1;
			} else {
				__stkpush(12, ENGINE_sexp);
				STATE = 0;
				return -1;
			}
		case 12:
			return 0;
		case 11:
			__stkpush(13, ENGINE_sexp);
			STATE = 0;
			return -1;
		case 13:
			return 0;
		case 5:
			if(__g && $c == 0) {
				STATE = 14;
				return 1;
			} else {
				__stkpush(15, ENGINE_number);
				STATE = 0;
				return -1;
			}
		case 15:
			if(__g && $c >= 9 && $c <= 13) {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == ' ') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == '"') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == '#') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == '\'') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == '(') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == ')') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == ',') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == ';') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else if(__g && $c == '`') {
				UNGET($c);
				STATE = 16;
				return 1;
			} else {
				UNGET($c);
				STATE = 17;
				return 1;
			}
		case 17:
			return 0;
		case 16:
			return 0;
		case 14:
			if(__g && $c >= 0 && $c <= 8) {
				STATE = 14;
				return 1;
			} else if(__g && $c >= 14 && $c <= 31) {
				STATE = 14;
				return 1;
			} else if(__g && $c == '!') {
				STATE = 14;
				return 1;
			} else if(__g && $c >= '$' && $c <= '\'') {
				STATE = 14;
				return 1;
			} else if(__g && $c >= '*' && $c <= ':') {
				STATE = 14;
				return 1;
			} else if(__g && $c >= '<' && $c <= 2147483647) {
				STATE = 14;
				return 1;
			}
			return 0;
		case 4:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 4;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 4;
				return 1;
			} else if(__g && $c == ')') {
				STATE = 18;
				return 1;
			} else {
				__stkpush(19, ENGINE_sexp);
				STATE = 0;
				return -1;
			}
		case 19:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 20;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 20;
				return 1;
			} else if(__g && $c == ')') {
				STATE = 18;
				return 1;
			} else if(__g && $c == '.') {
				STATE = 21;
				return 1;
			} else {
				__stkpush(19, ENGINE_sexp);
				STATE = 0;
				return -1;
			}
		case 21:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 22;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 22;
				return 1;
			} else if(__g && $c == '"') {
				UNGET($c);
				STATE = 22;
				return 1;
			} else if(__g && $c == '#') {
				UNGET($c);
				STATE = 22;
				return 1;
			} else if(__g && $c == '(') {
				UNGET($c);
				STATE = 22;
				return 1;
			} else if(__g && $c == ')') {
				UNGET($c);
				STATE = 22;
				return 1;
			} else if(__g && $c == ';') {
				UNGET($c);
				STATE = 22;
				return 1;
			} else {
				ay(46);
				STATE = 23;
				return 1;
			}
		case 23:
			if(__g && $c >= 0 && $c <= 8) {
				STATE = 23;
				return 1;
			} else if(__g && $c >= 14 && $c <= 31) {
				STATE = 23;
				return 1;
			} else if(__g && $c == '!') {
				STATE = 23;
				return 1;
			} else if(__g && $c >= '$' && $c <= '\'') {
				STATE = 23;
				return 1;
			} else if(__g && $c >= '*' && $c <= ':') {
				STATE = 23;
				return 1;
			} else if(__g && $c >= '<' && $c <= 2147483647) {
				STATE = 23;
				return 1;
			} else {
				UNGET($c);
				STATE = 19;
				return 1;
			}
		case 22:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 22;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 22;
				return 1;
			} else {
				__stkpush(24, ENGINE_sexp);
				STATE = 0;
				return -1;
			}
		case 24:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 24;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 24;
				return 1;
			} else if(__g && $c == ')') {
				STATE = 25;
				return 1;
			}
			return 0;
		case 25:
			return 0;
		case 20:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 20;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 20;
				return 1;
			} else if(__g && $c == ')') {
				STATE = 18;
				return 1;
			} else if(__g && $c == '.') {
				STATE = 21;
				return 1;
			} else {
				__stkpush(19, ENGINE_sexp);
				STATE = 0;
				return -1;
			}
		case 18:
			return 0;
		case 3:
			__stkpush(26, ENGINE_sexp);
			STATE = 0;
			return -1;
		case 26:
			return 0;
		case 2:
			if(__g && $c == '(') {
				STATE = 27;
				return 1;
			} else if(__g && $c == 'B') {
				STATE = 28;
				return 1;
			} else if(__g && $c == 'D') {
				STATE = 29;
				return 1;
			} else if(__g && $c == 'E') {
				STATE = 30;
				return 1;
			} else if(__g && $c == 'H') {
				STATE = 31;
				return 1;
			} else if(__g && $c == 'I') {
				STATE = 32;
				return 1;
			} else if(__g && $c == 'O') {
				STATE = 33;
				return 1;
			} else if(__g && $c == '\\') {
				STATE = 34;
				return 1;
			} else if(__g && $c == 'b') {
				STATE = 28;
				return 1;
			} else if(__g && $c == 'd') {
				STATE = 29;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 30;
				return 1;
			} else if(__g && $c == 'f') {
				STATE = 35;
				return 1;
			} else if(__g && $c == 'h') {
				STATE = 31;
				return 1;
			} else if(__g && $c == 'i') {
				STATE = 32;
				return 1;
			} else if(__g && $c == 'o') {
				STATE = 33;
				return 1;
			} else if(__g && $c == 't') {
				STATE = 36;
				return 1;
			}
			return 0;
		case 36:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 37;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'Z') {
				STATE = 37;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'z') {
				STATE = 37;
				return 1;
			}
			return 0;
		case 37:
			return 0;
		case 35:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 38;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'Z') {
				STATE = 38;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'z') {
				STATE = 38;
				return 1;
			}
			return 0;
		case 38:
			return 0;
		case 34:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 39;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'Z') {
				STATE = 39;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'z') {
				STATE = 39;
				return 1;
			} else {
				STATE = 40;
				return 1;
			}
		case 40:
			return 0;
		case 39:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 41;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'Z') {
				STATE = 41;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'z') {
				STATE = 41;
				return 1;
			}
			return 0;
		case 41:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 41;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'Z') {
				STATE = 41;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'z') {
				STATE = 41;
				return 1;
			}
			return 0;
		case 33:
			if(__g && $c == '#') {
				STATE = 42;
				return 1;
			} else if(__g && $c == '-') {
				STATE = 43;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 44;
				return 1;
			}
			return 0;
		case 44:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 44;
				return 1;
			}
			return 0;
		case 43:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 44;
				return 1;
			}
			return 0;
		case 42:
			if(__g && $c == 'E') {
				STATE = 45;
				return 1;
			} else if(__g && $c == 'I') {
				STATE = 46;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 45;
				return 1;
			} else if(__g && $c == 'i') {
				STATE = 46;
				return 1;
			}
			return 0;
		case 46:
			UNGET($c);
			STATE = 44;
			return 1;
		case 45:
			UNGET($c);
			STATE = 44;
			return 1;
		case 32:
			if(__g && $c == '#') {
				STATE = 47;
				return 1;
			} else {
				__stkpush(48, ENGINE_number);
				STATE = 0;
				return -1;
			}
		case 48:
			return 0;
		case 47:
			if(__g && $c == 'B') {
				STATE = 28;
				return 1;
			} else if(__g && $c == 'D') {
				STATE = 29;
				return 1;
			} else if(__g && $c == 'H') {
				STATE = 31;
				return 1;
			} else if(__g && $c == 'O') {
				STATE = 33;
				return 1;
			} else if(__g && $c == 'b') {
				STATE = 28;
				return 1;
			} else if(__g && $c == 'd') {
				STATE = 29;
				return 1;
			} else if(__g && $c == 'h') {
				STATE = 31;
				return 1;
			} else if(__g && $c == 'o') {
				STATE = 33;
				return 1;
			}
			return 0;
		case 31:
			if(__g && $c == '#') {
				STATE = 49;
				return 1;
			} else if(__g && $c == '-') {
				STATE = 50;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 51;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'F') {
				STATE = 51;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'f') {
				STATE = 51;
				return 1;
			}
			return 0;
		case 51:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 51;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'F') {
				STATE = 51;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'f') {
				STATE = 51;
				return 1;
			}
			return 0;
		case 50:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 51;
				return 1;
			} else if(__g && $c >= 'A' && $c <= 'F') {
				STATE = 51;
				return 1;
			} else if(__g && $c >= 'a' && $c <= 'f') {
				STATE = 51;
				return 1;
			}
			return 0;
		case 49:
			if(__g && $c == 'E') {
				STATE = 52;
				return 1;
			} else if(__g && $c == 'I') {
				STATE = 53;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 52;
				return 1;
			} else if(__g && $c == 'i') {
				STATE = 53;
				return 1;
			}
			return 0;
		case 53:
			UNGET($c);
			STATE = 51;
			return 1;
		case 52:
			UNGET($c);
			STATE = 51;
			return 1;
		case 30:
			if(__g && $c == '#') {
				STATE = 54;
				return 1;
			} else {
				__stkpush(55, ENGINE_number);
				STATE = 0;
				return -1;
			}
		case 55:
			return 0;
		case 54:
			if(__g && $c == 'B') {
				STATE = 28;
				return 1;
			} else if(__g && $c == 'D') {
				STATE = 29;
				return 1;
			} else if(__g && $c == 'H') {
				STATE = 31;
				return 1;
			} else if(__g && $c == 'O') {
				STATE = 33;
				return 1;
			} else if(__g && $c == 'b') {
				STATE = 28;
				return 1;
			} else if(__g && $c == 'd') {
				STATE = 29;
				return 1;
			} else if(__g && $c == 'h') {
				STATE = 31;
				return 1;
			} else if(__g && $c == 'o') {
				STATE = 33;
				return 1;
			}
			return 0;
		case 29:
			if(__g && $c == '#') {
				STATE = 56;
				return 1;
			} else if(__g && $c == '-') {
				STATE = 57;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 58;
				return 1;
			}
			return 0;
		case 58:
			return 0;
		case 57:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 58;
				return 1;
			}
			return 0;
		case 56:
			if(__g && $c == 'E') {
				STATE = 59;
				return 1;
			} else if(__g && $c == 'I') {
				STATE = 60;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 59;
				return 1;
			} else if(__g && $c == 'i') {
				STATE = 60;
				return 1;
			}
			return 0;
		case 60:
			UNGET($c);
			STATE = 58;
			return 1;
		case 59:
			UNGET($c);
			STATE = 58;
			return 1;
		case 28:
			if(__g && $c == '#') {
				STATE = 61;
				return 1;
			} else if(__g && $c == '-') {
				STATE = 62;
				return 1;
			} else if(__g && $c >= '0' && $c <= '9') {
				STATE = 63;
				return 1;
			}
			return 0;
		case 63:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 63;
				return 1;
			}
			return 0;
		case 62:
			if(__g && $c >= '0' && $c <= '9') {
				STATE = 63;
				return 1;
			}
			return 0;
		case 61:
			if(__g && $c == 'E') {
				STATE = 64;
				return 1;
			} else if(__g && $c == 'I') {
				STATE = 65;
				return 1;
			} else if(__g && $c == 'e') {
				STATE = 64;
				return 1;
			} else if(__g && $c == 'i') {
				STATE = 65;
				return 1;
			}
			return 0;
		case 65:
			UNGET($c);
			STATE = 63;
			return 1;
		case 64:
			UNGET($c);
			STATE = 63;
			return 1;
		case 27:
			UNGET($c);
			STATE = 66;
			return 1;
		case 66:
			if(__g && $c >= 9 && $c <= 13) {
				STATE = 66;
				return 1;
			} else if(__g && $c == ' ') {
				STATE = 66;
				return 1;
			} else if(__g && $c == ')') {
				STATE = 67;
				return 1;
			} else {
				__stkpush(68, ENGINE_sexp);
				STATE = 0;
				return -1;
			}
		case 68:
			if(__g && $c == ')') {
				STATE = 67;
				return 1;
			} else {
				UNGET($c);
				STATE = 66;
				return 1;
			}
		case 67:
			return 0;
		case 1:
			if(__g && $c == '"') {
				STATE = 69;
				return 1;
			} else if(__g && $c == '\\') {
				STATE = 70;
				return 1;
			} else {
				STATE = 1;
				return 1;
			}
		case 70:
			if(__g && $c == 'n') {
				ayn();
				STATE = 71;
				return 1;
			} else {
				ayq();
				STATE = 1;
				return 1;
			}
		case 71:
			UNGET($c);
			STATE = 1;
			return 1;
		case 69:
			return 0;
		}
		return 0;
	}
	private boolean sexp_accepted() {
		return (STATE == 0 ||
				STATE == 69 ||
				STATE == 7 ||
				STATE == 67 ||
				STATE == 9 ||
				STATE == 10 ||
				STATE == 12 ||
				STATE == 13 ||
				STATE == 14 ||
				STATE == 15 ||
				STATE == 16 ||
				STATE == 18 ||
				STATE == 23 ||
				STATE == 25 ||
				STATE == 26 ||
				STATE == 35 ||
				STATE == 39 ||
				STATE == 36 ||
				STATE == 40 ||
				STATE == 41 ||
				STATE == 44 ||
				STATE == 51 ||
				STATE == 48 ||
				STATE == 55 ||
				STATE == 58 ||
				STATE == 63);
	}

	int sexp_execaction(int  $c) {
		switch(STATE) {
		case 19:
			adg($c);
			break;
		case 50:
			ax($c);
			break;
		case 48:
			dtm = (num != null ? num : real).toInexact();
			break;
		case 27:
			lst.push(new ArrayList<Datum>());
			break;
		case 35:
			dtm = LispBoolean.FALSE;
			break;
		case 62:
			ab($c);
			break;
		case 46:
			exactness = INEXACT;
			break;
		case 57:
			az($c);
			break;
		case 56:
			break;
		case 53:
			exactness = INEXACT;
			break;
		case 45:
			exactness = EXACT;
			break;
		case 44:
			ao($c);
			break;
		case 40:
			chr = $c;
			break;
		case 54:
			break;
		case 30:
			break;
		case 2:
			break;
		case 25:
			l2d();
			break;
		case 14:
			ay($c);
			break;
		case 8:
			break;
		case 38:
			break;
		case 61:
			break;
		case 67:
			dtm = new LispVector(lst.pop());
			break;
		case 1:
			ay($c);
			break;
		case 42:
			break;
		case 11:
			break;
		case 60:
			exactness = INEXACT;
			break;
		case 15:
			dtm = num != null ? num : real;
			break;
		case 21:
			ybf = null;
			break;
		case 49:
			break;
		case 20:
			break;
		case 63:
			ab($c);
			break;
		case 18:
			dtm = LispUtils.listToCons(lst.pop());
			break;
		case 22:
			break;
		case 3:
			break;
		case 13:
			dtm = new Cons(UQS, new Cons(get(), Nil.NIL));
			break;
		case 39:
			chr = $c;
			break;
		case 33:
			break;
		case 34:
			break;
		case 41:
			ac($c);
			break;
		case 28:
			break;
		case 52:
			exactness = EXACT;
			break;
		case 23:
			dtm = null; ay($c);
			break;
		case 31:
			break;
		case 59:
			exactness = EXACT;
			break;
		case 43:
			ao($c);
			break;
		case 68:
			lst.peek().add(get());
			break;
		case 71:
			break;
		case 36:
			dtm = LispBoolean.TRUE;
			break;
		case 16:
			BACKTRACK_COMMIT();
			break;
		case 47:
			break;
		case 6:
			break;
		case 4:
			adl($c);
			break;
		case 51:
			ax($c);
			break;
		case 69:
			dtm = new LispString(ybf.substring(1));
			break;
		case 29:
			break;
		case 32:
			break;
		case 55:
			dtm = (num != null ? num : real).toExact();
			break;
		case 64:
			exactness = EXACT;
			break;
		case 26:
			dtm = new Cons(QUT, new Cons(get(), Nil.NIL));
			break;
		case 65:
			exactness = INEXACT;
			break;
		case 66:
			break;
		case 9:
			ay($c);
			break;
		case 5:
			SET_BACKTRACK(0);
			break;
		case 70:
			break;
		case 24:
			break;
		case 17:
			dtm = null;
			break;
		case 12:
			dtm = new Cons(UQT, new Cons(get(), Nil.NIL));
			break;
		case 58:
			az($c);
			break;
		case 10:
			dtm = new Cons(QQT, new Cons(get(), Nil.NIL));
			break;
		case 37:
			break;
		case 0:
			init();
			break;
		case 7:
			break;
		}
		return 1;
	}

	boolean sexp_isend() {
		return false;
	}

	private final Engine ENGINE_sexp = new Engine() {

		int step(java.io.Reader __rd,
				int c) throws java.io.IOException {
			return sexp_step(__rd, c);
		}

		boolean accepted() {
			return sexp_accepted();
		}

		int execaction(int c) {
			return sexp_execaction(c);
		}

		boolean isend() {
			return sexp_isend();
		}

		int recover(Exception e) {
			return -1;
		}

		int deadState() {
			return -1;
		}

		int stateSize() {
			return 72;
		}

		int finallyState() {
			return -1;
		}

		public String toString() {
			return "sexp";
		}

	};

	private int nanoParser_step(java.io.Reader __rd,
			int  $c) throws java.io.IOException {
		boolean __g = true;

		switch(STATE) {
		case 0:
			__stkpush(1, ENGINE_read);
			STATE = 0;
			return -1;
		case 1:
			if(__g && $c == '\n') {
				STATE = 0;
				return 1;
			} else {
				STATE = 1;
				return 1;
			}
		case 2:
			STATE = 2;
			return 1;
		case 3:
			UNGET($c);
			STATE = 0;
			return 1;
		}
		return 0;
	}
	private boolean nanoParser_accepted() {
		return (STATE == 0 ||
				STATE == 1 ||
				STATE == 2 ||
				STATE == 3);
	}

	int nanoParser_execaction(int  $c) {
		switch(STATE) {
		case 2:
			System.err.println("read error");
			break;
		case 3:
			System.err.println("error");
exception.printStackTrace();
			break;
		case 1:
			putresult(res);
			break;
		case 0:
			putprompt1();
			break;
		}
		return 1;
	}

	boolean nanoParser_isend() {
		return false;
	}

	private final Engine ENGINE_nanoParser = new Engine() {

		int step(java.io.Reader __rd,
				int c) throws java.io.IOException {
			return nanoParser_step(__rd, c);
		}

		boolean accepted() {
			return nanoParser_accepted();
		}

		int execaction(int c) {
			return nanoParser_execaction(c);
		}

		boolean isend() {
			return nanoParser_isend();
		}

		int recover(Exception e) {
			if(e instanceof LispException) {
				return 3;
			} else {
				return -1;
			}
		}

		int deadState() {
			return 2;
		}

		int stateSize() {
			return 4;
		}

		int finallyState() {
			return -1;
		}

		public String toString() {
			return "nanoParser";
		}

	};

	void __stkpush(int st, Engine en) {
		Object[][] c;
		Engine[] b;
		int[] a;

		if(__slen >= __sts.length) {
			a = new int[__sts.length * 2];
			b = new Engine[__stk.length * 2];
			c = new Object[__stk.length * 2][];
			System.arraycopy(__sts, 0, a, 0, __sts.length);
			System.arraycopy(__stk, 0, b, 0, __stk.length);
			System.arraycopy(__stv, 0, c, 0, __stv.length);
			__sts = a;
			__stk = b;
			__stv = c;
		}
		__sts[__slen] = st;
		__stk[__slen] = en;
		__stv[__slen++] = new Object[en.stateSize()];
	}

	private int _parse(java.io.Reader rd,
			int x) throws java.io.IOException {
		boolean b = false;
		int c = x, a;
		Engine en;

		b = __stk[__slen - 1].accepted();
		if(rd == null) {
			throw new RuntimeException("can not recurse");
		} else {
			switch(__stk[__slen - 1].execaction(NINA_BEGIN)) {
			case NINA_ACCEPT:
				__logprint("accept " + __stk[__slen - 1]);
				return NINA_ACCEPT;
			case NINA_FAIL:
				__logprint("match failed: begin");
				__puttrace();
				return NINA_FAIL;
			case NINA_HALT_ACCEPT:
				__logprint("machine halted: begin");
				return NINA_HALT_ACCEPT;
			case NINA_HALT_REJECT:
				__logprint("machine halted: begin");
				return NINA_HALT_REJECT;
			}
		}

		try {
			do {
				en = __stk[__slen - 1];
				if(c < 0) {
					// do nothing
				} else if((a = en.step(rd, c)) > 0) {
					__logprint("transit to state " + STATE + ": ", c);
					b = en.accepted();
					switch(en.execaction(c)) {
					case NINA_ACCEPT:
						__logprint("accept " + __stk[__slen - 1]);
						UNGET(c);
						return NINA_ACCEPT;
					case NINA_FAIL:
						__logprint("match failed: ", c);
						__puttrace();
						UNGET(c);
						return NINA_FAIL;
					case NINA_HALT_ACCEPT:
						__logprint("machine halted: ", c);
						return NINA_HALT_ACCEPT;
					case NINA_HALT_REJECT:
						__logprint("machine halted: ", c);
						return NINA_HALT_REJECT;
					}
					if(__backtrack_flg) {
						__write_backtrack(c);
						__backtrack_flg = false;
					}
				} else if(a < 0) {
					__logprint("entering " + __stk[__slen - 1]);
					return c;
				} else if(b) {
					__logprint("accept " + __stk[__slen - 1]);
					UNGET(c);
					return NINA_ACCEPT;
				} else if(BACKTRACK(c)) {
					__logprint("match failed: try backtracking: ", c);
				} else {
					__logprint("match failed: ", c);
					__puttrace();
					UNGET(c);
					return NINA_FAIL;
				}
			} while((c = _read(rd)) >= 0);
			if(!b)  throw new TokenException();
			return NINA_ACCEPT;
		} catch(RuntimeException e) {
			UNGET(c);
			throw e;
		}
	}

	private Boolean execfinally() {
		int a, b;

		if((a = __stk[__slen - 1].finallyState()) >= 0) {
			b = STATE;  STATE = a;
			switch(__stk[__slen - 1].execaction(NINA_BEGIN)) {
			case NINA_HALT_ACCEPT:
				__slen = 0;
				return Boolean.TRUE;
			case NINA_HALT_REJECT:
				__slen = 0;
				return Boolean.FALSE;
			}
			STATE = b;
		}
		return null;
	}

	private int getdeadstate() {
		return __stk[__slen - 1].deadState();
	}

	private int getrecover(Exception e) {
		return __stk[__slen - 1].recover(e);
	}

	 boolean parse(java.io.Reader rd,
			Engine entry) throws java.io.IOException {
		int c = -1;
		Boolean b;

		__logopen();
		try {
			__stkpush(0, entry);
			while(true) {
				try {
					if((c = _parse(rd, c)) >= 0) {
						// do nothing
					} else if(c == NINA_FAIL) {
						while((STATE = getdeadstate()) < 0) {
							if((b = execfinally()) != null)  return b;
							if(__slen-- <= 1) {
								throw new TokenException();
							}
						}
					} else if(c == NINA_HALT_ACCEPT) {
						if((b = execfinally()) != null)  return b;
						__slen = 0;
						return true;
					} else if(c == NINA_HALT_REJECT) {
						if((b = execfinally()) != null)  return b;
						__slen = 0;
						return false;
					} else if(__slen > 1) {
						if((b = execfinally()) != null)  return b;
						STATE = __sts[--__slen];
					} else {
						if((b = execfinally()) != null)  return b;
						break;
					}
				} catch(RuntimeException e) {
					exception = e;
					if(__slen <= 0)  throw e;
					while((STATE = getrecover(e)) < 0) {
						if((b = execfinally()) != null)  return b;
						if(__slen-- <= 1)  throw e;
					}
				}
			}
			return __stk[__slen - 1].accepted();
		} finally {
			__logclose();
		}
	}

	 boolean parse(
			java.io.Reader rd) throws java.io.IOException {
		return parse(rd, ENGINE_nanoParser);
	}

	 boolean parse(
			java.io.InputStream rd) throws java.io.IOException {
		return parse(new java.io.InputStreamReader(rd));
	}

	 static boolean parseAll(
			java.io.Reader rd) throws java.io.IOException {
		NanoParser o = new NanoParser();

		return o.parse(rd);
	}

	 static boolean parseAll(
			java.io.InputStream rd) throws java.io.IOException {
		return parseAll(new java.io.InputStreamReader(rd));
	}

}
