| author | |
| committer | |
| log | 66e3aa09104781f460da1ea721b083d18eec351b |
| tree | fa6a39c1df96635168fa02e1427daf238e31e8bd |
| parent | 180f539f6722e72b661825e9d4971651da872b99 |
3 files changed, 12 insertions(+), 9 deletions(-)
src/analyze.cpp+2-2| ... | @@ -454,8 +454,8 @@ static TypeTableEntry * analyze_expression(CodeGen *g, ImportTableEntry *import, | ... | @@ -454,8 +454,8 @@ static TypeTableEntry * analyze_expression(CodeGen *g, ImportTableEntry *import, |
| 454 | buf_sprintf("variable initialization is unreachable")); | 454 | buf_sprintf("variable initialization is unreachable")); |
| 455 | } | 455 | } |
| 456 | 456 | ||
| 457 | if (implicit_type == nullptr) { | 457 | if (implicit_type == nullptr && variable_declaration->is_const) { |
| 458 | add_node_error(g, node, buf_sprintf("initial values are required for variable declaration")); | 458 | add_node_error(g, node, buf_sprintf("variables must have initial values or be declared 'mut'.")); |
| 459 | } | 459 | } |
| 460 | 460 | ||
| 461 | TypeTableEntry *type = explicit_type != nullptr ? explicit_type : implicit_type; | 461 | TypeTableEntry *type = explicit_type != nullptr ? explicit_type : implicit_type; |
src/codegen.cpp+5-5| ... | @@ -526,14 +526,14 @@ static LLVMValueRef gen_expr(CodeGen *g, AstNode *node) { | ... | @@ -526,14 +526,14 @@ static LLVMValueRef gen_expr(CodeGen *g, AstNode *node) { |
| 526 | variable->value_ref = gen_expr(g, node->data.variable_declaration.expr); | 526 | variable->value_ref = gen_expr(g, node->data.variable_declaration.expr); |
| 527 | return nullptr; | 527 | return nullptr; |
| 528 | } else { | 528 | } else { |
| 529 | LLVMValueRef value; | ||
| 529 | if (node->data.variable_declaration.expr) { | 530 | if (node->data.variable_declaration.expr) { |
| 530 | LLVMValueRef value = gen_expr(g, node->data.variable_declaration.expr); | 531 | value = gen_expr(g, node->data.variable_declaration.expr); |
| 531 | |||
| 532 | add_debug_source_node(g, node); | ||
| 533 | return LLVMBuildStore(g->builder, value, variable->value_ref); | ||
| 534 | } else { | 532 | } else { |
| 535 | 533 | value = LLVMConstNull(variable->type->type_ref); | |
| 536 | } | 534 | } |
| 535 | add_debug_source_node(g, node); | ||
| 536 | return LLVMBuildStore(g->builder, value, variable->value_ref); | ||
| 537 | } | 537 | } |
| 538 | } | 538 | } |
| 539 | case NodeTypeCastExpr: | 539 | case NodeTypeCastExpr: |
test/run_tests.cpp+5-2| ... | @@ -332,7 +332,7 @@ fn void_fun(a : i32, b : void, c : i32) { | ... | @@ -332,7 +332,7 @@ fn void_fun(a : i32, b : void, c : i32) { |
| 332 | } | 332 | } |
| 333 | )SOURCE", "OK\n"); | 333 | )SOURCE", "OK\n"); |
| 334 | 334 | ||
| 335 | add_simple_case("void parameters", R"SOURCE( | 335 | add_simple_case("mutable local variables", R"SOURCE( |
| 336 | #link("c") | 336 | #link("c") |
| 337 | extern { | 337 | extern { |
| 338 | fn puts(s: *const u8) -> i32; | 338 | fn puts(s: *const u8) -> i32; |
| ... | @@ -340,6 +340,9 @@ extern { | ... | @@ -340,6 +340,9 @@ extern { |
| 340 | } | 340 | } |
| 341 | 341 | ||
| 342 | export fn _start() -> unreachable { | 342 | export fn _start() -> unreachable { |
| 343 | let mut zero : i32; | ||
| 344 | if (zero == 0) { puts("zero"); } | ||
| 345 | |||
| 343 | let mut i = 0; | 346 | let mut i = 0; |
| 344 | loop_start: | 347 | loop_start: |
| 345 | if i == 3 { | 348 | if i == 3 { |
| ... | @@ -351,7 +354,7 @@ loop_start: | ... | @@ -351,7 +354,7 @@ loop_start: |
| 351 | done: | 354 | done: |
| 352 | exit(0); | 355 | exit(0); |
| 353 | } | 356 | } |
| 354 | )SOURCE", "loop\nloop\nloop\n"); | 357 | )SOURCE", "zero\nloop\nloop\nloop\n"); |
| 355 | } | 358 | } |
| 356 | 359 | ||
| 357 | static void add_compile_failure_test_cases(void) { | 360 | static void add_compile_failure_test_cases(void) { |