def Expression(self): g = self.Term() first = True while self.WeakSeparator(Scanner.bar_Sym, 19, 20): g2 = self.Term() if first: Graph.MakeFirstAlt(g) first = False Graph.MakeAlternative(g, g2) return g
def TokenExpr(self): g = self.TokenTerm() first = True while self.WeakSeparator(Scanner.bar_Sym, 6, 7): g2 = self.TokenTerm() if first: Graph.MakeFirstAlt(g) first = False Graph.MakeAlternative(g, g2) return g
def TokenTerm(self): g = self.TokenFactor() while self.StartOf(6): g2 = self.TokenFactor() Graph.MakeSequence(g, g2) if (self.la.kind == Scanner.CONTEXT_Sym): self.Get() self.Expect(Scanner.lparen_Sym) g2 = self.TokenExpr() Graph.SetContextTrans(g2.l) Graph.MakeSequence(g, g2) self.Expect(Scanner.rparen_Sym) return g
def TokenFactor(self): g = None if self.la.kind == Scanner.ident_Sym or self.la.kind == Scanner.string_Sym: s = self.Sym() name, kind = s if kind == self.id: c = CharClass.Find(name) if c is None: self.SemErr("undefined name") c = CharClass(s.name, set()) p = Node(Node.clas, None, 0) p.val = c.n g = Graph(p) self.tokenString = self.noString else: # str g = Graph.StrToGraph(name) if self.tokenString is None: self.tokenString = name else: self.tokenString = self.noString elif self.la.kind == Scanner.lparen_Sym: self.Get() g = self.TokenExpr() self.Expect(Scanner.rparen_Sym) elif self.la.kind == Scanner.lbrack_Sym: self.Get() g = self.TokenExpr() self.Expect(Scanner.rbrack_Sym) Graph.MakeOption(g) elif self.la.kind == Scanner.lbrace_Sym: self.Get() g = self.TokenExpr() self.Expect(Scanner.rbrace_Sym) Graph.MakeIteration(g) else: self.SynErr(76) if g is None: # invalid start of TokenFactor g = Graph(Node(Node.eps, None, 0)) return g
def Term(self): rslv = None g = None if self.StartOf(22): if (self.la.kind == Scanner.IF_Sym): rslv = Node(Node.rslv, None, self.la.line) rslv.pos = self.Resolver() g = Graph(rslv) g2 = self.Factor() if rslv is not None: Graph.MakeSequence(g, g2) else: g = g2 while self.StartOf(23): g2 = self.Factor() Graph.MakeSequence(g, g2) elif self.StartOf(24): g = Graph(Node(Node.eps, None, 0)) else: self.SynErr(67) if g is None: # invalid start of Term g = Graph(Node(Node.eps, None, 0)) return g
def TokenDecl(self, typ): s = self.Sym() name, kind = s sym = Symbol.Find(name) if sym is not None: self.SemErr("name declared twice") else: sym = Symbol(typ, name, self.token.line) sym.tokenKind = Symbol.fixedToken self.tokenString = None while not (self.StartOf(4)): self.SynErr(52) self.Get() if self.la.kind == Scanner.equal_Sym: self.Get() g = self.TokenExpr() self.Expect(Scanner.point_Sym) if kind == self.str: self.SemErr("a literal must not be declared with a structure") Graph.Finish(g) if (self.tokenString is None) or (self.tokenString == self.noString): DFA.ConvertToStates(g.l, sym) else: # TokenExpr is a single string if Tab.literals.get(self.tokenString) is not None: self.SemErr("token string declared twice") Tab.literals[self.tokenString] = sym DFA.MatchLiteral(self.tokenString, sym) elif self.StartOf(5): if kind == self.id: genScanner = False else: DFA.MatchLiteral(sym.name, sym) else: self.SynErr(53) if (self.la.kind == Scanner.lparenpoint_Sym): sym.semPos = self.SemText() if typ != Node.pr: self.SemErr("semantic action not allowed here")
def Factor(self): weak = False g = None if self.la.kind == Scanner.ident_Sym or self.la.kind == Scanner.string_Sym or self.la.kind == Scanner.WEAK_Sym: if (self.la.kind == Scanner.WEAK_Sym): self.Get() weak = True s = self.Sym() name, kind = s sym = Symbol.Find(name) if (sym is None) and (kind == self.str): sym = Tab.literals.get(name) undef = (sym is None) if undef: if kind == self.id: sym = Symbol(Node.nt, name, 0) # forward nt elif self.genScanner: sym = Symbol(Node.t, name, self.token.line) DFA.MatchLiteral(sym.name, sym) else: # undefined string in production self.SemErr("undefined string in production") sym = Tab.eofSy # dummy typ = sym.typ if (typ != Node.t) and (typ != Node.nt): self.SemErr("this symbol kind is not allowed in a production") if weak: if typ == Node.t: typ = Node.wt else: self.SemErr("only terminals may be weak") p = Node(typ, sym, self.token.line) g = Graph(p) if (self.la.kind == Scanner.less_Sym or self.la.kind == Scanner.lesspoint_Sym): self.Attribs(p) if kind != self.id: self.SemErr("a literal must not have attributes") if undef: sym.attrPos = p.pos # dummy sym.retVar = p.retVar # AH - dummy elif ((p.pos is None) != (sym.attrPos is None)) or ((p.retVar is None) != (sym.retVar is None)): self.SemErr( "attribute mismatch between declaration and use of this symbol" ) elif self.la.kind == Scanner.lparen_Sym: self.Get() g = self.Expression() self.Expect(Scanner.rparen_Sym) elif self.la.kind == Scanner.lbrack_Sym: self.Get() g = self.Expression() self.Expect(Scanner.rbrack_Sym) Graph.MakeOption(g) elif self.la.kind == Scanner.lbrace_Sym: self.Get() g = self.Expression() self.Expect(Scanner.rbrace_Sym) Graph.MakeIteration(g) elif self.la.kind == Scanner.lparenpoint_Sym: pos = self.SemText() p = Node(Node.sem, None, 0) p.pos = pos g = Graph(p) elif self.la.kind == Scanner.ANY_Sym: self.Get() p = Node(Node.any, None, 0) # p.set is set in Tab.SetupAnys g = Graph(p) elif self.la.kind == Scanner.SYNC_Sym: self.Get() p = Node(Node.sync, None, 0) g = Graph(p) else: self.SynErr(68) if g is None: # invalid start of Factor g = Graph(Node(Node.eps, None, 0)) return g
def Coco(self): g = Graph() g1 = Graph() g2 = Graph() s = set() if (self.la.kind == Scanner.from_Sym or self.la.kind == Scanner.import_Sym): ParserGen.usingPos = self.Imports() self.Expect(Scanner.COMPILER_Sym) self.genScanner = True Tab.ignored = set() self.Expect(Scanner.ident_Sym) gramName = self.token.val beg = self.la.pos while self.StartOf(1): self.Get() Tab.semDeclPos = Position(self.scanner.buffer, beg, self.la.pos - beg, 0) if (self.la.kind == Scanner.IGNORECASE_Sym): self.Get() DFA.ignoreCase = True if (self.la.kind == Scanner.CHARACTERS_Sym): self.Get() while self.la.kind == Scanner.ident_Sym: self.SetDecl() if (self.la.kind == Scanner.TOKENS_Sym): self.Get() while self.la.kind == Scanner.ident_Sym or self.la.kind == Scanner.string_Sym: self.TokenDecl(Node.t) if (self.la.kind == Scanner.NAMES_Sym): self.Get() while self.la.kind == Scanner.ident_Sym: self.NameDecl() if (self.la.kind == Scanner.PRAGMAS_Sym): self.Get() while self.la.kind == Scanner.ident_Sym or self.la.kind == Scanner.string_Sym: self.TokenDecl(Node.pr) while self.la.kind == Scanner.COMMENTS_Sym: self.Get() nested = False self.Expect(Scanner.FROM_Sym) g1 = self.TokenExpr() self.Expect(Scanner.TO_Sym) g2 = self.TokenExpr() if (self.la.kind == Scanner.NESTED_Sym): self.Get() nested = True Comment(g1.l, g2.l, nested) while self.la.kind == Scanner.IGNORE_Sym: self.Get() s = self.Set() Tab.ignored |= s # set union while not (self.la.kind == Scanner.EOF_SYM or self.la.kind == Scanner.PRODUCTIONS_Sym): self.SynErr(49) self.Get() self.Expect(Scanner.PRODUCTIONS_Sym) if self.genScanner: DFA.MakeDeterministic() Graph.DeleteNodes() while self.la.kind == Scanner.ident_Sym: self.Get() sym = Symbol.Find(self.token.val) undef = (sym is None) if undef: sym = Symbol(Node.nt, self.token.val, self.token.line) else: if sym.typ == Node.nt: if sym.graph is not None: self.SemErr("name declared twice") else: self.SemErr( "this symbol kind not allowed on left side of production" ) sym.line = self.token.line noAttrs = (sym.attrPos is None) sym.attrPos = None noRet = (sym.retVar is None) sym.retVar = None if (self.la.kind == Scanner.less_Sym or self.la.kind == Scanner.lesspoint_Sym): self.AttrDecl(sym) if not undef: if noAttrs != (sym.attrPos is None) or (noRet != (sym.retVar is None)): self.SemErr( "attribute mismatch between declaration and use of this symbol" ) if (self.la.kind == Scanner.lparenpoint_Sym): sym.semPos = self.SemText() self.ExpectWeak(Scanner.equal_Sym, 2) g = self.Expression() sym.graph = g.l Graph.Finish(g) self.ExpectWeak(Scanner.point_Sym, 3) self.Expect(Scanner.END_Sym) self.Expect(Scanner.ident_Sym) if gramName != self.token.val: self.SemErr("name does not match grammar name") Tab.gramSy = Symbol.Find(gramName) if Tab.gramSy is None: self.SemErr("missing production for grammar name") else: sym = Tab.gramSy if sym.attrPos is not None: self.SemErr("grammar symbol must not have attributes") Tab.noSym = Symbol(Node.t, "???", 0) #noSym gets highest number Tab.SetupAnys() Tab.RenumberPragmas() if Tab.ddt[2]: Node.PrintNodes() if Errors.count == 0: sys.stdout.write("checking\n") Tab.CompSymbolSets() if Tab.ddt[7]: Tab.XRef() if Tab.GrammarOk(): if not Tab.ddt[9]: sys.stdout.write("parser") ParserGen.WriteParser(Tab.ddt[10]) if self.genScanner: sys.stdout.write(" + scanner") DFA.WriteScanner(Tab.ddt[10]) if Tab.ddt[0]: DFA.PrintStates() if Tab.ddt[11]: sys.stdout.write(" + driver") DriverGen.WriteDriver() sys.stdout.write(" generated\n") if Tab.ddt[8]: ParserGen.WriteStatistics() if Tab.ddt[6]: Tab.PrintSymbolTable() self.Expect(Scanner.point_Sym)