| author | |
| committer | |
| log | 5e636643d2a36c777a607b65cfd1abbb1822ad1e |
| tree | 500ec74bd5cc60bb8a4db95ab5f5e90fcfb222aa |
| parent | 9d422bff18dbb92d3a6b8705c3dae7404a34bba6 |
Notably, `vector`.
Additionally, all alternate encodings of `pointer`, `optional`, and
`array`.25 files changed, 1834 insertions(+), 2771 deletions(-)
src/Air.zig+8-5| ... | ... | @@ -1375,7 +1375,7 @@ pub fn typeOfIndex(air: Air, inst: Air.Inst.Index, ip: InternPool) Type { |
| 1375 | 1375 | |
| 1376 | 1376 | .bool_to_int => return Type.u1, |
| 1377 | 1377 | |
| 1378 | .tag_name, .error_name => return Type.initTag(.const_slice_u8_sentinel_0), | |
| 1378 | .tag_name, .error_name => return Type.const_slice_u8_sentinel_0, | |
| 1379 | 1379 | |
| 1380 | 1380 | .call, .call_always_tail, .call_never_tail, .call_never_inline => { |
| 1381 | 1381 | const callee_ty = air.typeOf(datas[inst].pl_op.operand, ip); |
| ... | ... | @@ -1384,18 +1384,21 @@ pub fn typeOfIndex(air: Air, inst: Air.Inst.Index, ip: InternPool) Type { |
| 1384 | 1384 | |
| 1385 | 1385 | .slice_elem_val, .ptr_elem_val, .array_elem_val => { |
| 1386 | 1386 | const ptr_ty = air.typeOf(datas[inst].bin_op.lhs, ip); |
| 1387 | return ptr_ty.elemType(); | |
| 1387 | return ptr_ty.childTypeIp(ip); | |
| 1388 | 1388 | }, |
| 1389 | 1389 | .atomic_load => { |
| 1390 | 1390 | const ptr_ty = air.typeOf(datas[inst].atomic_load.ptr, ip); |
| 1391 | return ptr_ty.elemType(); | |
| 1391 | return ptr_ty.childTypeIp(ip); | |
| 1392 | 1392 | }, |
| 1393 | 1393 | .atomic_rmw => { |
| 1394 | 1394 | const ptr_ty = air.typeOf(datas[inst].pl_op.operand, ip); |
| 1395 | return ptr_ty.elemType(); | |
| 1395 | return ptr_ty.childTypeIp(ip); | |
| 1396 | 1396 | }, |
| 1397 | 1397 | |
| 1398 | .reduce, .reduce_optimized => return air.typeOf(datas[inst].reduce.operand, ip).childType(), | |
| 1398 | .reduce, .reduce_optimized => { | |
| 1399 | const operand_ty = air.typeOf(datas[inst].reduce.operand, ip); | |
| 1400 | return ip.indexToKey(operand_ty.ip_index).vector_type.child.toType(); | |
| 1401 | }, | |
| 1399 | 1402 | |
| 1400 | 1403 | .mul_add => return air.typeOf(datas[inst].pl_op.operand, ip), |
| 1401 | 1404 | .select => { |
src/InternPool.zig+63-29| ... | ... | @@ -31,28 +31,10 @@ const KeyAdapter = struct { |
| 31 | 31 | |
| 32 | 32 | pub const Key = union(enum) { |
| 33 | 33 | int_type: IntType, |
| 34 | ptr_type: struct { | |
| 35 | elem_type: Index, | |
| 36 | sentinel: Index = .none, | |
| 37 | alignment: u16 = 0, | |
| 38 | size: std.builtin.Type.Pointer.Size, | |
| 39 | is_const: bool = false, | |
| 40 | is_volatile: bool = false, | |
| 41 | is_allowzero: bool = false, | |
| 42 | address_space: std.builtin.AddressSpace = .generic, | |
| 43 | }, | |
| 44 | array_type: struct { | |
| 45 | len: u64, | |
| 46 | child: Index, | |
| 47 | sentinel: Index, | |
| 48 | }, | |
| 49 | vector_type: struct { | |
| 50 | len: u32, | |
| 51 | child: Index, | |
| 52 | }, | |
| 53 | optional_type: struct { | |
| 54 | payload_type: Index, | |
| 55 | }, | |
| 34 | ptr_type: PtrType, | |
| 35 | array_type: ArrayType, | |
| 36 | vector_type: VectorType, | |
| 37 | opt_type: Index, | |
| 56 | 38 | error_union_type: struct { |
| 57 | 39 | error_set_type: Index, |
| 58 | 40 | payload_type: Index, |
| ... | ... | @@ -87,6 +69,47 @@ pub const Key = union(enum) { |
| 87 | 69 | |
| 88 | 70 | pub const IntType = std.builtin.Type.Int; |
| 89 | 71 | |
| 72 | pub const PtrType = struct { | |
| 73 | elem_type: Index, | |
| 74 | sentinel: Index = .none, | |
| 75 | /// If zero use pointee_type.abiAlignment() | |
| 76 | /// When creating pointer types, if alignment is equal to pointee type | |
| 77 | /// abi alignment, this value should be set to 0 instead. | |
| 78 | alignment: u16 = 0, | |
| 79 | /// If this is non-zero it means the pointer points to a sub-byte | |
| 80 | /// range of data, which is backed by a "host integer" with this | |
| 81 | /// number of bytes. | |
| 82 | /// When host_size=pointee_abi_size and bit_offset=0, this must be | |
| 83 | /// represented with host_size=0 instead. | |
| 84 | host_size: u16 = 0, | |
| 85 | bit_offset: u16 = 0, | |
| 86 | vector_index: VectorIndex = .none, | |
| 87 | size: std.builtin.Type.Pointer.Size = .One, | |
| 88 | is_const: bool = false, | |
| 89 | is_volatile: bool = false, | |
| 90 | is_allowzero: bool = false, | |
| 91 | /// See src/target.zig defaultAddressSpace function for how to obtain | |
| 92 | /// an appropriate value for this field. | |
| 93 | address_space: std.builtin.AddressSpace = .generic, | |
| 94 | ||
| 95 | pub const VectorIndex = enum(u32) { | |
| 96 | none = std.math.maxInt(u32), | |
| 97 | runtime = std.math.maxInt(u32) - 1, | |
| 98 | _, | |
| 99 | }; | |
| 100 | }; | |
| 101 | ||
| 102 | pub const ArrayType = struct { | |
| 103 | len: u64, | |
| 104 | child: Index, | |
| 105 | sentinel: Index, | |
| 106 | }; | |
| 107 | ||
| 108 | pub const VectorType = struct { | |
| 109 | len: u32, | |
| 110 | child: Index, | |
| 111 | }; | |
| 112 | ||
| 90 | 113 | pub fn hash32(key: Key) u32 { |
| 91 | 114 | return @truncate(u32, key.hash64()); |
| 92 | 115 | } |
| ... | ... | @@ -106,7 +129,7 @@ pub const Key = union(enum) { |
| 106 | 129 | .ptr_type, |
| 107 | 130 | .array_type, |
| 108 | 131 | .vector_type, |
| 109 | .optional_type, | |
| 132 | .opt_type, | |
| 110 | 133 | .error_union_type, |
| 111 | 134 | .simple_type, |
| 112 | 135 | .simple_value, |
| ... | ... | @@ -159,8 +182,8 @@ pub const Key = union(enum) { |
| 159 | 182 | const b_info = b.vector_type; |
| 160 | 183 | return std.meta.eql(a_info, b_info); |
| 161 | 184 | }, |
| 162 | .optional_type => |a_info| { | |
| 163 | const b_info = b.optional_type; | |
| 185 | .opt_type => |a_info| { | |
| 186 | const b_info = b.opt_type; | |
| 164 | 187 | return std.meta.eql(a_info, b_info); |
| 165 | 188 | }, |
| 166 | 189 | .error_union_type => |a_info| { |
| ... | ... | @@ -220,7 +243,7 @@ pub const Key = union(enum) { |
| 220 | 243 | .ptr_type, |
| 221 | 244 | .array_type, |
| 222 | 245 | .vector_type, |
| 223 | .optional_type, | |
| 246 | .opt_type, | |
| 224 | 247 | .error_union_type, |
| 225 | 248 | .simple_type, |
| 226 | 249 | .struct_type, |
| ... | ... | @@ -630,6 +653,7 @@ pub const Tag = enum(u8) { |
| 630 | 653 | /// data is payload to Vector. |
| 631 | 654 | type_vector, |
| 632 | 655 | /// A fully explicitly specified pointer type. |
| 656 | /// TODO actually this is missing some stuff like bit_offset | |
| 633 | 657 | /// data is payload to Pointer. |
| 634 | 658 | type_pointer, |
| 635 | 659 | /// An optional type. |
| ... | ... | @@ -893,7 +917,7 @@ pub fn indexToKey(ip: InternPool, index: Index) Key { |
| 893 | 917 | } }; |
| 894 | 918 | }, |
| 895 | 919 | |
| 896 | .type_optional => .{ .optional_type = .{ .payload_type = @intToEnum(Index, data) } }, | |
| 920 | .type_optional => .{ .opt_type = @intToEnum(Index, data) }, | |
| 897 | 921 | |
| 898 | 922 | .type_error_union => @panic("TODO"), |
| 899 | 923 | .type_enum_simple => @panic("TODO"), |
| ... | ... | @@ -971,10 +995,10 @@ pub fn get(ip: *InternPool, gpa: Allocator, key: Key) Allocator.Error!Index { |
| 971 | 995 | }), |
| 972 | 996 | }); |
| 973 | 997 | }, |
| 974 | .optional_type => |optional_type| { | |
| 998 | .opt_type => |opt_type| { | |
| 975 | 999 | ip.items.appendAssumeCapacity(.{ |
| 976 | 1000 | .tag = .type_optional, |
| 977 | .data = @enumToInt(optional_type.payload_type), | |
| 1001 | .data = @enumToInt(opt_type), | |
| 978 | 1002 | }); |
| 979 | 1003 | }, |
| 980 | 1004 | .error_union_type => |error_union_type| { |
| ... | ... | @@ -1192,3 +1216,13 @@ test "basic usage" { |
| 1192 | 1216 | } }); |
| 1193 | 1217 | try std.testing.expect(another_array_i32 == array_i32); |
| 1194 | 1218 | } |
| 1219 | ||
| 1220 | pub fn childType(ip: InternPool, i: Index) Index { | |
| 1221 | return switch (ip.indexToKey(i)) { | |
| 1222 | .ptr_type => |ptr_type| ptr_type.elem_type, | |
| 1223 | .vector_type => |vector_type| vector_type.child, | |
| 1224 | .array_type => |array_type| array_type.child, | |
| 1225 | .opt_type => |child| child, | |
| 1226 | else => unreachable, | |
| 1227 | }; | |
| 1228 | } |
src/Liveness.zig+5-3| ... | ... | @@ -225,6 +225,7 @@ pub fn categorizeOperand( |
| 225 | 225 | air: Air, |
| 226 | 226 | inst: Air.Inst.Index, |
| 227 | 227 | operand: Air.Inst.Index, |
| 228 | ip: InternPool, | |
| 228 | 229 | ) OperandCategory { |
| 229 | 230 | const air_tags = air.instructions.items(.tag); |
| 230 | 231 | const air_datas = air.instructions.items(.data); |
| ... | ... | @@ -534,7 +535,7 @@ pub fn categorizeOperand( |
| 534 | 535 | .aggregate_init => { |
| 535 | 536 | const ty_pl = air_datas[inst].ty_pl; |
| 536 | 537 | const aggregate_ty = air.getRefType(ty_pl.ty); |
| 537 | const len = @intCast(usize, aggregate_ty.arrayLen()); | |
| 538 | const len = @intCast(usize, aggregate_ty.arrayLenIp(ip)); | |
| 538 | 539 | const elements = @ptrCast([]const Air.Inst.Ref, air.extra[ty_pl.payload..][0..len]); |
| 539 | 540 | |
| 540 | 541 | if (elements.len <= bpi - 1) { |
| ... | ... | @@ -625,7 +626,7 @@ pub fn categorizeOperand( |
| 625 | 626 | |
| 626 | 627 | var operand_live: bool = true; |
| 627 | 628 | for (air.extra[cond_extra.end..][0..2]) |cond_inst| { |
| 628 | if (l.categorizeOperand(air, cond_inst, operand) == .tomb) | |
| 629 | if (l.categorizeOperand(air, cond_inst, operand, ip) == .tomb) | |
| 629 | 630 | operand_live = false; |
| 630 | 631 | |
| 631 | 632 | switch (air_tags[cond_inst]) { |
| ... | ... | @@ -872,6 +873,7 @@ fn analyzeInst( |
| 872 | 873 | data: *LivenessPassData(pass), |
| 873 | 874 | inst: Air.Inst.Index, |
| 874 | 875 | ) Allocator.Error!void { |
| 876 | const ip = a.intern_pool; | |
| 875 | 877 | const inst_tags = a.air.instructions.items(.tag); |
| 876 | 878 | const inst_datas = a.air.instructions.items(.data); |
| 877 | 879 | |
| ... | ... | @@ -1140,7 +1142,7 @@ fn analyzeInst( |
| 1140 | 1142 | .aggregate_init => { |
| 1141 | 1143 | const ty_pl = inst_datas[inst].ty_pl; |
| 1142 | 1144 | const aggregate_ty = a.air.getRefType(ty_pl.ty); |
| 1143 | const len = @intCast(usize, aggregate_ty.arrayLen()); | |
| 1145 | const len = @intCast(usize, aggregate_ty.arrayLenIp(ip.*)); | |
| 1144 | 1146 | const elements = @ptrCast([]const Air.Inst.Ref, a.air.extra[ty_pl.payload..][0..len]); |
| 1145 | 1147 | |
| 1146 | 1148 | if (elements.len <= bpi - 1) { |
src/Liveness/Verify.zig+1-1| ... | ... | @@ -325,7 +325,7 @@ fn verifyBody(self: *Verify, body: []const Air.Inst.Index) Error!void { |
| 325 | 325 | .aggregate_init => { |
| 326 | 326 | const ty_pl = data[inst].ty_pl; |
| 327 | 327 | const aggregate_ty = self.air.getRefType(ty_pl.ty); |
| 328 | const len = @intCast(usize, aggregate_ty.arrayLen()); | |
| 328 | const len = @intCast(usize, aggregate_ty.arrayLenIp(ip.*)); | |
| 329 | 329 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 330 | 330 | |
| 331 | 331 | var bt = self.liveness.iterateBigTomb(inst); |
src/Module.zig+37-4| ... | ... | @@ -5805,7 +5805,7 @@ pub fn analyzeFnBody(mod: *Module, func: *Fn, arena: Allocator) SemaError!Air { |
| 5805 | 5805 | // is unused so it just has to be a no-op. |
| 5806 | 5806 | sema.air_instructions.set(ptr_inst.*, .{ |
| 5807 | 5807 | .tag = .alloc, |
| 5808 | .data = .{ .ty = Type.initTag(.single_const_pointer_to_comptime_int) }, | |
| 5808 | .data = .{ .ty = Type.single_const_pointer_to_comptime_int }, | |
| 5809 | 5809 | }); |
| 5810 | 5810 | } |
| 5811 | 5811 | } |
| ... | ... | @@ -6545,7 +6545,7 @@ pub fn populateTestFunctions( |
| 6545 | 6545 | } |
| 6546 | 6546 | const decl = mod.declPtr(decl_index); |
| 6547 | 6547 | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 6548 | const tmp_test_fn_ty = decl.ty.slicePtrFieldType(&buf).elemType(); | |
| 6548 | const tmp_test_fn_ty = decl.ty.slicePtrFieldType(&buf).childType(mod); | |
| 6549 | 6549 | |
| 6550 | 6550 | const array_decl_index = d: { |
| 6551 | 6551 | // Add mod.test_functions to an array decl then make the test_functions |
| ... | ... | @@ -6575,7 +6575,7 @@ pub fn populateTestFunctions( |
| 6575 | 6575 | errdefer name_decl_arena.deinit(); |
| 6576 | 6576 | const bytes = try name_decl_arena.allocator().dupe(u8, test_name_slice); |
| 6577 | 6577 | const test_name_decl_index = try mod.createAnonymousDeclFromDecl(array_decl, array_decl.src_namespace, null, .{ |
| 6578 | .ty = try Type.Tag.array_u8.create(name_decl_arena.allocator(), bytes.len), | |
| 6578 | .ty = try Type.array(name_decl_arena.allocator(), bytes.len, null, Type.u8, mod), | |
| 6579 | 6579 | .val = try Value.Tag.bytes.create(name_decl_arena.allocator(), bytes), |
| 6580 | 6580 | }); |
| 6581 | 6581 | try mod.declPtr(test_name_decl_index).finalizeNewArena(&name_decl_arena); |
| ... | ... | @@ -6609,7 +6609,12 @@ pub fn populateTestFunctions( |
| 6609 | 6609 | |
| 6610 | 6610 | { |
| 6611 | 6611 | // This copy accesses the old Decl Type/Value so it must be done before `clearValues`. |
| 6612 | const new_ty = try Type.Tag.const_slice.create(arena, try tmp_test_fn_ty.copy(arena)); | |
| 6612 | const new_ty = try Type.ptr(arena, mod, .{ | |
| 6613 | .size = .Slice, | |
| 6614 | .pointee_type = try tmp_test_fn_ty.copy(arena), | |
| 6615 | .mutable = false, | |
| 6616 | .@"addrspace" = .generic, | |
| 6617 | }); | |
| 6613 | 6618 | const new_var = try gpa.create(Var); |
| 6614 | 6619 | errdefer gpa.destroy(new_var); |
| 6615 | 6620 | new_var.* = decl.val.castTag(.variable).?.data.*; |
| ... | ... | @@ -6819,6 +6824,34 @@ pub fn intType(mod: *Module, signedness: std.builtin.Signedness, bits: u16) Allo |
| 6819 | 6824 | return i.toType(); |
| 6820 | 6825 | } |
| 6821 | 6826 | |
| 6827 | pub fn arrayType(mod: *Module, info: InternPool.Key.ArrayType) Allocator.Error!Type { | |
| 6828 | const i = try intern(mod, .{ .array_type = info }); | |
| 6829 | return i.toType(); | |
| 6830 | } | |
| 6831 | ||
| 6832 | pub fn vectorType(mod: *Module, info: InternPool.Key.VectorType) Allocator.Error!Type { | |
| 6833 | const i = try intern(mod, .{ .vector_type = info }); | |
| 6834 | return i.toType(); | |
| 6835 | } | |
| 6836 | ||
| 6837 | pub fn optionalType(mod: *Module, child_type: InternPool.Index) Allocator.Error!Type { | |
| 6838 | const i = try intern(mod, .{ .opt_type = child_type }); | |
| 6839 | return i.toType(); | |
| 6840 | } | |
| 6841 | ||
| 6842 | pub fn ptrType(mod: *Module, info: InternPool.Key.PtrType) Allocator.Error!Type { | |
| 6843 | const i = try intern(mod, .{ .ptr_type = info }); | |
| 6844 | return i.toType(); | |
| 6845 | } | |
| 6846 | ||
| 6847 | pub fn singleMutPtrType(mod: *Module, child_type: Type) Allocator.Error!Type { | |
| 6848 | return ptrType(mod, .{ .elem_type = child_type.ip_index }); | |
| 6849 | } | |
| 6850 | ||
| 6851 | pub fn singleConstPtrType(mod: *Module, child_type: Type) Allocator.Error!Type { | |
| 6852 | return ptrType(mod, .{ .elem_type = child_type.ip_index, .is_const = true }); | |
| 6853 | } | |
| 6854 | ||
| 6822 | 6855 | pub fn smallestUnsignedInt(mod: *Module, max: u64) Allocator.Error!Type { |
| 6823 | 6856 | return intType(mod, .unsigned, Type.smallestUnsignedBits(max)); |
| 6824 | 6857 | } |
src/Sema.zig+519-556| ... | ... | @@ -585,13 +585,18 @@ pub const Block = struct { |
| 585 | 585 | } |
| 586 | 586 | |
| 587 | 587 | fn addCmpVector(block: *Block, lhs: Air.Inst.Ref, rhs: Air.Inst.Ref, cmp_op: std.math.CompareOperator) !Air.Inst.Ref { |
| 588 | const sema = block.sema; | |
| 589 | const mod = sema.mod; | |
| 588 | 590 | return block.addInst(.{ |
| 589 | 591 | .tag = if (block.float_mode == .Optimized) .cmp_vector_optimized else .cmp_vector, |
| 590 | 592 | .data = .{ .ty_pl = .{ |
| 591 | .ty = try block.sema.addType( | |
| 592 | try Type.vector(block.sema.arena, block.sema.typeOf(lhs).vectorLen(), Type.bool), | |
| 593 | .ty = try sema.addType( | |
| 594 | try mod.vectorType(.{ | |
| 595 | .len = sema.typeOf(lhs).vectorLen(mod), | |
| 596 | .child = .bool_type, | |
| 597 | }), | |
| 593 | 598 | ), |
| 594 | .payload = try block.sema.addExtra(Air.VectorCmp{ | |
| 599 | .payload = try sema.addExtra(Air.VectorCmp{ | |
| 595 | 600 | .lhs = lhs, |
| 596 | 601 | .rhs = rhs, |
| 597 | 602 | .op = Air.VectorCmp.encodeOp(cmp_op), |
| ... | ... | @@ -1760,7 +1765,7 @@ pub fn resolveConstString( |
| 1760 | 1765 | reason: []const u8, |
| 1761 | 1766 | ) ![]u8 { |
| 1762 | 1767 | const air_inst = try sema.resolveInst(zir_ref); |
| 1763 | const wanted_type = Type.initTag(.const_slice_u8); | |
| 1768 | const wanted_type = Type.const_slice_u8; | |
| 1764 | 1769 | const coerced_inst = try sema.coerce(block, wanted_type, air_inst, src); |
| 1765 | 1770 | const val = try sema.resolveConstValue(block, src, coerced_inst, reason); |
| 1766 | 1771 | return val.toAllocatedBytes(wanted_type, sema.arena, sema.mod); |
| ... | ... | @@ -1788,7 +1793,8 @@ fn analyzeAsType( |
| 1788 | 1793 | } |
| 1789 | 1794 | |
| 1790 | 1795 | pub fn setupErrorReturnTrace(sema: *Sema, block: *Block, last_arg_index: usize) !void { |
| 1791 | if (!sema.mod.backendSupportsFeature(.error_return_trace)) return; | |
| 1796 | const mod = sema.mod; | |
| 1797 | if (!mod.backendSupportsFeature(.error_return_trace)) return; | |
| 1792 | 1798 | |
| 1793 | 1799 | assert(!block.is_comptime); |
| 1794 | 1800 | var err_trace_block = block.makeSubBlock(); |
| ... | ... | @@ -1798,13 +1804,13 @@ pub fn setupErrorReturnTrace(sema: *Sema, block: *Block, last_arg_index: usize) |
| 1798 | 1804 | |
| 1799 | 1805 | // var addrs: [err_return_trace_addr_count]usize = undefined; |
| 1800 | 1806 | const err_return_trace_addr_count = 32; |
| 1801 | const addr_arr_ty = try Type.array(sema.arena, err_return_trace_addr_count, null, Type.usize, sema.mod); | |
| 1802 | const addrs_ptr = try err_trace_block.addTy(.alloc, try Type.Tag.single_mut_pointer.create(sema.arena, addr_arr_ty)); | |
| 1807 | const addr_arr_ty = try Type.array(sema.arena, err_return_trace_addr_count, null, Type.usize, mod); | |
| 1808 | const addrs_ptr = try err_trace_block.addTy(.alloc, try mod.singleMutPtrType(addr_arr_ty)); | |
| 1803 | 1809 | |
| 1804 | 1810 | // var st: StackTrace = undefined; |
| 1805 | 1811 | const unresolved_stack_trace_ty = try sema.getBuiltinType("StackTrace"); |
| 1806 | 1812 | const stack_trace_ty = try sema.resolveTypeFields(unresolved_stack_trace_ty); |
| 1807 | const st_ptr = try err_trace_block.addTy(.alloc, try Type.Tag.single_mut_pointer.create(sema.arena, stack_trace_ty)); | |
| 1813 | const st_ptr = try err_trace_block.addTy(.alloc, try mod.singleMutPtrType(stack_trace_ty)); | |
| 1808 | 1814 | |
| 1809 | 1815 | // st.instruction_addresses = &addrs; |
| 1810 | 1816 | const addr_field_ptr = try sema.fieldPtr(&err_trace_block, src, st_ptr, "instruction_addresses", src, true); |
| ... | ... | @@ -2101,11 +2107,10 @@ fn failWithUseOfAsync(sema: *Sema, block: *Block, src: LazySrcLoc) CompileError |
| 2101 | 2107 | |
| 2102 | 2108 | fn failWithInvalidFieldAccess(sema: *Sema, block: *Block, src: LazySrcLoc, object_ty: Type, field_name: []const u8) CompileError { |
| 2103 | 2109 | const mod = sema.mod; |
| 2104 | const inner_ty = if (object_ty.isSinglePointer(mod)) object_ty.childType() else object_ty; | |
| 2110 | const inner_ty = if (object_ty.isSinglePointer(mod)) object_ty.childType(mod) else object_ty; | |
| 2105 | 2111 | |
| 2106 | 2112 | if (inner_ty.zigTypeTag(mod) == .Optional) opt: { |
| 2107 | var buf: Type.Payload.ElemType = undefined; | |
| 2108 | const child_ty = inner_ty.optionalChild(&buf); | |
| 2113 | const child_ty = inner_ty.optionalChild(mod); | |
| 2109 | 2114 | if (!typeSupportsFieldAccess(mod, child_ty, field_name)) break :opt; |
| 2110 | 2115 | const msg = msg: { |
| 2111 | 2116 | const msg = try sema.errMsg(block, src, "optional type '{}' does not support field access", .{object_ty.fmt(sema.mod)}); |
| ... | ... | @@ -2132,7 +2137,7 @@ fn typeSupportsFieldAccess(mod: *const Module, ty: Type, field_name: []const u8) |
| 2132 | 2137 | switch (ty.zigTypeTag(mod)) { |
| 2133 | 2138 | .Array => return mem.eql(u8, field_name, "len"), |
| 2134 | 2139 | .Pointer => { |
| 2135 | const ptr_info = ty.ptrInfo().data; | |
| 2140 | const ptr_info = ty.ptrInfo(mod); | |
| 2136 | 2141 | if (ptr_info.size == .Slice) { |
| 2137 | 2142 | return mem.eql(u8, field_name, "ptr") or mem.eql(u8, field_name, "len"); |
| 2138 | 2143 | } else if (ptr_info.pointee_type.zigTypeTag(mod) == .Array) { |
| ... | ... | @@ -2504,6 +2509,7 @@ fn coerceResultPtr( |
| 2504 | 2509 | dummy_operand: Air.Inst.Ref, |
| 2505 | 2510 | trash_block: *Block, |
| 2506 | 2511 | ) CompileError!Air.Inst.Ref { |
| 2512 | const mod = sema.mod; | |
| 2507 | 2513 | const target = sema.mod.getTarget(); |
| 2508 | 2514 | const addr_space = target_util.defaultAddressSpace(target, .local); |
| 2509 | 2515 | const pointee_ty = sema.typeOf(dummy_operand); |
| ... | ... | @@ -2547,7 +2553,7 @@ fn coerceResultPtr( |
| 2547 | 2553 | return sema.addConstant(ptr_ty, ptr_val); |
| 2548 | 2554 | } |
| 2549 | 2555 | if (pointee_ty.eql(Type.null, sema.mod)) { |
| 2550 | const opt_ty = sema.typeOf(new_ptr).childType(); | |
| 2556 | const opt_ty = sema.typeOf(new_ptr).childType(mod); | |
| 2551 | 2557 | const null_inst = try sema.addConstant(opt_ty, Value.null); |
| 2552 | 2558 | _ = try block.addBinOp(.store, new_ptr, null_inst); |
| 2553 | 2559 | return Air.Inst.Ref.void_value; |
| ... | ... | @@ -3394,7 +3400,7 @@ fn zirEnsureErrUnionPayloadVoid(sema: *Sema, block: *Block, inst: Zir.Inst.Index |
| 3394 | 3400 | const operand = try sema.resolveInst(inst_data.operand); |
| 3395 | 3401 | const operand_ty = sema.typeOf(operand); |
| 3396 | 3402 | const err_union_ty = if (operand_ty.zigTypeTag(mod) == .Pointer) |
| 3397 | operand_ty.childType() | |
| 3403 | operand_ty.childType(mod) | |
| 3398 | 3404 | else |
| 3399 | 3405 | operand_ty; |
| 3400 | 3406 | if (err_union_ty.zigTypeTag(mod) != .ErrorUnion) return; |
| ... | ... | @@ -3430,7 +3436,7 @@ fn indexablePtrLen( |
| 3430 | 3436 | const mod = sema.mod; |
| 3431 | 3437 | const object_ty = sema.typeOf(object); |
| 3432 | 3438 | const is_pointer_to = object_ty.isSinglePointer(mod); |
| 3433 | const indexable_ty = if (is_pointer_to) object_ty.childType() else object_ty; | |
| 3439 | const indexable_ty = if (is_pointer_to) object_ty.childType(mod) else object_ty; | |
| 3434 | 3440 | try checkIndexable(sema, block, src, indexable_ty); |
| 3435 | 3441 | return sema.fieldVal(block, src, object, "len", src); |
| 3436 | 3442 | } |
| ... | ... | @@ -3441,9 +3447,10 @@ fn indexablePtrLenOrNone( |
| 3441 | 3447 | src: LazySrcLoc, |
| 3442 | 3448 | operand: Air.Inst.Ref, |
| 3443 | 3449 | ) CompileError!Air.Inst.Ref { |
| 3450 | const mod = sema.mod; | |
| 3444 | 3451 | const operand_ty = sema.typeOf(operand); |
| 3445 | 3452 | try checkMemOperand(sema, block, src, operand_ty); |
| 3446 | if (operand_ty.ptrSize() == .Many) return .none; | |
| 3453 | if (operand_ty.ptrSize(mod) == .Many) return .none; | |
| 3447 | 3454 | return sema.fieldVal(block, src, operand, "len", src); |
| 3448 | 3455 | } |
| 3449 | 3456 | |
| ... | ... | @@ -3529,11 +3536,12 @@ fn zirAllocComptime(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileErr |
| 3529 | 3536 | } |
| 3530 | 3537 | |
| 3531 | 3538 | fn zirMakePtrConst(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { |
| 3539 | const mod = sema.mod; | |
| 3532 | 3540 | const inst_data = sema.code.instructions.items(.data)[inst].un_node; |
| 3533 | 3541 | const alloc = try sema.resolveInst(inst_data.operand); |
| 3534 | 3542 | const alloc_ty = sema.typeOf(alloc); |
| 3535 | 3543 | |
| 3536 | var ptr_info = alloc_ty.ptrInfo().data; | |
| 3544 | var ptr_info = alloc_ty.ptrInfo(mod); | |
| 3537 | 3545 | const elem_ty = ptr_info.pointee_type; |
| 3538 | 3546 | |
| 3539 | 3547 | // Detect if all stores to an `.alloc` were comptime-known. |
| ... | ... | @@ -3589,9 +3597,10 @@ fn zirMakePtrConst(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileErro |
| 3589 | 3597 | } |
| 3590 | 3598 | |
| 3591 | 3599 | fn makePtrConst(sema: *Sema, block: *Block, alloc: Air.Inst.Ref) CompileError!Air.Inst.Ref { |
| 3600 | const mod = sema.mod; | |
| 3592 | 3601 | const alloc_ty = sema.typeOf(alloc); |
| 3593 | 3602 | |
| 3594 | var ptr_info = alloc_ty.ptrInfo().data; | |
| 3603 | var ptr_info = alloc_ty.ptrInfo(mod); | |
| 3595 | 3604 | ptr_info.mutable = false; |
| 3596 | 3605 | const const_ptr_ty = try Type.ptr(sema.arena, sema.mod, ptr_info); |
| 3597 | 3606 | |
| ... | ... | @@ -3947,13 +3956,13 @@ fn zirArrayBasePtr( |
| 3947 | 3956 | |
| 3948 | 3957 | const start_ptr = try sema.resolveInst(inst_data.operand); |
| 3949 | 3958 | var base_ptr = start_ptr; |
| 3950 | while (true) switch (sema.typeOf(base_ptr).childType().zigTypeTag(mod)) { | |
| 3959 | while (true) switch (sema.typeOf(base_ptr).childType(mod).zigTypeTag(mod)) { | |
| 3951 | 3960 | .ErrorUnion => base_ptr = try sema.analyzeErrUnionPayloadPtr(block, src, base_ptr, false, true), |
| 3952 | 3961 | .Optional => base_ptr = try sema.analyzeOptionalPayloadPtr(block, src, base_ptr, false, true), |
| 3953 | 3962 | else => break, |
| 3954 | 3963 | }; |
| 3955 | 3964 | |
| 3956 | const elem_ty = sema.typeOf(base_ptr).childType(); | |
| 3965 | const elem_ty = sema.typeOf(base_ptr).childType(mod); | |
| 3957 | 3966 | switch (elem_ty.zigTypeTag(mod)) { |
| 3958 | 3967 | .Array, .Vector => return base_ptr, |
| 3959 | 3968 | .Struct => if (elem_ty.isTuple()) { |
| ... | ... | @@ -3962,7 +3971,7 @@ fn zirArrayBasePtr( |
| 3962 | 3971 | }, |
| 3963 | 3972 | else => {}, |
| 3964 | 3973 | } |
| 3965 | return sema.failWithArrayInitNotSupported(block, src, sema.typeOf(start_ptr).childType()); | |
| 3974 | return sema.failWithArrayInitNotSupported(block, src, sema.typeOf(start_ptr).childType(mod)); | |
| 3966 | 3975 | } |
| 3967 | 3976 | |
| 3968 | 3977 | fn zirFieldBasePtr( |
| ... | ... | @@ -3976,18 +3985,18 @@ fn zirFieldBasePtr( |
| 3976 | 3985 | |
| 3977 | 3986 | const start_ptr = try sema.resolveInst(inst_data.operand); |
| 3978 | 3987 | var base_ptr = start_ptr; |
| 3979 | while (true) switch (sema.typeOf(base_ptr).childType().zigTypeTag(mod)) { | |
| 3988 | while (true) switch (sema.typeOf(base_ptr).childType(mod).zigTypeTag(mod)) { | |
| 3980 | 3989 | .ErrorUnion => base_ptr = try sema.analyzeErrUnionPayloadPtr(block, src, base_ptr, false, true), |
| 3981 | 3990 | .Optional => base_ptr = try sema.analyzeOptionalPayloadPtr(block, src, base_ptr, false, true), |
| 3982 | 3991 | else => break, |
| 3983 | 3992 | }; |
| 3984 | 3993 | |
| 3985 | const elem_ty = sema.typeOf(base_ptr).childType(); | |
| 3994 | const elem_ty = sema.typeOf(base_ptr).childType(mod); | |
| 3986 | 3995 | switch (elem_ty.zigTypeTag(mod)) { |
| 3987 | 3996 | .Struct, .Union => return base_ptr, |
| 3988 | 3997 | else => {}, |
| 3989 | 3998 | } |
| 3990 | return sema.failWithStructInitNotSupported(block, src, sema.typeOf(start_ptr).childType()); | |
| 3999 | return sema.failWithStructInitNotSupported(block, src, sema.typeOf(start_ptr).childType(mod)); | |
| 3991 | 4000 | } |
| 3992 | 4001 | |
| 3993 | 4002 | fn zirForLen(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { |
| ... | ... | @@ -4129,7 +4138,7 @@ fn validateArrayInitTy( |
| 4129 | 4138 | |
| 4130 | 4139 | switch (ty.zigTypeTag(mod)) { |
| 4131 | 4140 | .Array => { |
| 4132 | const array_len = ty.arrayLen(); | |
| 4141 | const array_len = ty.arrayLen(mod); | |
| 4133 | 4142 | if (extra.init_count != array_len) { |
| 4134 | 4143 | return sema.fail(block, src, "expected {d} array elements; found {d}", .{ |
| 4135 | 4144 | array_len, extra.init_count, |
| ... | ... | @@ -4138,7 +4147,7 @@ fn validateArrayInitTy( |
| 4138 | 4147 | return; |
| 4139 | 4148 | }, |
| 4140 | 4149 | .Vector => { |
| 4141 | const array_len = ty.arrayLen(); | |
| 4150 | const array_len = ty.arrayLen(mod); | |
| 4142 | 4151 | if (extra.init_count != array_len) { |
| 4143 | 4152 | return sema.fail(block, src, "expected {d} vector elements; found {d}", .{ |
| 4144 | 4153 | array_len, extra.init_count, |
| ... | ... | @@ -4148,7 +4157,7 @@ fn validateArrayInitTy( |
| 4148 | 4157 | }, |
| 4149 | 4158 | .Struct => if (ty.isTuple()) { |
| 4150 | 4159 | _ = try sema.resolveTypeFields(ty); |
| 4151 | const array_len = ty.arrayLen(); | |
| 4160 | const array_len = ty.arrayLen(mod); | |
| 4152 | 4161 | if (extra.init_count > array_len) { |
| 4153 | 4162 | return sema.fail(block, src, "expected at most {d} tuple fields; found {d}", .{ |
| 4154 | 4163 | array_len, extra.init_count, |
| ... | ... | @@ -4194,7 +4203,7 @@ fn zirValidateStructInit( |
| 4194 | 4203 | const field_ptr_data = sema.code.instructions.items(.data)[instrs[0]].pl_node; |
| 4195 | 4204 | const field_ptr_extra = sema.code.extraData(Zir.Inst.Field, field_ptr_data.payload_index).data; |
| 4196 | 4205 | const object_ptr = try sema.resolveInst(field_ptr_extra.lhs); |
| 4197 | const agg_ty = sema.typeOf(object_ptr).childType(); | |
| 4206 | const agg_ty = sema.typeOf(object_ptr).childType(mod); | |
| 4198 | 4207 | switch (agg_ty.zigTypeTag(mod)) { |
| 4199 | 4208 | .Struct => return sema.validateStructInit( |
| 4200 | 4209 | block, |
| ... | ... | @@ -4350,6 +4359,7 @@ fn validateStructInit( |
| 4350 | 4359 | init_src: LazySrcLoc, |
| 4351 | 4360 | instrs: []const Zir.Inst.Index, |
| 4352 | 4361 | ) CompileError!void { |
| 4362 | const mod = sema.mod; | |
| 4353 | 4363 | const gpa = sema.gpa; |
| 4354 | 4364 | |
| 4355 | 4365 | // Maps field index to field_ptr index of where it was already initialized. |
| ... | ... | @@ -4425,14 +4435,13 @@ fn validateStructInit( |
| 4425 | 4435 | try sema.tupleFieldPtr(block, init_src, struct_ptr, field_src, @intCast(u32, i), true) |
| 4426 | 4436 | else |
| 4427 | 4437 | try sema.structFieldPtrByIndex(block, init_src, struct_ptr, @intCast(u32, i), field_src, struct_ty, true); |
| 4428 | const field_ty = sema.typeOf(default_field_ptr).childType(); | |
| 4438 | const field_ty = sema.typeOf(default_field_ptr).childType(mod); | |
| 4429 | 4439 | const init = try sema.addConstant(field_ty, default_val); |
| 4430 | 4440 | try sema.storePtr2(block, init_src, default_field_ptr, init_src, init, field_src, .store); |
| 4431 | 4441 | } |
| 4432 | 4442 | |
| 4433 | 4443 | if (root_msg) |msg| { |
| 4434 | 4444 | if (struct_ty.castTag(.@"struct")) |struct_obj| { |
| 4435 | const mod = sema.mod; | |
| 4436 | 4445 | const fqn = try struct_obj.data.getFullyQualifiedName(mod); |
| 4437 | 4446 | defer gpa.free(fqn); |
| 4438 | 4447 | try mod.errNoteNonLazy( |
| ... | ... | @@ -4605,7 +4614,7 @@ fn validateStructInit( |
| 4605 | 4614 | try sema.tupleFieldPtr(block, init_src, struct_ptr, field_src, @intCast(u32, i), true) |
| 4606 | 4615 | else |
| 4607 | 4616 | try sema.structFieldPtrByIndex(block, init_src, struct_ptr, @intCast(u32, i), field_src, struct_ty, true); |
| 4608 | const field_ty = sema.typeOf(default_field_ptr).childType(); | |
| 4617 | const field_ty = sema.typeOf(default_field_ptr).childType(mod); | |
| 4609 | 4618 | const init = try sema.addConstant(field_ty, field_values[i]); |
| 4610 | 4619 | try sema.storePtr2(block, init_src, default_field_ptr, init_src, init, field_src, .store); |
| 4611 | 4620 | } |
| ... | ... | @@ -4624,8 +4633,8 @@ fn zirValidateArrayInit( |
| 4624 | 4633 | const first_elem_ptr_data = sema.code.instructions.items(.data)[instrs[0]].pl_node; |
| 4625 | 4634 | const elem_ptr_extra = sema.code.extraData(Zir.Inst.ElemPtrImm, first_elem_ptr_data.payload_index).data; |
| 4626 | 4635 | const array_ptr = try sema.resolveInst(elem_ptr_extra.ptr); |
| 4627 | const array_ty = sema.typeOf(array_ptr).childType(); | |
| 4628 | const array_len = array_ty.arrayLen(); | |
| 4636 | const array_ty = sema.typeOf(array_ptr).childType(mod); | |
| 4637 | const array_len = array_ty.arrayLen(mod); | |
| 4629 | 4638 | |
| 4630 | 4639 | if (instrs.len != array_len) switch (array_ty.zigTypeTag(mod)) { |
| 4631 | 4640 | .Struct => { |
| ... | ... | @@ -4670,10 +4679,10 @@ fn zirValidateArrayInit( |
| 4670 | 4679 | // at comptime so we have almost nothing to do here. However, in case of a |
| 4671 | 4680 | // sentinel-terminated array, the sentinel will not have been populated by |
| 4672 | 4681 | // any ZIR instructions at comptime; we need to do that here. |
| 4673 | if (array_ty.sentinel()) |sentinel_val| { | |
| 4682 | if (array_ty.sentinel(mod)) |sentinel_val| { | |
| 4674 | 4683 | const array_len_ref = try sema.addIntUnsigned(Type.usize, array_len); |
| 4675 | 4684 | const sentinel_ptr = try sema.elemPtrArray(block, init_src, init_src, array_ptr, init_src, array_len_ref, true, true); |
| 4676 | const sentinel = try sema.addConstant(array_ty.childType(), sentinel_val); | |
| 4685 | const sentinel = try sema.addConstant(array_ty.childType(mod), sentinel_val); | |
| 4677 | 4686 | try sema.storePtr2(block, init_src, sentinel_ptr, init_src, sentinel, init_src, .store); |
| 4678 | 4687 | } |
| 4679 | 4688 | return; |
| ... | ... | @@ -4685,7 +4694,7 @@ fn zirValidateArrayInit( |
| 4685 | 4694 | |
| 4686 | 4695 | // Collect the comptime element values in case the array literal ends up |
| 4687 | 4696 | // being comptime-known. |
| 4688 | const array_len_s = try sema.usizeCast(block, init_src, array_ty.arrayLenIncludingSentinel()); | |
| 4697 | const array_len_s = try sema.usizeCast(block, init_src, array_ty.arrayLenIncludingSentinel(mod)); | |
| 4689 | 4698 | const element_vals = try sema.arena.alloc(Value, array_len_s); |
| 4690 | 4699 | const opt_opv = try sema.typeHasOnePossibleValue(array_ty); |
| 4691 | 4700 | const air_tags = sema.air_instructions.items(.tag); |
| ... | ... | @@ -4784,7 +4793,7 @@ fn zirValidateArrayInit( |
| 4784 | 4793 | // Our task is to delete all the `elem_ptr` and `store` instructions, and insert |
| 4785 | 4794 | // instead a single `store` to the array_ptr with a comptime struct value. |
| 4786 | 4795 | // Also to populate the sentinel value, if any. |
| 4787 | if (array_ty.sentinel()) |sentinel_val| { | |
| 4796 | if (array_ty.sentinel(mod)) |sentinel_val| { | |
| 4788 | 4797 | element_vals[instrs.len] = sentinel_val; |
| 4789 | 4798 | } |
| 4790 | 4799 | |
| ... | ... | @@ -4806,13 +4815,13 @@ fn zirValidateDeref(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileErr |
| 4806 | 4815 | |
| 4807 | 4816 | if (operand_ty.zigTypeTag(mod) != .Pointer) { |
| 4808 | 4817 | return sema.fail(block, src, "cannot dereference non-pointer type '{}'", .{operand_ty.fmt(sema.mod)}); |
| 4809 | } else switch (operand_ty.ptrSize()) { | |
| 4818 | } else switch (operand_ty.ptrSize(mod)) { | |
| 4810 | 4819 | .One, .C => {}, |
| 4811 | 4820 | .Many => return sema.fail(block, src, "index syntax required for unknown-length pointer type '{}'", .{operand_ty.fmt(sema.mod)}), |
| 4812 | 4821 | .Slice => return sema.fail(block, src, "index syntax required for slice type '{}'", .{operand_ty.fmt(sema.mod)}), |
| 4813 | 4822 | } |
| 4814 | 4823 | |
| 4815 | if ((try sema.typeHasOnePossibleValue(operand_ty.childType())) != null) { | |
| 4824 | if ((try sema.typeHasOnePossibleValue(operand_ty.childType(mod))) != null) { | |
| 4816 | 4825 | // No need to validate the actual pointer value, we don't need it! |
| 4817 | 4826 | return; |
| 4818 | 4827 | } |
| ... | ... | @@ -5132,7 +5141,7 @@ fn addStrLit(sema: *Sema, block: *Block, zir_bytes: []const u8) CompileError!Air |
| 5132 | 5141 | defer anon_decl.deinit(); |
| 5133 | 5142 | |
| 5134 | 5143 | const decl_index = try anon_decl.finish( |
| 5135 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), gop.key_ptr.len), | |
| 5144 | try Type.array(anon_decl.arena(), gop.key_ptr.len, Value.zero, Type.u8, mod), | |
| 5136 | 5145 | try Value.Tag.str_lit.create(anon_decl.arena(), gop.key_ptr.*), |
| 5137 | 5146 | 0, // default alignment |
| 5138 | 5147 | ); |
| ... | ... | @@ -6003,10 +6012,11 @@ fn addDbgVar( |
| 6003 | 6012 | air_tag: Air.Inst.Tag, |
| 6004 | 6013 | name: []const u8, |
| 6005 | 6014 | ) CompileError!void { |
| 6015 | const mod = sema.mod; | |
| 6006 | 6016 | const operand_ty = sema.typeOf(operand); |
| 6007 | 6017 | switch (air_tag) { |
| 6008 | 6018 | .dbg_var_ptr => { |
| 6009 | if (!(try sema.typeHasRuntimeBits(operand_ty.childType()))) return; | |
| 6019 | if (!(try sema.typeHasRuntimeBits(operand_ty.childType(mod)))) return; | |
| 6010 | 6020 | }, |
| 6011 | 6021 | .dbg_var_val => { |
| 6012 | 6022 | if (!(try sema.typeHasRuntimeBits(operand_ty))) return; |
| ... | ... | @@ -6238,7 +6248,7 @@ fn popErrorReturnTrace( |
| 6238 | 6248 | |
| 6239 | 6249 | const unresolved_stack_trace_ty = try sema.getBuiltinType("StackTrace"); |
| 6240 | 6250 | const stack_trace_ty = try sema.resolveTypeFields(unresolved_stack_trace_ty); |
| 6241 | const ptr_stack_trace_ty = try Type.Tag.single_mut_pointer.create(sema.arena, stack_trace_ty); | |
| 6251 | const ptr_stack_trace_ty = try mod.singleMutPtrType(stack_trace_ty); | |
| 6242 | 6252 | const err_return_trace = try block.addTy(.err_return_trace, ptr_stack_trace_ty); |
| 6243 | 6253 | const field_ptr = try sema.structFieldPtr(block, src, err_return_trace, "index", src, stack_trace_ty, true); |
| 6244 | 6254 | try sema.storePtr2(block, src, field_ptr, src, saved_error_trace_index, src, .store); |
| ... | ... | @@ -6263,7 +6273,7 @@ fn popErrorReturnTrace( |
| 6263 | 6273 | // If non-error, then pop the error return trace by restoring the index. |
| 6264 | 6274 | const unresolved_stack_trace_ty = try sema.getBuiltinType("StackTrace"); |
| 6265 | 6275 | const stack_trace_ty = try sema.resolveTypeFields(unresolved_stack_trace_ty); |
| 6266 | const ptr_stack_trace_ty = try Type.Tag.single_mut_pointer.create(sema.arena, stack_trace_ty); | |
| 6276 | const ptr_stack_trace_ty = try mod.singleMutPtrType(stack_trace_ty); | |
| 6267 | 6277 | const err_return_trace = try then_block.addTy(.err_return_trace, ptr_stack_trace_ty); |
| 6268 | 6278 | const field_ptr = try sema.structFieldPtr(&then_block, src, err_return_trace, "index", src, stack_trace_ty, true); |
| 6269 | 6279 | try sema.storePtr2(&then_block, src, field_ptr, src, saved_error_trace_index, src, .store); |
| ... | ... | @@ -6456,16 +6466,15 @@ fn checkCallArgumentCount( |
| 6456 | 6466 | switch (callee_ty.zigTypeTag(mod)) { |
| 6457 | 6467 | .Fn => break :func_ty callee_ty, |
| 6458 | 6468 | .Pointer => { |
| 6459 | const ptr_info = callee_ty.ptrInfo().data; | |
| 6469 | const ptr_info = callee_ty.ptrInfo(mod); | |
| 6460 | 6470 | if (ptr_info.size == .One and ptr_info.pointee_type.zigTypeTag(mod) == .Fn) { |
| 6461 | 6471 | break :func_ty ptr_info.pointee_type; |
| 6462 | 6472 | } |
| 6463 | 6473 | }, |
| 6464 | 6474 | .Optional => { |
| 6465 | var buf: Type.Payload.ElemType = undefined; | |
| 6466 | const opt_child = callee_ty.optionalChild(&buf); | |
| 6475 | const opt_child = callee_ty.optionalChild(mod); | |
| 6467 | 6476 | if (opt_child.zigTypeTag(mod) == .Fn or (opt_child.isSinglePointer(mod) and |
| 6468 | opt_child.childType().zigTypeTag(mod) == .Fn)) | |
| 6477 | opt_child.childType(mod).zigTypeTag(mod) == .Fn)) | |
| 6469 | 6478 | { |
| 6470 | 6479 | const msg = msg: { |
| 6471 | 6480 | const msg = try sema.errMsg(block, func_src, "cannot call optional type '{}'", .{ |
| ... | ... | @@ -6529,7 +6538,7 @@ fn callBuiltin( |
| 6529 | 6538 | switch (callee_ty.zigTypeTag(mod)) { |
| 6530 | 6539 | .Fn => break :func_ty callee_ty, |
| 6531 | 6540 | .Pointer => { |
| 6532 | const ptr_info = callee_ty.ptrInfo().data; | |
| 6541 | const ptr_info = callee_ty.ptrInfo(mod); | |
| 6533 | 6542 | if (ptr_info.size == .One and ptr_info.pointee_type.zigTypeTag(mod) == .Fn) { |
| 6534 | 6543 | break :func_ty ptr_info.pointee_type; |
| 6535 | 6544 | } |
| ... | ... | @@ -7929,7 +7938,7 @@ fn zirOptionalType(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileErro |
| 7929 | 7938 | } else if (child_type.zigTypeTag(mod) == .Null) { |
| 7930 | 7939 | return sema.fail(block, operand_src, "type '{}' cannot be optional", .{child_type.fmt(sema.mod)}); |
| 7931 | 7940 | } |
| 7932 | const opt_type = try Type.optional(sema.arena, child_type); | |
| 7941 | const opt_type = try Type.optional(sema.arena, child_type, mod); | |
| 7933 | 7942 | |
| 7934 | 7943 | return sema.addType(opt_type); |
| 7935 | 7944 | } |
| ... | ... | @@ -7949,16 +7958,17 @@ fn zirElemTypeIndex(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileErr |
| 7949 | 7958 | } |
| 7950 | 7959 | |
| 7951 | 7960 | fn zirVectorType(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { |
| 7961 | const mod = sema.mod; | |
| 7952 | 7962 | const inst_data = sema.code.instructions.items(.data)[inst].pl_node; |
| 7953 | 7963 | const elem_type_src: LazySrcLoc = .{ .node_offset_builtin_call_arg0 = inst_data.src_node }; |
| 7954 | 7964 | const len_src: LazySrcLoc = .{ .node_offset_builtin_call_arg1 = inst_data.src_node }; |
| 7955 | 7965 | const extra = sema.code.extraData(Zir.Inst.Bin, inst_data.payload_index).data; |
| 7956 | const len = try sema.resolveInt(block, len_src, extra.lhs, Type.u32, "vector length must be comptime-known"); | |
| 7966 | const len = @intCast(u32, try sema.resolveInt(block, len_src, extra.lhs, Type.u32, "vector length must be comptime-known")); | |
| 7957 | 7967 | const elem_type = try sema.resolveType(block, elem_type_src, extra.rhs); |
| 7958 | 7968 | try sema.checkVectorElemType(block, elem_type_src, elem_type); |
| 7959 | const vector_type = try Type.Tag.vector.create(sema.arena, .{ | |
| 7960 | .len = @intCast(u32, len), | |
| 7961 | .elem_type = elem_type, | |
| 7969 | const vector_type = try mod.vectorType(.{ | |
| 7970 | .len = len, | |
| 7971 | .child = elem_type.ip_index, | |
| 7962 | 7972 | }); |
| 7963 | 7973 | return sema.addType(vector_type); |
| 7964 | 7974 | } |
| ... | ... | @@ -8377,16 +8387,16 @@ fn analyzeOptionalPayloadPtr( |
| 8377 | 8387 | const optional_ptr_ty = sema.typeOf(optional_ptr); |
| 8378 | 8388 | assert(optional_ptr_ty.zigTypeTag(mod) == .Pointer); |
| 8379 | 8389 | |
| 8380 | const opt_type = optional_ptr_ty.elemType(); | |
| 8390 | const opt_type = optional_ptr_ty.childType(mod); | |
| 8381 | 8391 | if (opt_type.zigTypeTag(mod) != .Optional) { |
| 8382 | 8392 | return sema.fail(block, src, "expected optional type, found '{}'", .{opt_type.fmt(sema.mod)}); |
| 8383 | 8393 | } |
| 8384 | 8394 | |
| 8385 | const child_type = try opt_type.optionalChildAlloc(sema.arena); | |
| 8395 | const child_type = opt_type.optionalChild(mod); | |
| 8386 | 8396 | const child_pointer = try Type.ptr(sema.arena, sema.mod, .{ |
| 8387 | 8397 | .pointee_type = child_type, |
| 8388 | 8398 | .mutable = !optional_ptr_ty.isConstPtr(), |
| 8389 | .@"addrspace" = optional_ptr_ty.ptrAddressSpace(), | |
| 8399 | .@"addrspace" = optional_ptr_ty.ptrAddressSpace(mod), | |
| 8390 | 8400 | }); |
| 8391 | 8401 | |
| 8392 | 8402 | if (try sema.resolveDefinedValue(block, src, optional_ptr)) |ptr_val| { |
| ... | ... | @@ -8401,7 +8411,7 @@ fn analyzeOptionalPayloadPtr( |
| 8401 | 8411 | child_pointer, |
| 8402 | 8412 | try Value.Tag.opt_payload_ptr.create(sema.arena, .{ |
| 8403 | 8413 | .container_ptr = ptr_val, |
| 8404 | .container_ty = optional_ptr_ty.childType(), | |
| 8414 | .container_ty = optional_ptr_ty.childType(mod), | |
| 8405 | 8415 | }), |
| 8406 | 8416 | ); |
| 8407 | 8417 | } |
| ... | ... | @@ -8414,7 +8424,7 @@ fn analyzeOptionalPayloadPtr( |
| 8414 | 8424 | child_pointer, |
| 8415 | 8425 | try Value.Tag.opt_payload_ptr.create(sema.arena, .{ |
| 8416 | 8426 | .container_ptr = ptr_val, |
| 8417 | .container_ty = optional_ptr_ty.childType(), | |
| 8427 | .container_ty = optional_ptr_ty.childType(mod), | |
| 8418 | 8428 | }), |
| 8419 | 8429 | ); |
| 8420 | 8430 | } |
| ... | ... | @@ -8448,14 +8458,14 @@ fn zirOptionalPayload( |
| 8448 | 8458 | const operand = try sema.resolveInst(inst_data.operand); |
| 8449 | 8459 | const operand_ty = sema.typeOf(operand); |
| 8450 | 8460 | const result_ty = switch (operand_ty.zigTypeTag(mod)) { |
| 8451 | .Optional => try operand_ty.optionalChildAlloc(sema.arena), | |
| 8461 | .Optional => operand_ty.optionalChild(mod), | |
| 8452 | 8462 | .Pointer => t: { |
| 8453 | if (operand_ty.ptrSize() != .C) { | |
| 8463 | if (operand_ty.ptrSize(mod) != .C) { | |
| 8454 | 8464 | return sema.failWithExpectedOptionalType(block, src, operand_ty); |
| 8455 | 8465 | } |
| 8456 | 8466 | // TODO https://github.com/ziglang/zig/issues/6597 |
| 8457 | 8467 | if (true) break :t operand_ty; |
| 8458 | const ptr_info = operand_ty.ptrInfo().data; | |
| 8468 | const ptr_info = operand_ty.ptrInfo(mod); | |
| 8459 | 8469 | break :t try Type.ptr(sema.arena, sema.mod, .{ |
| 8460 | 8470 | .pointee_type = try ptr_info.pointee_type.copy(sema.arena), |
| 8461 | 8471 | .@"align" = ptr_info.@"align", |
| ... | ... | @@ -8569,18 +8579,18 @@ fn analyzeErrUnionPayloadPtr( |
| 8569 | 8579 | const operand_ty = sema.typeOf(operand); |
| 8570 | 8580 | assert(operand_ty.zigTypeTag(mod) == .Pointer); |
| 8571 | 8581 | |
| 8572 | if (operand_ty.elemType().zigTypeTag(mod) != .ErrorUnion) { | |
| 8582 | if (operand_ty.childType(mod).zigTypeTag(mod) != .ErrorUnion) { | |
| 8573 | 8583 | return sema.fail(block, src, "expected error union type, found '{}'", .{ |
| 8574 | operand_ty.elemType().fmt(sema.mod), | |
| 8584 | operand_ty.childType(mod).fmt(sema.mod), | |
| 8575 | 8585 | }); |
| 8576 | 8586 | } |
| 8577 | 8587 | |
| 8578 | const err_union_ty = operand_ty.elemType(); | |
| 8588 | const err_union_ty = operand_ty.childType(mod); | |
| 8579 | 8589 | const payload_ty = err_union_ty.errorUnionPayload(); |
| 8580 | 8590 | const operand_pointer_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 8581 | 8591 | .pointee_type = payload_ty, |
| 8582 | 8592 | .mutable = !operand_ty.isConstPtr(), |
| 8583 | .@"addrspace" = operand_ty.ptrAddressSpace(), | |
| 8593 | .@"addrspace" = operand_ty.ptrAddressSpace(mod), | |
| 8584 | 8594 | }); |
| 8585 | 8595 | |
| 8586 | 8596 | if (try sema.resolveDefinedValue(block, src, operand)) |ptr_val| { |
| ... | ... | @@ -8596,7 +8606,7 @@ fn analyzeErrUnionPayloadPtr( |
| 8596 | 8606 | operand_pointer_ty, |
| 8597 | 8607 | try Value.Tag.eu_payload_ptr.create(sema.arena, .{ |
| 8598 | 8608 | .container_ptr = ptr_val, |
| 8599 | .container_ty = operand_ty.elemType(), | |
| 8609 | .container_ty = operand_ty.childType(mod), | |
| 8600 | 8610 | }), |
| 8601 | 8611 | ); |
| 8602 | 8612 | } |
| ... | ... | @@ -8609,7 +8619,7 @@ fn analyzeErrUnionPayloadPtr( |
| 8609 | 8619 | operand_pointer_ty, |
| 8610 | 8620 | try Value.Tag.eu_payload_ptr.create(sema.arena, .{ |
| 8611 | 8621 | .container_ptr = ptr_val, |
| 8612 | .container_ty = operand_ty.elemType(), | |
| 8622 | .container_ty = operand_ty.childType(mod), | |
| 8613 | 8623 | }), |
| 8614 | 8624 | ); |
| 8615 | 8625 | } |
| ... | ... | @@ -8674,13 +8684,13 @@ fn zirErrUnionCodePtr(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileE |
| 8674 | 8684 | const operand_ty = sema.typeOf(operand); |
| 8675 | 8685 | assert(operand_ty.zigTypeTag(mod) == .Pointer); |
| 8676 | 8686 | |
| 8677 | if (operand_ty.elemType().zigTypeTag(mod) != .ErrorUnion) { | |
| 8687 | if (operand_ty.childType(mod).zigTypeTag(mod) != .ErrorUnion) { | |
| 8678 | 8688 | return sema.fail(block, src, "expected error union type, found '{}'", .{ |
| 8679 | operand_ty.elemType().fmt(sema.mod), | |
| 8689 | operand_ty.childType(mod).fmt(sema.mod), | |
| 8680 | 8690 | }); |
| 8681 | 8691 | } |
| 8682 | 8692 | |
| 8683 | const result_ty = operand_ty.elemType().errorUnionSet(); | |
| 8693 | const result_ty = operand_ty.childType(mod).errorUnionSet(); | |
| 8684 | 8694 | |
| 8685 | 8695 | if (try sema.resolveDefinedValue(block, src, operand)) |pointer_val| { |
| 8686 | 8696 | if (try sema.pointerDeref(block, src, pointer_val, operand_ty)) |val| { |
| ... | ... | @@ -10119,7 +10129,7 @@ fn zirSwitchCapture( |
| 10119 | 10129 | const operand_is_ref = cond_tag == .switch_cond_ref; |
| 10120 | 10130 | const operand_ptr = try sema.resolveInst(cond_info.operand); |
| 10121 | 10131 | const operand_ptr_ty = sema.typeOf(operand_ptr); |
| 10122 | const operand_ty = if (operand_is_ref) operand_ptr_ty.childType() else operand_ptr_ty; | |
| 10132 | const operand_ty = if (operand_is_ref) operand_ptr_ty.childType(mod) else operand_ptr_ty; | |
| 10123 | 10133 | |
| 10124 | 10134 | if (block.inline_case_capture != .none) { |
| 10125 | 10135 | const item_val = sema.resolveConstValue(block, .unneeded, block.inline_case_capture, undefined) catch unreachable; |
| ... | ... | @@ -10131,9 +10141,9 @@ fn zirSwitchCapture( |
| 10131 | 10141 | if (is_ref) { |
| 10132 | 10142 | const ptr_field_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 10133 | 10143 | .pointee_type = field_ty, |
| 10134 | .mutable = operand_ptr_ty.ptrIsMutable(), | |
| 10144 | .mutable = operand_ptr_ty.ptrIsMutable(mod), | |
| 10135 | 10145 | .@"volatile" = operand_ptr_ty.isVolatilePtr(), |
| 10136 | .@"addrspace" = operand_ptr_ty.ptrAddressSpace(), | |
| 10146 | .@"addrspace" = operand_ptr_ty.ptrAddressSpace(mod), | |
| 10137 | 10147 | }); |
| 10138 | 10148 | return sema.addConstant( |
| 10139 | 10149 | ptr_field_ty, |
| ... | ... | @@ -10150,9 +10160,9 @@ fn zirSwitchCapture( |
| 10150 | 10160 | if (is_ref) { |
| 10151 | 10161 | const ptr_field_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 10152 | 10162 | .pointee_type = field_ty, |
| 10153 | .mutable = operand_ptr_ty.ptrIsMutable(), | |
| 10163 | .mutable = operand_ptr_ty.ptrIsMutable(mod), | |
| 10154 | 10164 | .@"volatile" = operand_ptr_ty.isVolatilePtr(), |
| 10155 | .@"addrspace" = operand_ptr_ty.ptrAddressSpace(), | |
| 10165 | .@"addrspace" = operand_ptr_ty.ptrAddressSpace(mod), | |
| 10156 | 10166 | }); |
| 10157 | 10167 | return block.addStructFieldPtr(operand_ptr, field_index, ptr_field_ty); |
| 10158 | 10168 | } else { |
| ... | ... | @@ -10235,7 +10245,7 @@ fn zirSwitchCapture( |
| 10235 | 10245 | const field_ty_ptr = try Type.ptr(sema.arena, sema.mod, .{ |
| 10236 | 10246 | .pointee_type = first_field.ty, |
| 10237 | 10247 | .@"addrspace" = .generic, |
| 10238 | .mutable = operand_ptr_ty.ptrIsMutable(), | |
| 10248 | .mutable = operand_ptr_ty.ptrIsMutable(mod), | |
| 10239 | 10249 | }); |
| 10240 | 10250 | |
| 10241 | 10251 | if (try sema.resolveDefinedValue(block, operand_src, operand_ptr)) |op_ptr_val| { |
| ... | ... | @@ -10311,7 +10321,7 @@ fn zirSwitchCaptureTag(sema: *Sema, block: *Block, inst: Zir.Inst.Index) Compile |
| 10311 | 10321 | const cond_data = zir_datas[Zir.refToIndex(inst_data.operand).?].un_node; |
| 10312 | 10322 | const operand_ptr = try sema.resolveInst(cond_data.operand); |
| 10313 | 10323 | const operand_ptr_ty = sema.typeOf(operand_ptr); |
| 10314 | const operand_ty = if (is_ref) operand_ptr_ty.childType() else operand_ptr_ty; | |
| 10324 | const operand_ty = if (is_ref) operand_ptr_ty.childType(mod) else operand_ptr_ty; | |
| 10315 | 10325 | |
| 10316 | 10326 | if (operand_ty.zigTypeTag(mod) != .Union) { |
| 10317 | 10327 | const msg = msg: { |
| ... | ... | @@ -10448,7 +10458,7 @@ fn zirSwitchBlock(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError |
| 10448 | 10458 | const cond_index = Zir.refToIndex(extra.data.operand).?; |
| 10449 | 10459 | const raw_operand = sema.resolveInst(zir_data[cond_index].un_node.operand) catch unreachable; |
| 10450 | 10460 | const target_ty = sema.typeOf(raw_operand); |
| 10451 | break :blk if (zir_tags[cond_index] == .switch_cond_ref) target_ty.elemType() else target_ty; | |
| 10461 | break :blk if (zir_tags[cond_index] == .switch_cond_ref) target_ty.childType(mod) else target_ty; | |
| 10452 | 10462 | }; |
| 10453 | 10463 | const union_originally = maybe_union_ty.zigTypeTag(mod) == .Union; |
| 10454 | 10464 | |
| ... | ... | @@ -12132,7 +12142,7 @@ fn zirEmbedFile(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!A |
| 12132 | 12142 | // into the final binary, and never loads the data into memory. |
| 12133 | 12143 | // - When a Decl is destroyed, it can free the `*Module.EmbedFile`. |
| 12134 | 12144 | embed_file.owner_decl = try anon_decl.finish( |
| 12135 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), embed_file.bytes.len), | |
| 12145 | try Type.array(anon_decl.arena(), embed_file.bytes.len, Value.zero, Type.u8, mod), | |
| 12136 | 12146 | try Value.Tag.bytes.create(anon_decl.arena(), bytes_including_null), |
| 12137 | 12147 | 0, // default alignment |
| 12138 | 12148 | ); |
| ... | ... | @@ -12200,7 +12210,7 @@ fn zirShl( |
| 12200 | 12210 | const bit_value = Value.initPayload(&bits_payload.base); |
| 12201 | 12211 | if (rhs_ty.zigTypeTag(mod) == .Vector) { |
| 12202 | 12212 | var i: usize = 0; |
| 12203 | while (i < rhs_ty.vectorLen()) : (i += 1) { | |
| 12213 | while (i < rhs_ty.vectorLen(mod)) : (i += 1) { | |
| 12204 | 12214 | var elem_value_buf: Value.ElemValueBuffer = undefined; |
| 12205 | 12215 | const rhs_elem = rhs_val.elemValueBuffer(sema.mod, i, &elem_value_buf); |
| 12206 | 12216 | if (rhs_elem.compareHetero(.gte, bit_value, mod)) { |
| ... | ... | @@ -12220,7 +12230,7 @@ fn zirShl( |
| 12220 | 12230 | } |
| 12221 | 12231 | if (rhs_ty.zigTypeTag(mod) == .Vector) { |
| 12222 | 12232 | var i: usize = 0; |
| 12223 | while (i < rhs_ty.vectorLen()) : (i += 1) { | |
| 12233 | while (i < rhs_ty.vectorLen(mod)) : (i += 1) { | |
| 12224 | 12234 | var elem_value_buf: Value.ElemValueBuffer = undefined; |
| 12225 | 12235 | const rhs_elem = rhs_val.elemValueBuffer(sema.mod, i, &elem_value_buf); |
| 12226 | 12236 | if (rhs_elem.compareHetero(.lt, Value.zero, mod)) { |
| ... | ... | @@ -12388,7 +12398,7 @@ fn zirShr( |
| 12388 | 12398 | const bit_value = Value.initPayload(&bits_payload.base); |
| 12389 | 12399 | if (rhs_ty.zigTypeTag(mod) == .Vector) { |
| 12390 | 12400 | var i: usize = 0; |
| 12391 | while (i < rhs_ty.vectorLen()) : (i += 1) { | |
| 12401 | while (i < rhs_ty.vectorLen(mod)) : (i += 1) { | |
| 12392 | 12402 | var elem_value_buf: Value.ElemValueBuffer = undefined; |
| 12393 | 12403 | const rhs_elem = rhs_val.elemValueBuffer(sema.mod, i, &elem_value_buf); |
| 12394 | 12404 | if (rhs_elem.compareHetero(.gte, bit_value, mod)) { |
| ... | ... | @@ -12408,7 +12418,7 @@ fn zirShr( |
| 12408 | 12418 | } |
| 12409 | 12419 | if (rhs_ty.zigTypeTag(mod) == .Vector) { |
| 12410 | 12420 | var i: usize = 0; |
| 12411 | while (i < rhs_ty.vectorLen()) : (i += 1) { | |
| 12421 | while (i < rhs_ty.vectorLen(mod)) : (i += 1) { | |
| 12412 | 12422 | var elem_value_buf: Value.ElemValueBuffer = undefined; |
| 12413 | 12423 | const rhs_elem = rhs_val.elemValueBuffer(sema.mod, i, &elem_value_buf); |
| 12414 | 12424 | if (rhs_elem.compareHetero(.lt, Value.zero, mod)) { |
| ... | ... | @@ -12571,7 +12581,7 @@ fn zirBitNot(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air. |
| 12571 | 12581 | if (val.isUndef()) { |
| 12572 | 12582 | return sema.addConstUndef(operand_type); |
| 12573 | 12583 | } else if (operand_type.zigTypeTag(mod) == .Vector) { |
| 12574 | const vec_len = try sema.usizeCast(block, operand_src, operand_type.vectorLen()); | |
| 12584 | const vec_len = try sema.usizeCast(block, operand_src, operand_type.vectorLen(mod)); | |
| 12575 | 12585 | var elem_val_buf: Value.ElemValueBuffer = undefined; |
| 12576 | 12586 | const elems = try sema.arena.alloc(Value, vec_len); |
| 12577 | 12587 | for (elems, 0..) |*elem, i| { |
| ... | ... | @@ -12768,8 +12778,8 @@ fn zirArrayCat(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 12768 | 12778 | const result_ty = try Type.array(sema.arena, result_len, res_sent_val, resolved_elem_ty, sema.mod); |
| 12769 | 12779 | const mod = sema.mod; |
| 12770 | 12780 | const ptr_addrspace = p: { |
| 12771 | if (lhs_ty.zigTypeTag(mod) == .Pointer) break :p lhs_ty.ptrAddressSpace(); | |
| 12772 | if (rhs_ty.zigTypeTag(mod) == .Pointer) break :p rhs_ty.ptrAddressSpace(); | |
| 12781 | if (lhs_ty.zigTypeTag(mod) == .Pointer) break :p lhs_ty.ptrAddressSpace(mod); | |
| 12782 | if (rhs_ty.zigTypeTag(mod) == .Pointer) break :p rhs_ty.ptrAddressSpace(mod); | |
| 12773 | 12783 | break :p null; |
| 12774 | 12784 | }; |
| 12775 | 12785 | |
| ... | ... | @@ -12883,9 +12893,9 @@ fn getArrayCatInfo(sema: *Sema, block: *Block, src: LazySrcLoc, operand: Air.Ins |
| 12883 | 12893 | const mod = sema.mod; |
| 12884 | 12894 | const operand_ty = sema.typeOf(operand); |
| 12885 | 12895 | switch (operand_ty.zigTypeTag(mod)) { |
| 12886 | .Array => return operand_ty.arrayInfo(), | |
| 12896 | .Array => return operand_ty.arrayInfo(mod), | |
| 12887 | 12897 | .Pointer => { |
| 12888 | const ptr_info = operand_ty.ptrInfo().data; | |
| 12898 | const ptr_info = operand_ty.ptrInfo(mod); | |
| 12889 | 12899 | switch (ptr_info.size) { |
| 12890 | 12900 | // TODO: in the Many case here this should only work if the type |
| 12891 | 12901 | // has a sentinel, and this code should compute the length based |
| ... | ... | @@ -12900,7 +12910,7 @@ fn getArrayCatInfo(sema: *Sema, block: *Block, src: LazySrcLoc, operand: Air.Ins |
| 12900 | 12910 | }, |
| 12901 | 12911 | .One => { |
| 12902 | 12912 | if (ptr_info.pointee_type.zigTypeTag(mod) == .Array) { |
| 12903 | return ptr_info.pointee_type.arrayInfo(); | |
| 12913 | return ptr_info.pointee_type.arrayInfo(mod); | |
| 12904 | 12914 | } |
| 12905 | 12915 | }, |
| 12906 | 12916 | .C => {}, |
| ... | ... | @@ -12912,7 +12922,7 @@ fn getArrayCatInfo(sema: *Sema, block: *Block, src: LazySrcLoc, operand: Air.Ins |
| 12912 | 12922 | return .{ |
| 12913 | 12923 | .elem_type = peer_ty.elemType2(mod), |
| 12914 | 12924 | .sentinel = null, |
| 12915 | .len = operand_ty.arrayLen(), | |
| 12925 | .len = operand_ty.arrayLen(mod), | |
| 12916 | 12926 | }; |
| 12917 | 12927 | } |
| 12918 | 12928 | }, |
| ... | ... | @@ -13035,7 +13045,7 @@ fn zirArrayMul(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 13035 | 13045 | |
| 13036 | 13046 | const result_ty = try Type.array(sema.arena, result_len, lhs_info.sentinel, lhs_info.elem_type, sema.mod); |
| 13037 | 13047 | |
| 13038 | const ptr_addrspace = if (lhs_ty.zigTypeTag(mod) == .Pointer) lhs_ty.ptrAddressSpace() else null; | |
| 13048 | const ptr_addrspace = if (lhs_ty.zigTypeTag(mod) == .Pointer) lhs_ty.ptrAddressSpace(mod) else null; | |
| 13039 | 13049 | const lhs_len = try sema.usizeCast(block, lhs_src, lhs_info.len); |
| 13040 | 13050 | |
| 13041 | 13051 | if (try sema.resolveDefinedValue(block, lhs_src, lhs)) |lhs_val| { |
| ... | ... | @@ -14022,7 +14032,7 @@ fn intRem( |
| 14022 | 14032 | ) CompileError!Value { |
| 14023 | 14033 | const mod = sema.mod; |
| 14024 | 14034 | if (ty.zigTypeTag(mod) == .Vector) { |
| 14025 | const result_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 14035 | const result_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 14026 | 14036 | for (result_data, 0..) |*scalar, i| { |
| 14027 | 14037 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 14028 | 14038 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -14484,7 +14494,10 @@ fn maybeRepeated(sema: *Sema, ty: Type, val: Value) !Value { |
| 14484 | 14494 | |
| 14485 | 14495 | fn overflowArithmeticTupleType(sema: *Sema, ty: Type) !Type { |
| 14486 | 14496 | const mod = sema.mod; |
| 14487 | const ov_ty = if (ty.zigTypeTag(mod) == .Vector) try Type.vector(sema.arena, ty.vectorLen(), Type.u1) else Type.u1; | |
| 14497 | const ov_ty = if (ty.zigTypeTag(mod) == .Vector) try mod.vectorType(.{ | |
| 14498 | .len = ty.vectorLen(mod), | |
| 14499 | .child = .u1_type, | |
| 14500 | }) else Type.u1; | |
| 14488 | 14501 | |
| 14489 | 14502 | const types = try sema.arena.alloc(Type, 2); |
| 14490 | 14503 | const values = try sema.arena.alloc(Value, 2); |
| ... | ... | @@ -14520,7 +14533,7 @@ fn analyzeArithmetic( |
| 14520 | 14533 | const rhs_zig_ty_tag = try rhs_ty.zigTypeTagOrPoison(mod); |
| 14521 | 14534 | try sema.checkVectorizableBinaryOperands(block, src, lhs_ty, rhs_ty, lhs_src, rhs_src); |
| 14522 | 14535 | |
| 14523 | if (lhs_zig_ty_tag == .Pointer) switch (lhs_ty.ptrSize()) { | |
| 14536 | if (lhs_zig_ty_tag == .Pointer) switch (lhs_ty.ptrSize(mod)) { | |
| 14524 | 14537 | .One, .Slice => {}, |
| 14525 | 14538 | .Many, .C => { |
| 14526 | 14539 | const air_tag: Air.Inst.Tag = switch (zir_tag) { |
| ... | ... | @@ -14993,9 +15006,9 @@ fn analyzePtrArithmetic( |
| 14993 | 15006 | const opt_ptr_val = try sema.resolveMaybeUndefVal(ptr); |
| 14994 | 15007 | const opt_off_val = try sema.resolveDefinedValue(block, offset_src, offset); |
| 14995 | 15008 | const ptr_ty = sema.typeOf(ptr); |
| 14996 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 15009 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 14997 | 15010 | const elem_ty = if (ptr_info.size == .One and ptr_info.pointee_type.zigTypeTag(mod) == .Array) |
| 14998 | ptr_info.pointee_type.childType() | |
| 15011 | ptr_info.pointee_type.childType(mod) | |
| 14999 | 15012 | else |
| 15000 | 15013 | ptr_info.pointee_type; |
| 15001 | 15014 | |
| ... | ... | @@ -15466,7 +15479,10 @@ fn cmpSelf( |
| 15466 | 15479 | if (rhs_val.isUndef()) return sema.addConstUndef(Type.bool); |
| 15467 | 15480 | |
| 15468 | 15481 | if (resolved_type.zigTypeTag(mod) == .Vector) { |
| 15469 | const result_ty = try Type.vector(sema.arena, resolved_type.vectorLen(), Type.bool); | |
| 15482 | const result_ty = try mod.vectorType(.{ | |
| 15483 | .len = resolved_type.vectorLen(mod), | |
| 15484 | .child = .bool_type, | |
| 15485 | }); | |
| 15470 | 15486 | const cmp_val = try sema.compareVector(lhs_val, op, rhs_val, resolved_type); |
| 15471 | 15487 | return sema.addConstant(result_ty, cmp_val); |
| 15472 | 15488 | } |
| ... | ... | @@ -15767,6 +15783,7 @@ fn zirBuiltinSrc( |
| 15767 | 15783 | const tracy = trace(@src()); |
| 15768 | 15784 | defer tracy.end(); |
| 15769 | 15785 | |
| 15786 | const mod = sema.mod; | |
| 15770 | 15787 | const extra = sema.code.extraData(Zir.Inst.Src, extended.operand).data; |
| 15771 | 15788 | const src = LazySrcLoc.nodeOffset(extra.node); |
| 15772 | 15789 | const func = sema.func orelse return sema.fail(block, src, "@src outside function", .{}); |
| ... | ... | @@ -15778,7 +15795,7 @@ fn zirBuiltinSrc( |
| 15778 | 15795 | const name = std.mem.span(fn_owner_decl.name); |
| 15779 | 15796 | const bytes = try anon_decl.arena().dupe(u8, name[0 .. name.len + 1]); |
| 15780 | 15797 | const new_decl = try anon_decl.finish( |
| 15781 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len - 1), | |
| 15798 | try Type.array(anon_decl.arena(), bytes.len - 1, Value.zero, Type.u8, mod), | |
| 15782 | 15799 | try Value.Tag.bytes.create(anon_decl.arena(), bytes), |
| 15783 | 15800 | 0, // default alignment |
| 15784 | 15801 | ); |
| ... | ... | @@ -15791,7 +15808,7 @@ fn zirBuiltinSrc( |
| 15791 | 15808 | // The compiler must not call realpath anywhere. |
| 15792 | 15809 | const name = try fn_owner_decl.getFileScope().fullPathZ(anon_decl.arena()); |
| 15793 | 15810 | const new_decl = try anon_decl.finish( |
| 15794 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), name.len), | |
| 15811 | try Type.array(anon_decl.arena(), name.len, Value.zero, Type.u8, mod), | |
| 15795 | 15812 | try Value.Tag.bytes.create(anon_decl.arena(), name[0 .. name.len + 1]), |
| 15796 | 15813 | 0, // default alignment |
| 15797 | 15814 | ); |
| ... | ... | @@ -16024,7 +16041,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16024 | 16041 | ); |
| 16025 | 16042 | }, |
| 16026 | 16043 | .Pointer => { |
| 16027 | const info = ty.ptrInfo().data; | |
| 16044 | const info = ty.ptrInfo(mod); | |
| 16028 | 16045 | const alignment = if (info.@"align" != 0) |
| 16029 | 16046 | try Value.Tag.int_u64.create(sema.arena, info.@"align") |
| 16030 | 16047 | else |
| ... | ... | @@ -16059,7 +16076,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16059 | 16076 | ); |
| 16060 | 16077 | }, |
| 16061 | 16078 | .Array => { |
| 16062 | const info = ty.arrayInfo(); | |
| 16079 | const info = ty.arrayInfo(mod); | |
| 16063 | 16080 | const field_values = try sema.arena.alloc(Value, 3); |
| 16064 | 16081 | // len: comptime_int, |
| 16065 | 16082 | field_values[0] = try Value.Tag.int_u64.create(sema.arena, info.len); |
| ... | ... | @@ -16077,7 +16094,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16077 | 16094 | ); |
| 16078 | 16095 | }, |
| 16079 | 16096 | .Vector => { |
| 16080 | const info = ty.arrayInfo(); | |
| 16097 | const info = ty.arrayInfo(mod); | |
| 16081 | 16098 | const field_values = try sema.arena.alloc(Value, 2); |
| 16082 | 16099 | // len: comptime_int, |
| 16083 | 16100 | field_values[0] = try Value.Tag.int_u64.create(sema.arena, info.len); |
| ... | ... | @@ -16095,7 +16112,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16095 | 16112 | .Optional => { |
| 16096 | 16113 | const field_values = try sema.arena.alloc(Value, 1); |
| 16097 | 16114 | // child: type, |
| 16098 | field_values[0] = try Value.Tag.ty.create(sema.arena, try ty.optionalChildAlloc(sema.arena)); | |
| 16115 | field_values[0] = try Value.Tag.ty.create(sema.arena, ty.optionalChild(mod)); | |
| 16099 | 16116 | |
| 16100 | 16117 | return sema.addConstant( |
| 16101 | 16118 | type_info_ty, |
| ... | ... | @@ -16141,7 +16158,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16141 | 16158 | defer anon_decl.deinit(); |
| 16142 | 16159 | const bytes = try anon_decl.arena().dupeZ(u8, name); |
| 16143 | 16160 | const new_decl = try anon_decl.finish( |
| 16144 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 16161 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 16145 | 16162 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 16146 | 16163 | 0, // default alignment |
| 16147 | 16164 | ); |
| ... | ... | @@ -16250,7 +16267,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16250 | 16267 | defer anon_decl.deinit(); |
| 16251 | 16268 | const bytes = try anon_decl.arena().dupeZ(u8, name); |
| 16252 | 16269 | const new_decl = try anon_decl.finish( |
| 16253 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 16270 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 16254 | 16271 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 16255 | 16272 | 0, // default alignment |
| 16256 | 16273 | ); |
| ... | ... | @@ -16338,7 +16355,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16338 | 16355 | defer anon_decl.deinit(); |
| 16339 | 16356 | const bytes = try anon_decl.arena().dupeZ(u8, name); |
| 16340 | 16357 | const new_decl = try anon_decl.finish( |
| 16341 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 16358 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 16342 | 16359 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 16343 | 16360 | 0, // default alignment |
| 16344 | 16361 | ); |
| ... | ... | @@ -16448,7 +16465,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16448 | 16465 | else |
| 16449 | 16466 | try std.fmt.allocPrintZ(anon_decl.arena(), "{d}", .{i}); |
| 16450 | 16467 | const new_decl = try anon_decl.finish( |
| 16451 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 16468 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 16452 | 16469 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 16453 | 16470 | 0, // default alignment |
| 16454 | 16471 | ); |
| ... | ... | @@ -16490,7 +16507,7 @@ fn zirTypeInfo(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 16490 | 16507 | defer anon_decl.deinit(); |
| 16491 | 16508 | const bytes = try anon_decl.arena().dupeZ(u8, name); |
| 16492 | 16509 | const new_decl = try anon_decl.finish( |
| 16493 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 16510 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 16494 | 16511 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 16495 | 16512 | 0, // default alignment |
| 16496 | 16513 | ); |
| ... | ... | @@ -16666,14 +16683,15 @@ fn typeInfoNamespaceDecls( |
| 16666 | 16683 | decl_vals: *std.ArrayList(Value), |
| 16667 | 16684 | seen_namespaces: *std.AutoHashMap(*Namespace, void), |
| 16668 | 16685 | ) !void { |
| 16686 | const mod = sema.mod; | |
| 16669 | 16687 | const gop = try seen_namespaces.getOrPut(namespace); |
| 16670 | 16688 | if (gop.found_existing) return; |
| 16671 | 16689 | const decls = namespace.decls.keys(); |
| 16672 | 16690 | for (decls) |decl_index| { |
| 16673 | const decl = sema.mod.declPtr(decl_index); | |
| 16691 | const decl = mod.declPtr(decl_index); | |
| 16674 | 16692 | if (decl.kind == .@"usingnamespace") { |
| 16675 | 16693 | if (decl.analysis == .in_progress) continue; |
| 16676 | try sema.mod.ensureDeclAnalyzed(decl_index); | |
| 16694 | try mod.ensureDeclAnalyzed(decl_index); | |
| 16677 | 16695 | const new_ns = decl.val.toType().getNamespace().?; |
| 16678 | 16696 | try sema.typeInfoNamespaceDecls(block, decls_anon_decl, new_ns, decl_vals, seen_namespaces); |
| 16679 | 16697 | continue; |
| ... | ... | @@ -16684,7 +16702,7 @@ fn typeInfoNamespaceDecls( |
| 16684 | 16702 | defer anon_decl.deinit(); |
| 16685 | 16703 | const bytes = try anon_decl.arena().dupeZ(u8, mem.sliceTo(decl.name, 0)); |
| 16686 | 16704 | const new_decl = try anon_decl.finish( |
| 16687 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 16705 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 16688 | 16706 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 16689 | 16707 | 0, // default alignment |
| 16690 | 16708 | ); |
| ... | ... | @@ -16770,9 +16788,9 @@ fn log2IntType(sema: *Sema, block: *Block, operand: Type, src: LazySrcLoc) Compi |
| 16770 | 16788 | .Vector => { |
| 16771 | 16789 | const elem_ty = operand.elemType2(mod); |
| 16772 | 16790 | const log2_elem_ty = try sema.log2IntType(block, elem_ty, src); |
| 16773 | return Type.Tag.vector.create(sema.arena, .{ | |
| 16774 | .len = operand.vectorLen(), | |
| 16775 | .elem_type = log2_elem_ty, | |
| 16791 | return mod.vectorType(.{ | |
| 16792 | .len = operand.vectorLen(mod), | |
| 16793 | .child = log2_elem_ty.ip_index, | |
| 16776 | 16794 | }); |
| 16777 | 16795 | }, |
| 16778 | 16796 | else => {}, |
| ... | ... | @@ -17207,7 +17225,7 @@ fn zirTryPtr(sema: *Sema, parent_block: *Block, inst: Zir.Inst.Index) CompileErr |
| 17207 | 17225 | _ = try sema.analyzeBodyInner(&sub_block, body); |
| 17208 | 17226 | |
| 17209 | 17227 | const operand_ty = sema.typeOf(operand); |
| 17210 | const ptr_info = operand_ty.ptrInfo().data; | |
| 17228 | const ptr_info = operand_ty.ptrInfo(mod); | |
| 17211 | 17229 | const res_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 17212 | 17230 | .pointee_type = err_union_ty.errorUnionPayload(), |
| 17213 | 17231 | .@"addrspace" = ptr_info.@"addrspace", |
| ... | ... | @@ -17398,6 +17416,7 @@ fn retWithErrTracing( |
| 17398 | 17416 | ret_tag: Air.Inst.Tag, |
| 17399 | 17417 | operand: Air.Inst.Ref, |
| 17400 | 17418 | ) CompileError!Zir.Inst.Index { |
| 17419 | const mod = sema.mod; | |
| 17401 | 17420 | const need_check = switch (is_non_err) { |
| 17402 | 17421 | .bool_true => { |
| 17403 | 17422 | _ = try block.addUnOp(ret_tag, operand); |
| ... | ... | @@ -17409,7 +17428,7 @@ fn retWithErrTracing( |
| 17409 | 17428 | const gpa = sema.gpa; |
| 17410 | 17429 | const unresolved_stack_trace_ty = try sema.getBuiltinType("StackTrace"); |
| 17411 | 17430 | const stack_trace_ty = try sema.resolveTypeFields(unresolved_stack_trace_ty); |
| 17412 | const ptr_stack_trace_ty = try Type.Tag.single_mut_pointer.create(sema.arena, stack_trace_ty); | |
| 17431 | const ptr_stack_trace_ty = try mod.singleMutPtrType(stack_trace_ty); | |
| 17413 | 17432 | const err_return_trace = try block.addTy(.err_return_trace, ptr_stack_trace_ty); |
| 17414 | 17433 | const return_err_fn = try sema.getBuiltin("returnError"); |
| 17415 | 17434 | const args: [1]Air.Inst.Ref = .{err_return_trace}; |
| ... | ... | @@ -17755,7 +17774,7 @@ fn structInitEmpty( |
| 17755 | 17774 | |
| 17756 | 17775 | fn arrayInitEmpty(sema: *Sema, block: *Block, src: LazySrcLoc, obj_ty: Type) CompileError!Air.Inst.Ref { |
| 17757 | 17776 | const mod = sema.mod; |
| 17758 | const arr_len = obj_ty.arrayLen(); | |
| 17777 | const arr_len = obj_ty.arrayLen(mod); | |
| 17759 | 17778 | if (arr_len != 0) { |
| 17760 | 17779 | if (obj_ty.zigTypeTag(mod) == .Array) { |
| 17761 | 17780 | return sema.fail(block, src, "expected {d} array elements; found 0", .{arr_len}); |
| ... | ... | @@ -17763,7 +17782,7 @@ fn arrayInitEmpty(sema: *Sema, block: *Block, src: LazySrcLoc, obj_ty: Type) Com |
| 17763 | 17782 | return sema.fail(block, src, "expected {d} vector elements; found 0", .{arr_len}); |
| 17764 | 17783 | } |
| 17765 | 17784 | } |
| 17766 | if (obj_ty.sentinel()) |sentinel| { | |
| 17785 | if (obj_ty.sentinel(mod)) |sentinel| { | |
| 17767 | 17786 | const val = try Value.Tag.empty_array_sentinel.create(sema.arena, sentinel); |
| 17768 | 17787 | return sema.addConstant(obj_ty, val); |
| 17769 | 17788 | } else { |
| ... | ... | @@ -18199,6 +18218,7 @@ fn zirArrayInit( |
| 18199 | 18218 | inst: Zir.Inst.Index, |
| 18200 | 18219 | is_ref: bool, |
| 18201 | 18220 | ) CompileError!Air.Inst.Ref { |
| 18221 | const mod = sema.mod; | |
| 18202 | 18222 | const gpa = sema.gpa; |
| 18203 | 18223 | const inst_data = sema.code.instructions.items(.data)[inst].pl_node; |
| 18204 | 18224 | const src = inst_data.src(); |
| ... | ... | @@ -18208,8 +18228,7 @@ fn zirArrayInit( |
| 18208 | 18228 | assert(args.len >= 2); // array_ty + at least one element |
| 18209 | 18229 | |
| 18210 | 18230 | const array_ty = try sema.resolveType(block, src, args[0]); |
| 18211 | const sentinel_val = array_ty.sentinel(); | |
| 18212 | const mod = sema.mod; | |
| 18231 | const sentinel_val = array_ty.sentinel(mod); | |
| 18213 | 18232 | |
| 18214 | 18233 | const resolved_args = try gpa.alloc(Air.Inst.Ref, args.len - 1 + @boolToInt(sentinel_val != null)); |
| 18215 | 18234 | defer gpa.free(resolved_args); |
| ... | ... | @@ -18489,14 +18508,16 @@ fn zirErrorReturnTrace(sema: *Sema, block: *Block) CompileError!Air.Inst.Ref { |
| 18489 | 18508 | } |
| 18490 | 18509 | |
| 18491 | 18510 | fn getErrorReturnTrace(sema: *Sema, block: *Block) CompileError!Air.Inst.Ref { |
| 18511 | const mod = sema.mod; | |
| 18492 | 18512 | const unresolved_stack_trace_ty = try sema.getBuiltinType("StackTrace"); |
| 18493 | 18513 | const stack_trace_ty = try sema.resolveTypeFields(unresolved_stack_trace_ty); |
| 18494 | const opt_ptr_stack_trace_ty = try Type.Tag.optional_single_mut_pointer.create(sema.arena, stack_trace_ty); | |
| 18514 | const ptr_stack_trace_ty = try mod.singleMutPtrType(stack_trace_ty); | |
| 18515 | const opt_ptr_stack_trace_ty = try Type.optional(sema.arena, ptr_stack_trace_ty, mod); | |
| 18495 | 18516 | |
| 18496 | 18517 | if (sema.owner_func != null and |
| 18497 | 18518 | sema.owner_func.?.calls_or_awaits_errorable_fn and |
| 18498 | sema.mod.comp.bin_file.options.error_return_tracing and | |
| 18499 | sema.mod.backendSupportsFeature(.error_return_trace)) | |
| 18519 | mod.comp.bin_file.options.error_return_tracing and | |
| 18520 | mod.backendSupportsFeature(.error_return_trace)) | |
| 18500 | 18521 | { |
| 18501 | 18522 | return block.addTy(.err_return_trace, opt_ptr_stack_trace_ty); |
| 18502 | 18523 | } |
| ... | ... | @@ -18585,8 +18606,11 @@ fn zirUnaryMath( |
| 18585 | 18606 | switch (operand_ty.zigTypeTag(mod)) { |
| 18586 | 18607 | .Vector => { |
| 18587 | 18608 | const scalar_ty = operand_ty.scalarType(mod); |
| 18588 | const vec_len = operand_ty.vectorLen(); | |
| 18589 | const result_ty = try Type.vector(sema.arena, vec_len, scalar_ty); | |
| 18609 | const vec_len = operand_ty.vectorLen(mod); | |
| 18610 | const result_ty = try mod.vectorType(.{ | |
| 18611 | .len = vec_len, | |
| 18612 | .child = scalar_ty.ip_index, | |
| 18613 | }); | |
| 18590 | 18614 | if (try sema.resolveMaybeUndefVal(operand)) |val| { |
| 18591 | 18615 | if (val.isUndef()) |
| 18592 | 18616 | return sema.addConstUndef(result_ty); |
| ... | ... | @@ -18730,12 +18754,15 @@ fn zirReify(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData, in |
| 18730 | 18754 | const len_val = struct_val[0]; |
| 18731 | 18755 | const child_val = struct_val[1]; |
| 18732 | 18756 | |
| 18733 | const len = len_val.toUnsignedInt(mod); | |
| 18757 | const len = @intCast(u32, len_val.toUnsignedInt(mod)); | |
| 18734 | 18758 | const child_ty = child_val.toType(); |
| 18735 | 18759 | |
| 18736 | 18760 | try sema.checkVectorElemType(block, src, child_ty); |
| 18737 | 18761 | |
| 18738 | const ty = try Type.vector(sema.arena, len, try child_ty.copy(sema.arena)); | |
| 18762 | const ty = try mod.vectorType(.{ | |
| 18763 | .len = len, | |
| 18764 | .child = child_ty.ip_index, | |
| 18765 | }); | |
| 18739 | 18766 | return sema.addType(ty); |
| 18740 | 18767 | }, |
| 18741 | 18768 | .Float => { |
| ... | ... | @@ -18872,7 +18899,7 @@ fn zirReify(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData, in |
| 18872 | 18899 | |
| 18873 | 18900 | const child_ty = try child_val.toType().copy(sema.arena); |
| 18874 | 18901 | |
| 18875 | const ty = try Type.optional(sema.arena, child_ty); | |
| 18902 | const ty = try Type.optional(sema.arena, child_ty, mod); | |
| 18876 | 18903 | return sema.addType(ty); |
| 18877 | 18904 | }, |
| 18878 | 18905 | .ErrorUnion => { |
| ... | ... | @@ -18912,7 +18939,7 @@ fn zirReify(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData, in |
| 18912 | 18939 | // TODO use reflection instead of magic numbers here |
| 18913 | 18940 | // error_set: type, |
| 18914 | 18941 | const name_val = struct_val[0]; |
| 18915 | const name_str = try name_val.toAllocatedBytes(Type.initTag(.const_slice_u8), sema.arena, sema.mod); | |
| 18942 | const name_str = try name_val.toAllocatedBytes(Type.const_slice_u8, sema.arena, sema.mod); | |
| 18916 | 18943 | |
| 18917 | 18944 | const kv = try mod.getErrorValue(name_str); |
| 18918 | 18945 | const gop = names.getOrPutAssumeCapacity(kv.key); |
| ... | ... | @@ -19038,7 +19065,7 @@ fn zirReify(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData, in |
| 19038 | 19065 | const value_val = field_struct_val[1]; |
| 19039 | 19066 | |
| 19040 | 19067 | const field_name = try name_val.toAllocatedBytes( |
| 19041 | Type.initTag(.const_slice_u8), | |
| 19068 | Type.const_slice_u8, | |
| 19042 | 19069 | new_decl_arena_allocator, |
| 19043 | 19070 | sema.mod, |
| 19044 | 19071 | ); |
| ... | ... | @@ -19215,7 +19242,7 @@ fn zirReify(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData, in |
| 19215 | 19242 | const alignment_val = field_struct_val[2]; |
| 19216 | 19243 | |
| 19217 | 19244 | const field_name = try name_val.toAllocatedBytes( |
| 19218 | Type.initTag(.const_slice_u8), | |
| 19245 | Type.const_slice_u8, | |
| 19219 | 19246 | new_decl_arena_allocator, |
| 19220 | 19247 | sema.mod, |
| 19221 | 19248 | ); |
| ... | ... | @@ -19482,7 +19509,7 @@ fn reifyStruct( |
| 19482 | 19509 | } |
| 19483 | 19510 | |
| 19484 | 19511 | const field_name = try name_val.toAllocatedBytes( |
| 19485 | Type.initTag(.const_slice_u8), | |
| 19512 | Type.const_slice_u8, | |
| 19486 | 19513 | new_decl_arena_allocator, |
| 19487 | 19514 | mod, |
| 19488 | 19515 | ); |
| ... | ... | @@ -19626,7 +19653,7 @@ fn zirAddrSpaceCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.Inst |
| 19626 | 19653 | |
| 19627 | 19654 | try sema.checkPtrOperand(block, ptr_src, ptr_ty); |
| 19628 | 19655 | |
| 19629 | var ptr_info = ptr_ty.ptrInfo().data; | |
| 19656 | var ptr_info = ptr_ty.ptrInfo(mod); | |
| 19630 | 19657 | const src_addrspace = ptr_info.@"addrspace"; |
| 19631 | 19658 | if (!target_util.addrSpaceCastIsValid(sema.mod.getTarget(), src_addrspace, dest_addrspace)) { |
| 19632 | 19659 | const msg = msg: { |
| ... | ... | @@ -19641,7 +19668,7 @@ fn zirAddrSpaceCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.Inst |
| 19641 | 19668 | ptr_info.@"addrspace" = dest_addrspace; |
| 19642 | 19669 | const dest_ptr_ty = try Type.ptr(sema.arena, sema.mod, ptr_info); |
| 19643 | 19670 | const dest_ty = if (ptr_ty.zigTypeTag(mod) == .Optional) |
| 19644 | try Type.optional(sema.arena, dest_ptr_ty) | |
| 19671 | try Type.optional(sema.arena, dest_ptr_ty, mod) | |
| 19645 | 19672 | else |
| 19646 | 19673 | dest_ptr_ty; |
| 19647 | 19674 | |
| ... | ... | @@ -19731,6 +19758,7 @@ fn zirCVaStart(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData) |
| 19731 | 19758 | } |
| 19732 | 19759 | |
| 19733 | 19760 | fn zirTypeName(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { |
| 19761 | const mod = sema.mod; | |
| 19734 | 19762 | const inst_data = sema.code.instructions.items(.data)[inst].un_node; |
| 19735 | 19763 | const ty_src: LazySrcLoc = .{ .node_offset_builtin_call_arg0 = inst_data.src_node }; |
| 19736 | 19764 | const ty = try sema.resolveType(block, ty_src, inst_data.operand); |
| ... | ... | @@ -19738,10 +19766,10 @@ fn zirTypeName(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 19738 | 19766 | var anon_decl = try block.startAnonDecl(); |
| 19739 | 19767 | defer anon_decl.deinit(); |
| 19740 | 19768 | |
| 19741 | const bytes = try ty.nameAllocArena(anon_decl.arena(), sema.mod); | |
| 19769 | const bytes = try ty.nameAllocArena(anon_decl.arena(), mod); | |
| 19742 | 19770 | |
| 19743 | 19771 | const new_decl = try anon_decl.finish( |
| 19744 | try Type.Tag.array_u8_sentinel_0.create(anon_decl.arena(), bytes.len), | |
| 19772 | try Type.array(anon_decl.arena(), bytes.len, Value.zero, Type.u8, mod), | |
| 19745 | 19773 | try Value.Tag.bytes.create(anon_decl.arena(), bytes[0 .. bytes.len + 1]), |
| 19746 | 19774 | 0, // default alignment |
| 19747 | 19775 | ); |
| ... | ... | @@ -19842,7 +19870,7 @@ fn zirIntToPtr(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 19842 | 19870 | const elem_ty = ptr_ty.elemType2(mod); |
| 19843 | 19871 | const ptr_align = try ptr_ty.ptrAlignmentAdvanced(mod, sema); |
| 19844 | 19872 | |
| 19845 | if (ptr_ty.isSlice()) { | |
| 19873 | if (ptr_ty.isSlice(mod)) { | |
| 19846 | 19874 | const msg = msg: { |
| 19847 | 19875 | const msg = try sema.errMsg(block, type_src, "integer cannot be converted to slice type '{}'", .{ptr_ty.fmt(sema.mod)}); |
| 19848 | 19876 | errdefer msg.destroy(sema.gpa); |
| ... | ... | @@ -19987,8 +20015,8 @@ fn zirPtrCast(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air |
| 19987 | 20015 | try sema.checkPtrType(block, dest_ty_src, dest_ty); |
| 19988 | 20016 | try sema.checkPtrOperand(block, operand_src, operand_ty); |
| 19989 | 20017 | |
| 19990 | const operand_info = operand_ty.ptrInfo().data; | |
| 19991 | const dest_info = dest_ty.ptrInfo().data; | |
| 20018 | const operand_info = operand_ty.ptrInfo(mod); | |
| 20019 | const dest_info = dest_ty.ptrInfo(mod); | |
| 19992 | 20020 | if (!operand_info.mutable and dest_info.mutable) { |
| 19993 | 20021 | const msg = msg: { |
| 19994 | 20022 | const msg = try sema.errMsg(block, src, "cast discards const qualifier", .{}); |
| ... | ... | @@ -20042,12 +20070,11 @@ fn zirPtrCast(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air |
| 20042 | 20070 | const aligned_dest_ty = if (operand_align <= dest_align) dest_ty else blk: { |
| 20043 | 20071 | // Unwrap the pointer (or pointer-like optional) type, set alignment, and re-wrap into result |
| 20044 | 20072 | if (dest_ty.zigTypeTag(mod) == .Optional) { |
| 20045 | var buf: Type.Payload.ElemType = undefined; | |
| 20046 | var dest_ptr_info = dest_ty.optionalChild(&buf).ptrInfo().data; | |
| 20073 | var dest_ptr_info = dest_ty.optionalChild(mod).ptrInfo(mod); | |
| 20047 | 20074 | dest_ptr_info.@"align" = operand_align; |
| 20048 | break :blk try Type.optional(sema.arena, try Type.ptr(sema.arena, sema.mod, dest_ptr_info)); | |
| 20075 | break :blk try Type.optional(sema.arena, try Type.ptr(sema.arena, sema.mod, dest_ptr_info), mod); | |
| 20049 | 20076 | } else { |
| 20050 | var dest_ptr_info = dest_ty.ptrInfo().data; | |
| 20077 | var dest_ptr_info = dest_ty.ptrInfo(mod); | |
| 20051 | 20078 | dest_ptr_info.@"align" = operand_align; |
| 20052 | 20079 | break :blk try Type.ptr(sema.arena, sema.mod, dest_ptr_info); |
| 20053 | 20080 | } |
| ... | ... | @@ -20110,6 +20137,7 @@ fn zirPtrCast(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air |
| 20110 | 20137 | } |
| 20111 | 20138 | |
| 20112 | 20139 | fn zirConstCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData) CompileError!Air.Inst.Ref { |
| 20140 | const mod = sema.mod; | |
| 20113 | 20141 | const extra = sema.code.extraData(Zir.Inst.UnNode, extended.operand).data; |
| 20114 | 20142 | const src = LazySrcLoc.nodeOffset(extra.node); |
| 20115 | 20143 | const operand_src: LazySrcLoc = .{ .node_offset_builtin_call_arg0 = extra.node }; |
| ... | ... | @@ -20117,7 +20145,7 @@ fn zirConstCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData |
| 20117 | 20145 | const operand_ty = sema.typeOf(operand); |
| 20118 | 20146 | try sema.checkPtrOperand(block, operand_src, operand_ty); |
| 20119 | 20147 | |
| 20120 | var ptr_info = operand_ty.ptrInfo().data; | |
| 20148 | var ptr_info = operand_ty.ptrInfo(mod); | |
| 20121 | 20149 | ptr_info.mutable = true; |
| 20122 | 20150 | const dest_ty = try Type.ptr(sema.arena, sema.mod, ptr_info); |
| 20123 | 20151 | |
| ... | ... | @@ -20130,6 +20158,7 @@ fn zirConstCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData |
| 20130 | 20158 | } |
| 20131 | 20159 | |
| 20132 | 20160 | fn zirVolatileCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData) CompileError!Air.Inst.Ref { |
| 20161 | const mod = sema.mod; | |
| 20133 | 20162 | const extra = sema.code.extraData(Zir.Inst.UnNode, extended.operand).data; |
| 20134 | 20163 | const src = LazySrcLoc.nodeOffset(extra.node); |
| 20135 | 20164 | const operand_src: LazySrcLoc = .{ .node_offset_builtin_call_arg0 = extra.node }; |
| ... | ... | @@ -20137,7 +20166,7 @@ fn zirVolatileCast(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstD |
| 20137 | 20166 | const operand_ty = sema.typeOf(operand); |
| 20138 | 20167 | try sema.checkPtrOperand(block, operand_src, operand_ty); |
| 20139 | 20168 | |
| 20140 | var ptr_info = operand_ty.ptrInfo().data; | |
| 20169 | var ptr_info = operand_ty.ptrInfo(mod); | |
| 20141 | 20170 | ptr_info.@"volatile" = false; |
| 20142 | 20171 | const dest_ty = try Type.ptr(sema.arena, sema.mod, ptr_info); |
| 20143 | 20172 | |
| ... | ... | @@ -20163,7 +20192,10 @@ fn zirTruncate(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 20163 | 20192 | const operand_scalar_ty = try sema.checkIntOrVectorAllowComptime(block, operand_ty, operand_src); |
| 20164 | 20193 | const is_vector = operand_ty.zigTypeTag(mod) == .Vector; |
| 20165 | 20194 | const dest_ty = if (is_vector) |
| 20166 | try Type.vector(sema.arena, operand_ty.vectorLen(), dest_scalar_ty) | |
| 20195 | try mod.vectorType(.{ | |
| 20196 | .len = operand_ty.vectorLen(mod), | |
| 20197 | .child = dest_scalar_ty.ip_index, | |
| 20198 | }) | |
| 20167 | 20199 | else |
| 20168 | 20200 | dest_scalar_ty; |
| 20169 | 20201 | |
| ... | ... | @@ -20218,7 +20250,7 @@ fn zirTruncate(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 20218 | 20250 | ); |
| 20219 | 20251 | } |
| 20220 | 20252 | var elem_buf: Value.ElemValueBuffer = undefined; |
| 20221 | const elems = try sema.arena.alloc(Value, operand_ty.vectorLen()); | |
| 20253 | const elems = try sema.arena.alloc(Value, operand_ty.vectorLen(mod)); | |
| 20222 | 20254 | for (elems, 0..) |*elem, i| { |
| 20223 | 20255 | const elem_val = val.elemValueBuffer(sema.mod, i, &elem_buf); |
| 20224 | 20256 | elem.* = try elem_val.intTrunc(operand_scalar_ty, sema.arena, dest_info.signedness, dest_info.bits, sema.mod); |
| ... | ... | @@ -20245,7 +20277,7 @@ fn zirAlignCast(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!A |
| 20245 | 20277 | |
| 20246 | 20278 | try sema.checkPtrOperand(block, ptr_src, ptr_ty); |
| 20247 | 20279 | |
| 20248 | var ptr_info = ptr_ty.ptrInfo().data; | |
| 20280 | var ptr_info = ptr_ty.ptrInfo(mod); | |
| 20249 | 20281 | ptr_info.@"align" = dest_align; |
| 20250 | 20282 | var dest_ty = try Type.ptr(sema.arena, sema.mod, ptr_info); |
| 20251 | 20283 | if (ptr_ty.zigTypeTag(mod) == .Optional) { |
| ... | ... | @@ -20314,8 +20346,11 @@ fn zirBitCount( |
| 20314 | 20346 | const result_scalar_ty = try mod.smallestUnsignedInt(bits); |
| 20315 | 20347 | switch (operand_ty.zigTypeTag(mod)) { |
| 20316 | 20348 | .Vector => { |
| 20317 | const vec_len = operand_ty.vectorLen(); | |
| 20318 | const result_ty = try Type.vector(sema.arena, vec_len, result_scalar_ty); | |
| 20349 | const vec_len = operand_ty.vectorLen(mod); | |
| 20350 | const result_ty = try mod.vectorType(.{ | |
| 20351 | .len = vec_len, | |
| 20352 | .child = result_scalar_ty.ip_index, | |
| 20353 | }); | |
| 20319 | 20354 | if (try sema.resolveMaybeUndefVal(operand)) |val| { |
| 20320 | 20355 | if (val.isUndef()) return sema.addConstUndef(result_ty); |
| 20321 | 20356 | |
| ... | ... | @@ -20388,7 +20423,7 @@ fn zirByteSwap(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Ai |
| 20388 | 20423 | if (val.isUndef()) |
| 20389 | 20424 | return sema.addConstUndef(operand_ty); |
| 20390 | 20425 | |
| 20391 | const vec_len = operand_ty.vectorLen(); | |
| 20426 | const vec_len = operand_ty.vectorLen(mod); | |
| 20392 | 20427 | var elem_buf: Value.ElemValueBuffer = undefined; |
| 20393 | 20428 | const elems = try sema.arena.alloc(Value, vec_len); |
| 20394 | 20429 | for (elems, 0..) |*elem, i| { |
| ... | ... | @@ -20437,7 +20472,7 @@ fn zirBitReverse(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError! |
| 20437 | 20472 | if (val.isUndef()) |
| 20438 | 20473 | return sema.addConstUndef(operand_ty); |
| 20439 | 20474 | |
| 20440 | const vec_len = operand_ty.vectorLen(); | |
| 20475 | const vec_len = operand_ty.vectorLen(mod); | |
| 20441 | 20476 | var elem_buf: Value.ElemValueBuffer = undefined; |
| 20442 | 20477 | const elems = try sema.arena.alloc(Value, vec_len); |
| 20443 | 20478 | for (elems, 0..) |*elem, i| { |
| ... | ... | @@ -20546,7 +20581,7 @@ fn checkInvalidPtrArithmetic( |
| 20546 | 20581 | ) CompileError!void { |
| 20547 | 20582 | const mod = sema.mod; |
| 20548 | 20583 | switch (try ty.zigTypeTagOrPoison(mod)) { |
| 20549 | .Pointer => switch (ty.ptrSize()) { | |
| 20584 | .Pointer => switch (ty.ptrSize(mod)) { | |
| 20550 | 20585 | .One, .Slice => return, |
| 20551 | 20586 | .Many, .C => return sema.fail( |
| 20552 | 20587 | block, |
| ... | ... | @@ -20676,7 +20711,7 @@ fn checkNumericType( |
| 20676 | 20711 | const mod = sema.mod; |
| 20677 | 20712 | switch (ty.zigTypeTag(mod)) { |
| 20678 | 20713 | .ComptimeFloat, .Float, .ComptimeInt, .Int => {}, |
| 20679 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 20714 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 20680 | 20715 | .ComptimeFloat, .Float, .ComptimeInt, .Int => {}, |
| 20681 | 20716 | else => |t| return sema.fail(block, ty_src, "expected number, found '{}'", .{t}), |
| 20682 | 20717 | }, |
| ... | ... | @@ -20726,7 +20761,7 @@ fn checkAtomicPtrOperand( |
| 20726 | 20761 | |
| 20727 | 20762 | const ptr_ty = sema.typeOf(ptr); |
| 20728 | 20763 | const ptr_data = switch (try ptr_ty.zigTypeTagOrPoison(mod)) { |
| 20729 | .Pointer => ptr_ty.ptrInfo().data, | |
| 20764 | .Pointer => ptr_ty.ptrInfo(mod), | |
| 20730 | 20765 | else => { |
| 20731 | 20766 | const wanted_ptr_ty = try Type.ptr(sema.arena, sema.mod, wanted_ptr_data); |
| 20732 | 20767 | _ = try sema.coerce(block, wanted_ptr_ty, ptr, ptr_src); |
| ... | ... | @@ -20797,7 +20832,7 @@ fn checkIntOrVector( |
| 20797 | 20832 | switch (try operand_ty.zigTypeTagOrPoison(mod)) { |
| 20798 | 20833 | .Int => return operand_ty, |
| 20799 | 20834 | .Vector => { |
| 20800 | const elem_ty = operand_ty.childType(); | |
| 20835 | const elem_ty = operand_ty.childType(mod); | |
| 20801 | 20836 | switch (try elem_ty.zigTypeTagOrPoison(mod)) { |
| 20802 | 20837 | .Int => return elem_ty, |
| 20803 | 20838 | else => return sema.fail(block, operand_src, "expected vector of integers; found vector of '{}'", .{ |
| ... | ... | @@ -20821,7 +20856,7 @@ fn checkIntOrVectorAllowComptime( |
| 20821 | 20856 | switch (try operand_ty.zigTypeTagOrPoison(mod)) { |
| 20822 | 20857 | .Int, .ComptimeInt => return operand_ty, |
| 20823 | 20858 | .Vector => { |
| 20824 | const elem_ty = operand_ty.childType(); | |
| 20859 | const elem_ty = operand_ty.childType(mod); | |
| 20825 | 20860 | switch (try elem_ty.zigTypeTagOrPoison(mod)) { |
| 20826 | 20861 | .Int, .ComptimeInt => return elem_ty, |
| 20827 | 20862 | else => return sema.fail(block, operand_src, "expected vector of integers; found vector of '{}'", .{ |
| ... | ... | @@ -20870,7 +20905,7 @@ fn checkSimdBinOp( |
| 20870 | 20905 | const rhs_ty = sema.typeOf(uncasted_rhs); |
| 20871 | 20906 | |
| 20872 | 20907 | try sema.checkVectorizableBinaryOperands(block, src, lhs_ty, rhs_ty, lhs_src, rhs_src); |
| 20873 | var vec_len: ?usize = if (lhs_ty.zigTypeTag(mod) == .Vector) lhs_ty.vectorLen() else null; | |
| 20908 | var vec_len: ?usize = if (lhs_ty.zigTypeTag(mod) == .Vector) lhs_ty.vectorLen(mod) else null; | |
| 20874 | 20909 | const result_ty = try sema.resolvePeerTypes(block, src, &.{ uncasted_lhs, uncasted_rhs }, .{ |
| 20875 | 20910 | .override = &[_]?LazySrcLoc{ lhs_src, rhs_src }, |
| 20876 | 20911 | }); |
| ... | ... | @@ -20912,8 +20947,8 @@ fn checkVectorizableBinaryOperands( |
| 20912 | 20947 | }; |
| 20913 | 20948 | |
| 20914 | 20949 | if (lhs_is_vector and rhs_is_vector) { |
| 20915 | const lhs_len = lhs_ty.arrayLen(); | |
| 20916 | const rhs_len = rhs_ty.arrayLen(); | |
| 20950 | const lhs_len = lhs_ty.arrayLen(mod); | |
| 20951 | const rhs_len = rhs_ty.arrayLen(mod); | |
| 20917 | 20952 | if (lhs_len != rhs_len) { |
| 20918 | 20953 | const msg = msg: { |
| 20919 | 20954 | const msg = try sema.errMsg(block, src, "vector length mismatch", .{}); |
| ... | ... | @@ -20966,7 +21001,7 @@ fn resolveExportOptions( |
| 20966 | 21001 | |
| 20967 | 21002 | const name_operand = try sema.fieldVal(block, src, options, "name", name_src); |
| 20968 | 21003 | const name_val = try sema.resolveConstValue(block, name_src, name_operand, "name of exported value must be comptime-known"); |
| 20969 | const name_ty = Type.initTag(.const_slice_u8); | |
| 21004 | const name_ty = Type.const_slice_u8; | |
| 20970 | 21005 | const name = try name_val.toAllocatedBytes(name_ty, sema.arena, mod); |
| 20971 | 21006 | |
| 20972 | 21007 | const linkage_operand = try sema.fieldVal(block, src, options, "linkage", linkage_src); |
| ... | ... | @@ -20975,7 +21010,7 @@ fn resolveExportOptions( |
| 20975 | 21010 | |
| 20976 | 21011 | const section_operand = try sema.fieldVal(block, src, options, "section", section_src); |
| 20977 | 21012 | const section_opt_val = try sema.resolveConstValue(block, section_src, section_operand, "linksection of exported value must be comptime-known"); |
| 20978 | const section_ty = Type.initTag(.const_slice_u8); | |
| 21013 | const section_ty = Type.const_slice_u8; | |
| 20979 | 21014 | const section = if (section_opt_val.optionalValue(mod)) |section_val| |
| 20980 | 21015 | try section_val.toAllocatedBytes(section_ty, sema.arena, mod) |
| 20981 | 21016 | else |
| ... | ... | @@ -21087,7 +21122,7 @@ fn zirCmpxchg( |
| 21087 | 21122 | return sema.fail(block, failure_order_src, "failure atomic ordering must not be Release or AcqRel", .{}); |
| 21088 | 21123 | } |
| 21089 | 21124 | |
| 21090 | const result_ty = try Type.optional(sema.arena, elem_ty); | |
| 21125 | const result_ty = try Type.optional(sema.arena, elem_ty, mod); | |
| 21091 | 21126 | |
| 21092 | 21127 | // special case zero bit types |
| 21093 | 21128 | if ((try sema.typeHasOnePossibleValue(elem_ty)) != null) { |
| ... | ... | @@ -21133,6 +21168,7 @@ fn zirCmpxchg( |
| 21133 | 21168 | } |
| 21134 | 21169 | |
| 21135 | 21170 | fn zirSplat(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.Inst.Ref { |
| 21171 | const mod = sema.mod; | |
| 21136 | 21172 | const inst_data = sema.code.instructions.items(.data)[inst].pl_node; |
| 21137 | 21173 | const extra = sema.code.extraData(Zir.Inst.Bin, inst_data.payload_index).data; |
| 21138 | 21174 | const len_src: LazySrcLoc = .{ .node_offset_bin_lhs = inst_data.src_node }; |
| ... | ... | @@ -21141,9 +21177,9 @@ fn zirSplat(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air.I |
| 21141 | 21177 | const scalar = try sema.resolveInst(extra.rhs); |
| 21142 | 21178 | const scalar_ty = sema.typeOf(scalar); |
| 21143 | 21179 | try sema.checkVectorElemType(block, scalar_src, scalar_ty); |
| 21144 | const vector_ty = try Type.Tag.vector.create(sema.arena, .{ | |
| 21180 | const vector_ty = try mod.vectorType(.{ | |
| 21145 | 21181 | .len = len, |
| 21146 | .elem_type = scalar_ty, | |
| 21182 | .child = scalar_ty.ip_index, | |
| 21147 | 21183 | }); |
| 21148 | 21184 | if (try sema.resolveMaybeUndefVal(scalar)) |scalar_val| { |
| 21149 | 21185 | if (scalar_val.isUndef()) return sema.addConstUndef(vector_ty); |
| ... | ... | @@ -21172,7 +21208,7 @@ fn zirReduce(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air. |
| 21172 | 21208 | return sema.fail(block, operand_src, "expected vector, found '{}'", .{operand_ty.fmt(mod)}); |
| 21173 | 21209 | } |
| 21174 | 21210 | |
| 21175 | const scalar_ty = operand_ty.childType(); | |
| 21211 | const scalar_ty = operand_ty.childType(mod); | |
| 21176 | 21212 | |
| 21177 | 21213 | // Type-check depending on operation. |
| 21178 | 21214 | switch (operation) { |
| ... | ... | @@ -21190,7 +21226,7 @@ fn zirReduce(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air. |
| 21190 | 21226 | }, |
| 21191 | 21227 | } |
| 21192 | 21228 | |
| 21193 | const vec_len = operand_ty.vectorLen(); | |
| 21229 | const vec_len = operand_ty.vectorLen(mod); | |
| 21194 | 21230 | if (vec_len == 0) { |
| 21195 | 21231 | // TODO re-evaluate if we should introduce a "neutral value" for some operations, |
| 21196 | 21232 | // e.g. zero for add and one for mul. |
| ... | ... | @@ -21243,12 +21279,12 @@ fn zirShuffle(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!Air |
| 21243 | 21279 | var mask_ty = sema.typeOf(mask); |
| 21244 | 21280 | |
| 21245 | 21281 | const mask_len = switch (sema.typeOf(mask).zigTypeTag(mod)) { |
| 21246 | .Array, .Vector => sema.typeOf(mask).arrayLen(), | |
| 21282 | .Array, .Vector => sema.typeOf(mask).arrayLen(mod), | |
| 21247 | 21283 | else => return sema.fail(block, mask_src, "expected vector or array, found '{}'", .{sema.typeOf(mask).fmt(sema.mod)}), |
| 21248 | 21284 | }; |
| 21249 | mask_ty = try Type.Tag.vector.create(sema.arena, .{ | |
| 21250 | .len = mask_len, | |
| 21251 | .elem_type = Type.i32, | |
| 21285 | mask_ty = try mod.vectorType(.{ | |
| 21286 | .len = @intCast(u32, mask_len), | |
| 21287 | .child = .i32_type, | |
| 21252 | 21288 | }); |
| 21253 | 21289 | mask = try sema.coerce(block, mask_ty, mask, mask_src); |
| 21254 | 21290 | const mask_val = try sema.resolveConstMaybeUndefVal(block, mask_src, mask, "shuffle mask must be comptime-known"); |
| ... | ... | @@ -21272,13 +21308,13 @@ fn analyzeShuffle( |
| 21272 | 21308 | var a = a_arg; |
| 21273 | 21309 | var b = b_arg; |
| 21274 | 21310 | |
| 21275 | const res_ty = try Type.Tag.vector.create(sema.arena, .{ | |
| 21311 | const res_ty = try mod.vectorType(.{ | |
| 21276 | 21312 | .len = mask_len, |
| 21277 | .elem_type = elem_ty, | |
| 21313 | .child = elem_ty.ip_index, | |
| 21278 | 21314 | }); |
| 21279 | 21315 | |
| 21280 | 21316 | var maybe_a_len = switch (sema.typeOf(a).zigTypeTag(mod)) { |
| 21281 | .Array, .Vector => sema.typeOf(a).arrayLen(), | |
| 21317 | .Array, .Vector => sema.typeOf(a).arrayLen(mod), | |
| 21282 | 21318 | .Undefined => null, |
| 21283 | 21319 | else => return sema.fail(block, a_src, "expected vector or array with element type '{}', found '{}'", .{ |
| 21284 | 21320 | elem_ty.fmt(sema.mod), |
| ... | ... | @@ -21286,7 +21322,7 @@ fn analyzeShuffle( |
| 21286 | 21322 | }), |
| 21287 | 21323 | }; |
| 21288 | 21324 | var maybe_b_len = switch (sema.typeOf(b).zigTypeTag(mod)) { |
| 21289 | .Array, .Vector => sema.typeOf(b).arrayLen(), | |
| 21325 | .Array, .Vector => sema.typeOf(b).arrayLen(mod), | |
| 21290 | 21326 | .Undefined => null, |
| 21291 | 21327 | else => return sema.fail(block, b_src, "expected vector or array with element type '{}', found '{}'", .{ |
| 21292 | 21328 | elem_ty.fmt(sema.mod), |
| ... | ... | @@ -21296,16 +21332,16 @@ fn analyzeShuffle( |
| 21296 | 21332 | if (maybe_a_len == null and maybe_b_len == null) { |
| 21297 | 21333 | return sema.addConstUndef(res_ty); |
| 21298 | 21334 | } |
| 21299 | const a_len = maybe_a_len orelse maybe_b_len.?; | |
| 21300 | const b_len = maybe_b_len orelse a_len; | |
| 21335 | const a_len = @intCast(u32, maybe_a_len orelse maybe_b_len.?); | |
| 21336 | const b_len = @intCast(u32, maybe_b_len orelse a_len); | |
| 21301 | 21337 | |
| 21302 | const a_ty = try Type.Tag.vector.create(sema.arena, .{ | |
| 21338 | const a_ty = try mod.vectorType(.{ | |
| 21303 | 21339 | .len = a_len, |
| 21304 | .elem_type = elem_ty, | |
| 21340 | .child = elem_ty.ip_index, | |
| 21305 | 21341 | }); |
| 21306 | const b_ty = try Type.Tag.vector.create(sema.arena, .{ | |
| 21342 | const b_ty = try mod.vectorType(.{ | |
| 21307 | 21343 | .len = b_len, |
| 21308 | .elem_type = elem_ty, | |
| 21344 | .child = elem_ty.ip_index, | |
| 21309 | 21345 | }); |
| 21310 | 21346 | |
| 21311 | 21347 | if (maybe_a_len == null) a = try sema.addConstUndef(a_ty) else a = try sema.coerce(block, a_ty, a, a_src); |
| ... | ... | @@ -21437,15 +21473,21 @@ fn zirSelect(sema: *Sema, block: *Block, extended: Zir.Inst.Extended.InstData) C |
| 21437 | 21473 | const pred_ty = sema.typeOf(pred_uncoerced); |
| 21438 | 21474 | |
| 21439 | 21475 | const vec_len_u64 = switch (try pred_ty.zigTypeTagOrPoison(mod)) { |
| 21440 | .Vector, .Array => pred_ty.arrayLen(), | |
| 21476 | .Vector, .Array => pred_ty.arrayLen(mod), | |
| 21441 | 21477 | else => return sema.fail(block, pred_src, "expected vector or array, found '{}'", .{pred_ty.fmt(sema.mod)}), |
| 21442 | 21478 | }; |
| 21443 | const vec_len = try sema.usizeCast(block, pred_src, vec_len_u64); | |
| 21479 | const vec_len = @intCast(u32, try sema.usizeCast(block, pred_src, vec_len_u64)); | |
| 21444 | 21480 | |
| 21445 | const bool_vec_ty = try Type.vector(sema.arena, vec_len, Type.bool); | |
| 21481 | const bool_vec_ty = try mod.vectorType(.{ | |
| 21482 | .len = vec_len, | |
| 21483 | .child = .bool_type, | |
| 21484 | }); | |
| 21446 | 21485 | const pred = try sema.coerce(block, bool_vec_ty, pred_uncoerced, pred_src); |
| 21447 | 21486 | |
| 21448 | const vec_ty = try Type.vector(sema.arena, vec_len, elem_ty); | |
| 21487 | const vec_ty = try mod.vectorType(.{ | |
| 21488 | .len = vec_len, | |
| 21489 | .child = elem_ty.ip_index, | |
| 21490 | }); | |
| 21449 | 21491 | const a = try sema.coerce(block, vec_ty, try sema.resolveInst(extra.a), a_src); |
| 21450 | 21492 | const b = try sema.coerce(block, vec_ty, try sema.resolveInst(extra.b), b_src); |
| 21451 | 21493 | |
| ... | ... | @@ -21854,7 +21896,7 @@ fn zirFieldParentPtr(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileEr |
| 21854 | 21896 | } |
| 21855 | 21897 | |
| 21856 | 21898 | try sema.checkPtrOperand(block, ptr_src, field_ptr_ty); |
| 21857 | const field_ptr_ty_info = field_ptr_ty.ptrInfo().data; | |
| 21899 | const field_ptr_ty_info = field_ptr_ty.ptrInfo(mod); | |
| 21858 | 21900 | |
| 21859 | 21901 | var ptr_ty_data: Type.Payload.Pointer.Data = .{ |
| 21860 | 21902 | .pointee_type = parent_ty.structFieldType(field_index), |
| ... | ... | @@ -22052,8 +22094,8 @@ fn analyzeMinMax( |
| 22052 | 22094 | } |
| 22053 | 22095 | |
| 22054 | 22096 | const refined_ty = if (orig_ty.zigTypeTag(mod) == .Vector) blk: { |
| 22055 | const elem_ty = orig_ty.childType(); | |
| 22056 | const len = orig_ty.vectorLen(); | |
| 22097 | const elem_ty = orig_ty.childType(mod); | |
| 22098 | const len = orig_ty.vectorLen(mod); | |
| 22057 | 22099 | |
| 22058 | 22100 | if (len == 0) break :blk orig_ty; |
| 22059 | 22101 | if (elem_ty.isAnyFloat()) break :blk orig_ty; // can't refine floats |
| ... | ... | @@ -22068,7 +22110,10 @@ fn analyzeMinMax( |
| 22068 | 22110 | } |
| 22069 | 22111 | |
| 22070 | 22112 | const refined_elem_ty = try mod.intFittingRange(cur_min, cur_max); |
| 22071 | break :blk try Type.vector(sema.arena, len, refined_elem_ty); | |
| 22113 | break :blk try mod.vectorType(.{ | |
| 22114 | .len = len, | |
| 22115 | .child = refined_elem_ty.ip_index, | |
| 22116 | }); | |
| 22072 | 22117 | } else blk: { |
| 22073 | 22118 | if (orig_ty.isAnyFloat()) break :blk orig_ty; // can't refine floats |
| 22074 | 22119 | if (val.isUndef()) break :blk orig_ty; // can't refine undef |
| ... | ... | @@ -22129,8 +22174,8 @@ fn analyzeMinMax( |
| 22129 | 22174 | if (known_undef) break :refine; // can't refine undef |
| 22130 | 22175 | const unrefined_ty = sema.typeOf(cur_minmax.?); |
| 22131 | 22176 | const is_vector = unrefined_ty.zigTypeTag(mod) == .Vector; |
| 22132 | const comptime_elem_ty = if (is_vector) comptime_ty.childType() else comptime_ty; | |
| 22133 | const unrefined_elem_ty = if (is_vector) unrefined_ty.childType() else unrefined_ty; | |
| 22177 | const comptime_elem_ty = if (is_vector) comptime_ty.childType(mod) else comptime_ty; | |
| 22178 | const unrefined_elem_ty = if (is_vector) unrefined_ty.childType(mod) else unrefined_ty; | |
| 22134 | 22179 | |
| 22135 | 22180 | if (unrefined_elem_ty.isAnyFloat()) break :refine; // we can't refine floats |
| 22136 | 22181 | |
| ... | ... | @@ -22150,7 +22195,10 @@ fn analyzeMinMax( |
| 22150 | 22195 | const final_elem_ty = try mod.intFittingRange(min_val, max_val); |
| 22151 | 22196 | |
| 22152 | 22197 | const final_ty = if (is_vector) |
| 22153 | try Type.vector(sema.arena, unrefined_ty.vectorLen(), final_elem_ty) | |
| 22198 | try mod.vectorType(.{ | |
| 22199 | .len = unrefined_ty.vectorLen(mod), | |
| 22200 | .child = final_elem_ty.ip_index, | |
| 22201 | }) | |
| 22154 | 22202 | else |
| 22155 | 22203 | final_elem_ty; |
| 22156 | 22204 | |
| ... | ... | @@ -22165,7 +22213,7 @@ fn analyzeMinMax( |
| 22165 | 22213 | |
| 22166 | 22214 | fn upgradeToArrayPtr(sema: *Sema, block: *Block, ptr: Air.Inst.Ref, len: u64) !Air.Inst.Ref { |
| 22167 | 22215 | const mod = sema.mod; |
| 22168 | const info = sema.typeOf(ptr).ptrInfo().data; | |
| 22216 | const info = sema.typeOf(ptr).ptrInfo(mod); | |
| 22169 | 22217 | if (info.size == .One) { |
| 22170 | 22218 | // Already an array pointer. |
| 22171 | 22219 | return ptr; |
| ... | ... | @@ -22659,7 +22707,7 @@ fn zirFuncFancy(sema: *Sema, block: *Block, inst: Zir.Inst.Index) CompileError!A |
| 22659 | 22707 | const body = sema.code.extra[extra_index..][0..body_len]; |
| 22660 | 22708 | extra_index += body.len; |
| 22661 | 22709 | |
| 22662 | const ty = Type.initTag(.const_slice_u8); | |
| 22710 | const ty = Type.const_slice_u8; | |
| 22663 | 22711 | const val = try sema.resolveGenericBody(block, section_src, body, inst, ty, "linksection must be comptime-known"); |
| 22664 | 22712 | if (val.isGenericPoison()) { |
| 22665 | 22713 | break :blk FuncLinkSection{ .generic = {} }; |
| ... | ... | @@ -22943,7 +22991,7 @@ fn resolveExternOptions( |
| 22943 | 22991 | |
| 22944 | 22992 | const name_ref = try sema.fieldVal(block, src, options, "name", name_src); |
| 22945 | 22993 | const name_val = try sema.resolveConstValue(block, name_src, name_ref, "name of the extern symbol must be comptime-known"); |
| 22946 | const name = try name_val.toAllocatedBytes(Type.initTag(.const_slice_u8), sema.arena, mod); | |
| 22994 | const name = try name_val.toAllocatedBytes(Type.const_slice_u8, sema.arena, mod); | |
| 22947 | 22995 | |
| 22948 | 22996 | const library_name_inst = try sema.fieldVal(block, src, options, "library_name", library_src); |
| 22949 | 22997 | const library_name_val = try sema.resolveConstValue(block, library_src, library_name_inst, "library in which extern symbol is must be comptime-known"); |
| ... | ... | @@ -22957,7 +23005,7 @@ fn resolveExternOptions( |
| 22957 | 23005 | |
| 22958 | 23006 | const library_name = if (!library_name_val.isNull(mod)) blk: { |
| 22959 | 23007 | const payload = library_name_val.castTag(.opt_payload).?.data; |
| 22960 | const library_name = try payload.toAllocatedBytes(Type.initTag(.const_slice_u8), sema.arena, mod); | |
| 23008 | const library_name = try payload.toAllocatedBytes(Type.const_slice_u8, sema.arena, mod); | |
| 22961 | 23009 | if (library_name.len == 0) { |
| 22962 | 23010 | return sema.fail(block, library_src, "library name cannot be empty", .{}); |
| 22963 | 23011 | } |
| ... | ... | @@ -22994,7 +23042,7 @@ fn zirBuiltinExtern( |
| 22994 | 23042 | if (!ty.isPtrAtRuntime(mod)) { |
| 22995 | 23043 | return sema.fail(block, ty_src, "expected (optional) pointer", .{}); |
| 22996 | 23044 | } |
| 22997 | if (!try sema.validateExternType(ty.childType(), .other)) { | |
| 23045 | if (!try sema.validateExternType(ty.childType(mod), .other)) { | |
| 22998 | 23046 | const msg = msg: { |
| 22999 | 23047 | const msg = try sema.errMsg(block, ty_src, "extern symbol cannot have type '{}'", .{ty.fmt(mod)}); |
| 23000 | 23048 | errdefer msg.destroy(sema.gpa); |
| ... | ... | @@ -23014,7 +23062,7 @@ fn zirBuiltinExtern( |
| 23014 | 23062 | }; |
| 23015 | 23063 | |
| 23016 | 23064 | if (options.linkage == .Weak and !ty.ptrAllowsZero(mod)) { |
| 23017 | ty = try Type.optional(sema.arena, ty); | |
| 23065 | ty = try Type.optional(sema.arena, ty, mod); | |
| 23018 | 23066 | } |
| 23019 | 23067 | |
| 23020 | 23068 | // TODO check duplicate extern |
| ... | ... | @@ -23194,7 +23242,7 @@ fn validateRunTimeType( |
| 23194 | 23242 | => return false, |
| 23195 | 23243 | |
| 23196 | 23244 | .Pointer => { |
| 23197 | const elem_ty = ty.childType(); | |
| 23245 | const elem_ty = ty.childType(mod); | |
| 23198 | 23246 | switch (elem_ty.zigTypeTag(mod)) { |
| 23199 | 23247 | .Opaque => return true, |
| 23200 | 23248 | .Fn => return elem_ty.isFnOrHasRuntimeBits(mod), |
| ... | ... | @@ -23204,11 +23252,10 @@ fn validateRunTimeType( |
| 23204 | 23252 | .Opaque => return is_extern, |
| 23205 | 23253 | |
| 23206 | 23254 | .Optional => { |
| 23207 | var buf: Type.Payload.ElemType = undefined; | |
| 23208 | const child_ty = ty.optionalChild(&buf); | |
| 23255 | const child_ty = ty.optionalChild(mod); | |
| 23209 | 23256 | return sema.validateRunTimeType(child_ty, is_extern); |
| 23210 | 23257 | }, |
| 23211 | .Array, .Vector => ty = ty.elemType(), | |
| 23258 | .Array, .Vector => ty = ty.childType(mod), | |
| 23212 | 23259 | |
| 23213 | 23260 | .ErrorUnion => ty = ty.errorUnionPayload(), |
| 23214 | 23261 | |
| ... | ... | @@ -23277,7 +23324,7 @@ fn explainWhyTypeIsComptimeInner( |
| 23277 | 23324 | }, |
| 23278 | 23325 | |
| 23279 | 23326 | .Array, .Vector => { |
| 23280 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.elemType(), type_set); | |
| 23327 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.childType(mod), type_set); | |
| 23281 | 23328 | }, |
| 23282 | 23329 | .Pointer => { |
| 23283 | 23330 | const elem_ty = ty.elemType2(mod); |
| ... | ... | @@ -23295,12 +23342,11 @@ fn explainWhyTypeIsComptimeInner( |
| 23295 | 23342 | } |
| 23296 | 23343 | return; |
| 23297 | 23344 | } |
| 23298 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.elemType(), type_set); | |
| 23345 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.childType(mod), type_set); | |
| 23299 | 23346 | }, |
| 23300 | 23347 | |
| 23301 | 23348 | .Optional => { |
| 23302 | var buf: Type.Payload.ElemType = undefined; | |
| 23303 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.optionalChild(&buf), type_set); | |
| 23349 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.optionalChild(mod), type_set); | |
| 23304 | 23350 | }, |
| 23305 | 23351 | .ErrorUnion => { |
| 23306 | 23352 | try sema.explainWhyTypeIsComptimeInner(msg, src_loc, ty.errorUnionPayload(), type_set); |
| ... | ... | @@ -23451,7 +23497,7 @@ fn explainWhyTypeIsNotExtern( |
| 23451 | 23497 | if (ty.isSlice(mod)) { |
| 23452 | 23498 | try mod.errNoteNonLazy(src_loc, msg, "slices have no guaranteed in-memory representation", .{}); |
| 23453 | 23499 | } else { |
| 23454 | const pointee_ty = ty.childType(); | |
| 23500 | const pointee_ty = ty.childType(mod); | |
| 23455 | 23501 | try mod.errNoteNonLazy(src_loc, msg, "pointer to comptime-only type '{}'", .{pointee_ty.fmt(sema.mod)}); |
| 23456 | 23502 | try sema.explainWhyTypeIsComptime(msg, src_loc, pointee_ty); |
| 23457 | 23503 | } |
| ... | ... | @@ -23698,7 +23744,7 @@ fn panicWithMsg( |
| 23698 | 23744 | .@"addrspace" = target_util.defaultAddressSpace(target, .global_constant), // TODO might need a place that is more dynamic |
| 23699 | 23745 | }); |
| 23700 | 23746 | const null_stack_trace = try sema.addConstant( |
| 23701 | try Type.optional(arena, ptr_stack_trace_ty), | |
| 23747 | try Type.optional(arena, ptr_stack_trace_ty, mod), | |
| 23702 | 23748 | Value.null, |
| 23703 | 23749 | ); |
| 23704 | 23750 | const args: [3]Air.Inst.Ref = .{ msg_inst, null_stack_trace, .null_value }; |
| ... | ... | @@ -23927,7 +23973,7 @@ fn fieldVal( |
| 23927 | 23973 | const is_pointer_to = object_ty.isSinglePointer(mod); |
| 23928 | 23974 | |
| 23929 | 23975 | const inner_ty = if (is_pointer_to) |
| 23930 | object_ty.childType() | |
| 23976 | object_ty.childType(mod) | |
| 23931 | 23977 | else |
| 23932 | 23978 | object_ty; |
| 23933 | 23979 | |
| ... | ... | @@ -23936,12 +23982,12 @@ fn fieldVal( |
| 23936 | 23982 | if (mem.eql(u8, field_name, "len")) { |
| 23937 | 23983 | return sema.addConstant( |
| 23938 | 23984 | Type.usize, |
| 23939 | try Value.Tag.int_u64.create(arena, inner_ty.arrayLen()), | |
| 23985 | try Value.Tag.int_u64.create(arena, inner_ty.arrayLen(mod)), | |
| 23940 | 23986 | ); |
| 23941 | 23987 | } else if (mem.eql(u8, field_name, "ptr") and is_pointer_to) { |
| 23942 | const ptr_info = object_ty.ptrInfo().data; | |
| 23988 | const ptr_info = object_ty.ptrInfo(mod); | |
| 23943 | 23989 | const result_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 23944 | .pointee_type = ptr_info.pointee_type.childType(), | |
| 23990 | .pointee_type = ptr_info.pointee_type.childType(mod), | |
| 23945 | 23991 | .sentinel = ptr_info.sentinel, |
| 23946 | 23992 | .@"align" = ptr_info.@"align", |
| 23947 | 23993 | .@"addrspace" = ptr_info.@"addrspace", |
| ... | ... | @@ -23964,7 +24010,7 @@ fn fieldVal( |
| 23964 | 24010 | } |
| 23965 | 24011 | }, |
| 23966 | 24012 | .Pointer => { |
| 23967 | const ptr_info = inner_ty.ptrInfo().data; | |
| 24013 | const ptr_info = inner_ty.ptrInfo(mod); | |
| 23968 | 24014 | if (ptr_info.size == .Slice) { |
| 23969 | 24015 | if (mem.eql(u8, field_name, "ptr")) { |
| 23970 | 24016 | const slice = if (is_pointer_to) |
| ... | ... | @@ -24107,7 +24153,7 @@ fn fieldPtr( |
| 24107 | 24153 | const object_ptr_src = src; // TODO better source location |
| 24108 | 24154 | const object_ptr_ty = sema.typeOf(object_ptr); |
| 24109 | 24155 | const object_ty = switch (object_ptr_ty.zigTypeTag(mod)) { |
| 24110 | .Pointer => object_ptr_ty.elemType(), | |
| 24156 | .Pointer => object_ptr_ty.childType(mod), | |
| 24111 | 24157 | else => return sema.fail(block, object_ptr_src, "expected pointer, found '{}'", .{object_ptr_ty.fmt(sema.mod)}), |
| 24112 | 24158 | }; |
| 24113 | 24159 | |
| ... | ... | @@ -24117,7 +24163,7 @@ fn fieldPtr( |
| 24117 | 24163 | const is_pointer_to = object_ty.isSinglePointer(mod); |
| 24118 | 24164 | |
| 24119 | 24165 | const inner_ty = if (is_pointer_to) |
| 24120 | object_ty.childType() | |
| 24166 | object_ty.childType(mod) | |
| 24121 | 24167 | else |
| 24122 | 24168 | object_ty; |
| 24123 | 24169 | |
| ... | ... | @@ -24128,7 +24174,7 @@ fn fieldPtr( |
| 24128 | 24174 | defer anon_decl.deinit(); |
| 24129 | 24175 | return sema.analyzeDeclRef(try anon_decl.finish( |
| 24130 | 24176 | Type.usize, |
| 24131 | try Value.Tag.int_u64.create(anon_decl.arena(), inner_ty.arrayLen()), | |
| 24177 | try Value.Tag.int_u64.create(anon_decl.arena(), inner_ty.arrayLen(mod)), | |
| 24132 | 24178 | 0, // default alignment |
| 24133 | 24179 | )); |
| 24134 | 24180 | } else { |
| ... | ... | @@ -24154,9 +24200,9 @@ fn fieldPtr( |
| 24154 | 24200 | |
| 24155 | 24201 | const result_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 24156 | 24202 | .pointee_type = slice_ptr_ty, |
| 24157 | .mutable = attr_ptr_ty.ptrIsMutable(), | |
| 24203 | .mutable = attr_ptr_ty.ptrIsMutable(mod), | |
| 24158 | 24204 | .@"volatile" = attr_ptr_ty.isVolatilePtr(), |
| 24159 | .@"addrspace" = attr_ptr_ty.ptrAddressSpace(), | |
| 24205 | .@"addrspace" = attr_ptr_ty.ptrAddressSpace(mod), | |
| 24160 | 24206 | }); |
| 24161 | 24207 | |
| 24162 | 24208 | if (try sema.resolveDefinedValue(block, object_ptr_src, inner_ptr)) |val| { |
| ... | ... | @@ -24175,9 +24221,9 @@ fn fieldPtr( |
| 24175 | 24221 | } else if (mem.eql(u8, field_name, "len")) { |
| 24176 | 24222 | const result_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 24177 | 24223 | .pointee_type = Type.usize, |
| 24178 | .mutable = attr_ptr_ty.ptrIsMutable(), | |
| 24224 | .mutable = attr_ptr_ty.ptrIsMutable(mod), | |
| 24179 | 24225 | .@"volatile" = attr_ptr_ty.isVolatilePtr(), |
| 24180 | .@"addrspace" = attr_ptr_ty.ptrAddressSpace(), | |
| 24226 | .@"addrspace" = attr_ptr_ty.ptrAddressSpace(mod), | |
| 24181 | 24227 | }); |
| 24182 | 24228 | |
| 24183 | 24229 | if (try sema.resolveDefinedValue(block, object_ptr_src, inner_ptr)) |val| { |
| ... | ... | @@ -24329,14 +24375,14 @@ fn fieldCallBind( |
| 24329 | 24375 | const mod = sema.mod; |
| 24330 | 24376 | const raw_ptr_src = src; // TODO better source location |
| 24331 | 24377 | const raw_ptr_ty = sema.typeOf(raw_ptr); |
| 24332 | const inner_ty = if (raw_ptr_ty.zigTypeTag(mod) == .Pointer and (raw_ptr_ty.ptrSize() == .One or raw_ptr_ty.ptrSize() == .C)) | |
| 24333 | raw_ptr_ty.childType() | |
| 24378 | const inner_ty = if (raw_ptr_ty.zigTypeTag(mod) == .Pointer and (raw_ptr_ty.ptrSize(mod) == .One or raw_ptr_ty.ptrSize(mod) == .C)) | |
| 24379 | raw_ptr_ty.childType(mod) | |
| 24334 | 24380 | else |
| 24335 | 24381 | return sema.fail(block, raw_ptr_src, "expected single pointer, found '{}'", .{raw_ptr_ty.fmt(sema.mod)}); |
| 24336 | 24382 | |
| 24337 | 24383 | // Optionally dereference a second pointer to get the concrete type. |
| 24338 | const is_double_ptr = inner_ty.zigTypeTag(mod) == .Pointer and inner_ty.ptrSize() == .One; | |
| 24339 | const concrete_ty = if (is_double_ptr) inner_ty.childType() else inner_ty; | |
| 24384 | const is_double_ptr = inner_ty.zigTypeTag(mod) == .Pointer and inner_ty.ptrSize(mod) == .One; | |
| 24385 | const concrete_ty = if (is_double_ptr) inner_ty.childType(mod) else inner_ty; | |
| 24340 | 24386 | const ptr_ty = if (is_double_ptr) inner_ty else raw_ptr_ty; |
| 24341 | 24387 | const object_ptr = if (is_double_ptr) |
| 24342 | 24388 | try sema.analyzeLoad(block, src, raw_ptr, src) |
| ... | ... | @@ -24404,9 +24450,9 @@ fn fieldCallBind( |
| 24404 | 24450 | // zig fmt: off |
| 24405 | 24451 | if (first_param_type.isGenericPoison() or ( |
| 24406 | 24452 | first_param_type.zigTypeTag(mod) == .Pointer and |
| 24407 | (first_param_type.ptrSize() == .One or | |
| 24408 | first_param_type.ptrSize() == .C) and | |
| 24409 | first_param_type.childType().eql(concrete_ty, sema.mod))) | |
| 24453 | (first_param_type.ptrSize(mod) == .One or | |
| 24454 | first_param_type.ptrSize(mod) == .C) and | |
| 24455 | first_param_type.childType(mod).eql(concrete_ty, sema.mod))) | |
| 24410 | 24456 | { |
| 24411 | 24457 | // zig fmt: on |
| 24412 | 24458 | // Note that if the param type is generic poison, we know that it must |
| ... | ... | @@ -24425,8 +24471,7 @@ fn fieldCallBind( |
| 24425 | 24471 | .arg0_inst = deref, |
| 24426 | 24472 | } }; |
| 24427 | 24473 | } else if (first_param_type.zigTypeTag(mod) == .Optional) { |
| 24428 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 24429 | const child = first_param_type.optionalChild(&opt_buf); | |
| 24474 | const child = first_param_type.optionalChild(mod); | |
| 24430 | 24475 | if (child.eql(concrete_ty, sema.mod)) { |
| 24431 | 24476 | const deref = try sema.analyzeLoad(block, src, object_ptr, src); |
| 24432 | 24477 | return .{ .method = .{ |
| ... | ... | @@ -24434,8 +24479,8 @@ fn fieldCallBind( |
| 24434 | 24479 | .arg0_inst = deref, |
| 24435 | 24480 | } }; |
| 24436 | 24481 | } else if (child.zigTypeTag(mod) == .Pointer and |
| 24437 | child.ptrSize() == .One and | |
| 24438 | child.childType().eql(concrete_ty, sema.mod)) | |
| 24482 | child.ptrSize(mod) == .One and | |
| 24483 | child.childType(mod).eql(concrete_ty, sema.mod)) | |
| 24439 | 24484 | { |
| 24440 | 24485 | return .{ .method = .{ |
| 24441 | 24486 | .func_inst = decl_val, |
| ... | ... | @@ -24482,15 +24527,15 @@ fn finishFieldCallBind( |
| 24482 | 24527 | field_index: u32, |
| 24483 | 24528 | object_ptr: Air.Inst.Ref, |
| 24484 | 24529 | ) CompileError!ResolvedFieldCallee { |
| 24530 | const mod = sema.mod; | |
| 24485 | 24531 | const arena = sema.arena; |
| 24486 | 24532 | const ptr_field_ty = try Type.ptr(arena, sema.mod, .{ |
| 24487 | 24533 | .pointee_type = field_ty, |
| 24488 | .mutable = ptr_ty.ptrIsMutable(), | |
| 24489 | .@"addrspace" = ptr_ty.ptrAddressSpace(), | |
| 24534 | .mutable = ptr_ty.ptrIsMutable(mod), | |
| 24535 | .@"addrspace" = ptr_ty.ptrAddressSpace(mod), | |
| 24490 | 24536 | }); |
| 24491 | 24537 | |
| 24492 | const mod = sema.mod; | |
| 24493 | const container_ty = ptr_ty.childType(); | |
| 24538 | const container_ty = ptr_ty.childType(mod); | |
| 24494 | 24539 | if (container_ty.zigTypeTag(mod) == .Struct) { |
| 24495 | 24540 | if (container_ty.structFieldValueComptime(mod, field_index)) |default_val| { |
| 24496 | 24541 | return .{ .direct = try sema.addConstant(field_ty, default_val) }; |
| ... | ... | @@ -24618,7 +24663,7 @@ fn structFieldPtrByIndex( |
| 24618 | 24663 | const struct_obj = struct_ty.castTag(.@"struct").?.data; |
| 24619 | 24664 | const field = struct_obj.fields.values()[field_index]; |
| 24620 | 24665 | const struct_ptr_ty = sema.typeOf(struct_ptr); |
| 24621 | const struct_ptr_ty_info = struct_ptr_ty.ptrInfo().data; | |
| 24666 | const struct_ptr_ty_info = struct_ptr_ty.ptrInfo(mod); | |
| 24622 | 24667 | |
| 24623 | 24668 | var ptr_ty_data: Type.Payload.Pointer.Data = .{ |
| 24624 | 24669 | .pointee_type = field.ty, |
| ... | ... | @@ -24696,7 +24741,7 @@ fn structFieldPtrByIndex( |
| 24696 | 24741 | ptr_field_ty, |
| 24697 | 24742 | try Value.Tag.field_ptr.create(sema.arena, .{ |
| 24698 | 24743 | .container_ptr = struct_ptr_val, |
| 24699 | .container_ty = struct_ptr_ty.childType(), | |
| 24744 | .container_ty = struct_ptr_ty.childType(mod), | |
| 24700 | 24745 | .field_index = field_index, |
| 24701 | 24746 | }), |
| 24702 | 24747 | ); |
| ... | ... | @@ -24846,9 +24891,9 @@ fn unionFieldPtr( |
| 24846 | 24891 | const field = union_obj.fields.values()[field_index]; |
| 24847 | 24892 | const ptr_field_ty = try Type.ptr(arena, sema.mod, .{ |
| 24848 | 24893 | .pointee_type = field.ty, |
| 24849 | .mutable = union_ptr_ty.ptrIsMutable(), | |
| 24894 | .mutable = union_ptr_ty.ptrIsMutable(mod), | |
| 24850 | 24895 | .@"volatile" = union_ptr_ty.isVolatilePtr(), |
| 24851 | .@"addrspace" = union_ptr_ty.ptrAddressSpace(), | |
| 24896 | .@"addrspace" = union_ptr_ty.ptrAddressSpace(mod), | |
| 24852 | 24897 | }); |
| 24853 | 24898 | const enum_field_index = @intCast(u32, union_obj.tag_ty.enumFieldIndex(field_name).?); |
| 24854 | 24899 | |
| ... | ... | @@ -25009,7 +25054,7 @@ fn elemPtr( |
| 25009 | 25054 | const indexable_ptr_ty = sema.typeOf(indexable_ptr); |
| 25010 | 25055 | |
| 25011 | 25056 | const indexable_ty = switch (indexable_ptr_ty.zigTypeTag(mod)) { |
| 25012 | .Pointer => indexable_ptr_ty.elemType(), | |
| 25057 | .Pointer => indexable_ptr_ty.childType(mod), | |
| 25013 | 25058 | else => return sema.fail(block, indexable_ptr_src, "expected pointer, found '{}'", .{indexable_ptr_ty.fmt(sema.mod)}), |
| 25014 | 25059 | }; |
| 25015 | 25060 | try checkIndexable(sema, block, src, indexable_ty); |
| ... | ... | @@ -25046,7 +25091,7 @@ fn elemPtrOneLayerOnly( |
| 25046 | 25091 | |
| 25047 | 25092 | try checkIndexable(sema, block, src, indexable_ty); |
| 25048 | 25093 | |
| 25049 | switch (indexable_ty.ptrSize()) { | |
| 25094 | switch (indexable_ty.ptrSize(mod)) { | |
| 25050 | 25095 | .Slice => return sema.elemPtrSlice(block, src, indexable_src, indexable, elem_index_src, elem_index, oob_safety), |
| 25051 | 25096 | .Many, .C => { |
| 25052 | 25097 | const maybe_ptr_val = try sema.resolveDefinedValue(block, indexable_src, indexable); |
| ... | ... | @@ -25065,7 +25110,7 @@ fn elemPtrOneLayerOnly( |
| 25065 | 25110 | return block.addPtrElemPtr(indexable, elem_index, result_ty); |
| 25066 | 25111 | }, |
| 25067 | 25112 | .One => { |
| 25068 | assert(indexable_ty.childType().zigTypeTag(mod) == .Array); // Guaranteed by checkIndexable | |
| 25113 | assert(indexable_ty.childType(mod).zigTypeTag(mod) == .Array); // Guaranteed by checkIndexable | |
| 25069 | 25114 | return sema.elemPtrArray(block, src, indexable_src, indexable, elem_index_src, elem_index, init, oob_safety); |
| 25070 | 25115 | }, |
| 25071 | 25116 | } |
| ... | ... | @@ -25091,7 +25136,7 @@ fn elemVal( |
| 25091 | 25136 | const elem_index = try sema.coerce(block, Type.usize, elem_index_uncasted, elem_index_src); |
| 25092 | 25137 | |
| 25093 | 25138 | switch (indexable_ty.zigTypeTag(mod)) { |
| 25094 | .Pointer => switch (indexable_ty.ptrSize()) { | |
| 25139 | .Pointer => switch (indexable_ty.ptrSize(mod)) { | |
| 25095 | 25140 | .Slice => return sema.elemValSlice(block, src, indexable_src, indexable, elem_index_src, elem_index, oob_safety), |
| 25096 | 25141 | .Many, .C => { |
| 25097 | 25142 | const maybe_indexable_val = try sema.resolveDefinedValue(block, indexable_src, indexable); |
| ... | ... | @@ -25112,7 +25157,7 @@ fn elemVal( |
| 25112 | 25157 | return block.addBinOp(.ptr_elem_val, indexable, elem_index); |
| 25113 | 25158 | }, |
| 25114 | 25159 | .One => { |
| 25115 | assert(indexable_ty.childType().zigTypeTag(mod) == .Array); // Guaranteed by checkIndexable | |
| 25160 | assert(indexable_ty.childType(mod).zigTypeTag(mod) == .Array); // Guaranteed by checkIndexable | |
| 25116 | 25161 | const elem_ptr = try sema.elemPtr(block, indexable_src, indexable, elem_index, elem_index_src, false, oob_safety); |
| 25117 | 25162 | return sema.analyzeLoad(block, indexable_src, elem_ptr, elem_index_src); |
| 25118 | 25163 | }, |
| ... | ... | @@ -25171,7 +25216,7 @@ fn tupleFieldPtr( |
| 25171 | 25216 | ) CompileError!Air.Inst.Ref { |
| 25172 | 25217 | const mod = sema.mod; |
| 25173 | 25218 | const tuple_ptr_ty = sema.typeOf(tuple_ptr); |
| 25174 | const tuple_ty = tuple_ptr_ty.childType(); | |
| 25219 | const tuple_ty = tuple_ptr_ty.childType(mod); | |
| 25175 | 25220 | _ = try sema.resolveTypeFields(tuple_ty); |
| 25176 | 25221 | const field_count = tuple_ty.structFieldCount(); |
| 25177 | 25222 | |
| ... | ... | @@ -25188,9 +25233,9 @@ fn tupleFieldPtr( |
| 25188 | 25233 | const field_ty = tuple_ty.structFieldType(field_index); |
| 25189 | 25234 | const ptr_field_ty = try Type.ptr(sema.arena, sema.mod, .{ |
| 25190 | 25235 | .pointee_type = field_ty, |
| 25191 | .mutable = tuple_ptr_ty.ptrIsMutable(), | |
| 25236 | .mutable = tuple_ptr_ty.ptrIsMutable(mod), | |
| 25192 | 25237 | .@"volatile" = tuple_ptr_ty.isVolatilePtr(), |
| 25193 | .@"addrspace" = tuple_ptr_ty.ptrAddressSpace(), | |
| 25238 | .@"addrspace" = tuple_ptr_ty.ptrAddressSpace(mod), | |
| 25194 | 25239 | }); |
| 25195 | 25240 | |
| 25196 | 25241 | if (tuple_ty.structFieldValueComptime(mod, field_index)) |default_val| { |
| ... | ... | @@ -25271,10 +25316,10 @@ fn elemValArray( |
| 25271 | 25316 | ) CompileError!Air.Inst.Ref { |
| 25272 | 25317 | const mod = sema.mod; |
| 25273 | 25318 | const array_ty = sema.typeOf(array); |
| 25274 | const array_sent = array_ty.sentinel(); | |
| 25275 | const array_len = array_ty.arrayLen(); | |
| 25319 | const array_sent = array_ty.sentinel(mod); | |
| 25320 | const array_len = array_ty.arrayLen(mod); | |
| 25276 | 25321 | const array_len_s = array_len + @boolToInt(array_sent != null); |
| 25277 | const elem_ty = array_ty.childType(); | |
| 25322 | const elem_ty = array_ty.childType(mod); | |
| 25278 | 25323 | |
| 25279 | 25324 | if (array_len_s == 0) { |
| 25280 | 25325 | return sema.fail(block, array_src, "indexing into empty array is not allowed", .{}); |
| ... | ... | @@ -25335,9 +25380,9 @@ fn elemPtrArray( |
| 25335 | 25380 | ) CompileError!Air.Inst.Ref { |
| 25336 | 25381 | const mod = sema.mod; |
| 25337 | 25382 | const array_ptr_ty = sema.typeOf(array_ptr); |
| 25338 | const array_ty = array_ptr_ty.childType(); | |
| 25339 | const array_sent = array_ty.sentinel() != null; | |
| 25340 | const array_len = array_ty.arrayLen(); | |
| 25383 | const array_ty = array_ptr_ty.childType(mod); | |
| 25384 | const array_sent = array_ty.sentinel(mod) != null; | |
| 25385 | const array_len = array_ty.arrayLen(mod); | |
| 25341 | 25386 | const array_len_s = array_len + @boolToInt(array_sent); |
| 25342 | 25387 | |
| 25343 | 25388 | if (array_len_s == 0) { |
| ... | ... | @@ -25396,7 +25441,7 @@ fn elemValSlice( |
| 25396 | 25441 | ) CompileError!Air.Inst.Ref { |
| 25397 | 25442 | const mod = sema.mod; |
| 25398 | 25443 | const slice_ty = sema.typeOf(slice); |
| 25399 | const slice_sent = slice_ty.sentinel() != null; | |
| 25444 | const slice_sent = slice_ty.sentinel(mod) != null; | |
| 25400 | 25445 | const elem_ty = slice_ty.elemType2(mod); |
| 25401 | 25446 | var runtime_src = slice_src; |
| 25402 | 25447 | |
| ... | ... | @@ -25453,7 +25498,7 @@ fn elemPtrSlice( |
| 25453 | 25498 | ) CompileError!Air.Inst.Ref { |
| 25454 | 25499 | const mod = sema.mod; |
| 25455 | 25500 | const slice_ty = sema.typeOf(slice); |
| 25456 | const slice_sent = slice_ty.sentinel() != null; | |
| 25501 | const slice_sent = slice_ty.sentinel(mod) != null; | |
| 25457 | 25502 | |
| 25458 | 25503 | const maybe_undef_slice_val = try sema.resolveMaybeUndefVal(slice); |
| 25459 | 25504 | // The index must not be undefined since it can be out of bounds. |
| ... | ... | @@ -25614,7 +25659,7 @@ fn coerceExtra( |
| 25614 | 25659 | } |
| 25615 | 25660 | |
| 25616 | 25661 | // T to ?T |
| 25617 | const child_type = try dest_ty.optionalChildAlloc(sema.arena); | |
| 25662 | const child_type = dest_ty.optionalChild(mod); | |
| 25618 | 25663 | const intermediate = sema.coerceExtra(block, child_type, inst, inst_src, .{ .report_err = false }) catch |err| switch (err) { |
| 25619 | 25664 | error.NotCoercible => { |
| 25620 | 25665 | if (in_memory_result == .no_match) { |
| ... | ... | @@ -25628,7 +25673,7 @@ fn coerceExtra( |
| 25628 | 25673 | return try sema.wrapOptional(block, dest_ty, intermediate, inst_src); |
| 25629 | 25674 | }, |
| 25630 | 25675 | .Pointer => pointer: { |
| 25631 | const dest_info = dest_ty.ptrInfo().data; | |
| 25676 | const dest_info = dest_ty.ptrInfo(mod); | |
| 25632 | 25677 | |
| 25633 | 25678 | // Function body to function pointer. |
| 25634 | 25679 | if (inst_ty.zigTypeTag(mod) == .Fn) { |
| ... | ... | @@ -25643,11 +25688,11 @@ fn coerceExtra( |
| 25643 | 25688 | if (dest_info.size != .One) break :single_item; |
| 25644 | 25689 | if (!inst_ty.isSinglePointer(mod)) break :single_item; |
| 25645 | 25690 | if (!sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) break :pointer; |
| 25646 | const ptr_elem_ty = inst_ty.childType(); | |
| 25691 | const ptr_elem_ty = inst_ty.childType(mod); | |
| 25647 | 25692 | const array_ty = dest_info.pointee_type; |
| 25648 | 25693 | if (array_ty.zigTypeTag(mod) != .Array) break :single_item; |
| 25649 | const array_elem_ty = array_ty.childType(); | |
| 25650 | if (array_ty.arrayLen() != 1) break :single_item; | |
| 25694 | const array_elem_ty = array_ty.childType(mod); | |
| 25695 | if (array_ty.arrayLen(mod) != 1) break :single_item; | |
| 25651 | 25696 | const dest_is_mut = dest_info.mutable; |
| 25652 | 25697 | switch (try sema.coerceInMemoryAllowed(block, array_elem_ty, ptr_elem_ty, dest_is_mut, target, dest_ty_src, inst_src)) { |
| 25653 | 25698 | .ok => {}, |
| ... | ... | @@ -25660,9 +25705,9 @@ fn coerceExtra( |
| 25660 | 25705 | src_array_ptr: { |
| 25661 | 25706 | if (!inst_ty.isSinglePointer(mod)) break :src_array_ptr; |
| 25662 | 25707 | if (!sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) break :pointer; |
| 25663 | const array_ty = inst_ty.childType(); | |
| 25708 | const array_ty = inst_ty.childType(mod); | |
| 25664 | 25709 | if (array_ty.zigTypeTag(mod) != .Array) break :src_array_ptr; |
| 25665 | const array_elem_type = array_ty.childType(); | |
| 25710 | const array_elem_type = array_ty.childType(mod); | |
| 25666 | 25711 | const dest_is_mut = dest_info.mutable; |
| 25667 | 25712 | |
| 25668 | 25713 | const dst_elem_type = dest_info.pointee_type; |
| ... | ... | @@ -25680,7 +25725,7 @@ fn coerceExtra( |
| 25680 | 25725 | } |
| 25681 | 25726 | |
| 25682 | 25727 | if (dest_info.sentinel) |dest_sent| { |
| 25683 | if (array_ty.sentinel()) |inst_sent| { | |
| 25728 | if (array_ty.sentinel(mod)) |inst_sent| { | |
| 25684 | 25729 | if (!dest_sent.eql(inst_sent, dst_elem_type, sema.mod)) { |
| 25685 | 25730 | in_memory_result = .{ .ptr_sentinel = .{ |
| 25686 | 25731 | .actual = inst_sent, |
| ... | ... | @@ -25721,7 +25766,7 @@ fn coerceExtra( |
| 25721 | 25766 | if (!sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) break :src_c_ptr; |
| 25722 | 25767 | // In this case we must add a safety check because the C pointer |
| 25723 | 25768 | // could be null. |
| 25724 | const src_elem_ty = inst_ty.childType(); | |
| 25769 | const src_elem_ty = inst_ty.childType(mod); | |
| 25725 | 25770 | const dest_is_mut = dest_info.mutable; |
| 25726 | 25771 | const dst_elem_type = dest_info.pointee_type; |
| 25727 | 25772 | switch (try sema.coerceInMemoryAllowed(block, dst_elem_type, src_elem_ty, dest_is_mut, target, dest_ty_src, inst_src)) { |
| ... | ... | @@ -25784,7 +25829,7 @@ fn coerceExtra( |
| 25784 | 25829 | }, |
| 25785 | 25830 | .Pointer => p: { |
| 25786 | 25831 | if (!sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) break :p; |
| 25787 | const inst_info = inst_ty.ptrInfo().data; | |
| 25832 | const inst_info = inst_ty.ptrInfo(mod); | |
| 25788 | 25833 | switch (try sema.coerceInMemoryAllowed( |
| 25789 | 25834 | block, |
| 25790 | 25835 | dest_info.pointee_type, |
| ... | ... | @@ -25814,7 +25859,7 @@ fn coerceExtra( |
| 25814 | 25859 | .Union => { |
| 25815 | 25860 | // pointer to anonymous struct to pointer to union |
| 25816 | 25861 | if (inst_ty.isSinglePointer(mod) and |
| 25817 | inst_ty.childType().isAnonStruct() and | |
| 25862 | inst_ty.childType(mod).isAnonStruct() and | |
| 25818 | 25863 | sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) |
| 25819 | 25864 | { |
| 25820 | 25865 | return sema.coerceAnonStructToUnionPtrs(block, dest_ty, dest_ty_src, inst, inst_src); |
| ... | ... | @@ -25823,7 +25868,7 @@ fn coerceExtra( |
| 25823 | 25868 | .Struct => { |
| 25824 | 25869 | // pointer to anonymous struct to pointer to struct |
| 25825 | 25870 | if (inst_ty.isSinglePointer(mod) and |
| 25826 | inst_ty.childType().isAnonStruct() and | |
| 25871 | inst_ty.childType(mod).isAnonStruct() and | |
| 25827 | 25872 | sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) |
| 25828 | 25873 | { |
| 25829 | 25874 | return sema.coerceAnonStructToStructPtrs(block, dest_ty, dest_ty_src, inst, inst_src) catch |err| switch (err) { |
| ... | ... | @@ -25835,7 +25880,7 @@ fn coerceExtra( |
| 25835 | 25880 | .Array => { |
| 25836 | 25881 | // pointer to tuple to pointer to array |
| 25837 | 25882 | if (inst_ty.isSinglePointer(mod) and |
| 25838 | inst_ty.childType().isTuple() and | |
| 25883 | inst_ty.childType(mod).isTuple() and | |
| 25839 | 25884 | sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) |
| 25840 | 25885 | { |
| 25841 | 25886 | return sema.coerceTupleToArrayPtrs(block, dest_ty, dest_ty_src, inst, inst_src); |
| ... | ... | @@ -25854,7 +25899,7 @@ fn coerceExtra( |
| 25854 | 25899 | } |
| 25855 | 25900 | |
| 25856 | 25901 | if (!inst_ty.isSinglePointer(mod)) break :to_slice; |
| 25857 | const inst_child_ty = inst_ty.childType(); | |
| 25902 | const inst_child_ty = inst_ty.childType(mod); | |
| 25858 | 25903 | if (!inst_child_ty.isTuple()) break :to_slice; |
| 25859 | 25904 | |
| 25860 | 25905 | // empty tuple to zero-length slice |
| ... | ... | @@ -25887,7 +25932,7 @@ fn coerceExtra( |
| 25887 | 25932 | .Many => p: { |
| 25888 | 25933 | if (!inst_ty.isSlice(mod)) break :p; |
| 25889 | 25934 | if (!sema.checkPtrAttributes(dest_ty, inst_ty, &in_memory_result)) break :p; |
| 25890 | const inst_info = inst_ty.ptrInfo().data; | |
| 25935 | const inst_info = inst_ty.ptrInfo(mod); | |
| 25891 | 25936 | |
| 25892 | 25937 | switch (try sema.coerceInMemoryAllowed( |
| 25893 | 25938 | block, |
| ... | ... | @@ -26196,9 +26241,8 @@ fn coerceExtra( |
| 26196 | 26241 | } |
| 26197 | 26242 | |
| 26198 | 26243 | // ?T to T |
| 26199 | var buf: Type.Payload.ElemType = undefined; | |
| 26200 | 26244 | if (inst_ty.zigTypeTag(mod) == .Optional and |
| 26201 | (try sema.coerceInMemoryAllowed(block, inst_ty.optionalChild(&buf), dest_ty, false, target, dest_ty_src, inst_src)) == .ok) | |
| 26245 | (try sema.coerceInMemoryAllowed(block, inst_ty.optionalChild(mod), dest_ty, false, target, dest_ty_src, inst_src)) == .ok) | |
| 26202 | 26246 | { |
| 26203 | 26247 | try sema.errNote(block, inst_src, msg, "cannot convert optional to payload type", .{}); |
| 26204 | 26248 | try sema.errNote(block, inst_src, msg, "consider using '.?', 'orelse', or 'if'", .{}); |
| ... | ... | @@ -26399,10 +26443,8 @@ const InMemoryCoercionResult = union(enum) { |
| 26399 | 26443 | cur = pair.child; |
| 26400 | 26444 | }, |
| 26401 | 26445 | .optional_shape => |pair| { |
| 26402 | var buf_actual: Type.Payload.ElemType = undefined; | |
| 26403 | var buf_wanted: Type.Payload.ElemType = undefined; | |
| 26404 | 26446 | try sema.errNote(block, src, msg, "optional type child '{}' cannot cast into optional type child '{}'", .{ |
| 26405 | pair.actual.optionalChild(&buf_actual).fmt(sema.mod), pair.wanted.optionalChild(&buf_wanted).fmt(sema.mod), | |
| 26447 | pair.actual.optionalChild(mod).fmt(sema.mod), pair.wanted.optionalChild(mod).fmt(sema.mod), | |
| 26406 | 26448 | }); |
| 26407 | 26449 | break; |
| 26408 | 26450 | }, |
| ... | ... | @@ -26640,10 +26682,8 @@ fn coerceInMemoryAllowed( |
| 26640 | 26682 | } |
| 26641 | 26683 | |
| 26642 | 26684 | // Pointers / Pointer-like Optionals |
| 26643 | var dest_buf: Type.Payload.ElemType = undefined; | |
| 26644 | var src_buf: Type.Payload.ElemType = undefined; | |
| 26645 | const maybe_dest_ptr_ty = try sema.typePtrOrOptionalPtrTy(dest_ty, &dest_buf); | |
| 26646 | const maybe_src_ptr_ty = try sema.typePtrOrOptionalPtrTy(src_ty, &src_buf); | |
| 26685 | const maybe_dest_ptr_ty = try sema.typePtrOrOptionalPtrTy(dest_ty); | |
| 26686 | const maybe_src_ptr_ty = try sema.typePtrOrOptionalPtrTy(src_ty); | |
| 26647 | 26687 | if (maybe_dest_ptr_ty) |dest_ptr_ty| { |
| 26648 | 26688 | if (maybe_src_ptr_ty) |src_ptr_ty| { |
| 26649 | 26689 | return try sema.coerceInMemoryAllowedPtrs(block, dest_ty, src_ty, dest_ptr_ty, src_ptr_ty, dest_is_mut, target, dest_src, src_src); |
| ... | ... | @@ -26685,8 +26725,8 @@ fn coerceInMemoryAllowed( |
| 26685 | 26725 | |
| 26686 | 26726 | // Arrays |
| 26687 | 26727 | if (dest_tag == .Array and src_tag == .Array) { |
| 26688 | const dest_info = dest_ty.arrayInfo(); | |
| 26689 | const src_info = src_ty.arrayInfo(); | |
| 26728 | const dest_info = dest_ty.arrayInfo(mod); | |
| 26729 | const src_info = src_ty.arrayInfo(mod); | |
| 26690 | 26730 | if (dest_info.len != src_info.len) { |
| 26691 | 26731 | return InMemoryCoercionResult{ .array_len = .{ |
| 26692 | 26732 | .actual = src_info.len, |
| ... | ... | @@ -26717,8 +26757,8 @@ fn coerceInMemoryAllowed( |
| 26717 | 26757 | |
| 26718 | 26758 | // Vectors |
| 26719 | 26759 | if (dest_tag == .Vector and src_tag == .Vector) { |
| 26720 | const dest_len = dest_ty.vectorLen(); | |
| 26721 | const src_len = src_ty.vectorLen(); | |
| 26760 | const dest_len = dest_ty.vectorLen(mod); | |
| 26761 | const src_len = src_ty.vectorLen(mod); | |
| 26722 | 26762 | if (dest_len != src_len) { |
| 26723 | 26763 | return InMemoryCoercionResult{ .vector_len = .{ |
| 26724 | 26764 | .actual = src_len, |
| ... | ... | @@ -26748,8 +26788,8 @@ fn coerceInMemoryAllowed( |
| 26748 | 26788 | .wanted = dest_ty, |
| 26749 | 26789 | } }; |
| 26750 | 26790 | } |
| 26751 | const dest_child_type = dest_ty.optionalChild(&dest_buf); | |
| 26752 | const src_child_type = src_ty.optionalChild(&src_buf); | |
| 26791 | const dest_child_type = dest_ty.optionalChild(mod); | |
| 26792 | const src_child_type = src_ty.optionalChild(mod); | |
| 26753 | 26793 | |
| 26754 | 26794 | const child = try sema.coerceInMemoryAllowed(block, dest_child_type, src_child_type, dest_is_mut, target, dest_src, src_src); |
| 26755 | 26795 | if (child != .ok) { |
| ... | ... | @@ -27019,8 +27059,8 @@ fn coerceInMemoryAllowedPtrs( |
| 27019 | 27059 | src_src: LazySrcLoc, |
| 27020 | 27060 | ) !InMemoryCoercionResult { |
| 27021 | 27061 | const mod = sema.mod; |
| 27022 | const dest_info = dest_ptr_ty.ptrInfo().data; | |
| 27023 | const src_info = src_ptr_ty.ptrInfo().data; | |
| 27062 | const dest_info = dest_ptr_ty.ptrInfo(mod); | |
| 27063 | const src_info = src_ptr_ty.ptrInfo(mod); | |
| 27024 | 27064 | |
| 27025 | 27065 | const ok_ptr_size = src_info.size == dest_info.size or |
| 27026 | 27066 | src_info.size == .C or dest_info.size == .C; |
| ... | ... | @@ -27206,11 +27246,12 @@ fn storePtr2( |
| 27206 | 27246 | operand_src: LazySrcLoc, |
| 27207 | 27247 | air_tag: Air.Inst.Tag, |
| 27208 | 27248 | ) CompileError!void { |
| 27249 | const mod = sema.mod; | |
| 27209 | 27250 | const ptr_ty = sema.typeOf(ptr); |
| 27210 | 27251 | if (ptr_ty.isConstPtr()) |
| 27211 | 27252 | return sema.fail(block, ptr_src, "cannot assign to constant", .{}); |
| 27212 | 27253 | |
| 27213 | const elem_ty = ptr_ty.childType(); | |
| 27254 | const elem_ty = ptr_ty.childType(mod); | |
| 27214 | 27255 | |
| 27215 | 27256 | // To generate better code for tuples, we detect a tuple operand here, and |
| 27216 | 27257 | // analyze field loads and stores directly. This avoids an extra allocation + memcpy |
| ... | ... | @@ -27221,7 +27262,6 @@ fn storePtr2( |
| 27221 | 27262 | // this code does not handle tuple-to-struct coercion which requires dealing with missing |
| 27222 | 27263 | // fields. |
| 27223 | 27264 | const operand_ty = sema.typeOf(uncasted_operand); |
| 27224 | const mod = sema.mod; | |
| 27225 | 27265 | if (operand_ty.isTuple() and elem_ty.zigTypeTag(mod) == .Array) { |
| 27226 | 27266 | const field_count = operand_ty.structFieldCount(); |
| 27227 | 27267 | var i: u32 = 0; |
| ... | ... | @@ -27247,7 +27287,7 @@ fn storePtr2( |
| 27247 | 27287 | // as well as working around an LLVM bug: |
| 27248 | 27288 | // https://github.com/ziglang/zig/issues/11154 |
| 27249 | 27289 | if (sema.obtainBitCastedVectorPtr(ptr)) |vector_ptr| { |
| 27250 | const vector_ty = sema.typeOf(vector_ptr).childType(); | |
| 27290 | const vector_ty = sema.typeOf(vector_ptr).childType(mod); | |
| 27251 | 27291 | const vector = sema.coerceExtra(block, vector_ty, uncasted_operand, operand_src, .{ .is_ret = is_ret }) catch |err| switch (err) { |
| 27252 | 27292 | error.NotCoercible => unreachable, |
| 27253 | 27293 | else => |e| return e, |
| ... | ... | @@ -27288,7 +27328,7 @@ fn storePtr2( |
| 27288 | 27328 | try sema.requireRuntimeBlock(block, src, runtime_src); |
| 27289 | 27329 | try sema.queueFullTypeResolution(elem_ty); |
| 27290 | 27330 | |
| 27291 | if (ptr_ty.ptrInfo().data.vector_index == .runtime) { | |
| 27331 | if (ptr_ty.ptrInfo(mod).vector_index == .runtime) { | |
| 27292 | 27332 | const ptr_inst = Air.refToIndex(ptr).?; |
| 27293 | 27333 | const air_tags = sema.air_instructions.items(.tag); |
| 27294 | 27334 | if (air_tags[ptr_inst] == .ptr_elem_ptr) { |
| ... | ... | @@ -27322,8 +27362,8 @@ fn storePtr2( |
| 27322 | 27362 | /// pointer. Only if the final element type matches the vector element type, and the |
| 27323 | 27363 | /// lengths match. |
| 27324 | 27364 | fn obtainBitCastedVectorPtr(sema: *Sema, ptr: Air.Inst.Ref) ?Air.Inst.Ref { |
| 27325 | const array_ty = sema.typeOf(ptr).childType(); | |
| 27326 | 27365 | const mod = sema.mod; |
| 27366 | const array_ty = sema.typeOf(ptr).childType(mod); | |
| 27327 | 27367 | if (array_ty.zigTypeTag(mod) != .Array) return null; |
| 27328 | 27368 | var ptr_inst = Air.refToIndex(ptr) orelse return null; |
| 27329 | 27369 | const air_datas = sema.air_instructions.items(.data); |
| ... | ... | @@ -27332,7 +27372,6 @@ fn obtainBitCastedVectorPtr(sema: *Sema, ptr: Air.Inst.Ref) ?Air.Inst.Ref { |
| 27332 | 27372 | const prev_ptr = air_datas[ptr_inst].ty_op.operand; |
| 27333 | 27373 | const prev_ptr_ty = sema.typeOf(prev_ptr); |
| 27334 | 27374 | const prev_ptr_child_ty = switch (prev_ptr_ty.tag()) { |
| 27335 | .single_mut_pointer => prev_ptr_ty.castTag(.single_mut_pointer).?.data, | |
| 27336 | 27375 | .pointer => prev_ptr_ty.castTag(.pointer).?.data.pointee_type, |
| 27337 | 27376 | else => return null, |
| 27338 | 27377 | }; |
| ... | ... | @@ -27342,9 +27381,9 @@ fn obtainBitCastedVectorPtr(sema: *Sema, ptr: Air.Inst.Ref) ?Air.Inst.Ref { |
| 27342 | 27381 | |
| 27343 | 27382 | // We have a pointer-to-array and a pointer-to-vector. If the elements and |
| 27344 | 27383 | // lengths match, return the result. |
| 27345 | const vector_ty = sema.typeOf(prev_ptr).childType(); | |
| 27346 | if (array_ty.childType().eql(vector_ty.childType(), sema.mod) and | |
| 27347 | array_ty.arrayLen() == vector_ty.vectorLen()) | |
| 27384 | const vector_ty = sema.typeOf(prev_ptr).childType(mod); | |
| 27385 | if (array_ty.childType(mod).eql(vector_ty.childType(mod), sema.mod) and | |
| 27386 | array_ty.arrayLen(mod) == vector_ty.vectorLen(mod)) | |
| 27348 | 27387 | { |
| 27349 | 27388 | return prev_ptr; |
| 27350 | 27389 | } else { |
| ... | ... | @@ -27476,14 +27515,14 @@ fn beginComptimePtrMutation( |
| 27476 | 27515 | switch (parent.pointee) { |
| 27477 | 27516 | .direct => |val_ptr| switch (parent.ty.zigTypeTag(mod)) { |
| 27478 | 27517 | .Array, .Vector => { |
| 27479 | const check_len = parent.ty.arrayLenIncludingSentinel(); | |
| 27518 | const check_len = parent.ty.arrayLenIncludingSentinel(mod); | |
| 27480 | 27519 | if (elem_ptr.index >= check_len) { |
| 27481 | 27520 | // TODO have the parent include the decl so we can say "declared here" |
| 27482 | 27521 | return sema.fail(block, src, "comptime store of index {d} out of bounds of array length {d}", .{ |
| 27483 | 27522 | elem_ptr.index, check_len, |
| 27484 | 27523 | }); |
| 27485 | 27524 | } |
| 27486 | const elem_ty = parent.ty.childType(); | |
| 27525 | const elem_ty = parent.ty.childType(mod); | |
| 27487 | 27526 | |
| 27488 | 27527 | // We might have a pointer to multiple elements of the array (e.g. a pointer |
| 27489 | 27528 | // to a sub-array). In this case, we just have to reinterpret the relevant |
| ... | ... | @@ -27510,7 +27549,7 @@ fn beginComptimePtrMutation( |
| 27510 | 27549 | defer parent.finishArena(sema.mod); |
| 27511 | 27550 | |
| 27512 | 27551 | const array_len_including_sentinel = |
| 27513 | try sema.usizeCast(block, src, parent.ty.arrayLenIncludingSentinel()); | |
| 27552 | try sema.usizeCast(block, src, parent.ty.arrayLenIncludingSentinel(mod)); | |
| 27514 | 27553 | const elems = try arena.alloc(Value, array_len_including_sentinel); |
| 27515 | 27554 | @memset(elems, Value.undef); |
| 27516 | 27555 | |
| ... | ... | @@ -27536,7 +27575,7 @@ fn beginComptimePtrMutation( |
| 27536 | 27575 | defer parent.finishArena(sema.mod); |
| 27537 | 27576 | |
| 27538 | 27577 | const bytes = val_ptr.castTag(.bytes).?.data; |
| 27539 | const dest_len = parent.ty.arrayLenIncludingSentinel(); | |
| 27578 | const dest_len = parent.ty.arrayLenIncludingSentinel(mod); | |
| 27540 | 27579 | // bytes.len may be one greater than dest_len because of the case when |
| 27541 | 27580 | // assigning `[N:S]T` to `[N]T`. This is allowed; the sentinel is omitted. |
| 27542 | 27581 | assert(bytes.len >= dest_len); |
| ... | ... | @@ -27567,13 +27606,13 @@ fn beginComptimePtrMutation( |
| 27567 | 27606 | defer parent.finishArena(sema.mod); |
| 27568 | 27607 | |
| 27569 | 27608 | const str_lit = val_ptr.castTag(.str_lit).?.data; |
| 27570 | const dest_len = parent.ty.arrayLenIncludingSentinel(); | |
| 27609 | const dest_len = parent.ty.arrayLenIncludingSentinel(mod); | |
| 27571 | 27610 | const bytes = sema.mod.string_literal_bytes.items[str_lit.index..][0..str_lit.len]; |
| 27572 | 27611 | const elems = try arena.alloc(Value, @intCast(usize, dest_len)); |
| 27573 | 27612 | for (bytes, 0..) |byte, i| { |
| 27574 | 27613 | elems[i] = try Value.Tag.int_u64.create(arena, byte); |
| 27575 | 27614 | } |
| 27576 | if (parent.ty.sentinel()) |sent_val| { | |
| 27615 | if (parent.ty.sentinel(mod)) |sent_val| { | |
| 27577 | 27616 | assert(elems.len == bytes.len + 1); |
| 27578 | 27617 | elems[bytes.len] = sent_val; |
| 27579 | 27618 | } |
| ... | ... | @@ -27603,7 +27642,7 @@ fn beginComptimePtrMutation( |
| 27603 | 27642 | |
| 27604 | 27643 | const repeated_val = try val_ptr.castTag(.repeated).?.data.copy(arena); |
| 27605 | 27644 | const array_len_including_sentinel = |
| 27606 | try sema.usizeCast(block, src, parent.ty.arrayLenIncludingSentinel()); | |
| 27645 | try sema.usizeCast(block, src, parent.ty.arrayLenIncludingSentinel(mod)); | |
| 27607 | 27646 | const elems = try arena.alloc(Value, array_len_including_sentinel); |
| 27608 | 27647 | if (elems.len > 0) elems[0] = repeated_val; |
| 27609 | 27648 | for (elems[1..]) |*elem| { |
| ... | ... | @@ -27906,12 +27945,12 @@ fn beginComptimePtrMutation( |
| 27906 | 27945 | }, |
| 27907 | 27946 | .opt_payload_ptr => { |
| 27908 | 27947 | const opt_ptr = if (ptr_val.castTag(.opt_payload_ptr)) |some| some.data else { |
| 27909 | return sema.beginComptimePtrMutation(block, src, ptr_val, try ptr_elem_ty.optionalChildAlloc(sema.arena)); | |
| 27948 | return sema.beginComptimePtrMutation(block, src, ptr_val, ptr_elem_ty.optionalChild(mod)); | |
| 27910 | 27949 | }; |
| 27911 | 27950 | var parent = try sema.beginComptimePtrMutation(block, src, opt_ptr.container_ptr, opt_ptr.container_ty); |
| 27912 | 27951 | switch (parent.pointee) { |
| 27913 | 27952 | .direct => |val_ptr| { |
| 27914 | const payload_ty = try parent.ty.optionalChildAlloc(sema.arena); | |
| 27953 | const payload_ty = parent.ty.optionalChild(mod); | |
| 27915 | 27954 | switch (val_ptr.tag()) { |
| 27916 | 27955 | .undef, .null_value => { |
| 27917 | 27956 | // An optional has been initialized to undefined at comptime and now we |
| ... | ... | @@ -27984,7 +28023,7 @@ fn beginComptimePtrMutationInner( |
| 27984 | 28023 | |
| 27985 | 28024 | // Handle the case that the decl is an array and we're actually trying to point to an element. |
| 27986 | 28025 | if (decl_ty.isArrayOrVector(mod)) { |
| 27987 | const decl_elem_ty = decl_ty.childType(); | |
| 28026 | const decl_elem_ty = decl_ty.childType(mod); | |
| 27988 | 28027 | if ((try sema.coerceInMemoryAllowed(block, ptr_elem_ty, decl_elem_ty, true, target, src, src)) == .ok) { |
| 27989 | 28028 | return ComptimePtrMutationKit{ |
| 27990 | 28029 | .decl_ref_mut = decl_ref_mut, |
| ... | ... | @@ -28105,7 +28144,7 @@ fn beginComptimePtrLoad( |
| 28105 | 28144 | // If we're loading an elem_ptr that was derived from a different type |
| 28106 | 28145 | // than the true type of the underlying decl, we cannot deref directly |
| 28107 | 28146 | const ty_matches = if (deref.pointee != null and deref.pointee.?.ty.isArrayOrVector(mod)) x: { |
| 28108 | const deref_elem_ty = deref.pointee.?.ty.childType(); | |
| 28147 | const deref_elem_ty = deref.pointee.?.ty.childType(mod); | |
| 28109 | 28148 | break :x (try sema.coerceInMemoryAllowed(block, deref_elem_ty, elem_ty, false, target, src, src)) == .ok or |
| 28110 | 28149 | (try sema.coerceInMemoryAllowed(block, elem_ty, deref_elem_ty, false, target, src, src)) == .ok; |
| 28111 | 28150 | } else false; |
| ... | ... | @@ -28115,12 +28154,12 @@ fn beginComptimePtrLoad( |
| 28115 | 28154 | } |
| 28116 | 28155 | |
| 28117 | 28156 | var array_tv = deref.pointee.?; |
| 28118 | const check_len = array_tv.ty.arrayLenIncludingSentinel(); | |
| 28157 | const check_len = array_tv.ty.arrayLenIncludingSentinel(mod); | |
| 28119 | 28158 | if (maybe_array_ty) |load_ty| { |
| 28120 | 28159 | // It's possible that we're loading a [N]T, in which case we'd like to slice |
| 28121 | 28160 | // the pointee array directly from our parent array. |
| 28122 | if (load_ty.isArrayOrVector(mod) and load_ty.childType().eql(elem_ty, sema.mod)) { | |
| 28123 | const N = try sema.usizeCast(block, src, load_ty.arrayLenIncludingSentinel()); | |
| 28161 | if (load_ty.isArrayOrVector(mod) and load_ty.childType(mod).eql(elem_ty, sema.mod)) { | |
| 28162 | const N = try sema.usizeCast(block, src, load_ty.arrayLenIncludingSentinel(mod)); | |
| 28124 | 28163 | deref.pointee = if (elem_ptr.index + N <= check_len) TypedValue{ |
| 28125 | 28164 | .ty = try Type.array(sema.arena, N, null, elem_ty, sema.mod), |
| 28126 | 28165 | .val = try array_tv.val.sliceArray(sema.mod, sema.arena, elem_ptr.index, elem_ptr.index + N), |
| ... | ... | @@ -28134,7 +28173,7 @@ fn beginComptimePtrLoad( |
| 28134 | 28173 | break :blk deref; |
| 28135 | 28174 | } |
| 28136 | 28175 | if (elem_ptr.index == check_len - 1) { |
| 28137 | if (array_tv.ty.sentinel()) |sent| { | |
| 28176 | if (array_tv.ty.sentinel(mod)) |sent| { | |
| 28138 | 28177 | deref.pointee = TypedValue{ |
| 28139 | 28178 | .ty = elem_ty, |
| 28140 | 28179 | .val = sent, |
| ... | ... | @@ -28226,7 +28265,7 @@ fn beginComptimePtrLoad( |
| 28226 | 28265 | const payload_ptr = ptr_val.cast(Value.Payload.PayloadPtr).?.data; |
| 28227 | 28266 | const payload_ty = switch (ptr_val.tag()) { |
| 28228 | 28267 | .eu_payload_ptr => payload_ptr.container_ty.errorUnionPayload(), |
| 28229 | .opt_payload_ptr => try payload_ptr.container_ty.optionalChildAlloc(sema.arena), | |
| 28268 | .opt_payload_ptr => payload_ptr.container_ty.optionalChild(mod), | |
| 28230 | 28269 | else => unreachable, |
| 28231 | 28270 | }; |
| 28232 | 28271 | var deref = try sema.beginComptimePtrLoad(block, src, payload_ptr.container_ptr, payload_ptr.container_ty); |
| ... | ... | @@ -28357,12 +28396,13 @@ fn coerceArrayPtrToSlice( |
| 28357 | 28396 | inst: Air.Inst.Ref, |
| 28358 | 28397 | inst_src: LazySrcLoc, |
| 28359 | 28398 | ) CompileError!Air.Inst.Ref { |
| 28399 | const mod = sema.mod; | |
| 28360 | 28400 | if (try sema.resolveMaybeUndefVal(inst)) |val| { |
| 28361 | 28401 | const ptr_array_ty = sema.typeOf(inst); |
| 28362 | const array_ty = ptr_array_ty.childType(); | |
| 28402 | const array_ty = ptr_array_ty.childType(mod); | |
| 28363 | 28403 | const slice_val = try Value.Tag.slice.create(sema.arena, .{ |
| 28364 | 28404 | .ptr = val, |
| 28365 | .len = try Value.Tag.int_u64.create(sema.arena, array_ty.arrayLen()), | |
| 28405 | .len = try Value.Tag.int_u64.create(sema.arena, array_ty.arrayLen(mod)), | |
| 28366 | 28406 | }); |
| 28367 | 28407 | return sema.addConstant(dest_ty, slice_val); |
| 28368 | 28408 | } |
| ... | ... | @@ -28371,11 +28411,11 @@ fn coerceArrayPtrToSlice( |
| 28371 | 28411 | } |
| 28372 | 28412 | |
| 28373 | 28413 | fn checkPtrAttributes(sema: *Sema, dest_ty: Type, inst_ty: Type, in_memory_result: *InMemoryCoercionResult) bool { |
| 28374 | const dest_info = dest_ty.ptrInfo().data; | |
| 28375 | const inst_info = inst_ty.ptrInfo().data; | |
| 28376 | 28414 | const mod = sema.mod; |
| 28377 | const len0 = (inst_info.pointee_type.zigTypeTag(mod) == .Array and (inst_info.pointee_type.arrayLenIncludingSentinel() == 0 or | |
| 28378 | (inst_info.pointee_type.arrayLen() == 0 and dest_info.sentinel == null and dest_info.size != .C and dest_info.size != .Many))) or | |
| 28415 | const dest_info = dest_ty.ptrInfo(mod); | |
| 28416 | const inst_info = inst_ty.ptrInfo(mod); | |
| 28417 | const len0 = (inst_info.pointee_type.zigTypeTag(mod) == .Array and (inst_info.pointee_type.arrayLenIncludingSentinel(mod) == 0 or | |
| 28418 | (inst_info.pointee_type.arrayLen(mod) == 0 and dest_info.sentinel == null and dest_info.size != .C and dest_info.size != .Many))) or | |
| 28379 | 28419 | (inst_info.pointee_type.isTuple() and inst_info.pointee_type.structFieldCount() == 0); |
| 28380 | 28420 | |
| 28381 | 28421 | const ok_cv_qualifiers = |
| ... | ... | @@ -28647,7 +28687,8 @@ fn coerceAnonStructToUnionPtrs( |
| 28647 | 28687 | ptr_anon_struct: Air.Inst.Ref, |
| 28648 | 28688 | anon_struct_src: LazySrcLoc, |
| 28649 | 28689 | ) !Air.Inst.Ref { |
| 28650 | const union_ty = ptr_union_ty.childType(); | |
| 28690 | const mod = sema.mod; | |
| 28691 | const union_ty = ptr_union_ty.childType(mod); | |
| 28651 | 28692 | const anon_struct = try sema.analyzeLoad(block, anon_struct_src, ptr_anon_struct, anon_struct_src); |
| 28652 | 28693 | const union_inst = try sema.coerceAnonStructToUnion(block, union_ty, union_ty_src, anon_struct, anon_struct_src); |
| 28653 | 28694 | return sema.analyzeRef(block, union_ty_src, union_inst); |
| ... | ... | @@ -28661,7 +28702,8 @@ fn coerceAnonStructToStructPtrs( |
| 28661 | 28702 | ptr_anon_struct: Air.Inst.Ref, |
| 28662 | 28703 | anon_struct_src: LazySrcLoc, |
| 28663 | 28704 | ) !Air.Inst.Ref { |
| 28664 | const struct_ty = ptr_struct_ty.childType(); | |
| 28705 | const mod = sema.mod; | |
| 28706 | const struct_ty = ptr_struct_ty.childType(mod); | |
| 28665 | 28707 | const anon_struct = try sema.analyzeLoad(block, anon_struct_src, ptr_anon_struct, anon_struct_src); |
| 28666 | 28708 | const struct_inst = try sema.coerceTupleToStruct(block, struct_ty, anon_struct, anon_struct_src); |
| 28667 | 28709 | return sema.analyzeRef(block, struct_ty_src, struct_inst); |
| ... | ... | @@ -28676,15 +28718,16 @@ fn coerceArrayLike( |
| 28676 | 28718 | inst: Air.Inst.Ref, |
| 28677 | 28719 | inst_src: LazySrcLoc, |
| 28678 | 28720 | ) !Air.Inst.Ref { |
| 28721 | const mod = sema.mod; | |
| 28679 | 28722 | const inst_ty = sema.typeOf(inst); |
| 28680 | const inst_len = inst_ty.arrayLen(); | |
| 28681 | const dest_len = try sema.usizeCast(block, dest_ty_src, dest_ty.arrayLen()); | |
| 28682 | const target = sema.mod.getTarget(); | |
| 28723 | const inst_len = inst_ty.arrayLen(mod); | |
| 28724 | const dest_len = try sema.usizeCast(block, dest_ty_src, dest_ty.arrayLen(mod)); | |
| 28725 | const target = mod.getTarget(); | |
| 28683 | 28726 | |
| 28684 | 28727 | if (dest_len != inst_len) { |
| 28685 | 28728 | const msg = msg: { |
| 28686 | 28729 | const msg = try sema.errMsg(block, inst_src, "expected type '{}', found '{}'", .{ |
| 28687 | dest_ty.fmt(sema.mod), inst_ty.fmt(sema.mod), | |
| 28730 | dest_ty.fmt(mod), inst_ty.fmt(mod), | |
| 28688 | 28731 | }); |
| 28689 | 28732 | errdefer msg.destroy(sema.gpa); |
| 28690 | 28733 | try sema.errNote(block, dest_ty_src, msg, "destination has length {d}", .{dest_len}); |
| ... | ... | @@ -28694,8 +28737,8 @@ fn coerceArrayLike( |
| 28694 | 28737 | return sema.failWithOwnedErrorMsg(msg); |
| 28695 | 28738 | } |
| 28696 | 28739 | |
| 28697 | const dest_elem_ty = dest_ty.childType(); | |
| 28698 | const inst_elem_ty = inst_ty.childType(); | |
| 28740 | const dest_elem_ty = dest_ty.childType(mod); | |
| 28741 | const inst_elem_ty = inst_ty.childType(mod); | |
| 28699 | 28742 | const in_memory_result = try sema.coerceInMemoryAllowed(block, dest_elem_ty, inst_elem_ty, false, target, dest_ty_src, inst_src); |
| 28700 | 28743 | if (in_memory_result == .ok) { |
| 28701 | 28744 | if (try sema.resolveMaybeUndefVal(inst)) |inst_val| { |
| ... | ... | @@ -28749,9 +28792,10 @@ fn coerceTupleToArray( |
| 28749 | 28792 | inst: Air.Inst.Ref, |
| 28750 | 28793 | inst_src: LazySrcLoc, |
| 28751 | 28794 | ) !Air.Inst.Ref { |
| 28795 | const mod = sema.mod; | |
| 28752 | 28796 | const inst_ty = sema.typeOf(inst); |
| 28753 | const inst_len = inst_ty.arrayLen(); | |
| 28754 | const dest_len = dest_ty.arrayLen(); | |
| 28797 | const inst_len = inst_ty.arrayLen(mod); | |
| 28798 | const dest_len = dest_ty.arrayLen(mod); | |
| 28755 | 28799 | |
| 28756 | 28800 | if (dest_len != inst_len) { |
| 28757 | 28801 | const msg = msg: { |
| ... | ... | @@ -28766,16 +28810,16 @@ fn coerceTupleToArray( |
| 28766 | 28810 | return sema.failWithOwnedErrorMsg(msg); |
| 28767 | 28811 | } |
| 28768 | 28812 | |
| 28769 | const dest_elems = try sema.usizeCast(block, dest_ty_src, dest_ty.arrayLenIncludingSentinel()); | |
| 28813 | const dest_elems = try sema.usizeCast(block, dest_ty_src, dest_ty.arrayLenIncludingSentinel(mod)); | |
| 28770 | 28814 | const element_vals = try sema.arena.alloc(Value, dest_elems); |
| 28771 | 28815 | const element_refs = try sema.arena.alloc(Air.Inst.Ref, dest_elems); |
| 28772 | const dest_elem_ty = dest_ty.childType(); | |
| 28816 | const dest_elem_ty = dest_ty.childType(mod); | |
| 28773 | 28817 | |
| 28774 | 28818 | var runtime_src: ?LazySrcLoc = null; |
| 28775 | 28819 | for (element_vals, 0..) |*elem, i_usize| { |
| 28776 | 28820 | const i = @intCast(u32, i_usize); |
| 28777 | 28821 | if (i_usize == inst_len) { |
| 28778 | elem.* = dest_ty.sentinel().?; | |
| 28822 | elem.* = dest_ty.sentinel(mod).?; | |
| 28779 | 28823 | element_refs[i] = try sema.addConstant(dest_elem_ty, elem.*); |
| 28780 | 28824 | break; |
| 28781 | 28825 | } |
| ... | ... | @@ -28812,9 +28856,10 @@ fn coerceTupleToSlicePtrs( |
| 28812 | 28856 | ptr_tuple: Air.Inst.Ref, |
| 28813 | 28857 | tuple_src: LazySrcLoc, |
| 28814 | 28858 | ) !Air.Inst.Ref { |
| 28815 | const tuple_ty = sema.typeOf(ptr_tuple).childType(); | |
| 28859 | const mod = sema.mod; | |
| 28860 | const tuple_ty = sema.typeOf(ptr_tuple).childType(mod); | |
| 28816 | 28861 | const tuple = try sema.analyzeLoad(block, tuple_src, ptr_tuple, tuple_src); |
| 28817 | const slice_info = slice_ty.ptrInfo().data; | |
| 28862 | const slice_info = slice_ty.ptrInfo(mod); | |
| 28818 | 28863 | const array_ty = try Type.array(sema.arena, tuple_ty.structFieldCount(), slice_info.sentinel, slice_info.pointee_type, sema.mod); |
| 28819 | 28864 | const array_inst = try sema.coerceTupleToArray(block, array_ty, slice_ty_src, tuple, tuple_src); |
| 28820 | 28865 | if (slice_info.@"align" != 0) { |
| ... | ... | @@ -28833,8 +28878,9 @@ fn coerceTupleToArrayPtrs( |
| 28833 | 28878 | ptr_tuple: Air.Inst.Ref, |
| 28834 | 28879 | tuple_src: LazySrcLoc, |
| 28835 | 28880 | ) !Air.Inst.Ref { |
| 28881 | const mod = sema.mod; | |
| 28836 | 28882 | const tuple = try sema.analyzeLoad(block, tuple_src, ptr_tuple, tuple_src); |
| 28837 | const ptr_info = ptr_array_ty.ptrInfo().data; | |
| 28883 | const ptr_info = ptr_array_ty.ptrInfo(mod); | |
| 28838 | 28884 | const array_ty = ptr_info.pointee_type; |
| 28839 | 28885 | const array_inst = try sema.coerceTupleToArray(block, array_ty, array_ty_src, tuple, tuple_src); |
| 28840 | 28886 | if (ptr_info.@"align" != 0) { |
| ... | ... | @@ -29231,7 +29277,7 @@ fn analyzeLoad( |
| 29231 | 29277 | const mod = sema.mod; |
| 29232 | 29278 | const ptr_ty = sema.typeOf(ptr); |
| 29233 | 29279 | const elem_ty = switch (ptr_ty.zigTypeTag(mod)) { |
| 29234 | .Pointer => ptr_ty.childType(), | |
| 29280 | .Pointer => ptr_ty.childType(mod), | |
| 29235 | 29281 | else => return sema.fail(block, ptr_src, "expected pointer, found '{}'", .{ptr_ty.fmt(sema.mod)}), |
| 29236 | 29282 | }; |
| 29237 | 29283 | |
| ... | ... | @@ -29245,7 +29291,7 @@ fn analyzeLoad( |
| 29245 | 29291 | } |
| 29246 | 29292 | } |
| 29247 | 29293 | |
| 29248 | if (ptr_ty.ptrInfo().data.vector_index == .runtime) { | |
| 29294 | if (ptr_ty.ptrInfo(mod).vector_index == .runtime) { | |
| 29249 | 29295 | const ptr_inst = Air.refToIndex(ptr).?; |
| 29250 | 29296 | const air_tags = sema.air_instructions.items(.tag); |
| 29251 | 29297 | if (air_tags[ptr_inst] == .ptr_elem_ptr) { |
| ... | ... | @@ -29318,8 +29364,7 @@ fn analyzeIsNull( |
| 29318 | 29364 | |
| 29319 | 29365 | const inverted_non_null_res = if (invert_logic) Air.Inst.Ref.bool_true else Air.Inst.Ref.bool_false; |
| 29320 | 29366 | const operand_ty = sema.typeOf(operand); |
| 29321 | var buf: Type.Payload.ElemType = undefined; | |
| 29322 | if (operand_ty.zigTypeTag(mod) == .Optional and operand_ty.optionalChild(&buf).zigTypeTag(mod) == .NoReturn) { | |
| 29367 | if (operand_ty.zigTypeTag(mod) == .Optional and operand_ty.optionalChild(mod).zigTypeTag(mod) == .NoReturn) { | |
| 29323 | 29368 | return inverted_non_null_res; |
| 29324 | 29369 | } |
| 29325 | 29370 | if (operand_ty.zigTypeTag(mod) != .Optional and !operand_ty.isPtrLikeOptional(mod)) { |
| ... | ... | @@ -29339,7 +29384,7 @@ fn analyzePtrIsNonErrComptimeOnly( |
| 29339 | 29384 | const mod = sema.mod; |
| 29340 | 29385 | const ptr_ty = sema.typeOf(operand); |
| 29341 | 29386 | assert(ptr_ty.zigTypeTag(mod) == .Pointer); |
| 29342 | const child_ty = ptr_ty.childType(); | |
| 29387 | const child_ty = ptr_ty.childType(mod); | |
| 29343 | 29388 | |
| 29344 | 29389 | const child_tag = child_ty.zigTypeTag(mod); |
| 29345 | 29390 | if (child_tag != .ErrorSet and child_tag != .ErrorUnion) return Air.Inst.Ref.bool_true; |
| ... | ... | @@ -29495,7 +29540,7 @@ fn analyzeSlice( |
| 29495 | 29540 | // the slice operand to be a pointer. In the case of a non-array, it will be a double pointer. |
| 29496 | 29541 | const ptr_ptr_ty = sema.typeOf(ptr_ptr); |
| 29497 | 29542 | const ptr_ptr_child_ty = switch (ptr_ptr_ty.zigTypeTag(mod)) { |
| 29498 | .Pointer => ptr_ptr_ty.elemType(), | |
| 29543 | .Pointer => ptr_ptr_ty.childType(mod), | |
| 29499 | 29544 | else => return sema.fail(block, ptr_src, "expected pointer, found '{}'", .{ptr_ptr_ty.fmt(sema.mod)}), |
| 29500 | 29545 | }; |
| 29501 | 29546 | |
| ... | ... | @@ -29506,30 +29551,30 @@ fn analyzeSlice( |
| 29506 | 29551 | var ptr_sentinel: ?Value = null; |
| 29507 | 29552 | switch (ptr_ptr_child_ty.zigTypeTag(mod)) { |
| 29508 | 29553 | .Array => { |
| 29509 | ptr_sentinel = ptr_ptr_child_ty.sentinel(); | |
| 29510 | elem_ty = ptr_ptr_child_ty.childType(); | |
| 29554 | ptr_sentinel = ptr_ptr_child_ty.sentinel(mod); | |
| 29555 | elem_ty = ptr_ptr_child_ty.childType(mod); | |
| 29511 | 29556 | }, |
| 29512 | .Pointer => switch (ptr_ptr_child_ty.ptrSize()) { | |
| 29557 | .Pointer => switch (ptr_ptr_child_ty.ptrSize(mod)) { | |
| 29513 | 29558 | .One => { |
| 29514 | const double_child_ty = ptr_ptr_child_ty.childType(); | |
| 29559 | const double_child_ty = ptr_ptr_child_ty.childType(mod); | |
| 29515 | 29560 | if (double_child_ty.zigTypeTag(mod) == .Array) { |
| 29516 | ptr_sentinel = double_child_ty.sentinel(); | |
| 29561 | ptr_sentinel = double_child_ty.sentinel(mod); | |
| 29517 | 29562 | ptr_or_slice = try sema.analyzeLoad(block, src, ptr_ptr, ptr_src); |
| 29518 | 29563 | slice_ty = ptr_ptr_child_ty; |
| 29519 | 29564 | array_ty = double_child_ty; |
| 29520 | elem_ty = double_child_ty.childType(); | |
| 29565 | elem_ty = double_child_ty.childType(mod); | |
| 29521 | 29566 | } else { |
| 29522 | 29567 | return sema.fail(block, src, "slice of single-item pointer", .{}); |
| 29523 | 29568 | } |
| 29524 | 29569 | }, |
| 29525 | 29570 | .Many, .C => { |
| 29526 | ptr_sentinel = ptr_ptr_child_ty.sentinel(); | |
| 29571 | ptr_sentinel = ptr_ptr_child_ty.sentinel(mod); | |
| 29527 | 29572 | ptr_or_slice = try sema.analyzeLoad(block, src, ptr_ptr, ptr_src); |
| 29528 | 29573 | slice_ty = ptr_ptr_child_ty; |
| 29529 | 29574 | array_ty = ptr_ptr_child_ty; |
| 29530 | elem_ty = ptr_ptr_child_ty.childType(); | |
| 29575 | elem_ty = ptr_ptr_child_ty.childType(mod); | |
| 29531 | 29576 | |
| 29532 | if (ptr_ptr_child_ty.ptrSize() == .C) { | |
| 29577 | if (ptr_ptr_child_ty.ptrSize(mod) == .C) { | |
| 29533 | 29578 | if (try sema.resolveDefinedValue(block, ptr_src, ptr_or_slice)) |ptr_val| { |
| 29534 | 29579 | if (ptr_val.isNull(mod)) { |
| 29535 | 29580 | return sema.fail(block, src, "slice of null pointer", .{}); |
| ... | ... | @@ -29538,11 +29583,11 @@ fn analyzeSlice( |
| 29538 | 29583 | } |
| 29539 | 29584 | }, |
| 29540 | 29585 | .Slice => { |
| 29541 | ptr_sentinel = ptr_ptr_child_ty.sentinel(); | |
| 29586 | ptr_sentinel = ptr_ptr_child_ty.sentinel(mod); | |
| 29542 | 29587 | ptr_or_slice = try sema.analyzeLoad(block, src, ptr_ptr, ptr_src); |
| 29543 | 29588 | slice_ty = ptr_ptr_child_ty; |
| 29544 | 29589 | array_ty = ptr_ptr_child_ty; |
| 29545 | elem_ty = ptr_ptr_child_ty.childType(); | |
| 29590 | elem_ty = ptr_ptr_child_ty.childType(mod); | |
| 29546 | 29591 | }, |
| 29547 | 29592 | }, |
| 29548 | 29593 | else => return sema.fail(block, src, "slice of non-array type '{}'", .{ptr_ptr_child_ty.fmt(mod)}), |
| ... | ... | @@ -29563,7 +29608,7 @@ fn analyzeSlice( |
| 29563 | 29608 | var end_is_len = uncasted_end_opt == .none; |
| 29564 | 29609 | const end = e: { |
| 29565 | 29610 | if (array_ty.zigTypeTag(mod) == .Array) { |
| 29566 | const len_val = try Value.Tag.int_u64.create(sema.arena, array_ty.arrayLen()); | |
| 29611 | const len_val = try Value.Tag.int_u64.create(sema.arena, array_ty.arrayLen(mod)); | |
| 29567 | 29612 | |
| 29568 | 29613 | if (!end_is_len) { |
| 29569 | 29614 | const end = if (by_length) end: { |
| ... | ... | @@ -29574,10 +29619,10 @@ fn analyzeSlice( |
| 29574 | 29619 | if (try sema.resolveMaybeUndefVal(end)) |end_val| { |
| 29575 | 29620 | const len_s_val = try Value.Tag.int_u64.create( |
| 29576 | 29621 | sema.arena, |
| 29577 | array_ty.arrayLenIncludingSentinel(), | |
| 29622 | array_ty.arrayLenIncludingSentinel(mod), | |
| 29578 | 29623 | ); |
| 29579 | 29624 | if (!(try sema.compareAll(end_val, .lte, len_s_val, Type.usize))) { |
| 29580 | const sentinel_label: []const u8 = if (array_ty.sentinel() != null) | |
| 29625 | const sentinel_label: []const u8 = if (array_ty.sentinel(mod) != null) | |
| 29581 | 29626 | " +1 (sentinel)" |
| 29582 | 29627 | else |
| 29583 | 29628 | ""; |
| ... | ... | @@ -29617,7 +29662,7 @@ fn analyzeSlice( |
| 29617 | 29662 | if (slice_val.isUndef()) { |
| 29618 | 29663 | return sema.fail(block, src, "slice of undefined", .{}); |
| 29619 | 29664 | } |
| 29620 | const has_sentinel = slice_ty.sentinel() != null; | |
| 29665 | const has_sentinel = slice_ty.sentinel(mod) != null; | |
| 29621 | 29666 | var int_payload: Value.Payload.U64 = .{ |
| 29622 | 29667 | .base = .{ .tag = .int_u64 }, |
| 29623 | 29668 | .data = slice_val.sliceLen(mod) + @boolToInt(has_sentinel), |
| ... | ... | @@ -29751,8 +29796,8 @@ fn analyzeSlice( |
| 29751 | 29796 | try sema.analyzeArithmetic(block, .sub, end, start, src, end_src, start_src, false); |
| 29752 | 29797 | const opt_new_len_val = try sema.resolveDefinedValue(block, src, new_len); |
| 29753 | 29798 | |
| 29754 | const new_ptr_ty_info = sema.typeOf(new_ptr).ptrInfo().data; | |
| 29755 | const new_allowzero = new_ptr_ty_info.@"allowzero" and sema.typeOf(ptr).ptrSize() != .C; | |
| 29799 | const new_ptr_ty_info = sema.typeOf(new_ptr).ptrInfo(mod); | |
| 29800 | const new_allowzero = new_ptr_ty_info.@"allowzero" and sema.typeOf(ptr).ptrSize(mod) != .C; | |
| 29756 | 29801 | |
| 29757 | 29802 | if (opt_new_len_val) |new_len_val| { |
| 29758 | 29803 | const new_len_int = new_len_val.toUnsignedInt(mod); |
| ... | ... | @@ -29780,7 +29825,7 @@ fn analyzeSlice( |
| 29780 | 29825 | |
| 29781 | 29826 | if (slice_ty.isSlice(mod)) { |
| 29782 | 29827 | const slice_len_inst = try block.addTyOp(.slice_len, Type.usize, ptr_or_slice); |
| 29783 | const actual_len = if (slice_ty.sentinel() == null) | |
| 29828 | const actual_len = if (slice_ty.sentinel(mod) == null) | |
| 29784 | 29829 | slice_len_inst |
| 29785 | 29830 | else |
| 29786 | 29831 | try sema.analyzeArithmetic(block, .add, slice_len_inst, .one, src, end_src, end_src, true); |
| ... | ... | @@ -29839,7 +29884,7 @@ fn analyzeSlice( |
| 29839 | 29884 | |
| 29840 | 29885 | // requirement: end <= len |
| 29841 | 29886 | const opt_len_inst = if (array_ty.zigTypeTag(mod) == .Array) |
| 29842 | try sema.addIntUnsigned(Type.usize, array_ty.arrayLenIncludingSentinel()) | |
| 29887 | try sema.addIntUnsigned(Type.usize, array_ty.arrayLenIncludingSentinel(mod)) | |
| 29843 | 29888 | else if (slice_ty.isSlice(mod)) blk: { |
| 29844 | 29889 | if (try sema.resolveDefinedValue(block, src, ptr_or_slice)) |slice_val| { |
| 29845 | 29890 | // we don't need to add one for sentinels because the |
| ... | ... | @@ -29848,7 +29893,7 @@ fn analyzeSlice( |
| 29848 | 29893 | } |
| 29849 | 29894 | |
| 29850 | 29895 | const slice_len_inst = try block.addTyOp(.slice_len, Type.usize, ptr_or_slice); |
| 29851 | if (slice_ty.sentinel() == null) break :blk slice_len_inst; | |
| 29896 | if (slice_ty.sentinel(mod) == null) break :blk slice_len_inst; | |
| 29852 | 29897 | |
| 29853 | 29898 | // we have to add one because slice lengths don't include the sentinel |
| 29854 | 29899 | break :blk try sema.analyzeArithmetic(block, .add, slice_len_inst, .one, src, end_src, end_src, true); |
| ... | ... | @@ -30284,7 +30329,10 @@ fn cmpVector( |
| 30284 | 30329 | const casted_lhs = try sema.coerce(block, resolved_ty, lhs, lhs_src); |
| 30285 | 30330 | const casted_rhs = try sema.coerce(block, resolved_ty, rhs, rhs_src); |
| 30286 | 30331 | |
| 30287 | const result_ty = try Type.vector(sema.arena, lhs_ty.vectorLen(), Type.bool); | |
| 30332 | const result_ty = try mod.vectorType(.{ | |
| 30333 | .len = lhs_ty.vectorLen(mod), | |
| 30334 | .child = .bool_type, | |
| 30335 | }); | |
| 30288 | 30336 | |
| 30289 | 30337 | const runtime_src: LazySrcLoc = src: { |
| 30290 | 30338 | if (try sema.resolveMaybeUndefVal(casted_lhs)) |lhs_val| { |
| ... | ... | @@ -30484,12 +30532,12 @@ fn resolvePeerTypes( |
| 30484 | 30532 | } |
| 30485 | 30533 | continue; |
| 30486 | 30534 | }, |
| 30487 | .Pointer => if (chosen_ty.ptrSize() == .C) continue, | |
| 30535 | .Pointer => if (chosen_ty.ptrSize(mod) == .C) continue, | |
| 30488 | 30536 | else => {}, |
| 30489 | 30537 | }, |
| 30490 | 30538 | .ComptimeInt => switch (chosen_ty_tag) { |
| 30491 | 30539 | .Int, .Float, .ComptimeFloat => continue, |
| 30492 | .Pointer => if (chosen_ty.ptrSize() == .C) continue, | |
| 30540 | .Pointer => if (chosen_ty.ptrSize(mod) == .C) continue, | |
| 30493 | 30541 | else => {}, |
| 30494 | 30542 | }, |
| 30495 | 30543 | .Float => switch (chosen_ty_tag) { |
| ... | ... | @@ -30654,10 +30702,10 @@ fn resolvePeerTypes( |
| 30654 | 30702 | }, |
| 30655 | 30703 | }, |
| 30656 | 30704 | .Pointer => { |
| 30657 | const cand_info = candidate_ty.ptrInfo().data; | |
| 30705 | const cand_info = candidate_ty.ptrInfo(mod); | |
| 30658 | 30706 | switch (chosen_ty_tag) { |
| 30659 | 30707 | .Pointer => { |
| 30660 | const chosen_info = chosen_ty.ptrInfo().data; | |
| 30708 | const chosen_info = chosen_ty.ptrInfo(mod); | |
| 30661 | 30709 | |
| 30662 | 30710 | seen_const = seen_const or !chosen_info.mutable or !cand_info.mutable; |
| 30663 | 30711 | |
| ... | ... | @@ -30690,8 +30738,8 @@ fn resolvePeerTypes( |
| 30690 | 30738 | chosen_info.pointee_type.zigTypeTag(mod) == .Array and |
| 30691 | 30739 | cand_info.pointee_type.zigTypeTag(mod) == .Array) |
| 30692 | 30740 | { |
| 30693 | const chosen_elem_ty = chosen_info.pointee_type.childType(); | |
| 30694 | const cand_elem_ty = cand_info.pointee_type.childType(); | |
| 30741 | const chosen_elem_ty = chosen_info.pointee_type.childType(mod); | |
| 30742 | const cand_elem_ty = cand_info.pointee_type.childType(mod); | |
| 30695 | 30743 | |
| 30696 | 30744 | const chosen_ok = .ok == try sema.coerceInMemoryAllowed(block, chosen_elem_ty, cand_elem_ty, chosen_info.mutable, target, src, src); |
| 30697 | 30745 | if (chosen_ok) { |
| ... | ... | @@ -30757,10 +30805,9 @@ fn resolvePeerTypes( |
| 30757 | 30805 | } |
| 30758 | 30806 | }, |
| 30759 | 30807 | .Optional => { |
| 30760 | var opt_child_buf: Type.Payload.ElemType = undefined; | |
| 30761 | const chosen_ptr_ty = chosen_ty.optionalChild(&opt_child_buf); | |
| 30808 | const chosen_ptr_ty = chosen_ty.optionalChild(mod); | |
| 30762 | 30809 | if (chosen_ptr_ty.zigTypeTag(mod) == .Pointer) { |
| 30763 | const chosen_info = chosen_ptr_ty.ptrInfo().data; | |
| 30810 | const chosen_info = chosen_ptr_ty.ptrInfo(mod); | |
| 30764 | 30811 | |
| 30765 | 30812 | seen_const = seen_const or !chosen_info.mutable or !cand_info.mutable; |
| 30766 | 30813 | |
| ... | ... | @@ -30777,7 +30824,7 @@ fn resolvePeerTypes( |
| 30777 | 30824 | .ErrorUnion => { |
| 30778 | 30825 | const chosen_ptr_ty = chosen_ty.errorUnionPayload(); |
| 30779 | 30826 | if (chosen_ptr_ty.zigTypeTag(mod) == .Pointer) { |
| 30780 | const chosen_info = chosen_ptr_ty.ptrInfo().data; | |
| 30827 | const chosen_info = chosen_ptr_ty.ptrInfo(mod); | |
| 30781 | 30828 | |
| 30782 | 30829 | seen_const = seen_const or !chosen_info.mutable or !cand_info.mutable; |
| 30783 | 30830 | |
| ... | ... | @@ -30802,8 +30849,7 @@ fn resolvePeerTypes( |
| 30802 | 30849 | } |
| 30803 | 30850 | }, |
| 30804 | 30851 | .Optional => { |
| 30805 | var opt_child_buf: Type.Payload.ElemType = undefined; | |
| 30806 | const opt_child_ty = candidate_ty.optionalChild(&opt_child_buf); | |
| 30852 | const opt_child_ty = candidate_ty.optionalChild(mod); | |
| 30807 | 30853 | if ((try sema.coerceInMemoryAllowed(block, chosen_ty, opt_child_ty, false, target, src, src)) == .ok) { |
| 30808 | 30854 | seen_const = seen_const or opt_child_ty.isConstPtr(); |
| 30809 | 30855 | any_are_null = true; |
| ... | ... | @@ -30818,13 +30864,13 @@ fn resolvePeerTypes( |
| 30818 | 30864 | }, |
| 30819 | 30865 | .Vector => switch (chosen_ty_tag) { |
| 30820 | 30866 | .Vector => { |
| 30821 | const chosen_len = chosen_ty.vectorLen(); | |
| 30822 | const candidate_len = candidate_ty.vectorLen(); | |
| 30867 | const chosen_len = chosen_ty.vectorLen(mod); | |
| 30868 | const candidate_len = candidate_ty.vectorLen(mod); | |
| 30823 | 30869 | if (chosen_len != candidate_len) |
| 30824 | 30870 | continue; |
| 30825 | 30871 | |
| 30826 | const chosen_child_ty = chosen_ty.childType(); | |
| 30827 | const candidate_child_ty = candidate_ty.childType(); | |
| 30872 | const chosen_child_ty = chosen_ty.childType(mod); | |
| 30873 | const candidate_child_ty = candidate_ty.childType(mod); | |
| 30828 | 30874 | if (chosen_child_ty.zigTypeTag(mod) == .Int and candidate_child_ty.zigTypeTag(mod) == .Int) { |
| 30829 | 30875 | const chosen_info = chosen_child_ty.intInfo(mod); |
| 30830 | 30876 | const candidate_info = candidate_child_ty.intInfo(mod); |
| ... | ... | @@ -30853,8 +30899,8 @@ fn resolvePeerTypes( |
| 30853 | 30899 | .Vector => continue, |
| 30854 | 30900 | else => {}, |
| 30855 | 30901 | }, |
| 30856 | .Fn => if (chosen_ty.isSinglePointer(mod) and chosen_ty.isConstPtr() and chosen_ty.childType().zigTypeTag(mod) == .Fn) { | |
| 30857 | if (.ok == try sema.coerceInMemoryAllowedFns(block, chosen_ty.childType(), candidate_ty, target, src, src)) { | |
| 30902 | .Fn => if (chosen_ty.isSinglePointer(mod) and chosen_ty.isConstPtr() and chosen_ty.childType(mod).zigTypeTag(mod) == .Fn) { | |
| 30903 | if (.ok == try sema.coerceInMemoryAllowedFns(block, chosen_ty.childType(mod), candidate_ty, target, src, src)) { | |
| 30858 | 30904 | continue; |
| 30859 | 30905 | } |
| 30860 | 30906 | }, |
| ... | ... | @@ -30874,8 +30920,7 @@ fn resolvePeerTypes( |
| 30874 | 30920 | continue; |
| 30875 | 30921 | }, |
| 30876 | 30922 | .Optional => { |
| 30877 | var opt_child_buf: Type.Payload.ElemType = undefined; | |
| 30878 | const opt_child_ty = chosen_ty.optionalChild(&opt_child_buf); | |
| 30923 | const opt_child_ty = chosen_ty.optionalChild(mod); | |
| 30879 | 30924 | if ((try sema.coerceInMemoryAllowed(block, opt_child_ty, candidate_ty, false, target, src, src)) == .ok) { |
| 30880 | 30925 | continue; |
| 30881 | 30926 | } |
| ... | ... | @@ -30949,16 +30994,16 @@ fn resolvePeerTypes( |
| 30949 | 30994 | |
| 30950 | 30995 | if (convert_to_slice) { |
| 30951 | 30996 | // turn *[N]T => []T |
| 30952 | const chosen_child_ty = chosen_ty.childType(); | |
| 30953 | var info = chosen_ty.ptrInfo(); | |
| 30954 | info.data.sentinel = chosen_child_ty.sentinel(); | |
| 30955 | info.data.size = .Slice; | |
| 30956 | info.data.mutable = !(seen_const or chosen_child_ty.isConstPtr()); | |
| 30957 | info.data.pointee_type = chosen_child_ty.elemType2(mod); | |
| 30958 | ||
| 30959 | const new_ptr_ty = try Type.ptr(sema.arena, mod, info.data); | |
| 30997 | const chosen_child_ty = chosen_ty.childType(mod); | |
| 30998 | var info = chosen_ty.ptrInfo(mod); | |
| 30999 | info.sentinel = chosen_child_ty.sentinel(mod); | |
| 31000 | info.size = .Slice; | |
| 31001 | info.mutable = !(seen_const or chosen_child_ty.isConstPtr()); | |
| 31002 | info.pointee_type = chosen_child_ty.elemType2(mod); | |
| 31003 | ||
| 31004 | const new_ptr_ty = try Type.ptr(sema.arena, mod, info); | |
| 30960 | 31005 | const opt_ptr_ty = if (any_are_null) |
| 30961 | try Type.optional(sema.arena, new_ptr_ty) | |
| 31006 | try Type.optional(sema.arena, new_ptr_ty, mod) | |
| 30962 | 31007 | else |
| 30963 | 31008 | new_ptr_ty; |
| 30964 | 31009 | const set_ty = err_set_ty orelse return opt_ptr_ty; |
| ... | ... | @@ -30970,22 +31015,22 @@ fn resolvePeerTypes( |
| 30970 | 31015 | switch (chosen_ty.zigTypeTag(mod)) { |
| 30971 | 31016 | .ErrorUnion => { |
| 30972 | 31017 | const ptr_ty = chosen_ty.errorUnionPayload(); |
| 30973 | var info = ptr_ty.ptrInfo(); | |
| 30974 | info.data.mutable = false; | |
| 30975 | const new_ptr_ty = try Type.ptr(sema.arena, mod, info.data); | |
| 31018 | var info = ptr_ty.ptrInfo(mod); | |
| 31019 | info.mutable = false; | |
| 31020 | const new_ptr_ty = try Type.ptr(sema.arena, mod, info); | |
| 30976 | 31021 | const opt_ptr_ty = if (any_are_null) |
| 30977 | try Type.optional(sema.arena, new_ptr_ty) | |
| 31022 | try Type.optional(sema.arena, new_ptr_ty, mod) | |
| 30978 | 31023 | else |
| 30979 | 31024 | new_ptr_ty; |
| 30980 | 31025 | const set_ty = err_set_ty orelse chosen_ty.errorUnionSet(); |
| 30981 | 31026 | return try Type.errorUnion(sema.arena, set_ty, opt_ptr_ty, mod); |
| 30982 | 31027 | }, |
| 30983 | 31028 | .Pointer => { |
| 30984 | var info = chosen_ty.ptrInfo(); | |
| 30985 | info.data.mutable = false; | |
| 30986 | const new_ptr_ty = try Type.ptr(sema.arena, mod, info.data); | |
| 31029 | var info = chosen_ty.ptrInfo(mod); | |
| 31030 | info.mutable = false; | |
| 31031 | const new_ptr_ty = try Type.ptr(sema.arena, mod, info); | |
| 30987 | 31032 | const opt_ptr_ty = if (any_are_null) |
| 30988 | try Type.optional(sema.arena, new_ptr_ty) | |
| 31033 | try Type.optional(sema.arena, new_ptr_ty, mod) | |
| 30989 | 31034 | else |
| 30990 | 31035 | new_ptr_ty; |
| 30991 | 31036 | const set_ty = err_set_ty orelse return opt_ptr_ty; |
| ... | ... | @@ -30998,7 +31043,7 @@ fn resolvePeerTypes( |
| 30998 | 31043 | if (any_are_null) { |
| 30999 | 31044 | const opt_ty = switch (chosen_ty.zigTypeTag(mod)) { |
| 31000 | 31045 | .Null, .Optional => chosen_ty, |
| 31001 | else => try Type.optional(sema.arena, chosen_ty), | |
| 31046 | else => try Type.optional(sema.arena, chosen_ty, mod), | |
| 31002 | 31047 | }; |
| 31003 | 31048 | const set_ty = err_set_ty orelse return opt_ty; |
| 31004 | 31049 | return try Type.errorUnion(sema.arena, set_ty, opt_ty, mod); |
| ... | ... | @@ -31077,13 +31122,12 @@ pub fn resolveTypeLayout(sema: *Sema, ty: Type) CompileError!void { |
| 31077 | 31122 | .Struct => return sema.resolveStructLayout(ty), |
| 31078 | 31123 | .Union => return sema.resolveUnionLayout(ty), |
| 31079 | 31124 | .Array => { |
| 31080 | if (ty.arrayLenIncludingSentinel() == 0) return; | |
| 31081 | const elem_ty = ty.childType(); | |
| 31125 | if (ty.arrayLenIncludingSentinel(mod) == 0) return; | |
| 31126 | const elem_ty = ty.childType(mod); | |
| 31082 | 31127 | return sema.resolveTypeLayout(elem_ty); |
| 31083 | 31128 | }, |
| 31084 | 31129 | .Optional => { |
| 31085 | var buf: Type.Payload.ElemType = undefined; | |
| 31086 | const payload_ty = ty.optionalChild(&buf); | |
| 31130 | const payload_ty = ty.optionalChild(mod); | |
| 31087 | 31131 | // In case of querying the ABI alignment of this optional, we will ask |
| 31088 | 31132 | // for hasRuntimeBits() of the payload type, so we need "requires comptime" |
| 31089 | 31133 | // to be known already before this function returns. |
| ... | ... | @@ -31343,10 +31387,10 @@ fn checkIndexable(sema: *Sema, block: *Block, src: LazySrcLoc, ty: Type) !void { |
| 31343 | 31387 | fn checkMemOperand(sema: *Sema, block: *Block, src: LazySrcLoc, ty: Type) !void { |
| 31344 | 31388 | const mod = sema.mod; |
| 31345 | 31389 | if (ty.zigTypeTag(mod) == .Pointer) { |
| 31346 | switch (ty.ptrSize()) { | |
| 31390 | switch (ty.ptrSize(mod)) { | |
| 31347 | 31391 | .Slice, .Many, .C => return, |
| 31348 | 31392 | .One => { |
| 31349 | const elem_ty = ty.childType(); | |
| 31393 | const elem_ty = ty.childType(mod); | |
| 31350 | 31394 | if (elem_ty.zigTypeTag(mod) == .Array) return; |
| 31351 | 31395 | // TODO https://github.com/ziglang/zig/issues/15479 |
| 31352 | 31396 | // if (elem_ty.isTuple()) return; |
| ... | ... | @@ -31418,8 +31462,8 @@ pub fn resolveTypeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 31418 | 31462 | .int_type => false, |
| 31419 | 31463 | .ptr_type => @panic("TODO"), |
| 31420 | 31464 | .array_type => @panic("TODO"), |
| 31421 | .vector_type => @panic("TODO"), | |
| 31422 | .optional_type => @panic("TODO"), | |
| 31465 | .vector_type => |vector_type| return sema.resolveTypeRequiresComptime(vector_type.child.toType()), | |
| 31466 | .opt_type => @panic("TODO"), | |
| 31423 | 31467 | .error_union_type => @panic("TODO"), |
| 31424 | 31468 | .simple_type => |t| switch (t) { |
| 31425 | 31469 | .f16, |
| ... | ... | @@ -31478,12 +31522,6 @@ pub fn resolveTypeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 31478 | 31522 | }; |
| 31479 | 31523 | |
| 31480 | 31524 | return switch (ty.tag()) { |
| 31481 | .manyptr_u8, | |
| 31482 | .manyptr_const_u8, | |
| 31483 | .manyptr_const_u8_sentinel_0, | |
| 31484 | .const_slice_u8, | |
| 31485 | .const_slice_u8_sentinel_0, | |
| 31486 | .anyerror_void_error_union, | |
| 31487 | 31525 | .empty_struct_literal, |
| 31488 | 31526 | .empty_struct, |
| 31489 | 31527 | .error_set, |
| ... | ... | @@ -31491,34 +31529,20 @@ pub fn resolveTypeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 31491 | 31529 | .error_set_inferred, |
| 31492 | 31530 | .error_set_merged, |
| 31493 | 31531 | .@"opaque", |
| 31494 | .array_u8, | |
| 31495 | .array_u8_sentinel_0, | |
| 31496 | 31532 | .enum_simple, |
| 31497 | 31533 | => false, |
| 31498 | 31534 | |
| 31499 | .single_const_pointer_to_comptime_int, | |
| 31500 | .function, | |
| 31501 | => true, | |
| 31535 | .function => true, | |
| 31502 | 31536 | |
| 31503 | 31537 | .inferred_alloc_mut => unreachable, |
| 31504 | 31538 | .inferred_alloc_const => unreachable, |
| 31505 | 31539 | |
| 31506 | 31540 | .array, |
| 31507 | 31541 | .array_sentinel, |
| 31508 | .vector, | |
| 31509 | => return sema.resolveTypeRequiresComptime(ty.childType()), | |
| 31542 | => return sema.resolveTypeRequiresComptime(ty.childType(mod)), | |
| 31510 | 31543 | |
| 31511 | .pointer, | |
| 31512 | .single_const_pointer, | |
| 31513 | .single_mut_pointer, | |
| 31514 | .many_const_pointer, | |
| 31515 | .many_mut_pointer, | |
| 31516 | .c_const_pointer, | |
| 31517 | .c_mut_pointer, | |
| 31518 | .const_slice, | |
| 31519 | .mut_slice, | |
| 31520 | => { | |
| 31521 | const child_ty = ty.childType(); | |
| 31544 | .pointer => { | |
| 31545 | const child_ty = ty.childType(mod); | |
| 31522 | 31546 | if (child_ty.zigTypeTag(mod) == .Fn) { |
| 31523 | 31547 | return child_ty.fnInfo().is_generic; |
| 31524 | 31548 | } else { |
| ... | ... | @@ -31526,12 +31550,8 @@ pub fn resolveTypeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 31526 | 31550 | } |
| 31527 | 31551 | }, |
| 31528 | 31552 | |
| 31529 | .optional, | |
| 31530 | .optional_single_mut_pointer, | |
| 31531 | .optional_single_const_pointer, | |
| 31532 | => { | |
| 31533 | var buf: Type.Payload.ElemType = undefined; | |
| 31534 | return sema.resolveTypeRequiresComptime(ty.optionalChild(&buf)); | |
| 31553 | .optional => { | |
| 31554 | return sema.resolveTypeRequiresComptime(ty.optionalChild(mod)); | |
| 31535 | 31555 | }, |
| 31536 | 31556 | |
| 31537 | 31557 | .tuple, .anon_struct => { |
| ... | ... | @@ -31609,7 +31629,7 @@ pub fn resolveTypeFully(sema: *Sema, ty: Type) CompileError!void { |
| 31609 | 31629 | const mod = sema.mod; |
| 31610 | 31630 | switch (ty.zigTypeTag(mod)) { |
| 31611 | 31631 | .Pointer => { |
| 31612 | const child_ty = try sema.resolveTypeFields(ty.childType()); | |
| 31632 | const child_ty = try sema.resolveTypeFields(ty.childType(mod)); | |
| 31613 | 31633 | return sema.resolveTypeFully(child_ty); |
| 31614 | 31634 | }, |
| 31615 | 31635 | .Struct => switch (ty.tag()) { |
| ... | ... | @@ -31624,10 +31644,9 @@ pub fn resolveTypeFully(sema: *Sema, ty: Type) CompileError!void { |
| 31624 | 31644 | else => {}, |
| 31625 | 31645 | }, |
| 31626 | 31646 | .Union => return sema.resolveUnionFully(ty), |
| 31627 | .Array => return sema.resolveTypeFully(ty.childType()), | |
| 31647 | .Array => return sema.resolveTypeFully(ty.childType(mod)), | |
| 31628 | 31648 | .Optional => { |
| 31629 | var buf: Type.Payload.ElemType = undefined; | |
| 31630 | return sema.resolveTypeFully(ty.optionalChild(&buf)); | |
| 31649 | return sema.resolveTypeFully(ty.optionalChild(mod)); | |
| 31631 | 31650 | }, |
| 31632 | 31651 | .ErrorUnion => return sema.resolveTypeFully(ty.errorUnionPayload()), |
| 31633 | 31652 | .Fn => { |
| ... | ... | @@ -32897,10 +32916,14 @@ pub fn typeHasOnePossibleValue(sema: *Sema, ty: Type) CompileError!?Value { |
| 32897 | 32916 | return null; |
| 32898 | 32917 | } |
| 32899 | 32918 | }, |
| 32900 | .ptr_type => @panic("TODO"), | |
| 32919 | .ptr_type => return null, | |
| 32901 | 32920 | .array_type => @panic("TODO"), |
| 32902 | .vector_type => @panic("TODO"), | |
| 32903 | .optional_type => @panic("TODO"), | |
| 32921 | .vector_type => |vector_type| { | |
| 32922 | if (vector_type.len == 0) return Value.initTag(.empty_array); | |
| 32923 | if (try sema.typeHasOnePossibleValue(vector_type.child.toType())) |v| return v; | |
| 32924 | return null; | |
| 32925 | }, | |
| 32926 | .opt_type => @panic("TODO"), | |
| 32904 | 32927 | .error_union_type => @panic("TODO"), |
| 32905 | 32928 | .simple_type => |t| switch (t) { |
| 32906 | 32929 | .f16, |
| ... | ... | @@ -32963,34 +32986,15 @@ pub fn typeHasOnePossibleValue(sema: *Sema, ty: Type) CompileError!?Value { |
| 32963 | 32986 | .error_set_merged, |
| 32964 | 32987 | .error_union, |
| 32965 | 32988 | .function, |
| 32966 | .single_const_pointer_to_comptime_int, | |
| 32967 | 32989 | .array_sentinel, |
| 32968 | .array_u8_sentinel_0, | |
| 32969 | .const_slice_u8, | |
| 32970 | .const_slice_u8_sentinel_0, | |
| 32971 | .const_slice, | |
| 32972 | .mut_slice, | |
| 32973 | .optional_single_mut_pointer, | |
| 32974 | .optional_single_const_pointer, | |
| 32975 | .anyerror_void_error_union, | |
| 32976 | 32990 | .error_set_inferred, |
| 32977 | 32991 | .@"opaque", |
| 32978 | .manyptr_u8, | |
| 32979 | .manyptr_const_u8, | |
| 32980 | .manyptr_const_u8_sentinel_0, | |
| 32981 | 32992 | .anyframe_T, |
| 32982 | .many_const_pointer, | |
| 32983 | .many_mut_pointer, | |
| 32984 | .c_const_pointer, | |
| 32985 | .c_mut_pointer, | |
| 32986 | .single_const_pointer, | |
| 32987 | .single_mut_pointer, | |
| 32988 | 32993 | .pointer, |
| 32989 | 32994 | => return null, |
| 32990 | 32995 | |
| 32991 | 32996 | .optional => { |
| 32992 | var buf: Type.Payload.ElemType = undefined; | |
| 32993 | const child_ty = ty.optionalChild(&buf); | |
| 32997 | const child_ty = ty.optionalChild(mod); | |
| 32994 | 32998 | if (child_ty.isNoReturn()) { |
| 32995 | 32999 | return Value.null; |
| 32996 | 33000 | } else { |
| ... | ... | @@ -33111,10 +33115,10 @@ pub fn typeHasOnePossibleValue(sema: *Sema, ty: Type) CompileError!?Value { |
| 33111 | 33115 | |
| 33112 | 33116 | .empty_struct, .empty_struct_literal => return Value.initTag(.empty_struct_value), |
| 33113 | 33117 | |
| 33114 | .vector, .array, .array_u8 => { | |
| 33115 | if (ty.arrayLen() == 0) | |
| 33118 | .array => { | |
| 33119 | if (ty.arrayLen(mod) == 0) | |
| 33116 | 33120 | return Value.initTag(.empty_array); |
| 33117 | if ((try sema.typeHasOnePossibleValue(ty.elemType())) != null) { | |
| 33121 | if ((try sema.typeHasOnePossibleValue(ty.childType(mod))) != null) { | |
| 33118 | 33122 | return Value.initTag(.the_only_possible_value); |
| 33119 | 33123 | } |
| 33120 | 33124 | return null; |
| ... | ... | @@ -33147,20 +33151,13 @@ pub fn addType(sema: *Sema, ty: Type) !Air.Inst.Ref { |
| 33147 | 33151 | .data = .{ .interned = ty.ip_index }, |
| 33148 | 33152 | }); |
| 33149 | 33153 | return Air.indexToRef(@intCast(u32, sema.air_instructions.len - 1)); |
| 33154 | } else { | |
| 33155 | try sema.air_instructions.append(sema.gpa, .{ | |
| 33156 | .tag = .const_ty, | |
| 33157 | .data = .{ .ty = ty }, | |
| 33158 | }); | |
| 33159 | return Air.indexToRef(@intCast(u32, sema.air_instructions.len - 1)); | |
| 33150 | 33160 | } |
| 33151 | switch (ty.tag()) { | |
| 33152 | .manyptr_u8 => return .manyptr_u8_type, | |
| 33153 | .manyptr_const_u8 => return .manyptr_const_u8_type, | |
| 33154 | .single_const_pointer_to_comptime_int => return .single_const_pointer_to_comptime_int_type, | |
| 33155 | .const_slice_u8 => return .const_slice_u8_type, | |
| 33156 | .anyerror_void_error_union => return .anyerror_void_error_union_type, | |
| 33157 | else => {}, | |
| 33158 | } | |
| 33159 | try sema.air_instructions.append(sema.gpa, .{ | |
| 33160 | .tag = .const_ty, | |
| 33161 | .data = .{ .ty = ty }, | |
| 33162 | }); | |
| 33163 | return Air.indexToRef(@intCast(u32, sema.air_instructions.len - 1)); | |
| 33164 | 33161 | } |
| 33165 | 33162 | |
| 33166 | 33163 | fn addIntUnsigned(sema: *Sema, ty: Type, int: u64) CompileError!Air.Inst.Ref { |
| ... | ... | @@ -33173,6 +33170,15 @@ fn addConstUndef(sema: *Sema, ty: Type) CompileError!Air.Inst.Ref { |
| 33173 | 33170 | |
| 33174 | 33171 | pub fn addConstant(sema: *Sema, ty: Type, val: Value) SemaError!Air.Inst.Ref { |
| 33175 | 33172 | const gpa = sema.gpa; |
| 33173 | if (val.ip_index != .none) { | |
| 33174 | if (@enumToInt(val.ip_index) < Air.ref_start_index) | |
| 33175 | return @intToEnum(Air.Inst.Ref, @enumToInt(val.ip_index)); | |
| 33176 | try sema.air_instructions.append(gpa, .{ | |
| 33177 | .tag = .interned, | |
| 33178 | .data = .{ .interned = val.ip_index }, | |
| 33179 | }); | |
| 33180 | return Air.indexToRef(@intCast(u32, sema.air_instructions.len - 1)); | |
| 33181 | } | |
| 33176 | 33182 | const ty_inst = try sema.addType(ty); |
| 33177 | 33183 | try sema.air_values.append(gpa, val); |
| 33178 | 33184 | try sema.air_instructions.append(gpa, .{ |
| ... | ... | @@ -33331,7 +33337,8 @@ pub fn analyzeAddressSpace( |
| 33331 | 33337 | /// Asserts the value is a pointer and dereferences it. |
| 33332 | 33338 | /// Returns `null` if the pointer contents cannot be loaded at comptime. |
| 33333 | 33339 | fn pointerDeref(sema: *Sema, block: *Block, src: LazySrcLoc, ptr_val: Value, ptr_ty: Type) CompileError!?Value { |
| 33334 | const load_ty = ptr_ty.childType(); | |
| 33340 | const mod = sema.mod; | |
| 33341 | const load_ty = ptr_ty.childType(mod); | |
| 33335 | 33342 | const res = try sema.pointerDerefExtra(block, src, ptr_val, load_ty, true); |
| 33336 | 33343 | switch (res) { |
| 33337 | 33344 | .runtime_load => return null, |
| ... | ... | @@ -33422,11 +33429,7 @@ fn usizeCast(sema: *Sema, block: *Block, src: LazySrcLoc, int: u64) CompileError |
| 33422 | 33429 | /// This can return `error.AnalysisFail` because it sometimes requires resolving whether |
| 33423 | 33430 | /// a type has zero bits, which can cause a "foo depends on itself" compile error. |
| 33424 | 33431 | /// This logic must be kept in sync with `Type.isPtrLikeOptional`. |
| 33425 | fn typePtrOrOptionalPtrTy( | |
| 33426 | sema: *Sema, | |
| 33427 | ty: Type, | |
| 33428 | buf: *Type.Payload.ElemType, | |
| 33429 | ) !?Type { | |
| 33432 | fn typePtrOrOptionalPtrTy(sema: *Sema, ty: Type) !?Type { | |
| 33430 | 33433 | const mod = sema.mod; |
| 33431 | 33434 | |
| 33432 | 33435 | if (ty.ip_index != .none) switch (mod.intern_pool.indexToKey(ty.ip_index)) { |
| ... | ... | @@ -33435,14 +33438,14 @@ fn typePtrOrOptionalPtrTy( |
| 33435 | 33438 | .C => return ptr_type.elem_type.toType(), |
| 33436 | 33439 | .One, .Many => return ty, |
| 33437 | 33440 | }, |
| 33438 | .optional_type => |o| switch (mod.intern_pool.indexToKey(o.payload_type)) { | |
| 33441 | .opt_type => |opt_child| switch (mod.intern_pool.indexToKey(opt_child)) { | |
| 33439 | 33442 | .ptr_type => |ptr_type| switch (ptr_type.size) { |
| 33440 | 33443 | .Slice, .C => return null, |
| 33441 | 33444 | .Many, .One => { |
| 33442 | 33445 | if (ptr_type.is_allowzero) return null; |
| 33443 | 33446 | |
| 33444 | 33447 | // optionals of zero sized types behave like bools, not pointers |
| 33445 | const payload_ty = o.payload_type.toType(); | |
| 33448 | const payload_ty = opt_child.toType(); | |
| 33446 | 33449 | if ((try sema.typeHasOnePossibleValue(payload_ty)) != null) { |
| 33447 | 33450 | return null; |
| 33448 | 33451 | } |
| ... | ... | @@ -33456,25 +33459,9 @@ fn typePtrOrOptionalPtrTy( |
| 33456 | 33459 | }; |
| 33457 | 33460 | |
| 33458 | 33461 | switch (ty.tag()) { |
| 33459 | .optional_single_const_pointer, | |
| 33460 | .optional_single_mut_pointer, | |
| 33461 | .c_const_pointer, | |
| 33462 | .c_mut_pointer, | |
| 33463 | => return ty.optionalChild(buf), | |
| 33464 | ||
| 33465 | .single_const_pointer_to_comptime_int, | |
| 33466 | .single_const_pointer, | |
| 33467 | .single_mut_pointer, | |
| 33468 | .many_const_pointer, | |
| 33469 | .many_mut_pointer, | |
| 33470 | .manyptr_u8, | |
| 33471 | .manyptr_const_u8, | |
| 33472 | .manyptr_const_u8_sentinel_0, | |
| 33473 | => return ty, | |
| 33474 | ||
| 33475 | .pointer => switch (ty.ptrSize()) { | |
| 33462 | .pointer => switch (ty.ptrSize(mod)) { | |
| 33476 | 33463 | .Slice => return null, |
| 33477 | .C => return ty.optionalChild(buf), | |
| 33464 | .C => return ty.optionalChild(mod), | |
| 33478 | 33465 | else => return ty, |
| 33479 | 33466 | }, |
| 33480 | 33467 | |
| ... | ... | @@ -33482,10 +33469,10 @@ fn typePtrOrOptionalPtrTy( |
| 33482 | 33469 | .inferred_alloc_mut => unreachable, |
| 33483 | 33470 | |
| 33484 | 33471 | .optional => { |
| 33485 | const child_type = ty.optionalChild(buf); | |
| 33472 | const child_type = ty.optionalChild(mod); | |
| 33486 | 33473 | if (child_type.zigTypeTag(mod) != .Pointer) return null; |
| 33487 | 33474 | |
| 33488 | const info = child_type.ptrInfo().data; | |
| 33475 | const info = child_type.ptrInfo(mod); | |
| 33489 | 33476 | switch (info.size) { |
| 33490 | 33477 | .Slice, .C => return null, |
| 33491 | 33478 | .Many, .One => { |
| ... | ... | @@ -33518,8 +33505,8 @@ pub fn typeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 33518 | 33505 | .int_type => return false, |
| 33519 | 33506 | .ptr_type => @panic("TODO"), |
| 33520 | 33507 | .array_type => @panic("TODO"), |
| 33521 | .vector_type => @panic("TODO"), | |
| 33522 | .optional_type => @panic("TODO"), | |
| 33508 | .vector_type => |vector_type| return sema.typeRequiresComptime(vector_type.child.toType()), | |
| 33509 | .opt_type => @panic("TODO"), | |
| 33523 | 33510 | .error_union_type => @panic("TODO"), |
| 33524 | 33511 | .simple_type => |t| return switch (t) { |
| 33525 | 33512 | .f16, |
| ... | ... | @@ -33578,12 +33565,6 @@ pub fn typeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 33578 | 33565 | } |
| 33579 | 33566 | } |
| 33580 | 33567 | return switch (ty.tag()) { |
| 33581 | .manyptr_u8, | |
| 33582 | .manyptr_const_u8, | |
| 33583 | .manyptr_const_u8_sentinel_0, | |
| 33584 | .const_slice_u8, | |
| 33585 | .const_slice_u8_sentinel_0, | |
| 33586 | .anyerror_void_error_union, | |
| 33587 | 33568 | .empty_struct_literal, |
| 33588 | 33569 | .empty_struct, |
| 33589 | 33570 | .error_set, |
| ... | ... | @@ -33591,34 +33572,20 @@ pub fn typeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 33591 | 33572 | .error_set_inferred, |
| 33592 | 33573 | .error_set_merged, |
| 33593 | 33574 | .@"opaque", |
| 33594 | .array_u8, | |
| 33595 | .array_u8_sentinel_0, | |
| 33596 | 33575 | .enum_simple, |
| 33597 | 33576 | => false, |
| 33598 | 33577 | |
| 33599 | .single_const_pointer_to_comptime_int, | |
| 33600 | .function, | |
| 33601 | => true, | |
| 33578 | .function => true, | |
| 33602 | 33579 | |
| 33603 | 33580 | .inferred_alloc_mut => unreachable, |
| 33604 | 33581 | .inferred_alloc_const => unreachable, |
| 33605 | 33582 | |
| 33606 | 33583 | .array, |
| 33607 | 33584 | .array_sentinel, |
| 33608 | .vector, | |
| 33609 | => return sema.typeRequiresComptime(ty.childType()), | |
| 33585 | => return sema.typeRequiresComptime(ty.childType(mod)), | |
| 33610 | 33586 | |
| 33611 | .pointer, | |
| 33612 | .single_const_pointer, | |
| 33613 | .single_mut_pointer, | |
| 33614 | .many_const_pointer, | |
| 33615 | .many_mut_pointer, | |
| 33616 | .c_const_pointer, | |
| 33617 | .c_mut_pointer, | |
| 33618 | .const_slice, | |
| 33619 | .mut_slice, | |
| 33620 | => { | |
| 33621 | const child_ty = ty.childType(); | |
| 33587 | .pointer => { | |
| 33588 | const child_ty = ty.childType(mod); | |
| 33622 | 33589 | if (child_ty.zigTypeTag(mod) == .Fn) { |
| 33623 | 33590 | return child_ty.fnInfo().is_generic; |
| 33624 | 33591 | } else { |
| ... | ... | @@ -33626,12 +33593,8 @@ pub fn typeRequiresComptime(sema: *Sema, ty: Type) CompileError!bool { |
| 33626 | 33593 | } |
| 33627 | 33594 | }, |
| 33628 | 33595 | |
| 33629 | .optional, | |
| 33630 | .optional_single_mut_pointer, | |
| 33631 | .optional_single_const_pointer, | |
| 33632 | => { | |
| 33633 | var buf: Type.Payload.ElemType = undefined; | |
| 33634 | return sema.typeRequiresComptime(ty.optionalChild(&buf)); | |
| 33596 | .optional => { | |
| 33597 | return sema.typeRequiresComptime(ty.optionalChild(mod)); | |
| 33635 | 33598 | }, |
| 33636 | 33599 | |
| 33637 | 33600 | .tuple, .anon_struct => { |
| ... | ... | @@ -33814,7 +33777,7 @@ fn queueFullTypeResolution(sema: *Sema, ty: Type) !void { |
| 33814 | 33777 | fn intAdd(sema: *Sema, lhs: Value, rhs: Value, ty: Type) !Value { |
| 33815 | 33778 | const mod = sema.mod; |
| 33816 | 33779 | if (ty.zigTypeTag(mod) == .Vector) { |
| 33817 | const result_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 33780 | const result_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 33818 | 33781 | for (result_data, 0..) |*scalar, i| { |
| 33819 | 33782 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 33820 | 33783 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -33874,7 +33837,7 @@ fn intSub( |
| 33874 | 33837 | ) !Value { |
| 33875 | 33838 | const mod = sema.mod; |
| 33876 | 33839 | if (ty.zigTypeTag(mod) == .Vector) { |
| 33877 | const result_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 33840 | const result_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 33878 | 33841 | for (result_data, 0..) |*scalar, i| { |
| 33879 | 33842 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 33880 | 33843 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -33934,7 +33897,7 @@ fn floatAdd( |
| 33934 | 33897 | ) !Value { |
| 33935 | 33898 | const mod = sema.mod; |
| 33936 | 33899 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 33937 | const result_data = try sema.arena.alloc(Value, float_type.vectorLen()); | |
| 33900 | const result_data = try sema.arena.alloc(Value, float_type.vectorLen(mod)); | |
| 33938 | 33901 | for (result_data, 0..) |*scalar, i| { |
| 33939 | 33902 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 33940 | 33903 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -33992,7 +33955,7 @@ fn floatSub( |
| 33992 | 33955 | ) !Value { |
| 33993 | 33956 | const mod = sema.mod; |
| 33994 | 33957 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 33995 | const result_data = try sema.arena.alloc(Value, float_type.vectorLen()); | |
| 33958 | const result_data = try sema.arena.alloc(Value, float_type.vectorLen(mod)); | |
| 33996 | 33959 | for (result_data, 0..) |*scalar, i| { |
| 33997 | 33960 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 33998 | 33961 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -34050,8 +34013,8 @@ fn intSubWithOverflow( |
| 34050 | 34013 | ) !Value.OverflowArithmeticResult { |
| 34051 | 34014 | const mod = sema.mod; |
| 34052 | 34015 | if (ty.zigTypeTag(mod) == .Vector) { |
| 34053 | const overflowed_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 34054 | const result_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 34016 | const overflowed_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 34017 | const result_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 34055 | 34018 | for (result_data, 0..) |*scalar, i| { |
| 34056 | 34019 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 34057 | 34020 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -34105,8 +34068,8 @@ fn floatToInt( |
| 34105 | 34068 | ) CompileError!Value { |
| 34106 | 34069 | const mod = sema.mod; |
| 34107 | 34070 | if (float_ty.zigTypeTag(mod) == .Vector) { |
| 34108 | const elem_ty = float_ty.childType(); | |
| 34109 | const result_data = try sema.arena.alloc(Value, float_ty.vectorLen()); | |
| 34071 | const elem_ty = float_ty.childType(mod); | |
| 34072 | const result_data = try sema.arena.alloc(Value, float_ty.vectorLen(mod)); | |
| 34110 | 34073 | for (result_data, 0..) |*scalar, i| { |
| 34111 | 34074 | var buf: Value.ElemValueBuffer = undefined; |
| 34112 | 34075 | const elem_val = val.elemValueBuffer(sema.mod, i, &buf); |
| ... | ... | @@ -34383,8 +34346,8 @@ fn intAddWithOverflow( |
| 34383 | 34346 | ) !Value.OverflowArithmeticResult { |
| 34384 | 34347 | const mod = sema.mod; |
| 34385 | 34348 | if (ty.zigTypeTag(mod) == .Vector) { |
| 34386 | const overflowed_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 34387 | const result_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 34349 | const overflowed_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 34350 | const result_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 34388 | 34351 | for (result_data, 0..) |*scalar, i| { |
| 34389 | 34352 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 34390 | 34353 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -34442,7 +34405,7 @@ fn compareAll( |
| 34442 | 34405 | const mod = sema.mod; |
| 34443 | 34406 | if (ty.zigTypeTag(mod) == .Vector) { |
| 34444 | 34407 | var i: usize = 0; |
| 34445 | while (i < ty.vectorLen()) : (i += 1) { | |
| 34408 | while (i < ty.vectorLen(mod)) : (i += 1) { | |
| 34446 | 34409 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 34447 | 34410 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| 34448 | 34411 | const lhs_elem = lhs.elemValueBuffer(sema.mod, i, &lhs_buf); |
| ... | ... | @@ -34490,7 +34453,7 @@ fn compareVector( |
| 34490 | 34453 | ) !Value { |
| 34491 | 34454 | const mod = sema.mod; |
| 34492 | 34455 | assert(ty.zigTypeTag(mod) == .Vector); |
| 34493 | const result_data = try sema.arena.alloc(Value, ty.vectorLen()); | |
| 34456 | const result_data = try sema.arena.alloc(Value, ty.vectorLen(mod)); | |
| 34494 | 34457 | for (result_data, 0..) |*scalar, i| { |
| 34495 | 34458 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 34496 | 34459 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -34511,10 +34474,10 @@ fn compareVector( |
| 34511 | 34474 | /// This code is duplicated in `analyzePtrArithmetic`. |
| 34512 | 34475 | fn elemPtrType(sema: *Sema, ptr_ty: Type, offset: ?usize) !Type { |
| 34513 | 34476 | const mod = sema.mod; |
| 34514 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 34477 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 34515 | 34478 | const elem_ty = ptr_ty.elemType2(mod); |
| 34516 | 34479 | const allow_zero = ptr_info.@"allowzero" and (offset orelse 0) == 0; |
| 34517 | const parent_ty = ptr_ty.childType(); | |
| 34480 | const parent_ty = ptr_ty.childType(mod); | |
| 34518 | 34481 | |
| 34519 | 34482 | const VI = Type.Payload.Pointer.Data.VectorIndex; |
| 34520 | 34483 | |
| ... | ... | @@ -34522,14 +34485,14 @@ fn elemPtrType(sema: *Sema, ptr_ty: Type, offset: ?usize) !Type { |
| 34522 | 34485 | host_size: u16 = 0, |
| 34523 | 34486 | alignment: u32 = 0, |
| 34524 | 34487 | vector_index: VI = .none, |
| 34525 | } = if (parent_ty.tag() == .vector and ptr_info.size == .One) blk: { | |
| 34488 | } = if (parent_ty.isVector(mod) and ptr_info.size == .One) blk: { | |
| 34526 | 34489 | const elem_bits = elem_ty.bitSize(mod); |
| 34527 | 34490 | if (elem_bits == 0) break :blk .{}; |
| 34528 | 34491 | const is_packed = elem_bits < 8 or !std.math.isPowerOfTwo(elem_bits); |
| 34529 | 34492 | if (!is_packed) break :blk .{}; |
| 34530 | 34493 | |
| 34531 | 34494 | break :blk .{ |
| 34532 | .host_size = @intCast(u16, parent_ty.arrayLen()), | |
| 34495 | .host_size = @intCast(u16, parent_ty.arrayLen(mod)), | |
| 34533 | 34496 | .alignment = @intCast(u16, parent_ty.abiAlignment(mod)), |
| 34534 | 34497 | .vector_index = if (offset) |some| @intToEnum(VI, some) else .runtime, |
| 34535 | 34498 | }; |
src/TypedValue.zig+6-26| ... | ... | @@ -77,15 +77,6 @@ pub fn print( |
| 77 | 77 | return writer.writeAll("(variable)"); |
| 78 | 78 | |
| 79 | 79 | while (true) switch (val.tag()) { |
| 80 | .single_const_pointer_to_comptime_int_type => return writer.writeAll("*const comptime_int"), | |
| 81 | .const_slice_u8_type => return writer.writeAll("[]const u8"), | |
| 82 | .const_slice_u8_sentinel_0_type => return writer.writeAll("[:0]const u8"), | |
| 83 | .anyerror_void_error_union_type => return writer.writeAll("anyerror!void"), | |
| 84 | ||
| 85 | .manyptr_u8_type => return writer.writeAll("[*]u8"), | |
| 86 | .manyptr_const_u8_type => return writer.writeAll("[*]const u8"), | |
| 87 | .manyptr_const_u8_sentinel_0_type => return writer.writeAll("[*:0]const u8"), | |
| 88 | ||
| 89 | 80 | .empty_struct_value, .aggregate => { |
| 90 | 81 | if (level == 0) { |
| 91 | 82 | return writer.writeAll(".{ ... }"); |
| ... | ... | @@ -112,7 +103,7 @@ pub fn print( |
| 112 | 103 | return writer.writeAll("}"); |
| 113 | 104 | } else { |
| 114 | 105 | const elem_ty = ty.elemType2(mod); |
| 115 | const len = ty.arrayLen(); | |
| 106 | const len = ty.arrayLen(mod); | |
| 116 | 107 | |
| 117 | 108 | if (elem_ty.eql(Type.u8, mod)) str: { |
| 118 | 109 | const max_len = @intCast(usize, std.math.min(len, max_string_len)); |
| ... | ... | @@ -288,7 +279,7 @@ pub fn print( |
| 288 | 279 | .ty = ty.elemType2(mod), |
| 289 | 280 | .val = val.castTag(.repeated).?.data, |
| 290 | 281 | }; |
| 291 | const len = ty.arrayLen(); | |
| 282 | const len = ty.arrayLen(mod); | |
| 292 | 283 | const max_len = std.math.min(len, max_aggregate_items); |
| 293 | 284 | while (i < max_len) : (i += 1) { |
| 294 | 285 | if (i != 0) try writer.writeAll(", "); |
| ... | ... | @@ -306,7 +297,7 @@ pub fn print( |
| 306 | 297 | try writer.writeAll(".{ "); |
| 307 | 298 | try print(.{ |
| 308 | 299 | .ty = ty.elemType2(mod), |
| 309 | .val = ty.sentinel().?, | |
| 300 | .val = ty.sentinel(mod).?, | |
| 310 | 301 | }, writer, level - 1, mod); |
| 311 | 302 | return writer.writeAll(" }"); |
| 312 | 303 | }, |
| ... | ... | @@ -364,8 +355,7 @@ pub fn print( |
| 364 | 355 | }, |
| 365 | 356 | .opt_payload => { |
| 366 | 357 | val = val.castTag(.opt_payload).?.data; |
| 367 | var buf: Type.Payload.ElemType = undefined; | |
| 368 | ty = ty.optionalChild(&buf); | |
| 358 | ty = ty.optionalChild(mod); | |
| 369 | 359 | return print(.{ .ty = ty, .val = val }, writer, level, mod); |
| 370 | 360 | }, |
| 371 | 361 | .eu_payload_ptr => { |
| ... | ... | @@ -386,13 +376,8 @@ pub fn print( |
| 386 | 376 | |
| 387 | 377 | try writer.writeAll(", &(payload of "); |
| 388 | 378 | |
| 389 | var ptr_ty: Type.Payload.ElemType = .{ | |
| 390 | .base = .{ .tag = .single_mut_pointer }, | |
| 391 | .data = data.container_ty, | |
| 392 | }; | |
| 393 | ||
| 394 | 379 | try print(.{ |
| 395 | .ty = Type.initPayload(&ptr_ty.base), | |
| 380 | .ty = mod.singleMutPtrType(data.container_ty) catch @panic("OOM"), | |
| 396 | 381 | .val = data.container_ptr, |
| 397 | 382 | }, writer, level - 1, mod); |
| 398 | 383 | |
| ... | ... | @@ -415,13 +400,8 @@ pub fn print( |
| 415 | 400 | |
| 416 | 401 | try writer.writeAll(", &(payload of "); |
| 417 | 402 | |
| 418 | var ptr_ty: Type.Payload.ElemType = .{ | |
| 419 | .base = .{ .tag = .single_mut_pointer }, | |
| 420 | .data = data.container_ty, | |
| 421 | }; | |
| 422 | ||
| 423 | 403 | try print(.{ |
| 424 | .ty = Type.initPayload(&ptr_ty.base), | |
| 404 | .ty = mod.singleMutPtrType(data.container_ty) catch @panic("OOM"), | |
| 425 | 405 | .val = data.container_ptr, |
| 426 | 406 | }, writer, level - 1, mod); |
| 427 | 407 |
src/arch/aarch64/CodeGen.zig+32-48| ... | ... | @@ -1030,7 +1030,7 @@ fn allocMem( |
| 1030 | 1030 | /// Use a pointer instruction as the basis for allocating stack memory. |
| 1031 | 1031 | fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !u32 { |
| 1032 | 1032 | const mod = self.bin_file.options.module.?; |
| 1033 | const elem_ty = self.typeOfIndex(inst).elemType(); | |
| 1033 | const elem_ty = self.typeOfIndex(inst).childType(mod); | |
| 1034 | 1034 | |
| 1035 | 1035 | if (!elem_ty.hasRuntimeBits(mod)) { |
| 1036 | 1036 | // return the stack offset 0. Stack offset 0 will be where all |
| ... | ... | @@ -1140,17 +1140,14 @@ fn airAlloc(self: *Self, inst: Air.Inst.Index) !void { |
| 1140 | 1140 | } |
| 1141 | 1141 | |
| 1142 | 1142 | fn airRetPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 1143 | const mod = self.bin_file.options.module.?; | |
| 1143 | 1144 | const result: MCValue = switch (self.ret_mcv) { |
| 1144 | 1145 | .none, .register => .{ .ptr_stack_offset = try self.allocMemPtr(inst) }, |
| 1145 | 1146 | .stack_offset => blk: { |
| 1146 | 1147 | // self.ret_mcv is an address to where this function |
| 1147 | 1148 | // should store its result into |
| 1148 | 1149 | const ret_ty = self.fn_type.fnReturnType(); |
| 1149 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 1150 | .base = .{ .tag = .single_mut_pointer }, | |
| 1151 | .data = ret_ty, | |
| 1152 | }; | |
| 1153 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 1150 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 1154 | 1151 | |
| 1155 | 1152 | // addr_reg will contain the address of where to store the |
| 1156 | 1153 | // result into |
| ... | ... | @@ -2406,9 +2403,9 @@ fn ptrArithmetic( |
| 2406 | 2403 | assert(rhs_ty.eql(Type.usize, mod)); |
| 2407 | 2404 | |
| 2408 | 2405 | const ptr_ty = lhs_ty; |
| 2409 | const elem_ty = switch (ptr_ty.ptrSize()) { | |
| 2410 | .One => ptr_ty.childType().childType(), // ptr to array, so get array element type | |
| 2411 | else => ptr_ty.childType(), | |
| 2406 | const elem_ty = switch (ptr_ty.ptrSize(mod)) { | |
| 2407 | .One => ptr_ty.childType(mod).childType(mod), // ptr to array, so get array element type | |
| 2408 | else => ptr_ty.childType(mod), | |
| 2412 | 2409 | }; |
| 2413 | 2410 | const elem_size = elem_ty.abiSize(mod); |
| 2414 | 2411 | |
| ... | ... | @@ -3024,8 +3021,7 @@ fn airOptionalPayload(self: *Self, inst: Air.Inst.Index) !void { |
| 3024 | 3021 | |
| 3025 | 3022 | fn optionalPayload(self: *Self, inst: Air.Inst.Index, mcv: MCValue, optional_ty: Type) !MCValue { |
| 3026 | 3023 | const mod = self.bin_file.options.module.?; |
| 3027 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 3028 | const payload_ty = optional_ty.optionalChild(&opt_buf); | |
| 3024 | const payload_ty = optional_ty.optionalChild(mod); | |
| 3029 | 3025 | if (!payload_ty.hasRuntimeBits(mod)) return MCValue.none; |
| 3030 | 3026 | if (optional_ty.isPtrLikeOptional(mod)) { |
| 3031 | 3027 | // TODO should we reuse the operand here? |
| ... | ... | @@ -3459,7 +3455,7 @@ fn ptrElemVal( |
| 3459 | 3455 | maybe_inst: ?Air.Inst.Index, |
| 3460 | 3456 | ) !MCValue { |
| 3461 | 3457 | const mod = self.bin_file.options.module.?; |
| 3462 | const elem_ty = ptr_ty.childType(); | |
| 3458 | const elem_ty = ptr_ty.childType(mod); | |
| 3463 | 3459 | const elem_size = @intCast(u32, elem_ty.abiSize(mod)); |
| 3464 | 3460 | |
| 3465 | 3461 | // TODO optimize for elem_sizes of 1, 2, 4, 8 |
| ... | ... | @@ -3617,7 +3613,7 @@ fn reuseOperand( |
| 3617 | 3613 | |
| 3618 | 3614 | fn load(self: *Self, dst_mcv: MCValue, ptr: MCValue, ptr_ty: Type) InnerError!void { |
| 3619 | 3615 | const mod = self.bin_file.options.module.?; |
| 3620 | const elem_ty = ptr_ty.elemType(); | |
| 3616 | const elem_ty = ptr_ty.childType(mod); | |
| 3621 | 3617 | const elem_size = elem_ty.abiSize(mod); |
| 3622 | 3618 | |
| 3623 | 3619 | switch (ptr) { |
| ... | ... | @@ -3773,7 +3769,7 @@ fn genInlineMemset( |
| 3773 | 3769 | ) !void { |
| 3774 | 3770 | const dst_reg = switch (dst) { |
| 3775 | 3771 | .register => |r| r, |
| 3776 | else => try self.copyToTmpRegister(Type.initTag(.manyptr_u8), dst), | |
| 3772 | else => try self.copyToTmpRegister(Type.manyptr_u8, dst), | |
| 3777 | 3773 | }; |
| 3778 | 3774 | const dst_reg_lock = self.register_manager.lockReg(dst_reg); |
| 3779 | 3775 | defer if (dst_reg_lock) |lock| self.register_manager.unlockReg(lock); |
| ... | ... | @@ -4096,7 +4092,7 @@ fn structFieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, inde |
| 4096 | 4092 | const mod = self.bin_file.options.module.?; |
| 4097 | 4093 | const mcv = try self.resolveInst(operand); |
| 4098 | 4094 | const ptr_ty = self.typeOf(operand); |
| 4099 | const struct_ty = ptr_ty.childType(); | |
| 4095 | const struct_ty = ptr_ty.childType(mod); | |
| 4100 | 4096 | const struct_field_offset = @intCast(u32, struct_ty.structFieldOffset(index, mod)); |
| 4101 | 4097 | switch (mcv) { |
| 4102 | 4098 | .ptr_stack_offset => |off| { |
| ... | ... | @@ -4173,7 +4169,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4173 | 4169 | const extra = self.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; |
| 4174 | 4170 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4175 | 4171 | const field_ptr = try self.resolveInst(extra.field_ptr); |
| 4176 | const struct_ty = self.air.getRefType(ty_pl.ty).childType(); | |
| 4172 | const struct_ty = self.air.getRefType(ty_pl.ty).childType(mod); | |
| 4177 | 4173 | const struct_field_offset = @intCast(u32, struct_ty.structFieldOffset(extra.field_index, mod)); |
| 4178 | 4174 | switch (field_ptr) { |
| 4179 | 4175 | .ptr_stack_offset => |off| { |
| ... | ... | @@ -4254,7 +4250,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 4254 | 4250 | |
| 4255 | 4251 | const fn_ty = switch (ty.zigTypeTag(mod)) { |
| 4256 | 4252 | .Fn => ty, |
| 4257 | .Pointer => ty.childType(), | |
| 4253 | .Pointer => ty.childType(mod), | |
| 4258 | 4254 | else => unreachable, |
| 4259 | 4255 | }; |
| 4260 | 4256 | |
| ... | ... | @@ -4280,11 +4276,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 4280 | 4276 | |
| 4281 | 4277 | const ret_ptr_reg = self.registerAlias(.x0, Type.usize); |
| 4282 | 4278 | |
| 4283 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 4284 | .base = .{ .tag = .single_mut_pointer }, | |
| 4285 | .data = ret_ty, | |
| 4286 | }; | |
| 4287 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 4279 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 4288 | 4280 | try self.register_manager.getReg(ret_ptr_reg, null); |
| 4289 | 4281 | try self.genSetReg(ptr_ty, ret_ptr_reg, .{ .ptr_stack_offset = stack_offset }); |
| 4290 | 4282 | |
| ... | ... | @@ -4453,11 +4445,7 @@ fn airRet(self: *Self, inst: Air.Inst.Index) !void { |
| 4453 | 4445 | // |
| 4454 | 4446 | // self.ret_mcv is an address to where this function |
| 4455 | 4447 | // should store its result into |
| 4456 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 4457 | .base = .{ .tag = .single_mut_pointer }, | |
| 4458 | .data = ret_ty, | |
| 4459 | }; | |
| 4460 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 4448 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 4461 | 4449 | try self.store(self.ret_mcv, operand, ptr_ty, ret_ty); |
| 4462 | 4450 | }, |
| 4463 | 4451 | else => unreachable, |
| ... | ... | @@ -4533,8 +4521,7 @@ fn cmp( |
| 4533 | 4521 | const mod = self.bin_file.options.module.?; |
| 4534 | 4522 | const int_ty = switch (lhs_ty.zigTypeTag(mod)) { |
| 4535 | 4523 | .Optional => blk: { |
| 4536 | var opt_buffer: Type.Payload.ElemType = undefined; | |
| 4537 | const payload_ty = lhs_ty.optionalChild(&opt_buffer); | |
| 4524 | const payload_ty = lhs_ty.optionalChild(mod); | |
| 4538 | 4525 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 4539 | 4526 | break :blk Type.u1; |
| 4540 | 4527 | } else if (lhs_ty.isPtrLikeOptional(mod)) { |
| ... | ... | @@ -4850,8 +4837,7 @@ fn airCondBr(self: *Self, inst: Air.Inst.Index) !void { |
| 4850 | 4837 | fn isNull(self: *Self, operand_bind: ReadArg.Bind, operand_ty: Type) !MCValue { |
| 4851 | 4838 | const mod = self.bin_file.options.module.?; |
| 4852 | 4839 | const sentinel: struct { ty: Type, bind: ReadArg.Bind } = if (!operand_ty.isPtrLikeOptional(mod)) blk: { |
| 4853 | var buf: Type.Payload.ElemType = undefined; | |
| 4854 | const payload_ty = operand_ty.optionalChild(&buf); | |
| 4840 | const payload_ty = operand_ty.optionalChild(mod); | |
| 4855 | 4841 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) |
| 4856 | 4842 | break :blk .{ .ty = operand_ty, .bind = operand_bind }; |
| 4857 | 4843 | |
| ... | ... | @@ -4947,11 +4933,12 @@ fn airIsNull(self: *Self, inst: Air.Inst.Index) !void { |
| 4947 | 4933 | } |
| 4948 | 4934 | |
| 4949 | 4935 | fn airIsNullPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4936 | const mod = self.bin_file.options.module.?; | |
| 4950 | 4937 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 4951 | 4938 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4952 | 4939 | const operand_ptr = try self.resolveInst(un_op); |
| 4953 | 4940 | const ptr_ty = self.typeOf(un_op); |
| 4954 | const elem_ty = ptr_ty.elemType(); | |
| 4941 | const elem_ty = ptr_ty.childType(mod); | |
| 4955 | 4942 | |
| 4956 | 4943 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 4957 | 4944 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -4973,11 +4960,12 @@ fn airIsNonNull(self: *Self, inst: Air.Inst.Index) !void { |
| 4973 | 4960 | } |
| 4974 | 4961 | |
| 4975 | 4962 | fn airIsNonNullPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4963 | const mod = self.bin_file.options.module.?; | |
| 4976 | 4964 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 4977 | 4965 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4978 | 4966 | const operand_ptr = try self.resolveInst(un_op); |
| 4979 | 4967 | const ptr_ty = self.typeOf(un_op); |
| 4980 | const elem_ty = ptr_ty.elemType(); | |
| 4968 | const elem_ty = ptr_ty.childType(mod); | |
| 4981 | 4969 | |
| 4982 | 4970 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 4983 | 4971 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -4999,11 +4987,12 @@ fn airIsErr(self: *Self, inst: Air.Inst.Index) !void { |
| 4999 | 4987 | } |
| 5000 | 4988 | |
| 5001 | 4989 | fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4990 | const mod = self.bin_file.options.module.?; | |
| 5002 | 4991 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 5003 | 4992 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 5004 | 4993 | const operand_ptr = try self.resolveInst(un_op); |
| 5005 | 4994 | const ptr_ty = self.typeOf(un_op); |
| 5006 | const elem_ty = ptr_ty.elemType(); | |
| 4995 | const elem_ty = ptr_ty.childType(mod); | |
| 5007 | 4996 | |
| 5008 | 4997 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 5009 | 4998 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -5025,11 +5014,12 @@ fn airIsNonErr(self: *Self, inst: Air.Inst.Index) !void { |
| 5025 | 5014 | } |
| 5026 | 5015 | |
| 5027 | 5016 | fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 5017 | const mod = self.bin_file.options.module.?; | |
| 5028 | 5018 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 5029 | 5019 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 5030 | 5020 | const operand_ptr = try self.resolveInst(un_op); |
| 5031 | 5021 | const ptr_ty = self.typeOf(un_op); |
| 5032 | const elem_ty = ptr_ty.elemType(); | |
| 5022 | const elem_ty = ptr_ty.childType(mod); | |
| 5033 | 5023 | |
| 5034 | 5024 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 5035 | 5025 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -5511,11 +5501,7 @@ fn genSetStack(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) InnerErro |
| 5511 | 5501 | const reg = try self.copyToTmpRegister(ty, mcv); |
| 5512 | 5502 | return self.genSetStack(ty, stack_offset, MCValue{ .register = reg }); |
| 5513 | 5503 | } else { |
| 5514 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 5515 | .base = .{ .tag = .single_mut_pointer }, | |
| 5516 | .data = ty, | |
| 5517 | }; | |
| 5518 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 5504 | const ptr_ty = try mod.singleMutPtrType(ty); | |
| 5519 | 5505 | |
| 5520 | 5506 | // TODO call extern memcpy |
| 5521 | 5507 | const regs = try self.register_manager.allocRegs(5, .{ null, null, null, null, null }, gp); |
| ... | ... | @@ -5833,11 +5819,7 @@ fn genSetStackArgument(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) I |
| 5833 | 5819 | const reg = try self.copyToTmpRegister(ty, mcv); |
| 5834 | 5820 | return self.genSetStackArgument(ty, stack_offset, MCValue{ .register = reg }); |
| 5835 | 5821 | } else { |
| 5836 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 5837 | .base = .{ .tag = .single_mut_pointer }, | |
| 5838 | .data = ty, | |
| 5839 | }; | |
| 5840 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 5822 | const ptr_ty = try mod.singleMutPtrType(ty); | |
| 5841 | 5823 | |
| 5842 | 5824 | // TODO call extern memcpy |
| 5843 | 5825 | const regs = try self.register_manager.allocRegs(5, .{ null, null, null, null, null }, gp); |
| ... | ... | @@ -5957,12 +5939,13 @@ fn airBitCast(self: *Self, inst: Air.Inst.Index) !void { |
| 5957 | 5939 | } |
| 5958 | 5940 | |
| 5959 | 5941 | fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 5942 | const mod = self.bin_file.options.module.?; | |
| 5960 | 5943 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 5961 | 5944 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 5962 | 5945 | const ptr_ty = self.typeOf(ty_op.operand); |
| 5963 | 5946 | const ptr = try self.resolveInst(ty_op.operand); |
| 5964 | const array_ty = ptr_ty.childType(); | |
| 5965 | const array_len = @intCast(u32, array_ty.arrayLen()); | |
| 5947 | const array_ty = ptr_ty.childType(mod); | |
| 5948 | const array_len = @intCast(u32, array_ty.arrayLen(mod)); | |
| 5966 | 5949 | |
| 5967 | 5950 | const ptr_bits = self.target.ptrBitWidth(); |
| 5968 | 5951 | const ptr_bytes = @divExact(ptr_bits, 8); |
| ... | ... | @@ -6079,8 +6062,9 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { |
| 6079 | 6062 | } |
| 6080 | 6063 | |
| 6081 | 6064 | fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 6065 | const mod = self.bin_file.options.module.?; | |
| 6082 | 6066 | const vector_ty = self.typeOfIndex(inst); |
| 6083 | const len = vector_ty.vectorLen(); | |
| 6067 | const len = vector_ty.vectorLen(mod); | |
| 6084 | 6068 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 6085 | 6069 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 6086 | 6070 | const result: MCValue = res: { |
src/arch/arm/CodeGen.zig+33-50| ... | ... | @@ -1010,7 +1010,7 @@ fn allocMem( |
| 1010 | 1010 | /// Use a pointer instruction as the basis for allocating stack memory. |
| 1011 | 1011 | fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !u32 { |
| 1012 | 1012 | const mod = self.bin_file.options.module.?; |
| 1013 | const elem_ty = self.typeOfIndex(inst).elemType(); | |
| 1013 | const elem_ty = self.typeOfIndex(inst).childType(mod); | |
| 1014 | 1014 | |
| 1015 | 1015 | if (!elem_ty.hasRuntimeBits(mod)) { |
| 1016 | 1016 | // As this stack item will never be dereferenced at runtime, |
| ... | ... | @@ -1117,17 +1117,14 @@ fn airAlloc(self: *Self, inst: Air.Inst.Index) !void { |
| 1117 | 1117 | } |
| 1118 | 1118 | |
| 1119 | 1119 | fn airRetPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 1120 | const mod = self.bin_file.options.module.?; | |
| 1120 | 1121 | const result: MCValue = switch (self.ret_mcv) { |
| 1121 | 1122 | .none, .register => .{ .ptr_stack_offset = try self.allocMemPtr(inst) }, |
| 1122 | 1123 | .stack_offset => blk: { |
| 1123 | 1124 | // self.ret_mcv is an address to where this function |
| 1124 | 1125 | // should store its result into |
| 1125 | 1126 | const ret_ty = self.fn_type.fnReturnType(); |
| 1126 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 1127 | .base = .{ .tag = .single_mut_pointer }, | |
| 1128 | .data = ret_ty, | |
| 1129 | }; | |
| 1130 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 1127 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 1131 | 1128 | |
| 1132 | 1129 | // addr_reg will contain the address of where to store the |
| 1133 | 1130 | // result into |
| ... | ... | @@ -2372,8 +2369,8 @@ fn ptrElemVal( |
| 2372 | 2369 | ptr_ty: Type, |
| 2373 | 2370 | maybe_inst: ?Air.Inst.Index, |
| 2374 | 2371 | ) !MCValue { |
| 2375 | const elem_ty = ptr_ty.childType(); | |
| 2376 | 2372 | const mod = self.bin_file.options.module.?; |
| 2373 | const elem_ty = ptr_ty.childType(mod); | |
| 2377 | 2374 | const elem_size = @intCast(u32, elem_ty.abiSize(mod)); |
| 2378 | 2375 | |
| 2379 | 2376 | switch (elem_size) { |
| ... | ... | @@ -2474,7 +2471,8 @@ fn arrayElemVal( |
| 2474 | 2471 | array_ty: Type, |
| 2475 | 2472 | maybe_inst: ?Air.Inst.Index, |
| 2476 | 2473 | ) InnerError!MCValue { |
| 2477 | const elem_ty = array_ty.childType(); | |
| 2474 | const mod = self.bin_file.options.module.?; | |
| 2475 | const elem_ty = array_ty.childType(mod); | |
| 2478 | 2476 | |
| 2479 | 2477 | const mcv = try array_bind.resolveToMcv(self); |
| 2480 | 2478 | switch (mcv) { |
| ... | ... | @@ -2508,11 +2506,7 @@ fn arrayElemVal( |
| 2508 | 2506 | |
| 2509 | 2507 | const base_bind: ReadArg.Bind = .{ .mcv = ptr_to_mcv }; |
| 2510 | 2508 | |
| 2511 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 2512 | .base = .{ .tag = .single_mut_pointer }, | |
| 2513 | .data = elem_ty, | |
| 2514 | }; | |
| 2515 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 2509 | const ptr_ty = try mod.singleMutPtrType(elem_ty); | |
| 2516 | 2510 | |
| 2517 | 2511 | return try self.ptrElemVal(base_bind, index_bind, ptr_ty, maybe_inst); |
| 2518 | 2512 | }, |
| ... | ... | @@ -2659,8 +2653,8 @@ fn reuseOperand( |
| 2659 | 2653 | } |
| 2660 | 2654 | |
| 2661 | 2655 | fn load(self: *Self, dst_mcv: MCValue, ptr: MCValue, ptr_ty: Type) InnerError!void { |
| 2662 | const elem_ty = ptr_ty.elemType(); | |
| 2663 | 2656 | const mod = self.bin_file.options.module.?; |
| 2657 | const elem_ty = ptr_ty.childType(mod); | |
| 2664 | 2658 | const elem_size = @intCast(u32, elem_ty.abiSize(mod)); |
| 2665 | 2659 | |
| 2666 | 2660 | switch (ptr) { |
| ... | ... | @@ -2888,7 +2882,7 @@ fn structFieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, inde |
| 2888 | 2882 | const mod = self.bin_file.options.module.?; |
| 2889 | 2883 | const mcv = try self.resolveInst(operand); |
| 2890 | 2884 | const ptr_ty = self.typeOf(operand); |
| 2891 | const struct_ty = ptr_ty.childType(); | |
| 2885 | const struct_ty = ptr_ty.childType(mod); | |
| 2892 | 2886 | const struct_field_offset = @intCast(u32, struct_ty.structFieldOffset(index, mod)); |
| 2893 | 2887 | switch (mcv) { |
| 2894 | 2888 | .ptr_stack_offset => |off| { |
| ... | ... | @@ -3004,7 +2998,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 3004 | 2998 | const extra = self.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; |
| 3005 | 2999 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 3006 | 3000 | const field_ptr = try self.resolveInst(extra.field_ptr); |
| 3007 | const struct_ty = self.air.getRefType(ty_pl.ty).childType(); | |
| 3001 | const struct_ty = self.air.getRefType(ty_pl.ty).childType(mod); | |
| 3008 | 3002 | |
| 3009 | 3003 | if (struct_ty.zigTypeTag(mod) == .Union) { |
| 3010 | 3004 | return self.fail("TODO implement @fieldParentPtr codegen for unions", .{}); |
| ... | ... | @@ -3898,9 +3892,9 @@ fn ptrArithmetic( |
| 3898 | 3892 | assert(rhs_ty.eql(Type.usize, mod)); |
| 3899 | 3893 | |
| 3900 | 3894 | const ptr_ty = lhs_ty; |
| 3901 | const elem_ty = switch (ptr_ty.ptrSize()) { | |
| 3902 | .One => ptr_ty.childType().childType(), // ptr to array, so get array element type | |
| 3903 | else => ptr_ty.childType(), | |
| 3895 | const elem_ty = switch (ptr_ty.ptrSize(mod)) { | |
| 3896 | .One => ptr_ty.childType(mod).childType(mod), // ptr to array, so get array element type | |
| 3897 | else => ptr_ty.childType(mod), | |
| 3904 | 3898 | }; |
| 3905 | 3899 | const elem_size = @intCast(u32, elem_ty.abiSize(mod)); |
| 3906 | 3900 | |
| ... | ... | @@ -4079,7 +4073,7 @@ fn genInlineMemset( |
| 4079 | 4073 | ) !void { |
| 4080 | 4074 | const dst_reg = switch (dst) { |
| 4081 | 4075 | .register => |r| r, |
| 4082 | else => try self.copyToTmpRegister(Type.initTag(.manyptr_u8), dst), | |
| 4076 | else => try self.copyToTmpRegister(Type.manyptr_u8, dst), | |
| 4083 | 4077 | }; |
| 4084 | 4078 | const dst_reg_lock = self.register_manager.lockReg(dst_reg); |
| 4085 | 4079 | defer if (dst_reg_lock) |lock| self.register_manager.unlockReg(lock); |
| ... | ... | @@ -4229,7 +4223,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 4229 | 4223 | |
| 4230 | 4224 | const fn_ty = switch (ty.zigTypeTag(mod)) { |
| 4231 | 4225 | .Fn => ty, |
| 4232 | .Pointer => ty.childType(), | |
| 4226 | .Pointer => ty.childType(mod), | |
| 4233 | 4227 | else => unreachable, |
| 4234 | 4228 | }; |
| 4235 | 4229 | |
| ... | ... | @@ -4259,11 +4253,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 4259 | 4253 | const ret_abi_align = @intCast(u32, ret_ty.abiAlignment(mod)); |
| 4260 | 4254 | const stack_offset = try self.allocMem(ret_abi_size, ret_abi_align, inst); |
| 4261 | 4255 | |
| 4262 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 4263 | .base = .{ .tag = .single_mut_pointer }, | |
| 4264 | .data = ret_ty, | |
| 4265 | }; | |
| 4266 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 4256 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 4267 | 4257 | try self.register_manager.getReg(.r0, null); |
| 4268 | 4258 | try self.genSetReg(ptr_ty, .r0, .{ .ptr_stack_offset = stack_offset }); |
| 4269 | 4259 | |
| ... | ... | @@ -4401,11 +4391,7 @@ fn airRet(self: *Self, inst: Air.Inst.Index) !void { |
| 4401 | 4391 | // |
| 4402 | 4392 | // self.ret_mcv is an address to where this function |
| 4403 | 4393 | // should store its result into |
| 4404 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 4405 | .base = .{ .tag = .single_mut_pointer }, | |
| 4406 | .data = ret_ty, | |
| 4407 | }; | |
| 4408 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 4394 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 4409 | 4395 | try self.store(self.ret_mcv, operand, ptr_ty, ret_ty); |
| 4410 | 4396 | }, |
| 4411 | 4397 | else => unreachable, // invalid return result |
| ... | ... | @@ -4482,8 +4468,7 @@ fn cmp( |
| 4482 | 4468 | const mod = self.bin_file.options.module.?; |
| 4483 | 4469 | const int_ty = switch (lhs_ty.zigTypeTag(mod)) { |
| 4484 | 4470 | .Optional => blk: { |
| 4485 | var opt_buffer: Type.Payload.ElemType = undefined; | |
| 4486 | const payload_ty = lhs_ty.optionalChild(&opt_buffer); | |
| 4471 | const payload_ty = lhs_ty.optionalChild(mod); | |
| 4487 | 4472 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 4488 | 4473 | break :blk Type.u1; |
| 4489 | 4474 | } else if (lhs_ty.isPtrLikeOptional(mod)) { |
| ... | ... | @@ -4837,11 +4822,12 @@ fn airIsNull(self: *Self, inst: Air.Inst.Index) !void { |
| 4837 | 4822 | } |
| 4838 | 4823 | |
| 4839 | 4824 | fn airIsNullPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4825 | const mod = self.bin_file.options.module.?; | |
| 4840 | 4826 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 4841 | 4827 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4842 | 4828 | const operand_ptr = try self.resolveInst(un_op); |
| 4843 | 4829 | const ptr_ty = self.typeOf(un_op); |
| 4844 | const elem_ty = ptr_ty.elemType(); | |
| 4830 | const elem_ty = ptr_ty.childType(mod); | |
| 4845 | 4831 | |
| 4846 | 4832 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 4847 | 4833 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -4863,11 +4849,12 @@ fn airIsNonNull(self: *Self, inst: Air.Inst.Index) !void { |
| 4863 | 4849 | } |
| 4864 | 4850 | |
| 4865 | 4851 | fn airIsNonNullPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4852 | const mod = self.bin_file.options.module.?; | |
| 4866 | 4853 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 4867 | 4854 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4868 | 4855 | const operand_ptr = try self.resolveInst(un_op); |
| 4869 | 4856 | const ptr_ty = self.typeOf(un_op); |
| 4870 | const elem_ty = ptr_ty.elemType(); | |
| 4857 | const elem_ty = ptr_ty.childType(mod); | |
| 4871 | 4858 | |
| 4872 | 4859 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 4873 | 4860 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -4924,11 +4911,12 @@ fn airIsErr(self: *Self, inst: Air.Inst.Index) !void { |
| 4924 | 4911 | } |
| 4925 | 4912 | |
| 4926 | 4913 | fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4914 | const mod = self.bin_file.options.module.?; | |
| 4927 | 4915 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 4928 | 4916 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4929 | 4917 | const operand_ptr = try self.resolveInst(un_op); |
| 4930 | 4918 | const ptr_ty = self.typeOf(un_op); |
| 4931 | const elem_ty = ptr_ty.elemType(); | |
| 4919 | const elem_ty = ptr_ty.childType(mod); | |
| 4932 | 4920 | |
| 4933 | 4921 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 4934 | 4922 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -4950,11 +4938,12 @@ fn airIsNonErr(self: *Self, inst: Air.Inst.Index) !void { |
| 4950 | 4938 | } |
| 4951 | 4939 | |
| 4952 | 4940 | fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 4941 | const mod = self.bin_file.options.module.?; | |
| 4953 | 4942 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 4954 | 4943 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 4955 | 4944 | const operand_ptr = try self.resolveInst(un_op); |
| 4956 | 4945 | const ptr_ty = self.typeOf(un_op); |
| 4957 | const elem_ty = ptr_ty.elemType(); | |
| 4946 | const elem_ty = ptr_ty.childType(mod); | |
| 4958 | 4947 | |
| 4959 | 4948 | const operand = try self.allocRegOrMem(elem_ty, true, null); |
| 4960 | 4949 | try self.load(operand, operand_ptr, ptr_ty); |
| ... | ... | @@ -5455,11 +5444,7 @@ fn genSetStack(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) InnerErro |
| 5455 | 5444 | const reg = try self.copyToTmpRegister(ty, mcv); |
| 5456 | 5445 | return self.genSetStack(ty, stack_offset, MCValue{ .register = reg }); |
| 5457 | 5446 | } else { |
| 5458 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 5459 | .base = .{ .tag = .single_mut_pointer }, | |
| 5460 | .data = ty, | |
| 5461 | }; | |
| 5462 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 5447 | const ptr_ty = try mod.singleMutPtrType(ty); | |
| 5463 | 5448 | |
| 5464 | 5449 | // TODO call extern memcpy |
| 5465 | 5450 | const regs = try self.register_manager.allocRegs(5, .{ null, null, null, null, null }, gp); |
| ... | ... | @@ -5816,11 +5801,7 @@ fn genSetStackArgument(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) I |
| 5816 | 5801 | const reg = try self.copyToTmpRegister(ty, mcv); |
| 5817 | 5802 | return self.genSetStackArgument(ty, stack_offset, MCValue{ .register = reg }); |
| 5818 | 5803 | } else { |
| 5819 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 5820 | .base = .{ .tag = .single_mut_pointer }, | |
| 5821 | .data = ty, | |
| 5822 | }; | |
| 5823 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 5804 | const ptr_ty = try mod.singleMutPtrType(ty); | |
| 5824 | 5805 | |
| 5825 | 5806 | // TODO call extern memcpy |
| 5826 | 5807 | const regs = try self.register_manager.allocRegs(5, .{ null, null, null, null, null }, gp); |
| ... | ... | @@ -5908,12 +5889,13 @@ fn airBitCast(self: *Self, inst: Air.Inst.Index) !void { |
| 5908 | 5889 | } |
| 5909 | 5890 | |
| 5910 | 5891 | fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 5892 | const mod = self.bin_file.options.module.?; | |
| 5911 | 5893 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 5912 | 5894 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 5913 | 5895 | const ptr_ty = self.typeOf(ty_op.operand); |
| 5914 | 5896 | const ptr = try self.resolveInst(ty_op.operand); |
| 5915 | const array_ty = ptr_ty.childType(); | |
| 5916 | const array_len = @intCast(u32, array_ty.arrayLen()); | |
| 5897 | const array_ty = ptr_ty.childType(mod); | |
| 5898 | const array_len = @intCast(u32, array_ty.arrayLen(mod)); | |
| 5917 | 5899 | |
| 5918 | 5900 | const stack_offset = try self.allocMem(8, 8, inst); |
| 5919 | 5901 | try self.genSetStack(ptr_ty, stack_offset, ptr); |
| ... | ... | @@ -6026,8 +6008,9 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { |
| 6026 | 6008 | } |
| 6027 | 6009 | |
| 6028 | 6010 | fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 6011 | const mod = self.bin_file.options.module.?; | |
| 6029 | 6012 | const vector_ty = self.typeOfIndex(inst); |
| 6030 | const len = vector_ty.vectorLen(); | |
| 6013 | const len = vector_ty.vectorLen(mod); | |
| 6031 | 6014 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 6032 | 6015 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 6033 | 6016 | const result: MCValue = res: { |
src/arch/riscv64/CodeGen.zig+8-6| ... | ... | @@ -807,7 +807,7 @@ fn allocMem(self: *Self, inst: Air.Inst.Index, abi_size: u32, abi_align: u32) !u |
| 807 | 807 | /// Use a pointer instruction as the basis for allocating stack memory. |
| 808 | 808 | fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !u32 { |
| 809 | 809 | const mod = self.bin_file.options.module.?; |
| 810 | const elem_ty = self.typeOfIndex(inst).elemType(); | |
| 810 | const elem_ty = self.typeOfIndex(inst).childType(mod); | |
| 811 | 811 | const abi_size = math.cast(u32, elem_ty.abiSize(mod)) orelse { |
| 812 | 812 | return self.fail("type '{}' too big to fit into stack frame", .{elem_ty.fmt(mod)}); |
| 813 | 813 | }; |
| ... | ... | @@ -1099,9 +1099,9 @@ fn binOp( |
| 1099 | 1099 | switch (lhs_ty.zigTypeTag(mod)) { |
| 1100 | 1100 | .Pointer => { |
| 1101 | 1101 | const ptr_ty = lhs_ty; |
| 1102 | const elem_ty = switch (ptr_ty.ptrSize()) { | |
| 1103 | .One => ptr_ty.childType().childType(), // ptr to array, so get array element type | |
| 1104 | else => ptr_ty.childType(), | |
| 1102 | const elem_ty = switch (ptr_ty.ptrSize(mod)) { | |
| 1103 | .One => ptr_ty.childType(mod).childType(mod), // ptr to array, so get array element type | |
| 1104 | else => ptr_ty.childType(mod), | |
| 1105 | 1105 | }; |
| 1106 | 1106 | const elem_size = elem_ty.abiSize(mod); |
| 1107 | 1107 | |
| ... | ... | @@ -1502,7 +1502,8 @@ fn reuseOperand(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, op_ind |
| 1502 | 1502 | } |
| 1503 | 1503 | |
| 1504 | 1504 | fn load(self: *Self, dst_mcv: MCValue, ptr: MCValue, ptr_ty: Type) InnerError!void { |
| 1505 | const elem_ty = ptr_ty.elemType(); | |
| 1505 | const mod = self.bin_file.options.module.?; | |
| 1506 | const elem_ty = ptr_ty.childType(mod); | |
| 1506 | 1507 | switch (ptr) { |
| 1507 | 1508 | .none => unreachable, |
| 1508 | 1509 | .undef => unreachable, |
| ... | ... | @@ -2496,8 +2497,9 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { |
| 2496 | 2497 | } |
| 2497 | 2498 | |
| 2498 | 2499 | fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 2500 | const mod = self.bin_file.options.module.?; | |
| 2499 | 2501 | const vector_ty = self.typeOfIndex(inst); |
| 2500 | const len = vector_ty.vectorLen(); | |
| 2502 | const len = vector_ty.vectorLen(mod); | |
| 2501 | 2503 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 2502 | 2504 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 2503 | 2505 | const result: MCValue = res: { |
src/arch/sparc64/CodeGen.zig+17-20| ... | ... | @@ -838,8 +838,9 @@ fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index) !void { |
| 838 | 838 | } |
| 839 | 839 | |
| 840 | 840 | fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 841 | const mod = self.bin_file.options.module.?; | |
| 841 | 842 | const vector_ty = self.typeOfIndex(inst); |
| 842 | const len = vector_ty.vectorLen(); | |
| 843 | const len = vector_ty.vectorLen(mod); | |
| 843 | 844 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 844 | 845 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 845 | 846 | const result: MCValue = res: { |
| ... | ... | @@ -871,12 +872,13 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 871 | 872 | } |
| 872 | 873 | |
| 873 | 874 | fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 875 | const mod = self.bin_file.options.module.?; | |
| 874 | 876 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 875 | 877 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else result: { |
| 876 | 878 | const ptr_ty = self.typeOf(ty_op.operand); |
| 877 | 879 | const ptr = try self.resolveInst(ty_op.operand); |
| 878 | const array_ty = ptr_ty.childType(); | |
| 879 | const array_len = @intCast(u32, array_ty.arrayLen()); | |
| 880 | const array_ty = ptr_ty.childType(mod); | |
| 881 | const array_len = @intCast(u32, array_ty.arrayLen(mod)); | |
| 880 | 882 | |
| 881 | 883 | const ptr_bits = self.target.ptrBitWidth(); |
| 882 | 884 | const ptr_bytes = @divExact(ptr_bits, 8); |
| ... | ... | @@ -1300,7 +1302,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 1300 | 1302 | const mod = self.bin_file.options.module.?; |
| 1301 | 1303 | const fn_ty = switch (ty.zigTypeTag(mod)) { |
| 1302 | 1304 | .Fn => ty, |
| 1303 | .Pointer => ty.childType(), | |
| 1305 | .Pointer => ty.childType(mod), | |
| 1304 | 1306 | else => unreachable, |
| 1305 | 1307 | }; |
| 1306 | 1308 | |
| ... | ... | @@ -1440,8 +1442,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void { |
| 1440 | 1442 | .Pointer => Type.usize, |
| 1441 | 1443 | .ErrorSet => Type.u16, |
| 1442 | 1444 | .Optional => blk: { |
| 1443 | var opt_buffer: Type.Payload.ElemType = undefined; | |
| 1444 | const payload_ty = lhs_ty.optionalChild(&opt_buffer); | |
| 1445 | const payload_ty = lhs_ty.optionalChild(mod); | |
| 1445 | 1446 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 1446 | 1447 | break :blk Type.u1; |
| 1447 | 1448 | } else if (lhs_ty.isPtrLikeOptional(mod)) { |
| ... | ... | @@ -2447,6 +2448,7 @@ fn airSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 2447 | 2448 | } |
| 2448 | 2449 | |
| 2449 | 2450 | fn airSliceElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 2451 | const mod = self.bin_file.options.module.?; | |
| 2450 | 2452 | const is_volatile = false; // TODO |
| 2451 | 2453 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 2452 | 2454 | |
| ... | ... | @@ -2456,8 +2458,7 @@ fn airSliceElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 2456 | 2458 | const index_mcv = try self.resolveInst(bin_op.rhs); |
| 2457 | 2459 | |
| 2458 | 2460 | const slice_ty = self.typeOf(bin_op.lhs); |
| 2459 | const elem_ty = slice_ty.childType(); | |
| 2460 | const mod = self.bin_file.options.module.?; | |
| 2461 | const elem_ty = slice_ty.childType(mod); | |
| 2461 | 2462 | const elem_size = elem_ty.abiSize(mod); |
| 2462 | 2463 | |
| 2463 | 2464 | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| ... | ... | @@ -2797,7 +2798,7 @@ fn allocMem(self: *Self, inst: Air.Inst.Index, abi_size: u32, abi_align: u32) !u |
| 2797 | 2798 | /// Use a pointer instruction as the basis for allocating stack memory. |
| 2798 | 2799 | fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !u32 { |
| 2799 | 2800 | const mod = self.bin_file.options.module.?; |
| 2800 | const elem_ty = self.typeOfIndex(inst).elemType(); | |
| 2801 | const elem_ty = self.typeOfIndex(inst).childType(mod); | |
| 2801 | 2802 | |
| 2802 | 2803 | if (!elem_ty.hasRuntimeBits(mod)) { |
| 2803 | 2804 | // As this stack item will never be dereferenced at runtime, |
| ... | ... | @@ -3001,9 +3002,9 @@ fn binOp( |
| 3001 | 3002 | switch (lhs_ty.zigTypeTag(mod)) { |
| 3002 | 3003 | .Pointer => { |
| 3003 | 3004 | const ptr_ty = lhs_ty; |
| 3004 | const elem_ty = switch (ptr_ty.ptrSize()) { | |
| 3005 | .One => ptr_ty.childType().childType(), // ptr to array, so get array element type | |
| 3006 | else => ptr_ty.childType(), | |
| 3005 | const elem_ty = switch (ptr_ty.ptrSize(mod)) { | |
| 3006 | .One => ptr_ty.childType(mod).childType(mod), // ptr to array, so get array element type | |
| 3007 | else => ptr_ty.childType(mod), | |
| 3007 | 3008 | }; |
| 3008 | 3009 | const elem_size = elem_ty.abiSize(mod); |
| 3009 | 3010 | |
| ... | ... | @@ -3019,7 +3020,7 @@ fn binOp( |
| 3019 | 3020 | // multiplying it with elem_size |
| 3020 | 3021 | |
| 3021 | 3022 | const offset = try self.binOp(.mul, rhs, .{ .immediate = elem_size }, Type.usize, Type.usize, null); |
| 3022 | const addr = try self.binOp(tag, lhs, offset, Type.initTag(.manyptr_u8), Type.usize, null); | |
| 3023 | const addr = try self.binOp(tag, lhs, offset, Type.manyptr_u8, Type.usize, null); | |
| 3023 | 3024 | return addr; |
| 3024 | 3025 | } |
| 3025 | 3026 | }, |
| ... | ... | @@ -4042,11 +4043,7 @@ fn genSetStack(self: *Self, ty: Type, stack_offset: u32, mcv: MCValue) InnerErro |
| 4042 | 4043 | const reg = try self.copyToTmpRegister(ty, mcv); |
| 4043 | 4044 | return self.genSetStack(ty, stack_offset, MCValue{ .register = reg }); |
| 4044 | 4045 | } else { |
| 4045 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 4046 | .base = .{ .tag = .single_mut_pointer }, | |
| 4047 | .data = ty, | |
| 4048 | }; | |
| 4049 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 4046 | const ptr_ty = try mod.singleMutPtrType(ty); | |
| 4050 | 4047 | |
| 4051 | 4048 | const regs = try self.register_manager.allocRegs(4, .{ null, null, null, null }, gp); |
| 4052 | 4049 | const regs_locks = self.register_manager.lockRegsAssumeUnused(4, regs); |
| ... | ... | @@ -4269,7 +4266,7 @@ fn jump(self: *Self, inst: Mir.Inst.Index) !void { |
| 4269 | 4266 | |
| 4270 | 4267 | fn load(self: *Self, dst_mcv: MCValue, ptr: MCValue, ptr_ty: Type) InnerError!void { |
| 4271 | 4268 | const mod = self.bin_file.options.module.?; |
| 4272 | const elem_ty = ptr_ty.elemType(); | |
| 4269 | const elem_ty = ptr_ty.childType(mod); | |
| 4273 | 4270 | const elem_size = elem_ty.abiSize(mod); |
| 4274 | 4271 | |
| 4275 | 4272 | switch (ptr) { |
| ... | ... | @@ -4729,7 +4726,7 @@ fn structFieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, inde |
| 4729 | 4726 | const mod = self.bin_file.options.module.?; |
| 4730 | 4727 | const mcv = try self.resolveInst(operand); |
| 4731 | 4728 | const ptr_ty = self.typeOf(operand); |
| 4732 | const struct_ty = ptr_ty.childType(); | |
| 4729 | const struct_ty = ptr_ty.childType(mod); | |
| 4733 | 4730 | const struct_field_offset = @intCast(u32, struct_ty.structFieldOffset(index, mod)); |
| 4734 | 4731 | switch (mcv) { |
| 4735 | 4732 | .ptr_stack_offset => |off| { |
src/arch/wasm/CodeGen.zig+80-88| ... | ... | @@ -1542,7 +1542,7 @@ fn allocStack(func: *CodeGen, ty: Type) !WValue { |
| 1542 | 1542 | fn allocStackPtr(func: *CodeGen, inst: Air.Inst.Index) !WValue { |
| 1543 | 1543 | const mod = func.bin_file.base.options.module.?; |
| 1544 | 1544 | const ptr_ty = func.typeOfIndex(inst); |
| 1545 | const pointee_ty = ptr_ty.childType(); | |
| 1545 | const pointee_ty = ptr_ty.childType(mod); | |
| 1546 | 1546 | |
| 1547 | 1547 | if (func.initial_stack_value == .none) { |
| 1548 | 1548 | try func.initializeStack(); |
| ... | ... | @@ -1766,8 +1766,7 @@ fn isByRef(ty: Type, mod: *const Module) bool { |
| 1766 | 1766 | }, |
| 1767 | 1767 | .Optional => { |
| 1768 | 1768 | if (ty.isPtrLikeOptional(mod)) return false; |
| 1769 | var buf: Type.Payload.ElemType = undefined; | |
| 1770 | const pl_type = ty.optionalChild(&buf); | |
| 1769 | const pl_type = ty.optionalChild(mod); | |
| 1771 | 1770 | if (pl_type.zigTypeTag(mod) == .ErrorSet) return false; |
| 1772 | 1771 | return pl_type.hasRuntimeBitsIgnoreComptime(mod); |
| 1773 | 1772 | }, |
| ... | ... | @@ -2139,7 +2138,7 @@ fn airRet(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 2139 | 2138 | |
| 2140 | 2139 | fn airRetPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 2141 | 2140 | const mod = func.bin_file.base.options.module.?; |
| 2142 | const child_type = func.typeOfIndex(inst).childType(); | |
| 2141 | const child_type = func.typeOfIndex(inst).childType(mod); | |
| 2143 | 2142 | |
| 2144 | 2143 | var result = result: { |
| 2145 | 2144 | if (!child_type.isFnOrHasRuntimeBitsIgnoreComptime(mod)) { |
| ... | ... | @@ -2161,7 +2160,7 @@ fn airRetLoad(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 2161 | 2160 | const mod = func.bin_file.base.options.module.?; |
| 2162 | 2161 | const un_op = func.air.instructions.items(.data)[inst].un_op; |
| 2163 | 2162 | const operand = try func.resolveInst(un_op); |
| 2164 | const ret_ty = func.typeOf(un_op).childType(); | |
| 2163 | const ret_ty = func.typeOf(un_op).childType(mod); | |
| 2165 | 2164 | |
| 2166 | 2165 | const fn_info = func.decl.ty.fnInfo(); |
| 2167 | 2166 | if (!ret_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| ... | ... | @@ -2188,7 +2187,7 @@ fn airCall(func: *CodeGen, inst: Air.Inst.Index, modifier: std.builtin.CallModif |
| 2188 | 2187 | const mod = func.bin_file.base.options.module.?; |
| 2189 | 2188 | const fn_ty = switch (ty.zigTypeTag(mod)) { |
| 2190 | 2189 | .Fn => ty, |
| 2191 | .Pointer => ty.childType(), | |
| 2190 | .Pointer => ty.childType(mod), | |
| 2192 | 2191 | else => unreachable, |
| 2193 | 2192 | }; |
| 2194 | 2193 | const ret_ty = fn_ty.fnReturnType(); |
| ... | ... | @@ -2301,8 +2300,8 @@ fn airStore(func: *CodeGen, inst: Air.Inst.Index, safety: bool) InnerError!void |
| 2301 | 2300 | const lhs = try func.resolveInst(bin_op.lhs); |
| 2302 | 2301 | const rhs = try func.resolveInst(bin_op.rhs); |
| 2303 | 2302 | const ptr_ty = func.typeOf(bin_op.lhs); |
| 2304 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 2305 | const ty = ptr_ty.childType(); | |
| 2303 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 2304 | const ty = ptr_ty.childType(mod); | |
| 2306 | 2305 | |
| 2307 | 2306 | if (ptr_info.host_size == 0) { |
| 2308 | 2307 | try func.store(lhs, rhs, ty, 0); |
| ... | ... | @@ -2360,8 +2359,7 @@ fn store(func: *CodeGen, lhs: WValue, rhs: WValue, ty: Type, offset: u32) InnerE |
| 2360 | 2359 | if (ty.isPtrLikeOptional(mod)) { |
| 2361 | 2360 | return func.store(lhs, rhs, Type.usize, 0); |
| 2362 | 2361 | } |
| 2363 | var buf: Type.Payload.ElemType = undefined; | |
| 2364 | const pl_ty = ty.optionalChild(&buf); | |
| 2362 | const pl_ty = ty.optionalChild(mod); | |
| 2365 | 2363 | if (!pl_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 2366 | 2364 | return func.store(lhs, rhs, Type.u8, 0); |
| 2367 | 2365 | } |
| ... | ... | @@ -2454,7 +2452,7 @@ fn airLoad(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 2454 | 2452 | const operand = try func.resolveInst(ty_op.operand); |
| 2455 | 2453 | const ty = func.air.getRefType(ty_op.ty); |
| 2456 | 2454 | const ptr_ty = func.typeOf(ty_op.operand); |
| 2457 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 2455 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 2458 | 2456 | |
| 2459 | 2457 | if (!ty.hasRuntimeBitsIgnoreComptime(mod)) return func.finishAir(inst, .none, &.{ty_op.operand}); |
| 2460 | 2458 | |
| ... | ... | @@ -2971,7 +2969,7 @@ fn lowerParentPtr(func: *CodeGen, ptr_val: Value, offset: u32) InnerError!WValue |
| 2971 | 2969 | break :blk field_offset; |
| 2972 | 2970 | }, |
| 2973 | 2971 | }, |
| 2974 | .Pointer => switch (parent_ty.ptrSize()) { | |
| 2972 | .Pointer => switch (parent_ty.ptrSize(mod)) { | |
| 2975 | 2973 | .Slice => switch (field_ptr.field_index) { |
| 2976 | 2974 | 0 => 0, |
| 2977 | 2975 | 1 => func.ptrSize(), |
| ... | ... | @@ -3001,11 +2999,7 @@ fn lowerParentPtrDecl(func: *CodeGen, ptr_val: Value, decl_index: Module.Decl.In |
| 3001 | 2999 | const mod = func.bin_file.base.options.module.?; |
| 3002 | 3000 | const decl = mod.declPtr(decl_index); |
| 3003 | 3001 | mod.markDeclAlive(decl); |
| 3004 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 3005 | .base = .{ .tag = .single_mut_pointer }, | |
| 3006 | .data = decl.ty, | |
| 3007 | }; | |
| 3008 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 3002 | const ptr_ty = try mod.singleMutPtrType(decl.ty); | |
| 3009 | 3003 | return func.lowerDeclRefValue(.{ .ty = ptr_ty, .val = ptr_val }, decl_index, offset); |
| 3010 | 3004 | } |
| 3011 | 3005 | |
| ... | ... | @@ -3145,8 +3139,7 @@ fn lowerConstant(func: *CodeGen, arg_val: Value, ty: Type) InnerError!WValue { |
| 3145 | 3139 | return func.fail("Wasm TODO: lowerConstant error union with non-zero-bit payload type", .{}); |
| 3146 | 3140 | }, |
| 3147 | 3141 | .Optional => if (ty.optionalReprIsPayload(mod)) { |
| 3148 | var buf: Type.Payload.ElemType = undefined; | |
| 3149 | const pl_ty = ty.optionalChild(&buf); | |
| 3142 | const pl_ty = ty.optionalChild(mod); | |
| 3150 | 3143 | if (val.castTag(.opt_payload)) |payload| { |
| 3151 | 3144 | return func.lowerConstant(payload.data, pl_ty); |
| 3152 | 3145 | } else if (val.isNull(mod)) { |
| ... | ... | @@ -3217,8 +3210,7 @@ fn emitUndefined(func: *CodeGen, ty: Type) InnerError!WValue { |
| 3217 | 3210 | else => unreachable, |
| 3218 | 3211 | }, |
| 3219 | 3212 | .Optional => { |
| 3220 | var buf: Type.Payload.ElemType = undefined; | |
| 3221 | const pl_ty = ty.optionalChild(&buf); | |
| 3213 | const pl_ty = ty.optionalChild(mod); | |
| 3222 | 3214 | if (ty.optionalReprIsPayload(mod)) { |
| 3223 | 3215 | return func.emitUndefined(pl_ty); |
| 3224 | 3216 | } |
| ... | ... | @@ -3403,8 +3395,7 @@ fn cmp(func: *CodeGen, lhs: WValue, rhs: WValue, ty: Type, op: std.math.CompareO |
| 3403 | 3395 | assert(!(lhs != .stack and rhs == .stack)); |
| 3404 | 3396 | const mod = func.bin_file.base.options.module.?; |
| 3405 | 3397 | if (ty.zigTypeTag(mod) == .Optional and !ty.optionalReprIsPayload(mod)) { |
| 3406 | var buf: Type.Payload.ElemType = undefined; | |
| 3407 | const payload_ty = ty.optionalChild(&buf); | |
| 3398 | const payload_ty = ty.optionalChild(mod); | |
| 3408 | 3399 | if (payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 3409 | 3400 | // When we hit this case, we must check the value of optionals |
| 3410 | 3401 | // that are not pointers. This means first checking against non-null for |
| ... | ... | @@ -3609,19 +3600,21 @@ fn bitcast(func: *CodeGen, wanted_ty: Type, given_ty: Type, operand: WValue) Inn |
| 3609 | 3600 | } |
| 3610 | 3601 | |
| 3611 | 3602 | fn airStructFieldPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 3603 | const mod = func.bin_file.base.options.module.?; | |
| 3612 | 3604 | const ty_pl = func.air.instructions.items(.data)[inst].ty_pl; |
| 3613 | 3605 | const extra = func.air.extraData(Air.StructField, ty_pl.payload); |
| 3614 | 3606 | |
| 3615 | 3607 | const struct_ptr = try func.resolveInst(extra.data.struct_operand); |
| 3616 | const struct_ty = func.typeOf(extra.data.struct_operand).childType(); | |
| 3608 | const struct_ty = func.typeOf(extra.data.struct_operand).childType(mod); | |
| 3617 | 3609 | const result = try func.structFieldPtr(inst, extra.data.struct_operand, struct_ptr, struct_ty, extra.data.field_index); |
| 3618 | 3610 | func.finishAir(inst, result, &.{extra.data.struct_operand}); |
| 3619 | 3611 | } |
| 3620 | 3612 | |
| 3621 | 3613 | fn airStructFieldPtrIndex(func: *CodeGen, inst: Air.Inst.Index, index: u32) InnerError!void { |
| 3614 | const mod = func.bin_file.base.options.module.?; | |
| 3622 | 3615 | const ty_op = func.air.instructions.items(.data)[inst].ty_op; |
| 3623 | 3616 | const struct_ptr = try func.resolveInst(ty_op.operand); |
| 3624 | const struct_ty = func.typeOf(ty_op.operand).childType(); | |
| 3617 | const struct_ty = func.typeOf(ty_op.operand).childType(mod); | |
| 3625 | 3618 | |
| 3626 | 3619 | const result = try func.structFieldPtr(inst, ty_op.operand, struct_ptr, struct_ty, index); |
| 3627 | 3620 | func.finishAir(inst, result, &.{ty_op.operand}); |
| ... | ... | @@ -3640,7 +3633,7 @@ fn structFieldPtr( |
| 3640 | 3633 | const offset = switch (struct_ty.containerLayout()) { |
| 3641 | 3634 | .Packed => switch (struct_ty.zigTypeTag(mod)) { |
| 3642 | 3635 | .Struct => offset: { |
| 3643 | if (result_ty.ptrInfo().data.host_size != 0) { | |
| 3636 | if (result_ty.ptrInfo(mod).host_size != 0) { | |
| 3644 | 3637 | break :offset @as(u32, 0); |
| 3645 | 3638 | } |
| 3646 | 3639 | break :offset struct_ty.packedStructFieldByteOffset(index, mod); |
| ... | ... | @@ -3981,7 +3974,7 @@ fn airUnwrapErrUnionPayload(func: *CodeGen, inst: Air.Inst.Index, op_is_ptr: boo |
| 3981 | 3974 | |
| 3982 | 3975 | const operand = try func.resolveInst(ty_op.operand); |
| 3983 | 3976 | const op_ty = func.typeOf(ty_op.operand); |
| 3984 | const err_ty = if (op_is_ptr) op_ty.childType() else op_ty; | |
| 3977 | const err_ty = if (op_is_ptr) op_ty.childType(mod) else op_ty; | |
| 3985 | 3978 | const payload_ty = err_ty.errorUnionPayload(); |
| 3986 | 3979 | |
| 3987 | 3980 | const result = result: { |
| ... | ... | @@ -4009,7 +4002,7 @@ fn airUnwrapErrUnionError(func: *CodeGen, inst: Air.Inst.Index, op_is_ptr: bool) |
| 4009 | 4002 | |
| 4010 | 4003 | const operand = try func.resolveInst(ty_op.operand); |
| 4011 | 4004 | const op_ty = func.typeOf(ty_op.operand); |
| 4012 | const err_ty = if (op_is_ptr) op_ty.childType() else op_ty; | |
| 4005 | const err_ty = if (op_is_ptr) op_ty.childType(mod) else op_ty; | |
| 4013 | 4006 | const payload_ty = err_ty.errorUnionPayload(); |
| 4014 | 4007 | |
| 4015 | 4008 | const result = result: { |
| ... | ... | @@ -4156,11 +4149,12 @@ fn intcast(func: *CodeGen, operand: WValue, given: Type, wanted: Type) InnerErro |
| 4156 | 4149 | } |
| 4157 | 4150 | |
| 4158 | 4151 | fn airIsNull(func: *CodeGen, inst: Air.Inst.Index, opcode: wasm.Opcode, op_kind: enum { value, ptr }) InnerError!void { |
| 4152 | const mod = func.bin_file.base.options.module.?; | |
| 4159 | 4153 | const un_op = func.air.instructions.items(.data)[inst].un_op; |
| 4160 | 4154 | const operand = try func.resolveInst(un_op); |
| 4161 | 4155 | |
| 4162 | 4156 | const op_ty = func.typeOf(un_op); |
| 4163 | const optional_ty = if (op_kind == .ptr) op_ty.childType() else op_ty; | |
| 4157 | const optional_ty = if (op_kind == .ptr) op_ty.childType(mod) else op_ty; | |
| 4164 | 4158 | const is_null = try func.isNull(operand, optional_ty, opcode); |
| 4165 | 4159 | const result = try is_null.toLocal(func, optional_ty); |
| 4166 | 4160 | func.finishAir(inst, result, &.{un_op}); |
| ... | ... | @@ -4171,8 +4165,7 @@ fn airIsNull(func: *CodeGen, inst: Air.Inst.Index, opcode: wasm.Opcode, op_kind: |
| 4171 | 4165 | fn isNull(func: *CodeGen, operand: WValue, optional_ty: Type, opcode: wasm.Opcode) InnerError!WValue { |
| 4172 | 4166 | const mod = func.bin_file.base.options.module.?; |
| 4173 | 4167 | try func.emitWValue(operand); |
| 4174 | var buf: Type.Payload.ElemType = undefined; | |
| 4175 | const payload_ty = optional_ty.optionalChild(&buf); | |
| 4168 | const payload_ty = optional_ty.optionalChild(mod); | |
| 4176 | 4169 | if (!optional_ty.optionalReprIsPayload(mod)) { |
| 4177 | 4170 | // When payload is zero-bits, we can treat operand as a value, rather than |
| 4178 | 4171 | // a pointer to the stack value |
| ... | ... | @@ -4221,14 +4214,13 @@ fn airOptionalPayload(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4221 | 4214 | } |
| 4222 | 4215 | |
| 4223 | 4216 | fn airOptionalPayloadPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4217 | const mod = func.bin_file.base.options.module.?; | |
| 4224 | 4218 | const ty_op = func.air.instructions.items(.data)[inst].ty_op; |
| 4225 | 4219 | const operand = try func.resolveInst(ty_op.operand); |
| 4226 | const opt_ty = func.typeOf(ty_op.operand).childType(); | |
| 4220 | const opt_ty = func.typeOf(ty_op.operand).childType(mod); | |
| 4227 | 4221 | |
| 4228 | const mod = func.bin_file.base.options.module.?; | |
| 4229 | 4222 | const result = result: { |
| 4230 | var buf: Type.Payload.ElemType = undefined; | |
| 4231 | const payload_ty = opt_ty.optionalChild(&buf); | |
| 4223 | const payload_ty = opt_ty.optionalChild(mod); | |
| 4232 | 4224 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod) or opt_ty.optionalReprIsPayload(mod)) { |
| 4233 | 4225 | break :result func.reuseOperand(ty_op.operand, operand); |
| 4234 | 4226 | } |
| ... | ... | @@ -4242,9 +4234,8 @@ fn airOptionalPayloadPtrSet(func: *CodeGen, inst: Air.Inst.Index) InnerError!voi |
| 4242 | 4234 | const mod = func.bin_file.base.options.module.?; |
| 4243 | 4235 | const ty_op = func.air.instructions.items(.data)[inst].ty_op; |
| 4244 | 4236 | const operand = try func.resolveInst(ty_op.operand); |
| 4245 | const opt_ty = func.typeOf(ty_op.operand).childType(); | |
| 4246 | var buf: Type.Payload.ElemType = undefined; | |
| 4247 | const payload_ty = opt_ty.optionalChild(&buf); | |
| 4237 | const opt_ty = func.typeOf(ty_op.operand).childType(mod); | |
| 4238 | const payload_ty = opt_ty.optionalChild(mod); | |
| 4248 | 4239 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 4249 | 4240 | return func.fail("TODO: Implement OptionalPayloadPtrSet for optional with zero-sized type {}", .{payload_ty.fmtDebug()}); |
| 4250 | 4241 | } |
| ... | ... | @@ -4325,13 +4316,13 @@ fn airSliceLen(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4325 | 4316 | } |
| 4326 | 4317 | |
| 4327 | 4318 | fn airSliceElemVal(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4319 | const mod = func.bin_file.base.options.module.?; | |
| 4328 | 4320 | const bin_op = func.air.instructions.items(.data)[inst].bin_op; |
| 4329 | 4321 | |
| 4330 | 4322 | const slice_ty = func.typeOf(bin_op.lhs); |
| 4331 | 4323 | const slice = try func.resolveInst(bin_op.lhs); |
| 4332 | 4324 | const index = try func.resolveInst(bin_op.rhs); |
| 4333 | const elem_ty = slice_ty.childType(); | |
| 4334 | const mod = func.bin_file.base.options.module.?; | |
| 4325 | const elem_ty = slice_ty.childType(mod); | |
| 4335 | 4326 | const elem_size = elem_ty.abiSize(mod); |
| 4336 | 4327 | |
| 4337 | 4328 | // load pointer onto stack |
| ... | ... | @@ -4355,11 +4346,11 @@ fn airSliceElemVal(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4355 | 4346 | } |
| 4356 | 4347 | |
| 4357 | 4348 | fn airSliceElemPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4349 | const mod = func.bin_file.base.options.module.?; | |
| 4358 | 4350 | const ty_pl = func.air.instructions.items(.data)[inst].ty_pl; |
| 4359 | 4351 | const bin_op = func.air.extraData(Air.Bin, ty_pl.payload).data; |
| 4360 | 4352 | |
| 4361 | const elem_ty = func.air.getRefType(ty_pl.ty).childType(); | |
| 4362 | const mod = func.bin_file.base.options.module.?; | |
| 4353 | const elem_ty = func.air.getRefType(ty_pl.ty).childType(mod); | |
| 4363 | 4354 | const elem_size = elem_ty.abiSize(mod); |
| 4364 | 4355 | |
| 4365 | 4356 | const slice = try func.resolveInst(bin_op.lhs); |
| ... | ... | @@ -4436,7 +4427,7 @@ fn airArrayToSlice(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4436 | 4427 | const ty_op = func.air.instructions.items(.data)[inst].ty_op; |
| 4437 | 4428 | |
| 4438 | 4429 | const operand = try func.resolveInst(ty_op.operand); |
| 4439 | const array_ty = func.typeOf(ty_op.operand).childType(); | |
| 4430 | const array_ty = func.typeOf(ty_op.operand).childType(mod); | |
| 4440 | 4431 | const slice_ty = func.air.getRefType(ty_op.ty); |
| 4441 | 4432 | |
| 4442 | 4433 | // create a slice on the stack |
| ... | ... | @@ -4448,7 +4439,7 @@ fn airArrayToSlice(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4448 | 4439 | } |
| 4449 | 4440 | |
| 4450 | 4441 | // store the length of the array in the slice |
| 4451 | const len = WValue{ .imm32 = @intCast(u32, array_ty.arrayLen()) }; | |
| 4442 | const len = WValue{ .imm32 = @intCast(u32, array_ty.arrayLen(mod)) }; | |
| 4452 | 4443 | try func.store(slice_local, len, Type.usize, func.ptrSize()); |
| 4453 | 4444 | |
| 4454 | 4445 | func.finishAir(inst, slice_local, &.{ty_op.operand}); |
| ... | ... | @@ -4470,13 +4461,13 @@ fn airPtrToInt(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4470 | 4461 | } |
| 4471 | 4462 | |
| 4472 | 4463 | fn airPtrElemVal(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4464 | const mod = func.bin_file.base.options.module.?; | |
| 4473 | 4465 | const bin_op = func.air.instructions.items(.data)[inst].bin_op; |
| 4474 | 4466 | |
| 4475 | 4467 | const ptr_ty = func.typeOf(bin_op.lhs); |
| 4476 | 4468 | const ptr = try func.resolveInst(bin_op.lhs); |
| 4477 | 4469 | const index = try func.resolveInst(bin_op.rhs); |
| 4478 | const elem_ty = ptr_ty.childType(); | |
| 4479 | const mod = func.bin_file.base.options.module.?; | |
| 4470 | const elem_ty = ptr_ty.childType(mod); | |
| 4480 | 4471 | const elem_size = elem_ty.abiSize(mod); |
| 4481 | 4472 | |
| 4482 | 4473 | // load pointer onto the stack |
| ... | ... | @@ -4507,12 +4498,12 @@ fn airPtrElemVal(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4507 | 4498 | } |
| 4508 | 4499 | |
| 4509 | 4500 | fn airPtrElemPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4501 | const mod = func.bin_file.base.options.module.?; | |
| 4510 | 4502 | const ty_pl = func.air.instructions.items(.data)[inst].ty_pl; |
| 4511 | 4503 | const bin_op = func.air.extraData(Air.Bin, ty_pl.payload).data; |
| 4512 | 4504 | |
| 4513 | 4505 | const ptr_ty = func.typeOf(bin_op.lhs); |
| 4514 | const elem_ty = func.air.getRefType(ty_pl.ty).childType(); | |
| 4515 | const mod = func.bin_file.base.options.module.?; | |
| 4506 | const elem_ty = func.air.getRefType(ty_pl.ty).childType(mod); | |
| 4516 | 4507 | const elem_size = elem_ty.abiSize(mod); |
| 4517 | 4508 | |
| 4518 | 4509 | const ptr = try func.resolveInst(bin_op.lhs); |
| ... | ... | @@ -4544,9 +4535,9 @@ fn airPtrBinOp(func: *CodeGen, inst: Air.Inst.Index, op: Op) InnerError!void { |
| 4544 | 4535 | const ptr = try func.resolveInst(bin_op.lhs); |
| 4545 | 4536 | const offset = try func.resolveInst(bin_op.rhs); |
| 4546 | 4537 | const ptr_ty = func.typeOf(bin_op.lhs); |
| 4547 | const pointee_ty = switch (ptr_ty.ptrSize()) { | |
| 4548 | .One => ptr_ty.childType().childType(), // ptr to array, so get array element type | |
| 4549 | else => ptr_ty.childType(), | |
| 4538 | const pointee_ty = switch (ptr_ty.ptrSize(mod)) { | |
| 4539 | .One => ptr_ty.childType(mod).childType(mod), // ptr to array, so get array element type | |
| 4540 | else => ptr_ty.childType(mod), | |
| 4550 | 4541 | }; |
| 4551 | 4542 | |
| 4552 | 4543 | const valtype = typeToValtype(Type.usize, mod); |
| ... | ... | @@ -4565,6 +4556,7 @@ fn airPtrBinOp(func: *CodeGen, inst: Air.Inst.Index, op: Op) InnerError!void { |
| 4565 | 4556 | } |
| 4566 | 4557 | |
| 4567 | 4558 | fn airMemset(func: *CodeGen, inst: Air.Inst.Index, safety: bool) InnerError!void { |
| 4559 | const mod = func.bin_file.base.options.module.?; | |
| 4568 | 4560 | if (safety) { |
| 4569 | 4561 | // TODO if the value is undef, write 0xaa bytes to dest |
| 4570 | 4562 | } else { |
| ... | ... | @@ -4575,16 +4567,16 @@ fn airMemset(func: *CodeGen, inst: Air.Inst.Index, safety: bool) InnerError!void |
| 4575 | 4567 | const ptr = try func.resolveInst(bin_op.lhs); |
| 4576 | 4568 | const ptr_ty = func.typeOf(bin_op.lhs); |
| 4577 | 4569 | const value = try func.resolveInst(bin_op.rhs); |
| 4578 | const len = switch (ptr_ty.ptrSize()) { | |
| 4570 | const len = switch (ptr_ty.ptrSize(mod)) { | |
| 4579 | 4571 | .Slice => try func.sliceLen(ptr), |
| 4580 | .One => @as(WValue, .{ .imm32 = @intCast(u32, ptr_ty.childType().arrayLen()) }), | |
| 4572 | .One => @as(WValue, .{ .imm32 = @intCast(u32, ptr_ty.childType(mod).arrayLen(mod)) }), | |
| 4581 | 4573 | .C, .Many => unreachable, |
| 4582 | 4574 | }; |
| 4583 | 4575 | |
| 4584 | const elem_ty = if (ptr_ty.ptrSize() == .One) | |
| 4585 | ptr_ty.childType().childType() | |
| 4576 | const elem_ty = if (ptr_ty.ptrSize(mod) == .One) | |
| 4577 | ptr_ty.childType(mod).childType(mod) | |
| 4586 | 4578 | else |
| 4587 | ptr_ty.childType(); | |
| 4579 | ptr_ty.childType(mod); | |
| 4588 | 4580 | |
| 4589 | 4581 | const dst_ptr = try func.sliceOrArrayPtr(ptr, ptr_ty); |
| 4590 | 4582 | try func.memset(elem_ty, dst_ptr, len, value); |
| ... | ... | @@ -4686,13 +4678,13 @@ fn memset(func: *CodeGen, elem_ty: Type, ptr: WValue, len: WValue, value: WValue |
| 4686 | 4678 | } |
| 4687 | 4679 | |
| 4688 | 4680 | fn airArrayElemVal(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4681 | const mod = func.bin_file.base.options.module.?; | |
| 4689 | 4682 | const bin_op = func.air.instructions.items(.data)[inst].bin_op; |
| 4690 | 4683 | |
| 4691 | 4684 | const array_ty = func.typeOf(bin_op.lhs); |
| 4692 | 4685 | const array = try func.resolveInst(bin_op.lhs); |
| 4693 | 4686 | const index = try func.resolveInst(bin_op.rhs); |
| 4694 | const elem_ty = array_ty.childType(); | |
| 4695 | const mod = func.bin_file.base.options.module.?; | |
| 4687 | const elem_ty = array_ty.childType(mod); | |
| 4696 | 4688 | const elem_size = elem_ty.abiSize(mod); |
| 4697 | 4689 | |
| 4698 | 4690 | if (isByRef(array_ty, mod)) { |
| ... | ... | @@ -4810,7 +4802,7 @@ fn airSplat(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4810 | 4802 | const ty_op = func.air.instructions.items(.data)[inst].ty_op; |
| 4811 | 4803 | const operand = try func.resolveInst(ty_op.operand); |
| 4812 | 4804 | const ty = func.typeOfIndex(inst); |
| 4813 | const elem_ty = ty.childType(); | |
| 4805 | const elem_ty = ty.childType(mod); | |
| 4814 | 4806 | |
| 4815 | 4807 | if (determineSimdStoreStrategy(ty, mod) == .direct) blk: { |
| 4816 | 4808 | switch (operand) { |
| ... | ... | @@ -4859,7 +4851,7 @@ fn airSplat(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4859 | 4851 | } |
| 4860 | 4852 | } |
| 4861 | 4853 | const elem_size = elem_ty.bitSize(mod); |
| 4862 | const vector_len = @intCast(usize, ty.vectorLen()); | |
| 4854 | const vector_len = @intCast(usize, ty.vectorLen(mod)); | |
| 4863 | 4855 | if ((!std.math.isPowerOfTwo(elem_size) or elem_size % 8 != 0) and vector_len > 1) { |
| 4864 | 4856 | return func.fail("TODO: WebAssembly `@splat` for arbitrary element bitsize {d}", .{elem_size}); |
| 4865 | 4857 | } |
| ... | ... | @@ -4895,7 +4887,7 @@ fn airShuffle(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4895 | 4887 | const mask = func.air.values[extra.mask]; |
| 4896 | 4888 | const mask_len = extra.mask_len; |
| 4897 | 4889 | |
| 4898 | const child_ty = inst_ty.childType(); | |
| 4890 | const child_ty = inst_ty.childType(mod); | |
| 4899 | 4891 | const elem_size = child_ty.abiSize(mod); |
| 4900 | 4892 | |
| 4901 | 4893 | // TODO: One of them could be by ref; handle in loop |
| ... | ... | @@ -4959,16 +4951,16 @@ fn airAggregateInit(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 4959 | 4951 | const mod = func.bin_file.base.options.module.?; |
| 4960 | 4952 | const ty_pl = func.air.instructions.items(.data)[inst].ty_pl; |
| 4961 | 4953 | const result_ty = func.typeOfIndex(inst); |
| 4962 | const len = @intCast(usize, result_ty.arrayLen()); | |
| 4954 | const len = @intCast(usize, result_ty.arrayLen(mod)); | |
| 4963 | 4955 | const elements = @ptrCast([]const Air.Inst.Ref, func.air.extra[ty_pl.payload..][0..len]); |
| 4964 | 4956 | |
| 4965 | 4957 | const result: WValue = result_value: { |
| 4966 | 4958 | switch (result_ty.zigTypeTag(mod)) { |
| 4967 | 4959 | .Array => { |
| 4968 | 4960 | const result = try func.allocStack(result_ty); |
| 4969 | const elem_ty = result_ty.childType(); | |
| 4961 | const elem_ty = result_ty.childType(mod); | |
| 4970 | 4962 | const elem_size = @intCast(u32, elem_ty.abiSize(mod)); |
| 4971 | const sentinel = if (result_ty.sentinel()) |sent| blk: { | |
| 4963 | const sentinel = if (result_ty.sentinel(mod)) |sent| blk: { | |
| 4972 | 4964 | break :blk try func.lowerConstant(sent, elem_ty); |
| 4973 | 4965 | } else null; |
| 4974 | 4966 | |
| ... | ... | @@ -5190,8 +5182,7 @@ fn cmpOptionals(func: *CodeGen, lhs: WValue, rhs: WValue, operand_ty: Type, op: |
| 5190 | 5182 | const mod = func.bin_file.base.options.module.?; |
| 5191 | 5183 | assert(operand_ty.hasRuntimeBitsIgnoreComptime(mod)); |
| 5192 | 5184 | assert(op == .eq or op == .neq); |
| 5193 | var buf: Type.Payload.ElemType = undefined; | |
| 5194 | const payload_ty = operand_ty.optionalChild(&buf); | |
| 5185 | const payload_ty = operand_ty.optionalChild(mod); | |
| 5195 | 5186 | |
| 5196 | 5187 | // We store the final result in here that will be validated |
| 5197 | 5188 | // if the optional is truly equal. |
| ... | ... | @@ -5268,7 +5259,7 @@ fn cmpBigInt(func: *CodeGen, lhs: WValue, rhs: WValue, operand_ty: Type, op: std |
| 5268 | 5259 | fn airSetUnionTag(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5269 | 5260 | const mod = func.bin_file.base.options.module.?; |
| 5270 | 5261 | const bin_op = func.air.instructions.items(.data)[inst].bin_op; |
| 5271 | const un_ty = func.typeOf(bin_op.lhs).childType(); | |
| 5262 | const un_ty = func.typeOf(bin_op.lhs).childType(mod); | |
| 5272 | 5263 | const tag_ty = func.typeOf(bin_op.rhs); |
| 5273 | 5264 | const layout = un_ty.unionGetLayout(mod); |
| 5274 | 5265 | if (layout.tag_size == 0) return func.finishAir(inst, .none, &.{ bin_op.lhs, bin_op.rhs }); |
| ... | ... | @@ -5398,7 +5389,7 @@ fn airErrUnionPayloadPtrSet(func: *CodeGen, inst: Air.Inst.Index) InnerError!voi |
| 5398 | 5389 | const mod = func.bin_file.base.options.module.?; |
| 5399 | 5390 | const ty_op = func.air.instructions.items(.data)[inst].ty_op; |
| 5400 | 5391 | |
| 5401 | const err_set_ty = func.typeOf(ty_op.operand).childType(); | |
| 5392 | const err_set_ty = func.typeOf(ty_op.operand).childType(mod); | |
| 5402 | 5393 | const payload_ty = err_set_ty.errorUnionPayload(); |
| 5403 | 5394 | const operand = try func.resolveInst(ty_op.operand); |
| 5404 | 5395 | |
| ... | ... | @@ -5426,7 +5417,7 @@ fn airFieldParentPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5426 | 5417 | const extra = func.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; |
| 5427 | 5418 | |
| 5428 | 5419 | const field_ptr = try func.resolveInst(extra.field_ptr); |
| 5429 | const parent_ty = func.air.getRefType(ty_pl.ty).childType(); | |
| 5420 | const parent_ty = func.air.getRefType(ty_pl.ty).childType(mod); | |
| 5430 | 5421 | const field_offset = parent_ty.structFieldOffset(extra.field_index, mod); |
| 5431 | 5422 | |
| 5432 | 5423 | const result = if (field_offset != 0) result: { |
| ... | ... | @@ -5455,10 +5446,10 @@ fn airMemcpy(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5455 | 5446 | const bin_op = func.air.instructions.items(.data)[inst].bin_op; |
| 5456 | 5447 | const dst = try func.resolveInst(bin_op.lhs); |
| 5457 | 5448 | const dst_ty = func.typeOf(bin_op.lhs); |
| 5458 | const ptr_elem_ty = dst_ty.childType(); | |
| 5449 | const ptr_elem_ty = dst_ty.childType(mod); | |
| 5459 | 5450 | const src = try func.resolveInst(bin_op.rhs); |
| 5460 | 5451 | const src_ty = func.typeOf(bin_op.rhs); |
| 5461 | const len = switch (dst_ty.ptrSize()) { | |
| 5452 | const len = switch (dst_ty.ptrSize(mod)) { | |
| 5462 | 5453 | .Slice => blk: { |
| 5463 | 5454 | const slice_len = try func.sliceLen(dst); |
| 5464 | 5455 | if (ptr_elem_ty.abiSize(mod) != 1) { |
| ... | ... | @@ -5470,7 +5461,7 @@ fn airMemcpy(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5470 | 5461 | break :blk slice_len; |
| 5471 | 5462 | }, |
| 5472 | 5463 | .One => @as(WValue, .{ |
| 5473 | .imm32 = @intCast(u32, ptr_elem_ty.arrayLen() * ptr_elem_ty.childType().abiSize(mod)), | |
| 5464 | .imm32 = @intCast(u32, ptr_elem_ty.arrayLen(mod) * ptr_elem_ty.childType(mod).abiSize(mod)), | |
| 5474 | 5465 | }), |
| 5475 | 5466 | .C, .Many => unreachable, |
| 5476 | 5467 | }; |
| ... | ... | @@ -5551,7 +5542,7 @@ fn airErrorName(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5551 | 5542 | // As the names are global and the slice elements are constant, we do not have |
| 5552 | 5543 | // to make a copy of the ptr+value but can point towards them directly. |
| 5553 | 5544 | const error_table_symbol = try func.bin_file.getErrorTableSymbol(); |
| 5554 | const name_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 5545 | const name_ty = Type.const_slice_u8_sentinel_0; | |
| 5555 | 5546 | const mod = func.bin_file.base.options.module.?; |
| 5556 | 5547 | const abi_size = name_ty.abiSize(mod); |
| 5557 | 5548 | |
| ... | ... | @@ -5857,7 +5848,7 @@ fn airMulWithOverflow(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5857 | 5848 | try func.addLabel(.local_set, overflow_bit.local.value); |
| 5858 | 5849 | break :blk try func.wrapOperand(bin_op, lhs_ty); |
| 5859 | 5850 | } else if (int_info.bits == 64 and int_info.signedness == .unsigned) blk: { |
| 5860 | const new_ty = Type.initTag(.u128); | |
| 5851 | const new_ty = Type.u128; | |
| 5861 | 5852 | var lhs_upcast = try (try func.intcast(lhs, lhs_ty, new_ty)).toLocal(func, lhs_ty); |
| 5862 | 5853 | defer lhs_upcast.free(func); |
| 5863 | 5854 | var rhs_upcast = try (try func.intcast(rhs, lhs_ty, new_ty)).toLocal(func, lhs_ty); |
| ... | ... | @@ -5878,7 +5869,7 @@ fn airMulWithOverflow(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5878 | 5869 | const bin_op = try func.callIntrinsic( |
| 5879 | 5870 | "__multi3", |
| 5880 | 5871 | &[_]Type{Type.i64} ** 4, |
| 5881 | Type.initTag(.i128), | |
| 5872 | Type.i128, | |
| 5882 | 5873 | &.{ lhs, lhs_shifted, rhs, rhs_shifted }, |
| 5883 | 5874 | ); |
| 5884 | 5875 | const res = try func.allocLocal(lhs_ty); |
| ... | ... | @@ -5902,19 +5893,19 @@ fn airMulWithOverflow(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5902 | 5893 | const mul1 = try func.callIntrinsic( |
| 5903 | 5894 | "__multi3", |
| 5904 | 5895 | &[_]Type{Type.i64} ** 4, |
| 5905 | Type.initTag(.i128), | |
| 5896 | Type.i128, | |
| 5906 | 5897 | &.{ lhs_lsb, zero, rhs_msb, zero }, |
| 5907 | 5898 | ); |
| 5908 | 5899 | const mul2 = try func.callIntrinsic( |
| 5909 | 5900 | "__multi3", |
| 5910 | 5901 | &[_]Type{Type.i64} ** 4, |
| 5911 | Type.initTag(.i128), | |
| 5902 | Type.i128, | |
| 5912 | 5903 | &.{ rhs_lsb, zero, lhs_msb, zero }, |
| 5913 | 5904 | ); |
| 5914 | 5905 | const mul3 = try func.callIntrinsic( |
| 5915 | 5906 | "__multi3", |
| 5916 | 5907 | &[_]Type{Type.i64} ** 4, |
| 5917 | Type.initTag(.i128), | |
| 5908 | Type.i128, | |
| 5918 | 5909 | &.{ lhs_msb, zero, rhs_msb, zero }, |
| 5919 | 5910 | ); |
| 5920 | 5911 | |
| ... | ... | @@ -5942,7 +5933,7 @@ fn airMulWithOverflow(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 5942 | 5933 | _ = try func.binOp(lsb_or, mul_add_lt, Type.bool, .@"or"); |
| 5943 | 5934 | try func.addLabel(.local_set, overflow_bit.local.value); |
| 5944 | 5935 | |
| 5945 | const tmp_result = try func.allocStack(Type.initTag(.u128)); | |
| 5936 | const tmp_result = try func.allocStack(Type.u128); | |
| 5946 | 5937 | try func.emitWValue(tmp_result); |
| 5947 | 5938 | const mul3_msb = try func.load(mul3, Type.u64, 0); |
| 5948 | 5939 | try func.store(.stack, mul3_msb, Type.u64, tmp_result.offset()); |
| ... | ... | @@ -6191,11 +6182,12 @@ fn airTry(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 6191 | 6182 | } |
| 6192 | 6183 | |
| 6193 | 6184 | fn airTryPtr(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 6185 | const mod = func.bin_file.base.options.module.?; | |
| 6194 | 6186 | const ty_pl = func.air.instructions.items(.data)[inst].ty_pl; |
| 6195 | 6187 | const extra = func.air.extraData(Air.TryPtr, ty_pl.payload); |
| 6196 | 6188 | const err_union_ptr = try func.resolveInst(extra.data.ptr); |
| 6197 | 6189 | const body = func.air.extra[extra.end..][0..extra.data.body_len]; |
| 6198 | const err_union_ty = func.typeOf(extra.data.ptr).childType(); | |
| 6190 | const err_union_ty = func.typeOf(extra.data.ptr).childType(mod); | |
| 6199 | 6191 | const result = try lowerTry(func, inst, err_union_ptr, body, err_union_ty, true); |
| 6200 | 6192 | func.finishAir(inst, result, &.{extra.data.ptr}); |
| 6201 | 6193 | } |
| ... | ... | @@ -6845,11 +6837,11 @@ fn getTagNameFunction(func: *CodeGen, enum_ty: Type) InnerError!u32 { |
| 6845 | 6837 | for (enum_ty.enumFields().keys(), 0..) |tag_name, field_index| { |
| 6846 | 6838 | // for each tag name, create an unnamed const, |
| 6847 | 6839 | // and then get a pointer to its value. |
| 6848 | var name_ty_payload: Type.Payload.Len = .{ | |
| 6849 | .base = .{ .tag = .array_u8_sentinel_0 }, | |
| 6850 | .data = @intCast(u64, tag_name.len), | |
| 6851 | }; | |
| 6852 | const name_ty = Type.initPayload(&name_ty_payload.base); | |
| 6840 | const name_ty = try mod.arrayType(.{ | |
| 6841 | .len = tag_name.len, | |
| 6842 | .child = .u8_type, | |
| 6843 | .sentinel = .zero_u8, | |
| 6844 | }); | |
| 6853 | 6845 | const string_bytes = &mod.string_literal_bytes; |
| 6854 | 6846 | try string_bytes.ensureUnusedCapacity(mod.gpa, tag_name.len); |
| 6855 | 6847 | const gop = try mod.string_literal_table.getOrPutContextAdapted(mod.gpa, tag_name, Module.StringLiteralAdapter{ |
| ... | ... | @@ -6972,7 +6964,7 @@ fn getTagNameFunction(func: *CodeGen, enum_ty: Type) InnerError!u32 { |
| 6972 | 6964 | // finish function body |
| 6973 | 6965 | try writer.writeByte(std.wasm.opcode(.end)); |
| 6974 | 6966 | |
| 6975 | const slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 6967 | const slice_ty = Type.const_slice_u8_sentinel_0; | |
| 6976 | 6968 | const func_type = try genFunctype(arena, .Unspecified, &.{int_tag_ty}, slice_ty, mod); |
| 6977 | 6969 | return func.bin_file.createFunction(func_name, func_type, &body_list, &relocs); |
| 6978 | 6970 | } |
| ... | ... | @@ -7068,7 +7060,7 @@ fn airCmpxchg(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 7068 | 7060 | const extra = func.air.extraData(Air.Cmpxchg, ty_pl.payload).data; |
| 7069 | 7061 | |
| 7070 | 7062 | const ptr_ty = func.typeOf(extra.ptr); |
| 7071 | const ty = ptr_ty.childType(); | |
| 7063 | const ty = ptr_ty.childType(mod); | |
| 7072 | 7064 | const result_ty = func.typeOfIndex(inst); |
| 7073 | 7065 | |
| 7074 | 7066 | const ptr_operand = try func.resolveInst(extra.ptr); |
| ... | ... | @@ -7355,7 +7347,7 @@ fn airAtomicStore(func: *CodeGen, inst: Air.Inst.Index) InnerError!void { |
| 7355 | 7347 | const ptr = try func.resolveInst(bin_op.lhs); |
| 7356 | 7348 | const operand = try func.resolveInst(bin_op.rhs); |
| 7357 | 7349 | const ptr_ty = func.typeOf(bin_op.lhs); |
| 7358 | const ty = ptr_ty.childType(); | |
| 7350 | const ty = ptr_ty.childType(mod); | |
| 7359 | 7351 | |
| 7360 | 7352 | if (func.useAtomicFeature()) { |
| 7361 | 7353 | const tag: wasm.AtomicsOpcode = switch (ty.abiSize(mod)) { |
src/arch/x86_64/CodeGen.zig+153-161| ... | ... | @@ -2259,7 +2259,7 @@ fn allocFrameIndex(self: *Self, alloc: FrameAlloc) !FrameIndex { |
| 2259 | 2259 | fn allocMemPtr(self: *Self, inst: Air.Inst.Index) !FrameIndex { |
| 2260 | 2260 | const mod = self.bin_file.options.module.?; |
| 2261 | 2261 | const ptr_ty = self.typeOfIndex(inst); |
| 2262 | const val_ty = ptr_ty.childType(); | |
| 2262 | const val_ty = ptr_ty.childType(mod); | |
| 2263 | 2263 | return self.allocFrameIndex(FrameAlloc.init(.{ |
| 2264 | 2264 | .size = math.cast(u32, val_ty.abiSize(mod)) orelse { |
| 2265 | 2265 | return self.fail("type '{}' too big to fit into stack frame", .{val_ty.fmt(mod)}); |
| ... | ... | @@ -2289,8 +2289,8 @@ fn allocRegOrMemAdvanced(self: *Self, ty: Type, inst: ?Air.Inst.Index, reg_ok: b |
| 2289 | 2289 | 80 => break :need_mem, |
| 2290 | 2290 | else => unreachable, |
| 2291 | 2291 | }, |
| 2292 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 2293 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 2292 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 2293 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 2294 | 2294 | 16, 32, 64, 128 => if (self.hasFeature(.avx)) 32 else 16, |
| 2295 | 2295 | 80 => break :need_mem, |
| 2296 | 2296 | else => unreachable, |
| ... | ... | @@ -2727,12 +2727,12 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 2727 | 2727 | try self.copyToRegisterWithInstTracking(inst, dst_ty, src_mcv); |
| 2728 | 2728 | |
| 2729 | 2729 | if (dst_ty.zigTypeTag(mod) == .Vector) { |
| 2730 | assert(src_ty.zigTypeTag(mod) == .Vector and dst_ty.vectorLen() == src_ty.vectorLen()); | |
| 2731 | const dst_info = dst_ty.childType().intInfo(mod); | |
| 2732 | const src_info = src_ty.childType().intInfo(mod); | |
| 2730 | assert(src_ty.zigTypeTag(mod) == .Vector and dst_ty.vectorLen(mod) == src_ty.vectorLen(mod)); | |
| 2731 | const dst_info = dst_ty.childType(mod).intInfo(mod); | |
| 2732 | const src_info = src_ty.childType(mod).intInfo(mod); | |
| 2733 | 2733 | const mir_tag = if (@as(?Mir.Inst.FixedTag, switch (dst_info.bits) { |
| 2734 | 2734 | 8 => switch (src_info.bits) { |
| 2735 | 16 => switch (dst_ty.vectorLen()) { | |
| 2735 | 16 => switch (dst_ty.vectorLen(mod)) { | |
| 2736 | 2736 | 1...8 => if (self.hasFeature(.avx)) .{ .vp_b, .ackusw } else .{ .p_b, .ackusw }, |
| 2737 | 2737 | 9...16 => if (self.hasFeature(.avx2)) .{ .vp_b, .ackusw } else null, |
| 2738 | 2738 | else => null, |
| ... | ... | @@ -2740,7 +2740,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 2740 | 2740 | else => null, |
| 2741 | 2741 | }, |
| 2742 | 2742 | 16 => switch (src_info.bits) { |
| 2743 | 32 => switch (dst_ty.vectorLen()) { | |
| 2743 | 32 => switch (dst_ty.vectorLen(mod)) { | |
| 2744 | 2744 | 1...4 => if (self.hasFeature(.avx)) |
| 2745 | 2745 | .{ .vp_w, .ackusd } |
| 2746 | 2746 | else if (self.hasFeature(.sse4_1)) |
| ... | ... | @@ -2769,14 +2769,10 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void { |
| 2769 | 2769 | }; |
| 2770 | 2770 | const splat_val = Value.initPayload(&splat_pl.base); |
| 2771 | 2771 | |
| 2772 | var full_pl = Type.Payload.Array{ | |
| 2773 | .base = .{ .tag = .vector }, | |
| 2774 | .data = .{ | |
| 2775 | .len = @divExact(@as(u64, if (src_abi_size > 16) 256 else 128), src_info.bits), | |
| 2776 | .elem_type = src_ty.childType(), | |
| 2777 | }, | |
| 2778 | }; | |
| 2779 | const full_ty = Type.initPayload(&full_pl.base); | |
| 2772 | const full_ty = try mod.vectorType(.{ | |
| 2773 | .len = @intCast(u32, @divExact(@as(u64, if (src_abi_size > 16) 256 else 128), src_info.bits)), | |
| 2774 | .child = src_ty.childType(mod).ip_index, | |
| 2775 | }); | |
| 2780 | 2776 | const full_abi_size = @intCast(u32, full_ty.abiSize(mod)); |
| 2781 | 2777 | |
| 2782 | 2778 | const splat_mcv = try self.genTypedValue(.{ .ty = full_ty, .val = splat_val }); |
| ... | ... | @@ -3587,7 +3583,7 @@ fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { |
| 3587 | 3583 | const result = result: { |
| 3588 | 3584 | const dst_ty = self.typeOfIndex(inst); |
| 3589 | 3585 | const src_ty = self.typeOf(ty_op.operand); |
| 3590 | const opt_ty = src_ty.childType(); | |
| 3586 | const opt_ty = src_ty.childType(mod); | |
| 3591 | 3587 | const src_mcv = try self.resolveInst(ty_op.operand); |
| 3592 | 3588 | |
| 3593 | 3589 | if (opt_ty.optionalReprIsPayload(mod)) { |
| ... | ... | @@ -3607,7 +3603,7 @@ fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { |
| 3607 | 3603 | else |
| 3608 | 3604 | try self.copyToRegisterWithInstTracking(inst, dst_ty, src_mcv); |
| 3609 | 3605 | |
| 3610 | const pl_ty = dst_ty.childType(); | |
| 3606 | const pl_ty = dst_ty.childType(mod); | |
| 3611 | 3607 | const pl_abi_size = @intCast(i32, pl_ty.abiSize(mod)); |
| 3612 | 3608 | try self.genSetMem(.{ .reg = dst_mcv.getReg().? }, pl_abi_size, Type.bool, .{ .immediate = 1 }); |
| 3613 | 3609 | break :result if (self.liveness.isUnused(inst)) .unreach else dst_mcv; |
| ... | ... | @@ -3737,7 +3733,7 @@ fn airUnwrapErrUnionErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 3737 | 3733 | const dst_lock = self.register_manager.lockRegAssumeUnused(dst_reg); |
| 3738 | 3734 | defer self.register_manager.unlockReg(dst_lock); |
| 3739 | 3735 | |
| 3740 | const eu_ty = src_ty.childType(); | |
| 3736 | const eu_ty = src_ty.childType(mod); | |
| 3741 | 3737 | const pl_ty = eu_ty.errorUnionPayload(); |
| 3742 | 3738 | const err_ty = eu_ty.errorUnionSet(); |
| 3743 | 3739 | const err_off = @intCast(i32, errUnionErrorOffset(pl_ty, mod)); |
| ... | ... | @@ -3777,7 +3773,7 @@ fn airUnwrapErrUnionPayloadPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 3777 | 3773 | const dst_lock = self.register_manager.lockReg(dst_reg); |
| 3778 | 3774 | defer if (dst_lock) |lock| self.register_manager.unlockReg(lock); |
| 3779 | 3775 | |
| 3780 | const eu_ty = src_ty.childType(); | |
| 3776 | const eu_ty = src_ty.childType(mod); | |
| 3781 | 3777 | const pl_ty = eu_ty.errorUnionPayload(); |
| 3782 | 3778 | const pl_off = @intCast(i32, errUnionPayloadOffset(pl_ty, mod)); |
| 3783 | 3779 | const dst_abi_size = @intCast(u32, dst_ty.abiSize(mod)); |
| ... | ... | @@ -3803,7 +3799,7 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void { |
| 3803 | 3799 | const src_lock = self.register_manager.lockRegAssumeUnused(src_reg); |
| 3804 | 3800 | defer self.register_manager.unlockReg(src_lock); |
| 3805 | 3801 | |
| 3806 | const eu_ty = src_ty.childType(); | |
| 3802 | const eu_ty = src_ty.childType(mod); | |
| 3807 | 3803 | const pl_ty = eu_ty.errorUnionPayload(); |
| 3808 | 3804 | const err_ty = eu_ty.errorUnionSet(); |
| 3809 | 3805 | const err_off = @intCast(i32, errUnionErrorOffset(pl_ty, mod)); |
| ... | ... | @@ -4057,7 +4053,7 @@ fn genSliceElemPtr(self: *Self, lhs: Air.Inst.Ref, rhs: Air.Inst.Ref) !MCValue { |
| 4057 | 4053 | }; |
| 4058 | 4054 | defer if (slice_mcv_lock) |lock| self.register_manager.unlockReg(lock); |
| 4059 | 4055 | |
| 4060 | const elem_ty = slice_ty.childType(); | |
| 4056 | const elem_ty = slice_ty.childType(mod); | |
| 4061 | 4057 | const elem_size = elem_ty.abiSize(mod); |
| 4062 | 4058 | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 4063 | 4059 | const slice_ptr_field_type = slice_ty.slicePtrFieldType(&buf); |
| ... | ... | @@ -4116,7 +4112,7 @@ fn airArrayElemVal(self: *Self, inst: Air.Inst.Index) !void { |
| 4116 | 4112 | }; |
| 4117 | 4113 | defer if (array_lock) |lock| self.register_manager.unlockReg(lock); |
| 4118 | 4114 | |
| 4119 | const elem_ty = array_ty.childType(); | |
| 4115 | const elem_ty = array_ty.childType(mod); | |
| 4120 | 4116 | const elem_abi_size = elem_ty.abiSize(mod); |
| 4121 | 4117 | |
| 4122 | 4118 | const index_ty = self.typeOf(bin_op.rhs); |
| ... | ... | @@ -4253,7 +4249,7 @@ fn airSetUnionTag(self: *Self, inst: Air.Inst.Index) !void { |
| 4253 | 4249 | const mod = self.bin_file.options.module.?; |
| 4254 | 4250 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 4255 | 4251 | const ptr_union_ty = self.typeOf(bin_op.lhs); |
| 4256 | const union_ty = ptr_union_ty.childType(); | |
| 4252 | const union_ty = ptr_union_ty.childType(mod); | |
| 4257 | 4253 | const tag_ty = self.typeOf(bin_op.rhs); |
| 4258 | 4254 | const layout = union_ty.unionGetLayout(mod); |
| 4259 | 4255 | |
| ... | ... | @@ -4287,7 +4283,9 @@ fn airSetUnionTag(self: *Self, inst: Air.Inst.Index) !void { |
| 4287 | 4283 | break :blk MCValue{ .register = reg }; |
| 4288 | 4284 | } else ptr; |
| 4289 | 4285 | |
| 4290 | var ptr_tag_pl = ptr_union_ty.ptrInfo(); | |
| 4286 | var ptr_tag_pl: Type.Payload.Pointer = .{ | |
| 4287 | .data = ptr_union_ty.ptrInfo(mod), | |
| 4288 | }; | |
| 4291 | 4289 | ptr_tag_pl.data.pointee_type = tag_ty; |
| 4292 | 4290 | const ptr_tag_ty = Type.initPayload(&ptr_tag_pl.base); |
| 4293 | 4291 | try self.store(ptr_tag_ty, adjusted_ptr, tag); |
| ... | ... | @@ -4924,14 +4922,11 @@ fn airFloatSign(self: *Self, inst: Air.Inst.Index) !void { |
| 4924 | 4922 | var stack align(@alignOf(ExpectedContents)) = |
| 4925 | 4923 | std.heap.stackFallback(@sizeOf(ExpectedContents), arena.allocator()); |
| 4926 | 4924 | |
| 4927 | var vec_pl = Type.Payload.Array{ | |
| 4928 | .base = .{ .tag = .vector }, | |
| 4929 | .data = .{ | |
| 4930 | .len = @divExact(abi_size * 8, scalar_bits), | |
| 4931 | .elem_type = try mod.intType(.signed, scalar_bits), | |
| 4932 | }, | |
| 4933 | }; | |
| 4934 | const vec_ty = Type.initPayload(&vec_pl.base); | |
| 4925 | const vec_ty = try mod.vectorType(.{ | |
| 4926 | .len = @divExact(abi_size * 8, scalar_bits), | |
| 4927 | .child = (try mod.intType(.signed, scalar_bits)).ip_index, | |
| 4928 | }); | |
| 4929 | ||
| 4935 | 4930 | const sign_val = switch (tag) { |
| 4936 | 4931 | .neg => try vec_ty.minInt(stack.get(), mod), |
| 4937 | 4932 | .fabs => try vec_ty.maxInt(stack.get(), mod), |
| ... | ... | @@ -5034,15 +5029,15 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: u4 |
| 5034 | 5029 | 16, 80, 128 => null, |
| 5035 | 5030 | else => unreachable, |
| 5036 | 5031 | }, |
| 5037 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 5038 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 5039 | 32 => switch (ty.vectorLen()) { | |
| 5032 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 5033 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 5034 | 32 => switch (ty.vectorLen(mod)) { | |
| 5040 | 5035 | 1 => if (self.hasFeature(.avx)) .{ .v_ss, .round } else .{ ._ss, .round }, |
| 5041 | 5036 | 2...4 => if (self.hasFeature(.avx)) .{ .v_ps, .round } else .{ ._ps, .round }, |
| 5042 | 5037 | 5...8 => if (self.hasFeature(.avx)) .{ .v_ps, .round } else null, |
| 5043 | 5038 | else => null, |
| 5044 | 5039 | }, |
| 5045 | 64 => switch (ty.vectorLen()) { | |
| 5040 | 64 => switch (ty.vectorLen(mod)) { | |
| 5046 | 5041 | 1 => if (self.hasFeature(.avx)) .{ .v_sd, .round } else .{ ._sd, .round }, |
| 5047 | 5042 | 2 => if (self.hasFeature(.avx)) .{ .v_pd, .round } else .{ ._pd, .round }, |
| 5048 | 5043 | 3...4 => if (self.hasFeature(.avx)) .{ .v_pd, .round } else null, |
| ... | ... | @@ -5131,9 +5126,9 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { |
| 5131 | 5126 | 80, 128 => null, |
| 5132 | 5127 | else => unreachable, |
| 5133 | 5128 | }, |
| 5134 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 5135 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 5136 | 16 => if (self.hasFeature(.f16c)) switch (ty.vectorLen()) { | |
| 5129 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 5130 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 5131 | 16 => if (self.hasFeature(.f16c)) switch (ty.vectorLen(mod)) { | |
| 5137 | 5132 | 1 => { |
| 5138 | 5133 | try self.asmRegisterRegister( |
| 5139 | 5134 | .{ .v_ps, .cvtph2 }, |
| ... | ... | @@ -5184,13 +5179,13 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void { |
| 5184 | 5179 | }, |
| 5185 | 5180 | else => null, |
| 5186 | 5181 | } else null, |
| 5187 | 32 => switch (ty.vectorLen()) { | |
| 5182 | 32 => switch (ty.vectorLen(mod)) { | |
| 5188 | 5183 | 1 => if (self.hasFeature(.avx)) .{ .v_ss, .sqrt } else .{ ._ss, .sqrt }, |
| 5189 | 5184 | 2...4 => if (self.hasFeature(.avx)) .{ .v_ps, .sqrt } else .{ ._ps, .sqrt }, |
| 5190 | 5185 | 5...8 => if (self.hasFeature(.avx)) .{ .v_ps, .sqrt } else null, |
| 5191 | 5186 | else => null, |
| 5192 | 5187 | }, |
| 5193 | 64 => switch (ty.vectorLen()) { | |
| 5188 | 64 => switch (ty.vectorLen(mod)) { | |
| 5194 | 5189 | 1 => if (self.hasFeature(.avx)) .{ .v_sd, .sqrt } else .{ ._sd, .sqrt }, |
| 5195 | 5190 | 2 => if (self.hasFeature(.avx)) .{ .v_pd, .sqrt } else .{ ._pd, .sqrt }, |
| 5196 | 5191 | 3...4 => if (self.hasFeature(.avx)) .{ .v_pd, .sqrt } else null, |
| ... | ... | @@ -5292,7 +5287,7 @@ fn reuseOperandAdvanced( |
| 5292 | 5287 | |
| 5293 | 5288 | fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerError!void { |
| 5294 | 5289 | const mod = self.bin_file.options.module.?; |
| 5295 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 5290 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 5296 | 5291 | |
| 5297 | 5292 | const val_ty = ptr_info.pointee_type; |
| 5298 | 5293 | const val_abi_size = @intCast(u32, val_ty.abiSize(mod)); |
| ... | ... | @@ -5365,7 +5360,8 @@ fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) Inn |
| 5365 | 5360 | } |
| 5366 | 5361 | |
| 5367 | 5362 | fn load(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) InnerError!void { |
| 5368 | const dst_ty = ptr_ty.childType(); | |
| 5363 | const mod = self.bin_file.options.module.?; | |
| 5364 | const dst_ty = ptr_ty.childType(mod); | |
| 5369 | 5365 | switch (ptr_mcv) { |
| 5370 | 5366 | .none, |
| 5371 | 5367 | .unreach, |
| ... | ... | @@ -5424,7 +5420,7 @@ fn airLoad(self: *Self, inst: Air.Inst.Index) !void { |
| 5424 | 5420 | else |
| 5425 | 5421 | try self.allocRegOrMem(inst, true); |
| 5426 | 5422 | |
| 5427 | if (ptr_ty.ptrInfo().data.host_size > 0) { | |
| 5423 | if (ptr_ty.ptrInfo(mod).host_size > 0) { | |
| 5428 | 5424 | try self.packedLoad(dst_mcv, ptr_ty, ptr_mcv); |
| 5429 | 5425 | } else { |
| 5430 | 5426 | try self.load(dst_mcv, ptr_ty, ptr_mcv); |
| ... | ... | @@ -5436,8 +5432,8 @@ fn airLoad(self: *Self, inst: Air.Inst.Index) !void { |
| 5436 | 5432 | |
| 5437 | 5433 | fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerError!void { |
| 5438 | 5434 | const mod = self.bin_file.options.module.?; |
| 5439 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 5440 | const src_ty = ptr_ty.childType(); | |
| 5435 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 5436 | const src_ty = ptr_ty.childType(mod); | |
| 5441 | 5437 | |
| 5442 | 5438 | const limb_abi_size: u16 = @min(ptr_info.host_size, 8); |
| 5443 | 5439 | const limb_abi_bits = limb_abi_size * 8; |
| ... | ... | @@ -5509,7 +5505,8 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In |
| 5509 | 5505 | } |
| 5510 | 5506 | |
| 5511 | 5507 | fn store(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerError!void { |
| 5512 | const src_ty = ptr_ty.childType(); | |
| 5508 | const mod = self.bin_file.options.module.?; | |
| 5509 | const src_ty = ptr_ty.childType(mod); | |
| 5513 | 5510 | switch (ptr_mcv) { |
| 5514 | 5511 | .none, |
| 5515 | 5512 | .unreach, |
| ... | ... | @@ -5544,6 +5541,7 @@ fn store(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) InnerErr |
| 5544 | 5541 | } |
| 5545 | 5542 | |
| 5546 | 5543 | fn airStore(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 5544 | const mod = self.bin_file.options.module.?; | |
| 5547 | 5545 | if (safety) { |
| 5548 | 5546 | // TODO if the value is undef, write 0xaa bytes to dest |
| 5549 | 5547 | } else { |
| ... | ... | @@ -5553,7 +5551,7 @@ fn airStore(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 5553 | 5551 | const ptr_mcv = try self.resolveInst(bin_op.lhs); |
| 5554 | 5552 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 5555 | 5553 | const src_mcv = try self.resolveInst(bin_op.rhs); |
| 5556 | if (ptr_ty.ptrInfo().data.host_size > 0) { | |
| 5554 | if (ptr_ty.ptrInfo(mod).host_size > 0) { | |
| 5557 | 5555 | try self.packedStore(ptr_ty, ptr_mcv, src_mcv); |
| 5558 | 5556 | } else { |
| 5559 | 5557 | try self.store(ptr_ty, ptr_mcv, src_mcv); |
| ... | ... | @@ -5578,11 +5576,11 @@ fn fieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, index: u32 |
| 5578 | 5576 | const mod = self.bin_file.options.module.?; |
| 5579 | 5577 | const ptr_field_ty = self.typeOfIndex(inst); |
| 5580 | 5578 | const ptr_container_ty = self.typeOf(operand); |
| 5581 | const container_ty = ptr_container_ty.childType(); | |
| 5579 | const container_ty = ptr_container_ty.childType(mod); | |
| 5582 | 5580 | const field_offset = @intCast(i32, switch (container_ty.containerLayout()) { |
| 5583 | 5581 | .Auto, .Extern => container_ty.structFieldOffset(index, mod), |
| 5584 | 5582 | .Packed => if (container_ty.zigTypeTag(mod) == .Struct and |
| 5585 | ptr_field_ty.ptrInfo().data.host_size == 0) | |
| 5583 | ptr_field_ty.ptrInfo(mod).host_size == 0) | |
| 5586 | 5584 | container_ty.packedStructFieldByteOffset(index, mod) |
| 5587 | 5585 | else |
| 5588 | 5586 | 0, |
| ... | ... | @@ -5760,7 +5758,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 5760 | 5758 | const extra = self.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; |
| 5761 | 5759 | |
| 5762 | 5760 | const inst_ty = self.typeOfIndex(inst); |
| 5763 | const parent_ty = inst_ty.childType(); | |
| 5761 | const parent_ty = inst_ty.childType(mod); | |
| 5764 | 5762 | const field_offset = @intCast(i32, parent_ty.structFieldOffset(extra.field_index, mod)); |
| 5765 | 5763 | |
| 5766 | 5764 | const src_mcv = try self.resolveInst(extra.field_ptr); |
| ... | ... | @@ -6680,10 +6678,10 @@ fn genBinOp( |
| 6680 | 6678 | 80, 128 => null, |
| 6681 | 6679 | else => unreachable, |
| 6682 | 6680 | }, |
| 6683 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 6681 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 6684 | 6682 | else => null, |
| 6685 | .Int => switch (lhs_ty.childType().intInfo(mod).bits) { | |
| 6686 | 8 => switch (lhs_ty.vectorLen()) { | |
| 6683 | .Int => switch (lhs_ty.childType(mod).intInfo(mod).bits) { | |
| 6684 | 8 => switch (lhs_ty.vectorLen(mod)) { | |
| 6687 | 6685 | 1...16 => switch (air_tag) { |
| 6688 | 6686 | .add, |
| 6689 | 6687 | .addwrap, |
| ... | ... | @@ -6694,7 +6692,7 @@ fn genBinOp( |
| 6694 | 6692 | .bit_and => if (self.hasFeature(.avx)) .{ .vp_, .@"and" } else .{ .p_, .@"and" }, |
| 6695 | 6693 | .bit_or => if (self.hasFeature(.avx)) .{ .vp_, .@"or" } else .{ .p_, .@"or" }, |
| 6696 | 6694 | .xor => if (self.hasFeature(.avx)) .{ .vp_, .xor } else .{ .p_, .xor }, |
| 6697 | .min => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6695 | .min => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6698 | 6696 | .signed => if (self.hasFeature(.avx)) |
| 6699 | 6697 | .{ .vp_b, .mins } |
| 6700 | 6698 | else if (self.hasFeature(.sse4_1)) |
| ... | ... | @@ -6708,7 +6706,7 @@ fn genBinOp( |
| 6708 | 6706 | else |
| 6709 | 6707 | null, |
| 6710 | 6708 | }, |
| 6711 | .max => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6709 | .max => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6712 | 6710 | .signed => if (self.hasFeature(.avx)) |
| 6713 | 6711 | .{ .vp_b, .maxs } |
| 6714 | 6712 | else if (self.hasFeature(.sse4_1)) |
| ... | ... | @@ -6734,11 +6732,11 @@ fn genBinOp( |
| 6734 | 6732 | .bit_and => if (self.hasFeature(.avx2)) .{ .vp_, .@"and" } else null, |
| 6735 | 6733 | .bit_or => if (self.hasFeature(.avx2)) .{ .vp_, .@"or" } else null, |
| 6736 | 6734 | .xor => if (self.hasFeature(.avx2)) .{ .vp_, .xor } else null, |
| 6737 | .min => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6735 | .min => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6738 | 6736 | .signed => if (self.hasFeature(.avx2)) .{ .vp_b, .mins } else null, |
| 6739 | 6737 | .unsigned => if (self.hasFeature(.avx)) .{ .vp_b, .minu } else null, |
| 6740 | 6738 | }, |
| 6741 | .max => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6739 | .max => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6742 | 6740 | .signed => if (self.hasFeature(.avx2)) .{ .vp_b, .maxs } else null, |
| 6743 | 6741 | .unsigned => if (self.hasFeature(.avx2)) .{ .vp_b, .maxu } else null, |
| 6744 | 6742 | }, |
| ... | ... | @@ -6746,7 +6744,7 @@ fn genBinOp( |
| 6746 | 6744 | }, |
| 6747 | 6745 | else => null, |
| 6748 | 6746 | }, |
| 6749 | 16 => switch (lhs_ty.vectorLen()) { | |
| 6747 | 16 => switch (lhs_ty.vectorLen(mod)) { | |
| 6750 | 6748 | 1...8 => switch (air_tag) { |
| 6751 | 6749 | .add, |
| 6752 | 6750 | .addwrap, |
| ... | ... | @@ -6760,7 +6758,7 @@ fn genBinOp( |
| 6760 | 6758 | .bit_and => if (self.hasFeature(.avx)) .{ .vp_, .@"and" } else .{ .p_, .@"and" }, |
| 6761 | 6759 | .bit_or => if (self.hasFeature(.avx)) .{ .vp_, .@"or" } else .{ .p_, .@"or" }, |
| 6762 | 6760 | .xor => if (self.hasFeature(.avx)) .{ .vp_, .xor } else .{ .p_, .xor }, |
| 6763 | .min => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6761 | .min => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6764 | 6762 | .signed => if (self.hasFeature(.avx)) |
| 6765 | 6763 | .{ .vp_w, .mins } |
| 6766 | 6764 | else |
| ... | ... | @@ -6770,7 +6768,7 @@ fn genBinOp( |
| 6770 | 6768 | else |
| 6771 | 6769 | .{ .p_w, .minu }, |
| 6772 | 6770 | }, |
| 6773 | .max => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6771 | .max => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6774 | 6772 | .signed => if (self.hasFeature(.avx)) |
| 6775 | 6773 | .{ .vp_w, .maxs } |
| 6776 | 6774 | else |
| ... | ... | @@ -6795,11 +6793,11 @@ fn genBinOp( |
| 6795 | 6793 | .bit_and => if (self.hasFeature(.avx2)) .{ .vp_, .@"and" } else null, |
| 6796 | 6794 | .bit_or => if (self.hasFeature(.avx2)) .{ .vp_, .@"or" } else null, |
| 6797 | 6795 | .xor => if (self.hasFeature(.avx2)) .{ .vp_, .xor } else null, |
| 6798 | .min => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6796 | .min => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6799 | 6797 | .signed => if (self.hasFeature(.avx2)) .{ .vp_w, .mins } else null, |
| 6800 | 6798 | .unsigned => if (self.hasFeature(.avx)) .{ .vp_w, .minu } else null, |
| 6801 | 6799 | }, |
| 6802 | .max => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6800 | .max => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6803 | 6801 | .signed => if (self.hasFeature(.avx2)) .{ .vp_w, .maxs } else null, |
| 6804 | 6802 | .unsigned => if (self.hasFeature(.avx2)) .{ .vp_w, .maxu } else null, |
| 6805 | 6803 | }, |
| ... | ... | @@ -6807,7 +6805,7 @@ fn genBinOp( |
| 6807 | 6805 | }, |
| 6808 | 6806 | else => null, |
| 6809 | 6807 | }, |
| 6810 | 32 => switch (lhs_ty.vectorLen()) { | |
| 6808 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 6811 | 6809 | 1...4 => switch (air_tag) { |
| 6812 | 6810 | .add, |
| 6813 | 6811 | .addwrap, |
| ... | ... | @@ -6826,7 +6824,7 @@ fn genBinOp( |
| 6826 | 6824 | .bit_and => if (self.hasFeature(.avx)) .{ .vp_, .@"and" } else .{ .p_, .@"and" }, |
| 6827 | 6825 | .bit_or => if (self.hasFeature(.avx)) .{ .vp_, .@"or" } else .{ .p_, .@"or" }, |
| 6828 | 6826 | .xor => if (self.hasFeature(.avx)) .{ .vp_, .xor } else .{ .p_, .xor }, |
| 6829 | .min => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6827 | .min => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6830 | 6828 | .signed => if (self.hasFeature(.avx)) |
| 6831 | 6829 | .{ .vp_d, .mins } |
| 6832 | 6830 | else if (self.hasFeature(.sse4_1)) |
| ... | ... | @@ -6840,7 +6838,7 @@ fn genBinOp( |
| 6840 | 6838 | else |
| 6841 | 6839 | null, |
| 6842 | 6840 | }, |
| 6843 | .max => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6841 | .max => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6844 | 6842 | .signed => if (self.hasFeature(.avx)) |
| 6845 | 6843 | .{ .vp_d, .maxs } |
| 6846 | 6844 | else if (self.hasFeature(.sse4_1)) |
| ... | ... | @@ -6869,11 +6867,11 @@ fn genBinOp( |
| 6869 | 6867 | .bit_and => if (self.hasFeature(.avx2)) .{ .vp_, .@"and" } else null, |
| 6870 | 6868 | .bit_or => if (self.hasFeature(.avx2)) .{ .vp_, .@"or" } else null, |
| 6871 | 6869 | .xor => if (self.hasFeature(.avx2)) .{ .vp_, .xor } else null, |
| 6872 | .min => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6870 | .min => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6873 | 6871 | .signed => if (self.hasFeature(.avx2)) .{ .vp_d, .mins } else null, |
| 6874 | 6872 | .unsigned => if (self.hasFeature(.avx)) .{ .vp_d, .minu } else null, |
| 6875 | 6873 | }, |
| 6876 | .max => switch (lhs_ty.childType().intInfo(mod).signedness) { | |
| 6874 | .max => switch (lhs_ty.childType(mod).intInfo(mod).signedness) { | |
| 6877 | 6875 | .signed => if (self.hasFeature(.avx2)) .{ .vp_d, .maxs } else null, |
| 6878 | 6876 | .unsigned => if (self.hasFeature(.avx2)) .{ .vp_d, .maxu } else null, |
| 6879 | 6877 | }, |
| ... | ... | @@ -6881,7 +6879,7 @@ fn genBinOp( |
| 6881 | 6879 | }, |
| 6882 | 6880 | else => null, |
| 6883 | 6881 | }, |
| 6884 | 64 => switch (lhs_ty.vectorLen()) { | |
| 6882 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 6885 | 6883 | 1...2 => switch (air_tag) { |
| 6886 | 6884 | .add, |
| 6887 | 6885 | .addwrap, |
| ... | ... | @@ -6910,8 +6908,8 @@ fn genBinOp( |
| 6910 | 6908 | }, |
| 6911 | 6909 | else => null, |
| 6912 | 6910 | }, |
| 6913 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 6914 | 16 => if (self.hasFeature(.f16c)) switch (lhs_ty.vectorLen()) { | |
| 6911 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 6912 | 16 => if (self.hasFeature(.f16c)) switch (lhs_ty.vectorLen(mod)) { | |
| 6915 | 6913 | 1 => { |
| 6916 | 6914 | const tmp_reg = (try self.register_manager.allocReg(null, sse)).to128(); |
| 6917 | 6915 | const tmp_lock = self.register_manager.lockRegAssumeUnused(tmp_reg); |
| ... | ... | @@ -7086,7 +7084,7 @@ fn genBinOp( |
| 7086 | 7084 | }, |
| 7087 | 7085 | else => null, |
| 7088 | 7086 | } else null, |
| 7089 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7087 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7090 | 7088 | 1 => switch (air_tag) { |
| 7091 | 7089 | .add => if (self.hasFeature(.avx)) .{ .v_ss, .add } else .{ ._ss, .add }, |
| 7092 | 7090 | .sub => if (self.hasFeature(.avx)) .{ .v_ss, .sub } else .{ ._ss, .sub }, |
| ... | ... | @@ -7124,7 +7122,7 @@ fn genBinOp( |
| 7124 | 7122 | } else null, |
| 7125 | 7123 | else => null, |
| 7126 | 7124 | }, |
| 7127 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7125 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7128 | 7126 | 1 => switch (air_tag) { |
| 7129 | 7127 | .add => if (self.hasFeature(.avx)) .{ .v_sd, .add } else .{ ._sd, .add }, |
| 7130 | 7128 | .sub => if (self.hasFeature(.avx)) .{ .v_sd, .sub } else .{ ._sd, .sub }, |
| ... | ... | @@ -7236,14 +7234,14 @@ fn genBinOp( |
| 7236 | 7234 | 16, 80, 128 => null, |
| 7237 | 7235 | else => unreachable, |
| 7238 | 7236 | }, |
| 7239 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7240 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7241 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7237 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7238 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7239 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7242 | 7240 | 1 => .{ .v_ss, .cmp }, |
| 7243 | 7241 | 2...8 => .{ .v_ps, .cmp }, |
| 7244 | 7242 | else => null, |
| 7245 | 7243 | }, |
| 7246 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7244 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7247 | 7245 | 1 => .{ .v_sd, .cmp }, |
| 7248 | 7246 | 2...4 => .{ .v_pd, .cmp }, |
| 7249 | 7247 | else => null, |
| ... | ... | @@ -7270,13 +7268,13 @@ fn genBinOp( |
| 7270 | 7268 | 16, 80, 128 => null, |
| 7271 | 7269 | else => unreachable, |
| 7272 | 7270 | }, |
| 7273 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7274 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7275 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7271 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7272 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7273 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7276 | 7274 | 1...8 => .{ .v_ps, .blendv }, |
| 7277 | 7275 | else => null, |
| 7278 | 7276 | }, |
| 7279 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7277 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7280 | 7278 | 1...4 => .{ .v_pd, .blendv }, |
| 7281 | 7279 | else => null, |
| 7282 | 7280 | }, |
| ... | ... | @@ -7304,14 +7302,14 @@ fn genBinOp( |
| 7304 | 7302 | 16, 80, 128 => null, |
| 7305 | 7303 | else => unreachable, |
| 7306 | 7304 | }, |
| 7307 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7308 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7309 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7305 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7306 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7307 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7310 | 7308 | 1 => .{ ._ss, .cmp }, |
| 7311 | 7309 | 2...4 => .{ ._ps, .cmp }, |
| 7312 | 7310 | else => null, |
| 7313 | 7311 | }, |
| 7314 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7312 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7315 | 7313 | 1 => .{ ._sd, .cmp }, |
| 7316 | 7314 | 2 => .{ ._pd, .cmp }, |
| 7317 | 7315 | else => null, |
| ... | ... | @@ -7337,13 +7335,13 @@ fn genBinOp( |
| 7337 | 7335 | 16, 80, 128 => null, |
| 7338 | 7336 | else => unreachable, |
| 7339 | 7337 | }, |
| 7340 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7341 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7342 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7338 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7339 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7340 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7343 | 7341 | 1...4 => .{ ._ps, .blendv }, |
| 7344 | 7342 | else => null, |
| 7345 | 7343 | }, |
| 7346 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7344 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7347 | 7345 | 1...2 => .{ ._pd, .blendv }, |
| 7348 | 7346 | else => null, |
| 7349 | 7347 | }, |
| ... | ... | @@ -7368,13 +7366,13 @@ fn genBinOp( |
| 7368 | 7366 | 16, 80, 128 => null, |
| 7369 | 7367 | else => unreachable, |
| 7370 | 7368 | }, |
| 7371 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7372 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7373 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7369 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7370 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7371 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7374 | 7372 | 1...4 => .{ ._ps, .@"and" }, |
| 7375 | 7373 | else => null, |
| 7376 | 7374 | }, |
| 7377 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7375 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7378 | 7376 | 1...2 => .{ ._pd, .@"and" }, |
| 7379 | 7377 | else => null, |
| 7380 | 7378 | }, |
| ... | ... | @@ -7398,13 +7396,13 @@ fn genBinOp( |
| 7398 | 7396 | 16, 80, 128 => null, |
| 7399 | 7397 | else => unreachable, |
| 7400 | 7398 | }, |
| 7401 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7402 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7403 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7399 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7400 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7401 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7404 | 7402 | 1...4 => .{ ._ps, .andn }, |
| 7405 | 7403 | else => null, |
| 7406 | 7404 | }, |
| 7407 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7405 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7408 | 7406 | 1...2 => .{ ._pd, .andn }, |
| 7409 | 7407 | else => null, |
| 7410 | 7408 | }, |
| ... | ... | @@ -7428,13 +7426,13 @@ fn genBinOp( |
| 7428 | 7426 | 16, 80, 128 => null, |
| 7429 | 7427 | else => unreachable, |
| 7430 | 7428 | }, |
| 7431 | .Vector => switch (lhs_ty.childType().zigTypeTag(mod)) { | |
| 7432 | .Float => switch (lhs_ty.childType().floatBits(self.target.*)) { | |
| 7433 | 32 => switch (lhs_ty.vectorLen()) { | |
| 7429 | .Vector => switch (lhs_ty.childType(mod).zigTypeTag(mod)) { | |
| 7430 | .Float => switch (lhs_ty.childType(mod).floatBits(self.target.*)) { | |
| 7431 | 32 => switch (lhs_ty.vectorLen(mod)) { | |
| 7434 | 7432 | 1...4 => .{ ._ps, .@"or" }, |
| 7435 | 7433 | else => null, |
| 7436 | 7434 | }, |
| 7437 | 64 => switch (lhs_ty.vectorLen()) { | |
| 7435 | 64 => switch (lhs_ty.vectorLen(mod)) { | |
| 7438 | 7436 | 1...2 => .{ ._pd, .@"or" }, |
| 7439 | 7437 | else => null, |
| 7440 | 7438 | }, |
| ... | ... | @@ -7586,11 +7584,7 @@ fn genBinOpMir( |
| 7586 | 7584 | .load_got, |
| 7587 | 7585 | .load_tlv, |
| 7588 | 7586 | => { |
| 7589 | var ptr_pl = Type.Payload.ElemType{ | |
| 7590 | .base = .{ .tag = .single_const_pointer }, | |
| 7591 | .data = ty, | |
| 7592 | }; | |
| 7593 | const ptr_ty = Type.initPayload(&ptr_pl.base); | |
| 7587 | const ptr_ty = try mod.singleConstPtrType(ty); | |
| 7594 | 7588 | const addr_reg = try self.copyToTmpRegister(ptr_ty, src_mcv.address()); |
| 7595 | 7589 | return self.genBinOpMir(mir_tag, ty, dst_mcv, .{ |
| 7596 | 7590 | .indirect = .{ .reg = addr_reg }, |
| ... | ... | @@ -8058,7 +8052,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier |
| 8058 | 8052 | |
| 8059 | 8053 | const fn_ty = switch (ty.zigTypeTag(mod)) { |
| 8060 | 8054 | .Fn => ty, |
| 8061 | .Pointer => ty.childType(), | |
| 8055 | .Pointer => ty.childType(mod), | |
| 8062 | 8056 | else => unreachable, |
| 8063 | 8057 | }; |
| 8064 | 8058 | |
| ... | ... | @@ -8506,10 +8500,11 @@ fn airTry(self: *Self, inst: Air.Inst.Index) !void { |
| 8506 | 8500 | } |
| 8507 | 8501 | |
| 8508 | 8502 | fn airTryPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 8503 | const mod = self.bin_file.options.module.?; | |
| 8509 | 8504 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 8510 | 8505 | const extra = self.air.extraData(Air.TryPtr, ty_pl.payload); |
| 8511 | 8506 | const body = self.air.extra[extra.end..][0..extra.data.body_len]; |
| 8512 | const err_union_ty = self.typeOf(extra.data.ptr).childType(); | |
| 8507 | const err_union_ty = self.typeOf(extra.data.ptr).childType(mod); | |
| 8513 | 8508 | const result = try self.genTry(inst, extra.data.ptr, body, err_union_ty, true); |
| 8514 | 8509 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 8515 | 8510 | } |
| ... | ... | @@ -8683,8 +8678,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC |
| 8683 | 8678 | try self.spillEflagsIfOccupied(); |
| 8684 | 8679 | self.eflags_inst = inst; |
| 8685 | 8680 | |
| 8686 | var pl_buf: Type.Payload.ElemType = undefined; | |
| 8687 | const pl_ty = opt_ty.optionalChild(&pl_buf); | |
| 8681 | const pl_ty = opt_ty.optionalChild(mod); | |
| 8688 | 8682 | |
| 8689 | 8683 | var ptr_buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 8690 | 8684 | const some_info: struct { off: i32, ty: Type } = if (opt_ty.optionalReprIsPayload(mod)) |
| ... | ... | @@ -8775,9 +8769,8 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue) |
| 8775 | 8769 | try self.spillEflagsIfOccupied(); |
| 8776 | 8770 | self.eflags_inst = inst; |
| 8777 | 8771 | |
| 8778 | const opt_ty = ptr_ty.childType(); | |
| 8779 | var pl_buf: Type.Payload.ElemType = undefined; | |
| 8780 | const pl_ty = opt_ty.optionalChild(&pl_buf); | |
| 8772 | const opt_ty = ptr_ty.childType(mod); | |
| 8773 | const pl_ty = opt_ty.optionalChild(mod); | |
| 8781 | 8774 | |
| 8782 | 8775 | var ptr_buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 8783 | 8776 | const some_info: struct { off: i32, ty: Type } = if (opt_ty.optionalReprIsPayload(mod)) |
| ... | ... | @@ -8919,6 +8912,7 @@ fn airIsErr(self: *Self, inst: Air.Inst.Index) !void { |
| 8919 | 8912 | } |
| 8920 | 8913 | |
| 8921 | 8914 | fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 8915 | const mod = self.bin_file.options.module.?; | |
| 8922 | 8916 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 8923 | 8917 | |
| 8924 | 8918 | const operand_ptr = try self.resolveInst(un_op); |
| ... | ... | @@ -8939,7 +8933,7 @@ fn airIsErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 8939 | 8933 | const ptr_ty = self.typeOf(un_op); |
| 8940 | 8934 | try self.load(operand, ptr_ty, operand_ptr); |
| 8941 | 8935 | |
| 8942 | const result = try self.isErr(inst, ptr_ty.childType(), operand); | |
| 8936 | const result = try self.isErr(inst, ptr_ty.childType(mod), operand); | |
| 8943 | 8937 | |
| 8944 | 8938 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 8945 | 8939 | } |
| ... | ... | @@ -8953,6 +8947,7 @@ fn airIsNonErr(self: *Self, inst: Air.Inst.Index) !void { |
| 8953 | 8947 | } |
| 8954 | 8948 | |
| 8955 | 8949 | fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 8950 | const mod = self.bin_file.options.module.?; | |
| 8956 | 8951 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 8957 | 8952 | |
| 8958 | 8953 | const operand_ptr = try self.resolveInst(un_op); |
| ... | ... | @@ -8973,7 +8968,7 @@ fn airIsNonErrPtr(self: *Self, inst: Air.Inst.Index) !void { |
| 8973 | 8968 | const ptr_ty = self.typeOf(un_op); |
| 8974 | 8969 | try self.load(operand, ptr_ty, operand_ptr); |
| 8975 | 8970 | |
| 8976 | const result = try self.isNonErr(inst, ptr_ty.childType(), operand); | |
| 8971 | const result = try self.isNonErr(inst, ptr_ty.childType(mod), operand); | |
| 8977 | 8972 | |
| 8978 | 8973 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 8979 | 8974 | } |
| ... | ... | @@ -9452,9 +9447,9 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9452 | 9447 | else if (aligned) .{ ._, .movdqa } else .{ ._, .movdqu } }, |
| 9453 | 9448 | else => {}, |
| 9454 | 9449 | }, |
| 9455 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 9456 | .Int => switch (ty.childType().intInfo(mod).bits) { | |
| 9457 | 8 => switch (ty.vectorLen()) { | |
| 9450 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 9451 | .Int => switch (ty.childType(mod).intInfo(mod).bits) { | |
| 9452 | 8 => switch (ty.vectorLen(mod)) { | |
| 9458 | 9453 | 1 => if (self.hasFeature(.avx)) return .{ .vex_insert_extract = .{ |
| 9459 | 9454 | .insert = .{ .vp_b, .insr }, |
| 9460 | 9455 | .extract = .{ .vp_b, .extr }, |
| ... | ... | @@ -9484,7 +9479,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9484 | 9479 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9485 | 9480 | else => {}, |
| 9486 | 9481 | }, |
| 9487 | 16 => switch (ty.vectorLen()) { | |
| 9482 | 16 => switch (ty.vectorLen(mod)) { | |
| 9488 | 9483 | 1 => return if (self.hasFeature(.avx)) .{ .vex_insert_extract = .{ |
| 9489 | 9484 | .insert = .{ .vp_w, .insr }, |
| 9490 | 9485 | .extract = .{ .vp_w, .extr }, |
| ... | ... | @@ -9507,7 +9502,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9507 | 9502 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9508 | 9503 | else => {}, |
| 9509 | 9504 | }, |
| 9510 | 32 => switch (ty.vectorLen()) { | |
| 9505 | 32 => switch (ty.vectorLen(mod)) { | |
| 9511 | 9506 | 1 => return .{ .move = if (self.hasFeature(.avx)) |
| 9512 | 9507 | .{ .v_d, .mov } |
| 9513 | 9508 | else |
| ... | ... | @@ -9523,7 +9518,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9523 | 9518 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9524 | 9519 | else => {}, |
| 9525 | 9520 | }, |
| 9526 | 64 => switch (ty.vectorLen()) { | |
| 9521 | 64 => switch (ty.vectorLen(mod)) { | |
| 9527 | 9522 | 1 => return .{ .move = if (self.hasFeature(.avx)) |
| 9528 | 9523 | .{ .v_q, .mov } |
| 9529 | 9524 | else |
| ... | ... | @@ -9535,7 +9530,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9535 | 9530 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9536 | 9531 | else => {}, |
| 9537 | 9532 | }, |
| 9538 | 128 => switch (ty.vectorLen()) { | |
| 9533 | 128 => switch (ty.vectorLen(mod)) { | |
| 9539 | 9534 | 1 => return .{ .move = if (self.hasFeature(.avx)) |
| 9540 | 9535 | if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } |
| 9541 | 9536 | else if (aligned) .{ ._, .movdqa } else .{ ._, .movdqu } }, |
| ... | ... | @@ -9543,15 +9538,15 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9543 | 9538 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9544 | 9539 | else => {}, |
| 9545 | 9540 | }, |
| 9546 | 256 => switch (ty.vectorLen()) { | |
| 9541 | 256 => switch (ty.vectorLen(mod)) { | |
| 9547 | 9542 | 1 => if (self.hasFeature(.avx)) |
| 9548 | 9543 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9549 | 9544 | else => {}, |
| 9550 | 9545 | }, |
| 9551 | 9546 | else => {}, |
| 9552 | 9547 | }, |
| 9553 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 9554 | 16 => switch (ty.vectorLen()) { | |
| 9548 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 9549 | 16 => switch (ty.vectorLen(mod)) { | |
| 9555 | 9550 | 1 => return if (self.hasFeature(.avx)) .{ .vex_insert_extract = .{ |
| 9556 | 9551 | .insert = .{ .vp_w, .insr }, |
| 9557 | 9552 | .extract = .{ .vp_w, .extr }, |
| ... | ... | @@ -9574,7 +9569,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9574 | 9569 | return .{ .move = if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } }, |
| 9575 | 9570 | else => {}, |
| 9576 | 9571 | }, |
| 9577 | 32 => switch (ty.vectorLen()) { | |
| 9572 | 32 => switch (ty.vectorLen(mod)) { | |
| 9578 | 9573 | 1 => return .{ .move = if (self.hasFeature(.avx)) |
| 9579 | 9574 | .{ .v_ss, .mov } |
| 9580 | 9575 | else |
| ... | ... | @@ -9590,7 +9585,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9590 | 9585 | return .{ .move = if (aligned) .{ .v_ps, .mova } else .{ .v_ps, .movu } }, |
| 9591 | 9586 | else => {}, |
| 9592 | 9587 | }, |
| 9593 | 64 => switch (ty.vectorLen()) { | |
| 9588 | 64 => switch (ty.vectorLen(mod)) { | |
| 9594 | 9589 | 1 => return .{ .move = if (self.hasFeature(.avx)) |
| 9595 | 9590 | .{ .v_sd, .mov } |
| 9596 | 9591 | else |
| ... | ... | @@ -9602,7 +9597,7 @@ fn moveStrategy(self: *Self, ty: Type, aligned: bool) !MoveStrategy { |
| 9602 | 9597 | return .{ .move = if (aligned) .{ .v_pd, .mova } else .{ .v_pd, .movu } }, |
| 9603 | 9598 | else => {}, |
| 9604 | 9599 | }, |
| 9605 | 128 => switch (ty.vectorLen()) { | |
| 9600 | 128 => switch (ty.vectorLen(mod)) { | |
| 9606 | 9601 | 1 => return .{ .move = if (self.hasFeature(.avx)) |
| 9607 | 9602 | if (aligned) .{ .v_, .movdqa } else .{ .v_, .movdqu } |
| 9608 | 9603 | else if (aligned) .{ ._, .movdqa } else .{ ._, .movdqu } }, |
| ... | ... | @@ -10248,8 +10243,8 @@ fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void { |
| 10248 | 10243 | const slice_ty = self.typeOfIndex(inst); |
| 10249 | 10244 | const ptr_ty = self.typeOf(ty_op.operand); |
| 10250 | 10245 | const ptr = try self.resolveInst(ty_op.operand); |
| 10251 | const array_ty = ptr_ty.childType(); | |
| 10252 | const array_len = array_ty.arrayLen(); | |
| 10246 | const array_ty = ptr_ty.childType(mod); | |
| 10247 | const array_len = array_ty.arrayLen(mod); | |
| 10253 | 10248 | |
| 10254 | 10249 | const frame_index = try self.allocFrameIndex(FrameAlloc.initType(slice_ty, mod)); |
| 10255 | 10250 | try self.genSetMem(.{ .frame = frame_index }, 0, ptr_ty, ptr); |
| ... | ... | @@ -10790,16 +10785,16 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 10790 | 10785 | const elem_abi_size = @intCast(u31, elem_ty.abiSize(mod)); |
| 10791 | 10786 | |
| 10792 | 10787 | if (elem_abi_size == 1) { |
| 10793 | const ptr: MCValue = switch (dst_ptr_ty.ptrSize()) { | |
| 10788 | const ptr: MCValue = switch (dst_ptr_ty.ptrSize(mod)) { | |
| 10794 | 10789 | // TODO: this only handles slices stored in the stack |
| 10795 | 10790 | .Slice => dst_ptr, |
| 10796 | 10791 | .One => dst_ptr, |
| 10797 | 10792 | .C, .Many => unreachable, |
| 10798 | 10793 | }; |
| 10799 | const len: MCValue = switch (dst_ptr_ty.ptrSize()) { | |
| 10794 | const len: MCValue = switch (dst_ptr_ty.ptrSize(mod)) { | |
| 10800 | 10795 | // TODO: this only handles slices stored in the stack |
| 10801 | 10796 | .Slice => dst_ptr.address().offset(8).deref(), |
| 10802 | .One => .{ .immediate = dst_ptr_ty.childType().arrayLen() }, | |
| 10797 | .One => .{ .immediate = dst_ptr_ty.childType(mod).arrayLen(mod) }, | |
| 10803 | 10798 | .C, .Many => unreachable, |
| 10804 | 10799 | }; |
| 10805 | 10800 | const len_lock: ?RegisterLock = switch (len) { |
| ... | ... | @@ -10815,7 +10810,7 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 10815 | 10810 | // Store the first element, and then rely on memcpy copying forwards. |
| 10816 | 10811 | // Length zero requires a runtime check - so we handle arrays specially |
| 10817 | 10812 | // here to elide it. |
| 10818 | switch (dst_ptr_ty.ptrSize()) { | |
| 10813 | switch (dst_ptr_ty.ptrSize(mod)) { | |
| 10819 | 10814 | .Slice => { |
| 10820 | 10815 | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 10821 | 10816 | const slice_ptr_ty = dst_ptr_ty.slicePtrFieldType(&buf); |
| ... | ... | @@ -10858,13 +10853,9 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 10858 | 10853 | try self.performReloc(skip_reloc); |
| 10859 | 10854 | }, |
| 10860 | 10855 | .One => { |
| 10861 | var elem_ptr_pl = Type.Payload.ElemType{ | |
| 10862 | .base = .{ .tag = .single_mut_pointer }, | |
| 10863 | .data = elem_ty, | |
| 10864 | }; | |
| 10865 | const elem_ptr_ty = Type.initPayload(&elem_ptr_pl.base); | |
| 10856 | const elem_ptr_ty = try mod.singleMutPtrType(elem_ty); | |
| 10866 | 10857 | |
| 10867 | const len = dst_ptr_ty.childType().arrayLen(); | |
| 10858 | const len = dst_ptr_ty.childType(mod).arrayLen(mod); | |
| 10868 | 10859 | |
| 10869 | 10860 | assert(len != 0); // prevented by Sema |
| 10870 | 10861 | try self.store(elem_ptr_ty, dst_ptr, src_val); |
| ... | ... | @@ -10889,6 +10880,7 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void { |
| 10889 | 10880 | } |
| 10890 | 10881 | |
| 10891 | 10882 | fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { |
| 10883 | const mod = self.bin_file.options.module.?; | |
| 10892 | 10884 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 10893 | 10885 | |
| 10894 | 10886 | const dst_ptr = try self.resolveInst(bin_op.lhs); |
| ... | ... | @@ -10906,9 +10898,9 @@ fn airMemcpy(self: *Self, inst: Air.Inst.Index) !void { |
| 10906 | 10898 | }; |
| 10907 | 10899 | defer if (src_ptr_lock) |lock| self.register_manager.unlockReg(lock); |
| 10908 | 10900 | |
| 10909 | const len: MCValue = switch (dst_ptr_ty.ptrSize()) { | |
| 10901 | const len: MCValue = switch (dst_ptr_ty.ptrSize(mod)) { | |
| 10910 | 10902 | .Slice => dst_ptr.address().offset(8).deref(), |
| 10911 | .One => .{ .immediate = dst_ptr_ty.childType().arrayLen() }, | |
| 10903 | .One => .{ .immediate = dst_ptr_ty.childType(mod).arrayLen(mod) }, | |
| 10912 | 10904 | .C, .Many => unreachable, |
| 10913 | 10905 | }; |
| 10914 | 10906 | const len_lock: ?RegisterLock = switch (len) { |
| ... | ... | @@ -11059,7 +11051,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 11059 | 11051 | switch (scalar_ty.zigTypeTag(mod)) { |
| 11060 | 11052 | else => {}, |
| 11061 | 11053 | .Float => switch (scalar_ty.floatBits(self.target.*)) { |
| 11062 | 32 => switch (vector_ty.vectorLen()) { | |
| 11054 | 32 => switch (vector_ty.vectorLen(mod)) { | |
| 11063 | 11055 | 1 => { |
| 11064 | 11056 | if (self.reuseOperand(inst, ty_op.operand, 0, src_mcv)) break :result src_mcv; |
| 11065 | 11057 | const dst_reg = try self.register_manager.allocReg(inst, dst_rc); |
| ... | ... | @@ -11139,7 +11131,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 11139 | 11131 | }, |
| 11140 | 11132 | else => {}, |
| 11141 | 11133 | }, |
| 11142 | 64 => switch (vector_ty.vectorLen()) { | |
| 11134 | 64 => switch (vector_ty.vectorLen(mod)) { | |
| 11143 | 11135 | 1 => { |
| 11144 | 11136 | if (self.reuseOperand(inst, ty_op.operand, 0, src_mcv)) break :result src_mcv; |
| 11145 | 11137 | const dst_reg = try self.register_manager.allocReg(inst, dst_rc); |
| ... | ... | @@ -11205,7 +11197,7 @@ fn airSplat(self: *Self, inst: Air.Inst.Index) !void { |
| 11205 | 11197 | }, |
| 11206 | 11198 | else => {}, |
| 11207 | 11199 | }, |
| 11208 | 128 => switch (vector_ty.vectorLen()) { | |
| 11200 | 128 => switch (vector_ty.vectorLen(mod)) { | |
| 11209 | 11201 | 1 => { |
| 11210 | 11202 | if (self.reuseOperand(inst, ty_op.operand, 0, src_mcv)) break :result src_mcv; |
| 11211 | 11203 | const dst_reg = try self.register_manager.allocReg(inst, dst_rc); |
| ... | ... | @@ -11271,7 +11263,7 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void { |
| 11271 | 11263 | fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 11272 | 11264 | const mod = self.bin_file.options.module.?; |
| 11273 | 11265 | const result_ty = self.typeOfIndex(inst); |
| 11274 | const len = @intCast(usize, result_ty.arrayLen()); | |
| 11266 | const len = @intCast(usize, result_ty.arrayLen(mod)); | |
| 11275 | 11267 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 11276 | 11268 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 11277 | 11269 | const result: MCValue = result: { |
| ... | ... | @@ -11375,7 +11367,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 11375 | 11367 | .Array => { |
| 11376 | 11368 | const frame_index = |
| 11377 | 11369 | try self.allocFrameIndex(FrameAlloc.initType(result_ty, mod)); |
| 11378 | const elem_ty = result_ty.childType(); | |
| 11370 | const elem_ty = result_ty.childType(mod); | |
| 11379 | 11371 | const elem_size = @intCast(u32, elem_ty.abiSize(mod)); |
| 11380 | 11372 | |
| 11381 | 11373 | for (elements, 0..) |elem, elem_i| { |
| ... | ... | @@ -11387,7 +11379,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void { |
| 11387 | 11379 | const elem_off = @intCast(i32, elem_size * elem_i); |
| 11388 | 11380 | try self.genSetMem(.{ .frame = frame_index }, elem_off, elem_ty, mat_elem_mcv); |
| 11389 | 11381 | } |
| 11390 | if (result_ty.sentinel()) |sentinel| try self.genSetMem( | |
| 11382 | if (result_ty.sentinel(mod)) |sentinel| try self.genSetMem( | |
| 11391 | 11383 | .{ .frame = frame_index }, |
| 11392 | 11384 | @intCast(i32, elem_size * elements.len), |
| 11393 | 11385 | elem_ty, |
| ... | ... | @@ -11512,14 +11504,14 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void { |
| 11512 | 11504 | 16, 80, 128 => null, |
| 11513 | 11505 | else => unreachable, |
| 11514 | 11506 | }, |
| 11515 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 11516 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 11517 | 32 => switch (ty.vectorLen()) { | |
| 11507 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 11508 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 11509 | 32 => switch (ty.vectorLen(mod)) { | |
| 11518 | 11510 | 1 => .{ .v_ss, .fmadd132 }, |
| 11519 | 11511 | 2...8 => .{ .v_ps, .fmadd132 }, |
| 11520 | 11512 | else => null, |
| 11521 | 11513 | }, |
| 11522 | 64 => switch (ty.vectorLen()) { | |
| 11514 | 64 => switch (ty.vectorLen(mod)) { | |
| 11523 | 11515 | 1 => .{ .v_sd, .fmadd132 }, |
| 11524 | 11516 | 2...4 => .{ .v_pd, .fmadd132 }, |
| 11525 | 11517 | else => null, |
| ... | ... | @@ -11539,14 +11531,14 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void { |
| 11539 | 11531 | 16, 80, 128 => null, |
| 11540 | 11532 | else => unreachable, |
| 11541 | 11533 | }, |
| 11542 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 11543 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 11544 | 32 => switch (ty.vectorLen()) { | |
| 11534 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 11535 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 11536 | 32 => switch (ty.vectorLen(mod)) { | |
| 11545 | 11537 | 1 => .{ .v_ss, .fmadd213 }, |
| 11546 | 11538 | 2...8 => .{ .v_ps, .fmadd213 }, |
| 11547 | 11539 | else => null, |
| 11548 | 11540 | }, |
| 11549 | 64 => switch (ty.vectorLen()) { | |
| 11541 | 64 => switch (ty.vectorLen(mod)) { | |
| 11550 | 11542 | 1 => .{ .v_sd, .fmadd213 }, |
| 11551 | 11543 | 2...4 => .{ .v_pd, .fmadd213 }, |
| 11552 | 11544 | else => null, |
| ... | ... | @@ -11566,14 +11558,14 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void { |
| 11566 | 11558 | 16, 80, 128 => null, |
| 11567 | 11559 | else => unreachable, |
| 11568 | 11560 | }, |
| 11569 | .Vector => switch (ty.childType().zigTypeTag(mod)) { | |
| 11570 | .Float => switch (ty.childType().floatBits(self.target.*)) { | |
| 11571 | 32 => switch (ty.vectorLen()) { | |
| 11561 | .Vector => switch (ty.childType(mod).zigTypeTag(mod)) { | |
| 11562 | .Float => switch (ty.childType(mod).floatBits(self.target.*)) { | |
| 11563 | 32 => switch (ty.vectorLen(mod)) { | |
| 11572 | 11564 | 1 => .{ .v_ss, .fmadd231 }, |
| 11573 | 11565 | 2...8 => .{ .v_ps, .fmadd231 }, |
| 11574 | 11566 | else => null, |
| 11575 | 11567 | }, |
| 11576 | 64 => switch (ty.vectorLen()) { | |
| 11568 | 64 => switch (ty.vectorLen(mod)) { | |
| 11577 | 11569 | 1 => .{ .v_sd, .fmadd231 }, |
| 11578 | 11570 | 2...4 => .{ .v_pd, .fmadd231 }, |
| 11579 | 11571 | else => null, |
src/arch/x86_64/abi.zig+3-3| ... | ... | @@ -76,7 +76,7 @@ pub fn classifySystemV(ty: Type, mod: *const Module, ctx: Context) [8]Class { |
| 76 | 76 | }; |
| 77 | 77 | var result = [1]Class{.none} ** 8; |
| 78 | 78 | switch (ty.zigTypeTag(mod)) { |
| 79 | .Pointer => switch (ty.ptrSize()) { | |
| 79 | .Pointer => switch (ty.ptrSize(mod)) { | |
| 80 | 80 | .Slice => { |
| 81 | 81 | result[0] = .integer; |
| 82 | 82 | result[1] = .integer; |
| ... | ... | @@ -158,8 +158,8 @@ pub fn classifySystemV(ty: Type, mod: *const Module, ctx: Context) [8]Class { |
| 158 | 158 | else => unreachable, |
| 159 | 159 | }, |
| 160 | 160 | .Vector => { |
| 161 | const elem_ty = ty.childType(); | |
| 162 | const bits = elem_ty.bitSize(mod) * ty.arrayLen(); | |
| 161 | const elem_ty = ty.childType(mod); | |
| 162 | const bits = elem_ty.bitSize(mod) * ty.arrayLen(mod); | |
| 163 | 163 | if (bits <= 64) return .{ |
| 164 | 164 | .sse, .none, .none, .none, |
| 165 | 165 | .none, .none, .none, .none, |
src/codegen.zig+17-19| ... | ... | @@ -230,7 +230,7 @@ pub fn generateSymbol( |
| 230 | 230 | .Array => switch (typed_value.val.tag()) { |
| 231 | 231 | .bytes => { |
| 232 | 232 | const bytes = typed_value.val.castTag(.bytes).?.data; |
| 233 | const len = @intCast(usize, typed_value.ty.arrayLenIncludingSentinel()); | |
| 233 | const len = @intCast(usize, typed_value.ty.arrayLenIncludingSentinel(mod)); | |
| 234 | 234 | // The bytes payload already includes the sentinel, if any |
| 235 | 235 | try code.ensureUnusedCapacity(len); |
| 236 | 236 | code.appendSliceAssumeCapacity(bytes[0..len]); |
| ... | ... | @@ -241,7 +241,7 @@ pub fn generateSymbol( |
| 241 | 241 | const bytes = mod.string_literal_bytes.items[str_lit.index..][0..str_lit.len]; |
| 242 | 242 | try code.ensureUnusedCapacity(bytes.len + 1); |
| 243 | 243 | code.appendSliceAssumeCapacity(bytes); |
| 244 | if (typed_value.ty.sentinel()) |sent_val| { | |
| 244 | if (typed_value.ty.sentinel(mod)) |sent_val| { | |
| 245 | 245 | const byte = @intCast(u8, sent_val.toUnsignedInt(mod)); |
| 246 | 246 | code.appendAssumeCapacity(byte); |
| 247 | 247 | } |
| ... | ... | @@ -249,8 +249,8 @@ pub fn generateSymbol( |
| 249 | 249 | }, |
| 250 | 250 | .aggregate => { |
| 251 | 251 | const elem_vals = typed_value.val.castTag(.aggregate).?.data; |
| 252 | const elem_ty = typed_value.ty.elemType(); | |
| 253 | const len = @intCast(usize, typed_value.ty.arrayLenIncludingSentinel()); | |
| 252 | const elem_ty = typed_value.ty.childType(mod); | |
| 253 | const len = @intCast(usize, typed_value.ty.arrayLenIncludingSentinel(mod)); | |
| 254 | 254 | for (elem_vals[0..len]) |elem_val| { |
| 255 | 255 | switch (try generateSymbol(bin_file, src_loc, .{ |
| 256 | 256 | .ty = elem_ty, |
| ... | ... | @@ -264,9 +264,9 @@ pub fn generateSymbol( |
| 264 | 264 | }, |
| 265 | 265 | .repeated => { |
| 266 | 266 | const array = typed_value.val.castTag(.repeated).?.data; |
| 267 | const elem_ty = typed_value.ty.childType(); | |
| 268 | const sentinel = typed_value.ty.sentinel(); | |
| 269 | const len = typed_value.ty.arrayLen(); | |
| 267 | const elem_ty = typed_value.ty.childType(mod); | |
| 268 | const sentinel = typed_value.ty.sentinel(mod); | |
| 269 | const len = typed_value.ty.arrayLen(mod); | |
| 270 | 270 | |
| 271 | 271 | var index: u64 = 0; |
| 272 | 272 | while (index < len) : (index += 1) { |
| ... | ... | @@ -292,8 +292,8 @@ pub fn generateSymbol( |
| 292 | 292 | return Result.ok; |
| 293 | 293 | }, |
| 294 | 294 | .empty_array_sentinel => { |
| 295 | const elem_ty = typed_value.ty.childType(); | |
| 296 | const sentinel_val = typed_value.ty.sentinel().?; | |
| 295 | const elem_ty = typed_value.ty.childType(mod); | |
| 296 | const sentinel_val = typed_value.ty.sentinel(mod).?; | |
| 297 | 297 | switch (try generateSymbol(bin_file, src_loc, .{ |
| 298 | 298 | .ty = elem_ty, |
| 299 | 299 | .val = sentinel_val, |
| ... | ... | @@ -618,8 +618,7 @@ pub fn generateSymbol( |
| 618 | 618 | return Result.ok; |
| 619 | 619 | }, |
| 620 | 620 | .Optional => { |
| 621 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 622 | const payload_type = typed_value.ty.optionalChild(&opt_buf); | |
| 621 | const payload_type = typed_value.ty.optionalChild(mod); | |
| 623 | 622 | const is_pl = !typed_value.val.isNull(mod); |
| 624 | 623 | const abi_size = math.cast(usize, typed_value.ty.abiSize(mod)) orelse return error.Overflow; |
| 625 | 624 | |
| ... | ... | @@ -751,7 +750,7 @@ pub fn generateSymbol( |
| 751 | 750 | .Vector => switch (typed_value.val.tag()) { |
| 752 | 751 | .bytes => { |
| 753 | 752 | const bytes = typed_value.val.castTag(.bytes).?.data; |
| 754 | const len = math.cast(usize, typed_value.ty.arrayLen()) orelse return error.Overflow; | |
| 753 | const len = math.cast(usize, typed_value.ty.arrayLen(mod)) orelse return error.Overflow; | |
| 755 | 754 | const padding = math.cast(usize, typed_value.ty.abiSize(mod) - len) orelse |
| 756 | 755 | return error.Overflow; |
| 757 | 756 | try code.ensureUnusedCapacity(len + padding); |
| ... | ... | @@ -761,8 +760,8 @@ pub fn generateSymbol( |
| 761 | 760 | }, |
| 762 | 761 | .aggregate => { |
| 763 | 762 | const elem_vals = typed_value.val.castTag(.aggregate).?.data; |
| 764 | const elem_ty = typed_value.ty.elemType(); | |
| 765 | const len = math.cast(usize, typed_value.ty.arrayLen()) orelse return error.Overflow; | |
| 763 | const elem_ty = typed_value.ty.childType(mod); | |
| 764 | const len = math.cast(usize, typed_value.ty.arrayLen(mod)) orelse return error.Overflow; | |
| 766 | 765 | const padding = math.cast(usize, typed_value.ty.abiSize(mod) - |
| 767 | 766 | (math.divCeil(u64, elem_ty.bitSize(mod) * len, 8) catch |err| switch (err) { |
| 768 | 767 | error.DivisionByZero => unreachable, |
| ... | ... | @@ -782,8 +781,8 @@ pub fn generateSymbol( |
| 782 | 781 | }, |
| 783 | 782 | .repeated => { |
| 784 | 783 | const array = typed_value.val.castTag(.repeated).?.data; |
| 785 | const elem_ty = typed_value.ty.childType(); | |
| 786 | const len = typed_value.ty.arrayLen(); | |
| 784 | const elem_ty = typed_value.ty.childType(mod); | |
| 785 | const len = typed_value.ty.arrayLen(mod); | |
| 787 | 786 | const padding = math.cast(usize, typed_value.ty.abiSize(mod) - |
| 788 | 787 | (math.divCeil(u64, elem_ty.bitSize(mod) * len, 8) catch |err| switch (err) { |
| 789 | 788 | error.DivisionByZero => unreachable, |
| ... | ... | @@ -1188,7 +1187,7 @@ pub fn genTypedValue( |
| 1188 | 1187 | |
| 1189 | 1188 | switch (typed_value.ty.zigTypeTag(mod)) { |
| 1190 | 1189 | .Void => return GenResult.mcv(.none), |
| 1191 | .Pointer => switch (typed_value.ty.ptrSize()) { | |
| 1190 | .Pointer => switch (typed_value.ty.ptrSize(mod)) { | |
| 1192 | 1191 | .Slice => {}, |
| 1193 | 1192 | else => { |
| 1194 | 1193 | switch (typed_value.val.tag()) { |
| ... | ... | @@ -1219,9 +1218,8 @@ pub fn genTypedValue( |
| 1219 | 1218 | if (typed_value.ty.isPtrLikeOptional(mod)) { |
| 1220 | 1219 | if (typed_value.val.tag() == .null_value) return GenResult.mcv(.{ .immediate = 0 }); |
| 1221 | 1220 | |
| 1222 | var buf: Type.Payload.ElemType = undefined; | |
| 1223 | 1221 | return genTypedValue(bin_file, src_loc, .{ |
| 1224 | .ty = typed_value.ty.optionalChild(&buf), | |
| 1222 | .ty = typed_value.ty.optionalChild(mod), | |
| 1225 | 1223 | .val = if (typed_value.val.castTag(.opt_payload)) |pl| pl.data else typed_value.val, |
| 1226 | 1224 | }, owner_decl_index); |
| 1227 | 1225 | } else if (typed_value.ty.abiSize(mod) == 1) { |
src/codegen/c.zig+106-97| ... | ... | @@ -625,7 +625,9 @@ pub const DeclGen = struct { |
| 625 | 625 | // Ensure complete type definition is visible before accessing fields. |
| 626 | 626 | _ = try dg.typeToIndex(field_ptr.container_ty, .complete); |
| 627 | 627 | |
| 628 | var container_ptr_pl = ptr_ty.ptrInfo(); | |
| 628 | var container_ptr_pl: Type.Payload.Pointer = .{ | |
| 629 | .data = ptr_ty.ptrInfo(mod), | |
| 630 | }; | |
| 629 | 631 | container_ptr_pl.data.pointee_type = field_ptr.container_ty; |
| 630 | 632 | const container_ptr_ty = Type.initPayload(&container_ptr_pl.base); |
| 631 | 633 | |
| ... | ... | @@ -653,7 +655,9 @@ pub const DeclGen = struct { |
| 653 | 655 | try dg.writeCValue(writer, field); |
| 654 | 656 | }, |
| 655 | 657 | .byte_offset => |byte_offset| { |
| 656 | var u8_ptr_pl = ptr_ty.ptrInfo(); | |
| 658 | var u8_ptr_pl: Type.Payload.Pointer = .{ | |
| 659 | .data = ptr_ty.ptrInfo(mod), | |
| 660 | }; | |
| 657 | 661 | u8_ptr_pl.data.pointee_type = Type.u8; |
| 658 | 662 | const u8_ptr_ty = Type.initPayload(&u8_ptr_pl.base); |
| 659 | 663 | |
| ... | ... | @@ -692,11 +696,10 @@ pub const DeclGen = struct { |
| 692 | 696 | }, |
| 693 | 697 | .elem_ptr => { |
| 694 | 698 | const elem_ptr = ptr_val.castTag(.elem_ptr).?.data; |
| 695 | var elem_ptr_ty_pl: Type.Payload.ElemType = .{ | |
| 696 | .base = .{ .tag = .c_mut_pointer }, | |
| 697 | .data = elem_ptr.elem_ty, | |
| 698 | }; | |
| 699 | const elem_ptr_ty = Type.initPayload(&elem_ptr_ty_pl.base); | |
| 699 | const elem_ptr_ty = try mod.ptrType(.{ | |
| 700 | .size = .C, | |
| 701 | .elem_type = elem_ptr.elem_ty.ip_index, | |
| 702 | }); | |
| 700 | 703 | |
| 701 | 704 | try writer.writeAll("&("); |
| 702 | 705 | try dg.renderParentPtr(writer, elem_ptr.array_ptr, elem_ptr_ty, location); |
| ... | ... | @@ -704,11 +707,10 @@ pub const DeclGen = struct { |
| 704 | 707 | }, |
| 705 | 708 | .opt_payload_ptr, .eu_payload_ptr => { |
| 706 | 709 | const payload_ptr = ptr_val.cast(Value.Payload.PayloadPtr).?.data; |
| 707 | var container_ptr_ty_pl: Type.Payload.ElemType = .{ | |
| 708 | .base = .{ .tag = .c_mut_pointer }, | |
| 709 | .data = payload_ptr.container_ty, | |
| 710 | }; | |
| 711 | const container_ptr_ty = Type.initPayload(&container_ptr_ty_pl.base); | |
| 710 | const container_ptr_ty = try mod.ptrType(.{ | |
| 711 | .elem_type = payload_ptr.container_ty.ip_index, | |
| 712 | .size = .C, | |
| 713 | }); | |
| 712 | 714 | |
| 713 | 715 | // Ensure complete type definition is visible before accessing fields. |
| 714 | 716 | _ = try dg.typeToIndex(payload_ptr.container_ty, .complete); |
| ... | ... | @@ -794,8 +796,7 @@ pub const DeclGen = struct { |
| 794 | 796 | return writer.print("){x})", .{try dg.fmtIntLiteral(Type.usize, val, .Other)}); |
| 795 | 797 | }, |
| 796 | 798 | .Optional => { |
| 797 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 798 | const payload_ty = ty.optionalChild(&opt_buf); | |
| 799 | const payload_ty = ty.optionalChild(mod); | |
| 799 | 800 | |
| 800 | 801 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 801 | 802 | return dg.renderValue(writer, Type.bool, val, location); |
| ... | ... | @@ -889,11 +890,11 @@ pub const DeclGen = struct { |
| 889 | 890 | return writer.writeAll(" }"); |
| 890 | 891 | }, |
| 891 | 892 | .Array, .Vector => { |
| 892 | const ai = ty.arrayInfo(); | |
| 893 | const ai = ty.arrayInfo(mod); | |
| 893 | 894 | if (ai.elem_type.eql(Type.u8, dg.module)) { |
| 894 | 895 | var literal = stringLiteral(writer); |
| 895 | 896 | try literal.start(); |
| 896 | const c_len = ty.arrayLenIncludingSentinel(); | |
| 897 | const c_len = ty.arrayLenIncludingSentinel(mod); | |
| 897 | 898 | var index: u64 = 0; |
| 898 | 899 | while (index < c_len) : (index += 1) |
| 899 | 900 | try literal.writeChar(0xaa); |
| ... | ... | @@ -906,11 +907,11 @@ pub const DeclGen = struct { |
| 906 | 907 | } |
| 907 | 908 | |
| 908 | 909 | try writer.writeByte('{'); |
| 909 | const c_len = ty.arrayLenIncludingSentinel(); | |
| 910 | const c_len = ty.arrayLenIncludingSentinel(mod); | |
| 910 | 911 | var index: u64 = 0; |
| 911 | 912 | while (index < c_len) : (index += 1) { |
| 912 | 913 | if (index > 0) try writer.writeAll(", "); |
| 913 | try dg.renderValue(writer, ty.childType(), val, initializer_type); | |
| 914 | try dg.renderValue(writer, ty.childType(mod), val, initializer_type); | |
| 914 | 915 | } |
| 915 | 916 | return writer.writeByte('}'); |
| 916 | 917 | } |
| ... | ... | @@ -1110,7 +1111,7 @@ pub const DeclGen = struct { |
| 1110 | 1111 | // First try specific tag representations for more efficiency. |
| 1111 | 1112 | switch (val.tag()) { |
| 1112 | 1113 | .undef, .empty_struct_value, .empty_array => { |
| 1113 | const ai = ty.arrayInfo(); | |
| 1114 | const ai = ty.arrayInfo(mod); | |
| 1114 | 1115 | try writer.writeByte('{'); |
| 1115 | 1116 | if (ai.sentinel) |s| { |
| 1116 | 1117 | try dg.renderValue(writer, ai.elem_type, s, initializer_type); |
| ... | ... | @@ -1128,9 +1129,9 @@ pub const DeclGen = struct { |
| 1128 | 1129 | }, |
| 1129 | 1130 | else => unreachable, |
| 1130 | 1131 | }; |
| 1131 | const sentinel = if (ty.sentinel()) |sentinel| @intCast(u8, sentinel.toUnsignedInt(mod)) else null; | |
| 1132 | const sentinel = if (ty.sentinel(mod)) |sentinel| @intCast(u8, sentinel.toUnsignedInt(mod)) else null; | |
| 1132 | 1133 | try writer.print("{s}", .{ |
| 1133 | fmtStringLiteral(bytes[0..@intCast(usize, ty.arrayLen())], sentinel), | |
| 1134 | fmtStringLiteral(bytes[0..@intCast(usize, ty.arrayLen(mod))], sentinel), | |
| 1134 | 1135 | }); |
| 1135 | 1136 | }, |
| 1136 | 1137 | else => { |
| ... | ... | @@ -1142,7 +1143,7 @@ pub const DeclGen = struct { |
| 1142 | 1143 | // MSVC throws C2078 if an array of size 65536 or greater is initialized with a string literal |
| 1143 | 1144 | const max_string_initializer_len = 65535; |
| 1144 | 1145 | |
| 1145 | const ai = ty.arrayInfo(); | |
| 1146 | const ai = ty.arrayInfo(mod); | |
| 1146 | 1147 | if (ai.elem_type.eql(Type.u8, dg.module)) { |
| 1147 | 1148 | if (ai.len <= max_string_initializer_len) { |
| 1148 | 1149 | var literal = stringLiteral(writer); |
| ... | ... | @@ -1198,8 +1199,7 @@ pub const DeclGen = struct { |
| 1198 | 1199 | } |
| 1199 | 1200 | }, |
| 1200 | 1201 | .Optional => { |
| 1201 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 1202 | const payload_ty = ty.optionalChild(&opt_buf); | |
| 1202 | const payload_ty = ty.optionalChild(mod); | |
| 1203 | 1203 | |
| 1204 | 1204 | const is_null_val = Value.makeBool(val.tag() == .null_value); |
| 1205 | 1205 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) |
| ... | ... | @@ -2410,12 +2410,13 @@ pub fn genGlobalAsm(mod: *Module, writer: anytype) !void { |
| 2410 | 2410 | } |
| 2411 | 2411 | |
| 2412 | 2412 | pub fn genErrDecls(o: *Object) !void { |
| 2413 | const mod = o.dg.module; | |
| 2413 | 2414 | const writer = o.writer(); |
| 2414 | 2415 | |
| 2415 | 2416 | try writer.writeAll("enum {\n"); |
| 2416 | 2417 | o.indent_writer.pushIndent(); |
| 2417 | 2418 | var max_name_len: usize = 0; |
| 2418 | for (o.dg.module.error_name_list.items, 0..) |name, value| { | |
| 2419 | for (mod.error_name_list.items, 0..) |name, value| { | |
| 2419 | 2420 | max_name_len = std.math.max(name.len, max_name_len); |
| 2420 | 2421 | var err_pl = Value.Payload.Error{ .data = .{ .name = name } }; |
| 2421 | 2422 | try o.dg.renderValue(writer, Type.anyerror, Value.initPayload(&err_pl.base), .Other); |
| ... | ... | @@ -2430,12 +2431,15 @@ pub fn genErrDecls(o: *Object) !void { |
| 2430 | 2431 | defer o.dg.gpa.free(name_buf); |
| 2431 | 2432 | |
| 2432 | 2433 | @memcpy(name_buf[0..name_prefix.len], name_prefix); |
| 2433 | for (o.dg.module.error_name_list.items) |name| { | |
| 2434 | for (mod.error_name_list.items) |name| { | |
| 2434 | 2435 | @memcpy(name_buf[name_prefix.len..][0..name.len], name); |
| 2435 | 2436 | const identifier = name_buf[0 .. name_prefix.len + name.len]; |
| 2436 | 2437 | |
| 2437 | var name_ty_pl = Type.Payload.Len{ .base = .{ .tag = .array_u8_sentinel_0 }, .data = name.len }; | |
| 2438 | const name_ty = Type.initPayload(&name_ty_pl.base); | |
| 2438 | const name_ty = try mod.arrayType(.{ | |
| 2439 | .len = name.len, | |
| 2440 | .child = .u8_type, | |
| 2441 | .sentinel = .zero_u8, | |
| 2442 | }); | |
| 2439 | 2443 | |
| 2440 | 2444 | var name_pl = Value.Payload.Bytes{ .base = .{ .tag = .bytes }, .data = name }; |
| 2441 | 2445 | const name_val = Value.initPayload(&name_pl.base); |
| ... | ... | @@ -2448,15 +2452,15 @@ pub fn genErrDecls(o: *Object) !void { |
| 2448 | 2452 | } |
| 2449 | 2453 | |
| 2450 | 2454 | var name_array_ty_pl = Type.Payload.Array{ .base = .{ .tag = .array }, .data = .{ |
| 2451 | .len = o.dg.module.error_name_list.items.len, | |
| 2452 | .elem_type = Type.initTag(.const_slice_u8_sentinel_0), | |
| 2455 | .len = mod.error_name_list.items.len, | |
| 2456 | .elem_type = Type.const_slice_u8_sentinel_0, | |
| 2453 | 2457 | } }; |
| 2454 | 2458 | const name_array_ty = Type.initPayload(&name_array_ty_pl.base); |
| 2455 | 2459 | |
| 2456 | 2460 | try writer.writeAll("static "); |
| 2457 | 2461 | try o.dg.renderTypeAndName(writer, name_array_ty, .{ .identifier = array_identifier }, Const, 0, .complete); |
| 2458 | 2462 | try writer.writeAll(" = {"); |
| 2459 | for (o.dg.module.error_name_list.items, 0..) |name, value| { | |
| 2463 | for (mod.error_name_list.items, 0..) |name, value| { | |
| 2460 | 2464 | if (value != 0) try writer.writeByte(','); |
| 2461 | 2465 | |
| 2462 | 2466 | var len_pl = Value.Payload.U64{ .base = .{ .tag = .int_u64 }, .data = name.len }; |
| ... | ... | @@ -2487,6 +2491,7 @@ fn genExports(o: *Object) !void { |
| 2487 | 2491 | } |
| 2488 | 2492 | |
| 2489 | 2493 | pub fn genLazyFn(o: *Object, lazy_fn: LazyFnMap.Entry) !void { |
| 2494 | const mod = o.dg.module; | |
| 2490 | 2495 | const w = o.writer(); |
| 2491 | 2496 | const key = lazy_fn.key_ptr.*; |
| 2492 | 2497 | const val = lazy_fn.value_ptr; |
| ... | ... | @@ -2495,7 +2500,7 @@ pub fn genLazyFn(o: *Object, lazy_fn: LazyFnMap.Entry) !void { |
| 2495 | 2500 | .tag_name => { |
| 2496 | 2501 | const enum_ty = val.data.tag_name; |
| 2497 | 2502 | |
| 2498 | const name_slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 2503 | const name_slice_ty = Type.const_slice_u8_sentinel_0; | |
| 2499 | 2504 | |
| 2500 | 2505 | try w.writeAll("static "); |
| 2501 | 2506 | try o.dg.renderType(w, name_slice_ty); |
| ... | ... | @@ -2514,11 +2519,11 @@ pub fn genLazyFn(o: *Object, lazy_fn: LazyFnMap.Entry) !void { |
| 2514 | 2519 | var int_pl: Value.Payload.U64 = undefined; |
| 2515 | 2520 | const int_val = tag_val.enumToInt(enum_ty, &int_pl); |
| 2516 | 2521 | |
| 2517 | var name_ty_pl = Type.Payload.Len{ | |
| 2518 | .base = .{ .tag = .array_u8_sentinel_0 }, | |
| 2519 | .data = name.len, | |
| 2520 | }; | |
| 2521 | const name_ty = Type.initPayload(&name_ty_pl.base); | |
| 2522 | const name_ty = try mod.arrayType(.{ | |
| 2523 | .len = name.len, | |
| 2524 | .child = .u8_type, | |
| 2525 | .sentinel = .zero_u8, | |
| 2526 | }); | |
| 2522 | 2527 | |
| 2523 | 2528 | var name_pl = Value.Payload.Bytes{ .base = .{ .tag = .bytes }, .data = name }; |
| 2524 | 2529 | const name_val = Value.initPayload(&name_pl.base); |
| ... | ... | @@ -2547,7 +2552,7 @@ pub fn genLazyFn(o: *Object, lazy_fn: LazyFnMap.Entry) !void { |
| 2547 | 2552 | try w.writeAll("}\n"); |
| 2548 | 2553 | }, |
| 2549 | 2554 | .never_tail, .never_inline => |fn_decl_index| { |
| 2550 | const fn_decl = o.dg.module.declPtr(fn_decl_index); | |
| 2555 | const fn_decl = mod.declPtr(fn_decl_index); | |
| 2551 | 2556 | const fn_cty = try o.dg.typeToCType(fn_decl.ty, .complete); |
| 2552 | 2557 | const fn_info = fn_cty.cast(CType.Payload.Function).?.data; |
| 2553 | 2558 | |
| ... | ... | @@ -3150,7 +3155,7 @@ fn airPtrElemPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3150 | 3155 | |
| 3151 | 3156 | const inst_ty = f.typeOfIndex(inst); |
| 3152 | 3157 | const ptr_ty = f.typeOf(bin_op.lhs); |
| 3153 | const elem_ty = ptr_ty.childType(); | |
| 3158 | const elem_ty = ptr_ty.childType(mod); | |
| 3154 | 3159 | const elem_has_bits = elem_ty.hasRuntimeBitsIgnoreComptime(mod); |
| 3155 | 3160 | |
| 3156 | 3161 | const ptr = try f.resolveInst(bin_op.lhs); |
| ... | ... | @@ -3166,7 +3171,7 @@ fn airPtrElemPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3166 | 3171 | try f.renderType(writer, inst_ty); |
| 3167 | 3172 | try writer.writeByte(')'); |
| 3168 | 3173 | if (elem_has_bits) try writer.writeByte('&'); |
| 3169 | if (elem_has_bits and ptr_ty.ptrSize() == .One) { | |
| 3174 | if (elem_has_bits and ptr_ty.ptrSize(mod) == .One) { | |
| 3170 | 3175 | // It's a pointer to an array, so we need to de-reference. |
| 3171 | 3176 | try f.writeCValueDeref(writer, ptr); |
| 3172 | 3177 | } else try f.writeCValue(writer, ptr, .Other); |
| ... | ... | @@ -3264,7 +3269,7 @@ fn airArrayElemVal(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3264 | 3269 | fn airAlloc(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3265 | 3270 | const mod = f.object.dg.module; |
| 3266 | 3271 | const inst_ty = f.typeOfIndex(inst); |
| 3267 | const elem_type = inst_ty.elemType(); | |
| 3272 | const elem_type = inst_ty.childType(mod); | |
| 3268 | 3273 | if (!elem_type.isFnOrHasRuntimeBitsIgnoreComptime(mod)) return .{ .undef = inst_ty }; |
| 3269 | 3274 | |
| 3270 | 3275 | const local = try f.allocLocalValue( |
| ... | ... | @@ -3280,7 +3285,7 @@ fn airAlloc(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3280 | 3285 | fn airRetPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3281 | 3286 | const mod = f.object.dg.module; |
| 3282 | 3287 | const inst_ty = f.typeOfIndex(inst); |
| 3283 | const elem_ty = inst_ty.elemType(); | |
| 3288 | const elem_ty = inst_ty.childType(mod); | |
| 3284 | 3289 | if (!elem_ty.isFnOrHasRuntimeBitsIgnoreComptime(mod)) return .{ .undef = inst_ty }; |
| 3285 | 3290 | |
| 3286 | 3291 | const local = try f.allocLocalValue( |
| ... | ... | @@ -3323,7 +3328,7 @@ fn airLoad(f: *Function, inst: Air.Inst.Index) !CValue { |
| 3323 | 3328 | |
| 3324 | 3329 | const ptr_ty = f.typeOf(ty_op.operand); |
| 3325 | 3330 | const ptr_scalar_ty = ptr_ty.scalarType(mod); |
| 3326 | const ptr_info = ptr_scalar_ty.ptrInfo().data; | |
| 3331 | const ptr_info = ptr_scalar_ty.ptrInfo(mod); | |
| 3327 | 3332 | const src_ty = ptr_info.pointee_type; |
| 3328 | 3333 | |
| 3329 | 3334 | if (!src_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| ... | ... | @@ -3412,7 +3417,7 @@ fn airRet(f: *Function, inst: Air.Inst.Index, is_ptr: bool) !CValue { |
| 3412 | 3417 | const writer = f.object.writer(); |
| 3413 | 3418 | const op_inst = Air.refToIndex(un_op); |
| 3414 | 3419 | const op_ty = f.typeOf(un_op); |
| 3415 | const ret_ty = if (is_ptr) op_ty.childType() else op_ty; | |
| 3420 | const ret_ty = if (is_ptr) op_ty.childType(mod) else op_ty; | |
| 3416 | 3421 | var lowered_ret_buf: LowerFnRetTyBuffer = undefined; |
| 3417 | 3422 | const lowered_ret_ty = lowerFnRetTy(ret_ty, &lowered_ret_buf, mod); |
| 3418 | 3423 | |
| ... | ... | @@ -3601,7 +3606,7 @@ fn airStore(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 3601 | 3606 | |
| 3602 | 3607 | const ptr_ty = f.typeOf(bin_op.lhs); |
| 3603 | 3608 | const ptr_scalar_ty = ptr_ty.scalarType(mod); |
| 3604 | const ptr_info = ptr_scalar_ty.ptrInfo().data; | |
| 3609 | const ptr_info = ptr_scalar_ty.ptrInfo(mod); | |
| 3605 | 3610 | |
| 3606 | 3611 | const ptr_val = try f.resolveInst(bin_op.lhs); |
| 3607 | 3612 | const src_ty = f.typeOf(bin_op.rhs); |
| ... | ... | @@ -4156,7 +4161,7 @@ fn airCall( |
| 4156 | 4161 | const callee_ty = f.typeOf(pl_op.operand); |
| 4157 | 4162 | const fn_ty = switch (callee_ty.zigTypeTag(mod)) { |
| 4158 | 4163 | .Fn => callee_ty, |
| 4159 | .Pointer => callee_ty.childType(), | |
| 4164 | .Pointer => callee_ty.childType(mod), | |
| 4160 | 4165 | else => unreachable, |
| 4161 | 4166 | }; |
| 4162 | 4167 | |
| ... | ... | @@ -4331,10 +4336,11 @@ fn airTry(f: *Function, inst: Air.Inst.Index) !CValue { |
| 4331 | 4336 | } |
| 4332 | 4337 | |
| 4333 | 4338 | fn airTryPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 4339 | const mod = f.object.dg.module; | |
| 4334 | 4340 | const ty_pl = f.air.instructions.items(.data)[inst].ty_pl; |
| 4335 | 4341 | const extra = f.air.extraData(Air.TryPtr, ty_pl.payload); |
| 4336 | 4342 | const body = f.air.extra[extra.end..][0..extra.data.body_len]; |
| 4337 | const err_union_ty = f.typeOf(extra.data.ptr).childType(); | |
| 4343 | const err_union_ty = f.typeOf(extra.data.ptr).childType(mod); | |
| 4338 | 4344 | return lowerTry(f, inst, extra.data.ptr, body, err_union_ty, true); |
| 4339 | 4345 | } |
| 4340 | 4346 | |
| ... | ... | @@ -4826,7 +4832,7 @@ fn airAsm(f: *Function, inst: Air.Inst.Index) !CValue { |
| 4826 | 4832 | |
| 4827 | 4833 | const is_reg = constraint[1] == '{'; |
| 4828 | 4834 | if (is_reg) { |
| 4829 | const output_ty = if (output == .none) inst_ty else f.typeOf(output).childType(); | |
| 4835 | const output_ty = if (output == .none) inst_ty else f.typeOf(output).childType(mod); | |
| 4830 | 4836 | try writer.writeAll("register "); |
| 4831 | 4837 | const alignment = 0; |
| 4832 | 4838 | const local_value = try f.allocLocalValue(output_ty, alignment); |
| ... | ... | @@ -5061,9 +5067,8 @@ fn airIsNull( |
| 5061 | 5067 | } |
| 5062 | 5068 | |
| 5063 | 5069 | const operand_ty = f.typeOf(un_op); |
| 5064 | const optional_ty = if (is_ptr) operand_ty.childType() else operand_ty; | |
| 5065 | var payload_buf: Type.Payload.ElemType = undefined; | |
| 5066 | const payload_ty = optional_ty.optionalChild(&payload_buf); | |
| 5070 | const optional_ty = if (is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 5071 | const payload_ty = optional_ty.optionalChild(mod); | |
| 5067 | 5072 | var slice_ptr_buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 5068 | 5073 | |
| 5069 | 5074 | const rhs = if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) |
| ... | ... | @@ -5097,8 +5102,7 @@ fn airOptionalPayload(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5097 | 5102 | try reap(f, inst, &.{ty_op.operand}); |
| 5098 | 5103 | const opt_ty = f.typeOf(ty_op.operand); |
| 5099 | 5104 | |
| 5100 | var buf: Type.Payload.ElemType = undefined; | |
| 5101 | const payload_ty = opt_ty.optionalChild(&buf); | |
| 5105 | const payload_ty = opt_ty.optionalChild(mod); | |
| 5102 | 5106 | |
| 5103 | 5107 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 5104 | 5108 | return .none; |
| ... | ... | @@ -5132,10 +5136,10 @@ fn airOptionalPayloadPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5132 | 5136 | const operand = try f.resolveInst(ty_op.operand); |
| 5133 | 5137 | try reap(f, inst, &.{ty_op.operand}); |
| 5134 | 5138 | const ptr_ty = f.typeOf(ty_op.operand); |
| 5135 | const opt_ty = ptr_ty.childType(); | |
| 5139 | const opt_ty = ptr_ty.childType(mod); | |
| 5136 | 5140 | const inst_ty = f.typeOfIndex(inst); |
| 5137 | 5141 | |
| 5138 | if (!inst_ty.childType().hasRuntimeBitsIgnoreComptime(mod)) { | |
| 5142 | if (!inst_ty.childType(mod).hasRuntimeBitsIgnoreComptime(mod)) { | |
| 5139 | 5143 | return .{ .undef = inst_ty }; |
| 5140 | 5144 | } |
| 5141 | 5145 | |
| ... | ... | @@ -5163,7 +5167,7 @@ fn airOptionalPayloadPtrSet(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5163 | 5167 | try reap(f, inst, &.{ty_op.operand}); |
| 5164 | 5168 | const operand_ty = f.typeOf(ty_op.operand); |
| 5165 | 5169 | |
| 5166 | const opt_ty = operand_ty.elemType(); | |
| 5170 | const opt_ty = operand_ty.childType(mod); | |
| 5167 | 5171 | |
| 5168 | 5172 | const inst_ty = f.typeOfIndex(inst); |
| 5169 | 5173 | |
| ... | ... | @@ -5221,7 +5225,7 @@ fn fieldLocation( |
| 5221 | 5225 | else |
| 5222 | 5226 | .{ .identifier = container_ty.structFieldName(next_field_index) } }; |
| 5223 | 5227 | } else if (container_ty.hasRuntimeBitsIgnoreComptime(mod)) .end else .begin, |
| 5224 | .Packed => if (field_ptr_ty.ptrInfo().data.host_size == 0) | |
| 5228 | .Packed => if (field_ptr_ty.ptrInfo(mod).host_size == 0) | |
| 5225 | 5229 | .{ .byte_offset = container_ty.packedStructFieldByteOffset(field_index, mod) } |
| 5226 | 5230 | else |
| 5227 | 5231 | .begin, |
| ... | ... | @@ -5243,7 +5247,7 @@ fn fieldLocation( |
| 5243 | 5247 | }, |
| 5244 | 5248 | .Packed => .begin, |
| 5245 | 5249 | }, |
| 5246 | .Pointer => switch (container_ty.ptrSize()) { | |
| 5250 | .Pointer => switch (container_ty.ptrSize(mod)) { | |
| 5247 | 5251 | .Slice => switch (field_index) { |
| 5248 | 5252 | 0 => .{ .field = .{ .identifier = "ptr" } }, |
| 5249 | 5253 | 1 => .{ .field = .{ .identifier = "len" } }, |
| ... | ... | @@ -5280,7 +5284,7 @@ fn airFieldParentPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5280 | 5284 | const extra = f.air.extraData(Air.FieldParentPtr, ty_pl.payload).data; |
| 5281 | 5285 | |
| 5282 | 5286 | const container_ptr_ty = f.typeOfIndex(inst); |
| 5283 | const container_ty = container_ptr_ty.childType(); | |
| 5287 | const container_ty = container_ptr_ty.childType(mod); | |
| 5284 | 5288 | |
| 5285 | 5289 | const field_ptr_ty = f.typeOf(extra.field_ptr); |
| 5286 | 5290 | const field_ptr_val = try f.resolveInst(extra.field_ptr); |
| ... | ... | @@ -5296,7 +5300,9 @@ fn airFieldParentPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5296 | 5300 | switch (fieldLocation(container_ty, field_ptr_ty, extra.field_index, mod)) { |
| 5297 | 5301 | .begin => try f.writeCValue(writer, field_ptr_val, .Initializer), |
| 5298 | 5302 | .field => |field| { |
| 5299 | var u8_ptr_pl = field_ptr_ty.ptrInfo(); | |
| 5303 | var u8_ptr_pl: Type.Payload.Pointer = .{ | |
| 5304 | .data = field_ptr_ty.ptrInfo(mod), | |
| 5305 | }; | |
| 5300 | 5306 | u8_ptr_pl.data.pointee_type = Type.u8; |
| 5301 | 5307 | const u8_ptr_ty = Type.initPayload(&u8_ptr_pl.base); |
| 5302 | 5308 | |
| ... | ... | @@ -5311,7 +5317,9 @@ fn airFieldParentPtr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5311 | 5317 | try writer.writeAll("))"); |
| 5312 | 5318 | }, |
| 5313 | 5319 | .byte_offset => |byte_offset| { |
| 5314 | var u8_ptr_pl = field_ptr_ty.ptrInfo(); | |
| 5320 | var u8_ptr_pl: Type.Payload.Pointer = .{ | |
| 5321 | .data = field_ptr_ty.ptrInfo(mod), | |
| 5322 | }; | |
| 5315 | 5323 | u8_ptr_pl.data.pointee_type = Type.u8; |
| 5316 | 5324 | const u8_ptr_ty = Type.initPayload(&u8_ptr_pl.base); |
| 5317 | 5325 | |
| ... | ... | @@ -5345,7 +5353,7 @@ fn fieldPtr( |
| 5345 | 5353 | field_index: u32, |
| 5346 | 5354 | ) !CValue { |
| 5347 | 5355 | const mod = f.object.dg.module; |
| 5348 | const container_ty = container_ptr_ty.elemType(); | |
| 5356 | const container_ty = container_ptr_ty.childType(mod); | |
| 5349 | 5357 | const field_ptr_ty = f.typeOfIndex(inst); |
| 5350 | 5358 | |
| 5351 | 5359 | // Ensure complete type definition is visible before accessing fields. |
| ... | ... | @@ -5365,7 +5373,9 @@ fn fieldPtr( |
| 5365 | 5373 | try f.writeCValueDerefMember(writer, container_ptr_val, field); |
| 5366 | 5374 | }, |
| 5367 | 5375 | .byte_offset => |byte_offset| { |
| 5368 | var u8_ptr_pl = field_ptr_ty.ptrInfo(); | |
| 5376 | var u8_ptr_pl: Type.Payload.Pointer = .{ | |
| 5377 | .data = field_ptr_ty.ptrInfo(mod), | |
| 5378 | }; | |
| 5369 | 5379 | u8_ptr_pl.data.pointee_type = Type.u8; |
| 5370 | 5380 | const u8_ptr_ty = Type.initPayload(&u8_ptr_pl.base); |
| 5371 | 5381 | |
| ... | ... | @@ -5532,7 +5542,7 @@ fn airUnwrapErrUnionErr(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5532 | 5542 | try reap(f, inst, &.{ty_op.operand}); |
| 5533 | 5543 | |
| 5534 | 5544 | const operand_is_ptr = operand_ty.zigTypeTag(mod) == .Pointer; |
| 5535 | const error_union_ty = if (operand_is_ptr) operand_ty.childType() else operand_ty; | |
| 5545 | const error_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 5536 | 5546 | const error_ty = error_union_ty.errorUnionSet(); |
| 5537 | 5547 | const payload_ty = error_union_ty.errorUnionPayload(); |
| 5538 | 5548 | const local = try f.allocLocal(inst, inst_ty); |
| ... | ... | @@ -5569,7 +5579,7 @@ fn airUnwrapErrUnionPay(f: *Function, inst: Air.Inst.Index, is_ptr: bool) !CValu |
| 5569 | 5579 | const operand = try f.resolveInst(ty_op.operand); |
| 5570 | 5580 | try reap(f, inst, &.{ty_op.operand}); |
| 5571 | 5581 | const operand_ty = f.typeOf(ty_op.operand); |
| 5572 | const error_union_ty = if (is_ptr) operand_ty.childType() else operand_ty; | |
| 5582 | const error_union_ty = if (is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 5573 | 5583 | |
| 5574 | 5584 | const writer = f.object.writer(); |
| 5575 | 5585 | if (!error_union_ty.errorUnionPayload().hasRuntimeBits(mod)) { |
| ... | ... | @@ -5673,7 +5683,7 @@ fn airErrUnionPayloadPtrSet(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5673 | 5683 | const writer = f.object.writer(); |
| 5674 | 5684 | const ty_op = f.air.instructions.items(.data)[inst].ty_op; |
| 5675 | 5685 | const operand = try f.resolveInst(ty_op.operand); |
| 5676 | const error_union_ty = f.typeOf(ty_op.operand).childType(); | |
| 5686 | const error_union_ty = f.typeOf(ty_op.operand).childType(mod); | |
| 5677 | 5687 | |
| 5678 | 5688 | const error_ty = error_union_ty.errorUnionSet(); |
| 5679 | 5689 | const payload_ty = error_union_ty.errorUnionPayload(); |
| ... | ... | @@ -5761,7 +5771,7 @@ fn airIsErr(f: *Function, inst: Air.Inst.Index, is_ptr: bool, operator: []const |
| 5761 | 5771 | try reap(f, inst, &.{un_op}); |
| 5762 | 5772 | const operand_ty = f.typeOf(un_op); |
| 5763 | 5773 | const local = try f.allocLocal(inst, Type.bool); |
| 5764 | const err_union_ty = if (is_ptr) operand_ty.childType() else operand_ty; | |
| 5774 | const err_union_ty = if (is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 5765 | 5775 | const payload_ty = err_union_ty.errorUnionPayload(); |
| 5766 | 5776 | const error_ty = err_union_ty.errorUnionSet(); |
| 5767 | 5777 | |
| ... | ... | @@ -5795,7 +5805,7 @@ fn airArrayToSlice(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5795 | 5805 | const inst_ty = f.typeOfIndex(inst); |
| 5796 | 5806 | const writer = f.object.writer(); |
| 5797 | 5807 | const local = try f.allocLocal(inst, inst_ty); |
| 5798 | const array_ty = f.typeOf(ty_op.operand).childType(); | |
| 5808 | const array_ty = f.typeOf(ty_op.operand).childType(mod); | |
| 5799 | 5809 | |
| 5800 | 5810 | try f.writeCValueMember(writer, local, .{ .identifier = "ptr" }); |
| 5801 | 5811 | try writer.writeAll(" = "); |
| ... | ... | @@ -5811,7 +5821,7 @@ fn airArrayToSlice(f: *Function, inst: Air.Inst.Index) !CValue { |
| 5811 | 5821 | } else try f.writeCValue(writer, operand, .Initializer); |
| 5812 | 5822 | try writer.writeAll("; "); |
| 5813 | 5823 | |
| 5814 | const array_len = array_ty.arrayLen(); | |
| 5824 | const array_len = array_ty.arrayLen(mod); | |
| 5815 | 5825 | var len_pl: Value.Payload.U64 = .{ .base = .{ .tag = .int_u64 }, .data = array_len }; |
| 5816 | 5826 | const len_val = Value.initPayload(&len_pl.base); |
| 5817 | 5827 | try f.writeCValueMember(writer, local, .{ .identifier = "len" }); |
| ... | ... | @@ -6050,7 +6060,7 @@ fn airCmpxchg(f: *Function, inst: Air.Inst.Index, flavor: [*:0]const u8) !CValue |
| 6050 | 6060 | const expected_value = try f.resolveInst(extra.expected_value); |
| 6051 | 6061 | const new_value = try f.resolveInst(extra.new_value); |
| 6052 | 6062 | const ptr_ty = f.typeOf(extra.ptr); |
| 6053 | const ty = ptr_ty.childType(); | |
| 6063 | const ty = ptr_ty.childType(mod); | |
| 6054 | 6064 | |
| 6055 | 6065 | const writer = f.object.writer(); |
| 6056 | 6066 | const new_value_mat = try Materialize.start(f, inst, writer, ty, new_value); |
| ... | ... | @@ -6152,7 +6162,7 @@ fn airAtomicRmw(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6152 | 6162 | const extra = f.air.extraData(Air.AtomicRmw, pl_op.payload).data; |
| 6153 | 6163 | const inst_ty = f.typeOfIndex(inst); |
| 6154 | 6164 | const ptr_ty = f.typeOf(pl_op.operand); |
| 6155 | const ty = ptr_ty.childType(); | |
| 6165 | const ty = ptr_ty.childType(mod); | |
| 6156 | 6166 | const ptr = try f.resolveInst(pl_op.operand); |
| 6157 | 6167 | const operand = try f.resolveInst(extra.operand); |
| 6158 | 6168 | |
| ... | ... | @@ -6207,7 +6217,7 @@ fn airAtomicLoad(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6207 | 6217 | const ptr = try f.resolveInst(atomic_load.ptr); |
| 6208 | 6218 | try reap(f, inst, &.{atomic_load.ptr}); |
| 6209 | 6219 | const ptr_ty = f.typeOf(atomic_load.ptr); |
| 6210 | const ty = ptr_ty.childType(); | |
| 6220 | const ty = ptr_ty.childType(mod); | |
| 6211 | 6221 | |
| 6212 | 6222 | const repr_ty = if (ty.isRuntimeFloat()) |
| 6213 | 6223 | mod.intType(.unsigned, @intCast(u16, ty.abiSize(mod) * 8)) catch unreachable |
| ... | ... | @@ -6241,7 +6251,7 @@ fn airAtomicStore(f: *Function, inst: Air.Inst.Index, order: [*:0]const u8) !CVa |
| 6241 | 6251 | const mod = f.object.dg.module; |
| 6242 | 6252 | const bin_op = f.air.instructions.items(.data)[inst].bin_op; |
| 6243 | 6253 | const ptr_ty = f.typeOf(bin_op.lhs); |
| 6244 | const ty = ptr_ty.childType(); | |
| 6254 | const ty = ptr_ty.childType(mod); | |
| 6245 | 6255 | const ptr = try f.resolveInst(bin_op.lhs); |
| 6246 | 6256 | const element = try f.resolveInst(bin_op.rhs); |
| 6247 | 6257 | |
| ... | ... | @@ -6299,7 +6309,7 @@ fn airMemset(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 6299 | 6309 | } |
| 6300 | 6310 | |
| 6301 | 6311 | try writer.writeAll("memset("); |
| 6302 | switch (dest_ty.ptrSize()) { | |
| 6312 | switch (dest_ty.ptrSize(mod)) { | |
| 6303 | 6313 | .Slice => { |
| 6304 | 6314 | try f.writeCValueMember(writer, dest_slice, .{ .identifier = "ptr" }); |
| 6305 | 6315 | try writer.writeAll(", 0xaa, "); |
| ... | ... | @@ -6311,8 +6321,8 @@ fn airMemset(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 6311 | 6321 | } |
| 6312 | 6322 | }, |
| 6313 | 6323 | .One => { |
| 6314 | const array_ty = dest_ty.childType(); | |
| 6315 | const len = array_ty.arrayLen() * elem_abi_size; | |
| 6324 | const array_ty = dest_ty.childType(mod); | |
| 6325 | const len = array_ty.arrayLen(mod) * elem_abi_size; | |
| 6316 | 6326 | |
| 6317 | 6327 | try f.writeCValue(writer, dest_slice, .FunctionArgument); |
| 6318 | 6328 | try writer.print(", 0xaa, {d});\n", .{len}); |
| ... | ... | @@ -6327,11 +6337,10 @@ fn airMemset(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 6327 | 6337 | // For the assignment in this loop, the array pointer needs to get |
| 6328 | 6338 | // casted to a regular pointer, otherwise an error like this occurs: |
| 6329 | 6339 | // error: array type 'uint32_t[20]' (aka 'unsigned int[20]') is not assignable |
| 6330 | var elem_ptr_ty_pl: Type.Payload.ElemType = .{ | |
| 6331 | .base = .{ .tag = .c_mut_pointer }, | |
| 6332 | .data = elem_ty, | |
| 6333 | }; | |
| 6334 | const elem_ptr_ty = Type.initPayload(&elem_ptr_ty_pl.base); | |
| 6340 | const elem_ptr_ty = try mod.ptrType(.{ | |
| 6341 | .size = .C, | |
| 6342 | .elem_type = elem_ty.ip_index, | |
| 6343 | }); | |
| 6335 | 6344 | |
| 6336 | 6345 | const index = try f.allocLocal(inst, Type.usize); |
| 6337 | 6346 | |
| ... | ... | @@ -6342,13 +6351,13 @@ fn airMemset(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 6342 | 6351 | try writer.writeAll("; "); |
| 6343 | 6352 | try f.writeCValue(writer, index, .Other); |
| 6344 | 6353 | try writer.writeAll(" != "); |
| 6345 | switch (dest_ty.ptrSize()) { | |
| 6354 | switch (dest_ty.ptrSize(mod)) { | |
| 6346 | 6355 | .Slice => { |
| 6347 | 6356 | try f.writeCValueMember(writer, dest_slice, .{ .identifier = "len" }); |
| 6348 | 6357 | }, |
| 6349 | 6358 | .One => { |
| 6350 | const array_ty = dest_ty.childType(); | |
| 6351 | try writer.print("{d}", .{array_ty.arrayLen()}); | |
| 6359 | const array_ty = dest_ty.childType(mod); | |
| 6360 | try writer.print("{d}", .{array_ty.arrayLen(mod)}); | |
| 6352 | 6361 | }, |
| 6353 | 6362 | .Many, .C => unreachable, |
| 6354 | 6363 | } |
| ... | ... | @@ -6377,7 +6386,7 @@ fn airMemset(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 6377 | 6386 | const bitcasted = try bitcast(f, Type.u8, value, elem_ty); |
| 6378 | 6387 | |
| 6379 | 6388 | try writer.writeAll("memset("); |
| 6380 | switch (dest_ty.ptrSize()) { | |
| 6389 | switch (dest_ty.ptrSize(mod)) { | |
| 6381 | 6390 | .Slice => { |
| 6382 | 6391 | try f.writeCValueMember(writer, dest_slice, .{ .identifier = "ptr" }); |
| 6383 | 6392 | try writer.writeAll(", "); |
| ... | ... | @@ -6387,8 +6396,8 @@ fn airMemset(f: *Function, inst: Air.Inst.Index, safety: bool) !CValue { |
| 6387 | 6396 | try writer.writeAll(");\n"); |
| 6388 | 6397 | }, |
| 6389 | 6398 | .One => { |
| 6390 | const array_ty = dest_ty.childType(); | |
| 6391 | const len = array_ty.arrayLen() * elem_abi_size; | |
| 6399 | const array_ty = dest_ty.childType(mod); | |
| 6400 | const len = array_ty.arrayLen(mod) * elem_abi_size; | |
| 6392 | 6401 | |
| 6393 | 6402 | try f.writeCValue(writer, dest_slice, .FunctionArgument); |
| 6394 | 6403 | try writer.writeAll(", "); |
| ... | ... | @@ -6416,9 +6425,9 @@ fn airMemcpy(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6416 | 6425 | try writer.writeAll(", "); |
| 6417 | 6426 | try writeSliceOrPtr(f, writer, src_ptr, src_ty); |
| 6418 | 6427 | try writer.writeAll(", "); |
| 6419 | switch (dest_ty.ptrSize()) { | |
| 6428 | switch (dest_ty.ptrSize(mod)) { | |
| 6420 | 6429 | .Slice => { |
| 6421 | const elem_ty = dest_ty.childType(); | |
| 6430 | const elem_ty = dest_ty.childType(mod); | |
| 6422 | 6431 | const elem_abi_size = elem_ty.abiSize(mod); |
| 6423 | 6432 | try f.writeCValueMember(writer, dest_ptr, .{ .identifier = "len" }); |
| 6424 | 6433 | if (elem_abi_size > 1) { |
| ... | ... | @@ -6428,10 +6437,10 @@ fn airMemcpy(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6428 | 6437 | } |
| 6429 | 6438 | }, |
| 6430 | 6439 | .One => { |
| 6431 | const array_ty = dest_ty.childType(); | |
| 6432 | const elem_ty = array_ty.childType(); | |
| 6440 | const array_ty = dest_ty.childType(mod); | |
| 6441 | const elem_ty = array_ty.childType(mod); | |
| 6433 | 6442 | const elem_abi_size = elem_ty.abiSize(mod); |
| 6434 | const len = array_ty.arrayLen() * elem_abi_size; | |
| 6443 | const len = array_ty.arrayLen(mod) * elem_abi_size; | |
| 6435 | 6444 | try writer.print("{d});\n", .{len}); |
| 6436 | 6445 | }, |
| 6437 | 6446 | .Many, .C => unreachable, |
| ... | ... | @@ -6448,7 +6457,7 @@ fn airSetUnionTag(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6448 | 6457 | const new_tag = try f.resolveInst(bin_op.rhs); |
| 6449 | 6458 | try reap(f, inst, &.{ bin_op.lhs, bin_op.rhs }); |
| 6450 | 6459 | |
| 6451 | const union_ty = f.typeOf(bin_op.lhs).childType(); | |
| 6460 | const union_ty = f.typeOf(bin_op.lhs).childType(mod); | |
| 6452 | 6461 | const layout = union_ty.unionGetLayout(mod); |
| 6453 | 6462 | if (layout.tag_size == 0) return .none; |
| 6454 | 6463 | const tag_ty = union_ty.unionTagTypeSafety().?; |
| ... | ... | @@ -6777,7 +6786,7 @@ fn airAggregateInit(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6777 | 6786 | const mod = f.object.dg.module; |
| 6778 | 6787 | const ty_pl = f.air.instructions.items(.data)[inst].ty_pl; |
| 6779 | 6788 | const inst_ty = f.typeOfIndex(inst); |
| 6780 | const len = @intCast(usize, inst_ty.arrayLen()); | |
| 6789 | const len = @intCast(usize, inst_ty.arrayLen(mod)); | |
| 6781 | 6790 | const elements = @ptrCast([]const Air.Inst.Ref, f.air.extra[ty_pl.payload..][0..len]); |
| 6782 | 6791 | const gpa = f.object.dg.gpa; |
| 6783 | 6792 | const resolved_elements = try gpa.alloc(CValue, elements.len); |
| ... | ... | @@ -6796,7 +6805,7 @@ fn airAggregateInit(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6796 | 6805 | const local = try f.allocLocal(inst, inst_ty); |
| 6797 | 6806 | switch (inst_ty.zigTypeTag(mod)) { |
| 6798 | 6807 | .Array, .Vector => { |
| 6799 | const elem_ty = inst_ty.childType(); | |
| 6808 | const elem_ty = inst_ty.childType(mod); | |
| 6800 | 6809 | const a = try Assignment.init(f, elem_ty); |
| 6801 | 6810 | for (resolved_elements, 0..) |element, i| { |
| 6802 | 6811 | try a.restart(f, writer); |
| ... | ... | @@ -6806,7 +6815,7 @@ fn airAggregateInit(f: *Function, inst: Air.Inst.Index) !CValue { |
| 6806 | 6815 | try f.writeCValue(writer, element, .Other); |
| 6807 | 6816 | try a.end(f, writer); |
| 6808 | 6817 | } |
| 6809 | if (inst_ty.sentinel()) |sentinel| { | |
| 6818 | if (inst_ty.sentinel(mod)) |sentinel| { | |
| 6810 | 6819 | try a.restart(f, writer); |
| 6811 | 6820 | try f.writeCValue(writer, local, .Other); |
| 6812 | 6821 | try writer.print("[{d}]", .{resolved_elements.len}); |
| ... | ... | @@ -7708,7 +7717,7 @@ const Vectorize = struct { |
| 7708 | 7717 | pub fn start(f: *Function, inst: Air.Inst.Index, writer: anytype, ty: Type) !Vectorize { |
| 7709 | 7718 | const mod = f.object.dg.module; |
| 7710 | 7719 | return if (ty.zigTypeTag(mod) == .Vector) index: { |
| 7711 | var len_pl = Value.Payload.U64{ .base = .{ .tag = .int_u64 }, .data = ty.vectorLen() }; | |
| 7720 | var len_pl = Value.Payload.U64{ .base = .{ .tag = .int_u64 }, .data = ty.vectorLen(mod) }; | |
| 7712 | 7721 | |
| 7713 | 7722 | const local = try f.allocLocal(inst, Type.usize); |
| 7714 | 7723 |
src/codegen/c/type.zig+4-5| ... | ... | @@ -1423,7 +1423,7 @@ pub const CType = extern union { |
| 1423 | 1423 | }), |
| 1424 | 1424 | |
| 1425 | 1425 | .Pointer => { |
| 1426 | const info = ty.ptrInfo().data; | |
| 1426 | const info = ty.ptrInfo(mod); | |
| 1427 | 1427 | switch (info.size) { |
| 1428 | 1428 | .Slice => { |
| 1429 | 1429 | if (switch (kind) { |
| ... | ... | @@ -1625,9 +1625,9 @@ pub const CType = extern union { |
| 1625 | 1625 | .Vector => .vector, |
| 1626 | 1626 | else => unreachable, |
| 1627 | 1627 | }; |
| 1628 | if (try lookup.typeToIndex(ty.childType(), kind)) |child_idx| { | |
| 1628 | if (try lookup.typeToIndex(ty.childType(mod), kind)) |child_idx| { | |
| 1629 | 1629 | self.storage = .{ .seq = .{ .base = .{ .tag = t }, .data = .{ |
| 1630 | .len = ty.arrayLenIncludingSentinel(), | |
| 1630 | .len = ty.arrayLenIncludingSentinel(mod), | |
| 1631 | 1631 | .elem_type = child_idx, |
| 1632 | 1632 | } } }; |
| 1633 | 1633 | self.value = .{ .cty = initPayload(&self.storage.seq) }; |
| ... | ... | @@ -1639,8 +1639,7 @@ pub const CType = extern union { |
| 1639 | 1639 | }, |
| 1640 | 1640 | |
| 1641 | 1641 | .Optional => { |
| 1642 | var buf: Type.Payload.ElemType = undefined; | |
| 1643 | const payload_ty = ty.optionalChild(&buf); | |
| 1642 | const payload_ty = ty.optionalChild(mod); | |
| 1644 | 1643 | if (payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 1645 | 1644 | if (ty.optionalReprIsPayload(mod)) { |
| 1646 | 1645 | try self.initType(payload_ty, kind, lookup); |
src/codegen/llvm.zig+144-182| ... | ... | @@ -597,7 +597,7 @@ pub const Object = struct { |
| 597 | 597 | llvm_usize_ty, |
| 598 | 598 | }; |
| 599 | 599 | const llvm_slice_ty = self.context.structType(&type_fields, type_fields.len, .False); |
| 600 | const slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 600 | const slice_ty = Type.const_slice_u8_sentinel_0; | |
| 601 | 601 | const slice_alignment = slice_ty.abiAlignment(mod); |
| 602 | 602 | |
| 603 | 603 | const error_name_list = mod.error_name_list.items; |
| ... | ... | @@ -1071,7 +1071,7 @@ pub const Object = struct { |
| 1071 | 1071 | .slice => { |
| 1072 | 1072 | assert(!it.byval_attr); |
| 1073 | 1073 | const param_ty = fn_info.param_types[it.zig_index - 1]; |
| 1074 | const ptr_info = param_ty.ptrInfo().data; | |
| 1074 | const ptr_info = param_ty.ptrInfo(mod); | |
| 1075 | 1075 | |
| 1076 | 1076 | if (math.cast(u5, it.zig_index - 1)) |i| { |
| 1077 | 1077 | if (@truncate(u1, fn_info.noalias_bits >> i) != 0) { |
| ... | ... | @@ -1596,7 +1596,7 @@ pub const Object = struct { |
| 1596 | 1596 | }, |
| 1597 | 1597 | .Pointer => { |
| 1598 | 1598 | // Normalize everything that the debug info does not represent. |
| 1599 | const ptr_info = ty.ptrInfo().data; | |
| 1599 | const ptr_info = ty.ptrInfo(mod); | |
| 1600 | 1600 | |
| 1601 | 1601 | if (ptr_info.sentinel != null or |
| 1602 | 1602 | ptr_info.@"addrspace" != .generic or |
| ... | ... | @@ -1755,8 +1755,8 @@ pub const Object = struct { |
| 1755 | 1755 | const array_di_ty = dib.createArrayType( |
| 1756 | 1756 | ty.abiSize(mod) * 8, |
| 1757 | 1757 | ty.abiAlignment(mod) * 8, |
| 1758 | try o.lowerDebugType(ty.childType(), .full), | |
| 1759 | @intCast(c_int, ty.arrayLen()), | |
| 1758 | try o.lowerDebugType(ty.childType(mod), .full), | |
| 1759 | @intCast(c_int, ty.arrayLen(mod)), | |
| 1760 | 1760 | ); |
| 1761 | 1761 | // The recursive call to `lowerDebugType` means we can't use `gop` anymore. |
| 1762 | 1762 | try o.di_type_map.putContext(gpa, ty, AnnotatedDITypePtr.initFull(array_di_ty), .{ .mod = o.module }); |
| ... | ... | @@ -1781,14 +1781,14 @@ pub const Object = struct { |
| 1781 | 1781 | break :blk dib.createBasicType(name, info.bits, dwarf_encoding); |
| 1782 | 1782 | }, |
| 1783 | 1783 | .Bool => dib.createBasicType("bool", 1, DW.ATE.boolean), |
| 1784 | else => try o.lowerDebugType(ty.childType(), .full), | |
| 1784 | else => try o.lowerDebugType(ty.childType(mod), .full), | |
| 1785 | 1785 | }; |
| 1786 | 1786 | |
| 1787 | 1787 | const vector_di_ty = dib.createVectorType( |
| 1788 | 1788 | ty.abiSize(mod) * 8, |
| 1789 | 1789 | ty.abiAlignment(mod) * 8, |
| 1790 | 1790 | elem_di_type, |
| 1791 | ty.vectorLen(), | |
| 1791 | ty.vectorLen(mod), | |
| 1792 | 1792 | ); |
| 1793 | 1793 | // The recursive call to `lowerDebugType` means we can't use `gop` anymore. |
| 1794 | 1794 | try o.di_type_map.putContext(gpa, ty, AnnotatedDITypePtr.initFull(vector_di_ty), .{ .mod = o.module }); |
| ... | ... | @@ -1797,8 +1797,7 @@ pub const Object = struct { |
| 1797 | 1797 | .Optional => { |
| 1798 | 1798 | const name = try ty.nameAlloc(gpa, o.module); |
| 1799 | 1799 | defer gpa.free(name); |
| 1800 | var buf: Type.Payload.ElemType = undefined; | |
| 1801 | const child_ty = ty.optionalChild(&buf); | |
| 1800 | const child_ty = ty.optionalChild(mod); | |
| 1802 | 1801 | if (!child_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 1803 | 1802 | const di_bits = 8; // lldb cannot handle non-byte sized types |
| 1804 | 1803 | const di_ty = dib.createBasicType(name, di_bits, DW.ATE.boolean); |
| ... | ... | @@ -2350,11 +2349,7 @@ pub const Object = struct { |
| 2350 | 2349 | try param_di_types.append(try o.lowerDebugType(di_ret_ty, .full)); |
| 2351 | 2350 | |
| 2352 | 2351 | if (sret) { |
| 2353 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 2354 | .base = .{ .tag = .single_mut_pointer }, | |
| 2355 | .data = fn_info.return_type, | |
| 2356 | }; | |
| 2357 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 2352 | const ptr_ty = try mod.singleMutPtrType(fn_info.return_type); | |
| 2358 | 2353 | try param_di_types.append(try o.lowerDebugType(ptr_ty, .full)); |
| 2359 | 2354 | } |
| 2360 | 2355 | } else { |
| ... | ... | @@ -2364,11 +2359,7 @@ pub const Object = struct { |
| 2364 | 2359 | if (fn_info.return_type.isError(mod) and |
| 2365 | 2360 | o.module.comp.bin_file.options.error_return_tracing) |
| 2366 | 2361 | { |
| 2367 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 2368 | .base = .{ .tag = .single_mut_pointer }, | |
| 2369 | .data = o.getStackTraceType(), | |
| 2370 | }; | |
| 2371 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 2362 | const ptr_ty = try mod.singleMutPtrType(o.getStackTraceType()); | |
| 2372 | 2363 | try param_di_types.append(try o.lowerDebugType(ptr_ty, .full)); |
| 2373 | 2364 | } |
| 2374 | 2365 | |
| ... | ... | @@ -2376,11 +2367,7 @@ pub const Object = struct { |
| 2376 | 2367 | if (!param_ty.hasRuntimeBitsIgnoreComptime(mod)) continue; |
| 2377 | 2368 | |
| 2378 | 2369 | if (isByRef(param_ty, mod)) { |
| 2379 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 2380 | .base = .{ .tag = .single_mut_pointer }, | |
| 2381 | .data = param_ty, | |
| 2382 | }; | |
| 2383 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 2370 | const ptr_ty = try mod.singleMutPtrType(param_ty); | |
| 2384 | 2371 | try param_di_types.append(try o.lowerDebugType(ptr_ty, .full)); |
| 2385 | 2372 | } else { |
| 2386 | 2373 | try param_di_types.append(try o.lowerDebugType(param_ty, .full)); |
| ... | ... | @@ -2843,7 +2830,7 @@ pub const DeclGen = struct { |
| 2843 | 2830 | }; |
| 2844 | 2831 | return dg.context.structType(&fields, fields.len, .False); |
| 2845 | 2832 | } |
| 2846 | const ptr_info = t.ptrInfo().data; | |
| 2833 | const ptr_info = t.ptrInfo(mod); | |
| 2847 | 2834 | const llvm_addrspace = toLlvmAddressSpace(ptr_info.@"addrspace", target); |
| 2848 | 2835 | return dg.context.pointerType(llvm_addrspace); |
| 2849 | 2836 | }, |
| ... | ... | @@ -2866,19 +2853,18 @@ pub const DeclGen = struct { |
| 2866 | 2853 | return llvm_struct_ty; |
| 2867 | 2854 | }, |
| 2868 | 2855 | .Array => { |
| 2869 | const elem_ty = t.childType(); | |
| 2856 | const elem_ty = t.childType(mod); | |
| 2870 | 2857 | assert(elem_ty.onePossibleValue(mod) == null); |
| 2871 | 2858 | const elem_llvm_ty = try dg.lowerType(elem_ty); |
| 2872 | const total_len = t.arrayLen() + @boolToInt(t.sentinel() != null); | |
| 2859 | const total_len = t.arrayLen(mod) + @boolToInt(t.sentinel(mod) != null); | |
| 2873 | 2860 | return elem_llvm_ty.arrayType(@intCast(c_uint, total_len)); |
| 2874 | 2861 | }, |
| 2875 | 2862 | .Vector => { |
| 2876 | const elem_type = try dg.lowerType(t.childType()); | |
| 2877 | return elem_type.vectorType(t.vectorLen()); | |
| 2863 | const elem_type = try dg.lowerType(t.childType(mod)); | |
| 2864 | return elem_type.vectorType(t.vectorLen(mod)); | |
| 2878 | 2865 | }, |
| 2879 | 2866 | .Optional => { |
| 2880 | var buf: Type.Payload.ElemType = undefined; | |
| 2881 | const child_ty = t.optionalChild(&buf); | |
| 2867 | const child_ty = t.optionalChild(mod); | |
| 2882 | 2868 | if (!child_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 2883 | 2869 | return dg.context.intType(8); |
| 2884 | 2870 | } |
| ... | ... | @@ -3173,11 +3159,7 @@ pub const DeclGen = struct { |
| 3173 | 3159 | if (fn_info.return_type.isError(mod) and |
| 3174 | 3160 | mod.comp.bin_file.options.error_return_tracing) |
| 3175 | 3161 | { |
| 3176 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 3177 | .base = .{ .tag = .single_mut_pointer }, | |
| 3178 | .data = dg.object.getStackTraceType(), | |
| 3179 | }; | |
| 3180 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 3162 | const ptr_ty = try mod.singleMutPtrType(dg.object.getStackTraceType()); | |
| 3181 | 3163 | try llvm_params.append(try dg.lowerType(ptr_ty)); |
| 3182 | 3164 | } |
| 3183 | 3165 | |
| ... | ... | @@ -3199,9 +3181,8 @@ pub const DeclGen = struct { |
| 3199 | 3181 | .slice => { |
| 3200 | 3182 | const param_ty = fn_info.param_types[it.zig_index - 1]; |
| 3201 | 3183 | var buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 3202 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 3203 | 3184 | const ptr_ty = if (param_ty.zigTypeTag(mod) == .Optional) |
| 3204 | param_ty.optionalChild(&opt_buf).slicePtrFieldType(&buf) | |
| 3185 | param_ty.optionalChild(mod).slicePtrFieldType(&buf) | |
| 3205 | 3186 | else |
| 3206 | 3187 | param_ty.slicePtrFieldType(&buf); |
| 3207 | 3188 | const ptr_llvm_ty = try dg.lowerType(ptr_ty); |
| ... | ... | @@ -3247,7 +3228,7 @@ pub const DeclGen = struct { |
| 3247 | 3228 | const lower_elem_ty = switch (elem_ty.zigTypeTag(mod)) { |
| 3248 | 3229 | .Opaque => true, |
| 3249 | 3230 | .Fn => !elem_ty.fnInfo().is_generic, |
| 3250 | .Array => elem_ty.childType().hasRuntimeBitsIgnoreComptime(mod), | |
| 3231 | .Array => elem_ty.childType(mod).hasRuntimeBitsIgnoreComptime(mod), | |
| 3251 | 3232 | else => elem_ty.hasRuntimeBitsIgnoreComptime(mod), |
| 3252 | 3233 | }; |
| 3253 | 3234 | const llvm_elem_ty = if (lower_elem_ty) |
| ... | ... | @@ -3417,7 +3398,7 @@ pub const DeclGen = struct { |
| 3417 | 3398 | return llvm_int.constIntToPtr(try dg.lowerType(tv.ty)); |
| 3418 | 3399 | }, |
| 3419 | 3400 | .field_ptr, .opt_payload_ptr, .eu_payload_ptr, .elem_ptr => { |
| 3420 | return dg.lowerParentPtr(tv.val, tv.ty.ptrInfo().data.bit_offset % 8 == 0); | |
| 3401 | return dg.lowerParentPtr(tv.val, tv.ty.ptrInfo(mod).bit_offset % 8 == 0); | |
| 3421 | 3402 | }, |
| 3422 | 3403 | .null_value, .zero => { |
| 3423 | 3404 | const llvm_type = try dg.lowerType(tv.ty); |
| ... | ... | @@ -3425,7 +3406,7 @@ pub const DeclGen = struct { |
| 3425 | 3406 | }, |
| 3426 | 3407 | .opt_payload => { |
| 3427 | 3408 | const payload = tv.val.castTag(.opt_payload).?.data; |
| 3428 | return dg.lowerParentPtr(payload, tv.ty.ptrInfo().data.bit_offset % 8 == 0); | |
| 3409 | return dg.lowerParentPtr(payload, tv.ty.ptrInfo(mod).bit_offset % 8 == 0); | |
| 3429 | 3410 | }, |
| 3430 | 3411 | else => |tag| return dg.todo("implement const of pointer type '{}' ({})", .{ |
| 3431 | 3412 | tv.ty.fmtDebug(), tag, |
| ... | ... | @@ -3436,14 +3417,14 @@ pub const DeclGen = struct { |
| 3436 | 3417 | const bytes = tv.val.castTag(.bytes).?.data; |
| 3437 | 3418 | return dg.context.constString( |
| 3438 | 3419 | bytes.ptr, |
| 3439 | @intCast(c_uint, tv.ty.arrayLenIncludingSentinel()), | |
| 3420 | @intCast(c_uint, tv.ty.arrayLenIncludingSentinel(mod)), | |
| 3440 | 3421 | .True, // Don't null terminate. Bytes has the sentinel, if any. |
| 3441 | 3422 | ); |
| 3442 | 3423 | }, |
| 3443 | 3424 | .str_lit => { |
| 3444 | 3425 | const str_lit = tv.val.castTag(.str_lit).?.data; |
| 3445 | 3426 | const bytes = dg.module.string_literal_bytes.items[str_lit.index..][0..str_lit.len]; |
| 3446 | if (tv.ty.sentinel()) |sent_val| { | |
| 3427 | if (tv.ty.sentinel(mod)) |sent_val| { | |
| 3447 | 3428 | const byte = @intCast(u8, sent_val.toUnsignedInt(mod)); |
| 3448 | 3429 | if (byte == 0 and bytes.len > 0) { |
| 3449 | 3430 | return dg.context.constString( |
| ... | ... | @@ -3472,9 +3453,9 @@ pub const DeclGen = struct { |
| 3472 | 3453 | }, |
| 3473 | 3454 | .aggregate => { |
| 3474 | 3455 | const elem_vals = tv.val.castTag(.aggregate).?.data; |
| 3475 | const elem_ty = tv.ty.elemType(); | |
| 3456 | const elem_ty = tv.ty.childType(mod); | |
| 3476 | 3457 | const gpa = dg.gpa; |
| 3477 | const len = @intCast(usize, tv.ty.arrayLenIncludingSentinel()); | |
| 3458 | const len = @intCast(usize, tv.ty.arrayLenIncludingSentinel(mod)); | |
| 3478 | 3459 | const llvm_elems = try gpa.alloc(*llvm.Value, len); |
| 3479 | 3460 | defer gpa.free(llvm_elems); |
| 3480 | 3461 | var need_unnamed = false; |
| ... | ... | @@ -3498,9 +3479,9 @@ pub const DeclGen = struct { |
| 3498 | 3479 | }, |
| 3499 | 3480 | .repeated => { |
| 3500 | 3481 | const val = tv.val.castTag(.repeated).?.data; |
| 3501 | const elem_ty = tv.ty.elemType(); | |
| 3502 | const sentinel = tv.ty.sentinel(); | |
| 3503 | const len = @intCast(usize, tv.ty.arrayLen()); | |
| 3482 | const elem_ty = tv.ty.childType(mod); | |
| 3483 | const sentinel = tv.ty.sentinel(mod); | |
| 3484 | const len = @intCast(usize, tv.ty.arrayLen(mod)); | |
| 3504 | 3485 | const len_including_sent = len + @boolToInt(sentinel != null); |
| 3505 | 3486 | const gpa = dg.gpa; |
| 3506 | 3487 | const llvm_elems = try gpa.alloc(*llvm.Value, len_including_sent); |
| ... | ... | @@ -3534,8 +3515,8 @@ pub const DeclGen = struct { |
| 3534 | 3515 | } |
| 3535 | 3516 | }, |
| 3536 | 3517 | .empty_array_sentinel => { |
| 3537 | const elem_ty = tv.ty.elemType(); | |
| 3538 | const sent_val = tv.ty.sentinel().?; | |
| 3518 | const elem_ty = tv.ty.childType(mod); | |
| 3519 | const sent_val = tv.ty.sentinel(mod).?; | |
| 3539 | 3520 | const sentinel = try dg.lowerValue(.{ .ty = elem_ty, .val = sent_val }); |
| 3540 | 3521 | const llvm_elems: [1]*llvm.Value = .{sentinel}; |
| 3541 | 3522 | const need_unnamed = dg.isUnnamedType(elem_ty, llvm_elems[0]); |
| ... | ... | @@ -3550,8 +3531,7 @@ pub const DeclGen = struct { |
| 3550 | 3531 | }, |
| 3551 | 3532 | .Optional => { |
| 3552 | 3533 | comptime assert(optional_layout_version == 3); |
| 3553 | var buf: Type.Payload.ElemType = undefined; | |
| 3554 | const payload_ty = tv.ty.optionalChild(&buf); | |
| 3534 | const payload_ty = tv.ty.optionalChild(mod); | |
| 3555 | 3535 | |
| 3556 | 3536 | const llvm_i8 = dg.context.intType(8); |
| 3557 | 3537 | const is_pl = !tv.val.isNull(mod); |
| ... | ... | @@ -3897,10 +3877,10 @@ pub const DeclGen = struct { |
| 3897 | 3877 | .bytes => { |
| 3898 | 3878 | // Note, sentinel is not stored even if the type has a sentinel. |
| 3899 | 3879 | const bytes = tv.val.castTag(.bytes).?.data; |
| 3900 | const vector_len = @intCast(usize, tv.ty.arrayLen()); | |
| 3880 | const vector_len = @intCast(usize, tv.ty.arrayLen(mod)); | |
| 3901 | 3881 | assert(vector_len == bytes.len or vector_len + 1 == bytes.len); |
| 3902 | 3882 | |
| 3903 | const elem_ty = tv.ty.elemType(); | |
| 3883 | const elem_ty = tv.ty.childType(mod); | |
| 3904 | 3884 | const llvm_elems = try dg.gpa.alloc(*llvm.Value, vector_len); |
| 3905 | 3885 | defer dg.gpa.free(llvm_elems); |
| 3906 | 3886 | for (llvm_elems, 0..) |*elem, i| { |
| ... | ... | @@ -3923,9 +3903,9 @@ pub const DeclGen = struct { |
| 3923 | 3903 | // Note, sentinel is not stored even if the type has a sentinel. |
| 3924 | 3904 | // The value includes the sentinel in those cases. |
| 3925 | 3905 | const elem_vals = tv.val.castTag(.aggregate).?.data; |
| 3926 | const vector_len = @intCast(usize, tv.ty.arrayLen()); | |
| 3906 | const vector_len = @intCast(usize, tv.ty.arrayLen(mod)); | |
| 3927 | 3907 | assert(vector_len == elem_vals.len or vector_len + 1 == elem_vals.len); |
| 3928 | const elem_ty = tv.ty.elemType(); | |
| 3908 | const elem_ty = tv.ty.childType(mod); | |
| 3929 | 3909 | const llvm_elems = try dg.gpa.alloc(*llvm.Value, vector_len); |
| 3930 | 3910 | defer dg.gpa.free(llvm_elems); |
| 3931 | 3911 | for (llvm_elems, 0..) |*elem, i| { |
| ... | ... | @@ -3939,8 +3919,8 @@ pub const DeclGen = struct { |
| 3939 | 3919 | .repeated => { |
| 3940 | 3920 | // Note, sentinel is not stored even if the type has a sentinel. |
| 3941 | 3921 | const val = tv.val.castTag(.repeated).?.data; |
| 3942 | const elem_ty = tv.ty.elemType(); | |
| 3943 | const len = @intCast(usize, tv.ty.arrayLen()); | |
| 3922 | const elem_ty = tv.ty.childType(mod); | |
| 3923 | const len = @intCast(usize, tv.ty.arrayLen(mod)); | |
| 3944 | 3924 | const llvm_elems = try dg.gpa.alloc(*llvm.Value, len); |
| 3945 | 3925 | defer dg.gpa.free(llvm_elems); |
| 3946 | 3926 | for (llvm_elems) |*elem| { |
| ... | ... | @@ -3955,10 +3935,10 @@ pub const DeclGen = struct { |
| 3955 | 3935 | // Note, sentinel is not stored |
| 3956 | 3936 | const str_lit = tv.val.castTag(.str_lit).?.data; |
| 3957 | 3937 | const bytes = dg.module.string_literal_bytes.items[str_lit.index..][0..str_lit.len]; |
| 3958 | const vector_len = @intCast(usize, tv.ty.arrayLen()); | |
| 3938 | const vector_len = @intCast(usize, tv.ty.arrayLen(mod)); | |
| 3959 | 3939 | assert(vector_len == bytes.len); |
| 3960 | 3940 | |
| 3961 | const elem_ty = tv.ty.elemType(); | |
| 3941 | const elem_ty = tv.ty.childType(mod); | |
| 3962 | 3942 | const llvm_elems = try dg.gpa.alloc(*llvm.Value, vector_len); |
| 3963 | 3943 | defer dg.gpa.free(llvm_elems); |
| 3964 | 3944 | for (llvm_elems, 0..) |*elem, i| { |
| ... | ... | @@ -4006,13 +3986,10 @@ pub const DeclGen = struct { |
| 4006 | 3986 | ptr_val: Value, |
| 4007 | 3987 | decl_index: Module.Decl.Index, |
| 4008 | 3988 | ) Error!*llvm.Value { |
| 4009 | const decl = dg.module.declPtr(decl_index); | |
| 4010 | dg.module.markDeclAlive(decl); | |
| 4011 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 4012 | .base = .{ .tag = .single_mut_pointer }, | |
| 4013 | .data = decl.ty, | |
| 4014 | }; | |
| 4015 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 3989 | const mod = dg.module; | |
| 3990 | const decl = mod.declPtr(decl_index); | |
| 3991 | mod.markDeclAlive(decl); | |
| 3992 | const ptr_ty = try mod.singleMutPtrType(decl.ty); | |
| 4016 | 3993 | return try dg.lowerDeclRefValue(.{ .ty = ptr_ty, .val = ptr_val }, decl_index); |
| 4017 | 3994 | } |
| 4018 | 3995 | |
| ... | ... | @@ -4135,9 +4112,8 @@ pub const DeclGen = struct { |
| 4135 | 4112 | .opt_payload_ptr => { |
| 4136 | 4113 | const opt_payload_ptr = ptr_val.castTag(.opt_payload_ptr).?.data; |
| 4137 | 4114 | const parent_llvm_ptr = try dg.lowerParentPtr(opt_payload_ptr.container_ptr, true); |
| 4138 | var buf: Type.Payload.ElemType = undefined; | |
| 4139 | 4115 | |
| 4140 | const payload_ty = opt_payload_ptr.container_ty.optionalChild(&buf); | |
| 4116 | const payload_ty = opt_payload_ptr.container_ty.optionalChild(mod); | |
| 4141 | 4117 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod) or |
| 4142 | 4118 | payload_ty.optionalReprIsPayload(mod)) |
| 4143 | 4119 | { |
| ... | ... | @@ -4251,7 +4227,8 @@ pub const DeclGen = struct { |
| 4251 | 4227 | } |
| 4252 | 4228 | |
| 4253 | 4229 | fn lowerPtrToVoid(dg: *DeclGen, ptr_ty: Type) !*llvm.Value { |
| 4254 | const alignment = ptr_ty.ptrInfo().data.@"align"; | |
| 4230 | const mod = dg.module; | |
| 4231 | const alignment = ptr_ty.ptrInfo(mod).@"align"; | |
| 4255 | 4232 | // Even though we are pointing at something which has zero bits (e.g. `void`), |
| 4256 | 4233 | // Pointers are defined to have bits. So we must return something here. |
| 4257 | 4234 | // The value cannot be undefined, because we use the `nonnull` annotation |
| ... | ... | @@ -4374,7 +4351,7 @@ pub const DeclGen = struct { |
| 4374 | 4351 | ) void { |
| 4375 | 4352 | const mod = dg.module; |
| 4376 | 4353 | if (param_ty.isPtrAtRuntime(mod)) { |
| 4377 | const ptr_info = param_ty.ptrInfo().data; | |
| 4354 | const ptr_info = param_ty.ptrInfo(mod); | |
| 4378 | 4355 | if (math.cast(u5, param_index)) |i| { |
| 4379 | 4356 | if (@truncate(u1, fn_info.noalias_bits >> i) != 0) { |
| 4380 | 4357 | dg.addArgAttr(llvm_fn, llvm_arg_i, "noalias"); |
| ... | ... | @@ -4786,7 +4763,7 @@ pub const FuncGen = struct { |
| 4786 | 4763 | const mod = self.dg.module; |
| 4787 | 4764 | const zig_fn_ty = switch (callee_ty.zigTypeTag(mod)) { |
| 4788 | 4765 | .Fn => callee_ty, |
| 4789 | .Pointer => callee_ty.childType(), | |
| 4766 | .Pointer => callee_ty.childType(mod), | |
| 4790 | 4767 | else => unreachable, |
| 4791 | 4768 | }; |
| 4792 | 4769 | const fn_info = zig_fn_ty.fnInfo(); |
| ... | ... | @@ -5014,7 +4991,7 @@ pub const FuncGen = struct { |
| 5014 | 4991 | .slice => { |
| 5015 | 4992 | assert(!it.byval_attr); |
| 5016 | 4993 | const param_ty = fn_info.param_types[it.zig_index - 1]; |
| 5017 | const ptr_info = param_ty.ptrInfo().data; | |
| 4994 | const ptr_info = param_ty.ptrInfo(mod); | |
| 5018 | 4995 | const llvm_arg_i = it.llvm_index - 2; |
| 5019 | 4996 | |
| 5020 | 4997 | if (math.cast(u5, it.zig_index - 1)) |i| { |
| ... | ... | @@ -5098,11 +5075,7 @@ pub const FuncGen = struct { |
| 5098 | 5075 | const ret_ty = self.typeOf(un_op); |
| 5099 | 5076 | if (self.ret_ptr) |ret_ptr| { |
| 5100 | 5077 | const operand = try self.resolveInst(un_op); |
| 5101 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 5102 | .base = .{ .tag = .single_mut_pointer }, | |
| 5103 | .data = ret_ty, | |
| 5104 | }; | |
| 5105 | const ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 5078 | const ptr_ty = try mod.singleMutPtrType(ret_ty); | |
| 5106 | 5079 | try self.store(ret_ptr, ptr_ty, operand, .NotAtomic); |
| 5107 | 5080 | _ = self.builder.buildRetVoid(); |
| 5108 | 5081 | return null; |
| ... | ... | @@ -5150,11 +5123,11 @@ pub const FuncGen = struct { |
| 5150 | 5123 | } |
| 5151 | 5124 | |
| 5152 | 5125 | fn airRetLoad(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 5126 | const mod = self.dg.module; | |
| 5153 | 5127 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 5154 | 5128 | const ptr_ty = self.typeOf(un_op); |
| 5155 | const ret_ty = ptr_ty.childType(); | |
| 5129 | const ret_ty = ptr_ty.childType(mod); | |
| 5156 | 5130 | const fn_info = self.dg.decl.ty.fnInfo(); |
| 5157 | const mod = self.dg.module; | |
| 5158 | 5131 | if (!ret_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 5159 | 5132 | if (fn_info.return_type.isError(mod)) { |
| 5160 | 5133 | // Functions with an empty error set are emitted with an error code |
| ... | ... | @@ -5301,15 +5274,13 @@ pub const FuncGen = struct { |
| 5301 | 5274 | operand_ty: Type, |
| 5302 | 5275 | op: math.CompareOperator, |
| 5303 | 5276 | ) Allocator.Error!*llvm.Value { |
| 5304 | var opt_buffer: Type.Payload.ElemType = undefined; | |
| 5305 | ||
| 5306 | 5277 | const mod = self.dg.module; |
| 5307 | 5278 | const scalar_ty = operand_ty.scalarType(mod); |
| 5308 | 5279 | const int_ty = switch (scalar_ty.zigTypeTag(mod)) { |
| 5309 | 5280 | .Enum => scalar_ty.intTagType(), |
| 5310 | 5281 | .Int, .Bool, .Pointer, .ErrorSet => scalar_ty, |
| 5311 | 5282 | .Optional => blk: { |
| 5312 | const payload_ty = operand_ty.optionalChild(&opt_buffer); | |
| 5283 | const payload_ty = operand_ty.optionalChild(mod); | |
| 5313 | 5284 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod) or |
| 5314 | 5285 | operand_ty.optionalReprIsPayload(mod)) |
| 5315 | 5286 | { |
| ... | ... | @@ -5506,11 +5477,12 @@ pub const FuncGen = struct { |
| 5506 | 5477 | } |
| 5507 | 5478 | |
| 5508 | 5479 | fn airTryPtr(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 5480 | const mod = self.dg.module; | |
| 5509 | 5481 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 5510 | 5482 | const extra = self.air.extraData(Air.TryPtr, ty_pl.payload); |
| 5511 | 5483 | const err_union_ptr = try self.resolveInst(extra.data.ptr); |
| 5512 | 5484 | const body = self.air.extra[extra.end..][0..extra.data.body_len]; |
| 5513 | const err_union_ty = self.typeOf(extra.data.ptr).childType(); | |
| 5485 | const err_union_ty = self.typeOf(extra.data.ptr).childType(mod); | |
| 5514 | 5486 | const is_unused = self.liveness.isUnused(inst); |
| 5515 | 5487 | return lowerTry(self, err_union_ptr, body, err_union_ty, true, true, is_unused); |
| 5516 | 5488 | } |
| ... | ... | @@ -5661,9 +5633,9 @@ pub const FuncGen = struct { |
| 5661 | 5633 | const mod = self.dg.module; |
| 5662 | 5634 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 5663 | 5635 | const operand_ty = self.typeOf(ty_op.operand); |
| 5664 | const array_ty = operand_ty.childType(); | |
| 5636 | const array_ty = operand_ty.childType(mod); | |
| 5665 | 5637 | const llvm_usize = try self.dg.lowerType(Type.usize); |
| 5666 | const len = llvm_usize.constInt(array_ty.arrayLen(), .False); | |
| 5638 | const len = llvm_usize.constInt(array_ty.arrayLen(mod), .False); | |
| 5667 | 5639 | const slice_llvm_ty = try self.dg.lowerType(self.typeOfIndex(inst)); |
| 5668 | 5640 | const operand = try self.resolveInst(ty_op.operand); |
| 5669 | 5641 | if (!array_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| ... | ... | @@ -5806,20 +5778,20 @@ pub const FuncGen = struct { |
| 5806 | 5778 | const mod = fg.dg.module; |
| 5807 | 5779 | const target = mod.getTarget(); |
| 5808 | 5780 | const llvm_usize_ty = fg.context.intType(target.ptrBitWidth()); |
| 5809 | switch (ty.ptrSize()) { | |
| 5781 | switch (ty.ptrSize(mod)) { | |
| 5810 | 5782 | .Slice => { |
| 5811 | 5783 | const len = fg.builder.buildExtractValue(ptr, 1, ""); |
| 5812 | const elem_ty = ty.childType(); | |
| 5784 | const elem_ty = ty.childType(mod); | |
| 5813 | 5785 | const abi_size = elem_ty.abiSize(mod); |
| 5814 | 5786 | if (abi_size == 1) return len; |
| 5815 | 5787 | const abi_size_llvm_val = llvm_usize_ty.constInt(abi_size, .False); |
| 5816 | 5788 | return fg.builder.buildMul(len, abi_size_llvm_val, ""); |
| 5817 | 5789 | }, |
| 5818 | 5790 | .One => { |
| 5819 | const array_ty = ty.childType(); | |
| 5820 | const elem_ty = array_ty.childType(); | |
| 5791 | const array_ty = ty.childType(mod); | |
| 5792 | const elem_ty = array_ty.childType(mod); | |
| 5821 | 5793 | const abi_size = elem_ty.abiSize(mod); |
| 5822 | return llvm_usize_ty.constInt(array_ty.arrayLen() * abi_size, .False); | |
| 5794 | return llvm_usize_ty.constInt(array_ty.arrayLen(mod) * abi_size, .False); | |
| 5823 | 5795 | }, |
| 5824 | 5796 | .Many, .C => unreachable, |
| 5825 | 5797 | } |
| ... | ... | @@ -5832,10 +5804,11 @@ pub const FuncGen = struct { |
| 5832 | 5804 | } |
| 5833 | 5805 | |
| 5834 | 5806 | fn airPtrSliceFieldPtr(self: *FuncGen, inst: Air.Inst.Index, index: c_uint) !?*llvm.Value { |
| 5807 | const mod = self.dg.module; | |
| 5835 | 5808 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 5836 | 5809 | const slice_ptr = try self.resolveInst(ty_op.operand); |
| 5837 | 5810 | const slice_ptr_ty = self.typeOf(ty_op.operand); |
| 5838 | const slice_llvm_ty = try self.dg.lowerPtrElemTy(slice_ptr_ty.childType()); | |
| 5811 | const slice_llvm_ty = try self.dg.lowerPtrElemTy(slice_ptr_ty.childType(mod)); | |
| 5839 | 5812 | |
| 5840 | 5813 | return self.builder.buildStructGEP(slice_llvm_ty, slice_ptr, index, ""); |
| 5841 | 5814 | } |
| ... | ... | @@ -5847,7 +5820,7 @@ pub const FuncGen = struct { |
| 5847 | 5820 | const slice_ty = self.typeOf(bin_op.lhs); |
| 5848 | 5821 | const slice = try self.resolveInst(bin_op.lhs); |
| 5849 | 5822 | const index = try self.resolveInst(bin_op.rhs); |
| 5850 | const elem_ty = slice_ty.childType(); | |
| 5823 | const elem_ty = slice_ty.childType(mod); | |
| 5851 | 5824 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(elem_ty); |
| 5852 | 5825 | const base_ptr = self.builder.buildExtractValue(slice, 0, ""); |
| 5853 | 5826 | const indices: [1]*llvm.Value = .{index}; |
| ... | ... | @@ -5863,13 +5836,14 @@ pub const FuncGen = struct { |
| 5863 | 5836 | } |
| 5864 | 5837 | |
| 5865 | 5838 | fn airSliceElemPtr(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 5839 | const mod = self.dg.module; | |
| 5866 | 5840 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 5867 | 5841 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 5868 | 5842 | const slice_ty = self.typeOf(bin_op.lhs); |
| 5869 | 5843 | |
| 5870 | 5844 | const slice = try self.resolveInst(bin_op.lhs); |
| 5871 | 5845 | const index = try self.resolveInst(bin_op.rhs); |
| 5872 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(slice_ty.childType()); | |
| 5846 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(slice_ty.childType(mod)); | |
| 5873 | 5847 | const base_ptr = self.builder.buildExtractValue(slice, 0, ""); |
| 5874 | 5848 | const indices: [1]*llvm.Value = .{index}; |
| 5875 | 5849 | return self.builder.buildInBoundsGEP(llvm_elem_ty, base_ptr, &indices, indices.len, ""); |
| ... | ... | @@ -5884,7 +5858,7 @@ pub const FuncGen = struct { |
| 5884 | 5858 | const array_llvm_val = try self.resolveInst(bin_op.lhs); |
| 5885 | 5859 | const rhs = try self.resolveInst(bin_op.rhs); |
| 5886 | 5860 | const array_llvm_ty = try self.dg.lowerType(array_ty); |
| 5887 | const elem_ty = array_ty.childType(); | |
| 5861 | const elem_ty = array_ty.childType(mod); | |
| 5888 | 5862 | if (isByRef(array_ty, mod)) { |
| 5889 | 5863 | const indices: [2]*llvm.Value = .{ self.context.intType(32).constNull(), rhs }; |
| 5890 | 5864 | if (isByRef(elem_ty, mod)) { |
| ... | ... | @@ -5923,7 +5897,7 @@ pub const FuncGen = struct { |
| 5923 | 5897 | const inst = body_tail[0]; |
| 5924 | 5898 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 5925 | 5899 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 5926 | const elem_ty = ptr_ty.childType(); | |
| 5900 | const elem_ty = ptr_ty.childType(mod); | |
| 5927 | 5901 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(elem_ty); |
| 5928 | 5902 | const base_ptr = try self.resolveInst(bin_op.lhs); |
| 5929 | 5903 | const rhs = try self.resolveInst(bin_op.rhs); |
| ... | ... | @@ -5951,14 +5925,14 @@ pub const FuncGen = struct { |
| 5951 | 5925 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 5952 | 5926 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 5953 | 5927 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 5954 | const elem_ty = ptr_ty.childType(); | |
| 5928 | const elem_ty = ptr_ty.childType(mod); | |
| 5955 | 5929 | if (!elem_ty.hasRuntimeBitsIgnoreComptime(mod)) return self.dg.lowerPtrToVoid(ptr_ty); |
| 5956 | 5930 | |
| 5957 | 5931 | const base_ptr = try self.resolveInst(bin_op.lhs); |
| 5958 | 5932 | const rhs = try self.resolveInst(bin_op.rhs); |
| 5959 | 5933 | |
| 5960 | 5934 | const elem_ptr = self.air.getRefType(ty_pl.ty); |
| 5961 | if (elem_ptr.ptrInfo().data.vector_index != .none) return base_ptr; | |
| 5935 | if (elem_ptr.ptrInfo(mod).vector_index != .none) return base_ptr; | |
| 5962 | 5936 | |
| 5963 | 5937 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(elem_ty); |
| 5964 | 5938 | if (ptr_ty.isSinglePointer(mod)) { |
| ... | ... | @@ -6098,7 +6072,7 @@ pub const FuncGen = struct { |
| 6098 | 6072 | const field_ptr = try self.resolveInst(extra.field_ptr); |
| 6099 | 6073 | |
| 6100 | 6074 | const target = self.dg.module.getTarget(); |
| 6101 | const parent_ty = self.air.getRefType(ty_pl.ty).childType(); | |
| 6075 | const parent_ty = self.air.getRefType(ty_pl.ty).childType(mod); | |
| 6102 | 6076 | const field_offset = parent_ty.structFieldOffset(extra.field_index, mod); |
| 6103 | 6077 | |
| 6104 | 6078 | const res_ty = try self.dg.lowerType(self.air.getRefType(ty_pl.ty)); |
| ... | ... | @@ -6232,6 +6206,7 @@ pub const FuncGen = struct { |
| 6232 | 6206 | } |
| 6233 | 6207 | |
| 6234 | 6208 | fn airDbgVarPtr(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 6209 | const mod = self.dg.module; | |
| 6235 | 6210 | const dib = self.dg.object.di_builder orelse return null; |
| 6236 | 6211 | const pl_op = self.air.instructions.items(.data)[inst].pl_op; |
| 6237 | 6212 | const operand = try self.resolveInst(pl_op.operand); |
| ... | ... | @@ -6243,7 +6218,7 @@ pub const FuncGen = struct { |
| 6243 | 6218 | name.ptr, |
| 6244 | 6219 | self.di_file.?, |
| 6245 | 6220 | self.prev_dbg_line, |
| 6246 | try self.dg.object.lowerDebugType(ptr_ty.childType(), .full), | |
| 6221 | try self.dg.object.lowerDebugType(ptr_ty.childType(mod), .full), | |
| 6247 | 6222 | true, // always preserve |
| 6248 | 6223 | 0, // flags |
| 6249 | 6224 | ); |
| ... | ... | @@ -6365,7 +6340,7 @@ pub const FuncGen = struct { |
| 6365 | 6340 | const output_inst = try self.resolveInst(output); |
| 6366 | 6341 | const output_ty = self.typeOf(output); |
| 6367 | 6342 | assert(output_ty.zigTypeTag(mod) == .Pointer); |
| 6368 | const elem_llvm_ty = try self.dg.lowerPtrElemTy(output_ty.childType()); | |
| 6343 | const elem_llvm_ty = try self.dg.lowerPtrElemTy(output_ty.childType(mod)); | |
| 6369 | 6344 | |
| 6370 | 6345 | if (llvm_ret_indirect[i]) { |
| 6371 | 6346 | // Pass the result by reference as an indirect output (e.g. "=*m") |
| ... | ... | @@ -6466,7 +6441,7 @@ pub const FuncGen = struct { |
| 6466 | 6441 | // an elementtype(<ty>) attribute. |
| 6467 | 6442 | if (constraint[0] == '*') { |
| 6468 | 6443 | llvm_param_attrs[llvm_param_i] = llvm_elem_ty orelse |
| 6469 | try self.dg.lowerPtrElemTy(arg_ty.childType()); | |
| 6444 | try self.dg.lowerPtrElemTy(arg_ty.childType(mod)); | |
| 6470 | 6445 | } else { |
| 6471 | 6446 | llvm_param_attrs[llvm_param_i] = null; |
| 6472 | 6447 | } |
| ... | ... | @@ -6657,14 +6632,13 @@ pub const FuncGen = struct { |
| 6657 | 6632 | operand_is_ptr: bool, |
| 6658 | 6633 | pred: llvm.IntPredicate, |
| 6659 | 6634 | ) !?*llvm.Value { |
| 6635 | const mod = self.dg.module; | |
| 6660 | 6636 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 6661 | 6637 | const operand = try self.resolveInst(un_op); |
| 6662 | 6638 | const operand_ty = self.typeOf(un_op); |
| 6663 | const optional_ty = if (operand_is_ptr) operand_ty.childType() else operand_ty; | |
| 6639 | const optional_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 6664 | 6640 | const optional_llvm_ty = try self.dg.lowerType(optional_ty); |
| 6665 | var buf: Type.Payload.ElemType = undefined; | |
| 6666 | const payload_ty = optional_ty.optionalChild(&buf); | |
| 6667 | const mod = self.dg.module; | |
| 6641 | const payload_ty = optional_ty.optionalChild(mod); | |
| 6668 | 6642 | if (optional_ty.optionalReprIsPayload(mod)) { |
| 6669 | 6643 | const loaded = if (operand_is_ptr) |
| 6670 | 6644 | self.builder.buildLoad(optional_llvm_ty, operand, "") |
| ... | ... | @@ -6709,7 +6683,7 @@ pub const FuncGen = struct { |
| 6709 | 6683 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 6710 | 6684 | const operand = try self.resolveInst(un_op); |
| 6711 | 6685 | const operand_ty = self.typeOf(un_op); |
| 6712 | const err_union_ty = if (operand_is_ptr) operand_ty.childType() else operand_ty; | |
| 6686 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 6713 | 6687 | const payload_ty = err_union_ty.errorUnionPayload(); |
| 6714 | 6688 | const err_set_ty = try self.dg.lowerType(Type.anyerror); |
| 6715 | 6689 | const zero = err_set_ty.constNull(); |
| ... | ... | @@ -6748,9 +6722,8 @@ pub const FuncGen = struct { |
| 6748 | 6722 | const mod = self.dg.module; |
| 6749 | 6723 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 6750 | 6724 | const operand = try self.resolveInst(ty_op.operand); |
| 6751 | const optional_ty = self.typeOf(ty_op.operand).childType(); | |
| 6752 | var buf: Type.Payload.ElemType = undefined; | |
| 6753 | const payload_ty = optional_ty.optionalChild(&buf); | |
| 6725 | const optional_ty = self.typeOf(ty_op.operand).childType(mod); | |
| 6726 | const payload_ty = optional_ty.optionalChild(mod); | |
| 6754 | 6727 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 6755 | 6728 | // We have a pointer to a zero-bit value and we need to return |
| 6756 | 6729 | // a pointer to a zero-bit value. |
| ... | ... | @@ -6770,9 +6743,8 @@ pub const FuncGen = struct { |
| 6770 | 6743 | const mod = self.dg.module; |
| 6771 | 6744 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 6772 | 6745 | const operand = try self.resolveInst(ty_op.operand); |
| 6773 | const optional_ty = self.typeOf(ty_op.operand).childType(); | |
| 6774 | var buf: Type.Payload.ElemType = undefined; | |
| 6775 | const payload_ty = optional_ty.optionalChild(&buf); | |
| 6746 | const optional_ty = self.typeOf(ty_op.operand).childType(mod); | |
| 6747 | const payload_ty = optional_ty.optionalChild(mod); | |
| 6776 | 6748 | const non_null_bit = self.context.intType(8).constInt(1, .False); |
| 6777 | 6749 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 6778 | 6750 | // We have a pointer to a i8. We need to set it to 1 and then return the same pointer. |
| ... | ... | @@ -6827,9 +6799,9 @@ pub const FuncGen = struct { |
| 6827 | 6799 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 6828 | 6800 | const operand = try self.resolveInst(ty_op.operand); |
| 6829 | 6801 | const operand_ty = self.typeOf(ty_op.operand); |
| 6830 | const err_union_ty = if (operand_is_ptr) operand_ty.childType() else operand_ty; | |
| 6802 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 6831 | 6803 | const result_ty = self.typeOfIndex(inst); |
| 6832 | const payload_ty = if (operand_is_ptr) result_ty.childType() else result_ty; | |
| 6804 | const payload_ty = if (operand_is_ptr) result_ty.childType(mod) else result_ty; | |
| 6833 | 6805 | |
| 6834 | 6806 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 6835 | 6807 | return if (operand_is_ptr) operand else null; |
| ... | ... | @@ -6862,7 +6834,7 @@ pub const FuncGen = struct { |
| 6862 | 6834 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 6863 | 6835 | const operand = try self.resolveInst(ty_op.operand); |
| 6864 | 6836 | const operand_ty = self.typeOf(ty_op.operand); |
| 6865 | const err_union_ty = if (operand_is_ptr) operand_ty.childType() else operand_ty; | |
| 6837 | const err_union_ty = if (operand_is_ptr) operand_ty.childType(mod) else operand_ty; | |
| 6866 | 6838 | if (err_union_ty.errorUnionSet().errorSetIsEmpty(mod)) { |
| 6867 | 6839 | const err_llvm_ty = try self.dg.lowerType(Type.anyerror); |
| 6868 | 6840 | if (operand_is_ptr) { |
| ... | ... | @@ -6895,7 +6867,7 @@ pub const FuncGen = struct { |
| 6895 | 6867 | const mod = self.dg.module; |
| 6896 | 6868 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 6897 | 6869 | const operand = try self.resolveInst(ty_op.operand); |
| 6898 | const err_union_ty = self.typeOf(ty_op.operand).childType(); | |
| 6870 | const err_union_ty = self.typeOf(ty_op.operand).childType(mod); | |
| 6899 | 6871 | |
| 6900 | 6872 | const payload_ty = err_union_ty.errorUnionPayload(); |
| 6901 | 6873 | const non_error_val = try self.dg.lowerValue(.{ .ty = Type.anyerror, .val = Value.zero }); |
| ... | ... | @@ -6961,11 +6933,7 @@ pub const FuncGen = struct { |
| 6961 | 6933 | if (isByRef(optional_ty, mod)) { |
| 6962 | 6934 | const optional_ptr = self.buildAlloca(llvm_optional_ty, optional_ty.abiAlignment(mod)); |
| 6963 | 6935 | const payload_ptr = self.builder.buildStructGEP(llvm_optional_ty, optional_ptr, 0, ""); |
| 6964 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 6965 | .base = .{ .tag = .single_mut_pointer }, | |
| 6966 | .data = payload_ty, | |
| 6967 | }; | |
| 6968 | const payload_ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 6936 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); | |
| 6969 | 6937 | try self.store(payload_ptr, payload_ptr_ty, operand, .NotAtomic); |
| 6970 | 6938 | const non_null_ptr = self.builder.buildStructGEP(llvm_optional_ty, optional_ptr, 1, ""); |
| 6971 | 6939 | _ = self.builder.buildStore(non_null_bit, non_null_ptr); |
| ... | ... | @@ -6995,11 +6963,7 @@ pub const FuncGen = struct { |
| 6995 | 6963 | const store_inst = self.builder.buildStore(ok_err_code, err_ptr); |
| 6996 | 6964 | store_inst.setAlignment(Type.anyerror.abiAlignment(mod)); |
| 6997 | 6965 | const payload_ptr = self.builder.buildStructGEP(err_un_llvm_ty, result_ptr, payload_offset, ""); |
| 6998 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 6999 | .base = .{ .tag = .single_mut_pointer }, | |
| 7000 | .data = payload_ty, | |
| 7001 | }; | |
| 7002 | const payload_ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 6966 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); | |
| 7003 | 6967 | try self.store(payload_ptr, payload_ptr_ty, operand, .NotAtomic); |
| 7004 | 6968 | return result_ptr; |
| 7005 | 6969 | } |
| ... | ... | @@ -7027,11 +6991,7 @@ pub const FuncGen = struct { |
| 7027 | 6991 | const store_inst = self.builder.buildStore(operand, err_ptr); |
| 7028 | 6992 | store_inst.setAlignment(Type.anyerror.abiAlignment(mod)); |
| 7029 | 6993 | const payload_ptr = self.builder.buildStructGEP(err_un_llvm_ty, result_ptr, payload_offset, ""); |
| 7030 | var ptr_ty_payload: Type.Payload.ElemType = .{ | |
| 7031 | .base = .{ .tag = .single_mut_pointer }, | |
| 7032 | .data = payload_ty, | |
| 7033 | }; | |
| 7034 | const payload_ptr_ty = Type.initPayload(&ptr_ty_payload.base); | |
| 6994 | const payload_ptr_ty = try mod.singleMutPtrType(payload_ty); | |
| 7035 | 6995 | // TODO store undef to payload_ptr |
| 7036 | 6996 | _ = payload_ptr; |
| 7037 | 6997 | _ = payload_ptr_ty; |
| ... | ... | @@ -7076,7 +7036,7 @@ pub const FuncGen = struct { |
| 7076 | 7036 | const operand = try self.resolveInst(extra.rhs); |
| 7077 | 7037 | |
| 7078 | 7038 | const loaded_vector = blk: { |
| 7079 | const elem_llvm_ty = try self.dg.lowerType(vector_ptr_ty.childType()); | |
| 7039 | const elem_llvm_ty = try self.dg.lowerType(vector_ptr_ty.childType(mod)); | |
| 7080 | 7040 | const load_inst = self.builder.buildLoad(elem_llvm_ty, vector_ptr, ""); |
| 7081 | 7041 | load_inst.setAlignment(vector_ptr_ty.ptrAlignment(mod)); |
| 7082 | 7042 | load_inst.setVolatile(llvm.Bool.fromBool(vector_ptr_ty.isVolatilePtr())); |
| ... | ... | @@ -7287,7 +7247,7 @@ pub const FuncGen = struct { |
| 7287 | 7247 | const inst_llvm_ty = try self.dg.lowerType(inst_ty); |
| 7288 | 7248 | const scalar_bit_size_minus_one = scalar_ty.bitSize(mod) - 1; |
| 7289 | 7249 | const bit_size_minus_one = if (inst_ty.zigTypeTag(mod) == .Vector) const_vector: { |
| 7290 | const vec_len = inst_ty.vectorLen(); | |
| 7250 | const vec_len = inst_ty.vectorLen(mod); | |
| 7291 | 7251 | const scalar_llvm_ty = try self.dg.lowerType(scalar_ty); |
| 7292 | 7252 | |
| 7293 | 7253 | const shifts = try self.gpa.alloc(*llvm.Value, vec_len); |
| ... | ... | @@ -7361,7 +7321,7 @@ pub const FuncGen = struct { |
| 7361 | 7321 | if (scalar_ty.isSignedInt(mod)) { |
| 7362 | 7322 | const scalar_bit_size_minus_one = scalar_ty.bitSize(mod) - 1; |
| 7363 | 7323 | const bit_size_minus_one = if (inst_ty.zigTypeTag(mod) == .Vector) const_vector: { |
| 7364 | const vec_len = inst_ty.vectorLen(); | |
| 7324 | const vec_len = inst_ty.vectorLen(mod); | |
| 7365 | 7325 | const scalar_llvm_ty = try self.dg.lowerType(scalar_ty); |
| 7366 | 7326 | |
| 7367 | 7327 | const shifts = try self.gpa.alloc(*llvm.Value, vec_len); |
| ... | ... | @@ -7384,13 +7344,14 @@ pub const FuncGen = struct { |
| 7384 | 7344 | } |
| 7385 | 7345 | |
| 7386 | 7346 | fn airPtrAdd(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 7347 | const mod = self.dg.module; | |
| 7387 | 7348 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 7388 | 7349 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 7389 | 7350 | const ptr = try self.resolveInst(bin_op.lhs); |
| 7390 | 7351 | const offset = try self.resolveInst(bin_op.rhs); |
| 7391 | 7352 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 7392 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(ptr_ty.childType()); | |
| 7393 | switch (ptr_ty.ptrSize()) { | |
| 7353 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(ptr_ty.childType(mod)); | |
| 7354 | switch (ptr_ty.ptrSize(mod)) { | |
| 7394 | 7355 | .One => { |
| 7395 | 7356 | // It's a pointer to an array, so according to LLVM we need an extra GEP index. |
| 7396 | 7357 | const indices: [2]*llvm.Value = .{ self.context.intType(32).constNull(), offset }; |
| ... | ... | @@ -7409,14 +7370,15 @@ pub const FuncGen = struct { |
| 7409 | 7370 | } |
| 7410 | 7371 | |
| 7411 | 7372 | fn airPtrSub(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 7373 | const mod = self.dg.module; | |
| 7412 | 7374 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 7413 | 7375 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 7414 | 7376 | const ptr = try self.resolveInst(bin_op.lhs); |
| 7415 | 7377 | const offset = try self.resolveInst(bin_op.rhs); |
| 7416 | 7378 | const negative_offset = self.builder.buildNeg(offset, ""); |
| 7417 | 7379 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 7418 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(ptr_ty.childType()); | |
| 7419 | switch (ptr_ty.ptrSize()) { | |
| 7380 | const llvm_elem_ty = try self.dg.lowerPtrElemTy(ptr_ty.childType(mod)); | |
| 7381 | switch (ptr_ty.ptrSize(mod)) { | |
| 7420 | 7382 | .One => { |
| 7421 | 7383 | // It's a pointer to an array, so according to LLVM we need an extra GEP index. |
| 7422 | 7384 | const indices: [2]*llvm.Value = .{ |
| ... | ... | @@ -7587,7 +7549,7 @@ pub const FuncGen = struct { |
| 7587 | 7549 | }; |
| 7588 | 7550 | |
| 7589 | 7551 | if (ty.zigTypeTag(mod) == .Vector) { |
| 7590 | const vec_len = ty.vectorLen(); | |
| 7552 | const vec_len = ty.vectorLen(mod); | |
| 7591 | 7553 | const vector_result_ty = llvm_i32.vectorType(vec_len); |
| 7592 | 7554 | |
| 7593 | 7555 | var result = vector_result_ty.getUndef(); |
| ... | ... | @@ -7672,8 +7634,8 @@ pub const FuncGen = struct { |
| 7672 | 7634 | const shift_amt = int_llvm_ty.constInt(float_bits - 1, .False); |
| 7673 | 7635 | const sign_mask = one.constShl(shift_amt); |
| 7674 | 7636 | const result = if (ty.zigTypeTag(mod) == .Vector) blk: { |
| 7675 | const splat_sign_mask = self.builder.buildVectorSplat(ty.vectorLen(), sign_mask, ""); | |
| 7676 | const cast_ty = int_llvm_ty.vectorType(ty.vectorLen()); | |
| 7637 | const splat_sign_mask = self.builder.buildVectorSplat(ty.vectorLen(mod), sign_mask, ""); | |
| 7638 | const cast_ty = int_llvm_ty.vectorType(ty.vectorLen(mod)); | |
| 7677 | 7639 | const bitcasted_operand = self.builder.buildBitCast(params[0], cast_ty, ""); |
| 7678 | 7640 | break :blk self.builder.buildXor(bitcasted_operand, splat_sign_mask, ""); |
| 7679 | 7641 | } else blk: { |
| ... | ... | @@ -7720,7 +7682,7 @@ pub const FuncGen = struct { |
| 7720 | 7682 | const libc_fn = self.getLibcFunction(fn_name, param_types[0..params.len], scalar_llvm_ty); |
| 7721 | 7683 | if (ty.zigTypeTag(mod) == .Vector) { |
| 7722 | 7684 | const result = llvm_ty.getUndef(); |
| 7723 | return self.buildElementwiseCall(libc_fn, &params, result, ty.vectorLen()); | |
| 7685 | return self.buildElementwiseCall(libc_fn, &params, result, ty.vectorLen(mod)); | |
| 7724 | 7686 | } |
| 7725 | 7687 | |
| 7726 | 7688 | break :b libc_fn; |
| ... | ... | @@ -7887,7 +7849,7 @@ pub const FuncGen = struct { |
| 7887 | 7849 | const bits = lhs_scalar_llvm_ty.constInt(lhs_bits, .False); |
| 7888 | 7850 | const lhs_max = lhs_scalar_llvm_ty.constAllOnes(); |
| 7889 | 7851 | if (rhs_ty.zigTypeTag(mod) == .Vector) { |
| 7890 | const vec_len = rhs_ty.vectorLen(); | |
| 7852 | const vec_len = rhs_ty.vectorLen(mod); | |
| 7891 | 7853 | const bits_vec = self.builder.buildVectorSplat(vec_len, bits, ""); |
| 7892 | 7854 | const lhs_max_vec = self.builder.buildVectorSplat(vec_len, lhs_max, ""); |
| 7893 | 7855 | const in_range = self.builder.buildICmp(.ULT, rhs, bits_vec, ""); |
| ... | ... | @@ -8059,7 +8021,7 @@ pub const FuncGen = struct { |
| 8059 | 8021 | } |
| 8060 | 8022 | |
| 8061 | 8023 | if (operand_ty.zigTypeTag(mod) == .Vector and inst_ty.zigTypeTag(mod) == .Array) { |
| 8062 | const elem_ty = operand_ty.childType(); | |
| 8024 | const elem_ty = operand_ty.childType(mod); | |
| 8063 | 8025 | if (!result_is_ref) { |
| 8064 | 8026 | return self.dg.todo("implement bitcast vector to non-ref array", .{}); |
| 8065 | 8027 | } |
| ... | ... | @@ -8074,7 +8036,7 @@ pub const FuncGen = struct { |
| 8074 | 8036 | const llvm_usize = try self.dg.lowerType(Type.usize); |
| 8075 | 8037 | const llvm_u32 = self.context.intType(32); |
| 8076 | 8038 | const zero = llvm_usize.constNull(); |
| 8077 | const vector_len = operand_ty.arrayLen(); | |
| 8039 | const vector_len = operand_ty.arrayLen(mod); | |
| 8078 | 8040 | var i: u64 = 0; |
| 8079 | 8041 | while (i < vector_len) : (i += 1) { |
| 8080 | 8042 | const index_usize = llvm_usize.constInt(i, .False); |
| ... | ... | @@ -8087,7 +8049,7 @@ pub const FuncGen = struct { |
| 8087 | 8049 | } |
| 8088 | 8050 | return array_ptr; |
| 8089 | 8051 | } else if (operand_ty.zigTypeTag(mod) == .Array and inst_ty.zigTypeTag(mod) == .Vector) { |
| 8090 | const elem_ty = operand_ty.childType(); | |
| 8052 | const elem_ty = operand_ty.childType(mod); | |
| 8091 | 8053 | const llvm_vector_ty = try self.dg.lowerType(inst_ty); |
| 8092 | 8054 | if (!operand_is_ref) { |
| 8093 | 8055 | return self.dg.todo("implement bitcast non-ref array to vector", .{}); |
| ... | ... | @@ -8108,7 +8070,7 @@ pub const FuncGen = struct { |
| 8108 | 8070 | const llvm_usize = try self.dg.lowerType(Type.usize); |
| 8109 | 8071 | const llvm_u32 = self.context.intType(32); |
| 8110 | 8072 | const zero = llvm_usize.constNull(); |
| 8111 | const vector_len = operand_ty.arrayLen(); | |
| 8073 | const vector_len = operand_ty.arrayLen(mod); | |
| 8112 | 8074 | var vector = llvm_vector_ty.getUndef(); |
| 8113 | 8075 | var i: u64 = 0; |
| 8114 | 8076 | while (i < vector_len) : (i += 1) { |
| ... | ... | @@ -8207,7 +8169,7 @@ pub const FuncGen = struct { |
| 8207 | 8169 | fn airAlloc(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 8208 | 8170 | const mod = self.dg.module; |
| 8209 | 8171 | const ptr_ty = self.typeOfIndex(inst); |
| 8210 | const pointee_type = ptr_ty.childType(); | |
| 8172 | const pointee_type = ptr_ty.childType(mod); | |
| 8211 | 8173 | if (!pointee_type.isFnOrHasRuntimeBitsIgnoreComptime(mod)) return self.dg.lowerPtrToVoid(ptr_ty); |
| 8212 | 8174 | |
| 8213 | 8175 | const pointee_llvm_ty = try self.dg.lowerType(pointee_type); |
| ... | ... | @@ -8218,7 +8180,7 @@ pub const FuncGen = struct { |
| 8218 | 8180 | fn airRetPtr(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 8219 | 8181 | const mod = self.dg.module; |
| 8220 | 8182 | const ptr_ty = self.typeOfIndex(inst); |
| 8221 | const ret_ty = ptr_ty.childType(); | |
| 8183 | const ret_ty = ptr_ty.childType(mod); | |
| 8222 | 8184 | if (!ret_ty.isFnOrHasRuntimeBitsIgnoreComptime(mod)) return self.dg.lowerPtrToVoid(ptr_ty); |
| 8223 | 8185 | if (self.ret_ptr) |ret_ptr| return ret_ptr; |
| 8224 | 8186 | const ret_llvm_ty = try self.dg.lowerType(ret_ty); |
| ... | ... | @@ -8232,11 +8194,11 @@ pub const FuncGen = struct { |
| 8232 | 8194 | } |
| 8233 | 8195 | |
| 8234 | 8196 | fn airStore(self: *FuncGen, inst: Air.Inst.Index, safety: bool) !?*llvm.Value { |
| 8197 | const mod = self.dg.module; | |
| 8235 | 8198 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 8236 | 8199 | const dest_ptr = try self.resolveInst(bin_op.lhs); |
| 8237 | 8200 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 8238 | const operand_ty = ptr_ty.childType(); | |
| 8239 | const mod = self.dg.module; | |
| 8201 | const operand_ty = ptr_ty.childType(mod); | |
| 8240 | 8202 | |
| 8241 | 8203 | const val_is_undef = if (self.air.value(bin_op.rhs, mod)) |val| val.isUndefDeep() else false; |
| 8242 | 8204 | if (val_is_undef) { |
| ... | ... | @@ -8271,8 +8233,10 @@ pub const FuncGen = struct { |
| 8271 | 8233 | /// |
| 8272 | 8234 | /// The first instruction of `body_tail` is the one whose copy we want to elide. |
| 8273 | 8235 | fn canElideLoad(fg: *FuncGen, body_tail: []const Air.Inst.Index) bool { |
| 8236 | const mod = fg.dg.module; | |
| 8237 | const ip = &mod.intern_pool; | |
| 8274 | 8238 | for (body_tail[1..]) |body_inst| { |
| 8275 | switch (fg.liveness.categorizeOperand(fg.air, body_inst, body_tail[0])) { | |
| 8239 | switch (fg.liveness.categorizeOperand(fg.air, body_inst, body_tail[0], ip.*)) { | |
| 8276 | 8240 | .none => continue, |
| 8277 | 8241 | .write, .noret, .complex => return false, |
| 8278 | 8242 | .tomb => return true, |
| ... | ... | @@ -8288,7 +8252,7 @@ pub const FuncGen = struct { |
| 8288 | 8252 | const inst = body_tail[0]; |
| 8289 | 8253 | const ty_op = fg.air.instructions.items(.data)[inst].ty_op; |
| 8290 | 8254 | const ptr_ty = fg.typeOf(ty_op.operand); |
| 8291 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 8255 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 8292 | 8256 | const ptr = try fg.resolveInst(ty_op.operand); |
| 8293 | 8257 | |
| 8294 | 8258 | elide: { |
| ... | ... | @@ -8363,7 +8327,7 @@ pub const FuncGen = struct { |
| 8363 | 8327 | const ptr = try self.resolveInst(extra.ptr); |
| 8364 | 8328 | var expected_value = try self.resolveInst(extra.expected_value); |
| 8365 | 8329 | var new_value = try self.resolveInst(extra.new_value); |
| 8366 | const operand_ty = self.typeOf(extra.ptr).elemType(); | |
| 8330 | const operand_ty = self.typeOf(extra.ptr).childType(mod); | |
| 8367 | 8331 | const opt_abi_ty = self.dg.getAtomicAbiType(operand_ty, false); |
| 8368 | 8332 | if (opt_abi_ty) |abi_ty| { |
| 8369 | 8333 | // operand needs widening and truncating |
| ... | ... | @@ -8409,7 +8373,7 @@ pub const FuncGen = struct { |
| 8409 | 8373 | const extra = self.air.extraData(Air.AtomicRmw, pl_op.payload).data; |
| 8410 | 8374 | const ptr = try self.resolveInst(pl_op.operand); |
| 8411 | 8375 | const ptr_ty = self.typeOf(pl_op.operand); |
| 8412 | const operand_ty = ptr_ty.elemType(); | |
| 8376 | const operand_ty = ptr_ty.childType(mod); | |
| 8413 | 8377 | const operand = try self.resolveInst(extra.operand); |
| 8414 | 8378 | const is_signed_int = operand_ty.isSignedInt(mod); |
| 8415 | 8379 | const is_float = operand_ty.isRuntimeFloat(); |
| ... | ... | @@ -8464,7 +8428,7 @@ pub const FuncGen = struct { |
| 8464 | 8428 | const atomic_load = self.air.instructions.items(.data)[inst].atomic_load; |
| 8465 | 8429 | const ptr = try self.resolveInst(atomic_load.ptr); |
| 8466 | 8430 | const ptr_ty = self.typeOf(atomic_load.ptr); |
| 8467 | const ptr_info = ptr_ty.ptrInfo().data; | |
| 8431 | const ptr_info = ptr_ty.ptrInfo(mod); | |
| 8468 | 8432 | const elem_ty = ptr_info.pointee_type; |
| 8469 | 8433 | if (!elem_ty.hasRuntimeBitsIgnoreComptime(mod)) |
| 8470 | 8434 | return null; |
| ... | ... | @@ -8497,7 +8461,7 @@ pub const FuncGen = struct { |
| 8497 | 8461 | const mod = self.dg.module; |
| 8498 | 8462 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 8499 | 8463 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 8500 | const operand_ty = ptr_ty.childType(); | |
| 8464 | const operand_ty = ptr_ty.childType(mod); | |
| 8501 | 8465 | if (!operand_ty.isFnOrHasRuntimeBitsIgnoreComptime(mod)) return null; |
| 8502 | 8466 | const ptr = try self.resolveInst(bin_op.lhs); |
| 8503 | 8467 | var element = try self.resolveInst(bin_op.rhs); |
| ... | ... | @@ -8595,9 +8559,9 @@ pub const FuncGen = struct { |
| 8595 | 8559 | const end_block = self.context.appendBasicBlock(self.llvm_func, "InlineMemsetEnd"); |
| 8596 | 8560 | |
| 8597 | 8561 | const llvm_usize_ty = self.context.intType(target.ptrBitWidth()); |
| 8598 | const len = switch (ptr_ty.ptrSize()) { | |
| 8562 | const len = switch (ptr_ty.ptrSize(mod)) { | |
| 8599 | 8563 | .Slice => self.builder.buildExtractValue(dest_slice, 1, ""), |
| 8600 | .One => llvm_usize_ty.constInt(ptr_ty.childType().arrayLen(), .False), | |
| 8564 | .One => llvm_usize_ty.constInt(ptr_ty.childType(mod).arrayLen(mod), .False), | |
| 8601 | 8565 | .Many, .C => unreachable, |
| 8602 | 8566 | }; |
| 8603 | 8567 | const elem_llvm_ty = try self.dg.lowerType(elem_ty); |
| ... | ... | @@ -8665,7 +8629,7 @@ pub const FuncGen = struct { |
| 8665 | 8629 | fn airSetUnionTag(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 8666 | 8630 | const mod = self.dg.module; |
| 8667 | 8631 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 8668 | const un_ty = self.typeOf(bin_op.lhs).childType(); | |
| 8632 | const un_ty = self.typeOf(bin_op.lhs).childType(mod); | |
| 8669 | 8633 | const layout = un_ty.unionGetLayout(mod); |
| 8670 | 8634 | if (layout.tag_size == 0) return null; |
| 8671 | 8635 | const union_ptr = try self.resolveInst(bin_op.lhs); |
| ... | ... | @@ -8791,7 +8755,7 @@ pub const FuncGen = struct { |
| 8791 | 8755 | // The truncated result at the end will be the correct bswap |
| 8792 | 8756 | const scalar_llvm_ty = self.context.intType(bits + 8); |
| 8793 | 8757 | if (operand_ty.zigTypeTag(mod) == .Vector) { |
| 8794 | const vec_len = operand_ty.vectorLen(); | |
| 8758 | const vec_len = operand_ty.vectorLen(mod); | |
| 8795 | 8759 | operand_llvm_ty = scalar_llvm_ty.vectorType(vec_len); |
| 8796 | 8760 | |
| 8797 | 8761 | const shifts = try self.gpa.alloc(*llvm.Value, vec_len); |
| ... | ... | @@ -8980,7 +8944,7 @@ pub const FuncGen = struct { |
| 8980 | 8944 | defer self.gpa.free(fqn); |
| 8981 | 8945 | const llvm_fn_name = try std.fmt.allocPrintZ(arena, "__zig_tag_name_{s}", .{fqn}); |
| 8982 | 8946 | |
| 8983 | const slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 8947 | const slice_ty = Type.const_slice_u8_sentinel_0; | |
| 8984 | 8948 | const llvm_ret_ty = try self.dg.lowerType(slice_ty); |
| 8985 | 8949 | const usize_llvm_ty = try self.dg.lowerType(Type.usize); |
| 8986 | 8950 | const slice_alignment = slice_ty.abiAlignment(mod); |
| ... | ... | @@ -9097,10 +9061,11 @@ pub const FuncGen = struct { |
| 9097 | 9061 | } |
| 9098 | 9062 | |
| 9099 | 9063 | fn airSplat(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 9064 | const mod = self.dg.module; | |
| 9100 | 9065 | const ty_op = self.air.instructions.items(.data)[inst].ty_op; |
| 9101 | 9066 | const scalar = try self.resolveInst(ty_op.operand); |
| 9102 | 9067 | const vector_ty = self.typeOfIndex(inst); |
| 9103 | const len = vector_ty.vectorLen(); | |
| 9068 | const len = vector_ty.vectorLen(mod); | |
| 9104 | 9069 | return self.builder.buildVectorSplat(len, scalar, ""); |
| 9105 | 9070 | } |
| 9106 | 9071 | |
| ... | ... | @@ -9122,7 +9087,7 @@ pub const FuncGen = struct { |
| 9122 | 9087 | const b = try self.resolveInst(extra.b); |
| 9123 | 9088 | const mask = self.air.values[extra.mask]; |
| 9124 | 9089 | const mask_len = extra.mask_len; |
| 9125 | const a_len = self.typeOf(extra.a).vectorLen(); | |
| 9090 | const a_len = self.typeOf(extra.a).vectorLen(mod); | |
| 9126 | 9091 | |
| 9127 | 9092 | // LLVM uses integers larger than the length of the first array to |
| 9128 | 9093 | // index into the second array. This was deemed unnecessarily fragile |
| ... | ... | @@ -9298,14 +9263,14 @@ pub const FuncGen = struct { |
| 9298 | 9263 | .ty = scalar_ty, |
| 9299 | 9264 | .val = Value.initPayload(&init_value_payload.base), |
| 9300 | 9265 | }); |
| 9301 | return self.buildReducedCall(libc_fn, operand, operand_ty.vectorLen(), init_value); | |
| 9266 | return self.buildReducedCall(libc_fn, operand, operand_ty.vectorLen(mod), init_value); | |
| 9302 | 9267 | } |
| 9303 | 9268 | |
| 9304 | 9269 | fn airAggregateInit(self: *FuncGen, inst: Air.Inst.Index) !?*llvm.Value { |
| 9305 | 9270 | const mod = self.dg.module; |
| 9306 | 9271 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 9307 | 9272 | const result_ty = self.typeOfIndex(inst); |
| 9308 | const len = @intCast(usize, result_ty.arrayLen()); | |
| 9273 | const len = @intCast(usize, result_ty.arrayLen(mod)); | |
| 9309 | 9274 | const elements = @ptrCast([]const Air.Inst.Ref, self.air.extra[ty_pl.payload..][0..len]); |
| 9310 | 9275 | const llvm_result_ty = try self.dg.lowerType(result_ty); |
| 9311 | 9276 | |
| ... | ... | @@ -9400,7 +9365,7 @@ pub const FuncGen = struct { |
| 9400 | 9365 | const llvm_usize = try self.dg.lowerType(Type.usize); |
| 9401 | 9366 | const alloca_inst = self.buildAlloca(llvm_result_ty, result_ty.abiAlignment(mod)); |
| 9402 | 9367 | |
| 9403 | const array_info = result_ty.arrayInfo(); | |
| 9368 | const array_info = result_ty.arrayInfo(mod); | |
| 9404 | 9369 | var elem_ptr_payload: Type.Payload.Pointer = .{ |
| 9405 | 9370 | .data = .{ |
| 9406 | 9371 | .pointee_type = array_info.elem_type, |
| ... | ... | @@ -9720,7 +9685,7 @@ pub const FuncGen = struct { |
| 9720 | 9685 | } |
| 9721 | 9686 | |
| 9722 | 9687 | const mod = self.dg.module; |
| 9723 | const slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 9688 | const slice_ty = Type.const_slice_u8_sentinel_0; | |
| 9724 | 9689 | const slice_alignment = slice_ty.abiAlignment(mod); |
| 9725 | 9690 | const llvm_slice_ptr_ty = self.context.pointerType(0); // TODO: Address space |
| 9726 | 9691 | |
| ... | ... | @@ -9763,9 +9728,8 @@ pub const FuncGen = struct { |
| 9763 | 9728 | opt_ty: Type, |
| 9764 | 9729 | can_elide_load: bool, |
| 9765 | 9730 | ) !*llvm.Value { |
| 9766 | var buf: Type.Payload.ElemType = undefined; | |
| 9767 | const payload_ty = opt_ty.optionalChild(&buf); | |
| 9768 | 9731 | const mod = fg.dg.module; |
| 9732 | const payload_ty = opt_ty.optionalChild(mod); | |
| 9769 | 9733 | |
| 9770 | 9734 | if (isByRef(opt_ty, mod)) { |
| 9771 | 9735 | // We have a pointer and we need to return a pointer to the first field. |
| ... | ... | @@ -9827,13 +9791,13 @@ pub const FuncGen = struct { |
| 9827 | 9791 | struct_ptr_ty: Type, |
| 9828 | 9792 | field_index: u32, |
| 9829 | 9793 | ) !?*llvm.Value { |
| 9830 | const struct_ty = struct_ptr_ty.childType(); | |
| 9831 | 9794 | const mod = self.dg.module; |
| 9795 | const struct_ty = struct_ptr_ty.childType(mod); | |
| 9832 | 9796 | switch (struct_ty.zigTypeTag(mod)) { |
| 9833 | 9797 | .Struct => switch (struct_ty.containerLayout()) { |
| 9834 | 9798 | .Packed => { |
| 9835 | 9799 | const result_ty = self.typeOfIndex(inst); |
| 9836 | const result_ty_info = result_ty.ptrInfo().data; | |
| 9800 | const result_ty_info = result_ty.ptrInfo(mod); | |
| 9837 | 9801 | |
| 9838 | 9802 | if (result_ty_info.host_size != 0) { |
| 9839 | 9803 | // From LLVM's perspective, a pointer to a packed struct and a pointer |
| ... | ... | @@ -9919,7 +9883,7 @@ pub const FuncGen = struct { |
| 9919 | 9883 | /// For isByRef=false types, it creates a load instruction and returns it. |
| 9920 | 9884 | fn load(self: *FuncGen, ptr: *llvm.Value, ptr_ty: Type) !?*llvm.Value { |
| 9921 | 9885 | const mod = self.dg.module; |
| 9922 | const info = ptr_ty.ptrInfo().data; | |
| 9886 | const info = ptr_ty.ptrInfo(mod); | |
| 9923 | 9887 | if (!info.pointee_type.hasRuntimeBitsIgnoreComptime(mod)) return null; |
| 9924 | 9888 | |
| 9925 | 9889 | const ptr_alignment = info.alignment(mod); |
| ... | ... | @@ -9954,7 +9918,7 @@ pub const FuncGen = struct { |
| 9954 | 9918 | containing_int.setAlignment(ptr_alignment); |
| 9955 | 9919 | containing_int.setVolatile(ptr_volatile); |
| 9956 | 9920 | |
| 9957 | const elem_bits = @intCast(c_uint, ptr_ty.elemType().bitSize(mod)); | |
| 9921 | const elem_bits = @intCast(c_uint, ptr_ty.childType(mod).bitSize(mod)); | |
| 9958 | 9922 | const shift_amt = containing_int.typeOf().constInt(info.bit_offset, .False); |
| 9959 | 9923 | const shifted_value = self.builder.buildLShr(containing_int, shift_amt, ""); |
| 9960 | 9924 | const elem_llvm_ty = try self.dg.lowerType(info.pointee_type); |
| ... | ... | @@ -9992,9 +9956,9 @@ pub const FuncGen = struct { |
| 9992 | 9956 | elem: *llvm.Value, |
| 9993 | 9957 | ordering: llvm.AtomicOrdering, |
| 9994 | 9958 | ) !void { |
| 9995 | const info = ptr_ty.ptrInfo().data; | |
| 9996 | const elem_ty = info.pointee_type; | |
| 9997 | 9959 | const mod = self.dg.module; |
| 9960 | const info = ptr_ty.ptrInfo(mod); | |
| 9961 | const elem_ty = info.pointee_type; | |
| 9998 | 9962 | if (!elem_ty.isFnOrHasRuntimeBitsIgnoreComptime(mod)) { |
| 9999 | 9963 | return; |
| 10000 | 9964 | } |
| ... | ... | @@ -10026,7 +9990,7 @@ pub const FuncGen = struct { |
| 10026 | 9990 | assert(ordering == .NotAtomic); |
| 10027 | 9991 | containing_int.setAlignment(ptr_alignment); |
| 10028 | 9992 | containing_int.setVolatile(ptr_volatile); |
| 10029 | const elem_bits = @intCast(c_uint, ptr_ty.elemType().bitSize(mod)); | |
| 9993 | const elem_bits = @intCast(c_uint, ptr_ty.childType(mod).bitSize(mod)); | |
| 10030 | 9994 | const containing_int_ty = containing_int.typeOf(); |
| 10031 | 9995 | const shift_amt = containing_int_ty.constInt(info.bit_offset, .False); |
| 10032 | 9996 | // Convert to equally-sized integer type in order to perform the bit |
| ... | ... | @@ -10864,8 +10828,7 @@ const ParamTypeIterator = struct { |
| 10864 | 10828 | .Unspecified, .Inline => { |
| 10865 | 10829 | it.zig_index += 1; |
| 10866 | 10830 | it.llvm_index += 1; |
| 10867 | var buf: Type.Payload.ElemType = undefined; | |
| 10868 | if (ty.isSlice(mod) or (ty.zigTypeTag(mod) == .Optional and ty.optionalChild(&buf).isSlice(mod))) { | |
| 10831 | if (ty.isSlice(mod) or (ty.zigTypeTag(mod) == .Optional and ty.optionalChild(mod).isSlice(mod))) { | |
| 10869 | 10832 | it.llvm_index += 1; |
| 10870 | 10833 | return .slice; |
| 10871 | 10834 | } else if (isByRef(ty, mod)) { |
| ... | ... | @@ -11185,8 +11148,7 @@ fn isByRef(ty: Type, mod: *const Module) bool { |
| 11185 | 11148 | return true; |
| 11186 | 11149 | }, |
| 11187 | 11150 | .Optional => { |
| 11188 | var buf: Type.Payload.ElemType = undefined; | |
| 11189 | const payload_ty = ty.optionalChild(&buf); | |
| 11151 | const payload_ty = ty.optionalChild(mod); | |
| 11190 | 11152 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 11191 | 11153 | return false; |
| 11192 | 11154 | } |
src/codegen/spirv.zig+33-31| ... | ... | @@ -625,20 +625,20 @@ pub const DeclGen = struct { |
| 625 | 625 | .Array => switch (val.tag()) { |
| 626 | 626 | .aggregate => { |
| 627 | 627 | const elem_vals = val.castTag(.aggregate).?.data; |
| 628 | const elem_ty = ty.elemType(); | |
| 629 | const len = @intCast(u32, ty.arrayLenIncludingSentinel()); // TODO: limit spir-v to 32 bit arrays in a more elegant way. | |
| 628 | const elem_ty = ty.childType(mod); | |
| 629 | const len = @intCast(u32, ty.arrayLenIncludingSentinel(mod)); // TODO: limit spir-v to 32 bit arrays in a more elegant way. | |
| 630 | 630 | for (elem_vals[0..len]) |elem_val| { |
| 631 | 631 | try self.lower(elem_ty, elem_val); |
| 632 | 632 | } |
| 633 | 633 | }, |
| 634 | 634 | .repeated => { |
| 635 | 635 | const elem_val = val.castTag(.repeated).?.data; |
| 636 | const elem_ty = ty.elemType(); | |
| 637 | const len = @intCast(u32, ty.arrayLen()); | |
| 636 | const elem_ty = ty.childType(mod); | |
| 637 | const len = @intCast(u32, ty.arrayLen(mod)); | |
| 638 | 638 | for (0..len) |_| { |
| 639 | 639 | try self.lower(elem_ty, elem_val); |
| 640 | 640 | } |
| 641 | if (ty.sentinel()) |sentinel| { | |
| 641 | if (ty.sentinel(mod)) |sentinel| { | |
| 642 | 642 | try self.lower(elem_ty, sentinel); |
| 643 | 643 | } |
| 644 | 644 | }, |
| ... | ... | @@ -646,7 +646,7 @@ pub const DeclGen = struct { |
| 646 | 646 | const str_lit = val.castTag(.str_lit).?.data; |
| 647 | 647 | const bytes = dg.module.string_literal_bytes.items[str_lit.index..][0..str_lit.len]; |
| 648 | 648 | try self.addBytes(bytes); |
| 649 | if (ty.sentinel()) |sentinel| { | |
| 649 | if (ty.sentinel(mod)) |sentinel| { | |
| 650 | 650 | try self.addByte(@intCast(u8, sentinel.toUnsignedInt(mod))); |
| 651 | 651 | } |
| 652 | 652 | }, |
| ... | ... | @@ -706,8 +706,7 @@ pub const DeclGen = struct { |
| 706 | 706 | } |
| 707 | 707 | }, |
| 708 | 708 | .Optional => { |
| 709 | var opt_buf: Type.Payload.ElemType = undefined; | |
| 710 | const payload_ty = ty.optionalChild(&opt_buf); | |
| 709 | const payload_ty = ty.optionalChild(mod); | |
| 711 | 710 | const has_payload = !val.isNull(mod); |
| 712 | 711 | const abi_size = ty.abiSize(mod); |
| 713 | 712 | |
| ... | ... | @@ -1216,10 +1215,10 @@ pub const DeclGen = struct { |
| 1216 | 1215 | return try self.spv.resolve(.{ .float_type = .{ .bits = bits } }); |
| 1217 | 1216 | }, |
| 1218 | 1217 | .Array => { |
| 1219 | const elem_ty = ty.childType(); | |
| 1218 | const elem_ty = ty.childType(mod); | |
| 1220 | 1219 | const elem_ty_ref = try self.resolveType(elem_ty, .direct); |
| 1221 | const total_len = std.math.cast(u32, ty.arrayLenIncludingSentinel()) orelse { | |
| 1222 | return self.fail("array type of {} elements is too large", .{ty.arrayLenIncludingSentinel()}); | |
| 1220 | const total_len = std.math.cast(u32, ty.arrayLenIncludingSentinel(mod)) orelse { | |
| 1221 | return self.fail("array type of {} elements is too large", .{ty.arrayLenIncludingSentinel(mod)}); | |
| 1223 | 1222 | }; |
| 1224 | 1223 | return self.spv.arrayType(total_len, elem_ty_ref); |
| 1225 | 1224 | }, |
| ... | ... | @@ -1248,7 +1247,7 @@ pub const DeclGen = struct { |
| 1248 | 1247 | }, |
| 1249 | 1248 | }, |
| 1250 | 1249 | .Pointer => { |
| 1251 | const ptr_info = ty.ptrInfo().data; | |
| 1250 | const ptr_info = ty.ptrInfo(mod); | |
| 1252 | 1251 | |
| 1253 | 1252 | const storage_class = spvStorageClass(ptr_info.@"addrspace"); |
| 1254 | 1253 | const child_ty_ref = try self.resolveType(ptr_info.pointee_type, .indirect); |
| ... | ... | @@ -1280,8 +1279,8 @@ pub const DeclGen = struct { |
| 1280 | 1279 | // TODO: Properly verify sizes and child type. |
| 1281 | 1280 | |
| 1282 | 1281 | return try self.spv.resolve(.{ .vector_type = .{ |
| 1283 | .component_type = try self.resolveType(ty.elemType(), repr), | |
| 1284 | .component_count = @intCast(u32, ty.vectorLen()), | |
| 1282 | .component_type = try self.resolveType(ty.childType(mod), repr), | |
| 1283 | .component_count = @intCast(u32, ty.vectorLen(mod)), | |
| 1285 | 1284 | } }); |
| 1286 | 1285 | }, |
| 1287 | 1286 | .Struct => { |
| ... | ... | @@ -1335,8 +1334,7 @@ pub const DeclGen = struct { |
| 1335 | 1334 | } }); |
| 1336 | 1335 | }, |
| 1337 | 1336 | .Optional => { |
| 1338 | var buf: Type.Payload.ElemType = undefined; | |
| 1339 | const payload_ty = ty.optionalChild(&buf); | |
| 1337 | const payload_ty = ty.optionalChild(mod); | |
| 1340 | 1338 | if (!payload_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 1341 | 1339 | // Just use a bool. |
| 1342 | 1340 | // Note: Always generate the bool with indirect format, to save on some sanity |
| ... | ... | @@ -1685,7 +1683,8 @@ pub const DeclGen = struct { |
| 1685 | 1683 | } |
| 1686 | 1684 | |
| 1687 | 1685 | fn load(self: *DeclGen, ptr_ty: Type, ptr_id: IdRef) !IdRef { |
| 1688 | const value_ty = ptr_ty.childType(); | |
| 1686 | const mod = self.module; | |
| 1687 | const value_ty = ptr_ty.childType(mod); | |
| 1689 | 1688 | const indirect_value_ty_ref = try self.resolveType(value_ty, .indirect); |
| 1690 | 1689 | const result_id = self.spv.allocId(); |
| 1691 | 1690 | const access = spec.MemoryAccess.Extended{ |
| ... | ... | @@ -1701,7 +1700,8 @@ pub const DeclGen = struct { |
| 1701 | 1700 | } |
| 1702 | 1701 | |
| 1703 | 1702 | fn store(self: *DeclGen, ptr_ty: Type, ptr_id: IdRef, value_id: IdRef) !void { |
| 1704 | const value_ty = ptr_ty.childType(); | |
| 1703 | const mod = self.module; | |
| 1704 | const value_ty = ptr_ty.childType(mod); | |
| 1705 | 1705 | const indirect_value_id = try self.convertToIndirect(value_ty, value_id); |
| 1706 | 1706 | const access = spec.MemoryAccess.Extended{ |
| 1707 | 1707 | .Volatile = ptr_ty.isVolatilePtr(), |
| ... | ... | @@ -2072,7 +2072,7 @@ pub const DeclGen = struct { |
| 2072 | 2072 | const b = try self.resolve(extra.b); |
| 2073 | 2073 | const mask = self.air.values[extra.mask]; |
| 2074 | 2074 | const mask_len = extra.mask_len; |
| 2075 | const a_len = self.typeOf(extra.a).vectorLen(); | |
| 2075 | const a_len = self.typeOf(extra.a).vectorLen(mod); | |
| 2076 | 2076 | |
| 2077 | 2077 | const result_id = self.spv.allocId(); |
| 2078 | 2078 | const result_type_id = try self.resolveTypeId(ty); |
| ... | ... | @@ -2138,9 +2138,10 @@ pub const DeclGen = struct { |
| 2138 | 2138 | } |
| 2139 | 2139 | |
| 2140 | 2140 | fn ptrAdd(self: *DeclGen, result_ty: Type, ptr_ty: Type, ptr_id: IdRef, offset_id: IdRef) !IdRef { |
| 2141 | const mod = self.module; | |
| 2141 | 2142 | const result_ty_ref = try self.resolveType(result_ty, .direct); |
| 2142 | 2143 | |
| 2143 | switch (ptr_ty.ptrSize()) { | |
| 2144 | switch (ptr_ty.ptrSize(mod)) { | |
| 2144 | 2145 | .One => { |
| 2145 | 2146 | // Pointer to array |
| 2146 | 2147 | // TODO: Is this correct? |
| ... | ... | @@ -2498,7 +2499,7 @@ pub const DeclGen = struct { |
| 2498 | 2499 | // Construct new pointer type for the resulting pointer |
| 2499 | 2500 | const elem_ty = ptr_ty.elemType2(mod); // use elemType() so that we get T for *[N]T. |
| 2500 | 2501 | const elem_ty_ref = try self.resolveType(elem_ty, .direct); |
| 2501 | const elem_ptr_ty_ref = try self.spv.ptrType(elem_ty_ref, spvStorageClass(ptr_ty.ptrAddressSpace())); | |
| 2502 | const elem_ptr_ty_ref = try self.spv.ptrType(elem_ty_ref, spvStorageClass(ptr_ty.ptrAddressSpace(mod))); | |
| 2502 | 2503 | if (ptr_ty.isSinglePointer(mod)) { |
| 2503 | 2504 | // Pointer-to-array. In this case, the resulting pointer is not of the same type |
| 2504 | 2505 | // as the ptr_ty (we want a *T, not a *[N]T), and hence we need to use accessChain. |
| ... | ... | @@ -2516,7 +2517,7 @@ pub const DeclGen = struct { |
| 2516 | 2517 | const ty_pl = self.air.instructions.items(.data)[inst].ty_pl; |
| 2517 | 2518 | const bin_op = self.air.extraData(Air.Bin, ty_pl.payload).data; |
| 2518 | 2519 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 2519 | const elem_ty = ptr_ty.childType(); | |
| 2520 | const elem_ty = ptr_ty.childType(mod); | |
| 2520 | 2521 | // TODO: Make this return a null ptr or something |
| 2521 | 2522 | if (!elem_ty.hasRuntimeBitsIgnoreComptime(mod)) return null; |
| 2522 | 2523 | |
| ... | ... | @@ -2526,6 +2527,7 @@ pub const DeclGen = struct { |
| 2526 | 2527 | } |
| 2527 | 2528 | |
| 2528 | 2529 | fn airPtrElemVal(self: *DeclGen, inst: Air.Inst.Index) !?IdRef { |
| 2530 | const mod = self.module; | |
| 2529 | 2531 | const bin_op = self.air.instructions.items(.data)[inst].bin_op; |
| 2530 | 2532 | const ptr_ty = self.typeOf(bin_op.lhs); |
| 2531 | 2533 | const ptr_id = try self.resolve(bin_op.lhs); |
| ... | ... | @@ -2536,9 +2538,9 @@ pub const DeclGen = struct { |
| 2536 | 2538 | // If we have a pointer-to-array, construct an element pointer to use with load() |
| 2537 | 2539 | // If we pass ptr_ty directly, it will attempt to load the entire array rather than |
| 2538 | 2540 | // just an element. |
| 2539 | var elem_ptr_info = ptr_ty.ptrInfo(); | |
| 2540 | elem_ptr_info.data.size = .One; | |
| 2541 | const elem_ptr_ty = Type.initPayload(&elem_ptr_info.base); | |
| 2541 | var elem_ptr_info = ptr_ty.ptrInfo(mod); | |
| 2542 | elem_ptr_info.size = .One; | |
| 2543 | const elem_ptr_ty = try Type.ptr(undefined, mod, elem_ptr_info); | |
| 2542 | 2544 | |
| 2543 | 2545 | return try self.load(elem_ptr_ty, elem_ptr_id); |
| 2544 | 2546 | } |
| ... | ... | @@ -2586,7 +2588,7 @@ pub const DeclGen = struct { |
| 2586 | 2588 | field_index: u32, |
| 2587 | 2589 | ) !?IdRef { |
| 2588 | 2590 | const mod = self.module; |
| 2589 | const object_ty = object_ptr_ty.childType(); | |
| 2591 | const object_ty = object_ptr_ty.childType(mod); | |
| 2590 | 2592 | switch (object_ty.zigTypeTag(mod)) { |
| 2591 | 2593 | .Struct => switch (object_ty.containerLayout()) { |
| 2592 | 2594 | .Packed => unreachable, // TODO |
| ... | ... | @@ -2662,9 +2664,10 @@ pub const DeclGen = struct { |
| 2662 | 2664 | |
| 2663 | 2665 | fn airAlloc(self: *DeclGen, inst: Air.Inst.Index) !?IdRef { |
| 2664 | 2666 | if (self.liveness.isUnused(inst)) return null; |
| 2667 | const mod = self.module; | |
| 2665 | 2668 | const ptr_ty = self.typeOfIndex(inst); |
| 2666 | assert(ptr_ty.ptrAddressSpace() == .generic); | |
| 2667 | const child_ty = ptr_ty.childType(); | |
| 2669 | assert(ptr_ty.ptrAddressSpace(mod) == .generic); | |
| 2670 | const child_ty = ptr_ty.childType(mod); | |
| 2668 | 2671 | const child_ty_ref = try self.resolveType(child_ty, .indirect); |
| 2669 | 2672 | return try self.alloc(child_ty_ref, null); |
| 2670 | 2673 | } |
| ... | ... | @@ -2834,7 +2837,7 @@ pub const DeclGen = struct { |
| 2834 | 2837 | const mod = self.module; |
| 2835 | 2838 | const un_op = self.air.instructions.items(.data)[inst].un_op; |
| 2836 | 2839 | const ptr_ty = self.typeOf(un_op); |
| 2837 | const ret_ty = ptr_ty.childType(); | |
| 2840 | const ret_ty = ptr_ty.childType(mod); | |
| 2838 | 2841 | |
| 2839 | 2842 | if (!ret_ty.hasRuntimeBitsIgnoreComptime(mod)) { |
| 2840 | 2843 | try self.func.body.emit(self.spv.gpa, .OpReturn, {}); |
| ... | ... | @@ -2971,8 +2974,7 @@ pub const DeclGen = struct { |
| 2971 | 2974 | const operand_id = try self.resolve(un_op); |
| 2972 | 2975 | const optional_ty = self.typeOf(un_op); |
| 2973 | 2976 | |
| 2974 | var buf: Type.Payload.ElemType = undefined; | |
| 2975 | const payload_ty = optional_ty.optionalChild(&buf); | |
| 2977 | const payload_ty = optional_ty.optionalChild(mod); | |
| 2976 | 2978 | |
| 2977 | 2979 | const bool_ty_ref = try self.resolveType(Type.bool, .direct); |
| 2978 | 2980 |
src/codegen/spirv/Module.zig+2-1| ... | ... | @@ -11,7 +11,8 @@ const std = @import("std"); |
| 11 | 11 | const Allocator = std.mem.Allocator; |
| 12 | 12 | const assert = std.debug.assert; |
| 13 | 13 | |
| 14 | const ZigDecl = @import("../../Module.zig").Decl; | |
| 14 | const ZigModule = @import("../../Module.zig"); | |
| 15 | const ZigDecl = ZigModule.Decl; | |
| 15 | 16 | |
| 16 | 17 | const spec = @import("spec.zig"); |
| 17 | 18 | const Word = spec.Word; |
src/link/Dwarf.zig+5-6| ... | ... | @@ -219,8 +219,7 @@ pub const DeclState = struct { |
| 219 | 219 | try dbg_info_buffer.writer().print("{}\x00", .{ty.fmt(mod)}); |
| 220 | 220 | } else { |
| 221 | 221 | // Non-pointer optionals are structs: struct { .maybe = *, .val = * } |
| 222 | var buf = try arena.create(Type.Payload.ElemType); | |
| 223 | const payload_ty = ty.optionalChild(buf); | |
| 222 | const payload_ty = ty.optionalChild(mod); | |
| 224 | 223 | // DW.AT.structure_type |
| 225 | 224 | try dbg_info_buffer.append(@enumToInt(AbbrevKind.struct_type)); |
| 226 | 225 | // DW.AT.byte_size, DW.FORM.udata |
| ... | ... | @@ -304,7 +303,7 @@ pub const DeclState = struct { |
| 304 | 303 | // DW.AT.type, DW.FORM.ref4 |
| 305 | 304 | const index = dbg_info_buffer.items.len; |
| 306 | 305 | try dbg_info_buffer.resize(index + 4); |
| 307 | try self.addTypeRelocGlobal(atom_index, ty.childType(), @intCast(u32, index)); | |
| 306 | try self.addTypeRelocGlobal(atom_index, ty.childType(mod), @intCast(u32, index)); | |
| 308 | 307 | } |
| 309 | 308 | }, |
| 310 | 309 | .Array => { |
| ... | ... | @@ -315,7 +314,7 @@ pub const DeclState = struct { |
| 315 | 314 | // DW.AT.type, DW.FORM.ref4 |
| 316 | 315 | var index = dbg_info_buffer.items.len; |
| 317 | 316 | try dbg_info_buffer.resize(index + 4); |
| 318 | try self.addTypeRelocGlobal(atom_index, ty.childType(), @intCast(u32, index)); | |
| 317 | try self.addTypeRelocGlobal(atom_index, ty.childType(mod), @intCast(u32, index)); | |
| 319 | 318 | // DW.AT.subrange_type |
| 320 | 319 | try dbg_info_buffer.append(@enumToInt(AbbrevKind.array_dim)); |
| 321 | 320 | // DW.AT.type, DW.FORM.ref4 |
| ... | ... | @@ -323,7 +322,7 @@ pub const DeclState = struct { |
| 323 | 322 | try dbg_info_buffer.resize(index + 4); |
| 324 | 323 | try self.addTypeRelocGlobal(atom_index, Type.usize, @intCast(u32, index)); |
| 325 | 324 | // DW.AT.count, DW.FORM.udata |
| 326 | const len = ty.arrayLenIncludingSentinel(); | |
| 325 | const len = ty.arrayLenIncludingSentinel(mod); | |
| 327 | 326 | try leb128.writeULEB128(dbg_info_buffer.writer(), len); |
| 328 | 327 | // DW.AT.array_type delimit children |
| 329 | 328 | try dbg_info_buffer.append(0); |
| ... | ... | @@ -688,7 +687,7 @@ pub const DeclState = struct { |
| 688 | 687 | const mod = self.mod; |
| 689 | 688 | const target = mod.getTarget(); |
| 690 | 689 | const endian = target.cpu.arch.endian(); |
| 691 | const child_ty = if (is_ptr) ty.childType() else ty; | |
| 690 | const child_ty = if (is_ptr) ty.childType(mod) else ty; | |
| 692 | 691 | |
| 693 | 692 | switch (loc) { |
| 694 | 693 | .register => |reg| { |
src/link/Wasm.zig+2-2| ... | ... | @@ -2931,7 +2931,7 @@ pub fn getErrorTableSymbol(wasm: *Wasm) !u32 { |
| 2931 | 2931 | |
| 2932 | 2932 | const atom_index = try wasm.createAtom(); |
| 2933 | 2933 | const atom = wasm.getAtomPtr(atom_index); |
| 2934 | const slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 2934 | const slice_ty = Type.const_slice_u8_sentinel_0; | |
| 2935 | 2935 | const mod = wasm.base.options.module.?; |
| 2936 | 2936 | atom.alignment = slice_ty.abiAlignment(mod); |
| 2937 | 2937 | const sym_index = atom.sym_index; |
| ... | ... | @@ -2988,7 +2988,7 @@ fn populateErrorNameTable(wasm: *Wasm) !void { |
| 2988 | 2988 | for (mod.error_name_list.items) |error_name| { |
| 2989 | 2989 | const len = @intCast(u32, error_name.len + 1); // names are 0-termianted |
| 2990 | 2990 | |
| 2991 | const slice_ty = Type.initTag(.const_slice_u8_sentinel_0); | |
| 2991 | const slice_ty = Type.const_slice_u8_sentinel_0; | |
| 2992 | 2992 | const offset = @intCast(u32, atom.code.items.len); |
| 2993 | 2993 | // first we create the data for the slice of the name |
| 2994 | 2994 | try atom.code.appendNTimes(wasm.base.allocator, 0, 4); // ptr to name, will be relocated |
src/print_air.zig+4-2| ... | ... | @@ -433,9 +433,10 @@ const Writer = struct { |
| 433 | 433 | } |
| 434 | 434 | |
| 435 | 435 | fn writeAggregateInit(w: *Writer, s: anytype, inst: Air.Inst.Index) @TypeOf(s).Error!void { |
| 436 | const mod = w.module; | |
| 436 | 437 | const ty_pl = w.air.instructions.items(.data)[inst].ty_pl; |
| 437 | 438 | const vector_ty = w.air.getRefType(ty_pl.ty); |
| 438 | const len = @intCast(usize, vector_ty.arrayLen()); | |
| 439 | const len = @intCast(usize, vector_ty.arrayLen(mod)); | |
| 439 | 440 | const elements = @ptrCast([]const Air.Inst.Ref, w.air.extra[ty_pl.payload..][0..len]); |
| 440 | 441 | |
| 441 | 442 | try w.writeType(s, vector_ty); |
| ... | ... | @@ -512,10 +513,11 @@ const Writer = struct { |
| 512 | 513 | } |
| 513 | 514 | |
| 514 | 515 | fn writeSelect(w: *Writer, s: anytype, inst: Air.Inst.Index) @TypeOf(s).Error!void { |
| 516 | const mod = w.module; | |
| 515 | 517 | const pl_op = w.air.instructions.items(.data)[inst].pl_op; |
| 516 | 518 | const extra = w.air.extraData(Air.Bin, pl_op.payload).data; |
| 517 | 519 | |
| 518 | const elem_ty = w.typeOfIndex(inst).childType(); | |
| 520 | const elem_ty = w.typeOfIndex(inst).childType(mod); | |
| 519 | 521 | try w.writeType(s, elem_ty); |
| 520 | 522 | try s.writeAll(", "); |
| 521 | 523 | try w.writeOperand(s, inst, 0, pl_op.operand); |
src/type.zig+472-1298| ... | ... | @@ -40,7 +40,7 @@ pub const Type = struct { |
| 40 | 40 | .ptr_type => return .Pointer, |
| 41 | 41 | .array_type => return .Array, |
| 42 | 42 | .vector_type => return .Vector, |
| 43 | .optional_type => return .Optional, | |
| 43 | .opt_type => return .Optional, | |
| 44 | 44 | .error_union_type => return .ErrorUnion, |
| 45 | 45 | .struct_type => return .Struct, |
| 46 | 46 | .union_type => return .Union, |
| ... | ... | @@ -118,38 +118,17 @@ pub const Type = struct { |
| 118 | 118 | .function => return .Fn, |
| 119 | 119 | |
| 120 | 120 | .array, |
| 121 | .array_u8_sentinel_0, | |
| 122 | .array_u8, | |
| 123 | 121 | .array_sentinel, |
| 124 | 122 | => return .Array, |
| 125 | 123 | |
| 126 | .vector => return .Vector, | |
| 127 | ||
| 128 | .single_const_pointer_to_comptime_int, | |
| 129 | .const_slice_u8, | |
| 130 | .const_slice_u8_sentinel_0, | |
| 131 | .single_const_pointer, | |
| 132 | .single_mut_pointer, | |
| 133 | .many_const_pointer, | |
| 134 | .many_mut_pointer, | |
| 135 | .c_const_pointer, | |
| 136 | .c_mut_pointer, | |
| 137 | .const_slice, | |
| 138 | .mut_slice, | |
| 139 | 124 | .pointer, |
| 140 | 125 | .inferred_alloc_const, |
| 141 | 126 | .inferred_alloc_mut, |
| 142 | .manyptr_u8, | |
| 143 | .manyptr_const_u8, | |
| 144 | .manyptr_const_u8_sentinel_0, | |
| 145 | 127 | => return .Pointer, |
| 146 | 128 | |
| 147 | .optional, | |
| 148 | .optional_single_const_pointer, | |
| 149 | .optional_single_mut_pointer, | |
| 150 | => return .Optional, | |
| 129 | .optional => return .Optional, | |
| 151 | 130 | |
| 152 | .anyerror_void_error_union, .error_union => return .ErrorUnion, | |
| 131 | .error_union => return .ErrorUnion, | |
| 153 | 132 | |
| 154 | 133 | .anyframe_T => return .AnyFrame, |
| 155 | 134 | |
| ... | ... | @@ -177,8 +156,7 @@ pub const Type = struct { |
| 177 | 156 | return switch (self.zigTypeTag(mod)) { |
| 178 | 157 | .ErrorUnion => self.errorUnionPayload().baseZigTypeTag(mod), |
| 179 | 158 | .Optional => { |
| 180 | var buf: Payload.ElemType = undefined; | |
| 181 | return self.optionalChild(&buf).baseZigTypeTag(mod); | |
| 159 | return self.optionalChild(mod).baseZigTypeTag(mod); | |
| 182 | 160 | }, |
| 183 | 161 | else => |t| t, |
| 184 | 162 | }; |
| ... | ... | @@ -218,8 +196,7 @@ pub const Type = struct { |
| 218 | 196 | .Pointer => !ty.isSlice(mod) and (is_equality_cmp or ty.isCPtr()), |
| 219 | 197 | .Optional => { |
| 220 | 198 | if (!is_equality_cmp) return false; |
| 221 | var buf: Payload.ElemType = undefined; | |
| 222 | return ty.optionalChild(&buf).isSelfComparable(mod, is_equality_cmp); | |
| 199 | return ty.optionalChild(mod).isSelfComparable(mod, is_equality_cmp); | |
| 223 | 200 | }, |
| 224 | 201 | }; |
| 225 | 202 | } |
| ... | ... | @@ -275,9 +252,8 @@ pub const Type = struct { |
| 275 | 252 | } |
| 276 | 253 | |
| 277 | 254 | pub fn castTag(self: Type, comptime t: Tag) ?*t.Type() { |
| 278 | if (self.ip_index != .none) { | |
| 279 | return null; | |
| 280 | } | |
| 255 | assert(self.ip_index == .none); | |
| 256 | ||
| 281 | 257 | if (@enumToInt(self.legacy.tag_if_small_enough) < Tag.no_payload_count) |
| 282 | 258 | return null; |
| 283 | 259 | |
| ... | ... | @@ -287,281 +263,61 @@ pub const Type = struct { |
| 287 | 263 | return null; |
| 288 | 264 | } |
| 289 | 265 | |
| 290 | pub fn castPointer(self: Type) ?*Payload.ElemType { | |
| 291 | return switch (self.tag()) { | |
| 292 | .single_const_pointer, | |
| 293 | .single_mut_pointer, | |
| 294 | .many_const_pointer, | |
| 295 | .many_mut_pointer, | |
| 296 | .c_const_pointer, | |
| 297 | .c_mut_pointer, | |
| 298 | .const_slice, | |
| 299 | .mut_slice, | |
| 300 | .optional_single_const_pointer, | |
| 301 | .optional_single_mut_pointer, | |
| 302 | .manyptr_u8, | |
| 303 | .manyptr_const_u8, | |
| 304 | .manyptr_const_u8_sentinel_0, | |
| 305 | => self.cast(Payload.ElemType), | |
| 306 | ||
| 307 | .inferred_alloc_const => unreachable, | |
| 308 | .inferred_alloc_mut => unreachable, | |
| 309 | ||
| 310 | else => null, | |
| 311 | }; | |
| 312 | } | |
| 313 | ||
| 314 | 266 | /// If it is a function pointer, returns the function type. Otherwise returns null. |
| 315 | 267 | pub fn castPtrToFn(ty: Type, mod: *const Module) ?Type { |
| 316 | 268 | if (ty.zigTypeTag(mod) != .Pointer) return null; |
| 317 | const elem_ty = ty.childType(); | |
| 269 | const elem_ty = ty.childType(mod); | |
| 318 | 270 | if (elem_ty.zigTypeTag(mod) != .Fn) return null; |
| 319 | 271 | return elem_ty; |
| 320 | 272 | } |
| 321 | 273 | |
| 322 | pub fn ptrIsMutable(ty: Type) bool { | |
| 323 | return switch (ty.tag()) { | |
| 324 | .single_const_pointer_to_comptime_int, | |
| 325 | .const_slice_u8, | |
| 326 | .const_slice_u8_sentinel_0, | |
| 327 | .single_const_pointer, | |
| 328 | .many_const_pointer, | |
| 329 | .manyptr_const_u8, | |
| 330 | .manyptr_const_u8_sentinel_0, | |
| 331 | .c_const_pointer, | |
| 332 | .const_slice, | |
| 333 | => false, | |
| 334 | ||
| 335 | .single_mut_pointer, | |
| 336 | .many_mut_pointer, | |
| 337 | .manyptr_u8, | |
| 338 | .c_mut_pointer, | |
| 339 | .mut_slice, | |
| 340 | => true, | |
| 341 | ||
| 342 | .pointer => ty.castTag(.pointer).?.data.mutable, | |
| 343 | ||
| 344 | else => unreachable, | |
| 274 | pub fn ptrIsMutable(ty: Type, mod: *const Module) bool { | |
| 275 | return switch (ty.ip_index) { | |
| 276 | .none => switch (ty.tag()) { | |
| 277 | .pointer => ty.castTag(.pointer).?.data.mutable, | |
| 278 | else => unreachable, | |
| 279 | }, | |
| 280 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 281 | .ptr_type => |ptr_type| !ptr_type.is_const, | |
| 282 | else => unreachable, | |
| 283 | }, | |
| 345 | 284 | }; |
| 346 | 285 | } |
| 347 | 286 | |
| 348 | pub const ArrayInfo = struct { elem_type: Type, sentinel: ?Value = null, len: u64 }; | |
| 349 | pub fn arrayInfo(self: Type) ArrayInfo { | |
| 287 | pub const ArrayInfo = struct { | |
| 288 | elem_type: Type, | |
| 289 | sentinel: ?Value = null, | |
| 290 | len: u64, | |
| 291 | }; | |
| 292 | ||
| 293 | pub fn arrayInfo(self: Type, mod: *const Module) ArrayInfo { | |
| 350 | 294 | return .{ |
| 351 | .len = self.arrayLen(), | |
| 352 | .sentinel = self.sentinel(), | |
| 353 | .elem_type = self.elemType(), | |
| 295 | .len = self.arrayLen(mod), | |
| 296 | .sentinel = self.sentinel(mod), | |
| 297 | .elem_type = self.childType(mod), | |
| 354 | 298 | }; |
| 355 | 299 | } |
| 356 | 300 | |
| 357 | pub fn ptrInfo(self: Type) Payload.Pointer { | |
| 358 | switch (self.ip_index) { | |
| 359 | .none => switch (self.tag()) { | |
| 360 | .single_const_pointer_to_comptime_int => return .{ .data = .{ | |
| 361 | .pointee_type = Type.comptime_int, | |
| 362 | .sentinel = null, | |
| 363 | .@"align" = 0, | |
| 364 | .@"addrspace" = .generic, | |
| 365 | .bit_offset = 0, | |
| 366 | .host_size = 0, | |
| 367 | .@"allowzero" = false, | |
| 368 | .mutable = false, | |
| 369 | .@"volatile" = false, | |
| 370 | .size = .One, | |
| 371 | } }, | |
| 372 | .const_slice_u8 => return .{ .data = .{ | |
| 373 | .pointee_type = Type.u8, | |
| 374 | .sentinel = null, | |
| 375 | .@"align" = 0, | |
| 376 | .@"addrspace" = .generic, | |
| 377 | .bit_offset = 0, | |
| 378 | .host_size = 0, | |
| 379 | .@"allowzero" = false, | |
| 380 | .mutable = false, | |
| 381 | .@"volatile" = false, | |
| 382 | .size = .Slice, | |
| 383 | } }, | |
| 384 | .const_slice_u8_sentinel_0 => return .{ .data = .{ | |
| 385 | .pointee_type = Type.u8, | |
| 386 | .sentinel = Value.zero, | |
| 387 | .@"align" = 0, | |
| 388 | .@"addrspace" = .generic, | |
| 389 | .bit_offset = 0, | |
| 390 | .host_size = 0, | |
| 391 | .@"allowzero" = false, | |
| 392 | .mutable = false, | |
| 393 | .@"volatile" = false, | |
| 394 | .size = .Slice, | |
| 395 | } }, | |
| 396 | .single_const_pointer => return .{ .data = .{ | |
| 397 | .pointee_type = self.castPointer().?.data, | |
| 398 | .sentinel = null, | |
| 399 | .@"align" = 0, | |
| 400 | .@"addrspace" = .generic, | |
| 401 | .bit_offset = 0, | |
| 402 | .host_size = 0, | |
| 403 | .@"allowzero" = false, | |
| 404 | .mutable = false, | |
| 405 | .@"volatile" = false, | |
| 406 | .size = .One, | |
| 407 | } }, | |
| 408 | .single_mut_pointer => return .{ .data = .{ | |
| 409 | .pointee_type = self.castPointer().?.data, | |
| 410 | .sentinel = null, | |
| 411 | .@"align" = 0, | |
| 412 | .@"addrspace" = .generic, | |
| 413 | .bit_offset = 0, | |
| 414 | .host_size = 0, | |
| 415 | .@"allowzero" = false, | |
| 416 | .mutable = true, | |
| 417 | .@"volatile" = false, | |
| 418 | .size = .One, | |
| 419 | } }, | |
| 420 | .many_const_pointer => return .{ .data = .{ | |
| 421 | .pointee_type = self.castPointer().?.data, | |
| 422 | .sentinel = null, | |
| 423 | .@"align" = 0, | |
| 424 | .@"addrspace" = .generic, | |
| 425 | .bit_offset = 0, | |
| 426 | .host_size = 0, | |
| 427 | .@"allowzero" = false, | |
| 428 | .mutable = false, | |
| 429 | .@"volatile" = false, | |
| 430 | .size = .Many, | |
| 431 | } }, | |
| 432 | .manyptr_const_u8 => return .{ .data = .{ | |
| 433 | .pointee_type = Type.u8, | |
| 434 | .sentinel = null, | |
| 435 | .@"align" = 0, | |
| 436 | .@"addrspace" = .generic, | |
| 437 | .bit_offset = 0, | |
| 438 | .host_size = 0, | |
| 439 | .@"allowzero" = false, | |
| 440 | .mutable = false, | |
| 441 | .@"volatile" = false, | |
| 442 | .size = .Many, | |
| 443 | } }, | |
| 444 | .manyptr_const_u8_sentinel_0 => return .{ .data = .{ | |
| 445 | .pointee_type = Type.u8, | |
| 446 | .sentinel = Value.zero, | |
| 447 | .@"align" = 0, | |
| 448 | .@"addrspace" = .generic, | |
| 449 | .bit_offset = 0, | |
| 450 | .host_size = 0, | |
| 451 | .@"allowzero" = false, | |
| 452 | .mutable = false, | |
| 453 | .@"volatile" = false, | |
| 454 | .size = .Many, | |
| 455 | } }, | |
| 456 | .many_mut_pointer => return .{ .data = .{ | |
| 457 | .pointee_type = self.castPointer().?.data, | |
| 458 | .sentinel = null, | |
| 459 | .@"align" = 0, | |
| 460 | .@"addrspace" = .generic, | |
| 461 | .bit_offset = 0, | |
| 462 | .host_size = 0, | |
| 463 | .@"allowzero" = false, | |
| 464 | .mutable = true, | |
| 465 | .@"volatile" = false, | |
| 466 | .size = .Many, | |
| 467 | } }, | |
| 468 | .manyptr_u8 => return .{ .data = .{ | |
| 469 | .pointee_type = Type.u8, | |
| 470 | .sentinel = null, | |
| 471 | .@"align" = 0, | |
| 472 | .@"addrspace" = .generic, | |
| 473 | .bit_offset = 0, | |
| 474 | .host_size = 0, | |
| 475 | .@"allowzero" = false, | |
| 476 | .mutable = true, | |
| 477 | .@"volatile" = false, | |
| 478 | .size = .Many, | |
| 479 | } }, | |
| 480 | .c_const_pointer => return .{ .data = .{ | |
| 481 | .pointee_type = self.castPointer().?.data, | |
| 482 | .sentinel = null, | |
| 483 | .@"align" = 0, | |
| 484 | .@"addrspace" = .generic, | |
| 485 | .bit_offset = 0, | |
| 486 | .host_size = 0, | |
| 487 | .@"allowzero" = true, | |
| 488 | .mutable = false, | |
| 489 | .@"volatile" = false, | |
| 490 | .size = .C, | |
| 491 | } }, | |
| 492 | .c_mut_pointer => return .{ .data = .{ | |
| 493 | .pointee_type = self.castPointer().?.data, | |
| 494 | .sentinel = null, | |
| 495 | .@"align" = 0, | |
| 496 | .@"addrspace" = .generic, | |
| 497 | .bit_offset = 0, | |
| 498 | .host_size = 0, | |
| 499 | .@"allowzero" = true, | |
| 500 | .mutable = true, | |
| 501 | .@"volatile" = false, | |
| 502 | .size = .C, | |
| 503 | } }, | |
| 504 | .const_slice => return .{ .data = .{ | |
| 505 | .pointee_type = self.castPointer().?.data, | |
| 506 | .sentinel = null, | |
| 507 | .@"align" = 0, | |
| 508 | .@"addrspace" = .generic, | |
| 509 | .bit_offset = 0, | |
| 510 | .host_size = 0, | |
| 511 | .@"allowzero" = false, | |
| 512 | .mutable = false, | |
| 513 | .@"volatile" = false, | |
| 514 | .size = .Slice, | |
| 515 | } }, | |
| 516 | .mut_slice => return .{ .data = .{ | |
| 517 | .pointee_type = self.castPointer().?.data, | |
| 518 | .sentinel = null, | |
| 519 | .@"align" = 0, | |
| 520 | .@"addrspace" = .generic, | |
| 521 | .bit_offset = 0, | |
| 522 | .host_size = 0, | |
| 523 | .@"allowzero" = false, | |
| 524 | .mutable = true, | |
| 525 | .@"volatile" = false, | |
| 526 | .size = .Slice, | |
| 527 | } }, | |
| 528 | ||
| 529 | .pointer => return self.castTag(.pointer).?.*, | |
| 530 | ||
| 531 | .optional_single_mut_pointer => return .{ .data = .{ | |
| 532 | .pointee_type = self.castPointer().?.data, | |
| 533 | .sentinel = null, | |
| 534 | .@"align" = 0, | |
| 535 | .@"addrspace" = .generic, | |
| 536 | .bit_offset = 0, | |
| 537 | .host_size = 0, | |
| 538 | .@"allowzero" = false, | |
| 539 | .mutable = true, | |
| 540 | .@"volatile" = false, | |
| 541 | .size = .One, | |
| 542 | } }, | |
| 543 | .optional_single_const_pointer => return .{ .data = .{ | |
| 544 | .pointee_type = self.castPointer().?.data, | |
| 545 | .sentinel = null, | |
| 546 | .@"align" = 0, | |
| 547 | .@"addrspace" = .generic, | |
| 548 | .bit_offset = 0, | |
| 549 | .host_size = 0, | |
| 550 | .@"allowzero" = false, | |
| 551 | .mutable = false, | |
| 552 | .@"volatile" = false, | |
| 553 | .size = .One, | |
| 554 | } }, | |
| 555 | .optional => { | |
| 556 | var buf: Payload.ElemType = undefined; | |
| 557 | const child_type = self.optionalChild(&buf); | |
| 558 | return child_type.ptrInfo(); | |
| 301 | pub fn ptrInfo(ty: Type, mod: *const Module) Payload.Pointer.Data { | |
| 302 | return switch (ty.ip_index) { | |
| 303 | .none => switch (ty.tag()) { | |
| 304 | .pointer => ty.castTag(.pointer).?.data, | |
| 305 | .optional => b: { | |
| 306 | const child_type = ty.optionalChild(mod); | |
| 307 | break :b child_type.ptrInfo(mod); | |
| 559 | 308 | }, |
| 560 | 309 | |
| 561 | 310 | else => unreachable, |
| 562 | 311 | }, |
| 563 | else => @panic("TODO"), | |
| 564 | } | |
| 312 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 313 | .ptr_type => |p| Payload.Pointer.Data.fromKey(p), | |
| 314 | .opt_type => |child| switch (mod.intern_pool.indexToKey(child)) { | |
| 315 | .ptr_type => |p| Payload.Pointer.Data.fromKey(p), | |
| 316 | else => unreachable, | |
| 317 | }, | |
| 318 | else => unreachable, | |
| 319 | }, | |
| 320 | }; | |
| 565 | 321 | } |
| 566 | 322 | |
| 567 | 323 | pub fn eql(a: Type, b: Type, mod: *Module) bool { |
| ... | ... | @@ -658,20 +414,17 @@ pub const Type = struct { |
| 658 | 414 | }, |
| 659 | 415 | |
| 660 | 416 | .array, |
| 661 | .array_u8_sentinel_0, | |
| 662 | .array_u8, | |
| 663 | 417 | .array_sentinel, |
| 664 | .vector, | |
| 665 | 418 | => { |
| 666 | 419 | if (a.zigTypeTag(mod) != b.zigTypeTag(mod)) return false; |
| 667 | 420 | |
| 668 | if (a.arrayLen() != b.arrayLen()) | |
| 421 | if (a.arrayLen(mod) != b.arrayLen(mod)) | |
| 669 | 422 | return false; |
| 670 | const elem_ty = a.elemType(); | |
| 671 | if (!elem_ty.eql(b.elemType(), mod)) | |
| 423 | const elem_ty = a.childType(mod); | |
| 424 | if (!elem_ty.eql(b.childType(mod), mod)) | |
| 672 | 425 | return false; |
| 673 | const sentinel_a = a.sentinel(); | |
| 674 | const sentinel_b = b.sentinel(); | |
| 426 | const sentinel_a = a.sentinel(mod); | |
| 427 | const sentinel_b = b.sentinel(mod); | |
| 675 | 428 | if (sentinel_a) |sa| { |
| 676 | 429 | if (sentinel_b) |sb| { |
| 677 | 430 | return sa.eql(sb, elem_ty, mod); |
| ... | ... | @@ -683,28 +436,14 @@ pub const Type = struct { |
| 683 | 436 | } |
| 684 | 437 | }, |
| 685 | 438 | |
| 686 | .single_const_pointer_to_comptime_int, | |
| 687 | .const_slice_u8, | |
| 688 | .const_slice_u8_sentinel_0, | |
| 689 | .single_const_pointer, | |
| 690 | .single_mut_pointer, | |
| 691 | .many_const_pointer, | |
| 692 | .many_mut_pointer, | |
| 693 | .c_const_pointer, | |
| 694 | .c_mut_pointer, | |
| 695 | .const_slice, | |
| 696 | .mut_slice, | |
| 697 | 439 | .pointer, |
| 698 | 440 | .inferred_alloc_const, |
| 699 | 441 | .inferred_alloc_mut, |
| 700 | .manyptr_u8, | |
| 701 | .manyptr_const_u8, | |
| 702 | .manyptr_const_u8_sentinel_0, | |
| 703 | 442 | => { |
| 704 | 443 | if (b.zigTypeTag(mod) != .Pointer) return false; |
| 705 | 444 | |
| 706 | const info_a = a.ptrInfo().data; | |
| 707 | const info_b = b.ptrInfo().data; | |
| 445 | const info_a = a.ptrInfo(mod); | |
| 446 | const info_b = b.ptrInfo(mod); | |
| 708 | 447 | if (!info_a.pointee_type.eql(info_b.pointee_type, mod)) |
| 709 | 448 | return false; |
| 710 | 449 | if (info_a.@"align" != info_b.@"align") |
| ... | ... | @@ -743,18 +482,13 @@ pub const Type = struct { |
| 743 | 482 | return true; |
| 744 | 483 | }, |
| 745 | 484 | |
| 746 | .optional, | |
| 747 | .optional_single_const_pointer, | |
| 748 | .optional_single_mut_pointer, | |
| 749 | => { | |
| 485 | .optional => { | |
| 750 | 486 | if (b.zigTypeTag(mod) != .Optional) return false; |
| 751 | 487 | |
| 752 | var buf_a: Payload.ElemType = undefined; | |
| 753 | var buf_b: Payload.ElemType = undefined; | |
| 754 | return a.optionalChild(&buf_a).eql(b.optionalChild(&buf_b), mod); | |
| 488 | return a.optionalChild(mod).eql(b.optionalChild(mod), mod); | |
| 755 | 489 | }, |
| 756 | 490 | |
| 757 | .anyerror_void_error_union, .error_union => { | |
| 491 | .error_union => { | |
| 758 | 492 | if (b.zigTypeTag(mod) != .ErrorUnion) return false; |
| 759 | 493 | |
| 760 | 494 | const a_set = a.errorUnionSet(); |
| ... | ... | @@ -947,47 +681,23 @@ pub const Type = struct { |
| 947 | 681 | }, |
| 948 | 682 | |
| 949 | 683 | .array, |
| 950 | .array_u8_sentinel_0, | |
| 951 | .array_u8, | |
| 952 | 684 | .array_sentinel, |
| 953 | 685 | => { |
| 954 | 686 | std.hash.autoHash(hasher, std.builtin.TypeId.Array); |
| 955 | 687 | |
| 956 | const elem_ty = ty.elemType(); | |
| 957 | std.hash.autoHash(hasher, ty.arrayLen()); | |
| 688 | const elem_ty = ty.childType(mod); | |
| 689 | std.hash.autoHash(hasher, ty.arrayLen(mod)); | |
| 958 | 690 | hashWithHasher(elem_ty, hasher, mod); |
| 959 | hashSentinel(ty.sentinel(), elem_ty, hasher, mod); | |
| 691 | hashSentinel(ty.sentinel(mod), elem_ty, hasher, mod); | |
| 960 | 692 | }, |
| 961 | 693 | |
| 962 | .vector => { | |
| 963 | std.hash.autoHash(hasher, std.builtin.TypeId.Vector); | |
| 964 | ||
| 965 | const elem_ty = ty.elemType(); | |
| 966 | std.hash.autoHash(hasher, ty.vectorLen()); | |
| 967 | hashWithHasher(elem_ty, hasher, mod); | |
| 968 | }, | |
| 969 | ||
| 970 | .single_const_pointer_to_comptime_int, | |
| 971 | .const_slice_u8, | |
| 972 | .const_slice_u8_sentinel_0, | |
| 973 | .single_const_pointer, | |
| 974 | .single_mut_pointer, | |
| 975 | .many_const_pointer, | |
| 976 | .many_mut_pointer, | |
| 977 | .c_const_pointer, | |
| 978 | .c_mut_pointer, | |
| 979 | .const_slice, | |
| 980 | .mut_slice, | |
| 981 | 694 | .pointer, |
| 982 | 695 | .inferred_alloc_const, |
| 983 | 696 | .inferred_alloc_mut, |
| 984 | .manyptr_u8, | |
| 985 | .manyptr_const_u8, | |
| 986 | .manyptr_const_u8_sentinel_0, | |
| 987 | 697 | => { |
| 988 | 698 | std.hash.autoHash(hasher, std.builtin.TypeId.Pointer); |
| 989 | 699 | |
| 990 | const info = ty.ptrInfo().data; | |
| 700 | const info = ty.ptrInfo(mod); | |
| 991 | 701 | hashWithHasher(info.pointee_type, hasher, mod); |
| 992 | 702 | hashSentinel(info.sentinel, info.pointee_type, hasher, mod); |
| 993 | 703 | std.hash.autoHash(hasher, info.@"align"); |
| ... | ... | @@ -1001,17 +711,13 @@ pub const Type = struct { |
| 1001 | 711 | std.hash.autoHash(hasher, info.size); |
| 1002 | 712 | }, |
| 1003 | 713 | |
| 1004 | .optional, | |
| 1005 | .optional_single_const_pointer, | |
| 1006 | .optional_single_mut_pointer, | |
| 1007 | => { | |
| 714 | .optional => { | |
| 1008 | 715 | std.hash.autoHash(hasher, std.builtin.TypeId.Optional); |
| 1009 | 716 | |
| 1010 | var buf: Payload.ElemType = undefined; | |
| 1011 | hashWithHasher(ty.optionalChild(&buf), hasher, mod); | |
| 717 | hashWithHasher(ty.optionalChild(mod), hasher, mod); | |
| 1012 | 718 | }, |
| 1013 | 719 | |
| 1014 | .anyerror_void_error_union, .error_union => { | |
| 720 | .error_union => { | |
| 1015 | 721 | std.hash.autoHash(hasher, std.builtin.TypeId.ErrorUnion); |
| 1016 | 722 | |
| 1017 | 723 | const set_ty = ty.errorUnionSet(); |
| ... | ... | @@ -1023,7 +729,7 @@ pub const Type = struct { |
| 1023 | 729 | |
| 1024 | 730 | .anyframe_T => { |
| 1025 | 731 | std.hash.autoHash(hasher, std.builtin.TypeId.AnyFrame); |
| 1026 | hashWithHasher(ty.childType(), hasher, mod); | |
| 732 | hashWithHasher(ty.childType(mod), hasher, mod); | |
| 1027 | 733 | }, |
| 1028 | 734 | |
| 1029 | 735 | .empty_struct => { |
| ... | ... | @@ -1129,33 +835,12 @@ pub const Type = struct { |
| 1129 | 835 | .legacy = .{ .tag_if_small_enough = self.legacy.tag_if_small_enough }, |
| 1130 | 836 | }; |
| 1131 | 837 | } else switch (self.legacy.ptr_otherwise.tag) { |
| 1132 | .single_const_pointer_to_comptime_int, | |
| 1133 | .const_slice_u8, | |
| 1134 | .const_slice_u8_sentinel_0, | |
| 1135 | .anyerror_void_error_union, | |
| 1136 | 838 | .inferred_alloc_const, |
| 1137 | 839 | .inferred_alloc_mut, |
| 1138 | 840 | .empty_struct_literal, |
| 1139 | .manyptr_u8, | |
| 1140 | .manyptr_const_u8, | |
| 1141 | .manyptr_const_u8_sentinel_0, | |
| 1142 | 841 | => unreachable, |
| 1143 | 842 | |
| 1144 | .array_u8, | |
| 1145 | .array_u8_sentinel_0, | |
| 1146 | => return self.copyPayloadShallow(allocator, Payload.Len), | |
| 1147 | ||
| 1148 | .single_const_pointer, | |
| 1149 | .single_mut_pointer, | |
| 1150 | .many_const_pointer, | |
| 1151 | .many_mut_pointer, | |
| 1152 | .c_const_pointer, | |
| 1153 | .c_mut_pointer, | |
| 1154 | .const_slice, | |
| 1155 | .mut_slice, | |
| 1156 | 843 | .optional, |
| 1157 | .optional_single_mut_pointer, | |
| 1158 | .optional_single_const_pointer, | |
| 1159 | 844 | .anyframe_T, |
| 1160 | 845 | => { |
| 1161 | 846 | const payload = self.cast(Payload.ElemType).?; |
| ... | ... | @@ -1170,13 +855,6 @@ pub const Type = struct { |
| 1170 | 855 | }; |
| 1171 | 856 | }, |
| 1172 | 857 | |
| 1173 | .vector => { | |
| 1174 | const payload = self.castTag(.vector).?.data; | |
| 1175 | return Tag.vector.create(allocator, .{ | |
| 1176 | .len = payload.len, | |
| 1177 | .elem_type = try payload.elem_type.copy(allocator), | |
| 1178 | }); | |
| 1179 | }, | |
| 1180 | 858 | .array => { |
| 1181 | 859 | const payload = self.castTag(.array).?.data; |
| 1182 | 860 | return Tag.array.create(allocator, .{ |
| ... | ... | @@ -1408,13 +1086,6 @@ pub const Type = struct { |
| 1408 | 1086 | }); |
| 1409 | 1087 | }, |
| 1410 | 1088 | |
| 1411 | .anyerror_void_error_union => return writer.writeAll("anyerror!void"), | |
| 1412 | .const_slice_u8 => return writer.writeAll("[]const u8"), | |
| 1413 | .const_slice_u8_sentinel_0 => return writer.writeAll("[:0]const u8"), | |
| 1414 | .single_const_pointer_to_comptime_int => return writer.writeAll("*const comptime_int"), | |
| 1415 | .manyptr_u8 => return writer.writeAll("[*]u8"), | |
| 1416 | .manyptr_const_u8 => return writer.writeAll("[*]const u8"), | |
| 1417 | .manyptr_const_u8_sentinel_0 => return writer.writeAll("[*:0]const u8"), | |
| 1418 | 1089 | .function => { |
| 1419 | 1090 | const payload = ty.castTag(.function).?.data; |
| 1420 | 1091 | try writer.writeAll("fn("); |
| ... | ... | @@ -1447,20 +1118,6 @@ pub const Type = struct { |
| 1447 | 1118 | ty = return_type; |
| 1448 | 1119 | continue; |
| 1449 | 1120 | }, |
| 1450 | .array_u8 => { | |
| 1451 | const len = ty.castTag(.array_u8).?.data; | |
| 1452 | return writer.print("[{d}]u8", .{len}); | |
| 1453 | }, | |
| 1454 | .array_u8_sentinel_0 => { | |
| 1455 | const len = ty.castTag(.array_u8_sentinel_0).?.data; | |
| 1456 | return writer.print("[{d}:0]u8", .{len}); | |
| 1457 | }, | |
| 1458 | .vector => { | |
| 1459 | const payload = ty.castTag(.vector).?.data; | |
| 1460 | try writer.print("@Vector({d}, ", .{payload.len}); | |
| 1461 | try payload.elem_type.dump("", .{}, writer); | |
| 1462 | return writer.writeAll(")"); | |
| 1463 | }, | |
| 1464 | 1121 | .array => { |
| 1465 | 1122 | const payload = ty.castTag(.array).?.data; |
| 1466 | 1123 | try writer.print("[{d}]", .{payload.len}); |
| ... | ... | @@ -1512,72 +1169,12 @@ pub const Type = struct { |
| 1512 | 1169 | try writer.writeAll("}"); |
| 1513 | 1170 | return; |
| 1514 | 1171 | }, |
| 1515 | .single_const_pointer => { | |
| 1516 | const pointee_type = ty.castTag(.single_const_pointer).?.data; | |
| 1517 | try writer.writeAll("*const "); | |
| 1518 | ty = pointee_type; | |
| 1519 | continue; | |
| 1520 | }, | |
| 1521 | .single_mut_pointer => { | |
| 1522 | const pointee_type = ty.castTag(.single_mut_pointer).?.data; | |
| 1523 | try writer.writeAll("*"); | |
| 1524 | ty = pointee_type; | |
| 1525 | continue; | |
| 1526 | }, | |
| 1527 | .many_const_pointer => { | |
| 1528 | const pointee_type = ty.castTag(.many_const_pointer).?.data; | |
| 1529 | try writer.writeAll("[*]const "); | |
| 1530 | ty = pointee_type; | |
| 1531 | continue; | |
| 1532 | }, | |
| 1533 | .many_mut_pointer => { | |
| 1534 | const pointee_type = ty.castTag(.many_mut_pointer).?.data; | |
| 1535 | try writer.writeAll("[*]"); | |
| 1536 | ty = pointee_type; | |
| 1537 | continue; | |
| 1538 | }, | |
| 1539 | .c_const_pointer => { | |
| 1540 | const pointee_type = ty.castTag(.c_const_pointer).?.data; | |
| 1541 | try writer.writeAll("[*c]const "); | |
| 1542 | ty = pointee_type; | |
| 1543 | continue; | |
| 1544 | }, | |
| 1545 | .c_mut_pointer => { | |
| 1546 | const pointee_type = ty.castTag(.c_mut_pointer).?.data; | |
| 1547 | try writer.writeAll("[*c]"); | |
| 1548 | ty = pointee_type; | |
| 1549 | continue; | |
| 1550 | }, | |
| 1551 | .const_slice => { | |
| 1552 | const pointee_type = ty.castTag(.const_slice).?.data; | |
| 1553 | try writer.writeAll("[]const "); | |
| 1554 | ty = pointee_type; | |
| 1555 | continue; | |
| 1556 | }, | |
| 1557 | .mut_slice => { | |
| 1558 | const pointee_type = ty.castTag(.mut_slice).?.data; | |
| 1559 | try writer.writeAll("[]"); | |
| 1560 | ty = pointee_type; | |
| 1561 | continue; | |
| 1562 | }, | |
| 1563 | 1172 | .optional => { |
| 1564 | 1173 | const child_type = ty.castTag(.optional).?.data; |
| 1565 | 1174 | try writer.writeByte('?'); |
| 1566 | 1175 | ty = child_type; |
| 1567 | 1176 | continue; |
| 1568 | 1177 | }, |
| 1569 | .optional_single_const_pointer => { | |
| 1570 | const pointee_type = ty.castTag(.optional_single_const_pointer).?.data; | |
| 1571 | try writer.writeAll("?*const "); | |
| 1572 | ty = pointee_type; | |
| 1573 | continue; | |
| 1574 | }, | |
| 1575 | .optional_single_mut_pointer => { | |
| 1576 | const pointee_type = ty.castTag(.optional_single_mut_pointer).?.data; | |
| 1577 | try writer.writeAll("?*"); | |
| 1578 | ty = pointee_type; | |
| 1579 | continue; | |
| 1580 | }, | |
| 1581 | 1178 | |
| 1582 | 1179 | .pointer => { |
| 1583 | 1180 | const payload = ty.castTag(.pointer).?.data; |
| ... | ... | @@ -1680,7 +1277,7 @@ pub const Type = struct { |
| 1680 | 1277 | .ptr_type => @panic("TODO"), |
| 1681 | 1278 | .array_type => @panic("TODO"), |
| 1682 | 1279 | .vector_type => @panic("TODO"), |
| 1683 | .optional_type => @panic("TODO"), | |
| 1280 | .opt_type => @panic("TODO"), | |
| 1684 | 1281 | .error_union_type => @panic("TODO"), |
| 1685 | 1282 | .simple_type => |s| return writer.writeAll(@tagName(s)), |
| 1686 | 1283 | .struct_type => @panic("TODO"), |
| ... | ... | @@ -1733,14 +1330,6 @@ pub const Type = struct { |
| 1733 | 1330 | try decl.renderFullyQualifiedName(mod, writer); |
| 1734 | 1331 | }, |
| 1735 | 1332 | |
| 1736 | .anyerror_void_error_union => try writer.writeAll("anyerror!void"), | |
| 1737 | .const_slice_u8 => try writer.writeAll("[]const u8"), | |
| 1738 | .const_slice_u8_sentinel_0 => try writer.writeAll("[:0]const u8"), | |
| 1739 | .single_const_pointer_to_comptime_int => try writer.writeAll("*const comptime_int"), | |
| 1740 | .manyptr_u8 => try writer.writeAll("[*]u8"), | |
| 1741 | .manyptr_const_u8 => try writer.writeAll("[*]const u8"), | |
| 1742 | .manyptr_const_u8_sentinel_0 => try writer.writeAll("[*:0]const u8"), | |
| 1743 | ||
| 1744 | 1333 | .error_set_inferred => { |
| 1745 | 1334 | const func = ty.castTag(.error_set_inferred).?.data.func; |
| 1746 | 1335 | |
| ... | ... | @@ -1799,20 +1388,6 @@ pub const Type = struct { |
| 1799 | 1388 | try print(error_union.payload, writer, mod); |
| 1800 | 1389 | }, |
| 1801 | 1390 | |
| 1802 | .array_u8 => { | |
| 1803 | const len = ty.castTag(.array_u8).?.data; | |
| 1804 | try writer.print("[{d}]u8", .{len}); | |
| 1805 | }, | |
| 1806 | .array_u8_sentinel_0 => { | |
| 1807 | const len = ty.castTag(.array_u8_sentinel_0).?.data; | |
| 1808 | try writer.print("[{d}:0]u8", .{len}); | |
| 1809 | }, | |
| 1810 | .vector => { | |
| 1811 | const payload = ty.castTag(.vector).?.data; | |
| 1812 | try writer.print("@Vector({d}, ", .{payload.len}); | |
| 1813 | try print(payload.elem_type, writer, mod); | |
| 1814 | try writer.writeAll(")"); | |
| 1815 | }, | |
| 1816 | 1391 | .array => { |
| 1817 | 1392 | const payload = ty.castTag(.array).?.data; |
| 1818 | 1393 | try writer.print("[{d}]", .{payload.len}); |
| ... | ... | @@ -1865,17 +1440,8 @@ pub const Type = struct { |
| 1865 | 1440 | try writer.writeAll("}"); |
| 1866 | 1441 | }, |
| 1867 | 1442 | |
| 1868 | .pointer, | |
| 1869 | .single_const_pointer, | |
| 1870 | .single_mut_pointer, | |
| 1871 | .many_const_pointer, | |
| 1872 | .many_mut_pointer, | |
| 1873 | .c_const_pointer, | |
| 1874 | .c_mut_pointer, | |
| 1875 | .const_slice, | |
| 1876 | .mut_slice, | |
| 1877 | => { | |
| 1878 | const info = ty.ptrInfo().data; | |
| 1443 | .pointer => { | |
| 1444 | const info = ty.ptrInfo(mod); | |
| 1879 | 1445 | |
| 1880 | 1446 | if (info.sentinel) |s| switch (info.size) { |
| 1881 | 1447 | .One, .C => unreachable, |
| ... | ... | @@ -1920,16 +1486,6 @@ pub const Type = struct { |
| 1920 | 1486 | try writer.writeByte('?'); |
| 1921 | 1487 | try print(child_type, writer, mod); |
| 1922 | 1488 | }, |
| 1923 | .optional_single_mut_pointer => { | |
| 1924 | const pointee_type = ty.castTag(.optional_single_mut_pointer).?.data; | |
| 1925 | try writer.writeAll("?*"); | |
| 1926 | try print(pointee_type, writer, mod); | |
| 1927 | }, | |
| 1928 | .optional_single_const_pointer => { | |
| 1929 | const pointee_type = ty.castTag(.optional_single_const_pointer).?.data; | |
| 1930 | try writer.writeAll("?*const "); | |
| 1931 | try print(pointee_type, writer, mod); | |
| 1932 | }, | |
| 1933 | 1489 | .anyframe_T => { |
| 1934 | 1490 | const return_type = ty.castTag(.anyframe_T).?.data; |
| 1935 | 1491 | try writer.print("anyframe->", .{}); |
| ... | ... | @@ -1963,12 +1519,6 @@ pub const Type = struct { |
| 1963 | 1519 | pub fn toValue(self: Type, allocator: Allocator) Allocator.Error!Value { |
| 1964 | 1520 | if (self.ip_index != .none) return self.ip_index.toValue(); |
| 1965 | 1521 | switch (self.tag()) { |
| 1966 | .single_const_pointer_to_comptime_int => return Value{ .ip_index = .single_const_pointer_to_comptime_int_type, .legacy = undefined }, | |
| 1967 | .const_slice_u8 => return Value{ .ip_index = .const_slice_u8_type, .legacy = undefined }, | |
| 1968 | .const_slice_u8_sentinel_0 => return Value{ .ip_index = .const_slice_u8_sentinel_0_type, .legacy = undefined }, | |
| 1969 | .manyptr_u8 => return Value{ .ip_index = .manyptr_u8_type, .legacy = undefined }, | |
| 1970 | .manyptr_const_u8 => return Value{ .ip_index = .manyptr_const_u8_type, .legacy = undefined }, | |
| 1971 | .manyptr_const_u8_sentinel_0 => return Value{ .ip_index = .manyptr_const_u8_sentinel_0_type, .legacy = undefined }, | |
| 1972 | 1522 | .inferred_alloc_const => unreachable, |
| 1973 | 1523 | .inferred_alloc_mut => unreachable, |
| 1974 | 1524 | else => return Value.Tag.ty.create(allocator, self), |
| ... | ... | @@ -1996,10 +1546,41 @@ pub const Type = struct { |
| 1996 | 1546 | ) RuntimeBitsError!bool { |
| 1997 | 1547 | if (ty.ip_index != .none) switch (mod.intern_pool.indexToKey(ty.ip_index)) { |
| 1998 | 1548 | .int_type => |int_type| return int_type.bits != 0, |
| 1999 | .ptr_type => @panic("TODO"), | |
| 2000 | .array_type => @panic("TODO"), | |
| 2001 | .vector_type => @panic("TODO"), | |
| 2002 | .optional_type => @panic("TODO"), | |
| 1549 | .ptr_type => |ptr_type| { | |
| 1550 | // Pointers to zero-bit types still have a runtime address; however, pointers | |
| 1551 | // to comptime-only types do not, with the exception of function pointers. | |
| 1552 | if (ignore_comptime_only) return true; | |
| 1553 | const child_ty = ptr_type.elem_type.toType(); | |
| 1554 | if (child_ty.zigTypeTag(mod) == .Fn) return !child_ty.fnInfo().is_generic; | |
| 1555 | if (strat == .sema) return !(try strat.sema.typeRequiresComptime(ty)); | |
| 1556 | return !comptimeOnly(ty, mod); | |
| 1557 | }, | |
| 1558 | .array_type => |array_type| { | |
| 1559 | if (array_type.sentinel != .none) { | |
| 1560 | return array_type.child.toType().hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat); | |
| 1561 | } else { | |
| 1562 | return array_type.len > 0 and | |
| 1563 | try array_type.child.toType().hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat); | |
| 1564 | } | |
| 1565 | }, | |
| 1566 | .vector_type => |vector_type| { | |
| 1567 | return vector_type.len > 0 and | |
| 1568 | try vector_type.child.toType().hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat); | |
| 1569 | }, | |
| 1570 | .opt_type => |child| { | |
| 1571 | const child_ty = child.toType(); | |
| 1572 | if (child_ty.isNoReturn()) { | |
| 1573 | // Then the optional is comptime-known to be null. | |
| 1574 | return false; | |
| 1575 | } | |
| 1576 | if (ignore_comptime_only) { | |
| 1577 | return true; | |
| 1578 | } else if (strat == .sema) { | |
| 1579 | return !(try strat.sema.typeRequiresComptime(child_ty)); | |
| 1580 | } else { | |
| 1581 | return !comptimeOnly(child_ty, mod); | |
| 1582 | } | |
| 1583 | }, | |
| 2003 | 1584 | .error_union_type => @panic("TODO"), |
| 2004 | 1585 | .simple_type => |t| return switch (t) { |
| 2005 | 1586 | .f16, |
| ... | ... | @@ -2058,14 +1639,7 @@ pub const Type = struct { |
| 2058 | 1639 | .enum_tag => unreachable, // it's a value, not a type |
| 2059 | 1640 | }; |
| 2060 | 1641 | switch (ty.tag()) { |
| 2061 | .const_slice_u8, | |
| 2062 | .const_slice_u8_sentinel_0, | |
| 2063 | .array_u8_sentinel_0, | |
| 2064 | .anyerror_void_error_union, | |
| 2065 | 1642 | .error_set_inferred, |
| 2066 | .manyptr_u8, | |
| 2067 | .manyptr_const_u8, | |
| 2068 | .manyptr_const_u8_sentinel_0, | |
| 2069 | 1643 | |
| 2070 | 1644 | .@"opaque", |
| 2071 | 1645 | .error_set_single, |
| ... | ... | @@ -2077,22 +1651,12 @@ pub const Type = struct { |
| 2077 | 1651 | // Pointers to zero-bit types still have a runtime address; however, pointers |
| 2078 | 1652 | // to comptime-only types do not, with the exception of function pointers. |
| 2079 | 1653 | .anyframe_T, |
| 2080 | .optional_single_mut_pointer, | |
| 2081 | .optional_single_const_pointer, | |
| 2082 | .single_const_pointer, | |
| 2083 | .single_mut_pointer, | |
| 2084 | .many_const_pointer, | |
| 2085 | .many_mut_pointer, | |
| 2086 | .c_const_pointer, | |
| 2087 | .c_mut_pointer, | |
| 2088 | .const_slice, | |
| 2089 | .mut_slice, | |
| 2090 | 1654 | .pointer, |
| 2091 | 1655 | => { |
| 2092 | 1656 | if (ignore_comptime_only) { |
| 2093 | 1657 | return true; |
| 2094 | } else if (ty.childType().zigTypeTag(mod) == .Fn) { | |
| 2095 | return !ty.childType().fnInfo().is_generic; | |
| 1658 | } else if (ty.childType(mod).zigTypeTag(mod) == .Fn) { | |
| 1659 | return !ty.childType(mod).fnInfo().is_generic; | |
| 2096 | 1660 | } else if (strat == .sema) { |
| 2097 | 1661 | return !(try strat.sema.typeRequiresComptime(ty)); |
| 2098 | 1662 | } else { |
| ... | ... | @@ -2101,7 +1665,6 @@ pub const Type = struct { |
| 2101 | 1665 | }, |
| 2102 | 1666 | |
| 2103 | 1667 | // These are false because they are comptime-only types. |
| 2104 | .single_const_pointer_to_comptime_int, | |
| 2105 | 1668 | .empty_struct, |
| 2106 | 1669 | .empty_struct_literal, |
| 2107 | 1670 | // These are function *bodies*, not pointers. |
| ... | ... | @@ -2111,8 +1674,7 @@ pub const Type = struct { |
| 2111 | 1674 | => return false, |
| 2112 | 1675 | |
| 2113 | 1676 | .optional => { |
| 2114 | var buf: Payload.ElemType = undefined; | |
| 2115 | const child_ty = ty.optionalChild(&buf); | |
| 1677 | const child_ty = ty.optionalChild(mod); | |
| 2116 | 1678 | if (child_ty.isNoReturn()) { |
| 2117 | 1679 | // Then the optional is comptime-known to be null. |
| 2118 | 1680 | return false; |
| ... | ... | @@ -2200,10 +1762,9 @@ pub const Type = struct { |
| 2200 | 1762 | } |
| 2201 | 1763 | }, |
| 2202 | 1764 | |
| 2203 | .array, .vector => return ty.arrayLen() != 0 and | |
| 2204 | try ty.elemType().hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat), | |
| 2205 | .array_u8 => return ty.arrayLen() != 0, | |
| 2206 | .array_sentinel => return ty.childType().hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat), | |
| 1765 | .array => return ty.arrayLen(mod) != 0 and | |
| 1766 | try ty.childType(mod).hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat), | |
| 1767 | .array_sentinel => return ty.childType(mod).hasRuntimeBitsAdvanced(mod, ignore_comptime_only, strat), | |
| 2207 | 1768 | |
| 2208 | 1769 | .tuple, .anon_struct => { |
| 2209 | 1770 | const tuple = ty.tupleFields(); |
| ... | ... | @@ -2224,14 +1785,14 @@ pub const Type = struct { |
| 2224 | 1785 | /// readFrom/writeToMemory are supported only for types with a well- |
| 2225 | 1786 | /// defined memory layout |
| 2226 | 1787 | pub fn hasWellDefinedLayout(ty: Type, mod: *const Module) bool { |
| 2227 | if (ty.ip_index != .none) switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 2228 | .int_type => return true, | |
| 2229 | .ptr_type => @panic("TODO"), | |
| 2230 | .array_type => @panic("TODO"), | |
| 2231 | .vector_type => @panic("TODO"), | |
| 2232 | .optional_type => @panic("TODO"), | |
| 2233 | .error_union_type => @panic("TODO"), | |
| 2234 | .simple_type => |t| return switch (t) { | |
| 1788 | if (ty.ip_index != .none) return switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 1789 | .int_type => true, | |
| 1790 | .ptr_type => true, | |
| 1791 | .array_type => |array_type| array_type.child.toType().hasWellDefinedLayout(mod), | |
| 1792 | .vector_type => true, | |
| 1793 | .opt_type => |child| child.toType().isPtrLikeOptional(mod), | |
| 1794 | .error_union_type => false, | |
| 1795 | .simple_type => |t| switch (t) { | |
| 2235 | 1796 | .f16, |
| 2236 | 1797 | .f32, |
| 2237 | 1798 | .f64, |
| ... | ... | @@ -2287,23 +1848,8 @@ pub const Type = struct { |
| 2287 | 1848 | .enum_tag => unreachable, // it's a value, not a type |
| 2288 | 1849 | }; |
| 2289 | 1850 | return switch (ty.tag()) { |
| 2290 | .manyptr_u8, | |
| 2291 | .manyptr_const_u8, | |
| 2292 | .manyptr_const_u8_sentinel_0, | |
| 2293 | .array_u8, | |
| 2294 | .array_u8_sentinel_0, | |
| 2295 | 1851 | .pointer, |
| 2296 | .single_const_pointer, | |
| 2297 | .single_mut_pointer, | |
| 2298 | .many_const_pointer, | |
| 2299 | .many_mut_pointer, | |
| 2300 | .c_const_pointer, | |
| 2301 | .c_mut_pointer, | |
| 2302 | .single_const_pointer_to_comptime_int, | |
| 2303 | 1852 | .enum_numbered, |
| 2304 | .vector, | |
| 2305 | .optional_single_mut_pointer, | |
| 2306 | .optional_single_const_pointer, | |
| 2307 | 1853 | => true, |
| 2308 | 1854 | |
| 2309 | 1855 | .error_set, |
| ... | ... | @@ -2313,13 +1859,8 @@ pub const Type = struct { |
| 2313 | 1859 | .@"opaque", |
| 2314 | 1860 | // These are function bodies, not function pointers. |
| 2315 | 1861 | .function, |
| 2316 | .const_slice_u8, | |
| 2317 | .const_slice_u8_sentinel_0, | |
| 2318 | .const_slice, | |
| 2319 | .mut_slice, | |
| 2320 | 1862 | .enum_simple, |
| 2321 | 1863 | .error_union, |
| 2322 | .anyerror_void_error_union, | |
| 2323 | 1864 | .anyframe_T, |
| 2324 | 1865 | .tuple, |
| 2325 | 1866 | .anon_struct, |
| ... | ... | @@ -2336,7 +1877,7 @@ pub const Type = struct { |
| 2336 | 1877 | |
| 2337 | 1878 | .array, |
| 2338 | 1879 | .array_sentinel, |
| 2339 | => ty.childType().hasWellDefinedLayout(mod), | |
| 1880 | => ty.childType(mod).hasWellDefinedLayout(mod), | |
| 2340 | 1881 | |
| 2341 | 1882 | .optional => ty.isPtrLikeOptional(mod), |
| 2342 | 1883 | .@"struct" => ty.castTag(.@"struct").?.data.layout != .Auto, |
| ... | ... | @@ -2417,76 +1958,36 @@ pub const Type = struct { |
| 2417 | 1958 | } |
| 2418 | 1959 | |
| 2419 | 1960 | pub fn ptrAlignmentAdvanced(ty: Type, mod: *const Module, opt_sema: ?*Sema) !u32 { |
| 2420 | switch (ty.tag()) { | |
| 2421 | .single_const_pointer, | |
| 2422 | .single_mut_pointer, | |
| 2423 | .many_const_pointer, | |
| 2424 | .many_mut_pointer, | |
| 2425 | .c_const_pointer, | |
| 2426 | .c_mut_pointer, | |
| 2427 | .const_slice, | |
| 2428 | .mut_slice, | |
| 2429 | .optional_single_const_pointer, | |
| 2430 | .optional_single_mut_pointer, | |
| 2431 | => { | |
| 2432 | const child_type = ty.cast(Payload.ElemType).?.data; | |
| 2433 | if (opt_sema) |sema| { | |
| 2434 | const res = try child_type.abiAlignmentAdvanced(mod, .{ .sema = sema }); | |
| 2435 | return res.scalar; | |
| 2436 | } | |
| 2437 | return (child_type.abiAlignmentAdvanced(mod, .eager) catch unreachable).scalar; | |
| 2438 | }, | |
| 2439 | ||
| 2440 | .manyptr_u8, | |
| 2441 | .manyptr_const_u8, | |
| 2442 | .manyptr_const_u8_sentinel_0, | |
| 2443 | .const_slice_u8, | |
| 2444 | .const_slice_u8_sentinel_0, | |
| 2445 | => return 1, | |
| 1961 | switch (ty.ip_index) { | |
| 1962 | .none => switch (ty.tag()) { | |
| 1963 | .pointer => { | |
| 1964 | const ptr_info = ty.castTag(.pointer).?.data; | |
| 1965 | if (ptr_info.@"align" != 0) { | |
| 1966 | return ptr_info.@"align"; | |
| 1967 | } else if (opt_sema) |sema| { | |
| 1968 | const res = try ptr_info.pointee_type.abiAlignmentAdvanced(mod, .{ .sema = sema }); | |
| 1969 | return res.scalar; | |
| 1970 | } else { | |
| 1971 | return (ptr_info.pointee_type.abiAlignmentAdvanced(mod, .eager) catch unreachable).scalar; | |
| 1972 | } | |
| 1973 | }, | |
| 1974 | .optional => return ty.castTag(.optional).?.data.ptrAlignmentAdvanced(mod, opt_sema), | |
| 2446 | 1975 | |
| 2447 | .pointer => { | |
| 2448 | const ptr_info = ty.castTag(.pointer).?.data; | |
| 2449 | if (ptr_info.@"align" != 0) { | |
| 2450 | return ptr_info.@"align"; | |
| 2451 | } else if (opt_sema) |sema| { | |
| 2452 | const res = try ptr_info.pointee_type.abiAlignmentAdvanced(mod, .{ .sema = sema }); | |
| 2453 | return res.scalar; | |
| 2454 | } else { | |
| 2455 | return (ptr_info.pointee_type.abiAlignmentAdvanced(mod, .eager) catch unreachable).scalar; | |
| 2456 | } | |
| 1976 | else => unreachable, | |
| 1977 | }, | |
| 1978 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 1979 | else => @panic("TODO"), | |
| 2457 | 1980 | }, |
| 2458 | .optional => return ty.castTag(.optional).?.data.ptrAlignmentAdvanced(mod, opt_sema), | |
| 2459 | ||
| 2460 | else => unreachable, | |
| 2461 | 1981 | } |
| 2462 | 1982 | } |
| 2463 | 1983 | |
| 2464 | pub fn ptrAddressSpace(self: Type) std.builtin.AddressSpace { | |
| 1984 | pub fn ptrAddressSpace(self: Type, mod: *const Module) std.builtin.AddressSpace { | |
| 2465 | 1985 | return switch (self.tag()) { |
| 2466 | .single_const_pointer_to_comptime_int, | |
| 2467 | .const_slice_u8, | |
| 2468 | .const_slice_u8_sentinel_0, | |
| 2469 | .single_const_pointer, | |
| 2470 | .single_mut_pointer, | |
| 2471 | .many_const_pointer, | |
| 2472 | .many_mut_pointer, | |
| 2473 | .c_const_pointer, | |
| 2474 | .c_mut_pointer, | |
| 2475 | .const_slice, | |
| 2476 | .mut_slice, | |
| 2477 | .inferred_alloc_const, | |
| 2478 | .inferred_alloc_mut, | |
| 2479 | .manyptr_u8, | |
| 2480 | .manyptr_const_u8, | |
| 2481 | .manyptr_const_u8_sentinel_0, | |
| 2482 | => .generic, | |
| 2483 | ||
| 2484 | 1986 | .pointer => self.castTag(.pointer).?.data.@"addrspace", |
| 2485 | 1987 | |
| 2486 | 1988 | .optional => { |
| 2487 | var buf: Payload.ElemType = undefined; | |
| 2488 | const child_type = self.optionalChild(&buf); | |
| 2489 | return child_type.ptrAddressSpace(); | |
| 1989 | const child_type = self.optionalChild(mod); | |
| 1990 | return child_type.ptrAddressSpace(mod); | |
| 2490 | 1991 | }, |
| 2491 | 1992 | |
| 2492 | 1993 | else => unreachable, |
| ... | ... | @@ -2530,15 +2031,31 @@ pub const Type = struct { |
| 2530 | 2031 | ) Module.CompileError!AbiAlignmentAdvanced { |
| 2531 | 2032 | const target = mod.getTarget(); |
| 2532 | 2033 | |
| 2034 | const opt_sema = switch (strat) { | |
| 2035 | .sema => |sema| sema, | |
| 2036 | else => null, | |
| 2037 | }; | |
| 2038 | ||
| 2533 | 2039 | if (ty.ip_index != .none) switch (mod.intern_pool.indexToKey(ty.ip_index)) { |
| 2534 | 2040 | .int_type => |int_type| { |
| 2535 | 2041 | if (int_type.bits == 0) return AbiAlignmentAdvanced{ .scalar = 0 }; |
| 2536 | 2042 | return AbiAlignmentAdvanced{ .scalar = intAbiAlignment(int_type.bits, target) }; |
| 2537 | 2043 | }, |
| 2538 | .ptr_type => @panic("TODO"), | |
| 2539 | .array_type => @panic("TODO"), | |
| 2540 | .vector_type => @panic("TODO"), | |
| 2541 | .optional_type => @panic("TODO"), | |
| 2044 | .ptr_type => { | |
| 2045 | return AbiAlignmentAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) }; | |
| 2046 | }, | |
| 2047 | .array_type => |array_type| { | |
| 2048 | return array_type.child.toType().abiAlignmentAdvanced(mod, strat); | |
| 2049 | }, | |
| 2050 | .vector_type => |vector_type| { | |
| 2051 | const bits_u64 = try bitSizeAdvanced(vector_type.child.toType(), mod, opt_sema); | |
| 2052 | const bits = @intCast(u32, bits_u64); | |
| 2053 | const bytes = ((bits * vector_type.len) + 7) / 8; | |
| 2054 | const alignment = std.math.ceilPowerOfTwoAssert(u32, bytes); | |
| 2055 | return AbiAlignmentAdvanced{ .scalar = alignment }; | |
| 2056 | }, | |
| 2057 | ||
| 2058 | .opt_type => @panic("TODO"), | |
| 2542 | 2059 | .error_union_type => @panic("TODO"), |
| 2543 | 2060 | .simple_type => |t| switch (t) { |
| 2544 | 2061 | .bool, |
| ... | ... | @@ -2617,15 +2134,8 @@ pub const Type = struct { |
| 2617 | 2134 | .enum_tag => unreachable, // it's a value, not a type |
| 2618 | 2135 | }; |
| 2619 | 2136 | |
| 2620 | const opt_sema = switch (strat) { | |
| 2621 | .sema => |sema| sema, | |
| 2622 | else => null, | |
| 2623 | }; | |
| 2624 | 2137 | switch (ty.tag()) { |
| 2625 | .array_u8_sentinel_0, | |
| 2626 | .array_u8, | |
| 2627 | .@"opaque", | |
| 2628 | => return AbiAlignmentAdvanced{ .scalar = 1 }, | |
| 2138 | .@"opaque" => return AbiAlignmentAdvanced{ .scalar = 1 }, | |
| 2629 | 2139 | |
| 2630 | 2140 | // represents machine code; not a pointer |
| 2631 | 2141 | .function => { |
| ... | ... | @@ -2634,47 +2144,21 @@ pub const Type = struct { |
| 2634 | 2144 | return AbiAlignmentAdvanced{ .scalar = target_util.defaultFunctionAlignment(target) }; |
| 2635 | 2145 | }, |
| 2636 | 2146 | |
| 2637 | .single_const_pointer_to_comptime_int, | |
| 2638 | .const_slice_u8, | |
| 2639 | .const_slice_u8_sentinel_0, | |
| 2640 | .single_const_pointer, | |
| 2641 | .single_mut_pointer, | |
| 2642 | .many_const_pointer, | |
| 2643 | .many_mut_pointer, | |
| 2644 | .c_const_pointer, | |
| 2645 | .c_mut_pointer, | |
| 2646 | .const_slice, | |
| 2647 | .mut_slice, | |
| 2648 | .optional_single_const_pointer, | |
| 2649 | .optional_single_mut_pointer, | |
| 2650 | 2147 | .pointer, |
| 2651 | .manyptr_u8, | |
| 2652 | .manyptr_const_u8, | |
| 2653 | .manyptr_const_u8_sentinel_0, | |
| 2654 | 2148 | .anyframe_T, |
| 2655 | 2149 | => return AbiAlignmentAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) }, |
| 2656 | 2150 | |
| 2657 | 2151 | // TODO revisit this when we have the concept of the error tag type |
| 2658 | .anyerror_void_error_union, | |
| 2659 | 2152 | .error_set_inferred, |
| 2660 | 2153 | .error_set_single, |
| 2661 | 2154 | .error_set, |
| 2662 | 2155 | .error_set_merged, |
| 2663 | 2156 | => return AbiAlignmentAdvanced{ .scalar = 2 }, |
| 2664 | 2157 | |
| 2665 | .array, .array_sentinel => return ty.elemType().abiAlignmentAdvanced(mod, strat), | |
| 2666 | ||
| 2667 | .vector => { | |
| 2668 | const len = ty.arrayLen(); | |
| 2669 | const bits = try bitSizeAdvanced(ty.elemType(), mod, opt_sema); | |
| 2670 | const bytes = ((bits * len) + 7) / 8; | |
| 2671 | const alignment = std.math.ceilPowerOfTwoAssert(u64, bytes); | |
| 2672 | return AbiAlignmentAdvanced{ .scalar = @intCast(u32, alignment) }; | |
| 2673 | }, | |
| 2158 | .array, .array_sentinel => return ty.childType(mod).abiAlignmentAdvanced(mod, strat), | |
| 2674 | 2159 | |
| 2675 | 2160 | .optional => { |
| 2676 | var buf: Payload.ElemType = undefined; | |
| 2677 | const child_type = ty.optionalChild(&buf); | |
| 2161 | const child_type = ty.optionalChild(mod); | |
| 2678 | 2162 | |
| 2679 | 2163 | switch (child_type.zigTypeTag(mod)) { |
| 2680 | 2164 | .Pointer => return AbiAlignmentAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) }, |
| ... | ... | @@ -2933,8 +2417,29 @@ pub const Type = struct { |
| 2933 | 2417 | }, |
| 2934 | 2418 | .ptr_type => @panic("TODO"), |
| 2935 | 2419 | .array_type => @panic("TODO"), |
| 2936 | .vector_type => @panic("TODO"), | |
| 2937 | .optional_type => @panic("TODO"), | |
| 2420 | .vector_type => |vector_type| { | |
| 2421 | const opt_sema = switch (strat) { | |
| 2422 | .sema => |sema| sema, | |
| 2423 | .eager => null, | |
| 2424 | .lazy => |arena| return AbiSizeAdvanced{ | |
| 2425 | .val = try Value.Tag.lazy_size.create(arena, ty), | |
| 2426 | }, | |
| 2427 | }; | |
| 2428 | const elem_bits_u64 = try vector_type.child.toType().bitSizeAdvanced(mod, opt_sema); | |
| 2429 | const elem_bits = @intCast(u32, elem_bits_u64); | |
| 2430 | const total_bits = elem_bits * vector_type.len; | |
| 2431 | const total_bytes = (total_bits + 7) / 8; | |
| 2432 | const alignment = switch (try ty.abiAlignmentAdvanced(mod, strat)) { | |
| 2433 | .scalar => |x| x, | |
| 2434 | .val => return AbiSizeAdvanced{ | |
| 2435 | .val = try Value.Tag.lazy_size.create(strat.lazy, ty), | |
| 2436 | }, | |
| 2437 | }; | |
| 2438 | const result = std.mem.alignForwardGeneric(u32, total_bytes, alignment); | |
| 2439 | return AbiSizeAdvanced{ .scalar = result }; | |
| 2440 | }, | |
| 2441 | ||
| 2442 | .opt_type => @panic("TODO"), | |
| 2938 | 2443 | .error_union_type => @panic("TODO"), |
| 2939 | 2444 | .simple_type => |t| switch (t) { |
| 2940 | 2445 | .bool, |
| ... | ... | @@ -3014,7 +2519,6 @@ pub const Type = struct { |
| 3014 | 2519 | .inferred_alloc_const => unreachable, |
| 3015 | 2520 | .inferred_alloc_mut => unreachable, |
| 3016 | 2521 | |
| 3017 | .single_const_pointer_to_comptime_int, | |
| 3018 | 2522 | .empty_struct_literal, |
| 3019 | 2523 | .empty_struct, |
| 3020 | 2524 | => return AbiSizeAdvanced{ .scalar = 0 }, |
| ... | ... | @@ -3068,8 +2572,6 @@ pub const Type = struct { |
| 3068 | 2572 | return abiSizeAdvancedUnion(ty, mod, strat, union_obj, true); |
| 3069 | 2573 | }, |
| 3070 | 2574 | |
| 3071 | .array_u8 => return AbiSizeAdvanced{ .scalar = ty.castTag(.array_u8).?.data }, | |
| 3072 | .array_u8_sentinel_0 => return AbiSizeAdvanced{ .scalar = ty.castTag(.array_u8_sentinel_0).?.data + 1 }, | |
| 3073 | 2575 | .array => { |
| 3074 | 2576 | const payload = ty.castTag(.array).?.data; |
| 3075 | 2577 | switch (try payload.elem_type.abiSizeAdvanced(mod, strat)) { |
| ... | ... | @@ -3093,47 +2595,7 @@ pub const Type = struct { |
| 3093 | 2595 | } |
| 3094 | 2596 | }, |
| 3095 | 2597 | |
| 3096 | .vector => { | |
| 3097 | const payload = ty.castTag(.vector).?.data; | |
| 3098 | const opt_sema = switch (strat) { | |
| 3099 | .sema => |sema| sema, | |
| 3100 | .eager => null, | |
| 3101 | .lazy => |arena| return AbiSizeAdvanced{ | |
| 3102 | .val = try Value.Tag.lazy_size.create(arena, ty), | |
| 3103 | }, | |
| 3104 | }; | |
| 3105 | const elem_bits = try payload.elem_type.bitSizeAdvanced(mod, opt_sema); | |
| 3106 | const total_bits = elem_bits * payload.len; | |
| 3107 | const total_bytes = (total_bits + 7) / 8; | |
| 3108 | const alignment = switch (try ty.abiAlignmentAdvanced(mod, strat)) { | |
| 3109 | .scalar => |x| x, | |
| 3110 | .val => return AbiSizeAdvanced{ | |
| 3111 | .val = try Value.Tag.lazy_size.create(strat.lazy, ty), | |
| 3112 | }, | |
| 3113 | }; | |
| 3114 | const result = std.mem.alignForwardGeneric(u64, total_bytes, alignment); | |
| 3115 | return AbiSizeAdvanced{ .scalar = result }; | |
| 3116 | }, | |
| 3117 | ||
| 3118 | .anyframe_T, | |
| 3119 | .optional_single_const_pointer, | |
| 3120 | .optional_single_mut_pointer, | |
| 3121 | .single_const_pointer, | |
| 3122 | .single_mut_pointer, | |
| 3123 | .many_const_pointer, | |
| 3124 | .many_mut_pointer, | |
| 3125 | .c_const_pointer, | |
| 3126 | .c_mut_pointer, | |
| 3127 | .manyptr_u8, | |
| 3128 | .manyptr_const_u8, | |
| 3129 | .manyptr_const_u8_sentinel_0, | |
| 3130 | => return AbiSizeAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) }, | |
| 3131 | ||
| 3132 | .const_slice, | |
| 3133 | .mut_slice, | |
| 3134 | .const_slice_u8, | |
| 3135 | .const_slice_u8_sentinel_0, | |
| 3136 | => return AbiSizeAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) * 2 }, | |
| 2598 | .anyframe_T => return AbiSizeAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) }, | |
| 3137 | 2599 | |
| 3138 | 2600 | .pointer => switch (ty.castTag(.pointer).?.data.size) { |
| 3139 | 2601 | .Slice => return AbiSizeAdvanced{ .scalar = @divExact(target.ptrBitWidth(), 8) * 2 }, |
| ... | ... | @@ -3141,7 +2603,6 @@ pub const Type = struct { |
| 3141 | 2603 | }, |
| 3142 | 2604 | |
| 3143 | 2605 | // TODO revisit this when we have the concept of the error tag type |
| 3144 | .anyerror_void_error_union, | |
| 3145 | 2606 | .error_set_inferred, |
| 3146 | 2607 | .error_set, |
| 3147 | 2608 | .error_set_merged, |
| ... | ... | @@ -3149,8 +2610,7 @@ pub const Type = struct { |
| 3149 | 2610 | => return AbiSizeAdvanced{ .scalar = 2 }, |
| 3150 | 2611 | |
| 3151 | 2612 | .optional => { |
| 3152 | var buf: Payload.ElemType = undefined; | |
| 3153 | const child_type = ty.optionalChild(&buf); | |
| 2613 | const child_type = ty.optionalChild(mod); | |
| 3154 | 2614 | |
| 3155 | 2615 | if (child_type.isNoReturn()) { |
| 3156 | 2616 | return AbiSizeAdvanced{ .scalar = 0 }; |
| ... | ... | @@ -3272,8 +2732,12 @@ pub const Type = struct { |
| 3272 | 2732 | .int_type => |int_type| return int_type.bits, |
| 3273 | 2733 | .ptr_type => @panic("TODO"), |
| 3274 | 2734 | .array_type => @panic("TODO"), |
| 3275 | .vector_type => @panic("TODO"), | |
| 3276 | .optional_type => @panic("TODO"), | |
| 2735 | .vector_type => |vector_type| { | |
| 2736 | const child_ty = vector_type.child.toType(); | |
| 2737 | const elem_bit_size = try bitSizeAdvanced(child_ty, mod, opt_sema); | |
| 2738 | return elem_bit_size * vector_type.len; | |
| 2739 | }, | |
| 2740 | .opt_type => @panic("TODO"), | |
| 3277 | 2741 | .error_union_type => @panic("TODO"), |
| 3278 | 2742 | .simple_type => |t| switch (t) { |
| 3279 | 2743 | .f16 => return 16, |
| ... | ... | @@ -3339,7 +2803,6 @@ pub const Type = struct { |
| 3339 | 2803 | |
| 3340 | 2804 | switch (ty.tag()) { |
| 3341 | 2805 | .function => unreachable, // represents machine code; not a pointer |
| 3342 | .single_const_pointer_to_comptime_int => unreachable, | |
| 3343 | 2806 | .empty_struct => unreachable, |
| 3344 | 2807 | .empty_struct_literal => unreachable, |
| 3345 | 2808 | .inferred_alloc_const => unreachable, |
| ... | ... | @@ -3388,13 +2851,6 @@ pub const Type = struct { |
| 3388 | 2851 | return size; |
| 3389 | 2852 | }, |
| 3390 | 2853 | |
| 3391 | .vector => { | |
| 3392 | const payload = ty.castTag(.vector).?.data; | |
| 3393 | const elem_bit_size = try bitSizeAdvanced(payload.elem_type, mod, opt_sema); | |
| 3394 | return elem_bit_size * payload.len; | |
| 3395 | }, | |
| 3396 | .array_u8 => return 8 * ty.castTag(.array_u8).?.data, | |
| 3397 | .array_u8_sentinel_0 => return 8 * (ty.castTag(.array_u8_sentinel_0).?.data + 1), | |
| 3398 | 2854 | .array => { |
| 3399 | 2855 | const payload = ty.castTag(.array).?.data; |
| 3400 | 2856 | const elem_size = std.math.max(payload.elem_type.abiAlignment(mod), payload.elem_type.abiSize(mod)); |
| ... | ... | @@ -3415,43 +2871,13 @@ pub const Type = struct { |
| 3415 | 2871 | |
| 3416 | 2872 | .anyframe_T => return target.ptrBitWidth(), |
| 3417 | 2873 | |
| 3418 | .const_slice, | |
| 3419 | .mut_slice, | |
| 3420 | => return target.ptrBitWidth() * 2, | |
| 3421 | ||
| 3422 | .const_slice_u8, | |
| 3423 | .const_slice_u8_sentinel_0, | |
| 3424 | => return target.ptrBitWidth() * 2, | |
| 3425 | ||
| 3426 | .optional_single_const_pointer, | |
| 3427 | .optional_single_mut_pointer, | |
| 3428 | => { | |
| 3429 | return target.ptrBitWidth(); | |
| 3430 | }, | |
| 3431 | ||
| 3432 | .single_const_pointer, | |
| 3433 | .single_mut_pointer, | |
| 3434 | .many_const_pointer, | |
| 3435 | .many_mut_pointer, | |
| 3436 | .c_const_pointer, | |
| 3437 | .c_mut_pointer, | |
| 3438 | => { | |
| 3439 | return target.ptrBitWidth(); | |
| 3440 | }, | |
| 3441 | ||
| 3442 | 2874 | .pointer => switch (ty.castTag(.pointer).?.data.size) { |
| 3443 | 2875 | .Slice => return target.ptrBitWidth() * 2, |
| 3444 | 2876 | else => return target.ptrBitWidth(), |
| 3445 | 2877 | }, |
| 3446 | 2878 | |
| 3447 | .manyptr_u8, | |
| 3448 | .manyptr_const_u8, | |
| 3449 | .manyptr_const_u8_sentinel_0, | |
| 3450 | => return target.ptrBitWidth(), | |
| 3451 | ||
| 3452 | 2879 | .error_set, |
| 3453 | 2880 | .error_set_single, |
| 3454 | .anyerror_void_error_union, | |
| 3455 | 2881 | .error_set_inferred, |
| 3456 | 2882 | .error_set_merged, |
| 3457 | 2883 | => return 16, // TODO revisit this when we have the concept of the error tag type |
| ... | ... | @@ -3481,12 +2907,11 @@ pub const Type = struct { |
| 3481 | 2907 | return true; |
| 3482 | 2908 | }, |
| 3483 | 2909 | .Array => { |
| 3484 | if (ty.arrayLenIncludingSentinel() == 0) return true; | |
| 3485 | return ty.childType().layoutIsResolved(mod); | |
| 2910 | if (ty.arrayLenIncludingSentinel(mod) == 0) return true; | |
| 2911 | return ty.childType(mod).layoutIsResolved(mod); | |
| 3486 | 2912 | }, |
| 3487 | 2913 | .Optional => { |
| 3488 | var buf: Type.Payload.ElemType = undefined; | |
| 3489 | const payload_ty = ty.optionalChild(&buf); | |
| 2914 | const payload_ty = ty.optionalChild(mod); | |
| 3490 | 2915 | return payload_ty.layoutIsResolved(mod); |
| 3491 | 2916 | }, |
| 3492 | 2917 | .ErrorUnion => { |
| ... | ... | @@ -3500,9 +2925,6 @@ pub const Type = struct { |
| 3500 | 2925 | pub fn isSinglePointer(ty: Type, mod: *const Module) bool { |
| 3501 | 2926 | switch (ty.ip_index) { |
| 3502 | 2927 | .none => return switch (ty.tag()) { |
| 3503 | .single_const_pointer, | |
| 3504 | .single_mut_pointer, | |
| 3505 | .single_const_pointer_to_comptime_int, | |
| 3506 | 2928 | .inferred_alloc_const, |
| 3507 | 2929 | .inferred_alloc_mut, |
| 3508 | 2930 | => true, |
| ... | ... | @@ -3519,54 +2941,33 @@ pub const Type = struct { |
| 3519 | 2941 | } |
| 3520 | 2942 | |
| 3521 | 2943 | /// Asserts `ty` is a pointer. |
| 3522 | pub fn ptrSize(ty: Type) std.builtin.Type.Pointer.Size { | |
| 3523 | return ptrSizeOrNull(ty).?; | |
| 2944 | pub fn ptrSize(ty: Type, mod: *const Module) std.builtin.Type.Pointer.Size { | |
| 2945 | return ptrSizeOrNull(ty, mod).?; | |
| 3524 | 2946 | } |
| 3525 | 2947 | |
| 3526 | 2948 | /// Returns `null` if `ty` is not a pointer. |
| 3527 | pub fn ptrSizeOrNull(ty: Type) ?std.builtin.Type.Pointer.Size { | |
| 3528 | return switch (ty.tag()) { | |
| 3529 | .const_slice, | |
| 3530 | .mut_slice, | |
| 3531 | .const_slice_u8, | |
| 3532 | .const_slice_u8_sentinel_0, | |
| 3533 | => .Slice, | |
| 3534 | ||
| 3535 | .many_const_pointer, | |
| 3536 | .many_mut_pointer, | |
| 3537 | .manyptr_u8, | |
| 3538 | .manyptr_const_u8, | |
| 3539 | .manyptr_const_u8_sentinel_0, | |
| 3540 | => .Many, | |
| 3541 | ||
| 3542 | .c_const_pointer, | |
| 3543 | .c_mut_pointer, | |
| 3544 | => .C, | |
| 3545 | ||
| 3546 | .single_const_pointer, | |
| 3547 | .single_mut_pointer, | |
| 3548 | .single_const_pointer_to_comptime_int, | |
| 3549 | .inferred_alloc_const, | |
| 3550 | .inferred_alloc_mut, | |
| 3551 | => .One, | |
| 2949 | pub fn ptrSizeOrNull(ty: Type, mod: *const Module) ?std.builtin.Type.Pointer.Size { | |
| 2950 | return switch (ty.ip_index) { | |
| 2951 | .none => switch (ty.tag()) { | |
| 2952 | .inferred_alloc_const, | |
| 2953 | .inferred_alloc_mut, | |
| 2954 | => .One, | |
| 3552 | 2955 | |
| 3553 | .pointer => ty.castTag(.pointer).?.data.size, | |
| 2956 | .pointer => ty.castTag(.pointer).?.data.size, | |
| 3554 | 2957 | |
| 3555 | else => null, | |
| 2958 | else => null, | |
| 2959 | }, | |
| 2960 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 2961 | .ptr_type => |ptr_info| ptr_info.size, | |
| 2962 | else => null, | |
| 2963 | }, | |
| 3556 | 2964 | }; |
| 3557 | 2965 | } |
| 3558 | 2966 | |
| 3559 | 2967 | pub fn isSlice(ty: Type, mod: *const Module) bool { |
| 3560 | 2968 | return switch (ty.ip_index) { |
| 3561 | 2969 | .none => switch (ty.tag()) { |
| 3562 | .const_slice, | |
| 3563 | .mut_slice, | |
| 3564 | .const_slice_u8, | |
| 3565 | .const_slice_u8_sentinel_0, | |
| 3566 | => true, | |
| 3567 | ||
| 3568 | 2970 | .pointer => ty.castTag(.pointer).?.data.size == .Slice, |
| 3569 | ||
| 3570 | 2971 | else => false, |
| 3571 | 2972 | }, |
| 3572 | 2973 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { |
| ... | ... | @@ -3583,78 +2984,28 @@ pub const Type = struct { |
| 3583 | 2984 | |
| 3584 | 2985 | pub fn slicePtrFieldType(self: Type, buffer: *SlicePtrFieldTypeBuffer) Type { |
| 3585 | 2986 | switch (self.tag()) { |
| 3586 | .const_slice_u8 => return Type.initTag(.manyptr_const_u8), | |
| 3587 | .const_slice_u8_sentinel_0 => return Type.initTag(.manyptr_const_u8_sentinel_0), | |
| 3588 | ||
| 3589 | .const_slice => { | |
| 3590 | const elem_type = self.castTag(.const_slice).?.data; | |
| 3591 | buffer.* = .{ | |
| 3592 | .elem_type = .{ | |
| 3593 | .base = .{ .tag = .many_const_pointer }, | |
| 3594 | .data = elem_type, | |
| 3595 | }, | |
| 3596 | }; | |
| 3597 | return Type.initPayload(&buffer.elem_type.base); | |
| 3598 | }, | |
| 3599 | .mut_slice => { | |
| 3600 | const elem_type = self.castTag(.mut_slice).?.data; | |
| 3601 | buffer.* = .{ | |
| 3602 | .elem_type = .{ | |
| 3603 | .base = .{ .tag = .many_mut_pointer }, | |
| 3604 | .data = elem_type, | |
| 3605 | }, | |
| 3606 | }; | |
| 3607 | return Type.initPayload(&buffer.elem_type.base); | |
| 3608 | }, | |
| 3609 | ||
| 3610 | 2987 | .pointer => { |
| 3611 | 2988 | const payload = self.castTag(.pointer).?.data; |
| 3612 | 2989 | assert(payload.size == .Slice); |
| 3613 | 2990 | |
| 3614 | if (payload.sentinel != null or | |
| 3615 | payload.@"align" != 0 or | |
| 3616 | payload.@"addrspace" != .generic or | |
| 3617 | payload.bit_offset != 0 or | |
| 3618 | payload.host_size != 0 or | |
| 3619 | payload.vector_index != .none or | |
| 3620 | payload.@"allowzero" or | |
| 3621 | payload.@"volatile") | |
| 3622 | { | |
| 3623 | buffer.* = .{ | |
| 3624 | .pointer = .{ | |
| 3625 | .data = .{ | |
| 3626 | .pointee_type = payload.pointee_type, | |
| 3627 | .sentinel = payload.sentinel, | |
| 3628 | .@"align" = payload.@"align", | |
| 3629 | .@"addrspace" = payload.@"addrspace", | |
| 3630 | .bit_offset = payload.bit_offset, | |
| 3631 | .host_size = payload.host_size, | |
| 3632 | .vector_index = payload.vector_index, | |
| 3633 | .@"allowzero" = payload.@"allowzero", | |
| 3634 | .mutable = payload.mutable, | |
| 3635 | .@"volatile" = payload.@"volatile", | |
| 3636 | .size = .Many, | |
| 3637 | }, | |
| 3638 | }, | |
| 3639 | }; | |
| 3640 | return Type.initPayload(&buffer.pointer.base); | |
| 3641 | } else if (payload.mutable) { | |
| 3642 | buffer.* = .{ | |
| 3643 | .elem_type = .{ | |
| 3644 | .base = .{ .tag = .many_mut_pointer }, | |
| 3645 | .data = payload.pointee_type, | |
| 3646 | }, | |
| 3647 | }; | |
| 3648 | return Type.initPayload(&buffer.elem_type.base); | |
| 3649 | } else { | |
| 3650 | buffer.* = .{ | |
| 3651 | .elem_type = .{ | |
| 3652 | .base = .{ .tag = .many_const_pointer }, | |
| 3653 | .data = payload.pointee_type, | |
| 2991 | buffer.* = .{ | |
| 2992 | .pointer = .{ | |
| 2993 | .data = .{ | |
| 2994 | .pointee_type = payload.pointee_type, | |
| 2995 | .sentinel = payload.sentinel, | |
| 2996 | .@"align" = payload.@"align", | |
| 2997 | .@"addrspace" = payload.@"addrspace", | |
| 2998 | .bit_offset = payload.bit_offset, | |
| 2999 | .host_size = payload.host_size, | |
| 3000 | .vector_index = payload.vector_index, | |
| 3001 | .@"allowzero" = payload.@"allowzero", | |
| 3002 | .mutable = payload.mutable, | |
| 3003 | .@"volatile" = payload.@"volatile", | |
| 3004 | .size = .Many, | |
| 3654 | 3005 | }, |
| 3655 | }; | |
| 3656 | return Type.initPayload(&buffer.elem_type.base); | |
| 3657 | } | |
| 3006 | }, | |
| 3007 | }; | |
| 3008 | return Type.initPayload(&buffer.pointer.base); | |
| 3658 | 3009 | }, |
| 3659 | 3010 | |
| 3660 | 3011 | else => unreachable, |
| ... | ... | @@ -3663,19 +3014,7 @@ pub const Type = struct { |
| 3663 | 3014 | |
| 3664 | 3015 | pub fn isConstPtr(self: Type) bool { |
| 3665 | 3016 | return switch (self.tag()) { |
| 3666 | .single_const_pointer, | |
| 3667 | .many_const_pointer, | |
| 3668 | .c_const_pointer, | |
| 3669 | .single_const_pointer_to_comptime_int, | |
| 3670 | .const_slice_u8, | |
| 3671 | .const_slice_u8_sentinel_0, | |
| 3672 | .const_slice, | |
| 3673 | .manyptr_const_u8, | |
| 3674 | .manyptr_const_u8_sentinel_0, | |
| 3675 | => true, | |
| 3676 | ||
| 3677 | 3017 | .pointer => !self.castTag(.pointer).?.data.mutable, |
| 3678 | ||
| 3679 | 3018 | else => false, |
| 3680 | 3019 | }; |
| 3681 | 3020 | } |
| ... | ... | @@ -3702,49 +3041,46 @@ pub const Type = struct { |
| 3702 | 3041 | |
| 3703 | 3042 | pub fn isCPtr(self: Type) bool { |
| 3704 | 3043 | return switch (self.tag()) { |
| 3705 | .c_const_pointer, | |
| 3706 | .c_mut_pointer, | |
| 3707 | => return true, | |
| 3708 | ||
| 3709 | 3044 | .pointer => self.castTag(.pointer).?.data.size == .C, |
| 3710 | 3045 | |
| 3711 | 3046 | else => return false, |
| 3712 | 3047 | }; |
| 3713 | 3048 | } |
| 3714 | 3049 | |
| 3715 | pub fn isPtrAtRuntime(self: Type, mod: *const Module) bool { | |
| 3716 | switch (self.tag()) { | |
| 3717 | .c_const_pointer, | |
| 3718 | .c_mut_pointer, | |
| 3719 | .many_const_pointer, | |
| 3720 | .many_mut_pointer, | |
| 3721 | .manyptr_const_u8, | |
| 3722 | .manyptr_const_u8_sentinel_0, | |
| 3723 | .manyptr_u8, | |
| 3724 | .optional_single_const_pointer, | |
| 3725 | .optional_single_mut_pointer, | |
| 3726 | .single_const_pointer, | |
| 3727 | .single_const_pointer_to_comptime_int, | |
| 3728 | .single_mut_pointer, | |
| 3729 | => return true, | |
| 3050 | pub fn isPtrAtRuntime(ty: Type, mod: *const Module) bool { | |
| 3051 | switch (ty.ip_index) { | |
| 3052 | .none => switch (ty.tag()) { | |
| 3053 | .pointer => switch (ty.castTag(.pointer).?.data.size) { | |
| 3054 | .Slice => return false, | |
| 3055 | .One, .Many, .C => return true, | |
| 3056 | }, | |
| 3730 | 3057 | |
| 3731 | .pointer => switch (self.castTag(.pointer).?.data.size) { | |
| 3732 | .Slice => return false, | |
| 3733 | .One, .Many, .C => return true, | |
| 3734 | }, | |
| 3058 | .optional => { | |
| 3059 | const child_type = ty.optionalChild(mod); | |
| 3060 | if (child_type.zigTypeTag(mod) != .Pointer) return false; | |
| 3061 | const info = child_type.ptrInfo(mod); | |
| 3062 | switch (info.size) { | |
| 3063 | .Slice, .C => return false, | |
| 3064 | .Many, .One => return !info.@"allowzero", | |
| 3065 | } | |
| 3066 | }, | |
| 3735 | 3067 | |
| 3736 | .optional => { | |
| 3737 | var buf: Payload.ElemType = undefined; | |
| 3738 | const child_type = self.optionalChild(&buf); | |
| 3739 | if (child_type.zigTypeTag(mod) != .Pointer) return false; | |
| 3740 | const info = child_type.ptrInfo().data; | |
| 3741 | switch (info.size) { | |
| 3742 | .Slice, .C => return false, | |
| 3743 | .Many, .One => return !info.@"allowzero", | |
| 3744 | } | |
| 3068 | else => return false, | |
| 3069 | }, | |
| 3070 | else => return switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 3071 | .ptr_type => |ptr_type| switch (ptr_type.size) { | |
| 3072 | .Slice => false, | |
| 3073 | .One, .Many, .C => true, | |
| 3074 | }, | |
| 3075 | .opt_type => |child| switch (mod.intern_pool.indexToKey(child)) { | |
| 3076 | .ptr_type => |p| switch (p.size) { | |
| 3077 | .Slice, .C => false, | |
| 3078 | .Many, .One => !p.is_allowzero, | |
| 3079 | }, | |
| 3080 | else => false, | |
| 3081 | }, | |
| 3082 | else => false, | |
| 3745 | 3083 | }, |
| 3746 | ||
| 3747 | else => return false, | |
| 3748 | 3084 | } |
| 3749 | 3085 | } |
| 3750 | 3086 | |
| ... | ... | @@ -3754,23 +3090,17 @@ pub const Type = struct { |
| 3754 | 3090 | if (ty.isPtrLikeOptional(mod)) { |
| 3755 | 3091 | return true; |
| 3756 | 3092 | } |
| 3757 | return ty.ptrInfo().data.@"allowzero"; | |
| 3093 | return ty.ptrInfo(mod).@"allowzero"; | |
| 3758 | 3094 | } |
| 3759 | 3095 | |
| 3760 | 3096 | /// See also `isPtrLikeOptional`. |
| 3761 | 3097 | pub fn optionalReprIsPayload(ty: Type, mod: *const Module) bool { |
| 3762 | 3098 | switch (ty.tag()) { |
| 3763 | .optional_single_const_pointer, | |
| 3764 | .optional_single_mut_pointer, | |
| 3765 | .c_const_pointer, | |
| 3766 | .c_mut_pointer, | |
| 3767 | => return true, | |
| 3768 | ||
| 3769 | 3099 | .optional => { |
| 3770 | 3100 | const child_ty = ty.castTag(.optional).?.data; |
| 3771 | 3101 | switch (child_ty.zigTypeTag(mod)) { |
| 3772 | 3102 | .Pointer => { |
| 3773 | const info = child_ty.ptrInfo().data; | |
| 3103 | const info = child_ty.ptrInfo(mod); | |
| 3774 | 3104 | switch (info.size) { |
| 3775 | 3105 | .C => return false, |
| 3776 | 3106 | .Slice, .Many, .One => return !info.@"allowzero", |
| ... | ... | @@ -3793,7 +3123,7 @@ pub const Type = struct { |
| 3793 | 3123 | pub fn isPtrLikeOptional(ty: Type, mod: *const Module) bool { |
| 3794 | 3124 | if (ty.ip_index != .none) return switch (mod.intern_pool.indexToKey(ty.ip_index)) { |
| 3795 | 3125 | .ptr_type => |ptr_type| ptr_type.size == .C, |
| 3796 | .optional_type => |o| switch (mod.intern_pool.indexToKey(o.payload_type)) { | |
| 3126 | .opt_type => |child| switch (mod.intern_pool.indexToKey(child)) { | |
| 3797 | 3127 | .ptr_type => |ptr_type| switch (ptr_type.size) { |
| 3798 | 3128 | .Slice, .C => false, |
| 3799 | 3129 | .Many, .One => !ptr_type.is_allowzero, |
| ... | ... | @@ -3803,16 +3133,10 @@ pub const Type = struct { |
| 3803 | 3133 | else => false, |
| 3804 | 3134 | }; |
| 3805 | 3135 | switch (ty.tag()) { |
| 3806 | .optional_single_const_pointer, | |
| 3807 | .optional_single_mut_pointer, | |
| 3808 | .c_const_pointer, | |
| 3809 | .c_mut_pointer, | |
| 3810 | => return true, | |
| 3811 | ||
| 3812 | 3136 | .optional => { |
| 3813 | 3137 | const child_ty = ty.castTag(.optional).?.data; |
| 3814 | 3138 | if (child_ty.zigTypeTag(mod) != .Pointer) return false; |
| 3815 | const info = child_ty.ptrInfo().data; | |
| 3139 | const info = child_ty.ptrInfo(mod); | |
| 3816 | 3140 | switch (info.size) { |
| 3817 | 3141 | .Slice, .C => return false, |
| 3818 | 3142 | .Many, .One => return !info.@"allowzero", |
| ... | ... | @@ -3828,43 +3152,24 @@ pub const Type = struct { |
| 3828 | 3152 | /// For *[N]T, returns [N]T. |
| 3829 | 3153 | /// For *T, returns T. |
| 3830 | 3154 | /// For [*]T, returns T. |
| 3831 | pub fn childType(ty: Type) Type { | |
| 3832 | return switch (ty.tag()) { | |
| 3833 | .vector => ty.castTag(.vector).?.data.elem_type, | |
| 3834 | .array => ty.castTag(.array).?.data.elem_type, | |
| 3835 | .array_sentinel => ty.castTag(.array_sentinel).?.data.elem_type, | |
| 3836 | .optional_single_mut_pointer, | |
| 3837 | .optional_single_const_pointer, | |
| 3838 | .single_const_pointer, | |
| 3839 | .single_mut_pointer, | |
| 3840 | .many_const_pointer, | |
| 3841 | .many_mut_pointer, | |
| 3842 | .c_const_pointer, | |
| 3843 | .c_mut_pointer, | |
| 3844 | .const_slice, | |
| 3845 | .mut_slice, | |
| 3846 | => ty.castPointer().?.data, | |
| 3847 | ||
| 3848 | .array_u8, | |
| 3849 | .array_u8_sentinel_0, | |
| 3850 | .const_slice_u8, | |
| 3851 | .const_slice_u8_sentinel_0, | |
| 3852 | .manyptr_u8, | |
| 3853 | .manyptr_const_u8, | |
| 3854 | .manyptr_const_u8_sentinel_0, | |
| 3855 | => Type.u8, | |
| 3856 | ||
| 3857 | .single_const_pointer_to_comptime_int => Type.comptime_int, | |
| 3858 | .pointer => ty.castTag(.pointer).?.data.pointee_type, | |
| 3155 | pub fn childType(ty: Type, mod: *const Module) Type { | |
| 3156 | return childTypeIp(ty, mod.intern_pool); | |
| 3157 | } | |
| 3859 | 3158 | |
| 3860 | else => unreachable, | |
| 3159 | pub fn childTypeIp(ty: Type, ip: InternPool) Type { | |
| 3160 | return switch (ty.ip_index) { | |
| 3161 | .none => switch (ty.tag()) { | |
| 3162 | .array => ty.castTag(.array).?.data.elem_type, | |
| 3163 | .array_sentinel => ty.castTag(.array_sentinel).?.data.elem_type, | |
| 3164 | ||
| 3165 | .pointer => ty.castTag(.pointer).?.data.pointee_type, | |
| 3166 | ||
| 3167 | else => unreachable, | |
| 3168 | }, | |
| 3169 | else => ip.childType(ty.ip_index).toType(), | |
| 3861 | 3170 | }; |
| 3862 | 3171 | } |
| 3863 | 3172 | |
| 3864 | /// Asserts the type is a pointer or array type. | |
| 3865 | /// TODO this is deprecated in favor of `childType`. | |
| 3866 | pub const elemType = childType; | |
| 3867 | ||
| 3868 | 3173 | /// For *[N]T, returns T. |
| 3869 | 3174 | /// For ?*T, returns T. |
| 3870 | 3175 | /// For ?*[N]T, returns T. |
| ... | ... | @@ -3875,54 +3180,42 @@ pub const Type = struct { |
| 3875 | 3180 | /// For []T, returns T. |
| 3876 | 3181 | /// For anyframe->T, returns T. |
| 3877 | 3182 | pub fn elemType2(ty: Type, mod: *const Module) Type { |
| 3878 | return switch (ty.tag()) { | |
| 3879 | .vector => ty.castTag(.vector).?.data.elem_type, | |
| 3880 | .array => ty.castTag(.array).?.data.elem_type, | |
| 3881 | .array_sentinel => ty.castTag(.array_sentinel).?.data.elem_type, | |
| 3882 | .many_const_pointer, | |
| 3883 | .many_mut_pointer, | |
| 3884 | .c_const_pointer, | |
| 3885 | .c_mut_pointer, | |
| 3886 | .const_slice, | |
| 3887 | .mut_slice, | |
| 3888 | => ty.castPointer().?.data, | |
| 3889 | ||
| 3890 | .single_const_pointer, | |
| 3891 | .single_mut_pointer, | |
| 3892 | => ty.castPointer().?.data.shallowElemType(mod), | |
| 3893 | ||
| 3894 | .array_u8, | |
| 3895 | .array_u8_sentinel_0, | |
| 3896 | .const_slice_u8, | |
| 3897 | .const_slice_u8_sentinel_0, | |
| 3898 | .manyptr_u8, | |
| 3899 | .manyptr_const_u8, | |
| 3900 | .manyptr_const_u8_sentinel_0, | |
| 3901 | => Type.u8, | |
| 3902 | ||
| 3903 | .single_const_pointer_to_comptime_int => Type.comptime_int, | |
| 3904 | .pointer => { | |
| 3905 | const info = ty.castTag(.pointer).?.data; | |
| 3906 | const child_ty = info.pointee_type; | |
| 3907 | if (info.size == .One) { | |
| 3908 | return child_ty.shallowElemType(mod); | |
| 3909 | } else { | |
| 3910 | return child_ty; | |
| 3911 | } | |
| 3912 | }, | |
| 3913 | .optional => ty.castTag(.optional).?.data.childType(), | |
| 3914 | .optional_single_mut_pointer => ty.castPointer().?.data, | |
| 3915 | .optional_single_const_pointer => ty.castPointer().?.data, | |
| 3183 | return switch (ty.ip_index) { | |
| 3184 | .none => switch (ty.tag()) { | |
| 3185 | .array => ty.castTag(.array).?.data.elem_type, | |
| 3186 | .array_sentinel => ty.castTag(.array_sentinel).?.data.elem_type, | |
| 3187 | ||
| 3188 | .pointer => { | |
| 3189 | const info = ty.castTag(.pointer).?.data; | |
| 3190 | const child_ty = info.pointee_type; | |
| 3191 | if (info.size == .One) { | |
| 3192 | return child_ty.shallowElemType(mod); | |
| 3193 | } else { | |
| 3194 | return child_ty; | |
| 3195 | } | |
| 3196 | }, | |
| 3197 | .optional => ty.castTag(.optional).?.data.childType(mod), | |
| 3916 | 3198 | |
| 3917 | .anyframe_T => ty.castTag(.anyframe_T).?.data, | |
| 3199 | .anyframe_T => ty.castTag(.anyframe_T).?.data, | |
| 3918 | 3200 | |
| 3919 | else => unreachable, | |
| 3201 | else => unreachable, | |
| 3202 | }, | |
| 3203 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 3204 | .ptr_type => |ptr_type| switch (ptr_type.size) { | |
| 3205 | .One => ptr_type.elem_type.toType().shallowElemType(mod), | |
| 3206 | .Many, .C, .Slice => ptr_type.elem_type.toType(), | |
| 3207 | }, | |
| 3208 | .vector_type => |vector_type| vector_type.child.toType(), | |
| 3209 | .array_type => |array_type| array_type.child.toType(), | |
| 3210 | .opt_type => |child| mod.intern_pool.childType(child).toType(), | |
| 3211 | else => unreachable, | |
| 3212 | }, | |
| 3920 | 3213 | }; |
| 3921 | 3214 | } |
| 3922 | 3215 | |
| 3923 | 3216 | fn shallowElemType(child_ty: Type, mod: *const Module) Type { |
| 3924 | 3217 | return switch (child_ty.zigTypeTag(mod)) { |
| 3925 | .Array, .Vector => child_ty.childType(), | |
| 3218 | .Array, .Vector => child_ty.childType(mod), | |
| 3926 | 3219 | else => child_ty, |
| 3927 | 3220 | }; |
| 3928 | 3221 | } |
| ... | ... | @@ -3930,7 +3223,7 @@ pub const Type = struct { |
| 3930 | 3223 | /// For vectors, returns the element type. Otherwise returns self. |
| 3931 | 3224 | pub fn scalarType(ty: Type, mod: *const Module) Type { |
| 3932 | 3225 | return switch (ty.zigTypeTag(mod)) { |
| 3933 | .Vector => ty.childType(), | |
| 3226 | .Vector => ty.childType(mod), | |
| 3934 | 3227 | else => ty, |
| 3935 | 3228 | }; |
| 3936 | 3229 | } |
| ... | ... | @@ -3938,51 +3231,25 @@ pub const Type = struct { |
| 3938 | 3231 | /// Asserts that the type is an optional. |
| 3939 | 3232 | /// Resulting `Type` will have inner memory referencing `buf`. |
| 3940 | 3233 | /// Note that for C pointers this returns the type unmodified. |
| 3941 | pub fn optionalChild(ty: Type, buf: *Payload.ElemType) Type { | |
| 3942 | return switch (ty.tag()) { | |
| 3943 | .optional => ty.castTag(.optional).?.data, | |
| 3944 | .optional_single_mut_pointer => { | |
| 3945 | buf.* = .{ | |
| 3946 | .base = .{ .tag = .single_mut_pointer }, | |
| 3947 | .data = ty.castPointer().?.data, | |
| 3948 | }; | |
| 3949 | return Type.initPayload(&buf.base); | |
| 3950 | }, | |
| 3951 | .optional_single_const_pointer => { | |
| 3952 | buf.* = .{ | |
| 3953 | .base = .{ .tag = .single_const_pointer }, | |
| 3954 | .data = ty.castPointer().?.data, | |
| 3955 | }; | |
| 3956 | return Type.initPayload(&buf.base); | |
| 3957 | }, | |
| 3234 | pub fn optionalChild(ty: Type, mod: *const Module) Type { | |
| 3235 | return switch (ty.ip_index) { | |
| 3236 | .none => switch (ty.tag()) { | |
| 3237 | .optional => ty.castTag(.optional).?.data, | |
| 3958 | 3238 | |
| 3959 | .pointer, // here we assume it is a C pointer | |
| 3960 | .c_const_pointer, | |
| 3961 | .c_mut_pointer, | |
| 3962 | => return ty, | |
| 3239 | .pointer, // here we assume it is a C pointer | |
| 3240 | => return ty, | |
| 3963 | 3241 | |
| 3964 | else => unreachable, | |
| 3965 | }; | |
| 3966 | } | |
| 3967 | ||
| 3968 | /// Asserts that the type is an optional. | |
| 3969 | /// Same as `optionalChild` but allocates the buffer if needed. | |
| 3970 | pub fn optionalChildAlloc(ty: Type, allocator: Allocator) !Type { | |
| 3971 | switch (ty.tag()) { | |
| 3972 | .optional => return ty.castTag(.optional).?.data, | |
| 3973 | .optional_single_mut_pointer => { | |
| 3974 | return Tag.single_mut_pointer.create(allocator, ty.castPointer().?.data); | |
| 3242 | else => unreachable, | |
| 3975 | 3243 | }, |
| 3976 | .optional_single_const_pointer => { | |
| 3977 | return Tag.single_const_pointer.create(allocator, ty.castPointer().?.data); | |
| 3244 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 3245 | .opt_type => |child| child.toType(), | |
| 3246 | .ptr_type => |ptr_type| b: { | |
| 3247 | assert(ptr_type.size == .C); | |
| 3248 | break :b ty; | |
| 3249 | }, | |
| 3250 | else => unreachable, | |
| 3978 | 3251 | }, |
| 3979 | .pointer, // here we assume it is a C pointer | |
| 3980 | .c_const_pointer, | |
| 3981 | .c_mut_pointer, | |
| 3982 | => return ty, | |
| 3983 | ||
| 3984 | else => unreachable, | |
| 3985 | } | |
| 3252 | }; | |
| 3986 | 3253 | } |
| 3987 | 3254 | |
| 3988 | 3255 | /// Returns the tag type of a union, if the type is a union and it has a tag type. |
| ... | ... | @@ -4071,19 +3338,25 @@ pub const Type = struct { |
| 4071 | 3338 | } |
| 4072 | 3339 | |
| 4073 | 3340 | /// Asserts that the type is an error union. |
| 4074 | pub fn errorUnionPayload(self: Type) Type { | |
| 4075 | return switch (self.tag()) { | |
| 4076 | .anyerror_void_error_union => Type.void, | |
| 4077 | .error_union => self.castTag(.error_union).?.data.payload, | |
| 4078 | else => unreachable, | |
| 3341 | pub fn errorUnionPayload(ty: Type) Type { | |
| 3342 | return switch (ty.ip_index) { | |
| 3343 | .anyerror_void_error_union_type => Type.void, | |
| 3344 | .none => switch (ty.tag()) { | |
| 3345 | .error_union => ty.castTag(.error_union).?.data.payload, | |
| 3346 | else => unreachable, | |
| 3347 | }, | |
| 3348 | else => @panic("TODO"), | |
| 4079 | 3349 | }; |
| 4080 | 3350 | } |
| 4081 | 3351 | |
| 4082 | pub fn errorUnionSet(self: Type) Type { | |
| 4083 | return switch (self.tag()) { | |
| 4084 | .anyerror_void_error_union => Type.anyerror, | |
| 4085 | .error_union => self.castTag(.error_union).?.data.error_set, | |
| 4086 | else => unreachable, | |
| 3352 | pub fn errorUnionSet(ty: Type) Type { | |
| 3353 | return switch (ty.ip_index) { | |
| 3354 | .anyerror_void_error_union_type => Type.anyerror, | |
| 3355 | .none => switch (ty.tag()) { | |
| 3356 | .error_union => ty.castTag(.error_union).?.data.error_set, | |
| 3357 | else => unreachable, | |
| 3358 | }, | |
| 3359 | else => @panic("TODO"), | |
| 4087 | 3360 | }; |
| 4088 | 3361 | } |
| 4089 | 3362 | |
| ... | ... | @@ -4168,67 +3441,73 @@ pub const Type = struct { |
| 4168 | 3441 | } |
| 4169 | 3442 | |
| 4170 | 3443 | /// Asserts the type is an array or vector or struct. |
| 4171 | pub fn arrayLen(ty: Type) u64 { | |
| 4172 | return switch (ty.tag()) { | |
| 4173 | .vector => ty.castTag(.vector).?.data.len, | |
| 4174 | .array => ty.castTag(.array).?.data.len, | |
| 4175 | .array_sentinel => ty.castTag(.array_sentinel).?.data.len, | |
| 4176 | .array_u8 => ty.castTag(.array_u8).?.data, | |
| 4177 | .array_u8_sentinel_0 => ty.castTag(.array_u8_sentinel_0).?.data, | |
| 4178 | .tuple => ty.castTag(.tuple).?.data.types.len, | |
| 4179 | .anon_struct => ty.castTag(.anon_struct).?.data.types.len, | |
| 4180 | .@"struct" => ty.castTag(.@"struct").?.data.fields.count(), | |
| 4181 | .empty_struct, .empty_struct_literal => 0, | |
| 3444 | pub fn arrayLen(ty: Type, mod: *const Module) u64 { | |
| 3445 | return arrayLenIp(ty, mod.intern_pool); | |
| 3446 | } | |
| 4182 | 3447 | |
| 4183 | else => unreachable, | |
| 3448 | pub fn arrayLenIp(ty: Type, ip: InternPool) u64 { | |
| 3449 | return switch (ty.ip_index) { | |
| 3450 | .none => switch (ty.tag()) { | |
| 3451 | .array => ty.castTag(.array).?.data.len, | |
| 3452 | .array_sentinel => ty.castTag(.array_sentinel).?.data.len, | |
| 3453 | .tuple => ty.castTag(.tuple).?.data.types.len, | |
| 3454 | .anon_struct => ty.castTag(.anon_struct).?.data.types.len, | |
| 3455 | .@"struct" => ty.castTag(.@"struct").?.data.fields.count(), | |
| 3456 | .empty_struct, .empty_struct_literal => 0, | |
| 3457 | ||
| 3458 | else => unreachable, | |
| 3459 | }, | |
| 3460 | else => switch (ip.indexToKey(ty.ip_index)) { | |
| 3461 | .vector_type => |vector_type| vector_type.len, | |
| 3462 | .array_type => |array_type| array_type.len, | |
| 3463 | else => unreachable, | |
| 3464 | }, | |
| 4184 | 3465 | }; |
| 4185 | 3466 | } |
| 4186 | 3467 | |
| 4187 | pub fn arrayLenIncludingSentinel(ty: Type) u64 { | |
| 4188 | return ty.arrayLen() + @boolToInt(ty.sentinel() != null); | |
| 3468 | pub fn arrayLenIncludingSentinel(ty: Type, mod: *const Module) u64 { | |
| 3469 | return ty.arrayLen(mod) + @boolToInt(ty.sentinel(mod) != null); | |
| 4189 | 3470 | } |
| 4190 | 3471 | |
| 4191 | pub fn vectorLen(ty: Type) u32 { | |
| 4192 | return switch (ty.tag()) { | |
| 4193 | .vector => @intCast(u32, ty.castTag(.vector).?.data.len), | |
| 4194 | .tuple => @intCast(u32, ty.castTag(.tuple).?.data.types.len), | |
| 4195 | .anon_struct => @intCast(u32, ty.castTag(.anon_struct).?.data.types.len), | |
| 4196 | else => unreachable, | |
| 3472 | pub fn vectorLen(ty: Type, mod: *const Module) u32 { | |
| 3473 | return switch (ty.ip_index) { | |
| 3474 | .none => switch (ty.tag()) { | |
| 3475 | .tuple => @intCast(u32, ty.castTag(.tuple).?.data.types.len), | |
| 3476 | .anon_struct => @intCast(u32, ty.castTag(.anon_struct).?.data.types.len), | |
| 3477 | else => unreachable, | |
| 3478 | }, | |
| 3479 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 3480 | .vector_type => |vector_type| vector_type.len, | |
| 3481 | else => unreachable, | |
| 3482 | }, | |
| 4197 | 3483 | }; |
| 4198 | 3484 | } |
| 4199 | 3485 | |
| 4200 | 3486 | /// Asserts the type is an array, pointer or vector. |
| 4201 | pub fn sentinel(self: Type) ?Value { | |
| 4202 | return switch (self.tag()) { | |
| 4203 | .single_const_pointer, | |
| 4204 | .single_mut_pointer, | |
| 4205 | .many_const_pointer, | |
| 4206 | .many_mut_pointer, | |
| 4207 | .c_const_pointer, | |
| 4208 | .c_mut_pointer, | |
| 4209 | .single_const_pointer_to_comptime_int, | |
| 4210 | .vector, | |
| 4211 | .array, | |
| 4212 | .array_u8, | |
| 4213 | .manyptr_u8, | |
| 4214 | .manyptr_const_u8, | |
| 4215 | .const_slice_u8, | |
| 4216 | .const_slice, | |
| 4217 | .mut_slice, | |
| 4218 | .tuple, | |
| 4219 | .empty_struct_literal, | |
| 4220 | .@"struct", | |
| 4221 | => return null, | |
| 3487 | pub fn sentinel(ty: Type, mod: *const Module) ?Value { | |
| 3488 | return switch (ty.ip_index) { | |
| 3489 | .none => switch (ty.tag()) { | |
| 3490 | .array, | |
| 3491 | .tuple, | |
| 3492 | .empty_struct_literal, | |
| 3493 | .@"struct", | |
| 3494 | => null, | |
| 4222 | 3495 | |
| 4223 | .pointer => return self.castTag(.pointer).?.data.sentinel, | |
| 4224 | .array_sentinel => return self.castTag(.array_sentinel).?.data.sentinel, | |
| 3496 | .pointer => ty.castTag(.pointer).?.data.sentinel, | |
| 3497 | .array_sentinel => ty.castTag(.array_sentinel).?.data.sentinel, | |
| 4225 | 3498 | |
| 4226 | .array_u8_sentinel_0, | |
| 4227 | .const_slice_u8_sentinel_0, | |
| 4228 | .manyptr_const_u8_sentinel_0, | |
| 4229 | => return Value.zero, | |
| 3499 | else => unreachable, | |
| 3500 | }, | |
| 3501 | else => switch (mod.intern_pool.indexToKey(ty.ip_index)) { | |
| 3502 | .vector_type, | |
| 3503 | .struct_type, | |
| 3504 | => null, | |
| 4230 | 3505 | |
| 4231 | else => unreachable, | |
| 3506 | .array_type => |t| if (t.sentinel != .none) t.sentinel.toValue() else null, | |
| 3507 | .ptr_type => |t| if (t.sentinel != .none) t.sentinel.toValue() else null, | |
| 3508 | ||
| 3509 | else => unreachable, | |
| 3510 | }, | |
| 4232 | 3511 | }; |
| 4233 | 3512 | } |
| 4234 | 3513 | |
| ... | ... | @@ -4292,8 +3571,6 @@ pub const Type = struct { |
| 4292 | 3571 | return .{ .signedness = .unsigned, .bits = 16 }; |
| 4293 | 3572 | }, |
| 4294 | 3573 | |
| 4295 | .vector => ty = ty.castTag(.vector).?.data.elem_type, | |
| 4296 | ||
| 4297 | 3574 | .@"struct" => { |
| 4298 | 3575 | const struct_obj = ty.castTag(.@"struct").?.data; |
| 4299 | 3576 | assert(struct_obj.layout == .Packed); |
| ... | ... | @@ -4321,8 +3598,9 @@ pub const Type = struct { |
| 4321 | 3598 | .int_type => |int_type| return int_type, |
| 4322 | 3599 | .ptr_type => unreachable, |
| 4323 | 3600 | .array_type => unreachable, |
| 4324 | .vector_type => @panic("TODO"), | |
| 4325 | .optional_type => unreachable, | |
| 3601 | .vector_type => |vector_type| ty = vector_type.child.toType(), | |
| 3602 | ||
| 3603 | .opt_type => unreachable, | |
| 4326 | 3604 | .error_union_type => unreachable, |
| 4327 | 3605 | .simple_type => unreachable, // handled via Index enum tag above |
| 4328 | 3606 | .struct_type => @panic("TODO"), |
| ... | ... | @@ -4426,7 +3704,11 @@ pub const Type = struct { |
| 4426 | 3704 | |
| 4427 | 3705 | /// Asserts the type is a function or a function pointer. |
| 4428 | 3706 | pub fn fnReturnType(ty: Type) Type { |
| 4429 | const fn_ty = if (ty.castPointer()) |p| p.data else ty; | |
| 3707 | const fn_ty = switch (ty.tag()) { | |
| 3708 | .pointer => ty.castTag(.pointer).?.data.pointee_type, | |
| 3709 | .function => ty, | |
| 3710 | else => unreachable, | |
| 3711 | }; | |
| 4430 | 3712 | return fn_ty.castTag(.function).?.data.return_type; |
| 4431 | 3713 | } |
| 4432 | 3714 | |
| ... | ... | @@ -4516,8 +3798,12 @@ pub const Type = struct { |
| 4516 | 3798 | }, |
| 4517 | 3799 | .ptr_type => @panic("TODO"), |
| 4518 | 3800 | .array_type => @panic("TODO"), |
| 4519 | .vector_type => @panic("TODO"), | |
| 4520 | .optional_type => @panic("TODO"), | |
| 3801 | .vector_type => |vector_type| { | |
| 3802 | if (vector_type.len == 0) return Value.initTag(.empty_array); | |
| 3803 | if (vector_type.child.toType().onePossibleValue(mod)) |v| return v; | |
| 3804 | return null; | |
| 3805 | }, | |
| 3806 | .opt_type => @panic("TODO"), | |
| 4521 | 3807 | .error_union_type => @panic("TODO"), |
| 4522 | 3808 | .simple_type => |t| switch (t) { |
| 4523 | 3809 | .f16, |
| ... | ... | @@ -4580,34 +3866,15 @@ pub const Type = struct { |
| 4580 | 3866 | .error_set, |
| 4581 | 3867 | .error_set_merged, |
| 4582 | 3868 | .function, |
| 4583 | .single_const_pointer_to_comptime_int, | |
| 4584 | 3869 | .array_sentinel, |
| 4585 | .array_u8_sentinel_0, | |
| 4586 | .const_slice_u8, | |
| 4587 | .const_slice_u8_sentinel_0, | |
| 4588 | .const_slice, | |
| 4589 | .mut_slice, | |
| 4590 | .optional_single_mut_pointer, | |
| 4591 | .optional_single_const_pointer, | |
| 4592 | .anyerror_void_error_union, | |
| 4593 | 3870 | .error_set_inferred, |
| 4594 | 3871 | .@"opaque", |
| 4595 | .manyptr_u8, | |
| 4596 | .manyptr_const_u8, | |
| 4597 | .manyptr_const_u8_sentinel_0, | |
| 4598 | 3872 | .anyframe_T, |
| 4599 | .many_const_pointer, | |
| 4600 | .many_mut_pointer, | |
| 4601 | .c_const_pointer, | |
| 4602 | .c_mut_pointer, | |
| 4603 | .single_const_pointer, | |
| 4604 | .single_mut_pointer, | |
| 4605 | 3873 | .pointer, |
| 4606 | 3874 | => return null, |
| 4607 | 3875 | |
| 4608 | 3876 | .optional => { |
| 4609 | var buf: Payload.ElemType = undefined; | |
| 4610 | const child_ty = ty.optionalChild(&buf); | |
| 3877 | const child_ty = ty.optionalChild(mod); | |
| 4611 | 3878 | if (child_ty.isNoReturn()) { |
| 4612 | 3879 | return Value.null; |
| 4613 | 3880 | } else { |
| ... | ... | @@ -4690,10 +3957,10 @@ pub const Type = struct { |
| 4690 | 3957 | |
| 4691 | 3958 | .empty_struct, .empty_struct_literal => return Value.initTag(.empty_struct_value), |
| 4692 | 3959 | |
| 4693 | .vector, .array, .array_u8 => { | |
| 4694 | if (ty.arrayLen() == 0) | |
| 3960 | .array => { | |
| 3961 | if (ty.arrayLen(mod) == 0) | |
| 4695 | 3962 | return Value.initTag(.empty_array); |
| 4696 | if (ty.elemType().onePossibleValue(mod) != null) | |
| 3963 | if (ty.childType(mod).onePossibleValue(mod) != null) | |
| 4697 | 3964 | return Value.initTag(.the_only_possible_value); |
| 4698 | 3965 | return null; |
| 4699 | 3966 | }, |
| ... | ... | @@ -4711,9 +3978,9 @@ pub const Type = struct { |
| 4711 | 3978 | if (ty.ip_index != .none) return switch (mod.intern_pool.indexToKey(ty.ip_index)) { |
| 4712 | 3979 | .int_type => false, |
| 4713 | 3980 | .ptr_type => @panic("TODO"), |
| 4714 | .array_type => @panic("TODO"), | |
| 4715 | .vector_type => @panic("TODO"), | |
| 4716 | .optional_type => @panic("TODO"), | |
| 3981 | .array_type => |array_type| return array_type.child.toType().comptimeOnly(mod), | |
| 3982 | .vector_type => |vector_type| return vector_type.child.toType().comptimeOnly(mod), | |
| 3983 | .opt_type => @panic("TODO"), | |
| 4717 | 3984 | .error_union_type => @panic("TODO"), |
| 4718 | 3985 | .simple_type => |t| switch (t) { |
| 4719 | 3986 | .f16, |
| ... | ... | @@ -4772,12 +4039,6 @@ pub const Type = struct { |
| 4772 | 4039 | }; |
| 4773 | 4040 | |
| 4774 | 4041 | return switch (ty.tag()) { |
| 4775 | .manyptr_u8, | |
| 4776 | .manyptr_const_u8, | |
| 4777 | .manyptr_const_u8_sentinel_0, | |
| 4778 | .const_slice_u8, | |
| 4779 | .const_slice_u8_sentinel_0, | |
| 4780 | .anyerror_void_error_union, | |
| 4781 | 4042 | .empty_struct_literal, |
| 4782 | 4043 | .empty_struct, |
| 4783 | 4044 | .error_set, |
| ... | ... | @@ -4785,35 +4046,21 @@ pub const Type = struct { |
| 4785 | 4046 | .error_set_inferred, |
| 4786 | 4047 | .error_set_merged, |
| 4787 | 4048 | .@"opaque", |
| 4788 | .array_u8, | |
| 4789 | .array_u8_sentinel_0, | |
| 4790 | 4049 | .enum_simple, |
| 4791 | 4050 | => false, |
| 4792 | 4051 | |
| 4793 | .single_const_pointer_to_comptime_int, | |
| 4794 | 4052 | // These are function bodies, not function pointers. |
| 4795 | .function, | |
| 4796 | => true, | |
| 4053 | .function => true, | |
| 4797 | 4054 | |
| 4798 | 4055 | .inferred_alloc_mut => unreachable, |
| 4799 | 4056 | .inferred_alloc_const => unreachable, |
| 4800 | 4057 | |
| 4801 | 4058 | .array, |
| 4802 | 4059 | .array_sentinel, |
| 4803 | .vector, | |
| 4804 | => return ty.childType().comptimeOnly(mod), | |
| 4060 | => return ty.childType(mod).comptimeOnly(mod), | |
| 4805 | 4061 | |
| 4806 | .pointer, | |
| 4807 | .single_const_pointer, | |
| 4808 | .single_mut_pointer, | |
| 4809 | .many_const_pointer, | |
| 4810 | .many_mut_pointer, | |
| 4811 | .c_const_pointer, | |
| 4812 | .c_mut_pointer, | |
| 4813 | .const_slice, | |
| 4814 | .mut_slice, | |
| 4815 | => { | |
| 4816 | const child_ty = ty.childType(); | |
| 4062 | .pointer => { | |
| 4063 | const child_ty = ty.childType(mod); | |
| 4817 | 4064 | if (child_ty.zigTypeTag(mod) == .Fn) { |
| 4818 | 4065 | return false; |
| 4819 | 4066 | } else { |
| ... | ... | @@ -4821,12 +4068,8 @@ pub const Type = struct { |
| 4821 | 4068 | } |
| 4822 | 4069 | }, |
| 4823 | 4070 | |
| 4824 | .optional, | |
| 4825 | .optional_single_mut_pointer, | |
| 4826 | .optional_single_const_pointer, | |
| 4827 | => { | |
| 4828 | var buf: Type.Payload.ElemType = undefined; | |
| 4829 | return ty.optionalChild(&buf).comptimeOnly(mod); | |
| 4071 | .optional => { | |
| 4072 | return ty.optionalChild(mod).comptimeOnly(mod); | |
| 4830 | 4073 | }, |
| 4831 | 4074 | |
| 4832 | 4075 | .tuple, .anon_struct => { |
| ... | ... | @@ -4882,6 +4125,10 @@ pub const Type = struct { |
| 4882 | 4125 | }; |
| 4883 | 4126 | } |
| 4884 | 4127 | |
| 4128 | pub fn isVector(ty: Type, mod: *const Module) bool { | |
| 4129 | return ty.zigTypeTag(mod) == .Vector; | |
| 4130 | } | |
| 4131 | ||
| 4885 | 4132 | pub fn isArrayOrVector(ty: Type, mod: *const Module) bool { |
| 4886 | 4133 | return switch (ty.zigTypeTag(mod)) { |
| 4887 | 4134 | .Array, .Vector => true, |
| ... | ... | @@ -4892,9 +4139,9 @@ pub const Type = struct { |
| 4892 | 4139 | pub fn isIndexable(ty: Type, mod: *const Module) bool { |
| 4893 | 4140 | return switch (ty.zigTypeTag(mod)) { |
| 4894 | 4141 | .Array, .Vector => true, |
| 4895 | .Pointer => switch (ty.ptrSize()) { | |
| 4142 | .Pointer => switch (ty.ptrSize(mod)) { | |
| 4896 | 4143 | .Slice, .Many, .C => true, |
| 4897 | .One => ty.elemType().zigTypeTag(mod) == .Array, | |
| 4144 | .One => ty.childType(mod).zigTypeTag(mod) == .Array, | |
| 4898 | 4145 | }, |
| 4899 | 4146 | .Struct => ty.isTuple(), |
| 4900 | 4147 | else => false, |
| ... | ... | @@ -4904,10 +4151,10 @@ pub const Type = struct { |
| 4904 | 4151 | pub fn indexableHasLen(ty: Type, mod: *const Module) bool { |
| 4905 | 4152 | return switch (ty.zigTypeTag(mod)) { |
| 4906 | 4153 | .Array, .Vector => true, |
| 4907 | .Pointer => switch (ty.ptrSize()) { | |
| 4154 | .Pointer => switch (ty.ptrSize(mod)) { | |
| 4908 | 4155 | .Many, .C => false, |
| 4909 | 4156 | .Slice => true, |
| 4910 | .One => ty.elemType().zigTypeTag(mod) == .Array, | |
| 4157 | .One => ty.childType(mod).zigTypeTag(mod) == .Array, | |
| 4911 | 4158 | }, |
| 4912 | 4159 | .Struct => ty.isTuple(), |
| 4913 | 4160 | else => false, |
| ... | ... | @@ -5527,14 +4774,6 @@ pub const Type = struct { |
| 5527 | 4774 | /// with different enum tags, because the the former requires more payload data than the latter. |
| 5528 | 4775 | /// See `zigTypeTag` for the function that corresponds to `std.builtin.TypeId`. |
| 5529 | 4776 | pub const Tag = enum(usize) { |
| 5530 | // The first section of this enum are tags that require no payload. | |
| 5531 | manyptr_u8, | |
| 5532 | manyptr_const_u8, | |
| 5533 | manyptr_const_u8_sentinel_0, | |
| 5534 | single_const_pointer_to_comptime_int, | |
| 5535 | const_slice_u8, | |
| 5536 | const_slice_u8_sentinel_0, | |
| 5537 | anyerror_void_error_union, | |
| 5538 | 4777 | /// Same as `empty_struct` except it has an empty namespace. |
| 5539 | 4778 | empty_struct_literal, |
| 5540 | 4779 | /// This is a special value that tracks a set of types that have been stored |
| ... | ... | @@ -5545,28 +4784,15 @@ pub const Type = struct { |
| 5545 | 4784 | inferred_alloc_const, // See last_no_payload_tag below. |
| 5546 | 4785 | // After this, the tag requires a payload. |
| 5547 | 4786 | |
| 5548 | array_u8, | |
| 5549 | array_u8_sentinel_0, | |
| 5550 | 4787 | array, |
| 5551 | 4788 | array_sentinel, |
| 5552 | vector, | |
| 5553 | 4789 | /// Possible Value tags for this: @"struct" |
| 5554 | 4790 | tuple, |
| 5555 | 4791 | /// Possible Value tags for this: @"struct" |
| 5556 | 4792 | anon_struct, |
| 5557 | 4793 | pointer, |
| 5558 | single_const_pointer, | |
| 5559 | single_mut_pointer, | |
| 5560 | many_const_pointer, | |
| 5561 | many_mut_pointer, | |
| 5562 | c_const_pointer, | |
| 5563 | c_mut_pointer, | |
| 5564 | const_slice, | |
| 5565 | mut_slice, | |
| 5566 | 4794 | function, |
| 5567 | 4795 | optional, |
| 5568 | optional_single_mut_pointer, | |
| 5569 | optional_single_const_pointer, | |
| 5570 | 4796 | error_union, |
| 5571 | 4797 | anyframe_T, |
| 5572 | 4798 | error_set, |
| ... | ... | @@ -5590,33 +4816,12 @@ pub const Type = struct { |
| 5590 | 4816 | |
| 5591 | 4817 | pub fn Type(comptime t: Tag) type { |
| 5592 | 4818 | return switch (t) { |
| 5593 | .single_const_pointer_to_comptime_int, | |
| 5594 | .anyerror_void_error_union, | |
| 5595 | .const_slice_u8, | |
| 5596 | .const_slice_u8_sentinel_0, | |
| 5597 | 4819 | .inferred_alloc_const, |
| 5598 | 4820 | .inferred_alloc_mut, |
| 5599 | 4821 | .empty_struct_literal, |
| 5600 | .manyptr_u8, | |
| 5601 | .manyptr_const_u8, | |
| 5602 | .manyptr_const_u8_sentinel_0, | |
| 5603 | 4822 | => @compileError("Type Tag " ++ @tagName(t) ++ " has no payload"), |
| 5604 | 4823 | |
| 5605 | .array_u8, | |
| 5606 | .array_u8_sentinel_0, | |
| 5607 | => Payload.Len, | |
| 5608 | ||
| 5609 | .single_const_pointer, | |
| 5610 | .single_mut_pointer, | |
| 5611 | .many_const_pointer, | |
| 5612 | .many_mut_pointer, | |
| 5613 | .c_const_pointer, | |
| 5614 | .c_mut_pointer, | |
| 5615 | .const_slice, | |
| 5616 | .mut_slice, | |
| 5617 | 4824 | .optional, |
| 5618 | .optional_single_mut_pointer, | |
| 5619 | .optional_single_const_pointer, | |
| 5620 | 4825 | .anyframe_T, |
| 5621 | 4826 | => Payload.ElemType, |
| 5622 | 4827 | |
| ... | ... | @@ -5624,7 +4829,7 @@ pub const Type = struct { |
| 5624 | 4829 | .error_set_inferred => Payload.ErrorSetInferred, |
| 5625 | 4830 | .error_set_merged => Payload.ErrorSetMerged, |
| 5626 | 4831 | |
| 5627 | .array, .vector => Payload.Array, | |
| 4832 | .array => Payload.Array, | |
| 5628 | 4833 | .array_sentinel => Payload.ArraySentinel, |
| 5629 | 4834 | .pointer => Payload.Pointer, |
| 5630 | 4835 | .function => Payload.Function, |
| ... | ... | @@ -5847,15 +5052,28 @@ pub const Type = struct { |
| 5847 | 5052 | @"volatile": bool = false, |
| 5848 | 5053 | size: std.builtin.Type.Pointer.Size = .One, |
| 5849 | 5054 | |
| 5850 | pub const VectorIndex = enum(u32) { | |
| 5851 | none = std.math.maxInt(u32), | |
| 5852 | runtime = std.math.maxInt(u32) - 1, | |
| 5853 | _, | |
| 5854 | }; | |
| 5055 | pub const VectorIndex = InternPool.Key.PtrType.VectorIndex; | |
| 5056 | ||
| 5855 | 5057 | pub fn alignment(data: Data, mod: *const Module) u32 { |
| 5856 | 5058 | if (data.@"align" != 0) return data.@"align"; |
| 5857 | 5059 | return abiAlignment(data.pointee_type, mod); |
| 5858 | 5060 | } |
| 5061 | ||
| 5062 | pub fn fromKey(p: InternPool.Key.PtrType) Data { | |
| 5063 | return .{ | |
| 5064 | .pointee_type = p.elem_type.toType(), | |
| 5065 | .sentinel = if (p.sentinel != .none) p.sentinel.toValue() else null, | |
| 5066 | .@"align" = p.alignment, | |
| 5067 | .@"addrspace" = p.address_space, | |
| 5068 | .bit_offset = p.bit_offset, | |
| 5069 | .host_size = p.host_size, | |
| 5070 | .vector_index = p.vector_index, | |
| 5071 | .@"allowzero" = p.is_allowzero, | |
| 5072 | .mutable = !p.is_const, | |
| 5073 | .@"volatile" = p.is_volatile, | |
| 5074 | .size = p.size, | |
| 5075 | }; | |
| 5076 | } | |
| 5859 | 5077 | }; |
| 5860 | 5078 | }; |
| 5861 | 5079 | |
| ... | ... | @@ -5986,6 +5204,17 @@ pub const Type = struct { |
| 5986 | 5204 | pub const @"c_ulonglong": Type = .{ .ip_index = .c_ulonglong_type, .legacy = undefined }; |
| 5987 | 5205 | pub const @"c_longdouble": Type = .{ .ip_index = .c_longdouble_type, .legacy = undefined }; |
| 5988 | 5206 | |
| 5207 | pub const const_slice_u8: Type = .{ .ip_index = .const_slice_u8_type, .legacy = undefined }; | |
| 5208 | pub const manyptr_u8: Type = .{ .ip_index = .manyptr_u8_type, .legacy = undefined }; | |
| 5209 | pub const single_const_pointer_to_comptime_int: Type = .{ | |
| 5210 | .ip_index = .single_const_pointer_to_comptime_int_type, | |
| 5211 | .legacy = undefined, | |
| 5212 | }; | |
| 5213 | pub const const_slice_u8_sentinel_0: Type = .{ | |
| 5214 | .ip_index = .const_slice_u8_sentinel_0_type, | |
| 5215 | .legacy = undefined, | |
| 5216 | }; | |
| 5217 | ||
| 5989 | 5218 | pub const generic_poison: Type = .{ .ip_index = .generic_poison_type, .legacy = undefined }; |
| 5990 | 5219 | |
| 5991 | 5220 | pub const err_int = Type.u16; |
| ... | ... | @@ -6019,50 +5248,6 @@ pub const Type = struct { |
| 6019 | 5248 | } |
| 6020 | 5249 | } |
| 6021 | 5250 | |
| 6022 | if (d.@"align" == 0 and d.@"addrspace" == .generic and | |
| 6023 | d.bit_offset == 0 and d.host_size == 0 and d.vector_index == .none and | |
| 6024 | !d.@"allowzero" and !d.@"volatile") | |
| 6025 | { | |
| 6026 | if (d.sentinel) |sent| { | |
| 6027 | if (!d.mutable and d.pointee_type.eql(Type.u8, mod)) { | |
| 6028 | switch (d.size) { | |
| 6029 | .Slice => { | |
| 6030 | if (sent.compareAllWithZero(.eq, mod)) { | |
| 6031 | return Type.initTag(.const_slice_u8_sentinel_0); | |
| 6032 | } | |
| 6033 | }, | |
| 6034 | .Many => { | |
| 6035 | if (sent.compareAllWithZero(.eq, mod)) { | |
| 6036 | return Type.initTag(.manyptr_const_u8_sentinel_0); | |
| 6037 | } | |
| 6038 | }, | |
| 6039 | else => {}, | |
| 6040 | } | |
| 6041 | } | |
| 6042 | } else if (!d.mutable and d.pointee_type.eql(Type.u8, mod)) { | |
| 6043 | switch (d.size) { | |
| 6044 | .Slice => return Type.initTag(.const_slice_u8), | |
| 6045 | .Many => return Type.initTag(.manyptr_const_u8), | |
| 6046 | else => {}, | |
| 6047 | } | |
| 6048 | } else { | |
| 6049 | const T = Type.Tag; | |
| 6050 | const type_payload = try arena.create(Type.Payload.ElemType); | |
| 6051 | type_payload.* = .{ | |
| 6052 | .base = .{ | |
| 6053 | .tag = switch (d.size) { | |
| 6054 | .One => if (d.mutable) T.single_mut_pointer else T.single_const_pointer, | |
| 6055 | .Many => if (d.mutable) T.many_mut_pointer else T.many_const_pointer, | |
| 6056 | .C => if (d.mutable) T.c_mut_pointer else T.c_const_pointer, | |
| 6057 | .Slice => if (d.mutable) T.mut_slice else T.const_slice, | |
| 6058 | }, | |
| 6059 | }, | |
| 6060 | .data = d.pointee_type, | |
| 6061 | }; | |
| 6062 | return Type.initPayload(&type_payload.base); | |
| 6063 | } | |
| 6064 | } | |
| 6065 | ||
| 6066 | 5251 | return Type.Tag.pointer.create(arena, d); |
| 6067 | 5252 | } |
| 6068 | 5253 | |
| ... | ... | @@ -6073,13 +5258,21 @@ pub const Type = struct { |
| 6073 | 5258 | elem_type: Type, |
| 6074 | 5259 | mod: *Module, |
| 6075 | 5260 | ) Allocator.Error!Type { |
| 6076 | if (elem_type.eql(Type.u8, mod)) { | |
| 6077 | if (sent) |some| { | |
| 6078 | if (some.eql(Value.zero, elem_type, mod)) { | |
| 6079 | return Tag.array_u8_sentinel_0.create(arena, len); | |
| 5261 | if (elem_type.ip_index != .none) { | |
| 5262 | if (sent) |s| { | |
| 5263 | if (s.ip_index != .none) { | |
| 5264 | return mod.arrayType(.{ | |
| 5265 | .len = len, | |
| 5266 | .child = elem_type.ip_index, | |
| 5267 | .sentinel = s.ip_index, | |
| 5268 | }); | |
| 6080 | 5269 | } |
| 6081 | 5270 | } else { |
| 6082 | return Tag.array_u8.create(arena, len); | |
| 5271 | return mod.arrayType(.{ | |
| 5272 | .len = len, | |
| 5273 | .child = elem_type.ip_index, | |
| 5274 | .sentinel = .none, | |
| 5275 | }); | |
| 6083 | 5276 | } |
| 6084 | 5277 | } |
| 6085 | 5278 | |
| ... | ... | @@ -6097,24 +5290,11 @@ pub const Type = struct { |
| 6097 | 5290 | }); |
| 6098 | 5291 | } |
| 6099 | 5292 | |
| 6100 | pub fn vector(arena: Allocator, len: u64, elem_type: Type) Allocator.Error!Type { | |
| 6101 | return Tag.vector.create(arena, .{ | |
| 6102 | .len = len, | |
| 6103 | .elem_type = elem_type, | |
| 6104 | }); | |
| 6105 | } | |
| 6106 | ||
| 6107 | pub fn optional(arena: Allocator, child_type: Type) Allocator.Error!Type { | |
| 6108 | switch (child_type.tag()) { | |
| 6109 | .single_const_pointer => return Type.Tag.optional_single_const_pointer.create( | |
| 6110 | arena, | |
| 6111 | child_type.elemType(), | |
| 6112 | ), | |
| 6113 | .single_mut_pointer => return Type.Tag.optional_single_mut_pointer.create( | |
| 6114 | arena, | |
| 6115 | child_type.elemType(), | |
| 6116 | ), | |
| 6117 | else => return Type.Tag.optional.create(arena, child_type), | |
| 5293 | pub fn optional(arena: Allocator, child_type: Type, mod: *Module) Allocator.Error!Type { | |
| 5294 | if (child_type.ip_index != .none) { | |
| 5295 | return mod.optionalType(child_type.ip_index); | |
| 5296 | } else { | |
| 5297 | return Type.Tag.optional.create(arena, child_type); | |
| 6118 | 5298 | } |
| 6119 | 5299 | } |
| 6120 | 5300 | |
| ... | ... | @@ -6125,12 +5305,6 @@ pub const Type = struct { |
| 6125 | 5305 | mod: *Module, |
| 6126 | 5306 | ) Allocator.Error!Type { |
| 6127 | 5307 | assert(error_set.zigTypeTag(mod) == .ErrorSet); |
| 6128 | if (error_set.eql(Type.anyerror, mod) and | |
| 6129 | payload.eql(Type.void, mod)) | |
| 6130 | { | |
| 6131 | return Type.initTag(.anyerror_void_error_union); | |
| 6132 | } | |
| 6133 | ||
| 6134 | 5308 | return Type.Tag.error_union.create(arena, .{ |
| 6135 | 5309 | .error_set = error_set, |
| 6136 | 5310 | .payload = payload, |
src/value.zig+80-128| ... | ... | @@ -33,14 +33,6 @@ pub const Value = struct { |
| 33 | 33 | // Keep in sync with tools/stage2_pretty_printers_common.py |
| 34 | 34 | pub const Tag = enum(usize) { |
| 35 | 35 | // The first section of this enum are tags that require no payload. |
| 36 | manyptr_u8_type, | |
| 37 | manyptr_const_u8_type, | |
| 38 | manyptr_const_u8_sentinel_0_type, | |
| 39 | single_const_pointer_to_comptime_int_type, | |
| 40 | const_slice_u8_type, | |
| 41 | const_slice_u8_sentinel_0_type, | |
| 42 | anyerror_void_error_union_type, | |
| 43 | ||
| 44 | 36 | undef, |
| 45 | 37 | zero, |
| 46 | 38 | one, |
| ... | ... | @@ -140,11 +132,6 @@ pub const Value = struct { |
| 140 | 132 | |
| 141 | 133 | pub fn Type(comptime t: Tag) type { |
| 142 | 134 | return switch (t) { |
| 143 | .single_const_pointer_to_comptime_int_type, | |
| 144 | .const_slice_u8_type, | |
| 145 | .const_slice_u8_sentinel_0_type, | |
| 146 | .anyerror_void_error_union_type, | |
| 147 | ||
| 148 | 135 | .undef, |
| 149 | 136 | .zero, |
| 150 | 137 | .one, |
| ... | ... | @@ -153,9 +140,6 @@ pub const Value = struct { |
| 153 | 140 | .empty_struct_value, |
| 154 | 141 | .empty_array, |
| 155 | 142 | .null_value, |
| 156 | .manyptr_u8_type, | |
| 157 | .manyptr_const_u8_type, | |
| 158 | .manyptr_const_u8_sentinel_0_type, | |
| 159 | 143 | => @compileError("Value Tag " ++ @tagName(t) ++ " has no payload"), |
| 160 | 144 | |
| 161 | 145 | .int_big_positive, |
| ... | ... | @@ -280,9 +264,7 @@ pub const Value = struct { |
| 280 | 264 | } |
| 281 | 265 | |
| 282 | 266 | pub fn castTag(self: Value, comptime t: Tag) ?*t.Type() { |
| 283 | if (self.ip_index != .none) { | |
| 284 | return null; | |
| 285 | } | |
| 267 | assert(self.ip_index == .none); | |
| 286 | 268 | |
| 287 | 269 | if (@enumToInt(self.legacy.tag_if_small_enough) < Tag.no_payload_count) |
| 288 | 270 | return null; |
| ... | ... | @@ -305,11 +287,6 @@ pub const Value = struct { |
| 305 | 287 | .legacy = .{ .tag_if_small_enough = self.legacy.tag_if_small_enough }, |
| 306 | 288 | }; |
| 307 | 289 | } else switch (self.legacy.ptr_otherwise.tag) { |
| 308 | .single_const_pointer_to_comptime_int_type, | |
| 309 | .const_slice_u8_type, | |
| 310 | .const_slice_u8_sentinel_0_type, | |
| 311 | .anyerror_void_error_union_type, | |
| 312 | ||
| 313 | 290 | .undef, |
| 314 | 291 | .zero, |
| 315 | 292 | .one, |
| ... | ... | @@ -318,9 +295,6 @@ pub const Value = struct { |
| 318 | 295 | .empty_array, |
| 319 | 296 | .null_value, |
| 320 | 297 | .empty_struct_value, |
| 321 | .manyptr_u8_type, | |
| 322 | .manyptr_const_u8_type, | |
| 323 | .manyptr_const_u8_sentinel_0_type, | |
| 324 | 298 | => unreachable, |
| 325 | 299 | |
| 326 | 300 | .ty, .lazy_align, .lazy_size => { |
| ... | ... | @@ -553,14 +527,6 @@ pub const Value = struct { |
| 553 | 527 | } |
| 554 | 528 | var val = start_val; |
| 555 | 529 | while (true) switch (val.tag()) { |
| 556 | .single_const_pointer_to_comptime_int_type => return out_stream.writeAll("*const comptime_int"), | |
| 557 | .const_slice_u8_type => return out_stream.writeAll("[]const u8"), | |
| 558 | .const_slice_u8_sentinel_0_type => return out_stream.writeAll("[:0]const u8"), | |
| 559 | .anyerror_void_error_union_type => return out_stream.writeAll("anyerror!void"), | |
| 560 | .manyptr_u8_type => return out_stream.writeAll("[*]u8"), | |
| 561 | .manyptr_const_u8_type => return out_stream.writeAll("[*]const u8"), | |
| 562 | .manyptr_const_u8_sentinel_0_type => return out_stream.writeAll("[*:0]const u8"), | |
| 563 | ||
| 564 | 530 | .empty_struct_value => return out_stream.writeAll("struct {}{}"), |
| 565 | 531 | .aggregate => { |
| 566 | 532 | return out_stream.writeAll("(aggregate)"); |
| ... | ... | @@ -674,7 +640,7 @@ pub const Value = struct { |
| 674 | 640 | switch (val.tag()) { |
| 675 | 641 | .bytes => { |
| 676 | 642 | const bytes = val.castTag(.bytes).?.data; |
| 677 | const adjusted_len = bytes.len - @boolToInt(ty.sentinel() != null); | |
| 643 | const adjusted_len = bytes.len - @boolToInt(ty.sentinel(mod) != null); | |
| 678 | 644 | const adjusted_bytes = bytes[0..adjusted_len]; |
| 679 | 645 | return allocator.dupe(u8, adjusted_bytes); |
| 680 | 646 | }, |
| ... | ... | @@ -686,7 +652,7 @@ pub const Value = struct { |
| 686 | 652 | .enum_literal => return allocator.dupe(u8, val.castTag(.enum_literal).?.data), |
| 687 | 653 | .repeated => { |
| 688 | 654 | const byte = @intCast(u8, val.castTag(.repeated).?.data.toUnsignedInt(mod)); |
| 689 | const result = try allocator.alloc(u8, @intCast(usize, ty.arrayLen())); | |
| 655 | const result = try allocator.alloc(u8, @intCast(usize, ty.arrayLen(mod))); | |
| 690 | 656 | @memset(result, byte); |
| 691 | 657 | return result; |
| 692 | 658 | }, |
| ... | ... | @@ -701,7 +667,7 @@ pub const Value = struct { |
| 701 | 667 | const slice = val.castTag(.slice).?.data; |
| 702 | 668 | return arrayToAllocatedBytes(slice.ptr, slice.len.toUnsignedInt(mod), allocator, mod); |
| 703 | 669 | }, |
| 704 | else => return arrayToAllocatedBytes(val, ty.arrayLen(), allocator, mod), | |
| 670 | else => return arrayToAllocatedBytes(val, ty.arrayLen(mod), allocator, mod), | |
| 705 | 671 | } |
| 706 | 672 | } |
| 707 | 673 | |
| ... | ... | @@ -720,13 +686,6 @@ pub const Value = struct { |
| 720 | 686 | if (self.ip_index != .none) return self.ip_index.toType(); |
| 721 | 687 | return switch (self.tag()) { |
| 722 | 688 | .ty => self.castTag(.ty).?.data, |
| 723 | .single_const_pointer_to_comptime_int_type => Type.initTag(.single_const_pointer_to_comptime_int), | |
| 724 | .const_slice_u8_type => Type.initTag(.const_slice_u8), | |
| 725 | .const_slice_u8_sentinel_0_type => Type.initTag(.const_slice_u8_sentinel_0), | |
| 726 | .anyerror_void_error_union_type => Type.initTag(.anyerror_void_error_union), | |
| 727 | .manyptr_u8_type => Type.initTag(.manyptr_u8), | |
| 728 | .manyptr_const_u8_type => Type.initTag(.manyptr_const_u8), | |
| 729 | .manyptr_const_u8_sentinel_0_type => Type.initTag(.manyptr_const_u8_sentinel_0), | |
| 730 | 689 | |
| 731 | 690 | else => unreachable, |
| 732 | 691 | }; |
| ... | ... | @@ -1096,8 +1055,8 @@ pub const Value = struct { |
| 1096 | 1055 | else => unreachable, |
| 1097 | 1056 | }, |
| 1098 | 1057 | .Array => { |
| 1099 | const len = ty.arrayLen(); | |
| 1100 | const elem_ty = ty.childType(); | |
| 1058 | const len = ty.arrayLen(mod); | |
| 1059 | const elem_ty = ty.childType(mod); | |
| 1101 | 1060 | const elem_size = @intCast(usize, elem_ty.abiSize(mod)); |
| 1102 | 1061 | var elem_i: usize = 0; |
| 1103 | 1062 | var elem_value_buf: ElemValueBuffer = undefined; |
| ... | ... | @@ -1150,8 +1109,7 @@ pub const Value = struct { |
| 1150 | 1109 | }, |
| 1151 | 1110 | .Optional => { |
| 1152 | 1111 | if (!ty.isPtrLikeOptional(mod)) return error.IllDefinedMemoryLayout; |
| 1153 | var buf: Type.Payload.ElemType = undefined; | |
| 1154 | const child = ty.optionalChild(&buf); | |
| 1112 | const child = ty.optionalChild(mod); | |
| 1155 | 1113 | const opt_val = val.optionalValue(mod); |
| 1156 | 1114 | if (opt_val) |some| { |
| 1157 | 1115 | return some.writeToMemory(child, mod, buffer); |
| ... | ... | @@ -1220,9 +1178,9 @@ pub const Value = struct { |
| 1220 | 1178 | else => unreachable, |
| 1221 | 1179 | }, |
| 1222 | 1180 | .Vector => { |
| 1223 | const elem_ty = ty.childType(); | |
| 1181 | const elem_ty = ty.childType(mod); | |
| 1224 | 1182 | const elem_bit_size = @intCast(u16, elem_ty.bitSize(mod)); |
| 1225 | const len = @intCast(usize, ty.arrayLen()); | |
| 1183 | const len = @intCast(usize, ty.arrayLen(mod)); | |
| 1226 | 1184 | |
| 1227 | 1185 | var bits: u16 = 0; |
| 1228 | 1186 | var elem_i: usize = 0; |
| ... | ... | @@ -1267,8 +1225,7 @@ pub const Value = struct { |
| 1267 | 1225 | }, |
| 1268 | 1226 | .Optional => { |
| 1269 | 1227 | assert(ty.isPtrLikeOptional(mod)); |
| 1270 | var buf: Type.Payload.ElemType = undefined; | |
| 1271 | const child = ty.optionalChild(&buf); | |
| 1228 | const child = ty.optionalChild(mod); | |
| 1272 | 1229 | const opt_val = val.optionalValue(mod); |
| 1273 | 1230 | if (opt_val) |some| { |
| 1274 | 1231 | return some.writeToPackedMemory(child, mod, buffer, bit_offset); |
| ... | ... | @@ -1335,9 +1292,9 @@ pub const Value = struct { |
| 1335 | 1292 | else => unreachable, |
| 1336 | 1293 | }, |
| 1337 | 1294 | .Array => { |
| 1338 | const elem_ty = ty.childType(); | |
| 1295 | const elem_ty = ty.childType(mod); | |
| 1339 | 1296 | const elem_size = elem_ty.abiSize(mod); |
| 1340 | const elems = try arena.alloc(Value, @intCast(usize, ty.arrayLen())); | |
| 1297 | const elems = try arena.alloc(Value, @intCast(usize, ty.arrayLen(mod))); | |
| 1341 | 1298 | var offset: usize = 0; |
| 1342 | 1299 | for (elems) |*elem| { |
| 1343 | 1300 | elem.* = try readFromMemory(elem_ty, mod, buffer[offset..], arena); |
| ... | ... | @@ -1386,8 +1343,7 @@ pub const Value = struct { |
| 1386 | 1343 | }, |
| 1387 | 1344 | .Optional => { |
| 1388 | 1345 | assert(ty.isPtrLikeOptional(mod)); |
| 1389 | var buf: Type.Payload.ElemType = undefined; | |
| 1390 | const child = ty.optionalChild(&buf); | |
| 1346 | const child = ty.optionalChild(mod); | |
| 1391 | 1347 | return readFromMemory(child, mod, buffer, arena); |
| 1392 | 1348 | }, |
| 1393 | 1349 | else => @panic("TODO implement readFromMemory for more types"), |
| ... | ... | @@ -1449,8 +1405,8 @@ pub const Value = struct { |
| 1449 | 1405 | else => unreachable, |
| 1450 | 1406 | }, |
| 1451 | 1407 | .Vector => { |
| 1452 | const elem_ty = ty.childType(); | |
| 1453 | const elems = try arena.alloc(Value, @intCast(usize, ty.arrayLen())); | |
| 1408 | const elem_ty = ty.childType(mod); | |
| 1409 | const elems = try arena.alloc(Value, @intCast(usize, ty.arrayLen(mod))); | |
| 1454 | 1410 | |
| 1455 | 1411 | var bits: u16 = 0; |
| 1456 | 1412 | const elem_bit_size = @intCast(u16, elem_ty.bitSize(mod)); |
| ... | ... | @@ -1483,8 +1439,7 @@ pub const Value = struct { |
| 1483 | 1439 | }, |
| 1484 | 1440 | .Optional => { |
| 1485 | 1441 | assert(ty.isPtrLikeOptional(mod)); |
| 1486 | var buf: Type.Payload.ElemType = undefined; | |
| 1487 | const child = ty.optionalChild(&buf); | |
| 1442 | const child = ty.optionalChild(mod); | |
| 1488 | 1443 | return readFromPackedMemory(child, mod, buffer, bit_offset, arena); |
| 1489 | 1444 | }, |
| 1490 | 1445 | else => @panic("TODO implement readFromPackedMemory for more types"), |
| ... | ... | @@ -1956,7 +1911,7 @@ pub const Value = struct { |
| 1956 | 1911 | pub fn compareAll(lhs: Value, op: std.math.CompareOperator, rhs: Value, ty: Type, mod: *Module) bool { |
| 1957 | 1912 | if (ty.zigTypeTag(mod) == .Vector) { |
| 1958 | 1913 | var i: usize = 0; |
| 1959 | while (i < ty.vectorLen()) : (i += 1) { | |
| 1914 | while (i < ty.vectorLen(mod)) : (i += 1) { | |
| 1960 | 1915 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 1961 | 1916 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| 1962 | 1917 | const lhs_elem = lhs.elemValueBuffer(mod, i, &lhs_buf); |
| ... | ... | @@ -2092,8 +2047,7 @@ pub const Value = struct { |
| 2092 | 2047 | .opt_payload => { |
| 2093 | 2048 | const a_payload = a.castTag(.opt_payload).?.data; |
| 2094 | 2049 | const b_payload = b.castTag(.opt_payload).?.data; |
| 2095 | var buffer: Type.Payload.ElemType = undefined; | |
| 2096 | const payload_ty = ty.optionalChild(&buffer); | |
| 2050 | const payload_ty = ty.optionalChild(mod); | |
| 2097 | 2051 | return eqlAdvanced(a_payload, payload_ty, b_payload, payload_ty, mod, opt_sema); |
| 2098 | 2052 | }, |
| 2099 | 2053 | .slice => { |
| ... | ... | @@ -2175,7 +2129,7 @@ pub const Value = struct { |
| 2175 | 2129 | return true; |
| 2176 | 2130 | } |
| 2177 | 2131 | |
| 2178 | const elem_ty = ty.childType(); | |
| 2132 | const elem_ty = ty.childType(mod); | |
| 2179 | 2133 | for (a_field_vals, 0..) |a_elem, i| { |
| 2180 | 2134 | const b_elem = b_field_vals[i]; |
| 2181 | 2135 | |
| ... | ... | @@ -2239,8 +2193,8 @@ pub const Value = struct { |
| 2239 | 2193 | return eqlAdvanced(a_val, int_ty, b_val, int_ty, mod, opt_sema); |
| 2240 | 2194 | }, |
| 2241 | 2195 | .Array, .Vector => { |
| 2242 | const len = ty.arrayLen(); | |
| 2243 | const elem_ty = ty.childType(); | |
| 2196 | const len = ty.arrayLen(mod); | |
| 2197 | const elem_ty = ty.childType(mod); | |
| 2244 | 2198 | var i: usize = 0; |
| 2245 | 2199 | var a_buf: ElemValueBuffer = undefined; |
| 2246 | 2200 | var b_buf: ElemValueBuffer = undefined; |
| ... | ... | @@ -2253,11 +2207,11 @@ pub const Value = struct { |
| 2253 | 2207 | } |
| 2254 | 2208 | return true; |
| 2255 | 2209 | }, |
| 2256 | .Pointer => switch (ty.ptrSize()) { | |
| 2210 | .Pointer => switch (ty.ptrSize(mod)) { | |
| 2257 | 2211 | .Slice => { |
| 2258 | const a_len = switch (a_ty.ptrSize()) { | |
| 2212 | const a_len = switch (a_ty.ptrSize(mod)) { | |
| 2259 | 2213 | .Slice => a.sliceLen(mod), |
| 2260 | .One => a_ty.childType().arrayLen(), | |
| 2214 | .One => a_ty.childType(mod).arrayLen(mod), | |
| 2261 | 2215 | else => unreachable, |
| 2262 | 2216 | }; |
| 2263 | 2217 | if (a_len != b.sliceLen(mod)) { |
| ... | ... | @@ -2266,7 +2220,7 @@ pub const Value = struct { |
| 2266 | 2220 | |
| 2267 | 2221 | var ptr_buf: Type.SlicePtrFieldTypeBuffer = undefined; |
| 2268 | 2222 | const ptr_ty = ty.slicePtrFieldType(&ptr_buf); |
| 2269 | const a_ptr = switch (a_ty.ptrSize()) { | |
| 2223 | const a_ptr = switch (a_ty.ptrSize(mod)) { | |
| 2270 | 2224 | .Slice => a.slicePtr(), |
| 2271 | 2225 | .One => a, |
| 2272 | 2226 | else => unreachable, |
| ... | ... | @@ -2412,8 +2366,8 @@ pub const Value = struct { |
| 2412 | 2366 | else => return hashPtr(val, hasher, mod), |
| 2413 | 2367 | }, |
| 2414 | 2368 | .Array, .Vector => { |
| 2415 | const len = ty.arrayLen(); | |
| 2416 | const elem_ty = ty.childType(); | |
| 2369 | const len = ty.arrayLen(mod); | |
| 2370 | const elem_ty = ty.childType(mod); | |
| 2417 | 2371 | var index: usize = 0; |
| 2418 | 2372 | var elem_value_buf: ElemValueBuffer = undefined; |
| 2419 | 2373 | while (index < len) : (index += 1) { |
| ... | ... | @@ -2438,8 +2392,7 @@ pub const Value = struct { |
| 2438 | 2392 | if (val.castTag(.opt_payload)) |payload| { |
| 2439 | 2393 | std.hash.autoHash(hasher, true); // non-null |
| 2440 | 2394 | const sub_val = payload.data; |
| 2441 | var buffer: Type.Payload.ElemType = undefined; | |
| 2442 | const sub_ty = ty.optionalChild(&buffer); | |
| 2395 | const sub_ty = ty.optionalChild(mod); | |
| 2443 | 2396 | sub_val.hash(sub_ty, hasher, mod); |
| 2444 | 2397 | } else { |
| 2445 | 2398 | std.hash.autoHash(hasher, false); // null |
| ... | ... | @@ -2534,8 +2487,8 @@ pub const Value = struct { |
| 2534 | 2487 | else => val.hashPtr(hasher, mod), |
| 2535 | 2488 | }, |
| 2536 | 2489 | .Array, .Vector => { |
| 2537 | const len = ty.arrayLen(); | |
| 2538 | const elem_ty = ty.childType(); | |
| 2490 | const len = ty.arrayLen(mod); | |
| 2491 | const elem_ty = ty.childType(mod); | |
| 2539 | 2492 | var index: usize = 0; |
| 2540 | 2493 | var elem_value_buf: ElemValueBuffer = undefined; |
| 2541 | 2494 | while (index < len) : (index += 1) { |
| ... | ... | @@ -2544,8 +2497,7 @@ pub const Value = struct { |
| 2544 | 2497 | } |
| 2545 | 2498 | }, |
| 2546 | 2499 | .Optional => if (val.castTag(.opt_payload)) |payload| { |
| 2547 | var buf: Type.Payload.ElemType = undefined; | |
| 2548 | const child_ty = ty.optionalChild(&buf); | |
| 2500 | const child_ty = ty.optionalChild(mod); | |
| 2549 | 2501 | payload.data.hashUncoerced(child_ty, hasher, mod); |
| 2550 | 2502 | } else std.hash.autoHash(hasher, std.builtin.TypeId.Null), |
| 2551 | 2503 | .ErrorSet, .ErrorUnion => if (val.getError()) |err| hasher.update(err) else { |
| ... | ... | @@ -2720,7 +2672,7 @@ pub const Value = struct { |
| 2720 | 2672 | const decl_index = val.castTag(.decl_ref).?.data; |
| 2721 | 2673 | const decl = mod.declPtr(decl_index); |
| 2722 | 2674 | if (decl.ty.zigTypeTag(mod) == .Array) { |
| 2723 | return decl.ty.arrayLen(); | |
| 2675 | return decl.ty.arrayLen(mod); | |
| 2724 | 2676 | } else { |
| 2725 | 2677 | return 1; |
| 2726 | 2678 | } |
| ... | ... | @@ -2729,7 +2681,7 @@ pub const Value = struct { |
| 2729 | 2681 | const decl_index = val.castTag(.decl_ref_mut).?.data.decl_index; |
| 2730 | 2682 | const decl = mod.declPtr(decl_index); |
| 2731 | 2683 | if (decl.ty.zigTypeTag(mod) == .Array) { |
| 2732 | return decl.ty.arrayLen(); | |
| 2684 | return decl.ty.arrayLen(mod); | |
| 2733 | 2685 | } else { |
| 2734 | 2686 | return 1; |
| 2735 | 2687 | } |
| ... | ... | @@ -2737,7 +2689,7 @@ pub const Value = struct { |
| 2737 | 2689 | .comptime_field_ptr => { |
| 2738 | 2690 | const payload = val.castTag(.comptime_field_ptr).?.data; |
| 2739 | 2691 | if (payload.field_ty.zigTypeTag(mod) == .Array) { |
| 2740 | return payload.field_ty.arrayLen(); | |
| 2692 | return payload.field_ty.arrayLen(mod); | |
| 2741 | 2693 | } else { |
| 2742 | 2694 | return 1; |
| 2743 | 2695 | } |
| ... | ... | @@ -3137,7 +3089,7 @@ pub const Value = struct { |
| 3137 | 3089 | |
| 3138 | 3090 | pub fn intToFloatAdvanced(val: Value, arena: Allocator, int_ty: Type, float_ty: Type, mod: *Module, opt_sema: ?*Sema) !Value { |
| 3139 | 3091 | if (int_ty.zigTypeTag(mod) == .Vector) { |
| 3140 | const result_data = try arena.alloc(Value, int_ty.vectorLen()); | |
| 3092 | const result_data = try arena.alloc(Value, int_ty.vectorLen(mod)); | |
| 3141 | 3093 | for (result_data, 0..) |*scalar, i| { |
| 3142 | 3094 | var buf: Value.ElemValueBuffer = undefined; |
| 3143 | 3095 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -3250,7 +3202,7 @@ pub const Value = struct { |
| 3250 | 3202 | mod: *Module, |
| 3251 | 3203 | ) !Value { |
| 3252 | 3204 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3253 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3205 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3254 | 3206 | for (result_data, 0..) |*scalar, i| { |
| 3255 | 3207 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3256 | 3208 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3298,7 +3250,7 @@ pub const Value = struct { |
| 3298 | 3250 | mod: *Module, |
| 3299 | 3251 | ) !Value { |
| 3300 | 3252 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3301 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3253 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3302 | 3254 | for (result_data, 0..) |*scalar, i| { |
| 3303 | 3255 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3304 | 3256 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3345,8 +3297,8 @@ pub const Value = struct { |
| 3345 | 3297 | mod: *Module, |
| 3346 | 3298 | ) !OverflowArithmeticResult { |
| 3347 | 3299 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3348 | const overflowed_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3349 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3300 | const overflowed_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3301 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3350 | 3302 | for (result_data, 0..) |*scalar, i| { |
| 3351 | 3303 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3352 | 3304 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3408,7 +3360,7 @@ pub const Value = struct { |
| 3408 | 3360 | mod: *Module, |
| 3409 | 3361 | ) !Value { |
| 3410 | 3362 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3411 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3363 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3412 | 3364 | for (result_data, 0..) |*scalar, i| { |
| 3413 | 3365 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3414 | 3366 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3452,7 +3404,7 @@ pub const Value = struct { |
| 3452 | 3404 | mod: *Module, |
| 3453 | 3405 | ) !Value { |
| 3454 | 3406 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3455 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3407 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3456 | 3408 | for (result_data, 0..) |*scalar, i| { |
| 3457 | 3409 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3458 | 3410 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3527,7 +3479,7 @@ pub const Value = struct { |
| 3527 | 3479 | /// operands must be (vectors of) integers; handles undefined scalars. |
| 3528 | 3480 | pub fn bitwiseNot(val: Value, ty: Type, arena: Allocator, mod: *Module) !Value { |
| 3529 | 3481 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3530 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3482 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3531 | 3483 | for (result_data, 0..) |*scalar, i| { |
| 3532 | 3484 | var buf: Value.ElemValueBuffer = undefined; |
| 3533 | 3485 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -3565,7 +3517,7 @@ pub const Value = struct { |
| 3565 | 3517 | /// operands must be (vectors of) integers; handles undefined scalars. |
| 3566 | 3518 | pub fn bitwiseAnd(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3567 | 3519 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3568 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3520 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3569 | 3521 | for (result_data, 0..) |*scalar, i| { |
| 3570 | 3522 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3571 | 3523 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3601,7 +3553,7 @@ pub const Value = struct { |
| 3601 | 3553 | /// operands must be (vectors of) integers; handles undefined scalars. |
| 3602 | 3554 | pub fn bitwiseNand(lhs: Value, rhs: Value, ty: Type, arena: Allocator, mod: *Module) !Value { |
| 3603 | 3555 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3604 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 3556 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 3605 | 3557 | for (result_data, 0..) |*scalar, i| { |
| 3606 | 3558 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3607 | 3559 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3631,7 +3583,7 @@ pub const Value = struct { |
| 3631 | 3583 | /// operands must be (vectors of) integers; handles undefined scalars. |
| 3632 | 3584 | pub fn bitwiseOr(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3633 | 3585 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3634 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3586 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3635 | 3587 | for (result_data, 0..) |*scalar, i| { |
| 3636 | 3588 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3637 | 3589 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3666,7 +3618,7 @@ pub const Value = struct { |
| 3666 | 3618 | /// operands must be (vectors of) integers; handles undefined scalars. |
| 3667 | 3619 | pub fn bitwiseXor(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3668 | 3620 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3669 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3621 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3670 | 3622 | for (result_data, 0..) |*scalar, i| { |
| 3671 | 3623 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3672 | 3624 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3701,7 +3653,7 @@ pub const Value = struct { |
| 3701 | 3653 | |
| 3702 | 3654 | pub fn intDiv(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3703 | 3655 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3704 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3656 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3705 | 3657 | for (result_data, 0..) |*scalar, i| { |
| 3706 | 3658 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3707 | 3659 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3741,7 +3693,7 @@ pub const Value = struct { |
| 3741 | 3693 | |
| 3742 | 3694 | pub fn intDivFloor(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3743 | 3695 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3744 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3696 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3745 | 3697 | for (result_data, 0..) |*scalar, i| { |
| 3746 | 3698 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3747 | 3699 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3781,7 +3733,7 @@ pub const Value = struct { |
| 3781 | 3733 | |
| 3782 | 3734 | pub fn intMod(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3783 | 3735 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3784 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3736 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3785 | 3737 | for (result_data, 0..) |*scalar, i| { |
| 3786 | 3738 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3787 | 3739 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3857,7 +3809,7 @@ pub const Value = struct { |
| 3857 | 3809 | pub fn floatRem(lhs: Value, rhs: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 3858 | 3810 | const target = mod.getTarget(); |
| 3859 | 3811 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 3860 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 3812 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 3861 | 3813 | for (result_data, 0..) |*scalar, i| { |
| 3862 | 3814 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3863 | 3815 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3904,7 +3856,7 @@ pub const Value = struct { |
| 3904 | 3856 | pub fn floatMod(lhs: Value, rhs: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 3905 | 3857 | const target = mod.getTarget(); |
| 3906 | 3858 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 3907 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 3859 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 3908 | 3860 | for (result_data, 0..) |*scalar, i| { |
| 3909 | 3861 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3910 | 3862 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3950,7 +3902,7 @@ pub const Value = struct { |
| 3950 | 3902 | |
| 3951 | 3903 | pub fn intMul(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 3952 | 3904 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3953 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3905 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3954 | 3906 | for (result_data, 0..) |*scalar, i| { |
| 3955 | 3907 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 3956 | 3908 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -3986,7 +3938,7 @@ pub const Value = struct { |
| 3986 | 3938 | |
| 3987 | 3939 | pub fn intTrunc(val: Value, ty: Type, allocator: Allocator, signedness: std.builtin.Signedness, bits: u16, mod: *Module) !Value { |
| 3988 | 3940 | if (ty.zigTypeTag(mod) == .Vector) { |
| 3989 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3941 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 3990 | 3942 | for (result_data, 0..) |*scalar, i| { |
| 3991 | 3943 | var buf: Value.ElemValueBuffer = undefined; |
| 3992 | 3944 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4007,7 +3959,7 @@ pub const Value = struct { |
| 4007 | 3959 | mod: *Module, |
| 4008 | 3960 | ) !Value { |
| 4009 | 3961 | if (ty.zigTypeTag(mod) == .Vector) { |
| 4010 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3962 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 4011 | 3963 | for (result_data, 0..) |*scalar, i| { |
| 4012 | 3964 | var buf: Value.ElemValueBuffer = undefined; |
| 4013 | 3965 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4038,7 +3990,7 @@ pub const Value = struct { |
| 4038 | 3990 | |
| 4039 | 3991 | pub fn shl(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 4040 | 3992 | if (ty.zigTypeTag(mod) == .Vector) { |
| 4041 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 3993 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 4042 | 3994 | for (result_data, 0..) |*scalar, i| { |
| 4043 | 3995 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4044 | 3996 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4078,8 +4030,8 @@ pub const Value = struct { |
| 4078 | 4030 | mod: *Module, |
| 4079 | 4031 | ) !OverflowArithmeticResult { |
| 4080 | 4032 | if (ty.zigTypeTag(mod) == .Vector) { |
| 4081 | const overflowed_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 4082 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 4033 | const overflowed_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 4034 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 4083 | 4035 | for (result_data, 0..) |*scalar, i| { |
| 4084 | 4036 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4085 | 4037 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4136,7 +4088,7 @@ pub const Value = struct { |
| 4136 | 4088 | mod: *Module, |
| 4137 | 4089 | ) !Value { |
| 4138 | 4090 | if (ty.zigTypeTag(mod) == .Vector) { |
| 4139 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 4091 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 4140 | 4092 | for (result_data, 0..) |*scalar, i| { |
| 4141 | 4093 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4142 | 4094 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4184,7 +4136,7 @@ pub const Value = struct { |
| 4184 | 4136 | mod: *Module, |
| 4185 | 4137 | ) !Value { |
| 4186 | 4138 | if (ty.zigTypeTag(mod) == .Vector) { |
| 4187 | const result_data = try arena.alloc(Value, ty.vectorLen()); | |
| 4139 | const result_data = try arena.alloc(Value, ty.vectorLen(mod)); | |
| 4188 | 4140 | for (result_data, 0..) |*scalar, i| { |
| 4189 | 4141 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4190 | 4142 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4212,7 +4164,7 @@ pub const Value = struct { |
| 4212 | 4164 | |
| 4213 | 4165 | pub fn shr(lhs: Value, rhs: Value, ty: Type, allocator: Allocator, mod: *Module) !Value { |
| 4214 | 4166 | if (ty.zigTypeTag(mod) == .Vector) { |
| 4215 | const result_data = try allocator.alloc(Value, ty.vectorLen()); | |
| 4167 | const result_data = try allocator.alloc(Value, ty.vectorLen(mod)); | |
| 4216 | 4168 | for (result_data, 0..) |*scalar, i| { |
| 4217 | 4169 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4218 | 4170 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4264,7 +4216,7 @@ pub const Value = struct { |
| 4264 | 4216 | ) !Value { |
| 4265 | 4217 | const target = mod.getTarget(); |
| 4266 | 4218 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4267 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4219 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4268 | 4220 | for (result_data, 0..) |*scalar, i| { |
| 4269 | 4221 | var buf: Value.ElemValueBuffer = undefined; |
| 4270 | 4222 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4300,7 +4252,7 @@ pub const Value = struct { |
| 4300 | 4252 | ) !Value { |
| 4301 | 4253 | const target = mod.getTarget(); |
| 4302 | 4254 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4303 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4255 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4304 | 4256 | for (result_data, 0..) |*scalar, i| { |
| 4305 | 4257 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4306 | 4258 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4359,7 +4311,7 @@ pub const Value = struct { |
| 4359 | 4311 | ) !Value { |
| 4360 | 4312 | const target = mod.getTarget(); |
| 4361 | 4313 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4362 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4314 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4363 | 4315 | for (result_data, 0..) |*scalar, i| { |
| 4364 | 4316 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4365 | 4317 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4418,7 +4370,7 @@ pub const Value = struct { |
| 4418 | 4370 | ) !Value { |
| 4419 | 4371 | const target = mod.getTarget(); |
| 4420 | 4372 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4421 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4373 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4422 | 4374 | for (result_data, 0..) |*scalar, i| { |
| 4423 | 4375 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4424 | 4376 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4477,7 +4429,7 @@ pub const Value = struct { |
| 4477 | 4429 | ) !Value { |
| 4478 | 4430 | const target = mod.getTarget(); |
| 4479 | 4431 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4480 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4432 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4481 | 4433 | for (result_data, 0..) |*scalar, i| { |
| 4482 | 4434 | var lhs_buf: Value.ElemValueBuffer = undefined; |
| 4483 | 4435 | var rhs_buf: Value.ElemValueBuffer = undefined; |
| ... | ... | @@ -4530,7 +4482,7 @@ pub const Value = struct { |
| 4530 | 4482 | pub fn sqrt(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4531 | 4483 | const target = mod.getTarget(); |
| 4532 | 4484 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4533 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4485 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4534 | 4486 | for (result_data, 0..) |*scalar, i| { |
| 4535 | 4487 | var buf: Value.ElemValueBuffer = undefined; |
| 4536 | 4488 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4570,7 +4522,7 @@ pub const Value = struct { |
| 4570 | 4522 | pub fn sin(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4571 | 4523 | const target = mod.getTarget(); |
| 4572 | 4524 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4573 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4525 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4574 | 4526 | for (result_data, 0..) |*scalar, i| { |
| 4575 | 4527 | var buf: Value.ElemValueBuffer = undefined; |
| 4576 | 4528 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4610,7 +4562,7 @@ pub const Value = struct { |
| 4610 | 4562 | pub fn cos(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4611 | 4563 | const target = mod.getTarget(); |
| 4612 | 4564 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4613 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4565 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4614 | 4566 | for (result_data, 0..) |*scalar, i| { |
| 4615 | 4567 | var buf: Value.ElemValueBuffer = undefined; |
| 4616 | 4568 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4650,7 +4602,7 @@ pub const Value = struct { |
| 4650 | 4602 | pub fn tan(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4651 | 4603 | const target = mod.getTarget(); |
| 4652 | 4604 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4653 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4605 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4654 | 4606 | for (result_data, 0..) |*scalar, i| { |
| 4655 | 4607 | var buf: Value.ElemValueBuffer = undefined; |
| 4656 | 4608 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4690,7 +4642,7 @@ pub const Value = struct { |
| 4690 | 4642 | pub fn exp(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4691 | 4643 | const target = mod.getTarget(); |
| 4692 | 4644 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4693 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4645 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4694 | 4646 | for (result_data, 0..) |*scalar, i| { |
| 4695 | 4647 | var buf: Value.ElemValueBuffer = undefined; |
| 4696 | 4648 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4730,7 +4682,7 @@ pub const Value = struct { |
| 4730 | 4682 | pub fn exp2(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4731 | 4683 | const target = mod.getTarget(); |
| 4732 | 4684 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4733 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4685 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4734 | 4686 | for (result_data, 0..) |*scalar, i| { |
| 4735 | 4687 | var buf: Value.ElemValueBuffer = undefined; |
| 4736 | 4688 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4770,7 +4722,7 @@ pub const Value = struct { |
| 4770 | 4722 | pub fn log(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4771 | 4723 | const target = mod.getTarget(); |
| 4772 | 4724 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4773 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4725 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4774 | 4726 | for (result_data, 0..) |*scalar, i| { |
| 4775 | 4727 | var buf: Value.ElemValueBuffer = undefined; |
| 4776 | 4728 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4810,7 +4762,7 @@ pub const Value = struct { |
| 4810 | 4762 | pub fn log2(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4811 | 4763 | const target = mod.getTarget(); |
| 4812 | 4764 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4813 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4765 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4814 | 4766 | for (result_data, 0..) |*scalar, i| { |
| 4815 | 4767 | var buf: Value.ElemValueBuffer = undefined; |
| 4816 | 4768 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4850,7 +4802,7 @@ pub const Value = struct { |
| 4850 | 4802 | pub fn log10(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4851 | 4803 | const target = mod.getTarget(); |
| 4852 | 4804 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4853 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4805 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4854 | 4806 | for (result_data, 0..) |*scalar, i| { |
| 4855 | 4807 | var buf: Value.ElemValueBuffer = undefined; |
| 4856 | 4808 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4890,7 +4842,7 @@ pub const Value = struct { |
| 4890 | 4842 | pub fn fabs(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4891 | 4843 | const target = mod.getTarget(); |
| 4892 | 4844 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4893 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4845 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4894 | 4846 | for (result_data, 0..) |*scalar, i| { |
| 4895 | 4847 | var buf: Value.ElemValueBuffer = undefined; |
| 4896 | 4848 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4930,7 +4882,7 @@ pub const Value = struct { |
| 4930 | 4882 | pub fn floor(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4931 | 4883 | const target = mod.getTarget(); |
| 4932 | 4884 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4933 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4885 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4934 | 4886 | for (result_data, 0..) |*scalar, i| { |
| 4935 | 4887 | var buf: Value.ElemValueBuffer = undefined; |
| 4936 | 4888 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -4970,7 +4922,7 @@ pub const Value = struct { |
| 4970 | 4922 | pub fn ceil(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 4971 | 4923 | const target = mod.getTarget(); |
| 4972 | 4924 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 4973 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4925 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 4974 | 4926 | for (result_data, 0..) |*scalar, i| { |
| 4975 | 4927 | var buf: Value.ElemValueBuffer = undefined; |
| 4976 | 4928 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -5010,7 +4962,7 @@ pub const Value = struct { |
| 5010 | 4962 | pub fn round(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 5011 | 4963 | const target = mod.getTarget(); |
| 5012 | 4964 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 5013 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 4965 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 5014 | 4966 | for (result_data, 0..) |*scalar, i| { |
| 5015 | 4967 | var buf: Value.ElemValueBuffer = undefined; |
| 5016 | 4968 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -5050,7 +5002,7 @@ pub const Value = struct { |
| 5050 | 5002 | pub fn trunc(val: Value, float_type: Type, arena: Allocator, mod: *Module) !Value { |
| 5051 | 5003 | const target = mod.getTarget(); |
| 5052 | 5004 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 5053 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 5005 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 5054 | 5006 | for (result_data, 0..) |*scalar, i| { |
| 5055 | 5007 | var buf: Value.ElemValueBuffer = undefined; |
| 5056 | 5008 | const elem_val = val.elemValueBuffer(mod, i, &buf); |
| ... | ... | @@ -5097,7 +5049,7 @@ pub const Value = struct { |
| 5097 | 5049 | ) !Value { |
| 5098 | 5050 | const target = mod.getTarget(); |
| 5099 | 5051 | if (float_type.zigTypeTag(mod) == .Vector) { |
| 5100 | const result_data = try arena.alloc(Value, float_type.vectorLen()); | |
| 5052 | const result_data = try arena.alloc(Value, float_type.vectorLen(mod)); | |
| 5101 | 5053 | for (result_data, 0..) |*scalar, i| { |
| 5102 | 5054 | var mulend1_buf: Value.ElemValueBuffer = undefined; |
| 5103 | 5055 | const mulend1_elem = mulend1.elemValueBuffer(mod, i, &mulend1_buf); |