--tree++ shows template rule when it is used

This commit is contained in:
rocky
2018-05-13 14:21:46 -04:00
parent c087bd785e
commit 4c74bf1d9d
3 changed files with 71 additions and 9 deletions

View File

@@ -46,6 +46,7 @@ Debugging Options:
--asm -a include byte-code (disables --verify)
--grammar -g show matching grammar
--tree -t include syntax tree (disables --verify)
--tree++ add template rules to --tree when possible
Extensions of generated files:
'.pyc_dis' '.pyo_dis' successfully decompiled (and verified if --verify)
@@ -61,7 +62,7 @@ from uncompyle6.version import VERSION
def usage():
print("""usage:
%s [--verify | --weak-verify ] [--asm] [--tree] [--grammar] [-o <path>] FILE|DIR...
%s [--verify | --weak-verify ] [--asm] [--tree[+]] [--grammar] [-o <path>] FILE|DIR...
%s [--help | -h | --version | -V]
""" % (program, program))
sys.exit(1)
@@ -87,8 +88,10 @@ def main_bin():
try:
opts, files = getopt.getopt(sys.argv[1:], 'hagtdrVo:c:p:',
'help asm grammar linemaps recurse timestamp tree '
'fragments verify verify-run version weak-verify '
'help asm grammar linemaps recurse '
'timestamp tree tree+ '
'fragments verify verify-run version '
'weak-verify '
'showgrammar'.split(' '))
except getopt.GetoptError as e:
print('%s: %s' % (os.path.basename(sys.argv[0]), e), file=sys.stderr)
@@ -118,6 +121,9 @@ def main_bin():
elif opt in ('--tree', '-t'):
options['showast'] = True
options['do_verify'] = None
elif opt in ('--tree+',):
options['showast'] = 'Full'
options['do_verify'] = None
elif opt in ('--grammar', '-g'):
options['showgrammar'] = True
elif opt == '-o':

View File

@@ -251,6 +251,55 @@ class SourceWalker(GenericASTTraversal, object):
return
def str_with_template(self, ast):
stream = sys.stdout
stream.write(self.str_with_template1(ast, '', None))
stream.write('\n')
def str_with_template1(self, ast, indent, sibNum=None):
rv = str(ast.kind)
if sibNum is not None:
rv = "%2d. %s" % (sibNum, rv)
enumerate_children = False
if len(ast) > 1:
rv += " (%d)" % (len(ast))
enumerate_children = True
mapping = self._get_mapping(ast)
table = mapping[0]
key = ast
for i in mapping[1:]:
key = key[i]
pass
if key.kind in table:
rv += ": %s" % str(table[key.kind])
rv = indent + rv
indent += ' '
i = 0
for node in ast:
if hasattr(node, '__repr1__'):
if enumerate_children:
child = self.str_with_template1(node, indent, i)
else:
child = self.str_with_template1(node, indent, None)
else:
inst = node.format(line_prefix='L.')
if inst.startswith("\n"):
# Nuke leading \n
inst = inst[1:]
if enumerate_children:
child = indent + "%2d. %s" % (i, inst)
else:
child = indent + inst
pass
rv += "\n" + child
i += 1
return rv
def indent_if_source_nl(self, line_number, indent):
if (line_number != self.line_number):
self.write("\n" + self.indent + INDENT_PER_LEVEL[:-1])
@@ -2081,7 +2130,7 @@ class SourceWalker(GenericASTTraversal, object):
self.p.insts = p_insts
except (python_parser.ParserError, AssertionError) as e:
raise ParserError(e, tokens)
maybe_show_tree(self.showast, ast)
maybe_show_tree(self, ast)
return ast
# The bytecode for the end of the main routine has a
@@ -2114,7 +2163,8 @@ class SourceWalker(GenericASTTraversal, object):
except (python_parser.ParserError, AssertionError) as e:
raise ParserError(e, tokens)
maybe_show_tree(self.showast, ast)
# from trepan.api import debug; debug()
maybe_show_tree(self, ast)
checker(ast, False, self.ast_errors)

View File

@@ -32,7 +32,7 @@ def maybe_show_asm(showasm, tokens):
stream.write('\n')
def maybe_show_tree(show_tree, ast):
def maybe_show_tree(walker, ast):
"""
Show the ast based on the showast flag (or file object), writing to the
appropriate stream depending on the type of the flag.
@@ -42,9 +42,15 @@ def maybe_show_tree(show_tree, ast):
like object, into which the ast will be written).
:param ast: The ast to show.
"""
if show_tree:
stream = show_tree if hasattr(show_tree, 'write') else sys.stdout
stream.write(str(ast))
if walker.showast:
if hasattr(walker.showast, 'write'):
stream = walker.showast
else:
stream = sys.stdout
if walker.showast == 'Full':
walker.str_with_template(ast)
else:
stream.write(str(ast))
stream.write('\n')