@@ -44,11 +44,14 @@ typedef struct _compiler_t {
4444 qstr qstr___doc__ ;
4545 qstr qstr_assertion_error ;
4646 qstr qstr_micropython ;
47+ qstr qstr_byte_code ;
4748 qstr qstr_native ;
4849 qstr qstr_viper ;
4950 qstr qstr_asm_thumb ;
5051
52+ bool is_repl ;
5153 pass_kind_t pass ;
54+ bool had_error ; // try to keep compiler clean from nlr
5255
5356 int next_label ;
5457
@@ -196,7 +199,7 @@ static int comp_next_label(compiler_t *comp) {
196199}
197200
198201static scope_t * scope_new_and_link (compiler_t * comp , scope_kind_t kind , py_parse_node_t pn , uint emit_options ) {
199- scope_t * scope = scope_new (kind , pn , rt_get_new_unique_code_id ( ), emit_options );
202+ scope_t * scope = scope_new (kind , pn , rt_get_unique_code_id ( kind == SCOPE_MODULE ), emit_options );
200203 scope -> parent = comp -> scope_cur ;
201204 scope -> next = NULL ;
202205 if (comp -> scope_head == NULL ) {
@@ -855,7 +858,8 @@ static bool compile_built_in_decorator(compiler_t *comp, int name_len, py_parse_
855858 }
856859
857860 qstr attr = PY_PARSE_NODE_LEAF_ARG (name_nodes [1 ]);
858- if (0 ) {
861+ if (attr == comp -> qstr_byte_code ) {
862+ * emit_options = EMIT_OPT_BYTE_CODE ;
859863#if MICROPY_EMIT_NATIVE
860864 } else if (attr == comp -> qstr_native ) {
861865 * emit_options = EMIT_OPT_NATIVE_PYTHON ;
@@ -1046,7 +1050,13 @@ void compile_continue_stmt(compiler_t *comp, py_parse_node_struct_t *pns) {
10461050}
10471051
10481052void compile_return_stmt (compiler_t * comp , py_parse_node_struct_t * pns ) {
1053+ if (comp -> scope_cur -> kind != SCOPE_FUNCTION ) {
1054+ printf ("SyntaxError: 'return' outside function\n" );
1055+ comp -> had_error = true;
1056+ return ;
1057+ }
10491058 if (PY_PARSE_NODE_IS_NULL (pns -> nodes [0 ])) {
1059+ // no argument to 'return', so return None
10501060 EMIT (load_const_tok , PY_TOKEN_KW_NONE );
10511061 } else if (PY_PARSE_NODE_IS_STRUCT_KIND (pns -> nodes [0 ], PN_test_if_expr )) {
10521062 // special case when returning an if-expression; to match CPython optimisation
@@ -1566,11 +1576,21 @@ void compile_with_stmt(compiler_t *comp, py_parse_node_struct_t *pns) {
15661576
15671577void compile_expr_stmt (compiler_t * comp , py_parse_node_struct_t * pns ) {
15681578 if (PY_PARSE_NODE_IS_NULL (pns -> nodes [1 ])) {
1569- if (PY_PARSE_NODE_IS_LEAF (pns -> nodes [0 ]) && !PY_PARSE_NODE_IS_ID (pns -> nodes [0 ])) {
1570- // do nothing with a lonely constant
1579+ if (comp -> is_repl && comp -> scope_cur -> kind == SCOPE_MODULE ) {
1580+ // for REPL, evaluate then print the expression
1581+ EMIT (load_id , qstr_from_str_static ("__repl_print__" ));
1582+ compile_node (comp , pns -> nodes [0 ]);
1583+ EMIT (call_function , 1 , 0 , false, false);
1584+ EMIT (pop_top );
1585+
15711586 } else {
1572- compile_node (comp , pns -> nodes [0 ]); // just an expression
1573- EMIT (pop_top ); // discard last result since this is a statement and leaves nothing on the stack
1587+ // for non-REPL, evaluate then discard the expression
1588+ if (PY_PARSE_NODE_IS_LEAF (pns -> nodes [0 ]) && !PY_PARSE_NODE_IS_ID (pns -> nodes [0 ])) {
1589+ // do nothing with a lonely constant
1590+ } else {
1591+ compile_node (comp , pns -> nodes [0 ]); // just an expression
1592+ EMIT (pop_top ); // discard last result since this is a statement and leaves nothing on the stack
1593+ }
15741594 }
15751595 } else {
15761596 py_parse_node_struct_t * pns1 = (py_parse_node_struct_t * )pns -> nodes [1 ];
@@ -2287,6 +2307,7 @@ void compile_node(compiler_t *comp, py_parse_node_t pn) {
22872307 case PY_PARSE_NODE_TOKEN :
22882308 if (arg == PY_TOKEN_NEWLINE ) {
22892309 // this can occur when file_input lets through a NEWLINE (eg if file starts with a newline)
2310+ // or when single_input lets through a NEWLINE (user enters a blank line)
22902311 // do nothing
22912312 } else {
22922313 EMIT (load_const_tok , arg );
@@ -2299,7 +2320,7 @@ void compile_node(compiler_t *comp, py_parse_node_t pn) {
22992320 compile_function_t f = compile_function [PY_PARSE_NODE_STRUCT_KIND (pns )];
23002321 if (f == NULL ) {
23012322 printf ("node %u cannot be compiled\n" , (uint )PY_PARSE_NODE_STRUCT_KIND (pns ));
2302- parse_node_show (pn , 0 );
2323+ py_parse_node_show (pn , 0 );
23032324 assert (0 );
23042325 } else {
23052326 f (comp , pns );
@@ -2481,14 +2502,17 @@ void compile_scope(compiler_t *comp, scope_t *scope, pass_kind_t pass) {
24812502 scope -> stack_size = 0 ;
24822503 }
24832504
2505+ #if MICROPY_EMIT_CPYTHON
24842506 if (comp -> pass == PASS_3 ) {
2485- //printf("----\n");
24862507 scope_print_info (scope );
24872508 }
2509+ #endif
24882510
24892511 // compile
24902512 if (scope -> kind == SCOPE_MODULE ) {
2491- check_for_doc_string (comp , scope -> pn );
2513+ if (!comp -> is_repl ) {
2514+ check_for_doc_string (comp , scope -> pn );
2515+ }
24922516 compile_node (comp , scope -> pn );
24932517 EMIT (load_const_tok , PY_TOKEN_KW_NONE );
24942518 EMIT (return_value );
@@ -2731,7 +2755,7 @@ void compile_scope_compute_things(compiler_t *comp, scope_t *scope) {
27312755 }
27322756}
27332757
2734- void py_compile (py_parse_node_t pn ) {
2758+ bool py_compile (py_parse_node_t pn , bool is_repl ) {
27352759 compiler_t * comp = m_new (compiler_t , 1 );
27362760
27372761 comp -> qstr___class__ = qstr_from_str_static ("__class__" );
@@ -2742,10 +2766,14 @@ void py_compile(py_parse_node_t pn) {
27422766 comp -> qstr___doc__ = qstr_from_str_static ("__doc__" );
27432767 comp -> qstr_assertion_error = qstr_from_str_static ("AssertionError" );
27442768 comp -> qstr_micropython = qstr_from_str_static ("micropython" );
2769+ comp -> qstr_byte_code = qstr_from_str_static ("byte_code" );
27452770 comp -> qstr_native = qstr_from_str_static ("native" );
27462771 comp -> qstr_viper = qstr_from_str_static ("viper" );
27472772 comp -> qstr_asm_thumb = qstr_from_str_static ("asm_thumb" );
27482773
2774+ comp -> is_repl = is_repl ;
2775+ comp -> had_error = false;
2776+
27492777 comp -> break_label = 0 ;
27502778 comp -> continue_label = 0 ;
27512779 comp -> except_nest_level = 0 ;
@@ -2764,7 +2792,7 @@ void py_compile(py_parse_node_t pn) {
27642792 comp -> emit_inline_asm = NULL ;
27652793 comp -> emit_inline_asm_method_table = NULL ;
27662794 uint max_num_labels = 0 ;
2767- for (scope_t * s = comp -> scope_head ; s != NULL ; s = s -> next ) {
2795+ for (scope_t * s = comp -> scope_head ; s != NULL && ! comp -> had_error ; s = s -> next ) {
27682796 if (false) {
27692797#if MICROPY_EMIT_INLINE_THUMB
27702798 } else if (s -> emit_options == EMIT_OPT_ASM_THUMB ) {
@@ -2781,7 +2809,7 @@ void py_compile(py_parse_node_t pn) {
27812809 }
27822810
27832811 // compute some things related to scope and identifiers
2784- for (scope_t * s = comp -> scope_head ; s != NULL ; s = s -> next ) {
2812+ for (scope_t * s = comp -> scope_head ; s != NULL && ! comp -> had_error ; s = s -> next ) {
27852813 compile_scope_compute_things (comp , s );
27862814 }
27872815
@@ -2796,7 +2824,7 @@ void py_compile(py_parse_node_t pn) {
27962824#if MICROPY_EMIT_INLINE_THUMB
27972825 emit_inline_asm_t * emit_inline_thumb = NULL ;
27982826#endif
2799- for (scope_t * s = comp -> scope_head ; s != NULL ; s = s -> next ) {
2827+ for (scope_t * s = comp -> scope_head ; s != NULL && ! comp -> had_error ; s = s -> next ) {
28002828 if (false) {
28012829 // dummy
28022830
@@ -2857,4 +2885,6 @@ void py_compile(py_parse_node_t pn) {
28572885 }
28582886
28592887 m_free (comp );
2888+
2889+ return !comp -> had_error ;
28602890}
0 commit comments