| author | |
| committer | |
| log | 4a5b0cde1330e0410612838a42dad62cc30b0e92 |
| tree | ac182440d6b067eeaa2159c26c240387ae51397d |
| parent | ab4cba14c8aac7151b4c10094fea4211694da145 |
| signature | Commit is signed but in an unrecognized format. |
Closes #2791. See that issue for more details; I documented the
debugging process quite thoroughly on this one.2 files changed, 20 insertions(+), 0 deletions(-)
src/codegen.cpp+9| ... | ... | @@ -3522,6 +3522,15 @@ static LLVMValueRef ir_render_store_ptr(CodeGen *g, IrExecutable *executable, Ir |
| 3522 | 3522 | assert(ptr_type->id == ZigTypeIdPointer); |
| 3523 | 3523 | if (!type_has_bits(ptr_type)) |
| 3524 | 3524 | return nullptr; |
| 3525 | if (instruction->ptr->ref_count == 0) { | |
| 3526 | // In this case, this StorePtr instruction should be elided. Something happened like this: | |
| 3527 | // var t = true; | |
| 3528 | // const x = if (t) Num.Two else unreachable; | |
| 3529 | // The if condition is a runtime value, so the StorePtr for `x = Num.Two` got generated | |
| 3530 | // (this instruction being rendered) but because of `else unreachable` the result ended | |
| 3531 | // up being a comptime const value. | |
| 3532 | return nullptr; | |
| 3533 | } | |
| 3525 | 3534 | |
| 3526 | 3535 | bool have_init_expr = !value_is_all_undef(&instruction->value->value); |
| 3527 | 3536 | if (have_init_expr) { |
test/stage1/behavior/if.zig+11| ... | ... | @@ -63,3 +63,14 @@ test "labeled break inside comptime if inside runtime if" { |
| 63 | 63 | } |
| 64 | 64 | expect(answer == 42); |
| 65 | 65 | } |
| 66 | ||
| 67 | test "const result loc, runtime if cond, else unreachable" { | |
| 68 | const Num = enum { | |
| 69 | One, | |
| 70 | Two, | |
| 71 | }; | |
| 72 | ||
| 73 | var t = true; | |
| 74 | const x = if (t) Num.Two else unreachable; | |
| 75 | if (x != .Two) @compileError("bad"); | |
| 76 | } |