diff options
author | Damien George <damien.p.george@gmail.com> | 2015-08-14 12:24:11 +0100 |
---|---|---|
committer | Damien George <damien.p.george@gmail.com> | 2015-08-17 12:51:26 +0100 |
commit | 65dc960e3b22a8426e369607e47c19b380ce30ea (patch) | |
tree | 5e55ec2861df54e14fdb0eac1d030b34f684743b /py | |
parent | 0e978349a5e7696aa44a0faf5d046081a0616ca5 (diff) | |
download | micropython-65dc960e3b22a8426e369607e47c19b380ce30ea.tar.gz micropython-65dc960e3b22a8426e369607e47c19b380ce30ea.zip |
unix-cpy: Remove unix-cpy. It's no longer needed.
unix-cpy was originally written to get semantic equivalent with CPython
without writing functional tests. When writing the initial
implementation of uPy it was a long way between lexer and functional
tests, so the half-way test was to make sure that the bytecode was
correct. The idea was that if the uPy bytecode matched CPython 1-1 then
uPy would be proper Python if the bytecodes acted correctly. And having
matching bytecode meant that it was less likely to miss some deep
subtlety in the Python semantics that would require an architectural
change later on.
But that is all history and it no longer makes sense to retain the
ability to output CPython bytecode, because:
1. It outputs CPython 3.3 compatible bytecode. CPython's bytecode
changes from version to version, and seems to have changed quite a bit
in 3.5. There's no point in changing the bytecode output to match
CPython anymore.
2. uPy and CPy do different optimisations to the bytecode which makes it
harder to match.
3. The bytecode tests are not run. They were never part of Travis and
are not run locally anymore.
4. The EMIT_CPYTHON option needs a lot of extra source code which adds
heaps of noise, especially in compile.c.
5. Now that there is an extensive test suite (which tests functionality)
there is no need to match the bytecode. Some very subtle behaviour is
tested with the test suite and passing these tests is a much better
way to stay Python-language compliant, rather than trying to match
CPy bytecode.
Diffstat (limited to 'py')
-rw-r--r-- | py/compile.c | 420 | ||||
-rw-r--r-- | py/emit.h | 8 | ||||
-rw-r--r-- | py/emitbc.c | 4 | ||||
-rw-r--r-- | py/emitcommon.c | 28 | ||||
-rw-r--r-- | py/emitcpy.c | 901 | ||||
-rw-r--r-- | py/mkrules.mk | 2 | ||||
-rw-r--r-- | py/mpconfig.h | 6 | ||||
-rw-r--r-- | py/parse.c | 4 | ||||
-rw-r--r-- | py/py.mk | 1 | ||||
-rw-r--r-- | py/scope.c | 56 | ||||
-rw-r--r-- | py/scope.h | 1 |
11 files changed, 26 insertions, 1405 deletions
diff --git a/py/compile.c b/py/compile.c index a124203e4b..b7ec070299 100644 --- a/py/compile.c +++ b/py/compile.c @@ -49,7 +49,7 @@ typedef enum { PN_const_object, // special node for a constant, generic Python object } pn_kind_t; -#define NEED_METHOD_TABLE (MICROPY_EMIT_CPYTHON || MICROPY_EMIT_NATIVE) +#define NEED_METHOD_TABLE MICROPY_EMIT_NATIVE #if NEED_METHOD_TABLE @@ -323,23 +323,6 @@ STATIC mp_parse_node_t fold_constants(compiler_t *comp, mp_parse_node_t pn, mp_m case PN_power: if (0) { -#if MICROPY_EMIT_CPYTHON - } else if (MP_PARSE_NODE_IS_SMALL_INT(pns->nodes[0]) && MP_PARSE_NODE_IS_NULL(pns->nodes[1]) && !MP_PARSE_NODE_IS_NULL(pns->nodes[2])) { - // int ** x - // can overflow; enabled only to compare with CPython - mp_parse_node_struct_t *pns2 = (mp_parse_node_struct_t*)pns->nodes[2]; - if (MP_PARSE_NODE_IS_SMALL_INT(pns2->nodes[0])) { - int power = MP_PARSE_NODE_LEAF_SMALL_INT(pns2->nodes[0]); - if (power >= 0) { - int ans = 1; - int base = MP_PARSE_NODE_LEAF_SMALL_INT(pns->nodes[0]); - for (; power > 0; power--) { - ans *= base; - } - pn = mp_parse_node_new_leaf(MP_PARSE_NODE_SMALL_INT, ans); - } - } -#endif #if MICROPY_COMP_MODULE_CONST } else if (MP_PARSE_NODE_IS_ID(pns->nodes[0]) && MP_PARSE_NODE_IS_STRUCT_KIND(pns->nodes[1], PN_trailer_period) && MP_PARSE_NODE_IS_NULL(pns->nodes[2])) { // id.id @@ -464,163 +447,7 @@ STATIC void compile_delete_id(compiler_t *comp, qstr qst) { } } -#if MICROPY_EMIT_CPYTHON -STATIC bool cpython_c_tuple_is_const(mp_parse_node_t pn) { - if (MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_string)) { - return true; - } - if (MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_bytes)) { - return true; - } - if (MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_const_object)) { - return true; - } - if (!MP_PARSE_NODE_IS_LEAF(pn)) { - return false; - } - if (MP_PARSE_NODE_IS_ID(pn)) { - return false; - } - return true; -} - -STATIC void cpython_c_print_quoted_str(vstr_t *vstr, const char *str, uint len, bool bytes) { - bool has_single_quote = false; - bool has_double_quote = false; - for (int i = 0; i < len; i++) { - if (str[i] == '\'') { - has_single_quote = true; - } else if (str[i] == '"') { - has_double_quote = true; - } - } - if (bytes) { - vstr_printf(vstr, "b"); - } - bool quote_single = false; - if (has_single_quote && !has_double_quote) { - vstr_printf(vstr, "\""); - } else { - quote_single = true; - vstr_printf(vstr, "'"); - } - for (int i = 0; i < len; i++) { - if (str[i] == '\n') { - vstr_printf(vstr, "\\n"); - } else if (str[i] == '\\') { - vstr_printf(vstr, "\\\\"); - } else if (str[i] == '\'' && quote_single) { - vstr_printf(vstr, "\\'"); - } else { - vstr_printf(vstr, "%c", str[i]); - } - } - if (has_single_quote && !has_double_quote) { - vstr_printf(vstr, "\""); - } else { - vstr_printf(vstr, "'"); - } -} - -STATIC void cpython_c_tuple_emit_const(compiler_t *comp, mp_parse_node_t pn, vstr_t *vstr) { - if (MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_string) || MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_bytes)) { - mp_parse_node_struct_t *pns = (mp_parse_node_struct_t*)pn; - cpython_c_print_quoted_str(vstr, (const char*)pns->nodes[0], (mp_uint_t)pns->nodes[1], MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_bytes)); - return; - } - - if (MP_PARSE_NODE_IS_STRUCT_KIND(pn, PN_const_object)) { - mp_parse_node_struct_t *pns = (mp_parse_node_struct_t*)pn; - mp_obj_print((mp_obj_t)pns->nodes[0], PRINT_REPR); - return; - } - - assert(MP_PARSE_NODE_IS_LEAF(pn)); - if (MP_PARSE_NODE_IS_SMALL_INT(pn)) { - vstr_printf(vstr, INT_FMT, MP_PARSE_NODE_LEAF_SMALL_INT(pn)); - return; - } - - mp_uint_t arg = MP_PARSE_NODE_LEAF_ARG(pn); - switch (MP_PARSE_NODE_LEAF_KIND(pn)) { - case MP_PARSE_NODE_ID: assert(0); - case MP_PARSE_NODE_STRING: - case MP_PARSE_NODE_BYTES: { - mp_uint_t len; - const byte *str = qstr_data(arg, &len); - cpython_c_print_quoted_str(vstr, (const char*)str, len, MP_PARSE_NODE_LEAF_KIND(pn) == MP_PARSE_NODE_BYTES); - break; - } - case MP_PARSE_NODE_TOKEN: - switch (arg) { - case MP_TOKEN_KW_FALSE: vstr_printf(vstr, "False"); break; - case MP_TOKEN_KW_NONE: vstr_printf(vstr, "None"); break; - case MP_TOKEN_KW_TRUE: vstr_printf(vstr, "True"); break; - default: assert(0); // shouldn't happen - } - break; - default: assert(0); - } -} - -STATIC void cpython_c_tuple(compiler_t *comp, mp_parse_node_t pn, mp_parse_node_struct_t *pns_list) { - int n = 0; - if (pns_list != NULL) { - n = MP_PARSE_NODE_STRUCT_NUM_NODES(pns_list); - } - int total = n; - bool is_const = true; - if (!MP_PARSE_NODE_IS_NULL(pn)) { - total += 1; - if (!cpython_c_tuple_is_const(pn)) { - is_const = false; - } - } - for (int i = 0; i < n; i++) { - if (!cpython_c_tuple_is_const(pns_list->nodes[i])) { - is_const = false; - break; - } - } - if (total > 0 && is_const) { - bool need_comma = false; - vstr_t *vstr = vstr_new(); - vstr_printf(vstr, "("); - if (!MP_PARSE_NODE_IS_NULL(pn)) { - cpython_c_tuple_emit_const(comp, pn, vstr); - need_comma = true; - } - for (int i = 0; i < n; i++) { - if (need_comma) { - vstr_printf(vstr, ", "); - } - cpython_c_tuple_emit_const(comp, pns_list->nodes[i], vstr); - need_comma = true; - } - if (total == 1) { - vstr_printf(vstr, ",)"); - } else { - vstr_printf(vstr, ")"); - } - EMIT_ARG(load_const_verbatim_strn, vstr_str(vstr), vstr_len(vstr)); - vstr_free(vstr); - } else { - if (!MP_PARSE_NODE_IS_NULL(pn)) { - compile_node(comp, pn); - } - for (int i = 0; i < n; i++) { - compile_node(comp, pns_list->nodes[i]); - } - EMIT_ARG(build_tuple, total); - } -} -#endif - -// funnelling all tuple creations through this function is purely so we can optionally agree with CPython STATIC void c_tuple(compiler_t *comp, mp_parse_node_t pn, mp_parse_node_struct_t *pns_list) { -#if MICROPY_EMIT_CPYTHON - cpython_c_tuple(comp, pn, pns_list); -#else int total = 0; if (!MP_PARSE_NODE_IS_NULL(pn)) { compile_node(comp, pn); @@ -634,7 +461,6 @@ STATIC void c_tuple(compiler_t *comp, mp_parse_node_t pn, mp_parse_node_struct_t total += n; } EMIT_ARG(build_tuple, total); -#endif } STATIC void compile_generic_tuple(compiler_t *comp, mp_parse_node_struct_t *pns) { @@ -652,66 +478,7 @@ STATIC bool node_is_const_true(mp_parse_node_t pn) { || (MP_PARSE_NODE_IS_SMALL_INT(pn) && MP_PARSE_NODE_LEAF_SMALL_INT(pn) != 0); } -#if MICROPY_EMIT_CPYTHON -// the is_nested variable is purely to match with CPython, which doesn't fully optimise not's -STATIC void cpython_c_if_cond(compiler_t *comp, mp_parse_node_t pn, bool jump_if, int label, bool is_nested) { - if (node_is_const_false(pn)) { - if (jump_if == false) { - EMIT_ARG(jump, label); - } - return; - } else if (node_is_const_true(pn)) { - if (jump_if == true) { - EMIT_ARG(jump, label); - } - return; - } else if (MP_PARSE_NODE_IS_STRUCT(pn)) { - mp_parse_node_struct_t *pns = (mp_parse_node_struct_t*)pn; - int n = MP_PARSE_NODE_STRUCT_NUM_NODES(pns); - if (MP_PARSE_NODE_STRUCT_KIND(pns) == PN_or_test) { - if (jump_if == false) { - uint label2 = comp_next_label(comp); - for (int i = 0; i < n - 1; i++) { - cpython_c_if_cond(comp, pns->nodes[i], true, label2, true); - } - cpython_c_if_cond(comp, pns->nodes[n - 1], false, label, true); - EMIT_ARG(label_assign, label2); - } else { - for (int i = 0; i < n; i++) { - cpython_c_if_cond(comp, pns->nodes[i], true, label, true); - } - } - return; - } else if (MP_PARSE_NODE_STRUCT_KIND(pns) == PN_and_test) { - if (jump_if == false) { - for (int i = 0; i < n; i++) { - cpython_c_if_cond(comp, pns->nodes[i], false, label, true); - } - } else { - uint label2 = comp_next_label(comp); - for (int i = 0; i < n - 1; i++) { - cpython_c_if_cond(comp, pns->nodes[i], false, label2, true); - } - cpython_c_if_cond(comp, pns->nodes[n - 1], true, label, true); - EMIT_ARG(label_assign, label2); - } - return; - } else if (!is_nested && MP_PARSE_NODE_STRUCT_KIND(pns) == PN_not_test_2) { - cpython_c_if_cond(comp, pns->nodes[0], !jump_if, label, true); - return; - } - } - - // nothing special, fall back to default compiling for node and jump - compile_node(comp, pn); - EMIT_ARG(pop_jump_if, jump_if, label); -} -#endif - STATIC void c_if_cond(compiler_t *comp, mp_parse_node_t pn, bool jump_if, int label) { -#if MICROPY_EMIT_CPYTHON - cpython_c_if_cond(comp, pn, jump_if, label, false); -#else if (node_is_const_false(pn)) { if (jump_if == false) { EMIT_ARG(jump, label); @@ -773,7 +540,6 @@ STATIC void c_if_cond(compiler_t *comp, mp_parse_node_t pn, bool jump_if, int la // nothing special, fall back to default compiling for node and jump compile_node(comp, pn); EMIT_ARG(pop_jump_if, jump_if, label); -#endif } typedef enum { ASSIGN_STORE, ASSIGN_AUG_LOAD, ASSIGN_AUG_STORE } assign_kind_t; @@ -992,8 +758,7 @@ STATIC void c_assign(compiler_t *comp, mp_parse_node_t pn, assign_kind_t assign_ compile_syntax_error(comp, pn, "illegal expression for augmented assignment"); } -// stuff for lambda and comprehensions and generators -// if we are not in CPython compatibility mode then: +// stuff for lambda and comprehensions and generators: // if n_pos_defaults > 0 then there is a tuple on the stack with the positional defaults // if n_kw_defaults > 0 then there is a dictionary on the stack with the keyword defaults // if both exist, the tuple is above the dictionary (ie the first pop gets the tuple) @@ -1011,12 +776,8 @@ STATIC void close_over_variables_etc(compiler_t *comp, scope_t *this_scope, int for (int j = 0; j < this_scope->id_info_len; j++) { id_info_t *id2 = &this_scope->id_info[j]; if (id2->kind == ID_INFO_KIND_FREE && id->qst == id2->qst) { -#if MICROPY_EMIT_CPYTHON - EMIT_ARG(load_closure, id->qst, id->local_num); -#else // in Micro Python we load closures using LOAD_FAST EMIT_LOAD_FAST(id->qst, id->local_num); -#endif nfree += 1; } } @@ -1085,10 +846,6 @@ STATIC void compile_funcdef_param(compiler_t *comp, mp_parse_node_t pn) { if (comp->have_star) { comp->num_dict_params += 1; -#if MICROPY_EMIT_CPYTHON - EMIT_ARG(load_const_str, MP_PARSE_NODE_LEAF_ARG(pn_id)); - compile_node(comp, pn_equal); -#else // in Micro Python we put the default dict parameters into a dictionary using the bytecode if (comp->num_dict_params == 1) { // in Micro Python we put the default positional parameters into a tuple using the bytecode @@ -1106,7 +863,6 @@ STATIC void compile_funcdef_param(compiler_t *comp, mp_parse_node_t pn) { compile_node(comp, pn_equal); EMIT_ARG(load_const_str, MP_PARSE_NODE_LEAF_ARG(pn_id)); EMIT(store_map); -#endif } else { comp->num_default_params += 1; compile_node(comp, pn_equal); @@ -1143,14 +899,12 @@ STATIC qstr compile_funcdef_helper(compiler_t *comp, mp_parse_node_struct_t *pns return MP_QSTR_NULL; } -#if !MICROPY_EMIT_CPYTHON // in Micro Python we put the default positional parameters into a tuple using the bytecode // the default keywords args may have already made the tuple; if not, do it now if (comp->num_default_params > 0 && comp->num_dict_params == 0) { EMIT_ARG(build_tuple, comp->num_default_params); EMIT(load_null); // sentinel indicating empty default keyword args } -#endif // get the scope for this function scope_t *fscope = (scope_t*)pns->nodes[4]; @@ -1558,12 +1312,8 @@ STATIC void compile_import_from(compiler_t *comp, mp_parse_node_struct_t *pns) { EMIT_ARG(load_const_small_int, import_level); // build the "fromlist" tuple -#if MICROPY_EMIT_CPYTHON - EMIT_ARG(load_const_verbatim_strn, "('*',)", 6); -#else EMIT_ARG(load_const_str, MP_QSTR__star_); EMIT_ARG(build_tuple, 1); -#endif // do the import qstr dummy_q; @@ -1576,31 +1326,6 @@ STATIC void compile_import_from(compiler_t *comp, mp_parse_node_struct_t *pns) { // build the "fromlist" tuple mp_parse_node_t *pn_nodes; int n = mp_parse_node_extract_list(&pns->nodes[1], PN_import_as_names, &pn_nodes); -#if MICROPY_EMIT_CPYTHON - { - vstr_t *vstr = vstr_new(); - vstr_printf(vstr, "("); - for (int i = 0; i < n; i++) { - assert(MP_PARSE_NODE_IS_STRUCT_KIND(pn_nodes[i], PN_import_as_name)); - mp_parse_node_struct_t *pns3 = (mp_parse_node_struct_t*)pn_nodes[i]; - qstr id2 = MP_PARSE_NODE_LEAF_ARG(pns3->nodes[0]); // should be id - if (i > 0) { - vstr_printf(vstr, ", "); - } - vstr_printf(vstr, "'"); - mp_uint_t len; - const byte *str = qstr_data(id2, &len); - vstr_add_strn(vstr, (const char*)str, len); - vstr_printf(vstr, "'"); - } - if (n == 1) { - vstr_printf(vstr, ","); - } - vstr_printf(vstr, ")"); - EMIT_ARG(load_const_verbatim_strn, vstr_str(vstr), vstr_len(vstr)); - vstr_free(vstr); - } -#else for (int i = 0; i < n; i++) { assert(MP_PARSE_NODE_IS_STRUCT_KIND(pn_nodes[i], PN_import_as_name)); mp_parse_node_struct_t *pns3 = (mp_parse_node_struct_t*)pn_nodes[i]; @@ -1608,7 +1333,6 @@ STATIC void compile_import_from(compiler_t *comp, mp_parse_node_struct_t *pns) { EMIT_ARG(load_const_str, id2); } EMIT_ARG(build_tuple, n); -#endif // do the import qstr dummy_q; @@ -1704,21 +1428,21 @@ STATIC void compile_if_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { uint l_end = comp_next_label(comp); - // optimisation: don't emit anything when "if False" (not in CPython) - if (MICROPY_EMIT_CPYTHON || !node_is_const_false(pns->nodes[0])) { + // optimisation: don't emit anything when "if False" + if (!node_is_const_false(pns->nodes[0])) { uint l_fail = comp_next_label(comp); c_if_cond(comp, pns->nodes[0], false, l_fail); // if condition compile_node(comp, pns->nodes[1]); // if block - // optimisation: skip everything else when "if True" (not in CPython) - if (!MICROPY_EMIT_CPYTHON && node_is_const_true(pns->nodes[0])) { + // optimisation: skip everything else when "if True" + if (node_is_const_true(pns->nodes[0])) { goto done; } if ( - // optimisation: don't jump over non-existent elif/else blocks (not in CPython) - (MICROPY_EMIT_CPYTHON || !(MP_PARSE_NODE_IS_NULL(pns->nodes[2]) && MP_PARSE_NODE_IS_NULL(pns->nodes[3]))) + // optimisation: don't jump over non-existent elif/else blocks + !(MP_PARSE_NODE_IS_NULL(pns->nodes[2]) && MP_PARSE_NODE_IS_NULL(pns->nodes[3])) // optimisation: don't jump if last instruction was return && !EMIT(last_emit_was_return_value) ) { @@ -1736,15 +1460,15 @@ STATIC void compile_if_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { assert(MP_PARSE_NODE_IS_STRUCT_KIND(pn_elif[i], PN_if_stmt_elif)); // should be mp_parse_node_struct_t *pns_elif = (mp_parse_node_struct_t*)pn_elif[i]; - // optimisation: don't emit anything when "if False" (not in CPython) - if (MICROPY_EMIT_CPYTHON || !node_is_const_false(pns_elif->nodes[0])) { + // optimisation: don't emit anything when "if False" + if (!node_is_const_false(pns_elif->nodes[0])) { uint l_fail = comp_next_label(comp); c_if_cond(comp, pns_elif->nodes[0], false, l_fail); // elif condition compile_node(comp, pns_elif->nodes[1]); // elif block - // optimisation: skip everything else when "elif True" (not in CPython) - if (!MICROPY_EMIT_CPYTHON && node_is_const_true(pns_elif->nodes[0])) { + // optimisation: skip everything else when "elif True" + if (node_is_const_true(pns_elif->nodes[0])) { goto done; } @@ -1781,23 +1505,6 @@ done: STATIC void compile_while_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { START_BREAK_CONTINUE_BLOCK - // compared to CPython, we have an optimised version of while loops -#if MICROPY_EMIT_CPYTHON - uint done_label = comp_next_label(comp); - EMIT_ARG(setup_loop, break_label); - EMIT_ARG(label_assign, continue_label); - c_if_cond(comp, pns->nodes[0], false, done_label); // condition - compile_node(comp, pns->nodes[1]); // body - if (!EMIT(last_emit_was_return_value)) { - EMIT_ARG(jump, continue_label); - } - EMIT_ARG(label_assign, done_label); - // CPython does not emit POP_BLOCK if the condition was a constant; don't undertand why - // this is a small hack to agree with CPython - if (!node_is_const_true(pns->nodes[0])) { - EMIT(pop_block); - } -#else if (!node_is_const_false(pns->nodes[0])) { // optimisation: don't emit anything for "while False" uint top_label = comp_next_label(comp); if (!node_is_const_true(pns->nodes[0])) { // optimisation: don't jump to cond for "while True" @@ -1808,7 +1515,6 @@ STATIC void compile_while_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { EMIT_ARG(label_assign, continue_label); c_if_cond(comp, pns->nodes[0], true, top_label); // condition } -#endif // break/continue apply to outer loop (if any) in the else block END_BREAK_CONTINUE_BLOCK @@ -1818,7 +1524,6 @@ STATIC void compile_while_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { EMIT_ARG(label_assign, break_label); } -#if !MICROPY_EMIT_CPYTHON // This function compiles an optimised for-loop of the form: // for <var> in range(<start>, <end>, <step>): // <body> @@ -1899,10 +1604,8 @@ STATIC void compile_for_stmt_optimised_range(compiler_t *comp, mp_parse_node_t p EMIT(pop_top); } } -#endif STATIC void compile_for_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { -#if !MICROPY_EMIT_CPYTHON // this bit optimises: for <x> in range(...), turning it into an explicitly incremented variable // this is actually slower, but uses no heap memory // for viper it will be much, much faster @@ -1945,7 +1648,6 @@ STATIC void compile_for_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { } } } -#endif START_BREAK_CONTINUE_BLOCK comp->break_label |= MP_EMIT_BREAK_FROM_FOR; @@ -1953,11 +1655,6 @@ STATIC void compile_for_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { uint pop_label = comp_next_label(comp); uint end_label = comp_next_label(comp); - // I don't think our implementation needs SETUP_LOOP/POP_BLOCK for for-statements -#if MICROPY_EMIT_CPYTHON - EMIT_ARG(setup_loop, end_label); -#endif - compile_node(comp, pns->nodes[1]); // iterator EMIT(get_iter); EMIT_ARG(label_assign, continue_label); @@ -1973,10 +1670,6 @@ STATIC void compile_for_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { // break/continue apply to outer loop (if any) in the else block END_BREAK_CONTINUE_BLOCK -#if MICROPY_EMIT_CPYTHON - EMIT(pop_block); -#endif - compile_node(comp, pns->nodes[3]); // else (not tested) EMIT_ARG(label_assign, break_label); @@ -2233,7 +1926,7 @@ STATIC void compile_expr_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { && MP_PARSE_NODE_IS_STRUCT_KIND(pns->nodes[0], PN_testlist_star_expr) && MP_PARSE_NODE_STRUCT_NUM_NODES((mp_parse_node_struct_t*)pns1->nodes[0]) == 2 && MP_PARSE_NODE_STRUCT_NUM_NODES((mp_parse_node_struct_t*)pns->nodes[0]) == 2) { - // optimisation for a, b = c, d; to match CPython's optimisation + // optimisation for a, b = c, d mp_parse_node_struct_t *pns10 = (mp_parse_node_struct_t*)pns1->nodes[0]; mp_parse_node_struct_t *pns0 = (mp_parse_node_struct_t*)pns->nodes[0]; if (MP_PARSE_NODE_IS_STRUCT_KIND(pns0->nodes[0], PN_star_expr) @@ -2251,7 +1944,7 @@ STATIC void compile_expr_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { && MP_PARSE_NODE_IS_STRUCT_KIND(pns->nodes[0], PN_testlist_star_expr) && MP_PARSE_NODE_STRUCT_NUM_NODES((mp_parse_node_struct_t*)pns1->nodes[0]) == 3 && MP_PARSE_NODE_STRUCT_NUM_NODES((mp_parse_node_struct_t*)pns->nodes[0]) == 3) { - // optimisation for a, b, c = d, e, f; to match CPython's optimisation + // optimisation for a, b, c = d, e, f mp_parse_node_struct_t *pns10 = (mp_parse_node_struct_t*)pns1->nodes[0]; mp_parse_node_struct_t *pns0 = (mp_parse_node_struct_t*)pns->nodes[0]; if (MP_PARSE_NODE_IS_STRUCT_KIND(pns0->nodes[0], PN_star_expr) @@ -2485,7 +2178,6 @@ STATIC void compile_power(compiler_t *comp, mp_parse_node_struct_t *pns) { STATIC void compile_trailer_paren_helper(compiler_t *comp, mp_parse_node_t pn_arglist, bool is_method_call, int n_positional_extra) { // function to call is on top of stack -#if !MICROPY_EMIT_CPYTHON // this is to handle special super() call if (MP_PARSE_NODE_IS_NULL(pn_arglist) && comp->func_arg_is_super && comp->scope_cur->kind == SCOPE_FUNCTION) { compile_load_id(comp, MP_QSTR___class__); @@ -2501,7 +2193,6 @@ STATIC void compile_trailer_paren_helper(compiler_t *comp, mp_parse_node_t pn_ar compile_syntax_error(comp, MP_PARSE_NODE_NULL, "super() call cannot find self"); // really a TypeError return; } -#endif // get the list of arguments mp_parse_node_t *args; @@ -3184,7 +2875,7 @@ STATIC void compile_scope_comp_iter(compiler_t *comp, mp_parse_node_t pn_iter, m } STATIC void check_for_doc_string(compiler_t *comp, mp_parse_node_t pn) { -#if MICROPY_EMIT_CPYTHON || MICROPY_ENABLE_DOC_STRING +#if MICROPY_ENABLE_DOC_STRING // see http://www.python.org/dev/peps/pep-0257/ // look for the first statement @@ -3240,12 +2931,6 @@ STATIC void compile_scope(compiler_t *comp, scope_t *scope, pass_kind_t pass) { scope->exc_stack_size = 0; } -#if MICROPY_EMIT_CPYTHON - if (comp->pass == MP_PASS_EMIT) { - scope_print_info(scope); - } -#endif - // compile if (MP_PARSE_NODE_IS_STRUCT_KIND(scope->pn, PN_eval_input)) { assert(scope->kind == SCOPE_MODULE); @@ -3331,11 +3016,7 @@ STATIC void compile_scope(compiler_t *comp, scope_t *scope, pass_kind_t pass) { // CPython uses .0, but we should be able to use anything that won't // clash with a user defined variable. Best to use an existing qstr, // so we use the blank qstr. -#if MICROPY_EMIT_CPYTHON - qstr qstr_arg = QSTR_FROM_STR_STATIC(".0"); -#else qstr qstr_arg = MP_QSTR_; -#endif if (comp->pass == MP_PASS_SCOPE) { bool added; id_info_t *id_info = scope_find_or_add_id(comp->scope_cur, qstr_arg, &added); @@ -3395,11 +3076,7 @@ STATIC void compile_scope(compiler_t *comp, scope_t *scope, pass_kind_t pass) { if (id->kind == ID_INFO_KIND_LOCAL) { EMIT_ARG(load_const_tok, MP_TOKEN_KW_NONE); } else { -#if MICROPY_EMIT_CPYTHON - EMIT_ARG(load_closure, MP_QSTR___class__, 0); // XXX check this is the correct local num -#else EMIT_LOAD_FAST(MP_QSTR___class__, id->local_num); -#endif } EMIT(return_value); } @@ -3547,7 +3224,6 @@ STATIC void compile_scope_inline_asm(compiler_t *comp, scope_t *scope, pass_kind #endif STATIC void scope_compute_things(scope_t *scope) { -#if !MICROPY_EMIT_CPYTHON // in Micro Python we put the *x parameter after all other parameters (except **y) if (scope->scope_flags & MP_SCOPE_FLAG_VARARGS) { id_info_t *id_param = NULL; @@ -3564,7 +3240,6 @@ STATIC void scope_compute_things(scope_t *scope) { } } } -#endif // in functions, turn implicit globals into explicit globals // compute the index of each local @@ -3584,19 +3259,9 @@ STATIC void scope_compute_things(scope_t *scope) { } } - // compute the index of cell vars (freevars[idx] in CPython) -#if MICROPY_EMIT_CPYTHON - int num_cell = 0; -#endif + // compute the index of cell vars for (int i = 0; i < scope->id_info_len; i++) { id_info_t *id = &scope->id_info[i]; -#if MICROPY_EMIT_CPYTHON - // in CPython the cells are numbered starting from 0 - if (id->kind == ID_INFO_KIND_CELL) { - id->local_num = num_cell; - num_cell += 1; - } -#else // in Micro Python the cells come right after the fast locals // parameters are not counted here, since they remain at the start // of the locals, even if they are cell vars @@ -3604,10 +3269,9 @@ STATIC void scope_compute_things(scope_t *scope) { id->local_num = scope->num_locals; scope->num_locals += 1; } -#endif } - // compute the index of free vars (freevars[idx] in CPython) + // compute the index of free vars // make sure they are in the order of the parent scope if (scope->parent != NULL) { int num_free = 0; @@ -3618,19 +3282,13 @@ STATIC void scope_compute_things(scope_t *scope) { id_info_t *id2 = &scope->id_info[j]; if (id2->kind == ID_INFO_KIND_FREE && id->qst == id2->qst) { assert(!(id2->flags & ID_FLAG_IS_PARAM)); // free vars should not be params -#if MICROPY_EMIT_CPYTHON - // in CPython the frees are numbered after the cells - id2->local_num = num_cell + num_free; -#else // in Micro Python the frees come first, before the params id2->local_num = num_free; -#endif num_free += 1; } } } } -#if !MICROPY_EMIT_CPYTHON // in Micro Python shift all other locals after the free locals if (num_free > 0) { for (int i = 0; i < scope->id_info_len; i++) { @@ -3642,23 +3300,9 @@ STATIC void scope_compute_things(scope_t *scope) { scope->num_pos_args += num_free; // free vars are counted as params for passing them into the function scope->num_locals += num_free; } -#endif } // compute scope_flags - -#if MICROPY_EMIT_CPYTHON - // these flags computed here are for CPython compatibility only - if (scope->kind == SCOPE_FUNCTION || scope->kind == SCOPE_LAMBDA || scope->kind == SCOPE_LIST_COMP || scope->kind == SCOPE_DICT_COMP || scope->kind == SCOPE_SET_COMP || scope->kind == SCOPE_GEN_EXPR) { - assert(scope->parent != NULL); - scope->scope_flags |= MP_SCOPE_FLAG_NEWLOCALS; - scope->scope_flags |= MP_SCOPE_FLAG_OPTIMISED; - if ((SCOPE_FUNCTION <= scope->parent->kind && scope->parent->kind <= SCOPE_SET_COMP) || (scope->parent->kind == SCOPE_CLASS && scope->parent->parent->kind == SCOPE_FUNCTION)) { - scope->scope_flags |= MP_SCOPE_FLAG_NESTED; - } - } -#endif - int num_free = 0; for (int i = 0; i < scope->id_info_len; i++) { id_info_t *id = &scope->id_info[i]; @@ -3688,22 +3332,13 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is mp_map_deinit(&consts); // create standard emitter; it's used at least for MP_PASS_SCOPE - #if MICROPY_EMIT_CPYTHON - emit_t *emit_cpython = emit_cpython_new(); - #else emit_t *emit_bc = emit_bc_new(); - #endif // compile pass 1 - #if MICROPY_EMIT_CPYTHON - comp->emit = emit_cpython; - comp->emit_method_table = &emit_cpython_method_table; - #else comp->emit = emit_bc; #if MICROPY_EMIT_NATIVE comp->emit_method_table = &emit_bc_method_table; #endif - #endif #if MICROPY_EMIT_INLINE_THUMB comp->emit_inline_asm = NULL; comp->emit_inline_asm_method_table = NULL; @@ -3731,21 +3366,15 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is } // set max number of labels now that it's calculated - #if MICROPY_EMIT_CPYTHON - emit_cpython_set_max_num_labels(emit_cpython, max_num_labels); - #else emit_bc_set_max_num_labels(emit_bc, max_num_labels); - #endif // compile pass 2 and 3 -#if !MICROPY_EMIT_CPYTHON #if MICROPY_EMIT_NATIVE emit_t *emit_native = NULL; #endif #if MICROPY_EMIT_INLINE_THUMB emit_inline_asm_t *emit_inline_thumb = NULL; #endif -#endif // !MICROPY_EMIT_CPYTHON for (scope_t *s = comp->scope_head; s != NULL && comp->compile_error == MP_OBJ_NULL; s = s->next) { if (false) { // dummy @@ -3770,10 +3399,6 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is // choose the emit type -#if MICROPY_EMIT_CPYTHON - comp->emit = emit_cpython; - comp->emit_method_table = &emit_cpython_method_table; -#else switch (s->emit_options) { #if MICROPY_EMIT_NATIVE @@ -3812,7 +3437,6 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is #endif break; } -#endif // !MICROPY_EMIT_CPYTHON // need a pass to compute stack size compile_scope(comp, s, MP_PASS_STACK_SIZE); @@ -3840,9 +3464,6 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is // free the emitters -#if MICROPY_EMIT_CPYTHON - emit_cpython_free(emit_cpython); -#else emit_bc_free(emit_bc); #if MICROPY_EMIT_NATIVE if (emit_native != NULL) { @@ -3862,7 +3483,6 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is emit_inline_thumb_free(emit_inline_thumb); } #endif -#endif // MICROPY_EMIT_CPYTHON // free the parse tree mp_parse_node_free(module_scope->pn); @@ -3882,13 +3502,7 @@ mp_obj_t mp_compile(mp_parse_node_t pn, qstr source_file, uint emit_opt, bool is if (compile_error != MP_OBJ_NULL) { nlr_raise(compile_error); } else { -#if MICROPY_EMIT_CPYTHON - // can't create code, so just return true - (void)outer_raw_code; // to suppress warning that outer_raw_code is unused - return mp_const_true; -#else // return function that executes the outer module return mp_make_function_from_raw_code(outer_raw_code, MP_OBJ_NULL, MP_OBJ_NULL); -#endif } } @@ -145,14 +145,6 @@ typedef struct _emit_method_table_t { // they may or may not emit code void (*start_except_handler)(emit_t *emit); void (*end_except_handler)(emit_t *emit); - -#if MICROPY_EMIT_CPYTHON - // these methods are only needed for emitcpy - void (*load_const_verbatim_strn)(emit_t *emit, const char *str, mp_uint_t len); - void (*load_closure)(emit_t *emit, qstr qst, mp_uint_t local_num); - void (*setup_loop)(emit_t *emit, mp_uint_t label); -#endif - } emit_method_table_t; void mp_emit_common_get_id_for_load(scope_t *scope, qstr qst); diff --git a/py/emitbc.c b/py/emitbc.c index fef9054c75..11e65f62e3 100644 --- a/py/emitbc.c +++ b/py/emitbc.c @@ -34,8 +34,6 @@ #include "py/emit.h" #include "py/bc0.h" -#if !MICROPY_EMIT_CPYTHON - #define BYTES_FOR_INT ((BYTES_PER_WORD * 8 + 6) / 7) #define DUMMY_DATA_SIZE (BYTES_FOR_INT) @@ -1030,5 +1028,3 @@ const mp_emit_method_table_id_ops_t mp_emit_bc_method_table_delete_id_ops = { mp_emit_bc_delete_global, }; #endif - -#endif // !MICROPY_EMIT_CPYTHON diff --git a/py/emitcommon.c b/py/emitcommon.c index 7eda5e05fd..1fd2bd1dc1 100644 --- a/py/emitcommon.c +++ b/py/emitcommon.c @@ -33,28 +33,12 @@ void mp_emit_common_get_id_for_load(scope_t *scope, qstr qst) { bool added; id_info_t *id = scope_find_or_add_id(scope, qst, &added); if (added) { -#if MICROPY_EMIT_CPYTHON - if (qst == MP_QSTR_super && scope->kind == SCOPE_FUNCTION) { - // special case, super is a global, and also counts as use of __class__ - id->kind = ID_INFO_KIND_GLOBAL_EXPLICIT; - id_info_t *id2 = scope_find_local_in_parent(scope, MP_QSTR___class__); - if (id2 != NULL) { - id2 = scope_find_or_add_id(scope, MP_QSTR___class__, &added); - if (added) { - id2->kind = ID_INFO_KIND_FREE; - scope_close_over_in_parents(scope, MP_QSTR___class__); - } - } - } else -#endif - { - id_info_t *id2 = scope_find_local_in_parent(scope, qst); - if (id2 != NULL && (id2->kind == ID_INFO_KIND_LOCAL || id2->kind == ID_INFO_KIND_CELL || id2->kind == ID_INFO_KIND_FREE)) { - id->kind = ID_INFO_KIND_FREE; - scope_close_over_in_parents(scope, qst); - } else { - id->kind = ID_INFO_KIND_GLOBAL_IMPLICIT; - } + id_info_t *id2 = scope_find_local_in_parent(scope, qst); + if (id2 != NULL && (id2->kind == ID_INFO_KIND_LOCAL || id2->kind == ID_INFO_KIND_CELL || id2->kind == ID_INFO_KIND_FREE)) { + id->kind = ID_INFO_KIND_FREE; + scope_close_over_in_parents(scope, qst); + } else { + id->kind = ID_INFO_KIND_GLOBAL_IMPLICIT; } } } diff --git a/py/emitcpy.c b/py/emitcpy.c deleted file mode 100644 index 3bdec1716d..0000000000 --- a/py/emitcpy.c +++ /dev/null @@ -1,901 +0,0 @@ -/* - * This file is part of the Micro Python project, http://micropython.org/ - * - * The MIT License (MIT) - * - * Copyright (c) 2013, 2014 Damien P. George - * - * Permission is hereby granted, free of charge, to any person obtaining a copy - * of this software and associated documentation files (the "Software"), to deal - * in the Software without restriction, including without limitation the rights - * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell - * copies of the Software, and to permit persons to whom the Software is - * furnished to do so, subject to the following conditions: - * - * The above copyright notice and this permission notice shall be included in - * all copies or substantial portions of the Software. - * - * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR - * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, - * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE - * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER - * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, - * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN - * THE SOFTWARE. - */ - -#include <stdbool.h> -#include <stdint.h> -#include <stdio.h> -#include <string.h> -#include <assert.h> - -#include "py/emit.h" - -// wrapper around everything in this file -#if MICROPY_EMIT_CPYTHON - -struct _emit_t { - int pass; - int bytecode_offset; - int stack_size; - bool last_emit_was_return_value; - - scope_t *scope; - - mp_uint_t max_num_labels; - mp_uint_t *label_offsets; -}; - -emit_t *emit_cpython_new(void) { - emit_t *emit = m_new0(emit_t, 1); - return emit; -} - -void emit_cpython_set_max_num_labels(emit_t* emit, mp_uint_t max_num_labels) { - emit->max_num_labels = max_num_labels; - emit->label_offsets = m_new(mp_uint_t, max_num_labels); -} - -void emit_cpython_free(emit_t *emit) { - m_del(mp_uint_t, emit->label_offsets, emit->max_num_labels); - m_del_obj(emit_t, emit); -} - -STATIC void emit_cpy_set_native_type(emit_t *emit, mp_uint_t op, mp_uint_t arg1, qstr arg2) { -} - -STATIC void emit_cpy_start_pass(emit_t *emit, pass_kind_t pass, scope_t *scope) { - emit->pass = pass; - emit->bytecode_offset = 0; - emit->stack_size = 0; - emit->last_emit_was_return_value = false; - emit->scope = scope; - if (pass < MP_PASS_EMIT) { - memset(emit->label_offsets, -1, emit->max_num_labels * sizeof(mp_uint_t)); - } -} - -STATIC void emit_cpy_end_pass(emit_t *emit) { - if (emit->pass == MP_PASS_SCOPE) { - return; - } - // check stack is back to zero size - if (emit->stack_size != 0) { - printf("ERROR: stack size not back to zero; got %d\n", emit->stack_size); - } -} - -STATIC bool emit_cpy_last_emit_was_return_value(emit_t *emit) { - return emit->last_emit_was_return_value; -} - -STATIC void emit_cpy_adjust_stack_size(emit_t *emit, mp_int_t delta) { - emit->stack_size += delta; -} - -STATIC void emit_cpy_set_source_line(emit_t *emit, mp_uint_t source_line) { -} - -// TODO: module-polymorphic function (read: name clash if made global) -static void emit_pre(emit_t *emit, int stack_size_delta, int bytecode_size) { - if (emit->pass == MP_PASS_SCOPE) { - return; - } - emit->stack_size += stack_size_delta; - if (emit->stack_size > emit->scope->stack_size) { - emit->scope->stack_size = emit->stack_size; - } - emit->last_emit_was_return_value = false; - if (emit->pass == MP_PASS_EMIT && bytecode_size > 0) { - if (emit->bytecode_offset >= 1000) { - printf("%d ", emit->bytecode_offset); - } else { - printf("% 4d ", emit->bytecode_offset); - } - } - emit->bytecode_offset += bytecode_size; -} - -STATIC void emit_cpy_label_assign(emit_t *emit, mp_uint_t l) { - emit_pre(emit, 0, 0); - if (emit->pass == MP_PASS_SCOPE) { - return; - } - assert(l < emit->max_num_labels); - if (emit->pass < MP_PASS_EMIT) { - // assign label offset - assert(emit->label_offsets[l] == -1); - emit->label_offsets[l] = emit->bytecode_offset; - } else { - // ensure label offset has not changed from MP_PASS_CODE_SIZE to MP_PASS_EMIT - assert(emit->label_offsets[l] == emit->bytecode_offset); - //printf("l%d: (at %d)\n", l, emit->bytecode_offset); - } -} - -STATIC void emit_cpy_import_name(emit_t *emit, qstr qst) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("IMPORT_NAME %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_import_from(emit_t *emit, qstr qst) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("IMPORT_FROM %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_import_star(emit_t *emit) { - emit_pre(emit, -1, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("IMPORT_STAR\n"); - } -} - -STATIC void emit_cpy_load_const_tok(emit_t *emit, mp_token_kind_t tok) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST "); - switch (tok) { - case MP_TOKEN_KW_FALSE: printf("False"); break; - case MP_TOKEN_KW_NONE: printf("None"); break; - case MP_TOKEN_KW_TRUE: printf("True"); break; - default: printf("?=%d\n", tok); return; assert(0); - } - printf("\n"); - } -} - -STATIC void emit_cpy_load_const_small_int(emit_t *emit, mp_int_t arg) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST " INT_FMT "\n", arg); - } -} - -STATIC void print_quoted_str(qstr qst) { - const char *str = qstr_str(qst); - int len = strlen(str); - bool has_single_quote = false; - bool has_double_quote = false; - for (int i = 0; i < len; i++) { - if (str[i] == '\'') { - has_single_quote = true; - } else if (str[i] == '"') { - has_double_quote = true; - } - } - int quote_char = '\''; - if (has_single_quote && !has_double_quote) { - quote_char = '"'; - } - printf("%c", quote_char); - for (const char *s = str, *top = str + len; s < top; s++) { - if (*s == quote_char) { - printf("\\%c", quote_char); - } else if (*s == '\\') { - printf("\\\\"); - } else if (32 <= *s && *s <= 126) { - printf("%c", *s); - } else if (*s == '\n') { - printf("\\n"); - // TODO add more escape codes here - } else { - printf("\\x%02x", (*s) & 0xff); - } - } - printf("%c", quote_char); -} - -STATIC void emit_cpy_load_const_str(emit_t *emit, qstr qst) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST "); - print_quoted_str(qst); - printf("\n"); - } -} - -STATIC void emit_cpy_load_const_obj(emit_t *emit, void *obj) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST "); - mp_obj_print(obj, PRINT_REPR); - printf("\n"); - } -} - -STATIC void emit_cpy_load_null(emit_t *emit) { - // unused for cpy - assert(0); -} - -STATIC void emit_cpy_load_fast(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_FAST " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_load_deref(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_DEREF " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_load_name(emit_t *emit, qstr qst) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_NAME %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_load_global(emit_t *emit, qstr qst) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_GLOBAL %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_load_attr(emit_t *emit, qstr qst) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_ATTR %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_load_method(emit_t *emit, qstr qst) { - emit_cpy_load_attr(emit, qst); -} - -STATIC void emit_cpy_load_build_class(emit_t *emit) { - emit_pre(emit, 1, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_BUILD_CLASS\n"); - } -} - -STATIC void emit_cpy_load_subscr(emit_t *emit) { - emit_pre(emit, -1, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("BINARY_SUBSCR\n"); - } -} - -STATIC void emit_cpy_store_fast(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_FAST " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_store_deref(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_DEREF " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_store_name(emit_t *emit, qstr qst) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_NAME %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_store_global(emit_t *emit, qstr qst) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_GLOBAL %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_store_attr(emit_t *emit, qstr qst) { - emit_pre(emit, -2, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_ATTR %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_store_subscr(emit_t *emit) { - emit_pre(emit, -3, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_SUBSCR\n"); - } -} - -STATIC void emit_cpy_delete_fast(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("DELETE_FAST " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_delete_deref(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("DELETE_DEREF " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_delete_name(emit_t *emit, qstr qst) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("DELETE_NAME %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_delete_global(emit_t *emit, qstr qst) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("DELETE_GLOBAL %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_delete_attr(emit_t *emit, qstr qst) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("DELETE_ATTR %s\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_delete_subscr(emit_t *emit) { - emit_pre(emit, -2, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("DELETE_SUBSCR\n"); - } -} - -STATIC void emit_cpy_dup_top(emit_t *emit) { - emit_pre(emit, 1, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("DUP_TOP\n"); - } -} - -STATIC void emit_cpy_dup_top_two(emit_t *emit) { - emit_pre(emit, 2, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("DUP_TOP_TWO\n"); - } -} - -STATIC void emit_cpy_pop_top(emit_t *emit) { - emit_pre(emit, -1, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("POP_TOP\n"); - } -} - -STATIC void emit_cpy_rot_two(emit_t *emit) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("ROT_TWO\n"); - } -} - -STATIC void emit_cpy_rot_three(emit_t *emit) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("ROT_THREE\n"); - } -} - -STATIC void emit_cpy_jump(emit_t *emit, mp_uint_t label) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - int dest = emit->label_offsets[label]; - if (dest < emit->bytecode_offset) { - printf("JUMP_ABSOLUTE " UINT_FMT "\n", emit->label_offsets[label]); - } else { - printf("JUMP_FORWARD " UINT_FMT "\n", emit->label_offsets[label]); - } - } -} - -STATIC void emit_cpy_pop_jump_if(emit_t *emit, bool cond, mp_uint_t label) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - if (cond) { - printf("POP_JUMP_IF_TRUE " UINT_FMT "\n", emit->label_offsets[label]); - } else { - printf("POP_JUMP_IF_FALSE " UINT_FMT "\n", emit->label_offsets[label]); - } - } -} - -STATIC void emit_cpy_jump_if_or_pop(emit_t *emit, bool cond, mp_uint_t label) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - if (cond) { - printf("JUMP_IF_TRUE_OR_POP " UINT_FMT "\n", emit->label_offsets[label]); - } else { - printf("JUMP_IF_FALSE_OR_POP " UINT_FMT "\n", emit->label_offsets[label]); - } - } -} - -STATIC void emit_cpy_break_loop(emit_t *emit, mp_uint_t label, mp_uint_t except_depth) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("BREAK_LOOP\n"); - } -} - -STATIC void emit_cpy_continue_loop(emit_t *emit, mp_uint_t label, mp_uint_t except_depth) { - if (except_depth == 0) { - emit_cpy_jump(emit, label); - } else { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("CONTINUE_LOOP " UINT_FMT "\n", emit->label_offsets[label]); - } - } -} - -STATIC void emit_cpy_setup_with(emit_t *emit, mp_uint_t label) { - emit_pre(emit, 7, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("SETUP_WITH " UINT_FMT "\n", emit->label_offsets[label]); - } -} - -STATIC void emit_cpy_with_cleanup(emit_t *emit) { - emit_pre(emit, -7, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("WITH_CLEANUP\n"); - } -} - -STATIC void emit_cpy_setup_except(emit_t *emit, mp_uint_t label) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("SETUP_EXCEPT " UINT_FMT "\n", emit->label_offsets[label]); - } -} - -STATIC void emit_cpy_setup_finally(emit_t *emit, mp_uint_t label) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("SETUP_FINALLY " UINT_FMT "\n", emit->label_offsets[label]); - } -} - -STATIC void emit_cpy_end_finally(emit_t *emit) { - emit_pre(emit, -1, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("END_FINALLY\n"); - } -} - -STATIC void emit_cpy_get_iter(emit_t *emit) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("GET_ITER\n"); - } -} - -STATIC void emit_cpy_for_iter(emit_t *emit, mp_uint_t label) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("FOR_ITER " UINT_FMT "\n", emit->label_offsets[label]); - } -} - -STATIC void emit_cpy_for_iter_end(emit_t *emit) { - emit_pre(emit, -1, 0); -} - -STATIC void emit_cpy_pop_block(emit_t *emit) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("POP_BLOCK\n"); - } -} - -STATIC void emit_cpy_pop_except(emit_t *emit) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("POP_EXCEPT\n"); - } -} - -STATIC void emit_cpy_unary_op(emit_t *emit, mp_unary_op_t op) { - emit_pre(emit, 0, 1); - if (emit->pass == MP_PASS_EMIT) { - switch (op) { - case MP_UNARY_OP_POSITIVE: printf("UNARY_POSITIVE\n"); break; - case MP_UNARY_OP_NEGATIVE: printf("UNARY_NEGATIVE\n"); break; - case MP_UNARY_OP_INVERT: printf("UNARY_INVERT\n"); break; - case MP_UNARY_OP_NOT: printf("UNARY_NOT\n"); break; - default: assert(0); - } - } -} - -STATIC void emit_cpy_binary_op(emit_t *emit, mp_binary_op_t op) { - if (op <= MP_BINARY_OP_INPLACE_POWER) { - // CPython uses a byte code for each binary op - emit_pre(emit, -1, 1); - } else { - // CPython uses a byte code plus an argument for compare ops - emit_pre(emit, -1, 3); - } - if (emit->pass == MP_PASS_EMIT) { - switch (op) { - case MP_BINARY_OP_OR: printf("BINARY_OR\n"); break; - case MP_BINARY_OP_XOR: printf("BINARY_XOR\n"); break; - case MP_BINARY_OP_AND: printf("BINARY_AND\n"); break; - case MP_BINARY_OP_LSHIFT: printf("BINARY_LSHIFT\n"); break; - case MP_BINARY_OP_RSHIFT: printf("BINARY_RSHIFT\n"); break; - case MP_BINARY_OP_ADD: printf("BINARY_ADD\n"); break; - case MP_BINARY_OP_SUBTRACT: printf("BINARY_SUBTRACT\n"); break; - case MP_BINARY_OP_MULTIPLY: printf("BINARY_MULTIPLY\n"); break; - case MP_BINARY_OP_FLOOR_DIVIDE: printf("BINARY_FLOOR_DIVIDE\n"); break; - case MP_BINARY_OP_TRUE_DIVIDE: printf("BINARY_TRUE_DIVIDE\n"); break; - case MP_BINARY_OP_MODULO: printf("BINARY_MODULO\n"); break; - case MP_BINARY_OP_POWER: printf("BINARY_POWER\n"); break; - case MP_BINARY_OP_INPLACE_OR: printf("INPLACE_OR\n"); break; - case MP_BINARY_OP_INPLACE_XOR: printf("INPLACE_XOR\n"); break; - case MP_BINARY_OP_INPLACE_AND: printf("INPLACE_AND\n"); break; - case MP_BINARY_OP_INPLACE_LSHIFT: printf("INPLACE_LSHIFT\n"); break; - case MP_BINARY_OP_INPLACE_RSHIFT: printf("INPLACE_RSHIFT\n"); break; - case MP_BINARY_OP_INPLACE_ADD: printf("INPLACE_ADD\n"); break; - case MP_BINARY_OP_INPLACE_SUBTRACT: printf("INPLACE_SUBTRACT\n"); break; - case MP_BINARY_OP_INPLACE_MULTIPLY: printf("INPLACE_MULTIPLY\n"); break; - case MP_BINARY_OP_INPLACE_FLOOR_DIVIDE: printf("INPLACE_FLOOR_DIVIDE\n"); break; - case MP_BINARY_OP_INPLACE_TRUE_DIVIDE: printf("INPLACE_TRUE_DIVIDE\n"); break; - case MP_BINARY_OP_INPLACE_MODULO: printf("INPLACE_MODULO\n"); break; - case MP_BINARY_OP_INPLACE_POWER: printf("INPLACE_POWER\n"); break; - case MP_BINARY_OP_LESS: printf("COMPARE_OP <\n"); break; - case MP_BINARY_OP_MORE: printf("COMPARE_OP >\n"); break; - case MP_BINARY_OP_EQUAL: printf("COMPARE_OP ==\n"); break; - case MP_BINARY_OP_LESS_EQUAL: printf("COMPARE_OP <=\n"); break; - case MP_BINARY_OP_MORE_EQUAL: printf("COMPARE_OP >=\n"); break; - case MP_BINARY_OP_NOT_EQUAL: printf("COMPARE_OP !=\n"); break; - case MP_BINARY_OP_IN: printf("COMPARE_OP in\n"); break; - case MP_BINARY_OP_IS: printf("COMPARE_OP is\n"); break; - case MP_BINARY_OP_EXCEPTION_MATCH: printf("COMPARE_OP exception match\n"); break; - case MP_BINARY_OP_NOT_IN: printf("COMPARE_OP not in\n"); break; - case MP_BINARY_OP_IS_NOT: printf("COMPARE_OP is not\n"); break; - default: assert(0); - } - } -} - -STATIC void emit_cpy_build_tuple(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, 1 - n_args, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("BUILD_TUPLE " UINT_FMT "\n", n_args); - } -} - -STATIC void emit_cpy_build_list(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, 1 - n_args, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("BUILD_LIST " UINT_FMT "\n", n_args); - } -} - -STATIC void emit_cpy_list_append(emit_t *emit, mp_uint_t list_index) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LIST_APPEND " UINT_FMT "\n", list_index); - } -} - -STATIC void emit_cpy_build_map(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("BUILD_MAP " UINT_FMT "\n", n_args); - } -} - -STATIC void emit_cpy_store_map(emit_t *emit) { - emit_pre(emit, -2, 1); - if (emit->pass == MP_PASS_EMIT) { - printf("STORE_MAP\n"); - } -} - -STATIC void emit_cpy_map_add(emit_t *emit, mp_uint_t map_index) { - emit_pre(emit, -2, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("MAP_ADD " UINT_FMT "\n", map_index); - } -} - -STATIC void emit_cpy_build_set(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, 1 - n_args, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("BUILD_SET " UINT_FMT "\n", n_args); - } -} - -STATIC void emit_cpy_set_add(emit_t *emit, mp_uint_t set_index) { - emit_pre(emit, -1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("SET_ADD " UINT_FMT "\n", set_index); - } -} - -STATIC void emit_cpy_build_slice(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, 1 - n_args, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("BUILD_SLICE " UINT_FMT "\n", n_args); - } -} - -STATIC void emit_cpy_unpack_sequence(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, -1 + n_args, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("UNPACK_SEQUENCE " UINT_FMT "\n", n_args); - } -} - -STATIC void emit_cpy_unpack_ex(emit_t *emit, mp_uint_t n_left, mp_uint_t n_right) { - emit_pre(emit, -1 + n_left + n_right + 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("UNPACK_EX " UINT_FMT "\n", n_left | (n_right << 8)); - } -} - -STATIC void emit_cpy_call_function(emit_t *emit, mp_uint_t n_positional, mp_uint_t n_keyword, mp_uint_t star_flags) { - mp_int_t s = 0; - if (star_flags & MP_EMIT_STAR_FLAG_SINGLE) { - s += 1; - } - if (star_flags & MP_EMIT_STAR_FLAG_DOUBLE) { - s += 1; - } - emit_pre(emit, -(mp_int_t)n_positional - 2 * (mp_int_t)n_keyword - s, 3); - if (emit->pass == MP_PASS_EMIT) { - if (star_flags & MP_EMIT_STAR_FLAG_SINGLE) { - if (star_flags & MP_EMIT_STAR_FLAG_DOUBLE) { - printf("CALL_FUNCTION_VAR_KW"); - } else { - printf("CALL_FUNCTION_VAR"); - } - } else { - if (star_flags & MP_EMIT_STAR_FLAG_DOUBLE) { - printf("CALL_FUNCTION_KW"); - } else { - printf("CALL_FUNCTION"); - } - } - printf(" " UINT_FMT ", " UINT_FMT "\n", n_positional, n_keyword); - } -} - -STATIC void emit_cpy_call_method(emit_t *emit, mp_uint_t n_positional, mp_uint_t n_keyword, mp_uint_t star_flags) { - emit_cpy_call_function(emit, n_positional, n_keyword, star_flags); -} - -STATIC void emit_cpy_return_value(emit_t *emit) { - emit_pre(emit, -1, 1); - emit->last_emit_was_return_value = true; - if (emit->pass == MP_PASS_EMIT) { - printf("RETURN_VALUE\n"); - } -} - -STATIC void emit_cpy_raise_varargs(emit_t *emit, mp_uint_t n_args) { - emit_pre(emit, -n_args, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("RAISE_VARARGS " UINT_FMT "\n", n_args); - } -} - -STATIC void load_cpy_const_code_and_name(emit_t *emit, qstr qst) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST code %s\n", qstr_str(qst)); - } - // load qualified name - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST '"); - // code just to work out the qualname (or whatever it is) - { - int depth = 0; - for (scope_t *s = emit->scope; s->parent != NULL; s = s->parent) { - depth += 1; - } - for (int wanted_depth = depth; wanted_depth >= 0; wanted_depth--) { - scope_t *s = emit->scope; - for (int i = 0; i < wanted_depth; i++) { - s = s->parent; - } - if (s->kind == SCOPE_FUNCTION) { - printf("%s.<locals>.", qstr_str(s->simple_name)); - } else if (s->kind == SCOPE_CLASS) { - printf("%s.", qstr_str(s->simple_name)); - } - } - } - printf("%s'\n", qstr_str(qst)); - } -} - -STATIC void emit_cpy_make_function(emit_t *emit, scope_t *scope, mp_uint_t n_pos_defaults, mp_uint_t n_kw_defaults) { - load_cpy_const_code_and_name(emit, scope->simple_name); - emit_pre(emit, -1 - n_pos_defaults - 2 * n_kw_defaults, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("MAKE_FUNCTION " UINT_FMT "\n", (n_kw_defaults << 8) | n_pos_defaults); - } -} - -STATIC void emit_cpy_make_closure(emit_t *emit, scope_t *scope, mp_uint_t n_closed_over, mp_uint_t n_pos_defaults, mp_uint_t n_kw_defaults) { - emit_cpy_build_tuple(emit, n_closed_over); - load_cpy_const_code_and_name(emit, scope->simple_name); - emit_pre(emit, -2 - n_pos_defaults - 2 * n_kw_defaults, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("MAKE_CLOSURE " UINT_FMT "\n", (n_kw_defaults << 8) | n_pos_defaults); - } -} - -STATIC void emit_cpy_yield_value(emit_t *emit) { - emit_pre(emit, 0, 1); - emit->scope->scope_flags |= MP_SCOPE_FLAG_GENERATOR; - if (emit->pass == MP_PASS_EMIT) { - printf("YIELD_VALUE\n"); - } -} - -STATIC void emit_cpy_yield_from(emit_t *emit) { - emit_pre(emit, -1, 1); - emit->scope->scope_flags |= MP_SCOPE_FLAG_GENERATOR; - if (emit->pass == MP_PASS_EMIT) { - printf("YIELD_FROM\n"); - } -} - -STATIC void emit_cpy_start_except_handler(emit_t *emit) { - emit_cpy_adjust_stack_size(emit, 3); // stack adjust for the 3 exception items -} - -STATIC void emit_cpy_end_except_handler(emit_t *emit) { - emit_cpy_adjust_stack_size(emit, -2); // stack adjust -} - -STATIC void emit_cpy_load_const_verbatim_strn(emit_t *emit, const char *str, mp_uint_t len) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CONST %.*s\n", (int)len, str); - } -} - -STATIC void emit_cpy_load_closure(emit_t *emit, qstr qst, mp_uint_t local_num) { - emit_pre(emit, 1, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("LOAD_CLOSURE " UINT_FMT " %s\n", local_num, qstr_str(qst)); - } -} - -STATIC void emit_cpy_setup_loop(emit_t *emit, mp_uint_t label) { - emit_pre(emit, 0, 3); - if (emit->pass == MP_PASS_EMIT) { - printf("SETUP_LOOP " UINT_FMT "\n", emit->label_offsets[label]); - } -} - -const emit_method_table_t emit_cpython_method_table = { - emit_cpy_set_native_type, - emit_cpy_start_pass, - emit_cpy_end_pass, - emit_cpy_last_emit_was_return_value, - emit_cpy_adjust_stack_size, - emit_cpy_set_source_line, - - { - emit_cpy_load_fast, - emit_cpy_load_deref, - emit_cpy_load_name, - emit_cpy_load_global, - }, - { - emit_cpy_store_fast, - emit_cpy_store_deref, - emit_cpy_store_name, - emit_cpy_store_global, - }, - { - emit_cpy_delete_fast, - emit_cpy_delete_deref, - emit_cpy_delete_name, - emit_cpy_delete_global, - }, - - emit_cpy_label_assign, - emit_cpy_import_name, - emit_cpy_import_from, - emit_cpy_import_star, - emit_cpy_load_const_tok, - emit_cpy_load_const_small_int, - emit_cpy_load_const_str, - emit_cpy_load_const_obj, - emit_cpy_load_null, - emit_cpy_load_attr, - emit_cpy_load_method, - emit_cpy_load_build_class, - emit_cpy_load_subscr, - emit_cpy_store_attr, - emit_cpy_store_subscr, - emit_cpy_delete_attr, - emit_cpy_delete_subscr, - emit_cpy_dup_top, - emit_cpy_dup_top_two, - emit_cpy_pop_top, - emit_cpy_rot_two, - emit_cpy_rot_three, - emit_cpy_jump, - emit_cpy_pop_jump_if, - emit_cpy_jump_if_or_pop, - emit_cpy_break_loop, - emit_cpy_continue_loop, - emit_cpy_setup_with, - emit_cpy_with_cleanup, - emit_cpy_setup_except, - emit_cpy_setup_finally, - emit_cpy_end_finally, - emit_cpy_get_iter, - emit_cpy_for_iter, - emit_cpy_for_iter_end, - emit_cpy_pop_block, - emit_cpy_pop_except, - emit_cpy_unary_op, - emit_cpy_binary_op, - emit_cpy_build_tuple, - emit_cpy_build_list, - emit_cpy_list_append, - emit_cpy_build_map, - emit_cpy_store_map, - emit_cpy_map_add, - emit_cpy_build_set, - emit_cpy_set_add, - emit_cpy_build_slice, - emit_cpy_unpack_sequence, - emit_cpy_unpack_ex, - emit_cpy_make_function, - emit_cpy_make_closure, - emit_cpy_call_function, - emit_cpy_call_method, - emit_cpy_return_value, - emit_cpy_raise_varargs, - emit_cpy_yield_value, - emit_cpy_yield_from, - - emit_cpy_start_except_handler, - emit_cpy_end_except_handler, - - // emitcpy specific functions - emit_cpy_load_const_verbatim_strn, - emit_cpy_load_closure, - emit_cpy_setup_loop, -}; - -#endif // MICROPY_EMIT_CPYTHON diff --git a/py/mkrules.mk b/py/mkrules.mk index a994016148..fe70a0ee37 100644 --- a/py/mkrules.mk +++ b/py/mkrules.mk @@ -75,7 +75,7 @@ $(HEADER_BUILD): $(MKDIR) -p $@ ifneq ($(PROG),) -# Build a standalone executable (unix and unix-cpy do this) +# Build a standalone executable (unix does this) all: $(PROG) diff --git a/py/mpconfig.h b/py/mpconfig.h index 35a14ba88e..bfa7a1f68d 100644 --- a/py/mpconfig.h +++ b/py/mpconfig.h @@ -173,12 +173,6 @@ /*****************************************************************************/ /* Micro Python emitters */ -// Whether to emit CPython byte codes (for debugging/testing) -// Enabling this overrides all other emitters -#ifndef MICROPY_EMIT_CPYTHON -#define MICROPY_EMIT_CPYTHON (0) -#endif - // Whether to emit x64 native code #ifndef MICROPY_EMIT_X64 #define MICROPY_EMIT_X64 (0) diff --git a/py/parse.c b/py/parse.c index b20fdaacd2..cd3acb2593 100644 --- a/py/parse.c +++ b/py/parse.c @@ -548,7 +548,7 @@ mp_parse_node_t mp_parse(mp_lexer_t *lex, mp_parse_input_kind_t input_kind) { } } -#if !MICROPY_EMIT_CPYTHON && !MICROPY_ENABLE_DOC_STRING + #if !MICROPY_ENABLE_DOC_STRING // this code discards lonely statements, such as doc strings if (input_kind != MP_PARSE_SINGLE_INPUT && rule->rule_id == RULE_expr_stmt && peek_result(&parser, 0) == MP_PARSE_NODE_NULL) { mp_parse_node_t p = peek_result(&parser, 1); @@ -559,7 +559,7 @@ mp_parse_node_t mp_parse(mp_lexer_t *lex, mp_parse_input_kind_t input_kind) { break; } } -#endif + #endif // always emit these rules, even if they have only 1 argument if (rule->rule_id == RULE_expr_stmt || rule->rule_id == RULE_yield_stmt) { @@ -32,7 +32,6 @@ PY_O_BASENAME = \ scope.o \ compile.o \ emitcommon.o \ - emitcpy.o \ emitbc.o \ asmx64.o \ emitnx64.o \ diff --git a/py/scope.c b/py/scope.c index 4739ac3236..f9b1fb122b 100644 --- a/py/scope.c +++ b/py/scope.c @@ -149,59 +149,3 @@ void scope_close_over_in_parents(scope_t *scope, qstr qst) { } assert(0); // we should have found the variable in one of the parents } - -#if MICROPY_EMIT_CPYTHON -#include <stdio.h> - -void scope_print_info(scope_t *s) { - if (s->kind == SCOPE_MODULE) { - printf("code <module>\n"); - } else if (s->kind == SCOPE_LAMBDA) { - printf("code <lambda>\n"); - } else if (s->kind == SCOPE_LIST_COMP) { - printf("code <listcomp>\n"); - } else if (s->kind == SCOPE_DICT_COMP) { - printf("code <dictcomp>\n"); - } else if (s->kind == SCOPE_SET_COMP) { - printf("code <setcomp>\n"); - } else if (s->kind == SCOPE_GEN_EXPR) { - printf("code <genexpr>\n"); - } else { - printf("code %s\n", qstr_str(s->simple_name)); - } - /* - printf("var global:"); - for (int i = 0; i < s->id_info_len; i++) { - if (s->id_info[i].kind == ID_INFO_KIND_GLOBAL_EXPLICIT) { - printf(" %s", qstr_str(s->id_info[i].qst)); - } - } - printf("\n"); - printf("var name:"); - for (int i = 0; i < s->id_info_len; i++) { - if (s->id_info[i].kind == ID_INFO_KIND_GLOBAL_IMPLICIT) { - printf(" %s", qstr_str(s->id_info[i].qst)); - } - } - printf("\n"); - printf("var local:"); - for (int i = 0; i < s->id_info_len; i++) { - if (s->id_info[i].kind == ID_INFO_KIND_LOCAL) { - printf(" %s", qstr_str(s->id_info[i].qst)); - } - } - printf("\n"); - printf("var free:"); - for (int i = 0; i < s->id_info_len; i++) { - if (s->id_info[i].kind == ID_INFO_KIND_FREE) { - printf(" %s", qstr_str(s->id_info[i].qst)); - } - } - printf("\n"); - */ - printf(" flags %04x\n", s->scope_flags); - printf(" argcount %d\n", s->num_pos_args); - printf(" nlocals %d\n", s->num_locals); - printf(" stacksize %d\n", s->stack_size); -} -#endif diff --git a/py/scope.h b/py/scope.h index 6d74b17d28..0ea003516a 100644 --- a/py/scope.h +++ b/py/scope.h @@ -81,6 +81,5 @@ id_info_t *scope_find(scope_t *scope, qstr qstr); id_info_t *scope_find_global(scope_t *scope, qstr qstr); id_info_t *scope_find_local_in_parent(scope_t *scope, qstr qstr); void scope_close_over_in_parents(scope_t *scope, qstr qstr); -void scope_print_info(scope_t *s); #endif // __MICROPY_INCLUDED_PY_SCOPE_H__ |