authorgravatar for git@vexu.euVeikka Tuominen <git@vexu.eu> 2023-02-01 21:41:02+02:00
committergravatar for git@vexu.euVeikka Tuominen <git@vexu.eu> 2023-02-02 00:31:35+02:00
log629c3108aa71f94bd26dba8d4f20c9f3a3945bd4
tree3e324f6279c895f5e09255013926c8eb7060a334
parent490addde278001694d554a9a9fe2eb8235831143

AstGen: fix orelse type coercion in call arguments

Closes #14506

2 files changed, 25 insertions(+), 1 deletions(-)

src/AstGen.zig+7-1
...@@ -8721,6 +8721,7 @@ fn callExpr(...@@ -8721,6 +8721,7 @@ fn callExpr(
8721 defer arg_block.unstack();8721 defer arg_block.unstack();
87228722
8723 // `call_inst` is reused to provide the param type.8723 // `call_inst` is reused to provide the param type.
8724 arg_block.rl_ty_inst = call_inst;
8724 const arg_ref = try expr(&arg_block, &arg_block.base, .{ .rl = .{ .coerced_ty = call_inst }, .ctx = .fn_arg }, param_node);8725 const arg_ref = try expr(&arg_block, &arg_block.base, .{ .rl = .{ .coerced_ty = call_inst }, .ctx = .fn_arg }, param_node);
8725 _ = try arg_block.addBreak(.break_inline, call_index, arg_ref);8726 _ = try arg_block.addBreak(.break_inline, call_index, arg_ref);
87268727
...@@ -10869,7 +10870,12 @@ const GenZir = struct {...@@ -10869,7 +10870,12 @@ const GenZir = struct {
10869 // we emit ZIR for the block break instructions to have the result values,10870 // we emit ZIR for the block break instructions to have the result values,
10870 // and then rvalue() on that to pass the value to the result location.10871 // and then rvalue() on that to pass the value to the result location.
10871 switch (parent_ri.rl) {10872 switch (parent_ri.rl) {
10872 .ty, .coerced_ty => |ty_inst| {10873 .coerced_ty => |ty_inst| {
10874 // Type coercion needs to happend before breaks.
10875 gz.rl_ty_inst = ty_inst;
10876 gz.break_result_info = .{ .rl = .{ .ty = ty_inst } };
10877 },
10878 .ty => |ty_inst| {
10873 gz.rl_ty_inst = ty_inst;10879 gz.rl_ty_inst = ty_inst;
10874 gz.break_result_info = parent_ri;10880 gz.break_result_info = parent_ri;
10875 },10881 },
test/behavior/basic.zig+18
...@@ -1125,3 +1125,21 @@ test "returning an opaque type from a function" {...@@ -1125,3 +1125,21 @@ test "returning an opaque type from a function" {
1125 };1125 };
1126 try expect(S.foo(123).b == 123);1126 try expect(S.foo(123).b == 123);
1127}1127}
1128
1129test "orelse coercion as function argument" {
1130 if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO
1131 if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO
1132
1133 const Loc = struct { start: i32 = -1 };
1134 const Container = struct {
1135 a: ?Loc = null,
1136 fn init(a: Loc) @This() {
1137 return .{
1138 .a = a,
1139 };
1140 }
1141 };
1142 var optional: ?Loc = .{};
1143 var foo = Container.init(optional orelse .{});
1144 try expect(foo.a.?.start == -1);
1145}