diff options
author | Damien George <damien.p.george@gmail.com> | 2017-08-30 11:24:29 +1000 |
---|---|---|
committer | Damien George <damien.p.george@gmail.com> | 2017-08-30 11:24:29 +1000 |
commit | d7576c4ba798f5067d9f07c745a4ab059b1121ea (patch) | |
tree | 3c6ed54a4d26f3fb0c4f0eb9aaa799a651ff4677 | |
parent | d88eab7445a905ea04fd55e75e40934a9f9acd80 (diff) | |
download | micropython-d7576c4ba798f5067d9f07c745a4ab059b1121ea.tar.gz micropython-d7576c4ba798f5067d9f07c745a4ab059b1121ea.zip |
py/compile2: Fix bug with break/continue in else of optimised for-range.
A port of 4c5f108321a8fd3f67f597ca918427eda813c12e.
-rw-r--r-- | py/compile2.c | 15 |
1 files changed, 15 insertions, 0 deletions
diff --git a/py/compile2.c b/py/compile2.c index f9636bd3c7..94a7591703 100644 --- a/py/compile2.c +++ b/py/compile2.c @@ -1455,8 +1455,19 @@ STATIC void compile_for_stmt_optimised_range(compiler_t *comp, const byte *pn_va // break/continue apply to outer loop (if any) in the else block END_BREAK_CONTINUE_BLOCK + // Compile the else block. We must pop the iterator variables before + // executing the else code because it may contain break/continue statements. + uint end_label = 0; if (pn_else != NULL) { + // discard final value of "var", and possible "end" value + EMIT(pop_top); + if (end_on_stack) { + EMIT(pop_top); + } compile_node(comp, pn_else); + end_label = comp_next_label(comp); + EMIT_ARG(jump, end_label); + EMIT_ARG(adjust_stack_size, 1 + end_on_stack); } EMIT_ARG(label_assign, break_label); @@ -1468,6 +1479,10 @@ STATIC void compile_for_stmt_optimised_range(compiler_t *comp, const byte *pn_va if (end_on_stack) { EMIT(pop_top); } + + if (pn_else != NULL) { + EMIT_ARG(label_assign, end_label); + } } STATIC void compile_for_stmt(compiler_t *comp, const byte *p, const byte *ptop) { |