diff --git a/uncompyle6/parsers/parse2.py b/uncompyle6/parsers/parse2.py index 37569812..ae992e66 100644 --- a/uncompyle6/parsers/parse2.py +++ b/uncompyle6/parsers/parse2.py @@ -181,6 +181,11 @@ class Python2Parser(PythonParser): trystmt ::= SETUP_EXCEPT suite_stmts_opt POP_BLOCK try_middle COME_FROM + try_middle ::= JUMP_FORWARD COME_FROM except_stmts + END_FINALLY COME_FROM + try_middle ::= jmp_abs COME_FROM except_stmts + END_FINALLY + except_stmts ::= except_stmts except_stmt except_stmts ::= except_stmt diff --git a/uncompyle6/parsers/parse26.py b/uncompyle6/parsers/parse26.py index a244eba2..b162c68f 100644 --- a/uncompyle6/parsers/parse26.py +++ b/uncompyle6/parsers/parse26.py @@ -27,11 +27,7 @@ class Python26Parser(Python2Parser): POP_TOP END_FINALLY come_froms try_middle ::= JUMP_FORWARD COME_FROM except_stmts - END_FINALLY come_froms - try_middle ::= JUMP_FORWARD COME_FROM except_stmts - come_from_pop END_FINALLY come_froms - try_middle ::= JUMP_FORWARD COME_FROM except_stmts - END_FINALLY come_froms + come_from_pop END_FINALLY COME_FROM try_middle ::= jmp_abs COME_FROM except_stmts POP_TOP END_FINALLY @@ -39,9 +35,6 @@ class Python26Parser(Python2Parser): try_middle ::= jmp_abs COME_FROM except_stmts come_from_pop END_FINALLY - try_middle ::= jmp_abs COME_FROM except_stmts - END_FINALLY - trystmt ::= SETUP_EXCEPT suite_stmts_opt come_from_pop try_middle diff --git a/uncompyle6/parsers/parse27.py b/uncompyle6/parsers/parse27.py index b1330a6d..91decb80 100644 --- a/uncompyle6/parsers/parse27.py +++ b/uncompyle6/parsers/parse27.py @@ -27,11 +27,6 @@ class Python27Parser(Python2Parser): def p_try27(self, args): """ - try_middle ::= JUMP_FORWARD COME_FROM except_stmts - END_FINALLY COME_FROM - try_middle ::= jmp_abs COME_FROM except_stmts - END_FINALLY - tryelsestmt ::= SETUP_EXCEPT suite_stmts_opt POP_BLOCK try_middle else_suite COME_FROM diff --git a/uncompyle6/scanners/scanner2.py b/uncompyle6/scanners/scanner2.py index ff23c627..fab27754 100644 --- a/uncompyle6/scanners/scanner2.py +++ b/uncompyle6/scanners/scanner2.py @@ -44,7 +44,7 @@ class Scanner2(scan.Scanner): Pick out tokens from an uncompyle6 code object, and transform them, returning a list of uncompyle6 'Token's. - The tranformations are made to assist the deparsing grammar. + The transformations are made to assist the deparsing grammar. Specificially: - various types of LOAD_CONST's are categorized in terms of what they load - COME_FROM instructions are added to assist parsing control structures @@ -56,7 +56,7 @@ class Scanner2(scan.Scanner): """ show_asm = self.show_asm if not show_asm else show_asm - # show_asm = 'both' + # show_asm = 'after' if show_asm in ('both', 'before'): from xdis.bytecode import Bytecode bytecode = Bytecode(co, self.opc) @@ -846,6 +846,8 @@ class Scanner2(scan.Scanner): pass pass + + # FIXME: All the <2.6 conditions are is horrible. We need a better way. if label is not None and label != -1: # In Python <= 2.6, the POP_TOP in: # RETURN_VALUE, POP_TOP @@ -854,8 +856,19 @@ class Scanner2(scan.Scanner): if not (self.version <= 2.6 and self.code[label] == self.opc.POP_TOP and self.code[self.prev[label]] == self.opc.RETURN_VALUE): - targets[label] = targets.get(label, []) + [offset] - elif op == self.opc.END_FINALLY and offset in self.fixed_jumps: + # In Python <= 2.6, don't add a COME_FROM, for: + # JUMP_FORWARD, END_FINALLY + # or: + # JUMP_FORWARD, POP_TOP, END_FINALLY + if not (self.version <= 2.6 and op == self.opc.JUMP_FORWARD + and ((self.code[offset+3] == self.opc.END_FINALLY) + or (self.code[offset+3] == self.opc.POP_TOP + and self.code[offset+4] == self.opc.END_FINALLY))): + targets[label] = targets.get(label, []) + [offset] + pass + pass + pass + elif op == self.opc.END_FINALLY and offset in self.fixed_jumps and self.version == 2.7: label = self.fixed_jumps[offset] targets[label] = targets.get(label, []) + [offset] return targets diff --git a/uncompyle6/scanners/scanner26.py b/uncompyle6/scanners/scanner26.py index c5da52b5..4e52369b 100755 --- a/uncompyle6/scanners/scanner26.py +++ b/uncompyle6/scanners/scanner26.py @@ -75,7 +75,7 @@ class Scanner26(scan.Scanner2): Pick out tokens from an uncompyle6 code object, and transform them, returning a list of uncompyle6 'Token's. - The tranformations are made to assist the deparsing grammar. + The transformations are made to assist the deparsing grammar. Specificially: - various types of LOAD_CONST's are categorized in terms of what they load - COME_FROM instructions are added to assist parsing control structures @@ -87,7 +87,7 @@ class Scanner26(scan.Scanner2): """ show_asm = self.show_asm if not show_asm else show_asm - # show_asm = 'both' + # show_asm = 'after' if show_asm in ('both', 'before'): from xdis.bytecode import Bytecode bytecode = Bytecode(co, self.opc) diff --git a/uncompyle6/scanners/scanner3.py b/uncompyle6/scanners/scanner3.py index 1089cb0f..59b54793 100644 --- a/uncompyle6/scanners/scanner3.py +++ b/uncompyle6/scanners/scanner3.py @@ -115,7 +115,7 @@ class Scanner3(Scanner): Pick out tokens from an uncompyle6 code object, and transform them, returning a list of uncompyle6 'Token's. - The tranformations are made to assist the deparsing grammar. + The transformations are made to assist the deparsing grammar. Specificially: - various types of LOAD_CONST's are categorized in terms of what they load - COME_FROM instructions are added to assist parsing control structures