| author | |
| committer | |
| log | 89b1dafa7808d22eab78ea486f158f794da46a2c |
| tree | 7f743c2d4604f622d6c6da6f29254dc98cd61eb2 |
| parent | 28dda3bf898cc338eb0040f3f21799eda1e25be0 |
| signature | Signed by SSH key SHA256:CQ99aPxq+RueiL9u7z0FEki5Fm7V6T8q4PrEGmINrA4 |
3 files changed, 42 insertions(+), 14 deletions(-)
src/codegen/spirv.zig+42-3| ... | @@ -2725,6 +2725,7 @@ const DeclGen = struct { | ... | @@ -2725,6 +2725,7 @@ const DeclGen = struct { |
| 2725 | if (self.liveness.isUnused(inst)) return null; | 2725 | if (self.liveness.isUnused(inst)) return null; |
| 2726 | 2726 | ||
| 2727 | const mod = self.module; | 2727 | const mod = self.module; |
| 2728 | const ip = &mod.intern_pool; | ||
| 2728 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; | 2729 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 2729 | const result_ty = self.typeOfIndex(inst); | 2730 | const result_ty = self.typeOfIndex(inst); |
| 2730 | const result_ty_ref = try self.resolveType(result_ty, .direct); | 2731 | const result_ty_ref = try self.resolveType(result_ty, .direct); |
| ... | @@ -2733,15 +2734,53 @@ const DeclGen = struct { | ... | @@ -2733,15 +2734,53 @@ const DeclGen = struct { |
| 2733 | 2734 | ||
| 2734 | switch (result_ty.zigTypeTag(mod)) { | 2735 | switch (result_ty.zigTypeTag(mod)) { |
| 2735 | .Vector => unreachable, // TODO | 2736 | .Vector => unreachable, // TODO |
| 2736 | .Struct => unreachable, // TODO | 2737 | .Struct => { |
| 2738 | if (mod.typeToPackedStruct(result_ty)) |struct_type| { | ||
| 2739 | _ = struct_type; | ||
| 2740 | unreachable; // TODO | ||
| 2741 | } | ||
| 2742 | |||
| 2743 | const constituents = try self.gpa.alloc(IdRef, elements.len); | ||
| 2744 | defer self.gpa.free(constituents); | ||
| 2745 | var index: usize = 0; | ||
| 2746 | |||
| 2747 | switch (ip.indexToKey(result_ty.toIntern())) { | ||
| 2748 | .anon_struct_type => |tuple| { | ||
| 2749 | for (tuple.types.get(ip), elements, 0..) |field_ty, element, i| { | ||
| 2750 | if ((try result_ty.structFieldValueComptime(mod, i)) != null) continue; | ||
| 2751 | assert(field_ty.toType().hasRuntimeBits(mod)); | ||
| 2752 | |||
| 2753 | const id = try self.resolve(element); | ||
| 2754 | constituents[index] = try self.convertToIndirect(field_ty.toType(), id); | ||
| 2755 | index += 1; | ||
| 2756 | } | ||
| 2757 | }, | ||
| 2758 | .struct_type => |struct_type| { | ||
| 2759 | var it = struct_type.iterateRuntimeOrder(ip); | ||
| 2760 | for (elements, 0..) |element, i| { | ||
| 2761 | const field_index = it.next().?; | ||
| 2762 | if ((try result_ty.structFieldValueComptime(mod, i)) != null) continue; | ||
| 2763 | const field_ty = struct_type.field_types.get(ip)[field_index].toType(); | ||
| 2764 | assert(field_ty.hasRuntimeBitsIgnoreComptime(mod)); | ||
| 2765 | |||
| 2766 | const id = try self.resolve(element); | ||
| 2767 | constituents[index] = try self.convertToIndirect(field_ty, id); | ||
| 2768 | index += 1; | ||
| 2769 | } | ||
| 2770 | }, | ||
| 2771 | else => unreachable, | ||
| 2772 | } | ||
| 2773 | |||
| 2774 | return try self.constructStruct(result_ty_ref, constituents[0..index]); | ||
| 2775 | }, | ||
| 2737 | .Array => { | 2776 | .Array => { |
| 2738 | const array_info = result_ty.arrayInfo(mod); | 2777 | const array_info = result_ty.arrayInfo(mod); |
| 2739 | const n_elems: usize = @intCast(result_ty.arrayLenIncludingSentinel(mod)); | 2778 | const n_elems: usize = @intCast(result_ty.arrayLenIncludingSentinel(mod)); |
| 2740 | const elem_ids = try self.gpa.alloc(IdRef, n_elems); | 2779 | const elem_ids = try self.gpa.alloc(IdRef, n_elems); |
| 2741 | defer self.gpa.free(elem_ids); | 2780 | defer self.gpa.free(elem_ids); |
| 2742 | 2781 | ||
| 2743 | for (elements, 0..) |elem_inst, i| { | 2782 | for (elements, 0..) |element, i| { |
| 2744 | const id = try self.resolve(elem_inst); | 2783 | const id = try self.resolve(element); |
| 2745 | elem_ids[i] = try self.convertToIndirect(array_info.elem_type, id); | 2784 | elem_ids[i] = try self.convertToIndirect(array_info.elem_type, id); |
| 2746 | } | 2785 | } |
| 2747 | 2786 |
test/behavior/basic.zig-5| ... | @@ -357,8 +357,6 @@ fn f2(x: bool) []const u8 { | ... | @@ -357,8 +357,6 @@ fn f2(x: bool) []const u8 { |
| 357 | } | 357 | } |
| 358 | 358 | ||
| 359 | test "variable is allowed to be a pointer to an opaque type" { | 359 | test "variable is allowed to be a pointer to an opaque type" { |
| 360 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 361 | |||
| 362 | var x: i32 = 1234; | 360 | var x: i32 = 1234; |
| 363 | _ = hereIsAnOpaqueType(@as(*OpaqueA, @ptrCast(&x))); | 361 | _ = hereIsAnOpaqueType(@as(*OpaqueA, @ptrCast(&x))); |
| 364 | } | 362 | } |
| ... | @@ -397,7 +395,6 @@ test "array 2D const double ptr" { | ... | @@ -397,7 +395,6 @@ test "array 2D const double ptr" { |
| 397 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; | 395 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; |
| 398 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 396 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 399 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; | 397 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; |
| 400 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 401 | 398 | ||
| 402 | const rect_2d_vertexes = [_][1]f32{ | 399 | const rect_2d_vertexes = [_][1]f32{ |
| 403 | [_]f32{1.0}, | 400 | [_]f32{1.0}, |
| ... | @@ -410,7 +407,6 @@ test "array 2D const double ptr with offset" { | ... | @@ -410,7 +407,6 @@ test "array 2D const double ptr with offset" { |
| 410 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; | 407 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; |
| 411 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 408 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 412 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; | 409 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; |
| 413 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 414 | 410 | ||
| 415 | const rect_2d_vertexes = [_][2]f32{ | 411 | const rect_2d_vertexes = [_][2]f32{ |
| 416 | [_]f32{ 3.0, 4.239 }, | 412 | [_]f32{ 3.0, 4.239 }, |
| ... | @@ -423,7 +419,6 @@ test "array 3D const double ptr with offset" { | ... | @@ -423,7 +419,6 @@ test "array 3D const double ptr with offset" { |
| 423 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; | 419 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; |
| 424 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 420 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 425 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; | 421 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; |
| 426 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 427 | 422 | ||
| 428 | const rect_3d_vertexes = [_][2][2]f32{ | 423 | const rect_3d_vertexes = [_][2][2]f32{ |
| 429 | [_][2]f32{ | 424 | [_][2]f32{ |
test/behavior/struct.zig-6| ... | @@ -311,7 +311,6 @@ test "struct point to self" { | ... | @@ -311,7 +311,6 @@ test "struct point to self" { |
| 311 | test "void struct fields" { | 311 | test "void struct fields" { |
| 312 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; | 312 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; |
| 313 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 313 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 314 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 315 | 314 | ||
| 316 | const foo = VoidStructFieldsFoo{ | 315 | const foo = VoidStructFieldsFoo{ |
| 317 | .a = void{}, | 316 | .a = void{}, |
| ... | @@ -340,7 +339,6 @@ fn testReturnEmptyStructFromFn() EmptyStruct2 { | ... | @@ -340,7 +339,6 @@ fn testReturnEmptyStructFromFn() EmptyStruct2 { |
| 340 | 339 | ||
| 341 | test "pass slice of empty struct to fn" { | 340 | test "pass slice of empty struct to fn" { |
| 342 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 341 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 343 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 344 | 342 | ||
| 345 | try expect(testPassSliceOfEmptyStructToFn(&[_]EmptyStruct2{EmptyStruct2{}}) == 1); | 343 | try expect(testPassSliceOfEmptyStructToFn(&[_]EmptyStruct2{EmptyStruct2{}}) == 1); |
| 346 | } | 344 | } |
| ... | @@ -1229,7 +1227,6 @@ test "typed init through error unions and optionals" { | ... | @@ -1229,7 +1227,6 @@ test "typed init through error unions and optionals" { |
| 1229 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO | 1227 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO |
| 1230 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO | 1228 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO |
| 1231 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 1229 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 1232 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 1233 | 1230 | ||
| 1234 | const S = struct { | 1231 | const S = struct { |
| 1235 | a: u32, | 1232 | a: u32, |
| ... | @@ -1550,7 +1547,6 @@ test "no dependency loop on optional field wrapped in generic function" { | ... | @@ -1550,7 +1547,6 @@ test "no dependency loop on optional field wrapped in generic function" { |
| 1550 | test "optional field init with tuple" { | 1547 | test "optional field init with tuple" { |
| 1551 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO | 1548 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO |
| 1552 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO | 1549 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO |
| 1553 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; | ||
| 1554 | 1550 | ||
| 1555 | const S = struct { | 1551 | const S = struct { |
| 1556 | a: ?struct { b: u32 }, | 1552 | a: ?struct { b: u32 }, |
| ... | @@ -1652,7 +1648,6 @@ test "struct field pointer has correct alignment" { | ... | @@ -1652,7 +1648,6 @@ test "struct field pointer has correct alignment" { |
| 1652 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO | 1648 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO |
| 1653 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO | 1649 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO |
| 1654 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 1650 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 1655 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; // TODO | ||
| 1656 | 1651 | ||
| 1657 | const S = struct { | 1652 | const S = struct { |
| 1658 | fn doTheTest() !void { | 1653 | fn doTheTest() !void { |
| ... | @@ -1683,7 +1678,6 @@ test "extern struct field pointer has correct alignment" { | ... | @@ -1683,7 +1678,6 @@ test "extern struct field pointer has correct alignment" { |
| 1683 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO | 1678 | if (builtin.zig_backend == .stage2_arm) return error.SkipZigTest; // TODO |
| 1684 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO | 1679 | if (builtin.zig_backend == .stage2_aarch64) return error.SkipZigTest; // TODO |
| 1685 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO | 1680 | if (builtin.zig_backend == .stage2_sparc64) return error.SkipZigTest; // TODO |
| 1686 | if (builtin.zig_backend == .stage2_spirv64) return error.SkipZigTest; // TODO | ||
| 1687 | 1681 | ||
| 1688 | const S = struct { | 1682 | const S = struct { |
| 1689 | fn doTheTest() !void { | 1683 | fn doTheTest() !void { |