From d78532f462b2d0b514bbd3c1c3ed36135dca766c Mon Sep 17 00:00:00 2001 From: Veikka Tuominen Date: Tue, 26 Jul 2022 13:20:29 +0300 Subject: [PATCH 1/5] Sema: give comptime_field_ptr priority over field_ptr in tuples Closes #11983 --- src/Sema.zig | 26 +++++++++++++------ .../invalid_store_to_comptime_field.zig | 5 ++++ 2 files changed, 23 insertions(+), 8 deletions(-) diff --git a/src/Sema.zig b/src/Sema.zig index ffe57c4a1b..57de32396d 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -20499,6 +20499,14 @@ fn tupleFieldPtr( .@"addrspace" = tuple_ptr_ty.ptrAddressSpace(), }); + if (tuple_ty.structFieldValueComptime(field_index)) |default_val| { + const val = try Value.Tag.comptime_field_ptr.create(sema.arena, .{ + .field_ty = field_ty, + .field_val = default_val, + }); + return sema.addConstant(ptr_field_ty, val); + } + if (try sema.resolveMaybeUndefVal(block, tuple_ptr_src, tuple_ptr)) |tuple_ptr_val| { return sema.addConstant( ptr_field_ty, @@ -20510,14 +20518,6 @@ fn tupleFieldPtr( ); } - if (tuple_ty.structFieldValueComptime(field_index)) |default_val| { - const val = try Value.Tag.comptime_field_ptr.create(sema.arena, .{ - .field_ty = field_ty, - .field_val = default_val, - }); - return sema.addConstant(ptr_field_ty, val); - } - if (!init) { try sema.validateRuntimeElemAccess(block, field_index_src, field_ty, tuple_ty, tuple_ptr_src); } @@ -23241,6 +23241,16 @@ fn beginComptimePtrLoad( break :blk deref; }, + .comptime_field_ptr => blk: { + const comptime_field_ptr = ptr_val.castTag(.comptime_field_ptr).?.data; + break :blk ComptimePtrLoadKit{ + .parent = null, + .pointee = .{ .ty = comptime_field_ptr.field_ty, .val = comptime_field_ptr.field_val }, + .is_mutable = false, + .ty_without_well_defined_layout = comptime_field_ptr.field_ty, + }; + }, + .opt_payload_ptr, .eu_payload_ptr, => blk: { diff --git a/test/cases/compile_errors/invalid_store_to_comptime_field.zig b/test/cases/compile_errors/invalid_store_to_comptime_field.zig index 7fdb08facb..6c528e0799 100644 --- a/test/cases/compile_errors/invalid_store_to_comptime_field.zig +++ b/test/cases/compile_errors/invalid_store_to_comptime_field.zig @@ -40,6 +40,10 @@ pub export fn entry4() void { }; _ = U.foo(.{ .foo = 2, .bar = 2 }); } +pub export fn entry5() void { + comptime var y = .{ 1, 2}; + y = .{ 3, 4 }; +} // pub export fn entry5() void { // var x: u32 = 15; // const T = @TypeOf(.{ @as(i32, -1234), @as(u32, 5678), x }); @@ -60,3 +64,4 @@ pub export fn entry4() void { // :31:19: error: value stored in comptime field does not match the default value of the field // :25:29: note: default value set here // :41:16: error: value stored in comptime field does not match the default value of the field +// :45:12: error: value stored in comptime field does not match the default value of the field From 3d18c8c1300986541bc81d60e81fd702d4417629 Mon Sep 17 00:00:00 2001 From: Veikka Tuominen Date: Tue, 26 Jul 2022 13:30:20 +0300 Subject: [PATCH 2/5] Sema: resolve lazy values for compile log Close #12204 --- src/Sema.zig | 5 +++++ test/cases/compile_errors/compile_log.zig | 5 +++++ 2 files changed, 10 insertions(+) diff --git a/src/Sema.zig b/src/Sema.zig index 57de32396d..52e4b4fac4 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -4508,6 +4508,7 @@ fn zirCompileLog( const arg = try sema.resolveInst(arg_ref); const arg_ty = sema.typeOf(arg); if (try sema.resolveMaybeUndefVal(block, src, arg)) |val| { + try sema.resolveLazyValue(block, src, val); try writer.print("@as({}, {})", .{ arg_ty.fmt(sema.mod), val.fmtValue(arg_ty, sema.mod), }); @@ -25440,6 +25441,10 @@ fn resolveLazyValue( const ty = val.castTag(.lazy_align).?.data; return sema.resolveTypeLayout(block, src, ty); }, + .lazy_size => { + const ty = val.castTag(.lazy_size).?.data; + return sema.resolveTypeLayout(block, src, ty); + }, else => return, } } diff --git a/test/cases/compile_errors/compile_log.zig b/test/cases/compile_errors/compile_log.zig index 281f8747d2..772853b023 100644 --- a/test/cases/compile_errors/compile_log.zig +++ b/test/cases/compile_errors/compile_log.zig @@ -6,9 +6,14 @@ fn bar(a: i32, b: []const u8) void { @compileLog("a", a, "b", b); @compileLog("end",); } +export fn baz() void { + const S = struct { a: u32 }; + @compileLog(@sizeOf(S)); +} // error // backend=llvm // target=native // // :5:5: error: found compile log statement +// :11:5: note: also here From 5d99e5ecd493b6cec54cf870d77d61b2a8480131 Mon Sep 17 00:00:00 2001 From: Veikka Tuominen Date: Tue, 26 Jul 2022 14:04:59 +0300 Subject: [PATCH 3/5] Sema: improve expression value ignored error Closes #4483 --- src/Sema.zig | 11 ++++++++++- .../ignored_assert-err-ok_return_value.zig | 4 +++- .../ignored_comptime_statement_value.zig | 4 +++- test/cases/compile_errors/ignored_comptime_value.zig | 4 +++- .../ignored_deferred_statement_value.zig | 4 +++- test/cases/compile_errors/ignored_return_value.zig | 4 +++- test/cases/compile_errors/ignored_statement_value.zig | 4 +++- 7 files changed, 28 insertions(+), 7 deletions(-) diff --git a/src/Sema.zig b/src/Sema.zig index 52e4b4fac4..5189ad818c 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -2869,7 +2869,16 @@ fn ensureResultUsed( }; return sema.failWithOwnedErrorMsg(block, msg); }, - else => return sema.fail(block, src, "expression value is ignored", .{}), + else => { + const msg = msg: { + const msg = try sema.errMsg(block, src, "value of type '{}' ignored", .{operand_ty.fmt(sema.mod)}); + errdefer msg.destroy(sema.gpa); + try sema.errNote(block, src, msg, "all non-void values must be used", .{}); + try sema.errNote(block, src, msg, "this error can be suppressed by assigning the value to '_'", .{}); + break :msg msg; + }; + return sema.failWithOwnedErrorMsg(block, msg); + }, } } diff --git a/test/cases/compile_errors/ignored_assert-err-ok_return_value.zig b/test/cases/compile_errors/ignored_assert-err-ok_return_value.zig index 04f6b3bd49..39657badd4 100644 --- a/test/cases/compile_errors/ignored_assert-err-ok_return_value.zig +++ b/test/cases/compile_errors/ignored_assert-err-ok_return_value.zig @@ -7,4 +7,6 @@ fn bar() anyerror!i32 { return 0; } // backend=stage2 // target=native // -// :2:11: error: expression value is ignored +// :2:11: error: value of type 'i32' ignored +// :2:11: note: all non-void values must be used +// :2:11: note: this error can be suppressed by assigning the value to '_' diff --git a/test/cases/compile_errors/ignored_comptime_statement_value.zig b/test/cases/compile_errors/ignored_comptime_statement_value.zig index 7a5258fb1d..fc6cdfdd28 100644 --- a/test/cases/compile_errors/ignored_comptime_statement_value.zig +++ b/test/cases/compile_errors/ignored_comptime_statement_value.zig @@ -6,4 +6,6 @@ export fn foo() void { // backend=stage2 // target=native // -// :2:15: error: expression value is ignored +// :2:15: error: value of type 'comptime_int' ignored +// :2:15: note: all non-void values must be used +// :2:15: note: this error can be suppressed by assigning the value to '_' diff --git a/test/cases/compile_errors/ignored_comptime_value.zig b/test/cases/compile_errors/ignored_comptime_value.zig index 6f207653d6..2f7c6edea3 100644 --- a/test/cases/compile_errors/ignored_comptime_value.zig +++ b/test/cases/compile_errors/ignored_comptime_value.zig @@ -6,4 +6,6 @@ export fn foo() void { // backend=stage2 // target=native // -// :2:5: error: expression value is ignored +// :2:5: error: value of type 'comptime_int' ignored +// :2:5: note: all non-void values must be used +// :2:5: note: this error can be suppressed by assigning the value to '_' diff --git a/test/cases/compile_errors/ignored_deferred_statement_value.zig b/test/cases/compile_errors/ignored_deferred_statement_value.zig index 6af541236a..9a270497af 100644 --- a/test/cases/compile_errors/ignored_deferred_statement_value.zig +++ b/test/cases/compile_errors/ignored_deferred_statement_value.zig @@ -6,4 +6,6 @@ export fn foo() void { // backend=stage2 // target=native // -// :2:12: error: expression value is ignored +// :2:12: error: value of type 'comptime_int' ignored +// :2:12: note: all non-void values must be used +// :2:12: note: this error can be suppressed by assigning the value to '_' diff --git a/test/cases/compile_errors/ignored_return_value.zig b/test/cases/compile_errors/ignored_return_value.zig index ac3756acf5..57f859e3d3 100644 --- a/test/cases/compile_errors/ignored_return_value.zig +++ b/test/cases/compile_errors/ignored_return_value.zig @@ -7,4 +7,6 @@ fn bar() i32 { return 0; } // backend=stage2 // target=native // -// :2:8: error: expression value is ignored +// :2:8: error: value of type 'i32' ignored +// :2:8: note: all non-void values must be used +// :2:8: note: this error can be suppressed by assigning the value to '_' diff --git a/test/cases/compile_errors/ignored_statement_value.zig b/test/cases/compile_errors/ignored_statement_value.zig index 5c79d1f964..c73da84420 100644 --- a/test/cases/compile_errors/ignored_statement_value.zig +++ b/test/cases/compile_errors/ignored_statement_value.zig @@ -6,4 +6,6 @@ export fn foo() void { // backend=stage2 // target=native // -// :2:5: error: expression value is ignored +// :2:5: error: value of type 'comptime_int' ignored +// :2:5: note: all non-void values must be used +// :2:5: note: this error can be suppressed by assigning the value to '_' From 7862ab9f410d20d0cfe799bf025f8cf57dd6f15a Mon Sep 17 00:00:00 2001 From: Veikka Tuominen Date: Tue, 26 Jul 2022 14:08:37 +0300 Subject: [PATCH 4/5] Sema: disable "unreachable else prong" error for error sets for now Closes #11798 --- src/Sema.zig | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/Sema.zig b/src/Sema.zig index 5189ad818c..72278f550c 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -8916,6 +8916,10 @@ fn zirSwitchBlock(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError if (special_prong == .@"else" and seen_errors.count() == operand_ty.errorSetNames().len) { + // TODO re-enable if defer implementation is improved + // https://github.com/ziglang/zig/issues/11798 + if (true) break :else_validation; + // In order to enable common patterns for generic code allow simple else bodies // else => unreachable, // else => return, From d6e3988fe846864a33adf9f5f04d800718b31392 Mon Sep 17 00:00:00 2001 From: Veikka Tuominen Date: Tue, 26 Jul 2022 15:39:47 +0300 Subject: [PATCH 5/5] Sema: better error when coercing error sets --- src/Sema.zig | 18 +++++++++++------ ...gnostic_string_for_top_level_decl_type.zig | 11 ++++++++++ .../nested_error_set_mismatch.zig | 19 ++++++++++++++++++ .../return_invalid_type_from_test.zig | 2 +- ...gnostic_string_for_top_level_decl_type.zig | 10 ---------- .../stage1/obj/nested_error_set_mismatch.zig | 20 ------------------- .../std.fmt_error_for_unused_arguments.zig | 4 ++-- .../obj => }/wrong_number_of_arguments.zig | 4 ++-- ..._given_to_atomic_order_args_in_cmpxchg.zig | 5 +++-- .../obj => }/wrong_types_given_to_export.zig | 5 +++-- 10 files changed, 53 insertions(+), 45 deletions(-) create mode 100644 test/cases/compile_errors/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig create mode 100644 test/cases/compile_errors/nested_error_set_mismatch.zig delete mode 100644 test/cases/compile_errors/stage1/obj/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig delete mode 100644 test/cases/compile_errors/stage1/obj/nested_error_set_mismatch.zig rename test/cases/compile_errors/{stage1/obj => }/std.fmt_error_for_unused_arguments.zig (65%) rename test/cases/compile_errors/{stage1/obj => }/wrong_number_of_arguments.zig (62%) rename test/cases/compile_errors/{stage1/obj => }/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig (57%) rename test/cases/compile_errors/{stage1/obj => }/wrong_types_given_to_export.zig (54%) diff --git a/src/Sema.zig b/src/Sema.zig index 72278f550c..ed4ed82a0c 100644 --- a/src/Sema.zig +++ b/src/Sema.zig @@ -5496,7 +5496,7 @@ fn analyzeCall( // TODO add error note: declared here return sema.fail( block, - func_src, + call_src, "expected {d} argument(s), found {d}", .{ fn_params_len, uncasted_args.len }, ); @@ -21275,7 +21275,7 @@ fn coerceExtra( else => {}, }, .ErrorUnion => switch (inst_ty.zigTypeTag()) { - .ErrorUnion => { + .ErrorUnion => eu: { if (maybe_inst_val) |inst_val| { switch (inst_val.tag()) { .undef => return sema.addConstUndef(dest_ty), @@ -21284,7 +21284,10 @@ fn coerceExtra( inst_ty.errorUnionPayload(), inst_val.castTag(.eu_payload).?.data, ); - return sema.wrapErrorUnionPayload(block, dest_ty, payload, inst_src); + return sema.wrapErrorUnionPayload(block, dest_ty, payload, inst_src) catch |err| switch (err) { + error.NotCoercible => break :eu, + else => |e| return e, + }; }, else => { const error_set = try sema.addConstant( @@ -21303,9 +21306,12 @@ fn coerceExtra( .Undefined => { return sema.addConstUndef(dest_ty); }, - else => { + else => eu: { // T to E!T - return sema.wrapErrorUnionPayload(block, dest_ty, inst, inst_src); + return sema.wrapErrorUnionPayload(block, dest_ty, inst, inst_src) catch |err| switch (err) { + error.NotCoercible => break :eu, + else => |e| return e, + }; }, }, .Union => switch (inst_ty.zigTypeTag()) { @@ -24795,7 +24801,7 @@ fn wrapErrorUnionPayload( inst_src: LazySrcLoc, ) !Air.Inst.Ref { const dest_payload_ty = dest_ty.errorUnionPayload(); - const coerced = try sema.coerce(block, dest_payload_ty, inst, inst_src); + const coerced = try sema.coerceExtra(block, dest_payload_ty, inst, inst_src, false, false); if (try sema.resolveMaybeUndefVal(block, inst_src, coerced)) |val| { return sema.addConstant(dest_ty, try Value.Tag.eu_payload.create(sema.arena, val)); } diff --git a/test/cases/compile_errors/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig b/test/cases/compile_errors/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig new file mode 100644 index 0000000000..9ae320650a --- /dev/null +++ b/test/cases/compile_errors/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig @@ -0,0 +1,11 @@ +export fn entry() void { + var foo: u32 = @This(){}; + _ = foo; +} + +// error +// backend=stage2 +// target=native +// +// :2:27: error: expected type 'u32', found 'tmp.tmp' +// :1:1: note: struct declared here diff --git a/test/cases/compile_errors/nested_error_set_mismatch.zig b/test/cases/compile_errors/nested_error_set_mismatch.zig new file mode 100644 index 0000000000..c0d68a5e53 --- /dev/null +++ b/test/cases/compile_errors/nested_error_set_mismatch.zig @@ -0,0 +1,19 @@ +const NextError = error{NextError}; +const OtherError = error{OutOfMemory}; + +export fn entry() void { + const a: ?NextError!i32 = foo(); + _ = a; +} + +fn foo() ?OtherError!i32 { + return null; +} + +// error +// backend=llvm +// target=native +// +// :4:1: error: expected type '?error{NextError}!i32', found '?error{OutOfMemory}!i32' +// :4:1: note: optional type child 'error{OutOfMemory}!i32' cannot cast into optional type child 'error{NextError}!i32' +// :4:1: note: 'error.OutOfMemory' not a member of destination error set diff --git a/test/cases/compile_errors/return_invalid_type_from_test.zig b/test/cases/compile_errors/return_invalid_type_from_test.zig index 6cad6af85f..a954bd7ee5 100644 --- a/test/cases/compile_errors/return_invalid_type_from_test.zig +++ b/test/cases/compile_errors/return_invalid_type_from_test.zig @@ -5,4 +5,4 @@ test "example" { return 1; } // target=native // is_test=1 // -// :1:25: error: expected type 'void', found 'comptime_int' +// :1:25: error: expected type '@typeInfo(@typeInfo(@TypeOf(tmp.test.example)).Fn.return_type.?).ErrorUnion.error_set!void', found 'comptime_int' \ No newline at end of file diff --git a/test/cases/compile_errors/stage1/obj/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig b/test/cases/compile_errors/stage1/obj/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig deleted file mode 100644 index c742cb9b77..0000000000 --- a/test/cases/compile_errors/stage1/obj/issue_2032_compile_diagnostic_string_for_top_level_decl_type.zig +++ /dev/null @@ -1,10 +0,0 @@ -export fn entry() void { - var foo: u32 = @This(){}; - _ = foo; -} - -// error -// backend=stage1 -// target=native -// -// tmp.zig:2:27: error: type 'u32' does not support array initialization diff --git a/test/cases/compile_errors/stage1/obj/nested_error_set_mismatch.zig b/test/cases/compile_errors/stage1/obj/nested_error_set_mismatch.zig deleted file mode 100644 index cd037635bc..0000000000 --- a/test/cases/compile_errors/stage1/obj/nested_error_set_mismatch.zig +++ /dev/null @@ -1,20 +0,0 @@ -const NextError = error{NextError}; -const OtherError = error{OutOfMemory}; - -export fn entry() void { - const a: ?NextError!i32 = foo(); - _ = a; -} - -fn foo() ?OtherError!i32 { - return null; -} - -// error -// backend=stage1 -// target=native -// -// tmp.zig:5:34: error: expected type '?NextError!i32', found '?OtherError!i32' -// tmp.zig:5:34: note: optional type child 'OtherError!i32' cannot cast into optional type child 'NextError!i32' -// tmp.zig:5:34: note: error set 'OtherError' cannot cast into error set 'NextError' -// tmp.zig:2:26: note: 'error.OutOfMemory' not a member of destination error set diff --git a/test/cases/compile_errors/stage1/obj/std.fmt_error_for_unused_arguments.zig b/test/cases/compile_errors/std.fmt_error_for_unused_arguments.zig similarity index 65% rename from test/cases/compile_errors/stage1/obj/std.fmt_error_for_unused_arguments.zig rename to test/cases/compile_errors/std.fmt_error_for_unused_arguments.zig index 21603ab3d3..a20f2798bc 100644 --- a/test/cases/compile_errors/stage1/obj/std.fmt_error_for_unused_arguments.zig +++ b/test/cases/compile_errors/std.fmt_error_for_unused_arguments.zig @@ -3,7 +3,7 @@ export fn entry() void { } // error -// backend=stage1 +// backend=llvm // target=native // -// ?:?:?: error: 10 unused arguments in '{d} {d} {d} {d} {d}' +// :?:?: error: 10 unused arguments in '{d} {d} {d} {d} {d}' diff --git a/test/cases/compile_errors/stage1/obj/wrong_number_of_arguments.zig b/test/cases/compile_errors/wrong_number_of_arguments.zig similarity index 62% rename from test/cases/compile_errors/stage1/obj/wrong_number_of_arguments.zig rename to test/cases/compile_errors/wrong_number_of_arguments.zig index f25c9dae08..64eb11650a 100644 --- a/test/cases/compile_errors/stage1/obj/wrong_number_of_arguments.zig +++ b/test/cases/compile_errors/wrong_number_of_arguments.zig @@ -4,7 +4,7 @@ export fn a() void { fn c(d: i32, e: i32, f: i32) void { _ = d; _ = e; _ = f; } // error -// backend=stage1 +// backend=stage2 // target=native // -// tmp.zig:2:6: error: expected 3 argument(s), found 1 +// :2:6: error: expected 3 argument(s), found 1 diff --git a/test/cases/compile_errors/stage1/obj/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig b/test/cases/compile_errors/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig similarity index 57% rename from test/cases/compile_errors/stage1/obj/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig rename to test/cases/compile_errors/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig index b0f484e2fd..f3a4676eb3 100644 --- a/test/cases/compile_errors/stage1/obj/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig +++ b/test/cases/compile_errors/wrong_types_given_to_atomic_order_args_in_cmpxchg.zig @@ -4,7 +4,8 @@ export fn entry() void { } // error -// backend=stage1 +// backend=stage2 // target=native // -// tmp.zig:3:47: error: expected type 'std.builtin.AtomicOrder', found 'u32' +// :3:47: error: expected type 'builtin.AtomicOrder', found 'u32' +// :?:?: note: enum declared here diff --git a/test/cases/compile_errors/stage1/obj/wrong_types_given_to_export.zig b/test/cases/compile_errors/wrong_types_given_to_export.zig similarity index 54% rename from test/cases/compile_errors/stage1/obj/wrong_types_given_to_export.zig rename to test/cases/compile_errors/wrong_types_given_to_export.zig index c06116204f..2ae55b4a63 100644 --- a/test/cases/compile_errors/stage1/obj/wrong_types_given_to_export.zig +++ b/test/cases/compile_errors/wrong_types_given_to_export.zig @@ -4,7 +4,8 @@ comptime { } // error -// backend=stage1 +// backend=stage2 // target=native // -// tmp.zig:3:59: error: expected type 'std.builtin.GlobalLinkage', found 'comptime_int' +// :3:50: error: expected type 'builtin.GlobalLinkage', found 'u32' +// :?:?: note: enum declared here