void CompSyncSets() { allSyncSets = new BitArray(terminals.Count); allSyncSets[eofSy.n] = true; visited = new BitArray(nodes.Count); foreach (Symbol sym in nonterminals) { curSy = sym; CompSync(curSy.graph); } }
void CompFollowSets() { foreach (Symbol sym in nonterminals) { sym.follow = new BitArray(terminals.Count); sym.nts = new BitArray(nonterminals.Count); } gramSy.follow[eofSy.n] = true; visited = new BitArray(nodes.Count); foreach (Symbol sym in nonterminals) { // get direct successors of nonterminals curSy = sym; CompFollow(sym.graph); } foreach (Symbol sym in nonterminals) { // add indirect successors to followers visited = new BitArray(nonterminals.Count); curSy = sym; Complete(sym); } }
void Complete(Symbol sym) { if (!visited[sym.n]) { visited[sym.n] = true; foreach (Symbol s in nonterminals) { if (sym.nts[s.n]) { Complete(s); sym.follow.Or(s.follow); if (sym == curSy) sym.nts[s.n] = false; } } } }
public Node NewNode(int typ, Symbol sym, int line) { Node node = new Node(typ, sym, line); node.n = nodes.Count; nodes.Add(node); return node; }
public Symbol NewSym(int typ, string name, int line) { if (name.Length == 2 && name[0] == '"') { parser.SemErr("empty token not allowed"); name = "???"; } Symbol sym = new Symbol(typ, name, line); switch (typ) { case Node.t: sym.n = terminals.Count; terminals.Add(sym); break; case Node.pr: pragmas.Add(sym); break; case Node.nt: sym.n = nonterminals.Count; nonterminals.Add(sym); break; } return sym; }
public BitArray Expected(Node p, Symbol curSy) { BitArray s = First(p); if (DelGraph(p)) s.Or(curSy.follow); return s; }
// does not look behind resolvers; only called during LL(1) test and in CheckRes public BitArray Expected0(Node p, Symbol curSy) { if (p.typ == Node.rslv) return new BitArray(terminals.Count); else return Expected(p, curSy); }
public void CheckLL1() { foreach (Symbol sym in nonterminals) { curSy = sym; CheckAlts(curSy.graph); } }
public void CheckResolvers() { foreach (Symbol sym in nonterminals) { curSy = sym; CheckRes(curSy.graph, false); } }
public CNode(Symbol l, Symbol r) { left = l; right = r; }
BitArray visited; // mark list for graph traversals #endregion Fields #region Constructors public Tab(Parser parser) { this.parser = parser; trace = parser.trace; errors = parser.errors; eofSy = NewSym(Node.t, "EOF", 0); literals = new Hashtable(); }
void PrintSym(Symbol sym) { trace.Write("{0,3} {1,-14} {2}", sym.n, Name(sym.name), nTyp[sym.typ]); if (sym.attrPos==null) trace.Write(" false "); else trace.Write(" true "); if (sym.typ == Node.nt) { trace.Write("{0,5}", Num(sym.graph)); if (sym.deletable) trace.Write(" true "); else trace.Write(" false "); } else trace.Write(" "); trace.WriteLine("{0,5}", sym.line); }
public bool up; // true: "next" leads to successor in enclosing structure #endregion Fields #region Constructors public Node(int typ, Symbol sym, int line) { this.typ = typ; this.sym = sym; this.line = line; }
//--------------- check for LL(1) errors ---------------------- void LL1Error(int cond, Symbol sym) { string s = " LL1 warning in " + curSy.name + ": "; if (sym != null) s += sym.name + " is "; switch (cond) { case 1: s += "start of several alternatives"; break; case 2: s += "start & successor of deletable structure"; break; case 3: s += "an ANY node that matches no symbol"; break; case 4: s += "contents of [...] or {...} must not be deletable"; break; } errors.Warning(s); }
void GenProductions() { foreach (Symbol sym in tab.nonterminals) { curSy = sym; gen.Write("\tvoid {0}(", sym.name); CopySourcePart(sym.attrPos, 0); gen.WriteLine(") {"); CopySourcePart(sym.semPos, 2); GenCode(sym.graph, 2, new BitArray(tab.terminals.Count)); gen.WriteLine("\t}"); gen.WriteLine(); } }
void GenErrorMsg(int errTyp, Symbol sym) { errorNr++; err.Write("\t\t\tcase " + errorNr + ": s = \""); switch (errTyp) { case tErr: if (sym.name[0] == '"') err.Write(tab.Escape(sym.name) + " expected"); else err.Write(sym.name + " expected"); break; case altErr: err.Write("invalid " + sym.name); break; case syncErr: err.Write("this symbol not expected in " + sym.name); break; } err.WriteLine("\"; break;"); }