- /** parse <tt>input</tt>, using the table <tt>pt</tt> to drive the parser */
- public Forest<R> parse(Token.Stream<T> input) throws IOException, Failed {
- GSS gss = new GSS();
- Token.Location loc = input.getLocation();
- GSS.Phase current = gss.new Phase(null, this, null, input.next(1, 0, 0), loc, null);
- current.newNode(null, Forest.leaf(null, null), pt.start, true);
- int count = 1;
- for(;;) {
- loc = input.getLocation();
- //current.checkFailure();
- current.reduce();
- Forest forest = current.token==null ? null : shiftedToken((T)current.token, loc);
- GSS.Phase next = gss.new Phase(current, this, current, input.next(count, gss.resets, gss.waits), loc, forest);
- count = next.hash.size();
- if (current.isDone()) return (Forest<R>)current.finalResult;
- current = next;
- }
- }
-
-
- // Exceptions //////////////////////////////////////////////////////////////////////////////
-
- public static class Failed extends RuntimeException {
- private final Token.Location location;
- private final String message;
- public Failed() { this("", null); }
- public Failed(String message, Token.Location loc) { this.location = loc; this.message = message; }
- public Token.Location getLocation() { return location; }
- public String toString() { return message/* + (location==null ? "" : (" at " + location))*/; }
- }
-
- public static class Ambiguous extends RuntimeException {
- public final Forest ambiguity;
- public Ambiguous(Forest ambiguity) { this.ambiguity = ambiguity; }
- public String toString() {
- StringBuffer sb = new StringBuffer();
- sb.append("unresolved ambiguity "/*"at " + ambiguity.getLocation() + ":"*/);
- for(Object result : ambiguity.expand(false))
- sb.append("\n " + result);
- return sb.toString();
+ /** parse <tt>input</tt>, and return the shared packed parse forest (or throw an exception) */
+ public Forest<NodeType> parse(Input<Token> input) throws IOException, ParseFailed {
+ verbose = System.getProperty("sbp.verbose", null) != null;
+ spinpos = 0;
+ try {
+ GSS gss = new GSS(input, this);
+ for(GSS.Phase current = gss.new Phase<Token>(pt.start); ;) {
+
+ if (verbose) {
+ String s;
+ s = " " + spin[spinpos++ % (spin.length)]+" parsing ";
+ s += input.getName();
+ s += " "+input.getLocation();
+ while(s.indexOf(':') != -1 && s.indexOf(':') < 8) s = " " + s;
+ String y = "@"+gss.viewPos+" ";
+ while(y.length() < 9) y = " " + y;
+ s += y;
+ //s += " doom="+Node.doomedNodes;
+ //while(s.length() < 40) s = s + " ";
+ s += " nodes="+gss.numOldNodes;
+ while(s.length() < 50) s = s + " ";
+ s += " shifted="+gss.numNewNodes;
+ while(s.length() < 60) s = s + " ";
+ s += " reductions="+gss.numReductions;
+ System.err.print("\r"+s+ANSI.clreol()+"\r");
+ }
+
+ // FIXME: make sure all the locations line up properly in here
+ if (current.isDone()) return (Forest<NodeType>)current.finalResult;
+ Forest forest = shiftToken((Token)current.token, input.getLocation());
+ current = gss.new Phase<Token>(current, forest);
+ }
+ } finally {
+ if (verbose)
+ System.err.print("\r \r");