zig

fork of https://codeberg.org/ziglang/zig
Log | Files | Refs | README | LICENSE

commit f464fe14f4ece387935dbe2bb6b73ecf466c3f83 (tree)
parent bb6b4f8db2bf793f4118ee68a05ff0b4df52c318
Author: Andrew Kelley <superjoe30@gmail.com>
Date:   Tue,  5 Dec 2017 22:26:17 -0500

switch on enum which only has 1 field is comptime known

closes #593

Diffstat:
Msrc/ir.cpp | 10++++++++++
Mtest/cases/enum.zig | 11+++++++++++
2 files changed, 21 insertions(+), 0 deletions(-)

diff --git a/src/ir.cpp b/src/ir.cpp @@ -13174,6 +13174,16 @@ static TypeTableEntry *ir_analyze_instruction_switch_target(IrAnalyze *ira, return tag_type; } case TypeTableEntryIdEnum: { + type_ensure_zero_bits_known(ira->codegen, target_type); + if (type_is_invalid(target_type)) + return ira->codegen->builtin_types.entry_invalid; + if (target_type->data.enumeration.src_field_count < 2) { + TypeEnumField *only_field = &target_type->data.enumeration.fields[0]; + ConstExprValue *out_val = ir_build_const_from(ira, &switch_target_instruction->base); + bigint_init_bigint(&out_val->data.x_enum_tag, &only_field->value); + return target_type; + } + if (pointee_val) { ConstExprValue *out_val = ir_build_const_from(ira, &switch_target_instruction->base); bigint_init_bigint(&out_val->data.x_enum_tag, &pointee_val->data.x_enum_tag); diff --git a/test/cases/enum.zig b/test/cases/enum.zig @@ -366,3 +366,14 @@ fn doALoopThing(id: EnumWithOneMember) { test "comparison operator on enum with one member is comptime known" { doALoopThing(EnumWithOneMember.Eof); } + +const State = enum { + Start, +}; +test "switch on enum with one member is comptime known" { + var state = State.Start; + switch (state) { + State.Start => return, + } + @compileError("analysis should not reach here"); +}