diff --git a/Sources/backends/cstyle.c b/Sources/backends/cstyle.c index e335ac8..d53f2b3 100644 --- a/Sources/backends/cstyle.c +++ b/Sources/backends/cstyle.c @@ -165,8 +165,17 @@ void cstyle_write_opcode(char *code, size_t *offset, opcode *o, type_string_func *offset += sprintf(&code[*offset], "\telse\n"); break; } - case OPCODE_WHILE: { - *offset += sprintf(&code[*offset], "\twhile (_%" PRIu64 ")\n", o->op_while.condition.index); + case OPCODE_WHILE_START: { + *offset += sprintf(&code[*offset], "\twhile (true)\n"); + *offset += sprintf(&code[*offset], "\t{\n"); + break; + } + case OPCODE_WHILE_CONDITION: { + *offset += sprintf(&code[*offset], "\tif (!_%" PRIu64 ") break;\n", o->op_while.condition.index); + break; + } + case OPCODE_WHILE_END: { + *offset += sprintf(&code[*offset], "\t}\n"); break; } case OPCODE_BLOCK_START: { diff --git a/Sources/compiler.c b/Sources/compiler.c index c2cbbd3..bdf4c1b 100644 --- a/Sources/compiler.c +++ b/Sources/compiler.c @@ -552,7 +552,14 @@ void emit_statement(opcodes *code, block *parent, statement *statement) { case STATEMENT_WHILE: { { opcode o; - o.type = OPCODE_WHILE; + o.type = OPCODE_WHILE_START; + o.size = OP_SIZE(o, op_nothing); + emit_op(code, &o); + } + + { + opcode o; + o.type = OPCODE_WHILE_CONDITION; o.size = OP_SIZE(o, op_while); variable v = emit_expression(code, parent, statement->willy.test); @@ -564,6 +571,13 @@ void emit_statement(opcodes *code, block *parent, statement *statement) { emit_statement(code, parent, statement->willy.while_block); + { + opcode o; + o.type = OPCODE_WHILE_END; + o.size = OP_SIZE(o, op_nothing); + emit_op(code, &o); + } + break; } case STATEMENT_BLOCK: { diff --git a/Sources/compiler.h b/Sources/compiler.h index df82dc0..0cd93f7 100644 --- a/Sources/compiler.h +++ b/Sources/compiler.h @@ -42,7 +42,10 @@ typedef struct opcode { OPCODE_OR, OPCODE_IF, OPCODE_ELSE, - OPCODE_WHILE, + OPCODE_WHILE_START, + OPCODE_WHILE_CONDITION, + OPCODE_WHILE_END, + OPCODE_WHILE_BODY, OPCODE_BLOCK_START, OPCODE_BLOCK_END } type;