You've already forked python-uncompyle6
mirror of
https://github.com/rocky/python-uncompyle6.git
synced 2025-08-04 01:09:52 +08:00
--tree++ shows template rule when it is used
This commit is contained in:
@@ -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':
|
||||
|
@@ -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)
|
||||
|
||||
|
@@ -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,8 +42,14 @@ 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
|
||||
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')
|
||||
|
||||
|
Reference in New Issue
Block a user