authorgravatar for mitchell.hashimoto@gmail.comMitchell Hashimoto <mitchell.hashimoto@gmail.com> 2022-02-25 13:33:11-08:00
committergravatar for mitchell.hashimoto@gmail.comMitchell Hashimoto <mitchell.hashimoto@gmail.com> 2022-02-25 13:33:11-08:00
log101918198260482d98f6690f0ce3b1fb77a30595
tree6399c1745a033a5805d0386df4946416aa75ddf8
parent117ef22d3cb86858632d84699e19a90c24745d89
signature Commit is signed but in an unrecognized format.

stage2: *[N]T and E![]T


2 files changed, 32 insertions(+), 12 deletions(-)

src/Sema.zig+30-2
...@@ -17073,6 +17073,30 @@ fn resolvePeerTypes(...@@ -17073,6 +17073,30 @@ fn resolvePeerTypes(
17073 },17073 },
17074 else => {},17074 else => {},
17075 },17075 },
17076 .ErrorUnion => {
17077 const payload_ty = candidate_ty.errorUnionPayload();
17078 if (chosen_ty_tag == .Pointer and
17079 chosen_ty.ptrSize() == .One and
17080 chosen_ty.childType().zigTypeTag() == .Array and
17081 payload_ty.isSlice())
17082 {
17083 const chosen_child_ty = chosen_ty.childType();
17084 const chosen_elem_ty = chosen_child_ty.elemType2();
17085 const candidate_elem_ty = payload_ty.elemType2();
17086 if ((try sema.coerceInMemoryAllowed(block, candidate_elem_ty, chosen_elem_ty, false, target, src, src)) == .ok) {
17087 chosen = candidate;
17088 chosen_i = candidate_i + 1;
17089
17090 convert_to_slice = false; // it already is a slice
17091
17092 // If the prev pointer is const then we need to const
17093 if (chosen_child_ty.isConstPtr())
17094 make_the_slice_const = true;
17095
17096 continue;
17097 }
17098 }
17099 },
17076 .Pointer => {17100 .Pointer => {
17077 if (candidate_ty.ptrSize() == .C) {17101 if (candidate_ty.ptrSize() == .C) {
17078 if (chosen_ty_tag == .Int or chosen_ty_tag == .ComptimeInt) {17102 if (chosen_ty_tag == .Int or chosen_ty_tag == .ComptimeInt) {
...@@ -17086,11 +17110,15 @@ fn resolvePeerTypes(...@@ -17086,11 +17110,15 @@ fn resolvePeerTypes(
17086 }17110 }
1708717111
17088 // *[N]T to []T (prev is slice)17112 // *[N]T to []T (prev is slice)
17089 if (chosen_ty.isSlice() and17113 // *[N]T to E![]T
17114 if ((chosen_ty.isSlice() or (chosen_ty_tag == .ErrorUnion and chosen_ty.errorUnionPayload().isSlice())) and
17090 candidate_ty.ptrSize() == .One and17115 candidate_ty.ptrSize() == .One and
17091 candidate_ty.childType().zigTypeTag() == .Array)17116 candidate_ty.childType().zigTypeTag() == .Array)
17092 {17117 {
17093 const chosen_elem_ty = chosen_ty.elemType2();17118 const chosen_elem_ty = switch (chosen_ty_tag) {
17119 .ErrorUnion => chosen_ty.errorUnionPayload().elemType2(),
17120 else => chosen_ty.elemType2(),
17121 };
17094 const candidate_elem_ty = candidate_ty.childType().elemType2();17122 const candidate_elem_ty = candidate_ty.childType().elemType2();
17095 if ((try sema.coerceInMemoryAllowed(block, candidate_elem_ty, chosen_elem_ty, false, target, src, src)) == .ok) {17123 if ((try sema.coerceInMemoryAllowed(block, candidate_elem_ty, chosen_elem_ty, false, target, src, src)) == .ok) {
17096 convert_to_slice = false; // it already is a slice17124 convert_to_slice = false; // it already is a slice
test/behavior/cast.zig+2-10
...@@ -358,8 +358,6 @@ fn testCastIntToErr(err: anyerror) !void {...@@ -358,8 +358,6 @@ fn testCastIntToErr(err: anyerror) !void {
358}358}
359359
360test "peer resolve array and const slice" {360test "peer resolve array and const slice" {
361 if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
362
363 try testPeerResolveArrayConstSlice(true);361 try testPeerResolveArrayConstSlice(true);
364 comptime try testPeerResolveArrayConstSlice(true);362 comptime try testPeerResolveArrayConstSlice(true);
365}363}
...@@ -492,8 +490,6 @@ fn testPeerErrorAndArray2(x: u8) anyerror![]const u8 {...@@ -492,8 +490,6 @@ fn testPeerErrorAndArray2(x: u8) anyerror![]const u8 {
492}490}
493491
494test "single-item pointer of array to slice to unknown length pointer" {492test "single-item pointer of array to slice to unknown length pointer" {
495 if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
496
497 try testCastPtrOfArrayToSliceAndPtr();493 try testCastPtrOfArrayToSliceAndPtr();
498 comptime try testCastPtrOfArrayToSliceAndPtr();494 comptime try testCastPtrOfArrayToSliceAndPtr();
499}495}
...@@ -607,18 +603,16 @@ test "peer type resolution: unreachable, error set, unreachable" {...@@ -607,18 +603,16 @@ test "peer type resolution: unreachable, error set, unreachable" {
607}603}
608604
609test "peer cast *[0]T to E![]const T" {605test "peer cast *[0]T to E![]const T" {
610 if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
611
612 var buffer: [5]u8 = "abcde".*;606 var buffer: [5]u8 = "abcde".*;
613 var buf: anyerror![]const u8 = buffer[0..];607 var buf: anyerror![]const u8 = buffer[0..];
614 var b = false;608 var b = false;
615 var y = if (b) &[0]u8{} else buf;609 var y = if (b) &[0]u8{} else buf;
610 var z = if (!b) buf else &[0]u8{};
616 try expect(mem.eql(u8, "abcde", y catch unreachable));611 try expect(mem.eql(u8, "abcde", y catch unreachable));
612 try expect(mem.eql(u8, "abcde", z catch unreachable));
617}613}
618614
619test "peer cast *[0]T to []const T" {615test "peer cast *[0]T to []const T" {
620 if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
621
622 var buffer: [5]u8 = "abcde".*;616 var buffer: [5]u8 = "abcde".*;
623 var buf: []const u8 = buffer[0..];617 var buf: []const u8 = buffer[0..];
624 var b = false;618 var b = false;
...@@ -744,8 +738,6 @@ test "peer type resolution implicit cast to variable type" {...@@ -744,8 +738,6 @@ test "peer type resolution implicit cast to variable type" {
744}738}
745739
746test "variable initialization uses result locations properly with regards to the type" {740test "variable initialization uses result locations properly with regards to the type" {
747 if (builtin.zig_backend != .stage1) return error.SkipZigTest; // TODO
748
749 var b = true;741 var b = true;
750 const x: i32 = if (b) 1 else 2;742 const x: i32 = if (b) 1 else 2;
751 try expect(x == 1);743 try expect(x == 1);