mirror of https://github.com/python/cpython
718 lines
18 KiB
Python
718 lines
18 KiB
Python
#!/usr/bin/env python3.8
|
|
# @generated by pegen from ./Tools/peg_generator/pegen/metagrammar.gram
|
|
|
|
import ast
|
|
import sys
|
|
import tokenize
|
|
|
|
from typing import Any, Optional
|
|
|
|
from pegen.parser import memoize, memoize_left_rec, logger, Parser
|
|
from ast import literal_eval
|
|
|
|
from pegen.grammar import (
|
|
Alt,
|
|
Cut,
|
|
Gather,
|
|
Group,
|
|
Item,
|
|
Lookahead,
|
|
LookaheadOrCut,
|
|
MetaTuple,
|
|
MetaList,
|
|
NameLeaf,
|
|
NamedItem,
|
|
NamedItemList,
|
|
NegativeLookahead,
|
|
Opt,
|
|
Plain,
|
|
PositiveLookahead,
|
|
Repeat0,
|
|
Repeat1,
|
|
Rhs,
|
|
Rule,
|
|
RuleList,
|
|
RuleName,
|
|
Grammar,
|
|
StringLeaf,
|
|
)
|
|
|
|
class GeneratedParser(Parser):
|
|
|
|
@memoize
|
|
def start(self) -> Optional[Grammar]:
|
|
# start: grammar $
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(grammar := self.grammar())
|
|
and
|
|
(endmarker := self.expect('ENDMARKER'))
|
|
):
|
|
return grammar
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def grammar(self) -> Optional[Grammar]:
|
|
# grammar: metas rules | rules
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(metas := self.metas())
|
|
and
|
|
(rules := self.rules())
|
|
):
|
|
return Grammar ( rules , metas )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(rules := self.rules())
|
|
):
|
|
return Grammar ( rules , [ ] )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def metas(self) -> Optional[MetaList]:
|
|
# metas: meta metas | meta
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(meta := self.meta())
|
|
and
|
|
(metas := self.metas())
|
|
):
|
|
return [ meta ] + metas
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(meta := self.meta())
|
|
):
|
|
return [ meta ]
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def meta(self) -> Optional[MetaTuple]:
|
|
# meta: "@" NAME NEWLINE | "@" NAME NAME NEWLINE | "@" NAME STRING NEWLINE
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("@"))
|
|
and
|
|
(name := self.name())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
):
|
|
return ( name . string , None )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("@"))
|
|
and
|
|
(a := self.name())
|
|
and
|
|
(b := self.name())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
):
|
|
return ( a . string , b . string )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("@"))
|
|
and
|
|
(name := self.name())
|
|
and
|
|
(string := self.string())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
):
|
|
return ( name . string , literal_eval ( string . string ) )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def rules(self) -> Optional[RuleList]:
|
|
# rules: rule rules | rule
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(rule := self.rule())
|
|
and
|
|
(rules := self.rules())
|
|
):
|
|
return [ rule ] + rules
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(rule := self.rule())
|
|
):
|
|
return [ rule ]
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def rule(self) -> Optional[Rule]:
|
|
# rule: rulename memoflag? ":" alts NEWLINE INDENT more_alts DEDENT | rulename memoflag? ":" NEWLINE INDENT more_alts DEDENT | rulename memoflag? ":" alts NEWLINE
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(rulename := self.rulename())
|
|
and
|
|
(opt := self.memoflag(),)
|
|
and
|
|
(literal := self.expect(":"))
|
|
and
|
|
(alts := self.alts())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
and
|
|
(indent := self.expect('INDENT'))
|
|
and
|
|
(more_alts := self.more_alts())
|
|
and
|
|
(dedent := self.expect('DEDENT'))
|
|
):
|
|
return Rule ( rulename [ 0 ] , rulename [ 1 ] , Rhs ( alts . alts + more_alts . alts ) , memo = opt )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(rulename := self.rulename())
|
|
and
|
|
(opt := self.memoflag(),)
|
|
and
|
|
(literal := self.expect(":"))
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
and
|
|
(indent := self.expect('INDENT'))
|
|
and
|
|
(more_alts := self.more_alts())
|
|
and
|
|
(dedent := self.expect('DEDENT'))
|
|
):
|
|
return Rule ( rulename [ 0 ] , rulename [ 1 ] , more_alts , memo = opt )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(rulename := self.rulename())
|
|
and
|
|
(opt := self.memoflag(),)
|
|
and
|
|
(literal := self.expect(":"))
|
|
and
|
|
(alts := self.alts())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
):
|
|
return Rule ( rulename [ 0 ] , rulename [ 1 ] , alts , memo = opt )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def rulename(self) -> Optional[RuleName]:
|
|
# rulename: NAME '[' NAME '*' ']' | NAME '[' NAME ']' | NAME
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
and
|
|
(literal := self.expect('['))
|
|
and
|
|
(type := self.name())
|
|
and
|
|
(literal_1 := self.expect('*'))
|
|
and
|
|
(literal_2 := self.expect(']'))
|
|
):
|
|
return ( name . string , type . string + "*" )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
and
|
|
(literal := self.expect('['))
|
|
and
|
|
(type := self.name())
|
|
and
|
|
(literal_1 := self.expect(']'))
|
|
):
|
|
return ( name . string , type . string )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
):
|
|
return ( name . string , None )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def memoflag(self) -> Optional[str]:
|
|
# memoflag: '(' 'memo' ')'
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect('('))
|
|
and
|
|
(literal_1 := self.expect('memo'))
|
|
and
|
|
(literal_2 := self.expect(')'))
|
|
):
|
|
return "memo"
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def alts(self) -> Optional[Rhs]:
|
|
# alts: alt "|" alts | alt
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(alt := self.alt())
|
|
and
|
|
(literal := self.expect("|"))
|
|
and
|
|
(alts := self.alts())
|
|
):
|
|
return Rhs ( [ alt ] + alts . alts )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(alt := self.alt())
|
|
):
|
|
return Rhs ( [ alt ] )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def more_alts(self) -> Optional[Rhs]:
|
|
# more_alts: "|" alts NEWLINE more_alts | "|" alts NEWLINE
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("|"))
|
|
and
|
|
(alts := self.alts())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
and
|
|
(more_alts := self.more_alts())
|
|
):
|
|
return Rhs ( alts . alts + more_alts . alts )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("|"))
|
|
and
|
|
(alts := self.alts())
|
|
and
|
|
(newline := self.expect('NEWLINE'))
|
|
):
|
|
return Rhs ( alts . alts )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def alt(self) -> Optional[Alt]:
|
|
# alt: items '$' action | items '$' | items action | items
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(items := self.items())
|
|
and
|
|
(literal := self.expect('$'))
|
|
and
|
|
(action := self.action())
|
|
):
|
|
return Alt ( items + [ NamedItem ( None , NameLeaf ( 'ENDMARKER' ) ) ] , action = action )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(items := self.items())
|
|
and
|
|
(literal := self.expect('$'))
|
|
):
|
|
return Alt ( items + [ NamedItem ( None , NameLeaf ( 'ENDMARKER' ) ) ] , action = None )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(items := self.items())
|
|
and
|
|
(action := self.action())
|
|
):
|
|
return Alt ( items , action = action )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(items := self.items())
|
|
):
|
|
return Alt ( items , action = None )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def items(self) -> Optional[NamedItemList]:
|
|
# items: named_item items | named_item
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(named_item := self.named_item())
|
|
and
|
|
(items := self.items())
|
|
):
|
|
return [ named_item ] + items
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(named_item := self.named_item())
|
|
):
|
|
return [ named_item ]
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def named_item(self) -> Optional[NamedItem]:
|
|
# named_item: NAME '[' NAME '*' ']' '=' ~ item | NAME '[' NAME ']' '=' ~ item | NAME '=' ~ item | item | lookahead
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
and
|
|
(literal := self.expect('['))
|
|
and
|
|
(type := self.name())
|
|
and
|
|
(literal_1 := self.expect('*'))
|
|
and
|
|
(literal_2 := self.expect(']'))
|
|
and
|
|
(literal_3 := self.expect('='))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(item := self.item())
|
|
):
|
|
return NamedItem ( name . string , item , f"{type.string}*" )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
and
|
|
(literal := self.expect('['))
|
|
and
|
|
(type := self.name())
|
|
and
|
|
(literal_1 := self.expect(']'))
|
|
and
|
|
(literal_2 := self.expect('='))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(item := self.item())
|
|
):
|
|
return NamedItem ( name . string , item , type . string )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
and
|
|
(literal := self.expect('='))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(item := self.item())
|
|
):
|
|
return NamedItem ( name . string , item )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(item := self.item())
|
|
):
|
|
return NamedItem ( None , item )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(it := self.lookahead())
|
|
):
|
|
return NamedItem ( None , it )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def lookahead(self) -> Optional[LookaheadOrCut]:
|
|
# lookahead: '&' ~ atom | '!' ~ atom | '~'
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect('&'))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(atom := self.atom())
|
|
):
|
|
return PositiveLookahead ( atom )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect('!'))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(atom := self.atom())
|
|
):
|
|
return NegativeLookahead ( atom )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect('~'))
|
|
):
|
|
return Cut ( )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def item(self) -> Optional[Item]:
|
|
# item: '[' ~ alts ']' | atom '?' | atom '*' | atom '+' | atom '.' atom '+' | atom
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect('['))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(alts := self.alts())
|
|
and
|
|
(literal_1 := self.expect(']'))
|
|
):
|
|
return Opt ( alts )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(atom := self.atom())
|
|
and
|
|
(literal := self.expect('?'))
|
|
):
|
|
return Opt ( atom )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(atom := self.atom())
|
|
and
|
|
(literal := self.expect('*'))
|
|
):
|
|
return Repeat0 ( atom )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(atom := self.atom())
|
|
and
|
|
(literal := self.expect('+'))
|
|
):
|
|
return Repeat1 ( atom )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(sep := self.atom())
|
|
and
|
|
(literal := self.expect('.'))
|
|
and
|
|
(node := self.atom())
|
|
and
|
|
(literal_1 := self.expect('+'))
|
|
):
|
|
return Gather ( sep , node )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(atom := self.atom())
|
|
):
|
|
return atom
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def atom(self) -> Optional[Plain]:
|
|
# atom: '(' ~ alts ')' | NAME | STRING
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect('('))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(alts := self.alts())
|
|
and
|
|
(literal_1 := self.expect(')'))
|
|
):
|
|
return Group ( alts )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
):
|
|
return NameLeaf ( name . string )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(string := self.string())
|
|
):
|
|
return StringLeaf ( string . string )
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def action(self) -> Optional[str]:
|
|
# action: "{" ~ target_atoms "}"
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("{"))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(target_atoms := self.target_atoms())
|
|
and
|
|
(literal_1 := self.expect("}"))
|
|
):
|
|
return target_atoms
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def target_atoms(self) -> Optional[str]:
|
|
# target_atoms: target_atom target_atoms | target_atom
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(target_atom := self.target_atom())
|
|
and
|
|
(target_atoms := self.target_atoms())
|
|
):
|
|
return target_atom + " " + target_atoms
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(target_atom := self.target_atom())
|
|
):
|
|
return target_atom
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
@memoize
|
|
def target_atom(self) -> Optional[str]:
|
|
# target_atom: "{" ~ target_atoms "}" | NAME | NUMBER | STRING | "?" | ":" | !"}" OP
|
|
mark = self.mark()
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("{"))
|
|
and
|
|
(cut := True)
|
|
and
|
|
(target_atoms := self.target_atoms())
|
|
and
|
|
(literal_1 := self.expect("}"))
|
|
):
|
|
return "{" + target_atoms + "}"
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(name := self.name())
|
|
):
|
|
return name . string
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(number := self.number())
|
|
):
|
|
return number . string
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(string := self.string())
|
|
):
|
|
return string . string
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect("?"))
|
|
):
|
|
return "?"
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
(literal := self.expect(":"))
|
|
):
|
|
return ":"
|
|
self.reset(mark)
|
|
if cut: return None
|
|
cut = False
|
|
if (
|
|
self.negative_lookahead(self.expect, "}")
|
|
and
|
|
(op := self.op())
|
|
):
|
|
return op . string
|
|
self.reset(mark)
|
|
if cut: return None
|
|
return None
|
|
|
|
|
|
if __name__ == '__main__':
|
|
from pegen.parser import simple_parser_main
|
|
simple_parser_main(GeneratedParser)
|