diff --git a/uncompyle6/parsers/parse37base.py b/uncompyle6/parsers/parse37base.py index 915fd22d..00e6c362 100644 --- a/uncompyle6/parsers/parse37base.py +++ b/uncompyle6/parsers/parse37base.py @@ -988,6 +988,20 @@ class Python37BaseParser(PythonParser): pass + self.reduce_check_table = { + "_ifstmts_jump": ifstmts_jump, + "and": and_check, + "ifelsestmt": ifelsestmt, + "iflaststmt": iflaststmt, + "iflaststmtl": iflaststmt, + "ifstmt": ifstmt, + "ifstmtl": ifstmt, + "or": or_check, + "testtrue": testtrue, + "while1elsestmt": while1elsestmt, + "while1stmt": while1stmt, + } + self.check_reduce["and"] = "AST" self.check_reduce["annotate_tuple"] = "noAST" self.check_reduce["aug_assign1"] = "AST" @@ -1087,21 +1101,14 @@ class Python37BaseParser(PythonParser): def reduce_is_invalid(self, rule, ast, tokens, first, last): lhs = rule[0] n = len(tokens) + fn = self.reduce_check_table.get(lhs, None) + if fn: + return fn(self, lhs, n, rule, ast, tokens, first, last) - if lhs == "and" and ast: - return and_check(self, lhs, n, rule, ast, tokens, first, last) - elif lhs in ("aug_assign1", "aug_assign2") and ast[0][0] == "and": + if lhs in ("aug_assign1", "aug_assign2") and ast[0][0] == "and": return True elif lhs == "annotate_tuple": return not isinstance(tokens[first].attr, tuple) - elif lhs == "_ifstmts_jump" and len(rule[1]) > 1 and ast: - return ifstmts_jump(self, lhs, n, rule, ast, tokens, first, last) - elif lhs in ("iflaststmt", "iflaststmtl") and ast: - return iflaststmt(self, lhs, n, rule, ast, tokens, first, last) - elif lhs == "ifelsestmt": - return ifelsestmt(self, lhs, n, rule, ast, tokens, first, last) - elif lhs in ("ifstmt", "ifstmtl"): - return ifstmt(self, lhs, n, rule, ast, tokens, first, last) elif lhs == "import_from37": importlist37 = ast[3] alias37 = importlist37[0] @@ -1110,13 +1117,5 @@ class Python37BaseParser(PythonParser): assert store == "store" return alias37[0].attr != store[0].attr return False - elif lhs == "or": - return or_check(self, lhs, n, rule, ast, tokens, first, last) - elif lhs == "while1elsestmt": - return while1elsestmt(self, lhs, n, rule, ast, tokens, first, last) - elif lhs == "testtrue": - return testtrue(self, lhs, n, rule, ast, tokens, first, last) - elif lhs == "while1stmt": - return while1stmt(self, lhs, n, rule, ast, tokens, first, last) return False diff --git a/uncompyle6/parsers/reducecheck/ifstmts_jump.py b/uncompyle6/parsers/reducecheck/ifstmts_jump.py index a4e6116d..28761d3e 100644 --- a/uncompyle6/parsers/reducecheck/ifstmts_jump.py +++ b/uncompyle6/parsers/reducecheck/ifstmts_jump.py @@ -4,6 +4,10 @@ from uncompyle6.scanners.tok import Token def ifstmts_jump(self, lhs, n, rule, ast, tokens, first, last): + + if len(rule[1]) <= 1 or not ast: + return False + come_froms = ast[-1] # Make sure all of the "come froms" offset at the # end of the "if" come from somewhere inside the "if". diff --git a/uncompyle6/parsers/reducecheck/testtrue.py b/uncompyle6/parsers/reducecheck/testtrue.py index ffc6b613..9f859acc 100644 --- a/uncompyle6/parsers/reducecheck/testtrue.py +++ b/uncompyle6/parsers/reducecheck/testtrue.py @@ -1,15 +1,15 @@ # Copyright (c) 2020 Rocky Bernstein + def testtrue(self, lhs, n, rule, ast, tokens, first, last): # FIXME: make this work for all versions if self.version != 3.7: return False if rule == ("testtrue", ("expr", "jmp_true")): - pjit = tokens[min(last-1, n-2)] + pjit = tokens[min(last - 1, n - 2)] # If we have a backwards (looping) jump then this is - # really a testfalse - if (pjit == "POP_JUMP_IF_TRUE" and - tokens[first].off2int() > pjit.attr): - assert_next = tokens[min(last+1, n-1)] + # really a testfalse. "assert"s throw this off too. + if pjit == "POP_JUMP_IF_TRUE" and tokens[first].off2int() > pjit.attr: + assert_next = tokens[min(last + 1, n - 1)] return assert_next != "RAISE_VARARGS_1" return False