diff options
| author | Ginger Bill <bill@gingerbill.org> | 2016-11-29 22:08:48 +0000 |
|---|---|---|
| committer | Ginger Bill <bill@gingerbill.org> | 2016-11-29 22:08:48 +0000 |
| commit | b232b9d5ea23fdd4d53f8e93cdfeb1f962811331 (patch) | |
| tree | 6b4fbe56bf1fc7e7929104790cfb05b42b5f4071 /src/ssa.c | |
| parent | 348bcc3f9a1375ddf24b952fad537b5c84e84053 (diff) | |
Basic `when` statement - Compile time if statement
This is similar to an #if in C but handled during the semantic checking stage.
Diffstat (limited to 'src/ssa.c')
| -rw-r--r-- | src/ssa.c | 27 |
1 files changed, 27 insertions, 0 deletions
@@ -3815,6 +3815,29 @@ void ssa_build_stmt(ssaProcedure *proc, AstNode *node) { proc->module->stmt_state_flags = prev_stmt_state_flags; } +void ssa_build_when_stmt(ssaProcedure *proc, AstNodeWhenStmt *ws) { + ssaValue *cond = ssa_build_expr(proc, ws->cond); + GB_ASSERT(cond->kind == ssaValue_Constant && + is_type_boolean(ssa_type(cond))); + + GB_ASSERT(cond->Constant.value.kind == ExactValue_Bool); + if (cond->Constant.value.value_bool) { + ssa_build_stmt_list(proc, ws->body->BlockStmt.stmts); + } else if (ws->else_stmt) { + switch (ws->else_stmt->kind) { + case AstNode_BlockStmt: + ssa_build_stmt_list(proc, ws->else_stmt->BlockStmt.stmts); + break; + case AstNode_WhenStmt: + ssa_build_when_stmt(proc, &ws->else_stmt->WhenStmt); + break; + default: + GB_PANIC("Invalid `else` statement in `when` statement"); + break; + } + } +} + void ssa_build_stmt_internal(ssaProcedure *proc, AstNode *node) { switch (node->kind) { case_ast_node(bs, EmptyStmt, node); @@ -3827,6 +3850,10 @@ void ssa_build_stmt_internal(ssaProcedure *proc, AstNode *node) { } case_end; + case_ast_node(ws, WhenStmt, node); + ssa_build_when_stmt(proc, ws); + case_end; + case_ast_node(vd, VarDecl, node); ssaModule *m = proc->module; gbTempArenaMemory tmp = gb_temp_arena_memory_begin(&m->tmp_arena); |