1 package ro.infoiasi.donald.compiler.parser.runtime; 2 3 import java.util.Stack ; 4 5 public abstract class SkeletonLRParser { 6 private Lexer lex; 7 8 protected StackSymbol currentToken; 9 protected Stack parseStack = new Stack (); 10 protected boolean doneParsing = false; 11 protected boolean DEBUG = false; 12 13 protected short[][] productionTable; 14 protected short[][] actionTable; 15 protected short[][] gotoTable; 16 17 public SkeletonLRParser() { 18 } 20 21 public SkeletonLRParser(Lexer lex) { 22 this(); 23 setLexer(lex); 24 } 25 26 public void setLexer(Lexer lex) { 27 this.lex = lex; 28 } 29 30 public Lexer getLexer() { 31 return lex; 32 } 33 34 public abstract short[][] getProductionTable(); 35 public abstract short[][] getActionTable(); 36 public abstract short[][] getGotoTable(); 37 public abstract int getStartState(); 38 public abstract int getStartProduction(); 39 public abstract int getEOF(); 40 public abstract int getTokenOffset(); 41 protected abstract void initActions() throws Exception ; 42 43 public abstract StackSymbol doAction(int actNo, 44 SkeletonLRParser parser, Stack stack) 45 throws Exception ; 46 47 public void initCode() throws Exception { 48 } 50 public StackSymbol scan() 51 throws Exception { 52 StackSymbol sym = getLexer().nextStackSymbol(); 53 if (sym != null) { 54 return sym; 55 } else { 56 return new StackSymbol(getEOF()); 57 } 58 } 59 60 public void doneParsing() { 61 doneParsing = true; 62 } 63 64 public StackSymbol parse() throws Exception { 65 int action; 66 StackSymbol lhs = null; 67 short rhsCount, lhsSID; 68 69 productionTable = getProductionTable(); 70 actionTable = getActionTable(); 71 gotoTable = getGotoTable(); 72 73 initActions(); 74 initCode(); 75 76 currentToken = scan(); 77 trace("# Current Symbol is " + currentToken.sym); 78 79 parseStack.removeAllElements(); 80 parseStack.push(new StackSymbol(0, getStartState())); 81 82 while (!doneParsing) { 83 int state = ((StackSymbol)parseStack.peek()).parseState; 84 action = actionTable[state][currentToken.sym-getTokenOffset()]; 85 if (action > 0) { currentToken.parseState = action-1; 87 parseStack.push(currentToken); 88 currentToken = scan(); 89 } else if (action < 0) { int prod = (-action)-1; 91 lhs = doAction(prod, this, parseStack); 92 lhsSID = productionTable[prod][0]; 93 rhsCount = productionTable[prod][1]; 94 for (int i = 0; i<rhsCount; i++) { 95 parseStack.pop(); 96 } 97 98 state = ((StackSymbol)parseStack.peek()).parseState; 99 action = gotoTable[state][lhsSID]; 100 101 lhs.parseState = action; 102 parseStack.push(lhs); 103 } else { syntaxError(currentToken); 105 } 106 } 107 return lhs; 108 } 109 110 public void syntaxError(StackSymbol sym) 111 throws Exception { 112 reportFatalError("Syntax Error", sym); 114 } 115 116 public void reportError(String message, Object info) { 117 System.err.print(message); 118 if (info instanceof StackSymbol) { 119 StackSymbol sym = (StackSymbol)info; 120 if (sym.line != -1) { 121 System.err.print(" at line "+sym.line); 122 if (sym.column != -1) { 123 System.err.print(", column "+sym.column); 124 } 125 System.err.println(" of input"); 126 } 127 } else { 128 System.err.println(); 129 } 130 } 131 132 public void reportFatalError(String message, Object info) 133 throws java.lang.Exception { 134 doneParsing(); 135 reportError(message, info); 136 throw new Exception ("Can't recover from previous error(s)"); 137 } 138 139 private void trace(String message) { 140 if (DEBUG) { 141 System.out.println(message); 142 } 143 } 144 145 protected static short[][] unpackFromStrings(String [] sa) { 146 StringBuffer sb = new StringBuffer (sa[0]); 148 for (int i = 1; i<sa.length; i++) { 149 sb.append(sa[i]); 150 } 151 int n = 0; int size1 = (((int)sb.charAt(n))<<16) | ((int)sb.charAt(n+1)); n+=2; 153 short[][] result = new short[size1][]; 154 for (int i=0; i<size1; i++) { 155 int size2 = (((int)sb.charAt(n))<<16) | ((int)sb.charAt(n+1)); n+=2; 156 result[i] = new short[size2]; 157 for (int j=0; j<size2; j++) 158 result[i][j] = (short) (sb.charAt(n++)-2); 159 } 160 return result; 161 } 162 } 163 | Popular Tags |