From 7b8fc18c666ba6952ad1571fbed4cc48e81f647d Mon Sep 17 00:00:00 2001 From: gabeuehlein Date: Mon, 14 Oct 2024 08:02:14 -0400 Subject: [PATCH] Sema: fail if analyzing return in `noreturn`-declared function before coercing `undefined` Just switches logic around in coerceExtra to check for returning in a noreturn function before coercing undefined to anything --- src/Sema.zig | 10 +++++----- .../compile_errors/return_undefined_from_noreturn.zig | 10 ++++++++++ 2 files changed, 15 insertions(+), 5 deletions(-) create mode 100644 test/cases/compile_errors/return_undefined_from_noreturn.zig diff --git a/src/Sema.zig b/src/Sema.zig index 1de0d73808..1250a06a9c 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -30346,11 +30346,6 @@ fn coerceExtra( else => {}, } - // undefined to anything. We do this after the big switch above so that - // special logic has a chance to run first, such as `*[N]T` to `[]T` which - // should initialize the length field of the slice. - if (maybe_inst_val) |val| if (val.toIntern() == .undef) return pt.undefRef(dest_ty); - if (!opts.report_err) return error.NotCoercible; if (opts.is_ret and dest_ty.zigTypeTag(zcu) == .noreturn) { @@ -30368,6 +30363,11 @@ fn coerceExtra( return sema.failWithOwnedErrorMsg(block, msg); } + // undefined to anything. We do this after the big switch above so that + // special logic has a chance to run first, such as `*[N]T` to `[]T` which + // should initialize the length field of the slice. + if (maybe_inst_val) |val| if (val.toIntern() == .undef) return pt.undefRef(dest_ty); + const msg = msg: { const msg = try sema.errMsg(inst_src, "expected type '{}', found '{}'", .{ dest_ty.fmt(pt), inst_ty.fmt(pt) }); errdefer msg.destroy(sema.gpa); diff --git a/test/cases/compile_errors/return_undefined_from_noreturn.zig b/test/cases/compile_errors/return_undefined_from_noreturn.zig new file mode 100644 index 0000000000..eabb7769d1 --- /dev/null +++ b/test/cases/compile_errors/return_undefined_from_noreturn.zig @@ -0,0 +1,10 @@ +export fn entry() noreturn { + return undefined; +} + +// error +// backend=stage2 +// target=native +// +// :2:12: error: function declared 'noreturn' returns +// :1:19: note: 'noreturn' declared here