Exemplo n.º 1
0
    def n_mkfunc(self, node):
        """If the function has a docstring (this is found in the code
        constants), pull that out and make it part of the syntax
        tree. When generating the source string that AST node rather
        than the code field is seen and used.
        """

        if self.version >= (3, 7):
            code_index = -3
        else:
            code_index = -2

        code = find_code_node(node, code_index).attr

        mkfunc_pattr = node[-1].pattr
        if isinstance(mkfunc_pattr, tuple):
            assert len(mkfunc_pattr, 4) and isinstance(mkfunc_pattr, int)
            is_closure = node[-1].pattr[3] != 0
        else:
            # FIXME: This is what we had before. It is hoaky and probably wrong.
            is_closure = mkfunc_pattr == "closure"

        if ((not is_closure) and len(code.co_consts) > 0
                and isinstance(code.co_consts[0], str)):
            docstring_node = SyntaxTree(
                "docstring",
                [Token("LOAD_STR", has_arg=True, pattr=code.co_consts[0])])
            docstring_node.transformed_by = "n_mkfunc"
            node = SyntaxTree("mkfunc", node[:-1] + [docstring_node, node[-1]])
            node.transformed_by = "n_mkfunc"

        return node
Exemplo n.º 2
0
    def n_mkfunc(self, node):
        """If the function has a docstring (this is found in the code
        constants), pull that out and make it part of the syntax
        tree. When generating the source string that AST node rather
        than the code field is seen and used.
        """

        if self.version >= 3.7:
            code_index = -3
        else:
            code_index = -2

        code = find_code_node(node, code_index).attr

        if (
            node[-1].pattr != "closure"
            and len(code.co_consts) > 0
            and code.co_consts[0] is not None
        ):
            docstring_node = SyntaxTree(
                "docstring", [Token("LOAD_STR", has_arg=True, pattr=code.co_consts[0])]
            )
            docstring_node.transformed_by = "n_mkfunc"
            node = SyntaxTree("mkfunc", node[:-1] + [docstring_node, node[-1]])
            node.transformed_by = "n_mkfunc"

        return node
Exemplo n.º 3
0
 def n_stmts(self, node):
     if node.first_child() == "SETUP_ANNOTATIONS":
         prev = node[0][0]
         new_stmts = [node[0]]
         for i, sstmt in enumerate(node[1:]):
             ann_assign = sstmt[0]
             if (ann_assign == "ann_assign" and prev == "assign"):
                 annotate_var = ann_assign[-2]
                 if annotate_var.attr == prev[-1][0].attr:
                     node[i].kind = "deleted " + node[i].kind
                     del new_stmts[-1]
                     ann_assign_init = SyntaxTree(
                         "ann_assign_init",
                         [ann_assign[0],
                          copy(prev[0]), annotate_var])
                     if sstmt[0] == "ann_assign":
                         sstmt[0] = ann_assign_init
                     else:
                         sstmt[0][0] = ann_assing_init
                     sstmt[0].transformed_by = "n_stmts"
                     pass
                 pass
             new_stmts.append(sstmt)
             prev = ann_assign
             pass
         node.data = new_stmts
     return node
Exemplo n.º 4
0
 def n_stmts(self, node):
     if node.first_child() == "SETUP_ANNOTATIONS":
         prev = node[0][0]
         new_stmts = [node[0]]
         for i, sstmt in enumerate(node[1:]):
             ann_assign = sstmt[0][0]
             if (
                 sstmt[0] == "stmt"
                 and ann_assign == "ann_assign"
                 and prev == "assign"
             ):
                 annotate_var = ann_assign[-2]
                 if annotate_var.attr == prev[-1][0].attr:
                     del new_stmts[-1]
                     sstmt[0][0] = SyntaxTree(
                         "ann_assign_init", [ann_assign[0], prev[0], annotate_var]
                     )
                     sstmt[0][0].transformed_by = "n_stmts"
                     pass
                 pass
             new_stmts.append(sstmt)
             prev = ann_assign
             pass
         node.data = new_stmts
     return node
Exemplo n.º 5
0
    def transform(self, ast, code):
        self.maybe_show_tree(ast)
        self.ast = copy(ast)
        self.ast = self.traverse(self.ast, is_lambda=False)

        try:
            # Disambiguate a string (expression) which appears as a "call_stmt" at
            # the beginning of a function versus a docstring. Seems pretty academic,
            # but this is Python.
            call_stmt = ast[0][0]
            if is_not_docstring(call_stmt):
                call_stmt.kind = "string_at_beginning"
                call_stmt.transformed_by = "transform"
                pass
        except:
            pass

        try:
            for i in range(len(self.ast)):
                sstmt = ast[i]
                if len(sstmt) == 1 and sstmt == "sstmt":
                    self.ast[i] = self.ast[i][0]

                if is_docstring(self.ast[i], self.version, code.co_consts):
                    load_const = self.ast[i].first_child()
                    docstring_ast = SyntaxTree(
                        "docstring",
                        [
                            Token(
                                "LOAD_STR",
                                has_arg=True,
                                offset=0,
                                attr=load_const.attr,
                                pattr=load_const.pattr,
                            )
                        ],
                    )
                    docstring_ast.transformed_by = "transform"
                    del self.ast[i]
                    self.ast.insert(0, docstring_ast)
                    break

            if self.ast[-1] == RETURN_NONE:
                self.ast.pop()  # remove last node
                # todo: if empty, add 'pass'
        except:
            pass

        return self.ast
Exemplo n.º 6
0
 def n_import_from37(self, node):
     importlist37 = node[3]
     assert importlist37 == "importlist37"
     if len(importlist37) == 1:
         alias37 = importlist37[0]
         store = alias37[1]
         assert store == "store"
         alias_name = store[0].attr
         import_name_attr = node[2]
         assert import_name_attr == "IMPORT_NAME_ATTR"
         dotted_names = import_name_attr.attr.split(".")
         if len(dotted_names) > 1 and dotted_names[-1] == alias_name:
             # Simulate:
             # Instead of
             # import_from37 ::= LOAD_CONST LOAD_CONST IMPORT_NAME_ATTR importlist37 POP_TOP
             # import_as37   ::= LOAD_CONST LOAD_CONST importlist37 store POP_TOP
             # 'import_as37':     ( '%|import %c as %c\n', 2, -2),
             node = SyntaxTree(
                 "import_as37",
                 [node[0], node[1], import_name_attr, store, node[-1]])
             node.transformed_by = "n_import_from37"
             pass
         pass
     return node
Exemplo n.º 7
0
    "list": 0,  # [expressions...]
    "list_comp": 0,
    "set_comp": 0,
    "set_comp_expr": 0,
    "unary_convert": 0,
}

LINE_LENGTH = 80

# Some parse trees created below are used for comparing code
# fragments (like "return None" at the end of functions).

RETURN_LOCALS = SyntaxTree(
    "return",
    [
        SyntaxTree("ret_expr", [SyntaxTree("expr", [Token("LOAD_LOCALS")])]),
        Token("RETURN_VALUE"),
    ],
)

NONE = SyntaxTree("expr", [NoneToken])

RETURN_NONE = SyntaxTree(
    "stmt", [SyntaxTree("return", [NONE, Token("RETURN_VALUE")])])

PASS = SyntaxTree(
    "stmts",
    [SyntaxTree("sstmt", [SyntaxTree("stmt", [SyntaxTree("pass", [])])])])

ASSIGN_DOC_STRING = lambda doc_string, doc_load: SyntaxTree(
    "stmt",
Exemplo n.º 8
0
def customize_for_version(self, is_pypy, version):
    if is_pypy:
        ########################
        # PyPy changes
        #######################
        TABLE_DIRECT.update({
            'assert_pypy': ('%|assert %c\n', (1, 'assert_expr')),
            # This is as a result of an if transoration
            'assert0_pypy': ('%|assert %c\n', (0, 'assert_expr')),
            'assert_not_pypy': ('%|assert not %c\n', (1, 'assert_exp')),
            'assert2_not_pypy':
            ('%|assert not %c, %c\n', (1, 'assert_exp'), (4, 'expr')),
            'assert2_pypy':
            ('%|assert %c, %c\n', (1, 'assert_expr'), (4, 'expr')),
            'try_except_pypy': ('%|try:\n%+%c%-%c\n\n', 1, 2),
            'tryfinallystmt_pypy':
            ('%|try:\n%+%c%-%|finally:\n%+%c%-\n\n', 1, 3),
            'assign3_pypy': ('%|%c, %c, %c = %c, %c, %c\n', 5, 4, 3, 0, 1, 2),
            'assign2_pypy': ('%|%c, %c = %c, %c\n', 3, 2, 0, 1),
        })
    else:
        ########################
        # Without PyPy
        #######################
        TABLE_DIRECT.update({
            # "assert" and "assert_expr" are added via transform rules.
            "assert": ("%|assert %c\n", 0),
            "assert2": ("%|assert %c, %c\n", 0, 3),

            # Created only via transformation
            "assertnot": ("%|assert not %p\n", (0, PRECEDENCE['unary_not'])),
            "assert2not":
            ("%|assert not %p, %c\n", (0, PRECEDENCE['unary_not']), 3),
            "assign2": ("%|%c, %c = %c, %c\n", 3, 4, 0, 1),
            "assign3": ("%|%c, %c, %c = %c, %c, %c\n", 5, 6, 7, 0, 1, 2),
            "try_except": ("%|try:\n%+%c%-%c\n\n", 1, 3),
        })
    if version >= 3.0:
        if version >= 3.2:
            TABLE_DIRECT.update({
                "del_deref_stmt": ("%|del %c\n", 0),
                "DELETE_DEREF": ("%{pattr}", 0)
            })
        from uncompyle6.semantics.customize3 import customize_for_version3

        customize_for_version3(self, version)
    else:  # < 3.0
        TABLE_DIRECT.update({
            "except_cond3": ("%|except %c, %c:\n", (1, "expr"), (-2, "store"))
        })
        if version <= 2.6:
            TABLE_DIRECT["testtrue_then"] = TABLE_DIRECT["testtrue"]

        if 2.4 <= version <= 2.6:
            TABLE_DIRECT.update({"comp_for": (" for %c in %c", 3, 1)})
        else:
            TABLE_DIRECT.update({"comp_for": (" for %c in %c%c", 2, 0, 3)})

        if version >= 2.5:
            from uncompyle6.semantics.customize25 import customize_for_version25

            customize_for_version25(self, version)

            if version >= 2.6:
                from uncompyle6.semantics.customize26_27 import (
                    customize_for_version26_27, )

                customize_for_version26_27(self, version)
                pass
        else:  # < 2.5
            global NAME_MODULE
            NAME_MODULE = SyntaxTree(
                "stmt",
                [
                    SyntaxTree(
                        "assign",
                        [
                            SyntaxTree(
                                "expr",
                                [
                                    Token(
                                        "LOAD_GLOBAL",
                                        pattr="__name__",
                                        offset=0,
                                        has_arg=True,
                                    )
                                ],
                            ),
                            SyntaxTree(
                                "store",
                                [
                                    Token(
                                        "STORE_NAME",
                                        pattr="__module__",
                                        offset=3,
                                        has_arg=True,
                                    )
                                ],
                            ),
                        ],
                    )
                ],
            )
            TABLE_DIRECT.update({
                "importmultiple": ("%|import %c%c\n", 2, 3),
                "import_cont": (", %c", 2),
                "tryfinallystmt": (
                    "%|try:\n%+%c%-%|finally:\n%+%c%-",
                    (1, "suite_stmts_opt"),
                    (5, "suite_stmts_opt"),
                ),
            })
            if version == 2.4:

                def n_iftrue_stmt24(node):
                    self.template_engine(("%c", 0), node)
                    self.default(node)
                    self.prune()

                self.n_iftrue_stmt24 = n_iftrue_stmt24
            else:  # version <= 2.3:
                TABLE_DIRECT.update({"if1_stmt": ("%|if 1\n%+%c%-", 5)})
                if version <= 2.1:
                    TABLE_DIRECT.update({
                        "importmultiple": ("%c", 2),
                        # FIXME: not quite right. We have indiividual imports
                        # when there is in fact one: "import a, b, ..."
                        "imports_cont": ("%C%,", (1, 100, "\n")),
                    })
                    pass
                pass
            pass  # < 2.5

        # < 3.0 continues

        TABLE_R.update({
            "STORE_SLICE+0": ("%c[:]", 0),
            "STORE_SLICE+1": ("%c[%p:]", 0, (1, -1)),
            "STORE_SLICE+2": ("%c[:%p]", 0, (1, -1)),
            "STORE_SLICE+3": ("%c[%p:%p]", 0, (1, -1), (2, -1)),
            "DELETE_SLICE+0": ("%|del %c[:]\n", 0),
            "DELETE_SLICE+1": ("%|del %c[%c:]\n", 0, 1),
            "DELETE_SLICE+2": ("%|del %c[:%c]\n", 0, 1),
            "DELETE_SLICE+3": ("%|del %c[%c:%c]\n", 0, 1, 2),
        })
        TABLE_DIRECT.update({"raise_stmt2": ("%|raise %c, %c\n", 0, 1)})

        # exec as a built-in statement is only in Python 2.x
        def n_exec_stmt(node):
            """
            exec_stmt ::= expr exprlist DUP_TOP EXEC_STMT
            exec_stmt ::= expr exprlist EXEC_STMT
            """
            self.write(self.indent, "exec ")
            self.preorder(node[0])
            if not node[1][0].isNone():
                sep = " in "
                for subnode in node[1]:
                    self.write(sep)
                    sep = ", "
                    self.preorder(subnode)
            self.println()
            self.prune()  # stop recursing

        self.n_exec_smt = n_exec_stmt

        pass  # < 3.0

    return
Exemplo n.º 9
0
    'dict_comp':              0,
    'generator_exp':          0,  # (expressions...)
    'list':                   0,  # [expressions...]
    'list_comp':              0,
    'set_comp':               0,
    'set_comp_expr':          0,
    'unary_convert':          0,
}

LINE_LENGTH = 80

# Some parse trees created below are used for comparing code
# fragments (like 'return None' at the end of functions).

RETURN_LOCALS = SyntaxTree('return',
                    [ SyntaxTree('ret_expr', [SyntaxTree('expr', [ Token('LOAD_LOCALS') ])]),
                      Token('RETURN_VALUE')])

NONE = SyntaxTree('expr', [ NoneToken ] )

RETURN_NONE = SyntaxTree('stmt',
                  [ SyntaxTree('return',
                        [ NONE, Token('RETURN_VALUE')]) ])

PASS = SyntaxTree('stmts',
           [ SyntaxTree('sstmt',
                 [ SyntaxTree('stmt',
                       [ SyntaxTree('pass', [])])])])

ASSIGN_DOC_STRING = lambda doc_string, doc_load: \
  SyntaxTree('stmt',
Exemplo n.º 10
0
    def n_ifstmt(self, node):
        """Here we check if we can turn an `ifstmt` or 'iflaststmtl` into
           some kind of `assert` statement"""

        testexpr = node[0]

        if testexpr.kind != "testexpr":
            return node
        if node.kind in ("ifstmt", "ifstmtl"):
            ifstmts_jump = node[1]

            if ifstmts_jump == "_ifstmts_jumpl" and ifstmts_jump[0] == "_ifstmts_jump":
                ifstmts_jump = ifstmts_jump[0]
            elif ifstmts_jump not in ("_ifstmts_jump", "ifstmts_jumpl"):
                return node
            stmts = ifstmts_jump[0]
        else:
            # iflaststmtl works this way
            stmts = node[1]

        if stmts in ("c_stmts",) and len(stmts) == 1:
            stmt = stmts[0]
            raise_stmt = stmt[0]
            if (
                raise_stmt == "raise_stmt1"
                and len(testexpr[0]) == 2
                and raise_stmt.first_child().pattr == "AssertionError"
            ):
                assert_expr = testexpr[0][0]
                assert_expr.kind = "assert_expr"
                jump_cond = testexpr[0][1]
                expr = raise_stmt[0]
                RAISE_VARARGS_1 = raise_stmt[1]
                call = expr[0]
                if call == "call":
                    # ifstmt
                    #     0. testexpr
                    #         testtrue (2)
                    #             0. expr
                    #     1. _ifstmts_jump (2)
                    #         0. c_stmts
                    #             stmt
                    #                 raise_stmt1 (2)
                    #                     0. expr
                    #                         call (3)
                    #                     1. RAISE_VARARGS_1
                    # becomes:
                    # assert2 ::= assert_expr jmp_true LOAD_ASSERT expr RAISE_VARARGS_1 COME_FROM
                    if jump_cond == "jmp_true":
                        kind = "assert2"
                    else:
                        assert jump_cond == "jmp_false"
                        kind = "assert2not"

                    LOAD_ASSERT = call[0].first_child()
                    if LOAD_ASSERT != "LOAD_ASSERT":
                        return node
                    if isinstance(call[1], SyntaxTree):
                        expr = call[1][0]
                        node = SyntaxTree(
                            kind,
                            [assert_expr, jump_cond, LOAD_ASSERT, expr, RAISE_VARARGS_1]
                        )
                        pass
                    pass
                else:
                    # ifstmt
                    #   0. testexpr (2)
                    #      testtrue
                    #       0. expr
                    #   1. _ifstmts_jump (2)
                    #      0. c_stmts
                    #        stmts
                    #           raise_stmt1 (2)
                    #             0. expr
                    #                  LOAD_ASSERT
                    #             1.   RAISE_VARARGS_1
                    # becomes:
                    # assert ::= assert_expr jmp_true LOAD_ASSERT RAISE_VARARGS_1 COME_FROM
                    if jump_cond == "jmp_true":
                        if self.is_pypy:
                            kind = "assert0_pypy"
                        else:
                            kind = "assert"
                    else:
                        assert jump_cond == "jmp_false"
                        kind = "assertnot"

                    LOAD_ASSERT = expr[0]
                    node = SyntaxTree(
                        kind,
                        [assert_expr, jump_cond, LOAD_ASSERT, RAISE_VARARGS_1]
                    )
                node.transformed_by="n_ifstmt",
                pass
            pass
        return node
Exemplo n.º 11
0
    def n_ifelsestmt(self, node, preprocess=False):
        """
        Here we turn:

          if ...
          else
             if ..

        into:

          if ..
          elif ...

          [else ...]

        where appropriate
        """
        else_suite = node[3]

        n = else_suite[0]
        old_stmts = None
        else_suite_index = 1

        if len(n) == 1 == len(n[0]) and n[0] == "stmt":
            n = n[0][0]
        elif n[0].kind in ("lastc_stmt", "lastl_stmt"):
            n = n[0]
            if n[0].kind in (
                "ifstmt",
                "iflaststmt",
                "iflaststmtl",
                "ifelsestmtl",
                "ifelsestmtc",
                "ifpoplaststmtl",
            ):
                n = n[0]
                if n.kind == "ifpoplaststmtl":
                    old_stmts = n[2]
                    else_suite_index = 2
                pass
            pass
        elif len(n) > 1 and 1 == len(n[0]) and n[0] == "stmt" and n[1].kind == "stmt":
            else_suite_stmts = n[0]
            if else_suite_stmts[0].kind not in ("ifstmt", "iflaststmt", "ifelsestmtl"):
                return node
            old_stmts = n
            n = else_suite_stmts[0]
        else:
            return node

        if n.kind in ("ifstmt", "iflaststmt", "iflaststmtl", "ifpoplaststmtl"):
            node.kind = "ifelifstmt"
            n.kind = "elifstmt"
        elif n.kind in ("ifelsestmtr",):
            node.kind = "ifelifstmt"
            n.kind = "elifelsestmtr"
        elif n.kind in ("ifelsestmt", "ifelsestmtc", "ifelsestmtl"):
            node.kind = "ifelifstmt"
            self.n_ifelsestmt(n, preprocess=True)
            if n == "ifelifstmt":
                n.kind = "elifelifstmt"
            elif n.kind in ("ifelsestmt", "ifelsestmtc", "ifelsestmtl"):
                n.kind = "elifelsestmt"
        if not preprocess:
            if old_stmts:
                if n.kind == "elifstmt":
                    trailing_else = SyntaxTree("stmts", old_stmts[1:])
                    if len(trailing_else):
                        # We use elifelsestmtr because it has 3 nodes
                        elifelse_stmt = SyntaxTree(
                            "elifelsestmtr", [n[0], n[else_suite_index], trailing_else]
                        )
                        node[3] = elifelse_stmt
                    else:
                        elif_stmt = SyntaxTree("elifstmt", [n[0], n[else_suite_index]])
                        node[3] = elif_stmt

                    node.transformed_by = "n_ifelsestmt"
                    pass
                else:
                    # Other cases for n.kind may happen here
                    pass
                pass
            return node
Exemplo n.º 12
0
    def n_ifstmt(self, node):
        """Here we check if we can turn an `ifstmt` or 'iflaststmtl` into
           some kind of `assert` statement"""

        testexpr = node[0]

        if testexpr.kind != "testexpr":
            return node
        if node.kind == "ifstmt":
            ifstmts_jump = node[1]
            if node[1] != "_ifstmts_jump":
                return node
            stmts = ifstmts_jump[0]
        else:
            # iflaststmtl works this way
            stmts = node[1]

        if stmts in ("c_stmts", ) and len(stmts) == 1:
            stmt = stmts[0]
            raise_stmt = stmt[0]
            if raise_stmt == "raise_stmt1" and len(testexpr[0]) == 2:
                assert_expr = testexpr[0][0]
                assert_expr.kind = "assert_expr"
                jump_cond = testexpr[0][1]
                expr = raise_stmt[0]
                RAISE_VARARGS_1 = raise_stmt[1]
                if expr[0] == "call":
                    # ifstmt
                    #     0. testexpr
                    #         testtrue (2)
                    #             0. expr
                    #     1. _ifstmts_jump (2)
                    #         0. c_stmts
                    #             stmt
                    #                 raise_stmt1 (2)
                    #                     0. expr
                    #                         call (3)
                    #                     1. RAISE_VARARGS_1
                    # becomes:
                    # assert2 ::= assert_expr jmp_true LOAD_ASSERT expr RAISE_VARARGS_1 COME_FROM
                    if jump_cond == "jmp_true":
                        kind = "assert2"
                    else:
                        assert jump_cond == "jmp_false"
                        kind = "assert2not"

                    call = expr[0]
                    LOAD_ASSERT = call[0]
                    expr = call[1][0]
                    node = SyntaxTree(kind, [
                        assert_expr, jump_cond, LOAD_ASSERT, expr,
                        RAISE_VARARGS_1
                    ])
                else:
                    # ifstmt
                    #   0. testexpr (2)
                    #      testtrue
                    #       0. expr
                    #   1. _ifstmts_jump (2)
                    #      0. c_stmts
                    #        stmts
                    #           raise_stmt1 (2)
                    #             0. expr
                    #                  LOAD_ASSERT
                    #             1.   RAISE_VARARGS_1
                    # becomes:
                    # assert ::= assert_expr jmp_true LOAD_ASSERT RAISE_VARARGS_1 COME_FROM
                    if jump_cond == "jmp_true":
                        kind = "assert"
                    else:
                        assert jump_cond == "jmp_false"
                        kind = "assertnot"

                    LOAD_ASSERT = expr[0]
                    node = SyntaxTree(
                        kind,
                        [assert_expr, jump_cond, LOAD_ASSERT, RAISE_VARARGS_1])
                node.transformed_by = "n_ifstmt",
                pass
            pass
        return node
Exemplo n.º 13
0
    def n_ifstmt(self, node):
        """Here we check if we can turn an `ifstmt` or 'iflaststmtl` into
           some kind of `assert` statement"""

        testexpr = node[0]

        if testexpr != "testexpr":
            return node

        if node.kind in ("ifstmt", "ifstmtl"):
            ifstmts_jump = node[1]

            if ifstmts_jump == "_ifstmts_jumpl" and ifstmts_jump[
                    0] == "_ifstmts_jump":
                ifstmts_jump = ifstmts_jump[0]
            elif ifstmts_jump not in ("_ifstmts_jump", "ifstmts_jumpl"):
                return node
            stmts = ifstmts_jump[0]
        else:
            # iflaststmtl works this way
            stmts = node[1]

        if stmts in ("c_stmts", ) and len(stmts) == 1:
            stmt = stmts[0]
            raise_stmt = stmt[0]
            testtrue_or_false = testexpr[0]
            if (raise_stmt == "raise_stmt1"
                    and 1 <= len(testtrue_or_false) <= 2
                    and raise_stmt.first_child().pattr == "AssertionError"):
                if testtrue_or_false == "testtrue":
                    # Skip over the testtrue because because it would
                    # produce a "not" and we don't want that here.
                    assert_expr = testtrue_or_false[0]
                    jump_cond = NoneToken
                else:
                    assert_expr = testtrue_or_false[0]
                    jump_cond = testtrue_or_false[1]
                    assert_expr.kind = "assert_expr"
                expr = raise_stmt[0]
                RAISE_VARARGS_1 = raise_stmt[1]
                call = expr[0]
                if call == "call":
                    # ifstmt
                    #     0. testexpr
                    #         testtrue (2)
                    #             0. expr
                    #     1. _ifstmts_jump (2)
                    #         0. c_stmts
                    #             stmt
                    #                 raise_stmt1 (2)
                    #                     0. expr
                    #                         call (3)
                    #                     1. RAISE_VARARGS_1
                    # becomes:
                    # assert2 ::= assert_expr jmp_true LOAD_ASSERT expr RAISE_VARARGS_1 COME_FROM
                    if jump_cond in ("jmp_true", NoneToken):
                        kind = "assert2"
                    else:
                        if jump_cond == "jmp_false":
                            # FIXME: We don't handle this kind of thing yet.
                            return node
                        kind = "assert2not"

                    LOAD_ASSERT = call[0].first_child()
                    if LOAD_ASSERT != "LOAD_ASSERT":
                        return node
                    if isinstance(call[1], SyntaxTree):
                        expr = call[1][0]
                        node = SyntaxTree(
                            kind,
                            [
                                assert_expr,
                                jump_cond,
                                LOAD_ASSERT,
                                expr,
                                RAISE_VARARGS_1,
                            ],
                        )
                        node.transformed_by = "n_ifstmt"
                        pass
                    pass
                else:
                    # ifstmt
                    #   0. testexpr (2)
                    #      testtrue
                    #       0. expr
                    #   1. _ifstmts_jump (2)
                    #      0. c_stmts
                    #        stmts
                    #           raise_stmt1 (2)
                    #             0. expr
                    #                  LOAD_ASSERT
                    #             1.   RAISE_VARARGS_1
                    # becomes:
                    # assert ::= assert_expr jmp_true LOAD_ASSERT RAISE_VARARGS_1 COME_FROM
                    if jump_cond in ("jmp_true", NoneToken):
                        if self.is_pypy:
                            kind = "assert0_pypy"
                        else:
                            kind = "assert"
                    else:
                        assert jump_cond == "jmp_false"
                        kind = "assertnot"

                    LOAD_ASSERT = expr[0]
                    node = SyntaxTree(
                        kind,
                        [assert_expr, jump_cond, LOAD_ASSERT, RAISE_VARARGS_1])
                node.transformed_by = ("n_ifstmt", )
                pass
            pass
        return node
Exemplo n.º 14
0
def customize_for_version(self, is_pypy, version):
    if is_pypy:
        ########################
        # PyPy changes
        #######################
        TABLE_DIRECT.update({
            'assert_pypy':	( '%|assert %c\n' , 1 ),
            'assert2_pypy':	( '%|assert %c, %c\n' , 1, 4 ),
            'try_except_pypy':	   ( '%|try:\n%+%c%-%c\n\n', 1, 2 ),
            'tryfinallystmt_pypy': ( '%|try:\n%+%c%-%|finally:\n%+%c%-\n\n', 1, 3 ),
            'assign3_pypy':        ( '%|%c, %c, %c = %c, %c, %c\n', 5, 4, 3, 0, 1, 2 ),
            'assign2_pypy':        ( '%|%c, %c = %c, %c\n', 3, 2, 0, 1),
            })
    else:
        ########################
        # Without PyPy
        #######################
        TABLE_DIRECT.update({
            'assert':		( '%|assert %c\n' , 0 ),
            'assert2':		( '%|assert %c, %c\n' , 0, 3 ),
            'try_except':	( '%|try:\n%+%c%-%c\n\n', 1, 3 ),
            'assign2':          ( '%|%c, %c = %c, %c\n',
                                  3, 4, 0, 1 ),
            'assign3':          ( '%|%c, %c, %c = %c, %c, %c\n',
                                  5, 6, 7, 0, 1, 2 ),
            })
    if version < 3.0:
        if version == 2.4:
            def n_iftrue_stmt24(node):
                self.template_engine(('%|%c', 0), node)
                self.default(node)
                self.prune()
            self.n_iftrue_stmt24 = n_iftrue_stmt24

        TABLE_R.update({
            'STORE_SLICE+0':	( '%c[:]', 0 ),
            'STORE_SLICE+1':	( '%c[%p:]', 0, (1, -1) ),
            'STORE_SLICE+2':	( '%c[:%p]', 0, (1, -1) ),
            'STORE_SLICE+3':	( '%c[%p:%p]', 0, (1, -1), (2, -1) ),
            'DELETE_SLICE+0':	( '%|del %c[:]\n', 0 ),
            'DELETE_SLICE+1':	( '%|del %c[%c:]\n', 0, 1 ),
            'DELETE_SLICE+2':	( '%|del %c[:%c]\n', 0, 1 ),
            'DELETE_SLICE+3':	( '%|del %c[%c:%c]\n', 0, 1, 2 ),
        })
        TABLE_DIRECT.update({
            'raise_stmt2':	( '%|raise %c, %c\n', 0, 1),
        })

        # exec as a built-in statement is only in Python 2.x
        def n_exec_stmt(node):
            """
            exec_stmt ::= expr exprlist DUP_TOP EXEC_STMT
            exec_stmt ::= expr exprlist EXEC_STMT
            """
            self.write(self.indent, 'exec ')
            self.preorder(node[0])
            if not node[1][0].isNone():
                sep = ' in '
                for subnode in node[1]:
                    self.write(sep); sep = ", "
                    self.preorder(subnode)
            self.println()
            self.prune() # stop recursing
        self.n_exec_smt = n_exec_stmt

    else:
        TABLE_DIRECT.update({
            # Gotta love Python for its futzing around with syntax like this
            'raise_stmt2':	 ( '%|raise %c from %c\n', 0, 1),
        })

        if version >= 3.2:
            TABLE_DIRECT.update({
            'del_deref_stmt': ( '%|del %c\n', 0),
            'DELETE_DEREF': ( '%{pattr}', 0 ),
            })

    if version <= 2.4:
        TABLE_DIRECT.update({
            'importmultiple': ( '%|import %c%c\n', 2, 3),
            'import_cont'   : ( ', %c', 2),
            'tryfinallystmt': ( '%|try:\n%+%c%-%|finally:\n%+%c%-',
                                (1, 'suite_stmts_opt') ,
                                (5, 'suite_stmts_opt') )
            })
        if version == 2.3:
            TABLE_DIRECT.update({
                'if1_stmt':	( '%|if 1\n%+%c%-', 5 )
            })

        global NAME_MODULE
        NAME_MODULE = SyntaxTree('stmt',
                          [ SyntaxTree('assign',
                                [ SyntaxTree('expr',
                                      [Token('LOAD_GLOBAL', pattr='__name__',
                                             offset=0, has_arg=True)]),
                                  SyntaxTree('store',
                                      [ Token('STORE_NAME', pattr='__module__',
                                              offset=3, has_arg=True)])
                                ])])
        pass
        if version <= 2.3:
            if version <= 2.1:
                TABLE_DIRECT.update({
                    'importmultiple': ( '%c', 2 ),
                    # FIXME: not quite right. We have indiividual imports
                    # when there is in fact one: "import a, b, ..."
                    'imports_cont': ( '%C%,', (1, 100, '\n') ),
                })
                pass
            pass
        pass
    elif version >= 2.5:
        ########################
        # Import style for 2.5+
        ########################
        TABLE_DIRECT.update({
            'importmultiple': ( '%|import %c%c\n', 2, 3 ),
            'import_cont'   : ( ', %c', 2 ),
            # With/as is allowed as "from future" thing in 2.5
            # Note: It is safe to put the variables after "as" in parenthesis,
            # and sometimes it is needed.
            'withstmt':     ( '%|with %c:\n%+%c%-', 0, 3),
            'withasstmt':   ( '%|with %c as (%c):\n%+%c%-', 0, 2, 3),
        })

        # In 2.5+ "except" handlers and the "finally" can appear in one
        # "try" statement. So the below has the effect of combining the
        # "tryfinally" with statement with the "try_except" statement
        def tryfinallystmt(node):
            if len(node[1][0]) == 1 and node[1][0][0] == 'stmt':
                if node[1][0][0][0] == 'try_except':
                    node[1][0][0][0].kind = 'tf_try_except'
                if node[1][0][0][0] == 'tryelsestmt':
                    node[1][0][0][0].kind = 'tf_tryelsestmt'
            self.default(node)
        self.n_tryfinallystmt = tryfinallystmt

    ########################################
    # Python 2.6+
    #    except <condition> as <var>
    # vs. older:
    #    except <condition> , <var>
    #
    # For 2.6 we use the older syntax which
    # matches how we parse this in bytecode
    ########################################
    if version > 2.6:
        TABLE_DIRECT.update({
            'except_cond2':	( '%|except %c as %c:\n', 1, 5 ),
        })
    else:
        TABLE_DIRECT.update({
            'except_cond3':	 ( '%|except %c, %c:\n', 1, 6 ),
            'testtrue_then': ( 'not %p', (0, 22) ),

        })

    if 2.4 <= version <= 2.6:
        TABLE_DIRECT.update({
            'comp_for':	( ' for %c in %c', 3, 1 ),
        })
    else:
        TABLE_DIRECT.update({
            'comp_for':	( ' for %c in %c%c', 2, 0, 3 ),
        })

    if  version >= 3.0:
        from uncompyle6.semantics.customize3 import customize_for_version3
        customize_for_version3(self, version)
    return
Exemplo n.º 15
0
def customize_for_version(self, is_pypy, version):
    if is_pypy:
        ########################
        # PyPy changes
        #######################
        TABLE_DIRECT.update({
            'assert_pypy':	( '%|assert %c\n' , 1 ),
            'assert2_pypy':	( '%|assert %c, %c\n' , 1, 4 ),
            'try_except_pypy':	   ( '%|try:\n%+%c%-%c\n\n', 1, 2 ),
            'tryfinallystmt_pypy': ( '%|try:\n%+%c%-%|finally:\n%+%c%-\n\n', 1, 3 ),
            'assign3_pypy':        ( '%|%c, %c, %c = %c, %c, %c\n', 5, 4, 3, 0, 1, 2 ),
            'assign2_pypy':        ( '%|%c, %c = %c, %c\n', 3, 2, 0, 1),
            })
    else:
        ########################
        # Without PyPy
        #######################
        TABLE_DIRECT.update({
            'assert':		( '%|assert %c\n' , 0 ),
            'assert2':		( '%|assert %c, %c\n' , 0, 3 ),
            'try_except':	( '%|try:\n%+%c%-%c\n\n', 1, 3 ),
            'assign2':          ( '%|%c, %c = %c, %c\n',
                                  3, 4, 0, 1 ),
            'assign3':          ( '%|%c, %c, %c = %c, %c, %c\n',
                                  5, 6, 7, 0, 1, 2 ),
            })
    if  version >= 3.0:
        TABLE_DIRECT.update({
            # Gotta love Python for its futzing around with syntax like this
            'raise_stmt2':	 ( '%|raise %c from %c\n', 0, 1),
        })

        if version >= 3.2:
            TABLE_DIRECT.update({
            'del_deref_stmt': ( '%|del %c\n', 0),
            'DELETE_DEREF': ( '%{pattr}', 0 ),
            })
        from uncompyle6.semantics.customize3 import customize_for_version3
        customize_for_version3(self, version)
    else:  # < 3.0
        if 2.4 <= version <= 2.6:
            TABLE_DIRECT.update({
                'comp_for':	( ' for %c in %c', 3, 1 ),
            })
        else:
            TABLE_DIRECT.update({
                'comp_for':	( ' for %c in %c%c', 2, 0, 3 ),
            })

        if version >= 2.5:
            from uncompyle6.semantics.customize25 import customize_for_version25
            customize_for_version25(self, version)

            if version >= 2.6:
                from uncompyle6.semantics.customize26_27 import customize_for_version26_27
                customize_for_version26_27(self, version)
                pass
        else:  # < 2.5
            global NAME_MODULE
            NAME_MODULE = SyntaxTree('stmt',
                              [ SyntaxTree('assign',
                                    [ SyntaxTree('expr',
                                          [Token('LOAD_GLOBAL', pattr='__name__',
                                                 offset=0, has_arg=True)]),
                                      SyntaxTree('store',
                                          [ Token('STORE_NAME', pattr='__module__',
                                                  offset=3, has_arg=True)])
                                    ])])
            TABLE_DIRECT.update({
                'importmultiple': ( '%|import %c%c\n', 2, 3),
                'import_cont'   : ( ', %c', 2),
                'tryfinallystmt': ( '%|try:\n%+%c%-%|finally:\n%+%c%-',
                                    (1, 'suite_stmts_opt') ,
                                    (5, 'suite_stmts_opt') )
                })
            if version == 2.4:
                def n_iftrue_stmt24(node):
                    self.template_engine(('%c', 0), node)
                    self.default(node)
                    self.prune()
                self.n_iftrue_stmt24 = n_iftrue_stmt24
            else:  # version <= 2.3:
                TABLE_DIRECT.update({
                    'if1_stmt':	( '%|if 1\n%+%c%-', 5 )
                })
                if version <= 2.1:
                    TABLE_DIRECT.update({
                        'importmultiple': ( '%c', 2 ),
                        # FIXME: not quite right. We have indiividual imports
                        # when there is in fact one: "import a, b, ..."
                        'imports_cont': ( '%C%,', (1, 100, '\n') ),
                    })
                    pass
                pass
            pass # < 2.5

        # < 3.0 continues

        TABLE_R.update({
            'STORE_SLICE+0':	( '%c[:]', 0 ),
            'STORE_SLICE+1':	( '%c[%p:]', 0, (1, -1) ),
            'STORE_SLICE+2':	( '%c[:%p]', 0, (1, -1) ),
            'STORE_SLICE+3':	( '%c[%p:%p]', 0, (1, -1), (2, -1) ),
            'DELETE_SLICE+0':	( '%|del %c[:]\n', 0 ),
            'DELETE_SLICE+1':	( '%|del %c[%c:]\n', 0, 1 ),
            'DELETE_SLICE+2':	( '%|del %c[:%c]\n', 0, 1 ),
            'DELETE_SLICE+3':	( '%|del %c[%c:%c]\n', 0, 1, 2 ),
        })
        TABLE_DIRECT.update({
            'raise_stmt2':	( '%|raise %c, %c\n', 0, 1),
        })

        # exec as a built-in statement is only in Python 2.x
        def n_exec_stmt(node):
            """
            exec_stmt ::= expr exprlist DUP_TOP EXEC_STMT
            exec_stmt ::= expr exprlist EXEC_STMT
            """
            self.write(self.indent, 'exec ')
            self.preorder(node[0])
            if not node[1][0].isNone():
                sep = ' in '
                for subnode in node[1]:
                    self.write(sep); sep = ", "
                    self.preorder(subnode)
            self.println()
            self.prune() # stop recursing
        self.n_exec_smt = n_exec_stmt

        pass # < 3.0

    return