authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2020-03-06 18:30:30-05:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2020-03-06 18:30:30-05:00
logfa46bcb36864e6616ce4449965063f3b8720f8e1
treed0f486600d651e47609ac57bed117422791930bc
parent83d27f71ef92d555cc15645bf9d948203ba8af1e
signaturelock-open Commit is signed but in an unrecognized format.

stage1: make get_optional_type more robust

Now it will emit a compile error rather than crashing when the child type has not been resolved properly. Introduces `get_optional_type2` which should be used generally inside ir.cpp. Fix some std lib compile errors noticed by the provided test case. Thanks @LemonBoy for the test case. Closes #4377. Fixes #4374.

5 files changed, 24 insertions(+), 6 deletions(-)

lib/std/builtin.zig+4-4
......@@ -27,7 +27,7 @@ pub const Cpu = std.Target.Cpu;
2727/// On non-Windows targets, this is `null`.
2828pub const subsystem: ?SubSystem = blk: {
2929 if (@hasDecl(@This(), "explicit_subsystem")) break :blk explicit_subsystem;
30 switch (os) {
30 switch (os.tag) {
3131 .windows => {
3232 if (is_test) {
3333 break :blk SubSystem.Console;
......@@ -406,9 +406,9 @@ pub const Version = struct {
406406 min: Version,
407407 max: Version,
408408
409 pub fn includesVersion(self: LinuxVersionRange, ver: Version) bool {
410 if (self.min.compare(ver) == .gt) return false;
411 if (self.max.compare(ver) == .lt) return false;
409 pub fn includesVersion(self: Range, ver: Version) bool {
410 if (self.min.order(ver) == .gt) return false;
411 if (self.max.order(ver) == .lt) return false;
412412 return true;
413413 }
414414 };
src/analyze.cpp+12-1
......@@ -649,11 +649,22 @@ ZigType *get_pointer_to_type(CodeGen *g, ZigType *child_type, bool is_const) {
649649}
650650
651651ZigType *get_optional_type(CodeGen *g, ZigType *child_type) {
652 ZigType *result = get_optional_type2(g, child_type);
653 if (result == nullptr) {
654 codegen_report_errors_and_exit(g);
655 }
656 return result;
657}
658
659ZigType *get_optional_type2(CodeGen *g, ZigType *child_type) {
652660 if (child_type->optional_parent != nullptr) {
653661 return child_type->optional_parent;
654662 }
655663
656 assert(type_is_resolved(child_type, ResolveStatusSizeKnown));
664 Error err;
665 if ((err = type_resolve(g, child_type, ResolveStatusSizeKnown))) {
666 return nullptr;
667 }
657668
658669 ZigType *entry = new_type_table_entry(ZigTypeIdOptional);
659670
src/analyze.hpp+1
......@@ -34,6 +34,7 @@ ZigType **get_c_int_type_ptr(CodeGen *g, CIntType c_int_type);
3434ZigType *get_c_int_type(CodeGen *g, CIntType c_int_type);
3535ZigType *get_fn_type(CodeGen *g, FnTypeId *fn_type_id);
3636ZigType *get_optional_type(CodeGen *g, ZigType *child_type);
37ZigType *get_optional_type2(CodeGen *g, ZigType *child_type);
3738ZigType *get_array_type(CodeGen *g, ZigType *child_type, uint64_t array_size, ZigValue *sentinel);
3839ZigType *get_slice_type(CodeGen *g, ZigType *ptr_type);
3940ZigType *get_partial_container_type(CodeGen *g, Scope *scope, ContainerKind kind,
src/ir.cpp+2-1
......@@ -24339,7 +24339,8 @@ static Error ir_make_type_info_value(IrAnalyze *ira, IrInst* source_instr, ZigTy
2433924339
2434024340 // default_value: var
2434124341 inner_fields[3]->special = ConstValSpecialStatic;
24342 inner_fields[3]->type = get_optional_type(ira->codegen, struct_field->type_entry);
24342 inner_fields[3]->type = get_optional_type2(ira->codegen, struct_field->type_entry);
24343 if (inner_fields[3]->type == nullptr) return ErrorSemanticAnalyzeFail;
2434324344 memoize_field_init_val(ira->codegen, type_entry, struct_field);
2434424345 set_optional_payload(inner_fields[3], struct_field->init_val);
2434524346
test/stage1/behavior/type_info.zig+5
......@@ -386,3 +386,8 @@ test "@typeInfo does not force declarations into existence" {
386386 };
387387 comptime expect(@typeInfo(S).Struct.fields.len == 1);
388388}
389
390test "defaut value for a var-typed field" {
391 const S = struct { x: var };
392 expect(@typeInfo(S).Struct.fields[0].default_value == null);
393}