From 3b60a6de2fd68d7d02de7a10b8b88c919aa088f0 Mon Sep 17 00:00:00 2001 From: Veikka Tuominen Date: Tue, 18 Oct 2022 13:56:20 +0300 Subject: [PATCH] Sema: fix using runtime instructions inside typeof in comptime only blocks Closes #13210 Follow up to 3ccd4907fbcd04ecddffb618a4b14581fd080279 --- src/Sema.zig | 8 +++++++- test/behavior/sizeof_and_typeof.zig | 24 ++++++++++++++++++++++++ 2 files changed, 31 insertions(+), 1 deletion(-) diff --git a/src/Sema.zig b/src/Sema.zig index 8945bc6bed..76e7e779e7 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -6433,7 +6433,7 @@ fn analyzeInlineCallArg( .ty = param_ty, .val = arg_val, }; - } else if ((try sema.resolveMaybeUndefVal(arg_block, arg_src, casted_arg) == null) or + } else if (((try sema.resolveMaybeUndefVal(arg_block, arg_src, casted_arg)) == null) or try sema.typeRequiresComptime(param_ty) or zir_tags[inst] == .param_comptime) { try sema.inst_map.putNoClobber(sema.gpa, inst, casted_arg); @@ -14521,6 +14521,12 @@ fn zirClosureGet( return sema.failWithOwnedErrorMsg(msg); } + if (tv.val.tag() == .unreachable_value) { + assert(block.is_typeof); + // We need a dummy runtime instruction with the correct type. + return block.addTy(.alloc, tv.ty); + } + return sema.addConstant(tv.ty, tv.val); } diff --git a/test/behavior/sizeof_and_typeof.zig b/test/behavior/sizeof_and_typeof.zig index 01501b05b2..0c0069b28f 100644 --- a/test/behavior/sizeof_and_typeof.zig +++ b/test/behavior/sizeof_and_typeof.zig @@ -314,3 +314,27 @@ test "lazy size cast to float" { test "bitSizeOf comptime_int" { try expect(@bitSizeOf(comptime_int) == 0); } + +test "runtime instructions inside typeof in comptime only scope" { + if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; + if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; + + { + var y: i8 = 2; + const i: [2]i8 = [_]i8{ 1, y }; + const T = struct { + a: @TypeOf(i) = undefined, // causes crash + b: @TypeOf(i[0]) = undefined, // causes crash + }; + try expect(@TypeOf((T{}).a) == [2]i8); + try expect(@TypeOf((T{}).b) == i8); + } + { + var y: i8 = 2; + const i = .{ 1, y }; + const T = struct { + b: @TypeOf(i[1]) = undefined, + }; + try expect(@TypeOf((T{}).b) == i8); + } +}