authorgravatar for jacobly@ziglang.orgJacob Young <jacobly@ziglang.org> 2023-06-25 19:13:47-04:00
committergravatar for jacobly@ziglang.orgJacob Young <jacobly@ziglang.org> 2023-06-25 19:14:26-04:00
log85902115d4fde6120b6cea610cd6f79baede5aaa
tree50bac6719a89a52f51efb1b0ec4b42b905868024
parent7013567f8abde19e5176d902ce88abc754fc9a3e

x86_64: cleanup `@as` invasion


1 files changed, 287 insertions(+), 309 deletions(-)

src/arch/x86_64/CodeGen.zig+287-309
...@@ -329,7 +329,7 @@ pub const MCValue = union(enum) {...@@ -329,7 +329,7 @@ pub const MCValue = union(enum) {
329 .load_frame,329 .load_frame,
330 .reserved_frame,330 .reserved_frame,
331 => unreachable, // not offsettable331 => unreachable, // not offsettable
332 .immediate => |imm| .{ .immediate = @as(u64, @bitCast(@as(i64, @bitCast(imm)) +% off)) },332 .immediate => |imm| .{ .immediate = @bitCast(@as(i64, @bitCast(imm)) +% off) },
333 .register => |reg| .{ .register_offset = .{ .reg = reg, .off = off } },333 .register => |reg| .{ .register_offset = .{ .reg = reg, .off = off } },
334 .register_offset => |reg_off| .{334 .register_offset => |reg_off| .{
335 .register_offset = .{ .reg = reg_off.reg, .off = reg_off.off + off },335 .register_offset = .{ .reg = reg_off.reg, .off = reg_off.off + off },
...@@ -606,7 +606,7 @@ const FrameAlloc = struct {...@@ -606,7 +606,7 @@ const FrameAlloc = struct {
606 fn init(alloc_abi: struct { size: u64, alignment: u32 }) FrameAlloc {606 fn init(alloc_abi: struct { size: u64, alignment: u32 }) FrameAlloc {
607 assert(math.isPowerOfTwo(alloc_abi.alignment));607 assert(math.isPowerOfTwo(alloc_abi.alignment));
608 return .{608 return .{
609 .abi_size = @as(u31, @intCast(alloc_abi.size)),609 .abi_size = @intCast(alloc_abi.size),
610 .abi_align = math.log2_int(u32, alloc_abi.alignment),610 .abi_align = math.log2_int(u32, alloc_abi.alignment),
611 .ref_count = 0,611 .ref_count = 0,
612 };612 };
...@@ -694,7 +694,7 @@ pub fn generate(...@@ -694,7 +694,7 @@ pub fn generate(
694 FrameAlloc.init(.{694 FrameAlloc.init(.{
695 .size = 0,695 .size = 0,
696 .alignment = if (mod.align_stack_fns.get(module_fn_index)) |set_align_stack|696 .alignment = if (mod.align_stack_fns.get(module_fn_index)) |set_align_stack|
697 @as(u32, @intCast(set_align_stack.alignment.toByteUnitsOptional().?))697 @intCast(set_align_stack.alignment.toByteUnitsOptional().?)
698 else698 else
699 1,699 1,
700 }),700 }),
...@@ -979,7 +979,7 @@ fn fmtTracking(self: *Self) std.fmt.Formatter(formatTracking) {...@@ -979,7 +979,7 @@ fn fmtTracking(self: *Self) std.fmt.Formatter(formatTracking) {
979fn addInst(self: *Self, inst: Mir.Inst) error{OutOfMemory}!Mir.Inst.Index {979fn addInst(self: *Self, inst: Mir.Inst) error{OutOfMemory}!Mir.Inst.Index {
980 const gpa = self.gpa;980 const gpa = self.gpa;
981 try self.mir_instructions.ensureUnusedCapacity(gpa, 1);981 try self.mir_instructions.ensureUnusedCapacity(gpa, 1);
982 const result_index = @as(Mir.Inst.Index, @intCast(self.mir_instructions.len));982 const result_index: Mir.Inst.Index = @intCast(self.mir_instructions.len);
983 self.mir_instructions.appendAssumeCapacity(inst);983 self.mir_instructions.appendAssumeCapacity(inst);
984 if (inst.tag != .pseudo or switch (inst.ops) {984 if (inst.tag != .pseudo or switch (inst.ops) {
985 else => true,985 else => true,
...@@ -1000,11 +1000,11 @@ fn addExtra(self: *Self, extra: anytype) Allocator.Error!u32 {...@@ -1000,11 +1000,11 @@ fn addExtra(self: *Self, extra: anytype) Allocator.Error!u32 {
10001000
1001fn addExtraAssumeCapacity(self: *Self, extra: anytype) u32 {1001fn addExtraAssumeCapacity(self: *Self, extra: anytype) u32 {
1002 const fields = std.meta.fields(@TypeOf(extra));1002 const fields = std.meta.fields(@TypeOf(extra));
1003 const result = @as(u32, @intCast(self.mir_extra.items.len));1003 const result: u32 = @intCast(self.mir_extra.items.len);
1004 inline for (fields) |field| {1004 inline for (fields) |field| {
1005 self.mir_extra.appendAssumeCapacity(switch (field.type) {1005 self.mir_extra.appendAssumeCapacity(switch (field.type) {
1006 u32 => @field(extra, field.name),1006 u32 => @field(extra, field.name),
1007 i32 => @as(u32, @bitCast(@field(extra, field.name))),1007 i32 => @bitCast(@field(extra, field.name)),
1008 else => @compileError("bad field type: " ++ field.name ++ ": " ++ @typeName(field.type)),1008 else => @compileError("bad field type: " ++ field.name ++ ": " ++ @typeName(field.type)),
1009 });1009 });
1010 }1010 }
...@@ -1214,8 +1214,8 @@ fn asmImmediate(self: *Self, tag: Mir.Inst.FixedTag, imm: Immediate) !void {...@@ -1214,8 +1214,8 @@ fn asmImmediate(self: *Self, tag: Mir.Inst.FixedTag, imm: Immediate) !void {
1214 .data = .{ .i = .{1214 .data = .{ .i = .{
1215 .fixes = tag[0],1215 .fixes = tag[0],
1216 .i = switch (imm) {1216 .i = switch (imm) {
1217 .signed => |s| @as(u32, @bitCast(s)),1217 .signed => |s| @bitCast(s),
1218 .unsigned => |u| @as(u32, @intCast(u)),1218 .unsigned => |u| @intCast(u),
1219 },1219 },
1220 } },1220 } },
1221 });1221 });
...@@ -1246,8 +1246,8 @@ fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm:...@@ -1246,8 +1246,8 @@ fn asmRegisterImmediate(self: *Self, tag: Mir.Inst.FixedTag, reg: Register, imm:
1246 .fixes = tag[0],1246 .fixes = tag[0],
1247 .r1 = reg,1247 .r1 = reg,
1248 .i = switch (imm) {1248 .i = switch (imm) {
1249 .signed => |s| @as(u32, @bitCast(s)),1249 .signed => |s| @bitCast(s),
1250 .unsigned => |u| @as(u32, @intCast(u)),1250 .unsigned => |u| @intCast(u),
1251 },1251 },
1252 } },1252 } },
1253 .ri64 => .{ .rx = .{1253 .ri64 => .{ .rx = .{
...@@ -1339,8 +1339,8 @@ fn asmRegisterRegisterImmediate(...@@ -1339,8 +1339,8 @@ fn asmRegisterRegisterImmediate(
1339 .r1 = reg1,1339 .r1 = reg1,
1340 .r2 = reg2,1340 .r2 = reg2,
1341 .i = switch (imm) {1341 .i = switch (imm) {
1342 .signed => |s| @as(u32, @bitCast(s)),1342 .signed => |s| @bitCast(s),
1343 .unsigned => |u| @as(u32, @intCast(u)),1343 .unsigned => |u| @intCast(u),
1344 },1344 },
1345 } },1345 } },
1346 });1346 });
...@@ -1458,7 +1458,7 @@ fn asmRegisterRegisterMemoryImmediate(...@@ -1458,7 +1458,7 @@ fn asmRegisterRegisterMemoryImmediate(
1458 .fixes = tag[0],1458 .fixes = tag[0],
1459 .r1 = reg1,1459 .r1 = reg1,
1460 .r2 = reg2,1460 .r2 = reg2,
1461 .i = @as(u8, @intCast(imm.unsigned)),1461 .i = @intCast(imm.unsigned),
1462 .payload = switch (m) {1462 .payload = switch (m) {
1463 .sib => try self.addExtra(Mir.MemorySib.encode(m)),1463 .sib => try self.addExtra(Mir.MemorySib.encode(m)),
1464 .rip => try self.addExtra(Mir.MemoryRip.encode(m)),1464 .rip => try self.addExtra(Mir.MemoryRip.encode(m)),
...@@ -1490,8 +1490,8 @@ fn asmMemoryRegister(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, reg: Regist...@@ -1490,8 +1490,8 @@ fn asmMemoryRegister(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, reg: Regist
14901490
1491fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immediate) !void {1491fn asmMemoryImmediate(self: *Self, tag: Mir.Inst.FixedTag, m: Memory, imm: Immediate) !void {
1492 const payload = try self.addExtra(Mir.Imm32{ .imm = switch (imm) {1492 const payload = try self.addExtra(Mir.Imm32{ .imm = switch (imm) {
1493 .signed => |s| @as(u32, @bitCast(s)),1493 .signed => |s| @bitCast(s),
1494 .unsigned => |u| @as(u32, @intCast(u)),1494 .unsigned => |u| @intCast(u),
1495 } });1495 } });
1496 assert(payload + 1 == switch (m) {1496 assert(payload + 1 == switch (m) {
1497 .sib => try self.addExtra(Mir.MemorySib.encode(m)),1497 .sib => try self.addExtra(Mir.MemorySib.encode(m)),
...@@ -1562,7 +1562,7 @@ fn asmMemoryRegisterImmediate(...@@ -1562,7 +1562,7 @@ fn asmMemoryRegisterImmediate(
1562 .data = .{ .rix = .{1562 .data = .{ .rix = .{
1563 .fixes = tag[0],1563 .fixes = tag[0],
1564 .r1 = reg,1564 .r1 = reg,
1565 .i = @as(u8, @intCast(imm.unsigned)),1565 .i = @intCast(imm.unsigned),
1566 .payload = switch (m) {1566 .payload = switch (m) {
1567 .sib => try self.addExtra(Mir.MemorySib.encode(m)),1567 .sib => try self.addExtra(Mir.MemorySib.encode(m)),
1568 .rip => try self.addExtra(Mir.MemoryRip.encode(m)),1568 .rip => try self.addExtra(Mir.MemoryRip.encode(m)),
...@@ -1617,7 +1617,7 @@ fn gen(self: *Self) InnerError!void {...@@ -1617,7 +1617,7 @@ fn gen(self: *Self) InnerError!void {
1617 // Eliding the reloc will cause a miscompilation in this case.1617 // Eliding the reloc will cause a miscompilation in this case.
1618 for (self.exitlude_jump_relocs.items) |jmp_reloc| {1618 for (self.exitlude_jump_relocs.items) |jmp_reloc| {
1619 self.mir_instructions.items(.data)[jmp_reloc].inst.inst =1619 self.mir_instructions.items(.data)[jmp_reloc].inst.inst =
1620 @as(u32, @intCast(self.mir_instructions.len));1620 @intCast(self.mir_instructions.len);
1621 }1621 }
16221622
1623 try self.asmPseudo(.pseudo_dbg_epilogue_begin_none);1623 try self.asmPseudo(.pseudo_dbg_epilogue_begin_none);
...@@ -1739,7 +1739,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void {...@@ -1739,7 +1739,7 @@ fn genBody(self: *Self, body: []const Air.Inst.Index) InnerError!void {
17391739
1740 for (body) |inst| {1740 for (body) |inst| {
1741 if (builtin.mode == .Debug) {1741 if (builtin.mode == .Debug) {
1742 const mir_inst = @as(Mir.Inst.Index, @intCast(self.mir_instructions.len));1742 const mir_inst: Mir.Inst.Index = @intCast(self.mir_instructions.len);
1743 try self.mir_to_air_map.put(self.gpa, mir_inst, inst);1743 try self.mir_to_air_map.put(self.gpa, mir_inst, inst);
1744 }1744 }
17451745
...@@ -2034,7 +2034,7 @@ fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void {...@@ -2034,7 +2034,7 @@ fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void {
20342034
2035 var data_off: i32 = 0;2035 var data_off: i32 = 0;
2036 for (exitlude_jump_relocs, 0..) |*exitlude_jump_reloc, index_usize| {2036 for (exitlude_jump_relocs, 0..) |*exitlude_jump_reloc, index_usize| {
2037 const index = @as(u32, @intCast(index_usize));2037 const index: u32 = @intCast(index_usize);
2038 const tag_name = mod.intern_pool.stringToSlice(enum_ty.enumFields(mod)[index_usize]);2038 const tag_name = mod.intern_pool.stringToSlice(enum_ty.enumFields(mod)[index_usize]);
2039 const tag_val = try mod.enumValueFieldIndex(enum_ty, index);2039 const tag_val = try mod.enumValueFieldIndex(enum_ty, index);
2040 const tag_mcv = try self.genTypedValue(.{ .ty = enum_ty, .val = tag_val });2040 const tag_mcv = try self.genTypedValue(.{ .ty = enum_ty, .val = tag_val });
...@@ -2052,7 +2052,7 @@ fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void {...@@ -2052,7 +2052,7 @@ fn genLazy(self: *Self, lazy_sym: link.File.LazySymbol) InnerError!void {
2052 exitlude_jump_reloc.* = try self.asmJmpReloc(undefined);2052 exitlude_jump_reloc.* = try self.asmJmpReloc(undefined);
2053 try self.performReloc(skip_reloc);2053 try self.performReloc(skip_reloc);
20542054
2055 data_off += @as(i32, @intCast(tag_name.len + 1));2055 data_off += @intCast(tag_name.len + 1);
2056 }2056 }
20572057
2058 try self.airTrap();2058 try self.airTrap();
...@@ -2169,7 +2169,7 @@ fn computeFrameLayout(self: *Self) !FrameLayout {...@@ -2169,7 +2169,7 @@ fn computeFrameLayout(self: *Self) !FrameLayout {
2169 const frame_offset = self.frame_locs.items(.disp);2169 const frame_offset = self.frame_locs.items(.disp);
21702170
2171 for (stack_frame_order, FrameIndex.named_count..) |*frame_order, frame_index|2171 for (stack_frame_order, FrameIndex.named_count..) |*frame_order, frame_index|
2172 frame_order.* = @as(FrameIndex, @enumFromInt(frame_index));2172 frame_order.* = @enumFromInt(frame_index);
2173 {2173 {
2174 const SortContext = struct {2174 const SortContext = struct {
2175 frame_align: @TypeOf(frame_align),2175 frame_align: @TypeOf(frame_align),
...@@ -2197,7 +2197,7 @@ fn computeFrameLayout(self: *Self) !FrameLayout {...@@ -2197,7 +2197,7 @@ fn computeFrameLayout(self: *Self) !FrameLayout {
2197 }2197 }
2198 }2198 }
21992199
2200 var rbp_offset = @as(i32, @intCast(save_reg_list.count() * 8));2200 var rbp_offset: i32 = @intCast(save_reg_list.count() * 8);
2201 self.setFrameLoc(.base_ptr, .rbp, &rbp_offset, false);2201 self.setFrameLoc(.base_ptr, .rbp, &rbp_offset, false);
2202 self.setFrameLoc(.ret_addr, .rbp, &rbp_offset, false);2202 self.setFrameLoc(.ret_addr, .rbp, &rbp_offset, false);
2203 self.setFrameLoc(.args_frame, .rbp, &rbp_offset, false);2203 self.setFrameLoc(.args_frame, .rbp, &rbp_offset, false);
...@@ -2212,11 +2212,11 @@ fn computeFrameLayout(self: *Self) !FrameLayout {...@@ -2212,11 +2212,11 @@ fn computeFrameLayout(self: *Self) !FrameLayout {
2212 rsp_offset = mem.alignForward(i32, rsp_offset, @as(i32, 1) << needed_align);2212 rsp_offset = mem.alignForward(i32, rsp_offset, @as(i32, 1) << needed_align);
2213 rsp_offset -= stack_frame_align_offset;2213 rsp_offset -= stack_frame_align_offset;
2214 frame_size[@intFromEnum(FrameIndex.call_frame)] =2214 frame_size[@intFromEnum(FrameIndex.call_frame)] =
2215 @as(u31, @intCast(rsp_offset - frame_offset[@intFromEnum(FrameIndex.stack_frame)]));2215 @intCast(rsp_offset - frame_offset[@intFromEnum(FrameIndex.stack_frame)]);
22162216
2217 return .{2217 return .{
2218 .stack_mask = @as(u32, math.maxInt(u32)) << (if (need_align_stack) needed_align else 0),2218 .stack_mask = @as(u32, math.maxInt(u32)) << (if (need_align_stack) needed_align else 0),
2219 .stack_adjust = @as(u32, @intCast(rsp_offset - frame_offset[@intFromEnum(FrameIndex.call_frame)])),2219 .stack_adjust = @intCast(rsp_offset - frame_offset[@intFromEnum(FrameIndex.call_frame)]),
2220 .save_reg_list = save_reg_list,2220 .save_reg_list = save_reg_list,
2221 };2221 };
2222}2222}
...@@ -2247,7 +2247,7 @@ fn allocFrameIndex(self: *Self, alloc: FrameAlloc) !FrameIndex {...@@ -2247,7 +2247,7 @@ fn allocFrameIndex(self: *Self, alloc: FrameAlloc) !FrameIndex {
2247 _ = self.free_frame_indices.swapRemoveAt(free_i);2247 _ = self.free_frame_indices.swapRemoveAt(free_i);
2248 return frame_index;2248 return frame_index;
2249 }2249 }
2250 const frame_index = @as(FrameIndex, @enumFromInt(self.frame_allocs.len));2250 const frame_index: FrameIndex = @enumFromInt(self.frame_allocs.len);
2251 try self.frame_allocs.append(self.gpa, alloc);2251 try self.frame_allocs.append(self.gpa, alloc);
2252 return frame_index;2252 return frame_index;
2253}2253}
...@@ -2323,7 +2323,7 @@ const State = struct {...@@ -2323,7 +2323,7 @@ const State = struct {
23232323
2324fn initRetroactiveState(self: *Self) State {2324fn initRetroactiveState(self: *Self) State {
2325 var state: State = undefined;2325 var state: State = undefined;
2326 state.inst_tracking_len = @as(u32, @intCast(self.inst_tracking.count()));2326 state.inst_tracking_len = @intCast(self.inst_tracking.count());
2327 state.scope_generation = self.scope_generation;2327 state.scope_generation = self.scope_generation;
2328 return state;2328 return state;
2329}2329}
...@@ -2394,9 +2394,7 @@ fn restoreState(self: *Self, state: State, deaths: []const Air.Inst.Index, compt...@@ -2394,9 +2394,7 @@ fn restoreState(self: *Self, state: State, deaths: []const Air.Inst.Index, compt
2394 self.inst_tracking.getPtr(current_inst).?.trackSpill(self, current_inst);2394 self.inst_tracking.getPtr(current_inst).?.trackSpill(self, current_inst);
2395 }2395 }
2396 {2396 {
2397 const reg = RegisterManager.regAtTrackedIndex(2397 const reg = RegisterManager.regAtTrackedIndex(@intCast(index));
2398 @as(RegisterManager.RegisterBitSet.ShiftInt, @intCast(index)),
2399 );
2400 self.register_manager.freeReg(reg);2398 self.register_manager.freeReg(reg);
2401 self.register_manager.getRegAssumeFree(reg, target_maybe_inst);2399 self.register_manager.getRegAssumeFree(reg, target_maybe_inst);
2402 }2400 }
...@@ -2630,7 +2628,7 @@ fn airIntCast(self: *Self, inst: Air.Inst.Index) !void {...@@ -2630,7 +2628,7 @@ fn airIntCast(self: *Self, inst: Air.Inst.Index) !void {
26302628
2631 const dst_ty = self.typeOfIndex(inst);2629 const dst_ty = self.typeOfIndex(inst);
2632 const dst_int_info = dst_ty.intInfo(mod);2630 const dst_int_info = dst_ty.intInfo(mod);
2633 const abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));2631 const abi_size: u32 = @intCast(dst_ty.abiSize(mod));
26342632
2635 const min_ty = if (dst_int_info.bits < src_int_info.bits) dst_ty else src_ty;2633 const min_ty = if (dst_int_info.bits < src_int_info.bits) dst_ty else src_ty;
2636 const extend = switch (src_int_info.signedness) {2634 const extend = switch (src_int_info.signedness) {
...@@ -2708,9 +2706,9 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void {...@@ -2708,9 +2706,9 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void {
2708 const ty_op = self.air.instructions.items(.data)[inst].ty_op;2706 const ty_op = self.air.instructions.items(.data)[inst].ty_op;
27092707
2710 const dst_ty = self.typeOfIndex(inst);2708 const dst_ty = self.typeOfIndex(inst);
2711 const dst_abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));2709 const dst_abi_size: u32 = @intCast(dst_ty.abiSize(mod));
2712 const src_ty = self.typeOf(ty_op.operand);2710 const src_ty = self.typeOf(ty_op.operand);
2713 const src_abi_size = @as(u32, @intCast(src_ty.abiSize(mod)));2711 const src_abi_size: u32 = @intCast(src_ty.abiSize(mod));
27142712
2715 const result = result: {2713 const result = result: {
2716 const src_mcv = try self.resolveInst(ty_op.operand);2714 const src_mcv = try self.resolveInst(ty_op.operand);
...@@ -2727,7 +2725,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void {...@@ -2727,7 +2725,7 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void {
2727 assert(src_ty.zigTypeTag(mod) == .Vector and dst_ty.vectorLen(mod) == src_ty.vectorLen(mod));2725 assert(src_ty.zigTypeTag(mod) == .Vector and dst_ty.vectorLen(mod) == src_ty.vectorLen(mod));
2728 const dst_info = dst_ty.childType(mod).intInfo(mod);2726 const dst_info = dst_ty.childType(mod).intInfo(mod);
2729 const src_info = src_ty.childType(mod).intInfo(mod);2727 const src_info = src_ty.childType(mod).intInfo(mod);
2730 const mir_tag = if (@as(?Mir.Inst.FixedTag, switch (dst_info.bits) {2728 const mir_tag = @as(?Mir.Inst.FixedTag, switch (dst_info.bits) {
2731 8 => switch (src_info.bits) {2729 8 => switch (src_info.bits) {
2732 16 => switch (dst_ty.vectorLen(mod)) {2730 16 => switch (dst_ty.vectorLen(mod)) {
2733 1...8 => if (self.hasFeature(.avx)) .{ .vp_b, .ackusw } else .{ .p_b, .ackusw },2731 1...8 => if (self.hasFeature(.avx)) .{ .vp_b, .ackusw } else .{ .p_b, .ackusw },
...@@ -2750,18 +2748,18 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void {...@@ -2750,18 +2748,18 @@ fn airTrunc(self: *Self, inst: Air.Inst.Index) !void {
2750 else => null,2748 else => null,
2751 },2749 },
2752 else => null,2750 else => null,
2753 })) |tag| tag else return self.fail("TODO implement airTrunc for {}", .{2751 }) orelse return self.fail("TODO implement airTrunc for {}", .{
2754 dst_ty.fmt(self.bin_file.options.module.?),2752 dst_ty.fmt(self.bin_file.options.module.?),
2755 });2753 });
27562754
2757 const elem_ty = src_ty.childType(mod);2755 const elem_ty = src_ty.childType(mod);
2758 const mask_val = try mod.intValue(elem_ty, @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - dst_info.bits)));2756 const mask_val = try mod.intValue(elem_ty, @as(u64, math.maxInt(u64)) >> @intCast(64 - dst_info.bits));
27592757
2760 const splat_ty = try mod.vectorType(.{2758 const splat_ty = try mod.vectorType(.{
2761 .len = @as(u32, @intCast(@divExact(@as(u64, if (src_abi_size > 16) 256 else 128), src_info.bits))),2759 .len = @intCast(@divExact(@as(u64, if (src_abi_size > 16) 256 else 128), src_info.bits)),
2762 .child = elem_ty.ip_index,2760 .child = elem_ty.ip_index,
2763 });2761 });
2764 const splat_abi_size = @as(u32, @intCast(splat_ty.abiSize(mod)));2762 const splat_abi_size: u32 = @intCast(splat_ty.abiSize(mod));
27652763
2766 const splat_val = try mod.intern(.{ .aggregate = .{2764 const splat_val = try mod.intern(.{ .aggregate = .{
2767 .ty = splat_ty.ip_index,2765 .ty = splat_ty.ip_index,
...@@ -2836,7 +2834,7 @@ fn airSlice(self: *Self, inst: Air.Inst.Index) !void {...@@ -2836,7 +2834,7 @@ fn airSlice(self: *Self, inst: Air.Inst.Index) !void {
2836 try self.genSetMem(.{ .frame = frame_index }, 0, ptr_ty, ptr);2834 try self.genSetMem(.{ .frame = frame_index }, 0, ptr_ty, ptr);
2837 try self.genSetMem(2835 try self.genSetMem(
2838 .{ .frame = frame_index },2836 .{ .frame = frame_index },
2839 @as(i32, @intCast(ptr_ty.abiSize(mod))),2837 @intCast(ptr_ty.abiSize(mod)),
2840 len_ty,2838 len_ty,
2841 len,2839 len,
2842 );2840 );
...@@ -2970,7 +2968,7 @@ fn airAddSat(self: *Self, inst: Air.Inst.Index) !void {...@@ -2970,7 +2968,7 @@ fn airAddSat(self: *Self, inst: Air.Inst.Index) !void {
2970 try self.genSetReg(limit_reg, ty, dst_mcv);2968 try self.genSetReg(limit_reg, ty, dst_mcv);
2971 try self.genShiftBinOpMir(.{ ._r, .sa }, ty, limit_mcv, .{ .immediate = reg_bits - 1 });2969 try self.genShiftBinOpMir(.{ ._r, .sa }, ty, limit_mcv, .{ .immediate = reg_bits - 1 });
2972 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, .{2970 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, .{
2973 .immediate = (@as(u64, 1) << @as(u6, @intCast(reg_bits - 1))) - 1,2971 .immediate = (@as(u64, 1) << @intCast(reg_bits - 1)) - 1,
2974 });2972 });
2975 if (reg_extra_bits > 0) {2973 if (reg_extra_bits > 0) {
2976 const shifted_rhs_reg = try self.copyToTmpRegister(ty, rhs_mcv);2974 const shifted_rhs_reg = try self.copyToTmpRegister(ty, rhs_mcv);
...@@ -2989,7 +2987,7 @@ fn airAddSat(self: *Self, inst: Air.Inst.Index) !void {...@@ -2989,7 +2987,7 @@ fn airAddSat(self: *Self, inst: Air.Inst.Index) !void {
2989 break :cc .o;2987 break :cc .o;
2990 } else cc: {2988 } else cc: {
2991 try self.genSetReg(limit_reg, ty, .{2989 try self.genSetReg(limit_reg, ty, .{
2992 .immediate = @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - ty.bitSize(mod))),2990 .immediate = @as(u64, math.maxInt(u64)) >> @intCast(64 - ty.bitSize(mod)),
2993 });2991 });
29942992
2995 try self.genBinOpMir(.{ ._, .add }, ty, dst_mcv, rhs_mcv);2993 try self.genBinOpMir(.{ ._, .add }, ty, dst_mcv, rhs_mcv);
...@@ -3053,7 +3051,7 @@ fn airSubSat(self: *Self, inst: Air.Inst.Index) !void {...@@ -3053,7 +3051,7 @@ fn airSubSat(self: *Self, inst: Air.Inst.Index) !void {
3053 try self.genSetReg(limit_reg, ty, dst_mcv);3051 try self.genSetReg(limit_reg, ty, dst_mcv);
3054 try self.genShiftBinOpMir(.{ ._r, .sa }, ty, limit_mcv, .{ .immediate = reg_bits - 1 });3052 try self.genShiftBinOpMir(.{ ._r, .sa }, ty, limit_mcv, .{ .immediate = reg_bits - 1 });
3055 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, .{3053 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, .{
3056 .immediate = (@as(u64, 1) << @as(u6, @intCast(reg_bits - 1))) - 1,3054 .immediate = (@as(u64, 1) << @intCast(reg_bits - 1)) - 1,
3057 });3055 });
3058 if (reg_extra_bits > 0) {3056 if (reg_extra_bits > 0) {
3059 const shifted_rhs_reg = try self.copyToTmpRegister(ty, rhs_mcv);3057 const shifted_rhs_reg = try self.copyToTmpRegister(ty, rhs_mcv);
...@@ -3128,12 +3126,12 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void {...@@ -3128,12 +3126,12 @@ fn airMulSat(self: *Self, inst: Air.Inst.Index) !void {
3128 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, rhs_mcv);3126 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, rhs_mcv);
3129 try self.genShiftBinOpMir(.{ ._, .sa }, ty, limit_mcv, .{ .immediate = reg_bits - 1 });3127 try self.genShiftBinOpMir(.{ ._, .sa }, ty, limit_mcv, .{ .immediate = reg_bits - 1 });
3130 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, .{3128 try self.genBinOpMir(.{ ._, .xor }, ty, limit_mcv, .{
3131 .immediate = (@as(u64, 1) << @as(u6, @intCast(reg_bits - 1))) - 1,3129 .immediate = (@as(u64, 1) << @intCast(reg_bits - 1)) - 1,
3132 });3130 });
3133 break :cc .o;3131 break :cc .o;
3134 } else cc: {3132 } else cc: {
3135 try self.genSetReg(limit_reg, ty, .{3133 try self.genSetReg(limit_reg, ty, .{
3136 .immediate = @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - reg_bits)),3134 .immediate = @as(u64, math.maxInt(u64)) >> @intCast(64 - reg_bits),
3137 });3135 });
3138 break :cc .c;3136 break :cc .c;
3139 };3137 };
...@@ -3186,13 +3184,13 @@ fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index) !void {...@@ -3186,13 +3184,13 @@ fn airAddSubWithOverflow(self: *Self, inst: Air.Inst.Index) !void {
3186 try self.allocFrameIndex(FrameAlloc.initType(tuple_ty, mod));3184 try self.allocFrameIndex(FrameAlloc.initType(tuple_ty, mod));
3187 try self.genSetMem(3185 try self.genSetMem(
3188 .{ .frame = frame_index },3186 .{ .frame = frame_index },
3189 @as(i32, @intCast(tuple_ty.structFieldOffset(1, mod))),3187 @intCast(tuple_ty.structFieldOffset(1, mod)),
3190 Type.u1,3188 Type.u1,
3191 .{ .eflags = cc },3189 .{ .eflags = cc },
3192 );3190 );
3193 try self.genSetMem(3191 try self.genSetMem(
3194 .{ .frame = frame_index },3192 .{ .frame = frame_index },
3195 @as(i32, @intCast(tuple_ty.structFieldOffset(0, mod))),3193 @intCast(tuple_ty.structFieldOffset(0, mod)),
3196 ty,3194 ty,
3197 partial_mcv,3195 partial_mcv,
3198 );3196 );
...@@ -3259,13 +3257,13 @@ fn airShlWithOverflow(self: *Self, inst: Air.Inst.Index) !void {...@@ -3259,13 +3257,13 @@ fn airShlWithOverflow(self: *Self, inst: Air.Inst.Index) !void {
3259 try self.allocFrameIndex(FrameAlloc.initType(tuple_ty, mod));3257 try self.allocFrameIndex(FrameAlloc.initType(tuple_ty, mod));
3260 try self.genSetMem(3258 try self.genSetMem(
3261 .{ .frame = frame_index },3259 .{ .frame = frame_index },
3262 @as(i32, @intCast(tuple_ty.structFieldOffset(1, mod))),3260 @intCast(tuple_ty.structFieldOffset(1, mod)),
3263 tuple_ty.structFieldType(1, mod),3261 tuple_ty.structFieldType(1, mod),
3264 .{ .eflags = cc },3262 .{ .eflags = cc },
3265 );3263 );
3266 try self.genSetMem(3264 try self.genSetMem(
3267 .{ .frame = frame_index },3265 .{ .frame = frame_index },
3268 @as(i32, @intCast(tuple_ty.structFieldOffset(0, mod))),3266 @intCast(tuple_ty.structFieldOffset(0, mod)),
3269 tuple_ty.structFieldType(0, mod),3267 tuple_ty.structFieldType(0, mod),
3270 partial_mcv,3268 partial_mcv,
3271 );3269 );
...@@ -3333,7 +3331,7 @@ fn genSetFrameTruncatedOverflowCompare(...@@ -3333,7 +3331,7 @@ fn genSetFrameTruncatedOverflowCompare(
3333 );3331 );
3334 }3332 }
33353333
3336 const payload_off = @as(i32, @intCast(tuple_ty.structFieldOffset(0, mod)));3334 const payload_off: i32 = @intCast(tuple_ty.structFieldOffset(0, mod));
3337 if (hi_limb_off > 0) try self.genSetMem(.{ .frame = frame_index }, payload_off, rest_ty, src_mcv);3335 if (hi_limb_off > 0) try self.genSetMem(.{ .frame = frame_index }, payload_off, rest_ty, src_mcv);
3338 try self.genSetMem(3336 try self.genSetMem(
3339 .{ .frame = frame_index },3337 .{ .frame = frame_index },
...@@ -3343,7 +3341,7 @@ fn genSetFrameTruncatedOverflowCompare(...@@ -3343,7 +3341,7 @@ fn genSetFrameTruncatedOverflowCompare(
3343 );3341 );
3344 try self.genSetMem(3342 try self.genSetMem(
3345 .{ .frame = frame_index },3343 .{ .frame = frame_index },
3346 @as(i32, @intCast(tuple_ty.structFieldOffset(1, mod))),3344 @intCast(tuple_ty.structFieldOffset(1, mod)),
3347 tuple_ty.structFieldType(1, mod),3345 tuple_ty.structFieldType(1, mod),
3348 if (overflow_cc) |_| .{ .register = overflow_reg.to8() } else .{ .eflags = .ne },3346 if (overflow_cc) |_| .{ .register = overflow_reg.to8() } else .{ .eflags = .ne },
3349 );3347 );
...@@ -3400,13 +3398,13 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void {...@@ -3400,13 +3398,13 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void {
3400 if (dst_info.bits >= lhs_active_bits + rhs_active_bits) {3398 if (dst_info.bits >= lhs_active_bits + rhs_active_bits) {
3401 try self.genSetMem(3399 try self.genSetMem(
3402 .{ .frame = frame_index },3400 .{ .frame = frame_index },
3403 @as(i32, @intCast(tuple_ty.structFieldOffset(0, mod))),3401 @intCast(tuple_ty.structFieldOffset(0, mod)),
3404 tuple_ty.structFieldType(0, mod),3402 tuple_ty.structFieldType(0, mod),
3405 partial_mcv,3403 partial_mcv,
3406 );3404 );
3407 try self.genSetMem(3405 try self.genSetMem(
3408 .{ .frame = frame_index },3406 .{ .frame = frame_index },
3409 @as(i32, @intCast(tuple_ty.structFieldOffset(1, mod))),3407 @intCast(tuple_ty.structFieldOffset(1, mod)),
3410 tuple_ty.structFieldType(1, mod),3408 tuple_ty.structFieldType(1, mod),
3411 .{ .immediate = 0 }, // cc being set is impossible3409 .{ .immediate = 0 }, // cc being set is impossible
3412 );3410 );
...@@ -3430,7 +3428,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void {...@@ -3430,7 +3428,7 @@ fn airMulWithOverflow(self: *Self, inst: Air.Inst.Index) !void {
3430/// Quotient is saved in .rax and remainder in .rdx.3428/// Quotient is saved in .rax and remainder in .rdx.
3431fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue, rhs: MCValue) !void {3429fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue, rhs: MCValue) !void {
3432 const mod = self.bin_file.options.module.?;3430 const mod = self.bin_file.options.module.?;
3433 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));3431 const abi_size: u32 = @intCast(ty.abiSize(mod));
3434 if (abi_size > 8) {3432 if (abi_size > 8) {
3435 return self.fail("TODO implement genIntMulDivOpMir for ABI size larger than 8", .{});3433 return self.fail("TODO implement genIntMulDivOpMir for ABI size larger than 8", .{});
3436 }3434 }
...@@ -3470,7 +3468,7 @@ fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue...@@ -3470,7 +3468,7 @@ fn genIntMulDivOpMir(self: *Self, tag: Mir.Inst.FixedTag, ty: Type, lhs: MCValue
3470/// Clobbers .rax and .rdx registers.3468/// Clobbers .rax and .rdx registers.
3471fn genInlineIntDivFloor(self: *Self, ty: Type, lhs: MCValue, rhs: MCValue) !MCValue {3469fn genInlineIntDivFloor(self: *Self, ty: Type, lhs: MCValue, rhs: MCValue) !MCValue {
3472 const mod = self.bin_file.options.module.?;3470 const mod = self.bin_file.options.module.?;
3473 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));3471 const abi_size: u32 = @intCast(ty.abiSize(mod));
3474 const int_info = ty.intInfo(mod);3472 const int_info = ty.intInfo(mod);
3475 const dividend: Register = switch (lhs) {3473 const dividend: Register = switch (lhs) {
3476 .register => |reg| reg,3474 .register => |reg| reg,
...@@ -3609,7 +3607,7 @@ fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void {...@@ -3609,7 +3607,7 @@ fn airOptionalPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void {
3609 try self.copyToRegisterWithInstTracking(inst, dst_ty, src_mcv);3607 try self.copyToRegisterWithInstTracking(inst, dst_ty, src_mcv);
36103608
3611 const pl_ty = dst_ty.childType(mod);3609 const pl_ty = dst_ty.childType(mod);
3612 const pl_abi_size = @as(i32, @intCast(pl_ty.abiSize(mod)));3610 const pl_abi_size: i32 = @intCast(pl_ty.abiSize(mod));
3613 try self.genSetMem(.{ .reg = dst_mcv.getReg().? }, pl_abi_size, Type.bool, .{ .immediate = 1 });3611 try self.genSetMem(.{ .reg = dst_mcv.getReg().? }, pl_abi_size, Type.bool, .{ .immediate = 1 });
3614 break :result if (self.liveness.isUnused(inst)) .unreach else dst_mcv;3612 break :result if (self.liveness.isUnused(inst)) .unreach else dst_mcv;
3615 };3613 };
...@@ -3641,17 +3639,12 @@ fn airUnwrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void {...@@ -3641,17 +3639,12 @@ fn airUnwrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void {
3641 defer if (eu_lock) |lock| self.register_manager.unlockReg(lock);3639 defer if (eu_lock) |lock| self.register_manager.unlockReg(lock);
36423640
3643 const result = try self.copyToRegisterWithInstTracking(inst, err_union_ty, operand);3641 const result = try self.copyToRegisterWithInstTracking(inst, err_union_ty, operand);
3644 if (err_off > 0) {3642 if (err_off > 0) try self.genShiftBinOpMir(
3645 const shift = @as(u6, @intCast(err_off * 8));3643 .{ ._r, .sh },
3646 try self.genShiftBinOpMir(3644 err_union_ty,
3647 .{ ._r, .sh },3645 result,
3648 err_union_ty,3646 .{ .immediate = @as(u6, @intCast(err_off * 8)) },
3649 result,3647 ) else try self.truncateRegister(Type.anyerror, result.register);
3650 .{ .immediate = shift },
3651 );
3652 } else {
3653 try self.truncateRegister(Type.anyerror, result.register);
3654 }
3655 break :result result;3648 break :result result;
3656 },3649 },
3657 .load_frame => |frame_addr| break :result .{ .load_frame = .{3650 .load_frame => |frame_addr| break :result .{ .load_frame = .{
...@@ -3699,17 +3692,12 @@ fn genUnwrapErrorUnionPayloadMir(...@@ -3699,17 +3692,12 @@ fn genUnwrapErrorUnionPayloadMir(
3699 try self.copyToRegisterWithInstTracking(inst, err_union_ty, err_union)3692 try self.copyToRegisterWithInstTracking(inst, err_union_ty, err_union)
3700 else3693 else
3701 .{ .register = try self.copyToTmpRegister(err_union_ty, err_union) };3694 .{ .register = try self.copyToTmpRegister(err_union_ty, err_union) };
3702 if (payload_off > 0) {3695 if (payload_off > 0) try self.genShiftBinOpMir(
3703 const shift = @as(u6, @intCast(payload_off * 8));3696 .{ ._r, .sh },
3704 try self.genShiftBinOpMir(3697 err_union_ty,
3705 .{ ._r, .sh },3698 result_mcv,
3706 err_union_ty,3699 .{ .immediate = @as(u6, @intCast(payload_off * 8)) },
3707 result_mcv,3700 ) else try self.truncateRegister(payload_ty, result_mcv.register);
3708 .{ .immediate = shift },
3709 );
3710 } else {
3711 try self.truncateRegister(payload_ty, result_mcv.register);
3712 }
3713 break :result result_mcv;3701 break :result result_mcv;
3714 },3702 },
3715 else => return self.fail("TODO implement genUnwrapErrorUnionPayloadMir for {}", .{err_union}),3703 else => return self.fail("TODO implement genUnwrapErrorUnionPayloadMir for {}", .{err_union}),
...@@ -3741,8 +3729,8 @@ fn airUnwrapErrUnionErrPtr(self: *Self, inst: Air.Inst.Index) !void {...@@ -3741,8 +3729,8 @@ fn airUnwrapErrUnionErrPtr(self: *Self, inst: Air.Inst.Index) !void {
3741 const eu_ty = src_ty.childType(mod);3729 const eu_ty = src_ty.childType(mod);
3742 const pl_ty = eu_ty.errorUnionPayload(mod);3730 const pl_ty = eu_ty.errorUnionPayload(mod);
3743 const err_ty = eu_ty.errorUnionSet(mod);3731 const err_ty = eu_ty.errorUnionSet(mod);
3744 const err_off = @as(i32, @intCast(errUnionErrorOffset(pl_ty, mod)));3732 const err_off: i32 = @intCast(errUnionErrorOffset(pl_ty, mod));
3745 const err_abi_size = @as(u32, @intCast(err_ty.abiSize(mod)));3733 const err_abi_size: u32 = @intCast(err_ty.abiSize(mod));
3746 try self.asmRegisterMemory(3734 try self.asmRegisterMemory(
3747 .{ ._, .mov },3735 .{ ._, .mov },
3748 registerAlias(dst_reg, err_abi_size),3736 registerAlias(dst_reg, err_abi_size),
...@@ -3780,8 +3768,8 @@ fn airUnwrapErrUnionPayloadPtr(self: *Self, inst: Air.Inst.Index) !void {...@@ -3780,8 +3768,8 @@ fn airUnwrapErrUnionPayloadPtr(self: *Self, inst: Air.Inst.Index) !void {
37803768
3781 const eu_ty = src_ty.childType(mod);3769 const eu_ty = src_ty.childType(mod);
3782 const pl_ty = eu_ty.errorUnionPayload(mod);3770 const pl_ty = eu_ty.errorUnionPayload(mod);
3783 const pl_off = @as(i32, @intCast(errUnionPayloadOffset(pl_ty, mod)));3771 const pl_off: i32 = @intCast(errUnionPayloadOffset(pl_ty, mod));
3784 const dst_abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));3772 const dst_abi_size: u32 = @intCast(dst_ty.abiSize(mod));
3785 try self.asmRegisterMemory(3773 try self.asmRegisterMemory(
3786 .{ ._, .lea },3774 .{ ._, .lea },
3787 registerAlias(dst_reg, dst_abi_size),3775 registerAlias(dst_reg, dst_abi_size),
...@@ -3807,8 +3795,8 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void {...@@ -3807,8 +3795,8 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void {
3807 const eu_ty = src_ty.childType(mod);3795 const eu_ty = src_ty.childType(mod);
3808 const pl_ty = eu_ty.errorUnionPayload(mod);3796 const pl_ty = eu_ty.errorUnionPayload(mod);
3809 const err_ty = eu_ty.errorUnionSet(mod);3797 const err_ty = eu_ty.errorUnionSet(mod);
3810 const err_off = @as(i32, @intCast(errUnionErrorOffset(pl_ty, mod)));3798 const err_off: i32 = @intCast(errUnionErrorOffset(pl_ty, mod));
3811 const err_abi_size = @as(u32, @intCast(err_ty.abiSize(mod)));3799 const err_abi_size: u32 = @intCast(err_ty.abiSize(mod));
3812 try self.asmMemoryImmediate(3800 try self.asmMemoryImmediate(
3813 .{ ._, .mov },3801 .{ ._, .mov },
3814 Memory.sib(Memory.PtrSize.fromSize(err_abi_size), .{3802 Memory.sib(Memory.PtrSize.fromSize(err_abi_size), .{
...@@ -3828,8 +3816,8 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void {...@@ -3828,8 +3816,8 @@ fn airErrUnionPayloadPtrSet(self: *Self, inst: Air.Inst.Index) !void {
3828 const dst_lock = self.register_manager.lockReg(dst_reg);3816 const dst_lock = self.register_manager.lockReg(dst_reg);
3829 defer if (dst_lock) |lock| self.register_manager.unlockReg(lock);3817 defer if (dst_lock) |lock| self.register_manager.unlockReg(lock);
38303818
3831 const pl_off = @as(i32, @intCast(errUnionPayloadOffset(pl_ty, mod)));3819 const pl_off: i32 = @intCast(errUnionPayloadOffset(pl_ty, mod));
3832 const dst_abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));3820 const dst_abi_size: u32 = @intCast(dst_ty.abiSize(mod));
3833 try self.asmRegisterMemory(3821 try self.asmRegisterMemory(
3834 .{ ._, .lea },3822 .{ ._, .lea },
3835 registerAlias(dst_reg, dst_abi_size),3823 registerAlias(dst_reg, dst_abi_size),
...@@ -3878,7 +3866,7 @@ fn airWrapOptional(self: *Self, inst: Air.Inst.Index) !void {...@@ -3878,7 +3866,7 @@ fn airWrapOptional(self: *Self, inst: Air.Inst.Index) !void {
3878 try self.genCopy(pl_ty, opt_mcv, pl_mcv);3866 try self.genCopy(pl_ty, opt_mcv, pl_mcv);
38793867
3880 if (!same_repr) {3868 if (!same_repr) {
3881 const pl_abi_size = @as(i32, @intCast(pl_ty.abiSize(mod)));3869 const pl_abi_size: i32 = @intCast(pl_ty.abiSize(mod));
3882 switch (opt_mcv) {3870 switch (opt_mcv) {
3883 else => unreachable,3871 else => unreachable,
38843872
...@@ -3917,8 +3905,8 @@ fn airWrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void {...@@ -3917,8 +3905,8 @@ fn airWrapErrUnionPayload(self: *Self, inst: Air.Inst.Index) !void {
3917 if (!pl_ty.hasRuntimeBitsIgnoreComptime(mod)) break :result .{ .immediate = 0 };3905 if (!pl_ty.hasRuntimeBitsIgnoreComptime(mod)) break :result .{ .immediate = 0 };
39183906
3919 const frame_index = try self.allocFrameIndex(FrameAlloc.initType(eu_ty, mod));3907 const frame_index = try self.allocFrameIndex(FrameAlloc.initType(eu_ty, mod));
3920 const pl_off = @as(i32, @intCast(errUnionPayloadOffset(pl_ty, mod)));3908 const pl_off: i32 = @intCast(errUnionPayloadOffset(pl_ty, mod));
3921 const err_off = @as(i32, @intCast(errUnionErrorOffset(pl_ty, mod)));3909 const err_off: i32 = @intCast(errUnionErrorOffset(pl_ty, mod));
3922 try self.genSetMem(.{ .frame = frame_index }, pl_off, pl_ty, operand);3910 try self.genSetMem(.{ .frame = frame_index }, pl_off, pl_ty, operand);
3923 try self.genSetMem(.{ .frame = frame_index }, err_off, err_ty, .{ .immediate = 0 });3911 try self.genSetMem(.{ .frame = frame_index }, err_off, err_ty, .{ .immediate = 0 });
3924 break :result .{ .load_frame = .{ .index = frame_index } };3912 break :result .{ .load_frame = .{ .index = frame_index } };
...@@ -3939,8 +3927,8 @@ fn airWrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void {...@@ -3939,8 +3927,8 @@ fn airWrapErrUnionErr(self: *Self, inst: Air.Inst.Index) !void {
3939 if (!pl_ty.hasRuntimeBitsIgnoreComptime(mod)) break :result try self.resolveInst(ty_op.operand);3927 if (!pl_ty.hasRuntimeBitsIgnoreComptime(mod)) break :result try self.resolveInst(ty_op.operand);
39403928
3941 const frame_index = try self.allocFrameIndex(FrameAlloc.initType(eu_ty, mod));3929 const frame_index = try self.allocFrameIndex(FrameAlloc.initType(eu_ty, mod));
3942 const pl_off = @as(i32, @intCast(errUnionPayloadOffset(pl_ty, mod)));3930 const pl_off: i32 = @intCast(errUnionPayloadOffset(pl_ty, mod));
3943 const err_off = @as(i32, @intCast(errUnionErrorOffset(pl_ty, mod)));3931 const err_off: i32 = @intCast(errUnionErrorOffset(pl_ty, mod));
3944 try self.genSetMem(.{ .frame = frame_index }, pl_off, pl_ty, .undef);3932 try self.genSetMem(.{ .frame = frame_index }, pl_off, pl_ty, .undef);
3945 const operand = try self.resolveInst(ty_op.operand);3933 const operand = try self.resolveInst(ty_op.operand);
3946 try self.genSetMem(.{ .frame = frame_index }, err_off, err_ty, operand);3934 try self.genSetMem(.{ .frame = frame_index }, err_off, err_ty, operand);
...@@ -4002,7 +3990,7 @@ fn airPtrSliceLenPtr(self: *Self, inst: Air.Inst.Index) !void {...@@ -4002,7 +3990,7 @@ fn airPtrSliceLenPtr(self: *Self, inst: Air.Inst.Index) !void {
4002 const dst_lock = self.register_manager.lockReg(dst_reg);3990 const dst_lock = self.register_manager.lockReg(dst_reg);
4003 defer if (dst_lock) |lock| self.register_manager.unlockReg(lock);3991 defer if (dst_lock) |lock| self.register_manager.unlockReg(lock);
40043992
4005 const dst_abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));3993 const dst_abi_size: u32 = @intCast(dst_ty.abiSize(mod));
4006 try self.asmRegisterMemory(3994 try self.asmRegisterMemory(
4007 .{ ._, .lea },3995 .{ ._, .lea },
4008 registerAlias(dst_reg, dst_abi_size),3996 registerAlias(dst_reg, dst_abi_size),
...@@ -4179,7 +4167,7 @@ fn airPtrElemVal(self: *Self, inst: Air.Inst.Index) !void {...@@ -4179,7 +4167,7 @@ fn airPtrElemVal(self: *Self, inst: Air.Inst.Index) !void {
4179 // additional `mov` is needed at the end to get the actual value4167 // additional `mov` is needed at the end to get the actual value
41804168
4181 const elem_ty = ptr_ty.elemType2(mod);4169 const elem_ty = ptr_ty.elemType2(mod);
4182 const elem_abi_size = @as(u32, @intCast(elem_ty.abiSize(mod)));4170 const elem_abi_size: u32 = @intCast(elem_ty.abiSize(mod));
4183 const index_ty = self.typeOf(bin_op.rhs);4171 const index_ty = self.typeOf(bin_op.rhs);
4184 const index_mcv = try self.resolveInst(bin_op.rhs);4172 const index_mcv = try self.resolveInst(bin_op.rhs);
4185 const index_lock = switch (index_mcv) {4173 const index_lock = switch (index_mcv) {
...@@ -4319,7 +4307,7 @@ fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void {...@@ -4319,7 +4307,7 @@ fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void {
4319 .load_frame => |frame_addr| {4307 .load_frame => |frame_addr| {
4320 if (tag_abi_size <= 8) {4308 if (tag_abi_size <= 8) {
4321 const off: i32 = if (layout.tag_align < layout.payload_align)4309 const off: i32 = if (layout.tag_align < layout.payload_align)
4322 @as(i32, @intCast(layout.payload_size))4310 @intCast(layout.payload_size)
4323 else4311 else
4324 0;4312 0;
4325 break :blk try self.copyToRegisterWithInstTracking(inst, tag_ty, .{4313 break :blk try self.copyToRegisterWithInstTracking(inst, tag_ty, .{
...@@ -4331,13 +4319,13 @@ fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void {...@@ -4331,13 +4319,13 @@ fn airGetUnionTag(self: *Self, inst: Air.Inst.Index) !void {
4331 },4319 },
4332 .register => {4320 .register => {
4333 const shift: u6 = if (layout.tag_align < layout.payload_align)4321 const shift: u6 = if (layout.tag_align < layout.payload_align)
4334 @as(u6, @intCast(layout.payload_size * 8))4322 @intCast(layout.payload_size * 8)
4335 else4323 else
4336 0;4324 0;
4337 const result = try self.copyToRegisterWithInstTracking(inst, union_ty, operand);4325 const result = try self.copyToRegisterWithInstTracking(inst, union_ty, operand);
4338 try self.genShiftBinOpMir(.{ ._r, .sh }, Type.usize, result, .{ .immediate = shift });4326 try self.genShiftBinOpMir(.{ ._r, .sh }, Type.usize, result, .{ .immediate = shift });
4339 break :blk MCValue{4327 break :blk MCValue{
4340 .register = registerAlias(result.register, @as(u32, @intCast(layout.tag_size))),4328 .register = registerAlias(result.register, @intCast(layout.tag_size)),
4341 };4329 };
4342 },4330 },
4343 else => return self.fail("TODO implement get_union_tag for {}", .{operand}),4331 else => return self.fail("TODO implement get_union_tag for {}", .{operand}),
...@@ -4447,7 +4435,7 @@ fn airClz(self: *Self, inst: Air.Inst.Index) !void {...@@ -4447,7 +4435,7 @@ fn airClz(self: *Self, inst: Air.Inst.Index) !void {
4447 try self.genBinOpMir(.{ ._, .xor }, dst_ty, dst_mcv, .{ .immediate = src_bits - 1 });4435 try self.genBinOpMir(.{ ._, .xor }, dst_ty, dst_mcv, .{ .immediate = src_bits - 1 });
4448 } else {4436 } else {
4449 const imm_reg = try self.copyToTmpRegister(dst_ty, .{4437 const imm_reg = try self.copyToTmpRegister(dst_ty, .{
4450 .immediate = @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - self.regBitSize(dst_ty))),4438 .immediate = @as(u64, math.maxInt(u64)) >> @intCast(64 - self.regBitSize(dst_ty)),
4451 });4439 });
4452 const imm_lock = self.register_manager.lockRegAssumeUnused(imm_reg);4440 const imm_lock = self.register_manager.lockRegAssumeUnused(imm_reg);
4453 defer self.register_manager.unlockReg(imm_lock);4441 defer self.register_manager.unlockReg(imm_lock);
...@@ -4518,8 +4506,8 @@ fn airCtz(self: *Self, inst: Air.Inst.Index) !void {...@@ -4518,8 +4506,8 @@ fn airCtz(self: *Self, inst: Air.Inst.Index) !void {
4518 .{ ._, .@"or" },4506 .{ ._, .@"or" },
4519 wide_ty,4507 wide_ty,
4520 tmp_mcv,4508 tmp_mcv,
4521 .{ .immediate = (@as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - extra_bits))) <<4509 .{ .immediate = (@as(u64, math.maxInt(u64)) >> @intCast(64 - extra_bits)) <<
4522 @as(u6, @intCast(src_bits)) },4510 @intCast(src_bits) },
4523 );4511 );
4524 break :masked tmp_mcv;4512 break :masked tmp_mcv;
4525 } else mat_src_mcv;4513 } else mat_src_mcv;
...@@ -4536,7 +4524,7 @@ fn airCtz(self: *Self, inst: Air.Inst.Index) !void {...@@ -4536,7 +4524,7 @@ fn airCtz(self: *Self, inst: Air.Inst.Index) !void {
4536 .{ ._, .@"or" },4524 .{ ._, .@"or" },
4537 Type.u64,4525 Type.u64,
4538 dst_mcv,4526 dst_mcv,
4539 .{ .immediate = @as(u64, math.maxInt(u64)) << @as(u6, @intCast(src_bits - 64)) },4527 .{ .immediate = @as(u64, math.maxInt(u64)) << @intCast(src_bits - 64) },
4540 );4528 );
4541 break :masked dst_mcv;4529 break :masked dst_mcv;
4542 } else mat_src_mcv.address().offset(8).deref();4530 } else mat_src_mcv.address().offset(8).deref();
...@@ -4607,7 +4595,7 @@ fn airPopcount(self: *Self, inst: Air.Inst.Index) !void {...@@ -4607,7 +4595,7 @@ fn airPopcount(self: *Self, inst: Air.Inst.Index) !void {
4607 break :result dst_mcv;4595 break :result dst_mcv;
4608 }4596 }
46094597
4610 const mask = @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - src_abi_size * 8));4598 const mask = @as(u64, math.maxInt(u64)) >> @intCast(64 - src_abi_size * 8);
4611 const imm_0_1 = Immediate.u(mask / 0b1_1);4599 const imm_0_1 = Immediate.u(mask / 0b1_1);
4612 const imm_00_11 = Immediate.u(mask / 0b01_01);4600 const imm_00_11 = Immediate.u(mask / 0b01_01);
4613 const imm_0000_1111 = Immediate.u(mask / 0b0001_0001);4601 const imm_0000_1111 = Immediate.u(mask / 0b0001_0001);
...@@ -4780,7 +4768,7 @@ fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void {...@@ -4780,7 +4768,7 @@ fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void {
4780 const ty_op = self.air.instructions.items(.data)[inst].ty_op;4768 const ty_op = self.air.instructions.items(.data)[inst].ty_op;
47814769
4782 const src_ty = self.typeOf(ty_op.operand);4770 const src_ty = self.typeOf(ty_op.operand);
4783 const src_abi_size = @as(u32, @intCast(src_ty.abiSize(mod)));4771 const src_abi_size: u32 = @intCast(src_ty.abiSize(mod));
4784 const src_mcv = try self.resolveInst(ty_op.operand);4772 const src_mcv = try self.resolveInst(ty_op.operand);
47854773
4786 const dst_mcv = try self.byteSwap(inst, src_ty, src_mcv, false);4774 const dst_mcv = try self.byteSwap(inst, src_ty, src_mcv, false);
...@@ -4800,7 +4788,7 @@ fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void {...@@ -4800,7 +4788,7 @@ fn airBitReverse(self: *Self, inst: Air.Inst.Index) !void {
4800 else4788 else
4801 undefined;4789 undefined;
48024790
4803 const mask = @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - src_abi_size * 8));4791 const mask = @as(u64, math.maxInt(u64)) >> @intCast(64 - src_abi_size * 8);
4804 const imm_0000_1111 = Immediate.u(mask / 0b0001_0001);4792 const imm_0000_1111 = Immediate.u(mask / 0b0001_0001);
4805 const imm_00_11 = Immediate.u(mask / 0b01_01);4793 const imm_00_11 = Immediate.u(mask / 0b01_01);
4806 const imm_0_1 = Immediate.u(mask / 0b1_1);4794 const imm_0_1 = Immediate.u(mask / 0b1_1);
...@@ -5016,7 +5004,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: u4...@@ -5016,7 +5004,7 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: u4
5016 if (!self.hasFeature(.sse4_1))5004 if (!self.hasFeature(.sse4_1))
5017 return self.fail("TODO implement genRound without sse4_1 feature", .{});5005 return self.fail("TODO implement genRound without sse4_1 feature", .{});
50185006
5019 const mir_tag = if (@as(?Mir.Inst.FixedTag, switch (ty.zigTypeTag(mod)) {5007 const mir_tag = @as(?Mir.Inst.FixedTag, switch (ty.zigTypeTag(mod)) {
5020 .Float => switch (ty.floatBits(self.target.*)) {5008 .Float => switch (ty.floatBits(self.target.*)) {
5021 32 => if (self.hasFeature(.avx)) .{ .v_ss, .round } else .{ ._ss, .round },5009 32 => if (self.hasFeature(.avx)) .{ .v_ss, .round } else .{ ._ss, .round },
5022 64 => if (self.hasFeature(.avx)) .{ .v_sd, .round } else .{ ._sd, .round },5010 64 => if (self.hasFeature(.avx)) .{ .v_sd, .round } else .{ ._sd, .round },
...@@ -5043,10 +5031,10 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: u4...@@ -5043,10 +5031,10 @@ fn genRound(self: *Self, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: u4
5043 else => null,5031 else => null,
5044 },5032 },
5045 else => unreachable,5033 else => unreachable,
5046 })) |tag| tag else return self.fail("TODO implement genRound for {}", .{5034 }) orelse return self.fail("TODO implement genRound for {}", .{
5047 ty.fmt(self.bin_file.options.module.?),5035 ty.fmt(self.bin_file.options.module.?),
5048 });5036 });
5049 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));5037 const abi_size: u32 = @intCast(ty.abiSize(mod));
5050 const dst_alias = registerAlias(dst_reg, abi_size);5038 const dst_alias = registerAlias(dst_reg, abi_size);
5051 switch (mir_tag[0]) {5039 switch (mir_tag[0]) {
5052 .v_ss, .v_sd => if (src_mcv.isMemory()) try self.asmRegisterRegisterMemoryImmediate(5040 .v_ss, .v_sd => if (src_mcv.isMemory()) try self.asmRegisterRegisterMemoryImmediate(
...@@ -5086,7 +5074,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {...@@ -5086,7 +5074,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {
5086 const mod = self.bin_file.options.module.?;5074 const mod = self.bin_file.options.module.?;
5087 const un_op = self.air.instructions.items(.data)[inst].un_op;5075 const un_op = self.air.instructions.items(.data)[inst].un_op;
5088 const ty = self.typeOf(un_op);5076 const ty = self.typeOf(un_op);
5089 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));5077 const abi_size: u32 = @intCast(ty.abiSize(mod));
50905078
5091 const src_mcv = try self.resolveInst(un_op);5079 const src_mcv = try self.resolveInst(un_op);
5092 const dst_mcv = if (src_mcv.isRegister() and self.reuseOperand(inst, un_op, 0, src_mcv))5080 const dst_mcv = if (src_mcv.isRegister() and self.reuseOperand(inst, un_op, 0, src_mcv))
...@@ -5098,7 +5086,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {...@@ -5098,7 +5086,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {
5098 defer if (dst_lock) |lock| self.register_manager.unlockReg(lock);5086 defer if (dst_lock) |lock| self.register_manager.unlockReg(lock);
50995087
5100 const result: MCValue = result: {5088 const result: MCValue = result: {
5101 const mir_tag = if (@as(?Mir.Inst.FixedTag, switch (ty.zigTypeTag(mod)) {5089 const mir_tag = @as(?Mir.Inst.FixedTag, switch (ty.zigTypeTag(mod)) {
5102 .Float => switch (ty.floatBits(self.target.*)) {5090 .Float => switch (ty.floatBits(self.target.*)) {
5103 16 => if (self.hasFeature(.f16c)) {5091 16 => if (self.hasFeature(.f16c)) {
5104 const mat_src_reg = if (src_mcv.isRegister())5092 const mat_src_reg = if (src_mcv.isRegister())
...@@ -5152,7 +5140,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {...@@ -5152,7 +5140,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {
5152 .{ .v_ps, .cvtph2 },5140 .{ .v_ps, .cvtph2 },
5153 wide_reg,5141 wide_reg,
5154 src_mcv.mem(Memory.PtrSize.fromSize(5142 src_mcv.mem(Memory.PtrSize.fromSize(
5155 @as(u32, @intCast(@divExact(wide_reg.bitSize(), 16))),5143 @intCast(@divExact(wide_reg.bitSize(), 16)),
5156 )),5144 )),
5157 ) else try self.asmRegisterRegister(5145 ) else try self.asmRegisterRegister(
5158 .{ .v_ps, .cvtph2 },5146 .{ .v_ps, .cvtph2 },
...@@ -5191,7 +5179,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {...@@ -5191,7 +5179,7 @@ fn airSqrt(self: *Self, inst: Air.Inst.Index) !void {
5191 else => unreachable,5179 else => unreachable,
5192 },5180 },
5193 else => unreachable,5181 else => unreachable,
5194 })) |tag| tag else return self.fail("TODO implement airSqrt for {}", .{5182 }) orelse return self.fail("TODO implement airSqrt for {}", .{
5195 ty.fmt(mod),5183 ty.fmt(mod),
5196 });5184 });
5197 switch (mir_tag[0]) {5185 switch (mir_tag[0]) {
...@@ -5284,10 +5272,10 @@ fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) Inn...@@ -5284,10 +5272,10 @@ fn packedLoad(self: *Self, dst_mcv: MCValue, ptr_ty: Type, ptr_mcv: MCValue) Inn
5284 const ptr_info = ptr_ty.ptrInfo(mod);5272 const ptr_info = ptr_ty.ptrInfo(mod);
52855273
5286 const val_ty = ptr_info.child.toType();5274 const val_ty = ptr_info.child.toType();
5287 const val_abi_size = @as(u32, @intCast(val_ty.abiSize(mod)));5275 const val_abi_size: u32 = @intCast(val_ty.abiSize(mod));
5288 const limb_abi_size: u32 = @min(val_abi_size, 8);5276 const limb_abi_size: u32 = @min(val_abi_size, 8);
5289 const limb_abi_bits = limb_abi_size * 8;5277 const limb_abi_bits = limb_abi_size * 8;
5290 const val_byte_off = @as(i32, @intCast(ptr_info.packed_offset.bit_offset / limb_abi_bits * limb_abi_size));5278 const val_byte_off: i32 = @intCast(ptr_info.packed_offset.bit_offset / limb_abi_bits * limb_abi_size);
5291 const val_bit_off = ptr_info.packed_offset.bit_offset % limb_abi_bits;5279 const val_bit_off = ptr_info.packed_offset.bit_offset % limb_abi_bits;
5292 const val_extra_bits = self.regExtraBits(val_ty);5280 const val_extra_bits = self.regExtraBits(val_ty);
52935281
...@@ -5434,7 +5422,7 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In...@@ -5434,7 +5422,7 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In
5434 const limb_ty = try mod.intType(.unsigned, limb_abi_bits);5422 const limb_ty = try mod.intType(.unsigned, limb_abi_bits);
54355423
5436 const src_bit_size = src_ty.bitSize(mod);5424 const src_bit_size = src_ty.bitSize(mod);
5437 const src_byte_off = @as(i32, @intCast(ptr_info.packed_offset.bit_offset / limb_abi_bits * limb_abi_size));5425 const src_byte_off: i32 = @intCast(ptr_info.packed_offset.bit_offset / limb_abi_bits * limb_abi_size);
5438 const src_bit_off = ptr_info.packed_offset.bit_offset % limb_abi_bits;5426 const src_bit_off = ptr_info.packed_offset.bit_offset % limb_abi_bits;
54395427
5440 const ptr_reg = try self.copyToTmpRegister(ptr_ty, ptr_mcv);5428 const ptr_reg = try self.copyToTmpRegister(ptr_ty, ptr_mcv);
...@@ -5451,10 +5439,9 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In...@@ -5451,10 +5439,9 @@ fn packedStore(self: *Self, ptr_ty: Type, ptr_mcv: MCValue, src_mcv: MCValue) In
5451 .disp = src_byte_off + limb_i * limb_abi_bits,5439 .disp = src_byte_off + limb_i * limb_abi_bits,
5452 });5440 });
54535441
5454 const part_mask = (@as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - part_bit_size))) <<5442 const part_mask = (@as(u64, math.maxInt(u64)) >> @intCast(64 - part_bit_size)) <<
5455 @as(u6, @intCast(part_bit_off));5443 @intCast(part_bit_off);
5456 const part_mask_not = part_mask ^5444 const part_mask_not = part_mask ^ (@as(u64, math.maxInt(u64)) >> @intCast(64 - limb_abi_bits));
5457 (@as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - limb_abi_bits)));
5458 if (limb_abi_size <= 4) {5445 if (limb_abi_size <= 4) {
5459 try self.asmMemoryImmediate(.{ ._, .@"and" }, limb_mem, Immediate.u(part_mask_not));5446 try self.asmMemoryImmediate(.{ ._, .@"and" }, limb_mem, Immediate.u(part_mask_not));
5460 } else if (math.cast(i32, @as(i64, @bitCast(part_mask_not)))) |small| {5447 } else if (math.cast(i32, @as(i64, @bitCast(part_mask_not)))) |small| {
...@@ -5572,14 +5559,14 @@ fn fieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, index: u32...@@ -5572,14 +5559,14 @@ fn fieldPtr(self: *Self, inst: Air.Inst.Index, operand: Air.Inst.Ref, index: u32
5572 const ptr_field_ty = self.typeOfIndex(inst);5559 const ptr_field_ty = self.typeOfIndex(inst);
5573 const ptr_container_ty = self.typeOf(operand);5560 const ptr_container_ty = self.typeOf(operand);
5574 const container_ty = ptr_container_ty.childType(mod);5561 const container_ty = ptr_container_ty.childType(mod);
5575 const field_offset = @as(i32, @intCast(switch (container_ty.containerLayout(mod)) {5562 const field_offset: i32 = @intCast(switch (container_ty.containerLayout(mod)) {
5576 .Auto, .Extern => container_ty.structFieldOffset(index, mod),5563 .Auto, .Extern => container_ty.structFieldOffset(index, mod),
5577 .Packed => if (container_ty.zigTypeTag(mod) == .Struct and5564 .Packed => if (container_ty.zigTypeTag(mod) == .Struct and
5578 ptr_field_ty.ptrInfo(mod).packed_offset.host_size == 0)5565 ptr_field_ty.ptrInfo(mod).packed_offset.host_size == 0)
5579 container_ty.packedStructFieldByteOffset(index, mod)5566 container_ty.packedStructFieldByteOffset(index, mod)
5580 else5567 else
5581 0,5568 0,
5582 }));5569 });
55835570
5584 const src_mcv = try self.resolveInst(operand);5571 const src_mcv = try self.resolveInst(operand);
5585 const dst_mcv = if (switch (src_mcv) {5572 const dst_mcv = if (switch (src_mcv) {
...@@ -5606,8 +5593,8 @@ fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void {...@@ -5606,8 +5593,8 @@ fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void {
5606 const field_is_gp = field_rc.supersetOf(gp);5593 const field_is_gp = field_rc.supersetOf(gp);
56075594
5608 const src_mcv = try self.resolveInst(operand);5595 const src_mcv = try self.resolveInst(operand);
5609 const field_off = switch (container_ty.containerLayout(mod)) {5596 const field_off: u32 = switch (container_ty.containerLayout(mod)) {
5610 .Auto, .Extern => @as(u32, @intCast(container_ty.structFieldOffset(index, mod) * 8)),5597 .Auto, .Extern => @intCast(container_ty.structFieldOffset(index, mod) * 8),
5611 .Packed => if (mod.typeToStruct(container_ty)) |struct_obj|5598 .Packed => if (mod.typeToStruct(container_ty)) |struct_obj|
5612 struct_obj.packedFieldBitOffset(mod, index)5599 struct_obj.packedFieldBitOffset(mod, index)
5613 else5600 else
...@@ -5650,7 +5637,7 @@ fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void {...@@ -5650,7 +5637,7 @@ fn airStructFieldVal(self: *Self, inst: Air.Inst.Index) !void {
56505637
5651 const limb_abi_size: u32 = @min(field_abi_size, 8);5638 const limb_abi_size: u32 = @min(field_abi_size, 8);
5652 const limb_abi_bits = limb_abi_size * 8;5639 const limb_abi_bits = limb_abi_size * 8;
5653 const field_byte_off = @as(i32, @intCast(field_off / limb_abi_bits * limb_abi_size));5640 const field_byte_off: i32 = @intCast(field_off / limb_abi_bits * limb_abi_size);
5654 const field_bit_off = field_off % limb_abi_bits;5641 const field_bit_off = field_off % limb_abi_bits;
56555642
5656 if (field_abi_size > 8) {5643 if (field_abi_size > 8) {
...@@ -5775,7 +5762,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void {...@@ -5775,7 +5762,7 @@ fn airFieldParentPtr(self: *Self, inst: Air.Inst.Index) !void {
57755762
5776 const inst_ty = self.typeOfIndex(inst);5763 const inst_ty = self.typeOfIndex(inst);
5777 const parent_ty = inst_ty.childType(mod);5764 const parent_ty = inst_ty.childType(mod);
5778 const field_offset = @as(i32, @intCast(parent_ty.structFieldOffset(extra.field_index, mod)));5765 const field_offset: i32 = @intCast(parent_ty.structFieldOffset(extra.field_index, mod));
57795766
5780 const src_mcv = try self.resolveInst(extra.field_ptr);5767 const src_mcv = try self.resolveInst(extra.field_ptr);
5781 const dst_mcv = if (src_mcv.isRegisterOffset() and5768 const dst_mcv = if (src_mcv.isRegisterOffset() and
...@@ -5824,14 +5811,14 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air:...@@ -5824,14 +5811,14 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air:
58245811
5825 switch (tag) {5812 switch (tag) {
5826 .not => {5813 .not => {
5827 const limb_abi_size = @as(u16, @intCast(@min(src_ty.abiSize(mod), 8)));5814 const limb_abi_size: u16 = @intCast(@min(src_ty.abiSize(mod), 8));
5828 const int_info = if (src_ty.ip_index == .bool_type)5815 const int_info = if (src_ty.ip_index == .bool_type)
5829 std.builtin.Type.Int{ .signedness = .unsigned, .bits = 1 }5816 std.builtin.Type.Int{ .signedness = .unsigned, .bits = 1 }
5830 else5817 else
5831 src_ty.intInfo(mod);5818 src_ty.intInfo(mod);
5832 var byte_off: i32 = 0;5819 var byte_off: i32 = 0;
5833 while (byte_off * 8 < int_info.bits) : (byte_off += limb_abi_size) {5820 while (byte_off * 8 < int_info.bits) : (byte_off += limb_abi_size) {
5834 const limb_bits = @as(u16, @intCast(@min(int_info.bits - byte_off * 8, limb_abi_size * 8)));5821 const limb_bits: u16 = @intCast(@min(int_info.bits - byte_off * 8, limb_abi_size * 8));
5835 const limb_ty = try mod.intType(int_info.signedness, limb_bits);5822 const limb_ty = try mod.intType(int_info.signedness, limb_bits);
5836 const limb_mcv = switch (byte_off) {5823 const limb_mcv = switch (byte_off) {
5837 0 => dst_mcv,5824 0 => dst_mcv,
...@@ -5839,7 +5826,7 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air:...@@ -5839,7 +5826,7 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air:
5839 };5826 };
58405827
5841 if (int_info.signedness == .unsigned and self.regExtraBits(limb_ty) > 0) {5828 if (int_info.signedness == .unsigned and self.regExtraBits(limb_ty) > 0) {
5842 const mask = @as(u64, math.maxInt(u64)) >> @as(u6, @intCast(64 - limb_bits));5829 const mask = @as(u64, math.maxInt(u64)) >> @intCast(64 - limb_bits);
5843 try self.genBinOpMir(.{ ._, .xor }, limb_ty, limb_mcv, .{ .immediate = mask });5830 try self.genBinOpMir(.{ ._, .xor }, limb_ty, limb_mcv, .{ .immediate = mask });
5844 } else try self.genUnOpMir(.{ ._, .not }, limb_ty, limb_mcv);5831 } else try self.genUnOpMir(.{ ._, .not }, limb_ty, limb_mcv);
5845 }5832 }
...@@ -5852,7 +5839,7 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air:...@@ -5852,7 +5839,7 @@ fn genUnOp(self: *Self, maybe_inst: ?Air.Inst.Index, tag: Air.Inst.Tag, src_air:
58525839
5853fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MCValue) !void {5840fn genUnOpMir(self: *Self, mir_tag: Mir.Inst.FixedTag, dst_ty: Type, dst_mcv: MCValue) !void {
5854 const mod = self.bin_file.options.module.?;5841 const mod = self.bin_file.options.module.?;
5855 const abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));5842 const abi_size: u32 = @intCast(dst_ty.abiSize(mod));
5856 if (abi_size > 8) return self.fail("TODO implement {} for {}", .{5843 if (abi_size > 8) return self.fail("TODO implement {} for {}", .{
5857 mir_tag,5844 mir_tag,
5858 dst_ty.fmt(self.bin_file.options.module.?),5845 dst_ty.fmt(self.bin_file.options.module.?),
...@@ -5914,7 +5901,7 @@ fn genShiftBinOpMir(...@@ -5914,7 +5901,7 @@ fn genShiftBinOpMir(
5914 break :rhs .{ .register = .rcx };5901 break :rhs .{ .register = .rcx };
5915 };5902 };
59165903
5917 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));5904 const abi_size: u32 = @intCast(ty.abiSize(mod));
5918 if (abi_size <= 8) {5905 if (abi_size <= 8) {
5919 switch (lhs_mcv) {5906 switch (lhs_mcv) {
5920 .register => |lhs_reg| switch (rhs_mcv) {5907 .register => |lhs_reg| switch (rhs_mcv) {
...@@ -6602,7 +6589,7 @@ fn genBinOp(...@@ -6602,7 +6589,7 @@ fn genBinOp(
6602 Memory.sib(Memory.PtrSize.fromSize(cmov_abi_size), switch (mat_src_mcv) {6589 Memory.sib(Memory.PtrSize.fromSize(cmov_abi_size), switch (mat_src_mcv) {
6603 .memory => |addr| .{6590 .memory => |addr| .{
6604 .base = .{ .reg = .ds },6591 .base = .{ .reg = .ds },
6605 .disp = @as(i32, @intCast(@as(i64, @bitCast(addr)))),6592 .disp = @intCast(@as(i64, @bitCast(addr))),
6606 },6593 },
6607 .indirect => |reg_off| .{6594 .indirect => |reg_off| .{
6608 .base = .{ .reg = reg_off.reg },6595 .base = .{ .reg = reg_off.reg },
...@@ -6628,7 +6615,7 @@ fn genBinOp(...@@ -6628,7 +6615,7 @@ fn genBinOp(
6628 }6615 }
66296616
6630 const dst_reg = registerAlias(dst_mcv.getReg().?, abi_size);6617 const dst_reg = registerAlias(dst_mcv.getReg().?, abi_size);
6631 const mir_tag = if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {6618 const mir_tag = @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
6632 else => unreachable,6619 else => unreachable,
6633 .Float => switch (lhs_ty.floatBits(self.target.*)) {6620 .Float => switch (lhs_ty.floatBits(self.target.*)) {
6634 16 => if (self.hasFeature(.f16c)) {6621 16 => if (self.hasFeature(.f16c)) {
...@@ -7190,7 +7177,7 @@ fn genBinOp(...@@ -7190,7 +7177,7 @@ fn genBinOp(
7190 else => unreachable,7177 else => unreachable,
7191 },7178 },
7192 },7179 },
7193 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7180 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7194 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7181 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7195 });7182 });
71967183
...@@ -7253,7 +7240,7 @@ fn genBinOp(...@@ -7253,7 +7240,7 @@ fn genBinOp(
7253 const rhs_copy_reg = registerAlias(src_mcv.getReg().?, abi_size);7240 const rhs_copy_reg = registerAlias(src_mcv.getReg().?, abi_size);
72547241
7255 try self.asmRegisterRegisterRegisterImmediate(7242 try self.asmRegisterRegisterRegisterImmediate(
7256 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7243 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7257 .Float => switch (lhs_ty.floatBits(self.target.*)) {7244 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7258 32 => .{ .v_ss, .cmp },7245 32 => .{ .v_ss, .cmp },
7259 64 => .{ .v_sd, .cmp },7246 64 => .{ .v_sd, .cmp },
...@@ -7278,7 +7265,7 @@ fn genBinOp(...@@ -7278,7 +7265,7 @@ fn genBinOp(
7278 else => unreachable,7265 else => unreachable,
7279 },7266 },
7280 else => unreachable,7267 else => unreachable,
7281 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7268 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7282 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7269 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7283 }),7270 }),
7284 mask_reg,7271 mask_reg,
...@@ -7287,7 +7274,7 @@ fn genBinOp(...@@ -7287,7 +7274,7 @@ fn genBinOp(
7287 Immediate.u(3), // unord7274 Immediate.u(3), // unord
7288 );7275 );
7289 try self.asmRegisterRegisterRegisterRegister(7276 try self.asmRegisterRegisterRegisterRegister(
7290 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7277 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7291 .Float => switch (lhs_ty.floatBits(self.target.*)) {7278 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7292 32 => .{ .v_ps, .blendv },7279 32 => .{ .v_ps, .blendv },
7293 64 => .{ .v_pd, .blendv },7280 64 => .{ .v_pd, .blendv },
...@@ -7310,7 +7297,7 @@ fn genBinOp(...@@ -7310,7 +7297,7 @@ fn genBinOp(
7310 else => unreachable,7297 else => unreachable,
7311 },7298 },
7312 else => unreachable,7299 else => unreachable,
7313 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7300 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7314 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7301 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7315 }),7302 }),
7316 dst_reg,7303 dst_reg,
...@@ -7321,7 +7308,7 @@ fn genBinOp(...@@ -7321,7 +7308,7 @@ fn genBinOp(
7321 } else {7308 } else {
7322 const has_blend = self.hasFeature(.sse4_1);7309 const has_blend = self.hasFeature(.sse4_1);
7323 try self.asmRegisterRegisterImmediate(7310 try self.asmRegisterRegisterImmediate(
7324 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7311 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7325 .Float => switch (lhs_ty.floatBits(self.target.*)) {7312 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7326 32 => .{ ._ss, .cmp },7313 32 => .{ ._ss, .cmp },
7327 64 => .{ ._sd, .cmp },7314 64 => .{ ._sd, .cmp },
...@@ -7346,7 +7333,7 @@ fn genBinOp(...@@ -7346,7 +7333,7 @@ fn genBinOp(
7346 else => unreachable,7333 else => unreachable,
7347 },7334 },
7348 else => unreachable,7335 else => unreachable,
7349 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7336 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7350 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7337 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7351 }),7338 }),
7352 mask_reg,7339 mask_reg,
...@@ -7354,7 +7341,7 @@ fn genBinOp(...@@ -7354,7 +7341,7 @@ fn genBinOp(
7354 Immediate.u(if (has_blend) 3 else 7), // unord, ord7341 Immediate.u(if (has_blend) 3 else 7), // unord, ord
7355 );7342 );
7356 if (has_blend) try self.asmRegisterRegisterRegister(7343 if (has_blend) try self.asmRegisterRegisterRegister(
7357 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7344 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7358 .Float => switch (lhs_ty.floatBits(self.target.*)) {7345 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7359 32 => .{ ._ps, .blendv },7346 32 => .{ ._ps, .blendv },
7360 64 => .{ ._pd, .blendv },7347 64 => .{ ._pd, .blendv },
...@@ -7377,7 +7364,7 @@ fn genBinOp(...@@ -7377,7 +7364,7 @@ fn genBinOp(
7377 else => unreachable,7364 else => unreachable,
7378 },7365 },
7379 else => unreachable,7366 else => unreachable,
7380 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7367 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7381 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7368 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7382 }),7369 }),
7383 dst_reg,7370 dst_reg,
...@@ -7385,7 +7372,7 @@ fn genBinOp(...@@ -7385,7 +7372,7 @@ fn genBinOp(
7385 mask_reg,7372 mask_reg,
7386 ) else {7373 ) else {
7387 try self.asmRegisterRegister(7374 try self.asmRegisterRegister(
7388 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7375 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7389 .Float => switch (lhs_ty.floatBits(self.target.*)) {7376 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7390 32 => .{ ._ps, .@"and" },7377 32 => .{ ._ps, .@"and" },
7391 64 => .{ ._pd, .@"and" },7378 64 => .{ ._pd, .@"and" },
...@@ -7408,14 +7395,14 @@ fn genBinOp(...@@ -7408,14 +7395,14 @@ fn genBinOp(
7408 else => unreachable,7395 else => unreachable,
7409 },7396 },
7410 else => unreachable,7397 else => unreachable,
7411 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7398 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7412 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7399 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7413 }),7400 }),
7414 dst_reg,7401 dst_reg,
7415 mask_reg,7402 mask_reg,
7416 );7403 );
7417 try self.asmRegisterRegister(7404 try self.asmRegisterRegister(
7418 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7405 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7419 .Float => switch (lhs_ty.floatBits(self.target.*)) {7406 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7420 32 => .{ ._ps, .andn },7407 32 => .{ ._ps, .andn },
7421 64 => .{ ._pd, .andn },7408 64 => .{ ._pd, .andn },
...@@ -7438,14 +7425,14 @@ fn genBinOp(...@@ -7438,14 +7425,14 @@ fn genBinOp(
7438 else => unreachable,7425 else => unreachable,
7439 },7426 },
7440 else => unreachable,7427 else => unreachable,
7441 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7428 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7442 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7429 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7443 }),7430 }),
7444 mask_reg,7431 mask_reg,
7445 lhs_copy_reg.?,7432 lhs_copy_reg.?,
7446 );7433 );
7447 try self.asmRegisterRegister(7434 try self.asmRegisterRegister(
7448 if (@as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {7435 @as(?Mir.Inst.FixedTag, switch (lhs_ty.zigTypeTag(mod)) {
7449 .Float => switch (lhs_ty.floatBits(self.target.*)) {7436 .Float => switch (lhs_ty.floatBits(self.target.*)) {
7450 32 => .{ ._ps, .@"or" },7437 32 => .{ ._ps, .@"or" },
7451 64 => .{ ._pd, .@"or" },7438 64 => .{ ._pd, .@"or" },
...@@ -7468,7 +7455,7 @@ fn genBinOp(...@@ -7468,7 +7455,7 @@ fn genBinOp(
7468 else => unreachable,7455 else => unreachable,
7469 },7456 },
7470 else => unreachable,7457 else => unreachable,
7471 })) |tag| tag else return self.fail("TODO implement genBinOp for {s} {}", .{7458 }) orelse return self.fail("TODO implement genBinOp for {s} {}", .{
7472 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),7459 @tagName(air_tag), lhs_ty.fmt(self.bin_file.options.module.?),
7473 }),7460 }),
7474 dst_reg,7461 dst_reg,
...@@ -7490,7 +7477,7 @@ fn genBinOpMir(...@@ -7490,7 +7477,7 @@ fn genBinOpMir(
7490 src_mcv: MCValue,7477 src_mcv: MCValue,
7491) !void {7478) !void {
7492 const mod = self.bin_file.options.module.?;7479 const mod = self.bin_file.options.module.?;
7493 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));7480 const abi_size: u32 = @intCast(ty.abiSize(mod));
7494 switch (dst_mcv) {7481 switch (dst_mcv) {
7495 .none,7482 .none,
7496 .unreach,7483 .unreach,
...@@ -7738,10 +7725,10 @@ fn genBinOpMir(...@@ -7738,10 +7725,10 @@ fn genBinOpMir(
7738 else => unreachable,7725 else => unreachable,
7739 },7726 },
7740 .immediate => |src_imm| {7727 .immediate => |src_imm| {
7741 const imm = switch (off) {7728 const imm: u64 = switch (off) {
7742 0 => src_imm,7729 0 => src_imm,
7743 else => switch (ty_signedness) {7730 else => switch (ty_signedness) {
7744 .signed => @as(u64, @bitCast(@as(i64, @bitCast(src_imm)) >> 63)),7731 .signed => @bitCast(@as(i64, @bitCast(src_imm)) >> 63),
7745 .unsigned => 0,7732 .unsigned => 0,
7746 },7733 },
7747 };7734 };
...@@ -7814,7 +7801,7 @@ fn genBinOpMir(...@@ -7814,7 +7801,7 @@ fn genBinOpMir(
7814 0 => src_mcv,7801 0 => src_mcv,
7815 else => .{ .immediate = 0 },7802 else => .{ .immediate = 0 },
7816 },7803 },
7817 .memory => |addr| .{ .memory = @as(u64, @bitCast(@as(i64, @bitCast(addr)) + off)) },7804 .memory => |addr| .{ .memory = @bitCast(@as(i64, @bitCast(addr)) + off) },
7818 .indirect => |reg_off| .{ .indirect = .{7805 .indirect => |reg_off| .{ .indirect = .{
7819 .reg = reg_off.reg,7806 .reg = reg_off.reg,
7820 .off = reg_off.off + off,7807 .off = reg_off.off + off,
...@@ -7841,7 +7828,7 @@ fn genBinOpMir(...@@ -7841,7 +7828,7 @@ fn genBinOpMir(
7841/// Does not support byte-size operands.7828/// Does not support byte-size operands.
7842fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError!void {7829fn genIntMulComplexOpMir(self: *Self, dst_ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError!void {
7843 const mod = self.bin_file.options.module.?;7830 const mod = self.bin_file.options.module.?;
7844 const abi_size = @as(u32, @intCast(dst_ty.abiSize(mod)));7831 const abi_size: u32 = @intCast(dst_ty.abiSize(mod));
7845 switch (dst_mcv) {7832 switch (dst_mcv) {
7846 .none,7833 .none,
7847 .unreach,7834 .unreach,
...@@ -8075,7 +8062,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier...@@ -8075,7 +8062,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier
8075 const pl_op = self.air.instructions.items(.data)[inst].pl_op;8062 const pl_op = self.air.instructions.items(.data)[inst].pl_op;
8076 const callee = pl_op.operand;8063 const callee = pl_op.operand;
8077 const extra = self.air.extraData(Air.Call, pl_op.payload);8064 const extra = self.air.extraData(Air.Call, pl_op.payload);
8078 const args = @as([]const Air.Inst.Ref, @ptrCast(self.air.extra[extra.end..][0..extra.data.args_len]));8065 const args: []const Air.Inst.Ref = @ptrCast(self.air.extra[extra.end..][0..extra.data.args_len]);
8079 const ty = self.typeOf(callee);8066 const ty = self.typeOf(callee);
80808067
8081 const fn_ty = switch (ty.zigTypeTag(mod)) {8068 const fn_ty = switch (ty.zigTypeTag(mod)) {
...@@ -8168,7 +8155,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier...@@ -8168,7 +8155,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier
8168 const got_addr = atom.getOffsetTableAddress(elf_file);8155 const got_addr = atom.getOffsetTableAddress(elf_file);
8169 try self.asmMemory(.{ ._, .call }, Memory.sib(.qword, .{8156 try self.asmMemory(.{ ._, .call }, Memory.sib(.qword, .{
8170 .base = .{ .reg = .ds },8157 .base = .{ .reg = .ds },
8171 .disp = @as(i32, @intCast(got_addr)),8158 .disp = @intCast(got_addr),
8172 }));8159 }));
8173 } else if (self.bin_file.cast(link.File.Coff)) |coff_file| {8160 } else if (self.bin_file.cast(link.File.Coff)) |coff_file| {
8174 const atom = try coff_file.getOrCreateAtomForDecl(owner_decl);8161 const atom = try coff_file.getOrCreateAtomForDecl(owner_decl);
...@@ -8185,7 +8172,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier...@@ -8185,7 +8172,7 @@ fn airCall(self: *Self, inst: Air.Inst.Index, modifier: std.builtin.CallModifier
8185 const atom = p9.getAtom(atom_index);8172 const atom = p9.getAtom(atom_index);
8186 try self.asmMemory(.{ ._, .call }, Memory.sib(.qword, .{8173 try self.asmMemory(.{ ._, .call }, Memory.sib(.qword, .{
8187 .base = .{ .reg = .ds },8174 .base = .{ .reg = .ds },
8188 .disp = @as(i32, @intCast(atom.getOffsetTableAddress(p9))),8175 .disp = @intCast(atom.getOffsetTableAddress(p9)),
8189 }));8176 }));
8190 } else unreachable;8177 } else unreachable;
8191 } else if (func_value.getExternFunc(mod)) |extern_func| {8178 } else if (func_value.getExternFunc(mod)) |extern_func| {
...@@ -8305,7 +8292,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void {...@@ -8305,7 +8292,7 @@ fn airCmp(self: *Self, inst: Air.Inst.Index, op: math.CompareOperator) !void {
8305 const result = MCValue{8292 const result = MCValue{
8306 .eflags = switch (ty.zigTypeTag(mod)) {8293 .eflags = switch (ty.zigTypeTag(mod)) {
8307 else => result: {8294 else => result: {
8308 const abi_size = @as(u16, @intCast(ty.abiSize(mod)));8295 const abi_size: u16 = @intCast(ty.abiSize(mod));
8309 const may_flip: enum {8296 const may_flip: enum {
8310 may_flip,8297 may_flip,
8311 must_flip,8298 must_flip,
...@@ -8502,7 +8489,7 @@ fn airCmpLtErrorsLen(self: *Self, inst: Air.Inst.Index) !void {...@@ -8502,7 +8489,7 @@ fn airCmpLtErrorsLen(self: *Self, inst: Air.Inst.Index) !void {
8502 self.eflags_inst = inst;8489 self.eflags_inst = inst;
85038490
8504 const op_ty = self.typeOf(un_op);8491 const op_ty = self.typeOf(un_op);
8505 const op_abi_size = @as(u32, @intCast(op_ty.abiSize(mod)));8492 const op_abi_size: u32 = @intCast(op_ty.abiSize(mod));
8506 const op_mcv = try self.resolveInst(un_op);8493 const op_mcv = try self.resolveInst(un_op);
8507 const dst_reg = switch (op_mcv) {8494 const dst_reg = switch (op_mcv) {
8508 .register => |reg| reg,8495 .register => |reg| reg,
...@@ -8711,7 +8698,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC...@@ -8711,7 +8698,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC
8711 const some_info: struct { off: i32, ty: Type } = if (opt_ty.optionalReprIsPayload(mod))8698 const some_info: struct { off: i32, ty: Type } = if (opt_ty.optionalReprIsPayload(mod))
8712 .{ .off = 0, .ty = if (pl_ty.isSlice(mod)) pl_ty.slicePtrFieldType(mod) else pl_ty }8699 .{ .off = 0, .ty = if (pl_ty.isSlice(mod)) pl_ty.slicePtrFieldType(mod) else pl_ty }
8713 else8700 else
8714 .{ .off = @as(i32, @intCast(pl_ty.abiSize(mod))), .ty = Type.bool };8701 .{ .off = @intCast(pl_ty.abiSize(mod)), .ty = Type.bool };
87158702
8716 switch (opt_mcv) {8703 switch (opt_mcv) {
8717 .none,8704 .none,
...@@ -8731,14 +8718,14 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC...@@ -8731,14 +8718,14 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC
87318718
8732 .register => |opt_reg| {8719 .register => |opt_reg| {
8733 if (some_info.off == 0) {8720 if (some_info.off == 0) {
8734 const some_abi_size = @as(u32, @intCast(some_info.ty.abiSize(mod)));8721 const some_abi_size: u32 = @intCast(some_info.ty.abiSize(mod));
8735 const alias_reg = registerAlias(opt_reg, some_abi_size);8722 const alias_reg = registerAlias(opt_reg, some_abi_size);
8736 assert(some_abi_size * 8 == alias_reg.bitSize());8723 assert(some_abi_size * 8 == alias_reg.bitSize());
8737 try self.asmRegisterRegister(.{ ._, .@"test" }, alias_reg, alias_reg);8724 try self.asmRegisterRegister(.{ ._, .@"test" }, alias_reg, alias_reg);
8738 return .{ .eflags = .z };8725 return .{ .eflags = .z };
8739 }8726 }
8740 assert(some_info.ty.ip_index == .bool_type);8727 assert(some_info.ty.ip_index == .bool_type);
8741 const opt_abi_size = @as(u32, @intCast(opt_ty.abiSize(mod)));8728 const opt_abi_size: u32 = @intCast(opt_ty.abiSize(mod));
8742 try self.asmRegisterImmediate(8729 try self.asmRegisterImmediate(
8743 .{ ._, .bt },8730 .{ ._, .bt },
8744 registerAlias(opt_reg, opt_abi_size),8731 registerAlias(opt_reg, opt_abi_size),
...@@ -8757,7 +8744,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC...@@ -8757,7 +8744,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC
8757 defer self.register_manager.unlockReg(addr_reg_lock);8744 defer self.register_manager.unlockReg(addr_reg_lock);
87588745
8759 try self.genSetReg(addr_reg, Type.usize, opt_mcv.address());8746 try self.genSetReg(addr_reg, Type.usize, opt_mcv.address());
8760 const some_abi_size = @as(u32, @intCast(some_info.ty.abiSize(mod)));8747 const some_abi_size: u32 = @intCast(some_info.ty.abiSize(mod));
8761 try self.asmMemoryImmediate(8748 try self.asmMemoryImmediate(
8762 .{ ._, .cmp },8749 .{ ._, .cmp },
8763 Memory.sib(Memory.PtrSize.fromSize(some_abi_size), .{8750 Memory.sib(Memory.PtrSize.fromSize(some_abi_size), .{
...@@ -8770,7 +8757,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC...@@ -8770,7 +8757,7 @@ fn isNull(self: *Self, inst: Air.Inst.Index, opt_ty: Type, opt_mcv: MCValue) !MC
8770 },8757 },
87718758
8772 .indirect, .load_frame => {8759 .indirect, .load_frame => {
8773 const some_abi_size = @as(u32, @intCast(some_info.ty.abiSize(mod)));8760 const some_abi_size: u32 = @intCast(some_info.ty.abiSize(mod));
8774 try self.asmMemoryImmediate(8761 try self.asmMemoryImmediate(
8775 .{ ._, .cmp },8762 .{ ._, .cmp },
8776 Memory.sib(Memory.PtrSize.fromSize(some_abi_size), switch (opt_mcv) {8763 Memory.sib(Memory.PtrSize.fromSize(some_abi_size), switch (opt_mcv) {
...@@ -8802,7 +8789,7 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue)...@@ -8802,7 +8789,7 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue)
8802 const some_info: struct { off: i32, ty: Type } = if (opt_ty.optionalReprIsPayload(mod))8789 const some_info: struct { off: i32, ty: Type } = if (opt_ty.optionalReprIsPayload(mod))
8803 .{ .off = 0, .ty = if (pl_ty.isSlice(mod)) pl_ty.slicePtrFieldType(mod) else pl_ty }8790 .{ .off = 0, .ty = if (pl_ty.isSlice(mod)) pl_ty.slicePtrFieldType(mod) else pl_ty }
8804 else8791 else
8805 .{ .off = @as(i32, @intCast(pl_ty.abiSize(mod))), .ty = Type.bool };8792 .{ .off = @intCast(pl_ty.abiSize(mod)), .ty = Type.bool };
88068793
8807 const ptr_reg = switch (ptr_mcv) {8794 const ptr_reg = switch (ptr_mcv) {
8808 .register => |reg| reg,8795 .register => |reg| reg,
...@@ -8811,7 +8798,7 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue)...@@ -8811,7 +8798,7 @@ fn isNullPtr(self: *Self, inst: Air.Inst.Index, ptr_ty: Type, ptr_mcv: MCValue)
8811 const ptr_lock = self.register_manager.lockReg(ptr_reg);8798 const ptr_lock = self.register_manager.lockReg(ptr_reg);
8812 defer if (ptr_lock) |lock| self.register_manager.unlockReg(lock);8799 defer if (ptr_lock) |lock| self.register_manager.unlockReg(lock);
88138800
8814 const some_abi_size = @as(u32, @intCast(some_info.ty.abiSize(mod)));8801 const some_abi_size: u32 = @intCast(some_info.ty.abiSize(mod));
8815 try self.asmMemoryImmediate(8802 try self.asmMemoryImmediate(
8816 .{ ._, .cmp },8803 .{ ._, .cmp },
8817 Memory.sib(Memory.PtrSize.fromSize(some_abi_size), .{8804 Memory.sib(Memory.PtrSize.fromSize(some_abi_size), .{
...@@ -8844,12 +8831,11 @@ fn isErr(self: *Self, maybe_inst: ?Air.Inst.Index, ty: Type, operand: MCValue) !...@@ -8844,12 +8831,11 @@ fn isErr(self: *Self, maybe_inst: ?Air.Inst.Index, ty: Type, operand: MCValue) !
88448831
8845 const tmp_reg = try self.copyToTmpRegister(ty, operand);8832 const tmp_reg = try self.copyToTmpRegister(ty, operand);
8846 if (err_off > 0) {8833 if (err_off > 0) {
8847 const shift = @as(u6, @intCast(err_off * 8));
8848 try self.genShiftBinOpMir(8834 try self.genShiftBinOpMir(
8849 .{ ._r, .sh },8835 .{ ._r, .sh },
8850 ty,8836 ty,
8851 .{ .register = tmp_reg },8837 .{ .register = tmp_reg },
8852 .{ .immediate = shift },8838 .{ .immediate = @as(u6, @intCast(err_off * 8)) },
8853 );8839 );
8854 } else {8840 } else {
8855 try self.truncateRegister(Type.anyerror, tmp_reg);8841 try self.truncateRegister(Type.anyerror, tmp_reg);
...@@ -9004,7 +8990,7 @@ fn airLoop(self: *Self, inst: Air.Inst.Index) !void {...@@ -9004,7 +8990,7 @@ fn airLoop(self: *Self, inst: Air.Inst.Index) !void {
9004 const ty_pl = self.air.instructions.items(.data)[inst].ty_pl;8990 const ty_pl = self.air.instructions.items(.data)[inst].ty_pl;
9005 const loop = self.air.extraData(Air.Block, ty_pl.payload);8991 const loop = self.air.extraData(Air.Block, ty_pl.payload);
9006 const body = self.air.extra[loop.end..][0..loop.data.body_len];8992 const body = self.air.extra[loop.end..][0..loop.data.body_len];
9007 const jmp_target = @as(u32, @intCast(self.mir_instructions.len));8993 const jmp_target: u32 = @intCast(self.mir_instructions.len);
90088994
9009 self.scope_generation += 1;8995 self.scope_generation += 1;
9010 const state = try self.saveState();8996 const state = try self.saveState();
...@@ -9076,10 +9062,8 @@ fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void {...@@ -9076,10 +9062,8 @@ fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void {
90769062
9077 while (case_i < switch_br.data.cases_len) : (case_i += 1) {9063 while (case_i < switch_br.data.cases_len) : (case_i += 1) {
9078 const case = self.air.extraData(Air.SwitchBr.Case, extra_index);9064 const case = self.air.extraData(Air.SwitchBr.Case, extra_index);
9079 const items = @as(9065 const items: []const Air.Inst.Ref =
9080 []const Air.Inst.Ref,9066 @ptrCast(self.air.extra[case.end..][0..case.data.items_len]);
9081 @ptrCast(self.air.extra[case.end..][0..case.data.items_len]),
9082 );
9083 const case_body = self.air.extra[case.end + items.len ..][0..case.data.body_len];9067 const case_body = self.air.extra[case.end + items.len ..][0..case.data.body_len];
9084 extra_index = case.end + items.len + case_body.len;9068 extra_index = case.end + items.len + case_body.len;
90859069
...@@ -9127,7 +9111,7 @@ fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void {...@@ -9127,7 +9111,7 @@ fn airSwitchBr(self: *Self, inst: Air.Inst.Index) !void {
9127}9111}
91289112
9129fn performReloc(self: *Self, reloc: Mir.Inst.Index) !void {9113fn performReloc(self: *Self, reloc: Mir.Inst.Index) !void {
9130 const next_inst = @as(u32, @intCast(self.mir_instructions.len));9114 const next_inst: u32 = @intCast(self.mir_instructions.len);
9131 switch (self.mir_instructions.items(.tag)[reloc]) {9115 switch (self.mir_instructions.items(.tag)[reloc]) {
9132 .j, .jmp => {},9116 .j, .jmp => {},
9133 .pseudo => switch (self.mir_instructions.items(.ops)[reloc]) {9117 .pseudo => switch (self.mir_instructions.items(.ops)[reloc]) {
...@@ -9202,11 +9186,12 @@ fn airBr(self: *Self, inst: Air.Inst.Index) !void {...@@ -9202,11 +9186,12 @@ fn airBr(self: *Self, inst: Air.Inst.Index) !void {
9202fn airAsm(self: *Self, inst: Air.Inst.Index) !void {9186fn airAsm(self: *Self, inst: Air.Inst.Index) !void {
9203 const ty_pl = self.air.instructions.items(.data)[inst].ty_pl;9187 const ty_pl = self.air.instructions.items(.data)[inst].ty_pl;
9204 const extra = self.air.extraData(Air.Asm, ty_pl.payload);9188 const extra = self.air.extraData(Air.Asm, ty_pl.payload);
9205 const clobbers_len = @as(u31, @truncate(extra.data.flags));9189 const clobbers_len: u31 = @truncate(extra.data.flags);
9206 var extra_i: usize = extra.end;9190 var extra_i: usize = extra.end;
9207 const outputs = @as([]const Air.Inst.Ref, @ptrCast(self.air.extra[extra_i..][0..extra.data.outputs_len]));9191 const outputs: []const Air.Inst.Ref =
9192 @ptrCast(self.air.extra[extra_i..][0..extra.data.outputs_len]);
9208 extra_i += outputs.len;9193 extra_i += outputs.len;
9209 const inputs = @as([]const Air.Inst.Ref, @ptrCast(self.air.extra[extra_i..][0..extra.data.inputs_len]));9194 const inputs: []const Air.Inst.Ref = @ptrCast(self.air.extra[extra_i..][0..extra.data.inputs_len]);
9210 extra_i += inputs.len;9195 extra_i += inputs.len;
92119196
9212 var result: MCValue = .none;9197 var result: MCValue = .none;
...@@ -9341,16 +9326,14 @@ fn airAsm(self: *Self, inst: Air.Inst.Index) !void {...@@ -9341,16 +9326,14 @@ fn airAsm(self: *Self, inst: Air.Inst.Index) !void {
9341 } else if (mem.startsWith(u8, op_str, "$")) {9326 } else if (mem.startsWith(u8, op_str, "$")) {
9342 if (std.fmt.parseInt(i32, op_str["$".len..], 0)) |s| {9327 if (std.fmt.parseInt(i32, op_str["$".len..], 0)) |s| {
9343 if (mnem_size) |size| {9328 if (mnem_size) |size| {
9344 const max = @as(u64, math.maxInt(u64)) >>9329 const max = @as(u64, math.maxInt(u64)) >> @intCast(64 - (size.bitSize() - 1));
9345 @as(u6, @intCast(64 - (size.bitSize() - 1)));
9346 if ((if (s < 0) ~s else s) > max)9330 if ((if (s < 0) ~s else s) > max)
9347 return self.fail("Invalid immediate size: '{s}'", .{op_str});9331 return self.fail("Invalid immediate size: '{s}'", .{op_str});
9348 }9332 }
9349 op.* = .{ .imm = Immediate.s(s) };9333 op.* = .{ .imm = Immediate.s(s) };
9350 } else |_| if (std.fmt.parseInt(u64, op_str["$".len..], 0)) |u| {9334 } else |_| if (std.fmt.parseInt(u64, op_str["$".len..], 0)) |u| {
9351 if (mnem_size) |size| {9335 if (mnem_size) |size| {
9352 const max = @as(u64, math.maxInt(u64)) >>9336 const max = @as(u64, math.maxInt(u64)) >> @intCast(64 - size.bitSize());
9353 @as(u6, @intCast(64 - size.bitSize()));
9354 if (u > max)9337 if (u > max)
9355 return self.fail("Invalid immediate size: '{s}'", .{op_str});9338 return self.fail("Invalid immediate size: '{s}'", .{op_str});
9356 }9339 }
...@@ -9702,7 +9685,7 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError...@@ -9702,7 +9685,7 @@ fn genCopy(self: *Self, ty: Type, dst_mcv: MCValue, src_mcv: MCValue) InnerError
97029685
9703fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerError!void {9686fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerError!void {
9704 const mod = self.bin_file.options.module.?;9687 const mod = self.bin_file.options.module.?;
9705 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));9688 const abi_size: u32 = @intCast(ty.abiSize(mod));
9706 if (abi_size * 8 > dst_reg.bitSize())9689 if (abi_size * 8 > dst_reg.bitSize())
9707 return self.fail("genSetReg called with a value larger than dst_reg", .{});9690 return self.fail("genSetReg called with a value larger than dst_reg", .{});
9708 switch (src_mcv) {9691 switch (src_mcv) {
...@@ -9727,7 +9710,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr...@@ -9727,7 +9710,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr
9727 try self.asmRegisterImmediate(9710 try self.asmRegisterImmediate(
9728 .{ ._, .mov },9711 .{ ._, .mov },
9729 registerAlias(dst_reg, abi_size),9712 registerAlias(dst_reg, abi_size),
9730 Immediate.s(@as(i32, @intCast(@as(i64, @bitCast(imm))))),9713 Immediate.s(@intCast(@as(i64, @bitCast(imm)))),
9731 );9714 );
9732 } else {9715 } else {
9733 try self.asmRegisterImmediate(9716 try self.asmRegisterImmediate(
...@@ -9785,7 +9768,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr...@@ -9785,7 +9768,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr
9785 .{ .register = try self.copyToTmpRegister(ty, src_mcv) },9768 .{ .register = try self.copyToTmpRegister(ty, src_mcv) },
9786 ),9769 ),
9787 .sse => try self.asmRegisterRegister(9770 .sse => try self.asmRegisterRegister(
9788 if (@as(?Mir.Inst.FixedTag, switch (ty.scalarType(mod).zigTypeTag(mod)) {9771 @as(?Mir.Inst.FixedTag, switch (ty.scalarType(mod).zigTypeTag(mod)) {
9789 else => switch (abi_size) {9772 else => switch (abi_size) {
9790 1...4 => if (self.hasFeature(.avx)) .{ .v_d, .mov } else .{ ._d, .mov },9773 1...4 => if (self.hasFeature(.avx)) .{ .v_d, .mov } else .{ ._d, .mov },
9791 5...8 => if (self.hasFeature(.avx)) .{ .v_q, .mov } else .{ ._q, .mov },9774 5...8 => if (self.hasFeature(.avx)) .{ .v_q, .mov } else .{ ._q, .mov },
...@@ -9809,7 +9792,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr...@@ -9809,7 +9792,7 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr
9809 80 => null,9792 80 => null,
9810 else => unreachable,9793 else => unreachable,
9811 },9794 },
9812 })) |tag| tag else return self.fail("TODO implement genSetReg for {}", .{9795 }) orelse return self.fail("TODO implement genSetReg for {}", .{
9813 ty.fmt(self.bin_file.options.module.?),9796 ty.fmt(self.bin_file.options.module.?),
9814 }),9797 }),
9815 registerAlias(dst_reg, abi_size),9798 registerAlias(dst_reg, abi_size),
...@@ -9989,9 +9972,9 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr...@@ -9989,9 +9972,9 @@ fn genSetReg(self: *Self, dst_reg: Register, ty: Type, src_mcv: MCValue) InnerEr
99899972
9990fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCValue) InnerError!void {9973fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCValue) InnerError!void {
9991 const mod = self.bin_file.options.module.?;9974 const mod = self.bin_file.options.module.?;
9992 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));9975 const abi_size: u32 = @intCast(ty.abiSize(mod));
9993 const dst_ptr_mcv: MCValue = switch (base) {9976 const dst_ptr_mcv: MCValue = switch (base) {
9994 .none => .{ .immediate = @as(u64, @bitCast(@as(i64, disp))) },9977 .none => .{ .immediate = @bitCast(@as(i64, disp)) },
9995 .reg => |base_reg| .{ .register_offset = .{ .reg = base_reg, .off = disp } },9978 .reg => |base_reg| .{ .register_offset = .{ .reg = base_reg, .off = disp } },
9996 .frame => |base_frame_index| .{ .lea_frame = .{ .index = base_frame_index, .off = disp } },9979 .frame => |base_frame_index| .{ .lea_frame = .{ .index = base_frame_index, .off = disp } },
9997 };9980 };
...@@ -10002,7 +9985,7 @@ fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCVal...@@ -10002,7 +9985,7 @@ fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCVal
10002 .immediate => |imm| switch (abi_size) {9985 .immediate => |imm| switch (abi_size) {
10003 1, 2, 4 => {9986 1, 2, 4 => {
10004 const immediate = if (ty.isSignedInt(mod))9987 const immediate = if (ty.isSignedInt(mod))
10005 Immediate.s(@as(i32, @truncate(@as(i64, @bitCast(imm)))))9988 Immediate.s(@truncate(@as(i64, @bitCast(imm))))
10006 else9989 else
10007 Immediate.u(@as(u32, @intCast(imm)));9990 Immediate.u(@as(u32, @intCast(imm)));
10008 try self.asmMemoryImmediate(9991 try self.asmMemoryImmediate(
...@@ -10024,10 +10007,9 @@ fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCVal...@@ -10024,10 +10007,9 @@ fn genSetMem(self: *Self, base: Memory.Base, disp: i32, ty: Type, src_mcv: MCVal
10024 .{ ._, .mov },10007 .{ ._, .mov },
10025 Memory.sib(.dword, .{ .base = base, .disp = disp + offset }),10008 Memory.sib(.dword, .{ .base = base, .disp = disp + offset }),
10026 if (ty.isSignedInt(mod))10009 if (ty.isSignedInt(mod))
10027 Immediate.s(@as(10010 Immediate.s(
10028 i32,
10029 @truncate(@as(i64, @bitCast(imm)) >> (math.cast(u6, offset * 8) orelse 63)),10011 @truncate(@as(i64, @bitCast(imm)) >> (math.cast(u6, offset * 8) orelse 63)),
10030 ))10012 )
10031 else10013 else
10032 Immediate.u(@as(10014 Immediate.u(@as(
10033 u32,10015 u32,
...@@ -10138,7 +10120,7 @@ fn genLazySymbolRef(...@@ -10138,7 +10120,7 @@ fn genLazySymbolRef(
10138 _ = try atom.getOrCreateOffsetTableEntry(elf_file);10120 _ = try atom.getOrCreateOffsetTableEntry(elf_file);
10139 const got_addr = atom.getOffsetTableAddress(elf_file);10121 const got_addr = atom.getOffsetTableAddress(elf_file);
10140 const got_mem =10122 const got_mem =
10141 Memory.sib(.qword, .{ .base = .{ .reg = .ds }, .disp = @as(i32, @intCast(got_addr)) });10123 Memory.sib(.qword, .{ .base = .{ .reg = .ds }, .disp = @intCast(got_addr) });
10142 switch (tag) {10124 switch (tag) {
10143 .lea, .mov => try self.asmRegisterMemory(.{ ._, .mov }, reg.to64(), got_mem),10125 .lea, .mov => try self.asmRegisterMemory(.{ ._, .mov }, reg.to64(), got_mem),
10144 .call => try self.asmMemory(.{ ._, .call }, got_mem),10126 .call => try self.asmMemory(.{ ._, .call }, got_mem),
...@@ -10160,7 +10142,7 @@ fn genLazySymbolRef(...@@ -10160,7 +10142,7 @@ fn genLazySymbolRef(
10160 _ = atom.getOrCreateOffsetTableEntry(p9_file);10142 _ = atom.getOrCreateOffsetTableEntry(p9_file);
10161 const got_addr = atom.getOffsetTableAddress(p9_file);10143 const got_addr = atom.getOffsetTableAddress(p9_file);
10162 const got_mem =10144 const got_mem =
10163 Memory.sib(.qword, .{ .base = .{ .reg = .ds }, .disp = @as(i32, @intCast(got_addr)) });10145 Memory.sib(.qword, .{ .base = .{ .reg = .ds }, .disp = @intCast(got_addr) });
10164 switch (tag) {10146 switch (tag) {
10165 .lea, .mov => try self.asmRegisterMemory(.{ ._, .mov }, reg.to64(), got_mem),10147 .lea, .mov => try self.asmRegisterMemory(.{ ._, .mov }, reg.to64(), got_mem),
10166 .call => try self.asmMemory(.{ ._, .call }, got_mem),10148 .call => try self.asmMemory(.{ ._, .call }, got_mem),
...@@ -10256,8 +10238,8 @@ fn airBitCast(self: *Self, inst: Air.Inst.Index) !void {...@@ -10256,8 +10238,8 @@ fn airBitCast(self: *Self, inst: Air.Inst.Index) !void {
10256 if (src_ty.isAbiInt(mod)) src_ty.intInfo(mod).signedness else .unsigned;10238 if (src_ty.isAbiInt(mod)) src_ty.intInfo(mod).signedness else .unsigned;
10257 if (dst_signedness == src_signedness) break :result dst_mcv;10239 if (dst_signedness == src_signedness) break :result dst_mcv;
1025810240
10259 const abi_size = @as(u16, @intCast(dst_ty.abiSize(mod)));10241 const abi_size: u16 = @intCast(dst_ty.abiSize(mod));
10260 const bit_size = @as(u16, @intCast(dst_ty.bitSize(mod)));10242 const bit_size: u16 = @intCast(dst_ty.bitSize(mod));
10261 if (abi_size * 8 <= bit_size) break :result dst_mcv;10243 if (abi_size * 8 <= bit_size) break :result dst_mcv;
1026210244
10263 const dst_limbs_len = math.divCeil(i32, bit_size, 64) catch unreachable;10245 const dst_limbs_len = math.divCeil(i32, bit_size, 64) catch unreachable;
...@@ -10298,7 +10280,7 @@ fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void {...@@ -10298,7 +10280,7 @@ fn airArrayToSlice(self: *Self, inst: Air.Inst.Index) !void {
10298 try self.genSetMem(.{ .frame = frame_index }, 0, ptr_ty, ptr);10280 try self.genSetMem(.{ .frame = frame_index }, 0, ptr_ty, ptr);
10299 try self.genSetMem(10281 try self.genSetMem(
10300 .{ .frame = frame_index },10282 .{ .frame = frame_index },
10301 @as(i32, @intCast(ptr_ty.abiSize(mod))),10283 @intCast(ptr_ty.abiSize(mod)),
10302 Type.usize,10284 Type.usize,
10303 .{ .immediate = array_len },10285 .{ .immediate = array_len },
10304 );10286 );
...@@ -10312,7 +10294,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void {...@@ -10312,7 +10294,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void {
10312 const ty_op = self.air.instructions.items(.data)[inst].ty_op;10294 const ty_op = self.air.instructions.items(.data)[inst].ty_op;
1031310295
10314 const src_ty = self.typeOf(ty_op.operand);10296 const src_ty = self.typeOf(ty_op.operand);
10315 const src_bits = @as(u32, @intCast(src_ty.bitSize(mod)));10297 const src_bits: u32 = @intCast(src_ty.bitSize(mod));
10316 const src_signedness =10298 const src_signedness =
10317 if (src_ty.isAbiInt(mod)) src_ty.intInfo(mod).signedness else .unsigned;10299 if (src_ty.isAbiInt(mod)) src_ty.intInfo(mod).signedness else .unsigned;
10318 const dst_ty = self.typeOfIndex(inst);10300 const dst_ty = self.typeOfIndex(inst);
...@@ -10340,7 +10322,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void {...@@ -10340,7 +10322,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void {
10340 const dst_lock = self.register_manager.lockRegAssumeUnused(dst_reg);10322 const dst_lock = self.register_manager.lockRegAssumeUnused(dst_reg);
10341 defer self.register_manager.unlockReg(dst_lock);10323 defer self.register_manager.unlockReg(dst_lock);
1034210324
10343 const mir_tag = if (@as(?Mir.Inst.FixedTag, switch (dst_ty.zigTypeTag(mod)) {10325 const mir_tag = @as(?Mir.Inst.FixedTag, switch (dst_ty.zigTypeTag(mod)) {
10344 .Float => switch (dst_ty.floatBits(self.target.*)) {10326 .Float => switch (dst_ty.floatBits(self.target.*)) {
10345 32 => if (self.hasFeature(.avx)) .{ .v_ss, .cvtsi2 } else .{ ._ss, .cvtsi2 },10327 32 => if (self.hasFeature(.avx)) .{ .v_ss, .cvtsi2 } else .{ ._ss, .cvtsi2 },
10346 64 => if (self.hasFeature(.avx)) .{ .v_sd, .cvtsi2 } else .{ ._sd, .cvtsi2 },10328 64 => if (self.hasFeature(.avx)) .{ .v_sd, .cvtsi2 } else .{ ._sd, .cvtsi2 },
...@@ -10348,7 +10330,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void {...@@ -10348,7 +10330,7 @@ fn airFloatFromInt(self: *Self, inst: Air.Inst.Index) !void {
10348 else => unreachable,10330 else => unreachable,
10349 },10331 },
10350 else => null,10332 else => null,
10351 })) |tag| tag else return self.fail("TODO implement airFloatFromInt from {} to {}", .{10333 }) orelse return self.fail("TODO implement airFloatFromInt from {} to {}", .{
10352 src_ty.fmt(mod), dst_ty.fmt(mod),10334 src_ty.fmt(mod), dst_ty.fmt(mod),
10353 });10335 });
10354 const dst_alias = dst_reg.to128();10336 const dst_alias = dst_reg.to128();
...@@ -10367,7 +10349,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void {...@@ -10367,7 +10349,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void {
1036710349
10368 const src_ty = self.typeOf(ty_op.operand);10350 const src_ty = self.typeOf(ty_op.operand);
10369 const dst_ty = self.typeOfIndex(inst);10351 const dst_ty = self.typeOfIndex(inst);
10370 const dst_bits = @as(u32, @intCast(dst_ty.bitSize(mod)));10352 const dst_bits: u32 = @intCast(dst_ty.bitSize(mod));
10371 const dst_signedness =10353 const dst_signedness =
10372 if (dst_ty.isAbiInt(mod)) dst_ty.intInfo(mod).signedness else .unsigned;10354 if (dst_ty.isAbiInt(mod)) dst_ty.intInfo(mod).signedness else .unsigned;
1037310355
...@@ -10393,7 +10375,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void {...@@ -10393,7 +10375,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void {
10393 defer self.register_manager.unlockReg(dst_lock);10375 defer self.register_manager.unlockReg(dst_lock);
1039410376
10395 try self.asmRegisterRegister(10377 try self.asmRegisterRegister(
10396 if (@as(?Mir.Inst.FixedTag, switch (src_ty.zigTypeTag(mod)) {10378 @as(?Mir.Inst.FixedTag, switch (src_ty.zigTypeTag(mod)) {
10397 .Float => switch (src_ty.floatBits(self.target.*)) {10379 .Float => switch (src_ty.floatBits(self.target.*)) {
10398 32 => if (self.hasFeature(.avx)) .{ .v_, .cvttss2si } else .{ ._, .cvttss2si },10380 32 => if (self.hasFeature(.avx)) .{ .v_, .cvttss2si } else .{ ._, .cvttss2si },
10399 64 => if (self.hasFeature(.avx)) .{ .v_, .cvttsd2si } else .{ ._, .cvttsd2si },10381 64 => if (self.hasFeature(.avx)) .{ .v_, .cvttsd2si } else .{ ._, .cvttsd2si },
...@@ -10401,7 +10383,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void {...@@ -10401,7 +10383,7 @@ fn airIntFromFloat(self: *Self, inst: Air.Inst.Index) !void {
10401 else => unreachable,10383 else => unreachable,
10402 },10384 },
10403 else => null,10385 else => null,
10404 })) |tag| tag else return self.fail("TODO implement airIntFromFloat from {} to {}", .{10386 }) orelse return self.fail("TODO implement airIntFromFloat from {} to {}", .{
10405 src_ty.fmt(self.bin_file.options.module.?), dst_ty.fmt(self.bin_file.options.module.?),10387 src_ty.fmt(self.bin_file.options.module.?), dst_ty.fmt(self.bin_file.options.module.?),
10406 }),10388 }),
10407 registerAlias(dst_reg, dst_size),10389 registerAlias(dst_reg, dst_size),
...@@ -10420,7 +10402,7 @@ fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void {...@@ -10420,7 +10402,7 @@ fn airCmpxchg(self: *Self, inst: Air.Inst.Index) !void {
1042010402
10421 const ptr_ty = self.typeOf(extra.ptr);10403 const ptr_ty = self.typeOf(extra.ptr);
10422 const val_ty = self.typeOf(extra.expected_value);10404 const val_ty = self.typeOf(extra.expected_value);
10423 const val_abi_size = @as(u32, @intCast(val_ty.abiSize(mod)));10405 const val_abi_size: u32 = @intCast(val_ty.abiSize(mod));
1042410406
10425 try self.spillRegisters(&.{ .rax, .rdx, .rbx, .rcx });10407 try self.spillRegisters(&.{ .rax, .rdx, .rbx, .rcx });
10426 const regs_lock = self.register_manager.lockRegsAssumeUnused(4, .{ .rax, .rdx, .rbx, .rcx });10408 const regs_lock = self.register_manager.lockRegsAssumeUnused(4, .{ .rax, .rdx, .rbx, .rcx });
...@@ -10522,7 +10504,7 @@ fn atomicOp(...@@ -10522,7 +10504,7 @@ fn atomicOp(
10522 };10504 };
10523 defer if (val_lock) |lock| self.register_manager.unlockReg(lock);10505 defer if (val_lock) |lock| self.register_manager.unlockReg(lock);
1052410506
10525 const val_abi_size = @as(u32, @intCast(val_ty.abiSize(mod)));10507 const val_abi_size: u32 = @intCast(val_ty.abiSize(mod));
10526 const ptr_size = Memory.PtrSize.fromSize(val_abi_size);10508 const ptr_size = Memory.PtrSize.fromSize(val_abi_size);
10527 const ptr_mem = switch (ptr_mcv) {10509 const ptr_mem = switch (ptr_mcv) {
10528 .immediate, .register, .register_offset, .lea_frame => ptr_mcv.deref().mem(ptr_size),10510 .immediate, .register, .register_offset, .lea_frame => ptr_mcv.deref().mem(ptr_size),
...@@ -10600,7 +10582,7 @@ fn atomicOp(...@@ -10600,7 +10582,7 @@ fn atomicOp(
10600 defer self.register_manager.unlockReg(tmp_lock);10582 defer self.register_manager.unlockReg(tmp_lock);
1060110583
10602 try self.asmRegisterMemory(.{ ._, .mov }, registerAlias(.rax, val_abi_size), ptr_mem);10584 try self.asmRegisterMemory(.{ ._, .mov }, registerAlias(.rax, val_abi_size), ptr_mem);
10603 const loop = @as(u32, @intCast(self.mir_instructions.len));10585 const loop: u32 = @intCast(self.mir_instructions.len);
10604 if (rmw_op != std.builtin.AtomicRmwOp.Xchg) {10586 if (rmw_op != std.builtin.AtomicRmwOp.Xchg) {
10605 try self.genSetReg(tmp_reg, val_ty, .{ .register = .rax });10587 try self.genSetReg(tmp_reg, val_ty, .{ .register = .rax });
10606 }10588 }
...@@ -10674,7 +10656,7 @@ fn atomicOp(...@@ -10674,7 +10656,7 @@ fn atomicOp(
10674 .scale_index = ptr_mem.scaleIndex(),10656 .scale_index = ptr_mem.scaleIndex(),
10675 .disp = ptr_mem.sib.disp + 8,10657 .disp = ptr_mem.sib.disp + 8,
10676 }));10658 }));
10677 const loop = @as(u32, @intCast(self.mir_instructions.len));10659 const loop: u32 = @intCast(self.mir_instructions.len);
10678 const val_mem_mcv: MCValue = switch (val_mcv) {10660 const val_mem_mcv: MCValue = switch (val_mcv) {
10679 .memory, .indirect, .load_frame => val_mcv,10661 .memory, .indirect, .load_frame => val_mcv,
10680 else => .{ .indirect = .{10662 else => .{ .indirect = .{
...@@ -10830,7 +10812,7 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void {...@@ -10830,7 +10812,7 @@ fn airMemset(self: *Self, inst: Air.Inst.Index, safety: bool) !void {
10830 };10812 };
10831 defer if (src_val_lock) |lock| self.register_manager.unlockReg(lock);10813 defer if (src_val_lock) |lock| self.register_manager.unlockReg(lock);
1083210814
10833 const elem_abi_size = @as(u31, @intCast(elem_ty.abiSize(mod)));10815 const elem_abi_size: u31 = @intCast(elem_ty.abiSize(mod));
1083410816
10835 if (elem_abi_size == 1) {10817 if (elem_abi_size == 1) {
10836 const ptr: MCValue = switch (dst_ptr_ty.ptrSize(mod)) {10818 const ptr: MCValue = switch (dst_ptr_ty.ptrSize(mod)) {
...@@ -11310,9 +11292,9 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void {...@@ -11310,9 +11292,9 @@ fn airReduce(self: *Self, inst: Air.Inst.Index) !void {
11310fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {11292fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {
11311 const mod = self.bin_file.options.module.?;11293 const mod = self.bin_file.options.module.?;
11312 const result_ty = self.typeOfIndex(inst);11294 const result_ty = self.typeOfIndex(inst);
11313 const len = @as(usize, @intCast(result_ty.arrayLen(mod)));11295 const len: usize = @intCast(result_ty.arrayLen(mod));
11314 const ty_pl = self.air.instructions.items(.data)[inst].ty_pl;11296 const ty_pl = self.air.instructions.items(.data)[inst].ty_pl;
11315 const elements = @as([]const Air.Inst.Ref, @ptrCast(self.air.extra[ty_pl.payload..][0..len]));11297 const elements: []const Air.Inst.Ref = @ptrCast(self.air.extra[ty_pl.payload..][0..len]);
11316 const result: MCValue = result: {11298 const result: MCValue = result: {
11317 switch (result_ty.zigTypeTag(mod)) {11299 switch (result_ty.zigTypeTag(mod)) {
11318 .Struct => {11300 .Struct => {
...@@ -11329,17 +11311,17 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {...@@ -11329,17 +11311,17 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {
11329 if ((try result_ty.structFieldValueComptime(mod, elem_i)) != null) continue;11311 if ((try result_ty.structFieldValueComptime(mod, elem_i)) != null) continue;
1133011312
11331 const elem_ty = result_ty.structFieldType(elem_i, mod);11313 const elem_ty = result_ty.structFieldType(elem_i, mod);
11332 const elem_bit_size = @as(u32, @intCast(elem_ty.bitSize(mod)));11314 const elem_bit_size: u32 = @intCast(elem_ty.bitSize(mod));
11333 if (elem_bit_size > 64) {11315 if (elem_bit_size > 64) {
11334 return self.fail(11316 return self.fail(
11335 "TODO airAggregateInit implement packed structs with large fields",11317 "TODO airAggregateInit implement packed structs with large fields",
11336 .{},11318 .{},
11337 );11319 );
11338 }11320 }
11339 const elem_abi_size = @as(u32, @intCast(elem_ty.abiSize(mod)));11321 const elem_abi_size: u32 = @intCast(elem_ty.abiSize(mod));
11340 const elem_abi_bits = elem_abi_size * 8;11322 const elem_abi_bits = elem_abi_size * 8;
11341 const elem_off = struct_obj.packedFieldBitOffset(mod, elem_i);11323 const elem_off = struct_obj.packedFieldBitOffset(mod, elem_i);
11342 const elem_byte_off = @as(i32, @intCast(elem_off / elem_abi_bits * elem_abi_size));11324 const elem_byte_off: i32 = @intCast(elem_off / elem_abi_bits * elem_abi_size);
11343 const elem_bit_off = elem_off % elem_abi_bits;11325 const elem_bit_off = elem_off % elem_abi_bits;
11344 const elem_mcv = try self.resolveInst(elem);11326 const elem_mcv = try self.resolveInst(elem);
11345 const mat_elem_mcv = switch (elem_mcv) {11327 const mat_elem_mcv = switch (elem_mcv) {
...@@ -11401,7 +11383,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {...@@ -11401,7 +11383,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {
11401 if ((try result_ty.structFieldValueComptime(mod, elem_i)) != null) continue;11383 if ((try result_ty.structFieldValueComptime(mod, elem_i)) != null) continue;
1140211384
11403 const elem_ty = result_ty.structFieldType(elem_i, mod);11385 const elem_ty = result_ty.structFieldType(elem_i, mod);
11404 const elem_off = @as(i32, @intCast(result_ty.structFieldOffset(elem_i, mod)));11386 const elem_off: i32 = @intCast(result_ty.structFieldOffset(elem_i, mod));
11405 const elem_mcv = try self.resolveInst(elem);11387 const elem_mcv = try self.resolveInst(elem);
11406 const mat_elem_mcv = switch (elem_mcv) {11388 const mat_elem_mcv = switch (elem_mcv) {
11407 .load_tlv => |sym_index| MCValue{ .lea_tlv = sym_index },11389 .load_tlv => |sym_index| MCValue{ .lea_tlv = sym_index },
...@@ -11415,7 +11397,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {...@@ -11415,7 +11397,7 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {
11415 const frame_index =11397 const frame_index =
11416 try self.allocFrameIndex(FrameAlloc.initType(result_ty, mod));11398 try self.allocFrameIndex(FrameAlloc.initType(result_ty, mod));
11417 const elem_ty = result_ty.childType(mod);11399 const elem_ty = result_ty.childType(mod);
11418 const elem_size = @as(u32, @intCast(elem_ty.abiSize(mod)));11400 const elem_size: u32 = @intCast(elem_ty.abiSize(mod));
1141911401
11420 for (elements, 0..) |elem, elem_i| {11402 for (elements, 0..) |elem, elem_i| {
11421 const elem_mcv = try self.resolveInst(elem);11403 const elem_mcv = try self.resolveInst(elem);
...@@ -11423,12 +11405,12 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {...@@ -11423,12 +11405,12 @@ fn airAggregateInit(self: *Self, inst: Air.Inst.Index) !void {
11423 .load_tlv => |sym_index| MCValue{ .lea_tlv = sym_index },11405 .load_tlv => |sym_index| MCValue{ .lea_tlv = sym_index },
11424 else => elem_mcv,11406 else => elem_mcv,
11425 };11407 };
11426 const elem_off = @as(i32, @intCast(elem_size * elem_i));11408 const elem_off: i32 = @intCast(elem_size * elem_i);
11427 try self.genSetMem(.{ .frame = frame_index }, elem_off, elem_ty, mat_elem_mcv);11409 try self.genSetMem(.{ .frame = frame_index }, elem_off, elem_ty, mat_elem_mcv);
11428 }11410 }
11429 if (result_ty.sentinel(mod)) |sentinel| try self.genSetMem(11411 if (result_ty.sentinel(mod)) |sentinel| try self.genSetMem(
11430 .{ .frame = frame_index },11412 .{ .frame = frame_index },
11431 @as(i32, @intCast(elem_size * elements.len)),11413 @intCast(elem_size * elements.len),
11432 elem_ty,11414 elem_ty,
11433 try self.genTypedValue(.{ .ty = elem_ty, .val = sentinel }),11415 try self.genTypedValue(.{ .ty = elem_ty, .val = sentinel }),
11434 );11416 );
...@@ -11476,16 +11458,16 @@ fn airUnionInit(self: *Self, inst: Air.Inst.Index) !void {...@@ -11476,16 +11458,16 @@ fn airUnionInit(self: *Self, inst: Air.Inst.Index) !void {
11476 const tag_val = try mod.enumValueFieldIndex(tag_ty, field_index);11458 const tag_val = try mod.enumValueFieldIndex(tag_ty, field_index);
11477 const tag_int_val = try tag_val.intFromEnum(tag_ty, mod);11459 const tag_int_val = try tag_val.intFromEnum(tag_ty, mod);
11478 const tag_int = tag_int_val.toUnsignedInt(mod);11460 const tag_int = tag_int_val.toUnsignedInt(mod);
11479 const tag_off = if (layout.tag_align < layout.payload_align)11461 const tag_off: i32 = if (layout.tag_align < layout.payload_align)
11480 @as(i32, @intCast(layout.payload_size))11462 @intCast(layout.payload_size)
11481 else11463 else
11482 0;11464 0;
11483 try self.genCopy(tag_ty, dst_mcv.address().offset(tag_off).deref(), .{ .immediate = tag_int });11465 try self.genCopy(tag_ty, dst_mcv.address().offset(tag_off).deref(), .{ .immediate = tag_int });
1148411466
11485 const pl_off = if (layout.tag_align < layout.payload_align)11467 const pl_off: i32 = if (layout.tag_align < layout.payload_align)
11486 011468 0
11487 else11469 else
11488 @as(i32, @intCast(layout.tag_size));11470 @intCast(layout.tag_size);
11489 try self.genCopy(src_ty, dst_mcv.address().offset(pl_off).deref(), src_mcv);11471 try self.genCopy(src_ty, dst_mcv.address().offset(pl_off).deref(), src_mcv);
1149011472
11491 break :result dst_mcv;11473 break :result dst_mcv;
...@@ -11515,7 +11497,7 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void {...@@ -11515,7 +11497,7 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void {
11515 var order = [1]u2{0} ** 3;11497 var order = [1]u2{0} ** 3;
11516 var unused = std.StaticBitSet(3).initFull();11498 var unused = std.StaticBitSet(3).initFull();
11517 for (ops, &mcvs, &locks, 0..) |op, *mcv, *lock, op_i| {11499 for (ops, &mcvs, &locks, 0..) |op, *mcv, *lock, op_i| {
11518 const op_index = @as(u2, @intCast(op_i));11500 const op_index: u2 = @intCast(op_i);
11519 mcv.* = try self.resolveInst(op);11501 mcv.* = try self.resolveInst(op);
11520 if (unused.isSet(0) and mcv.isRegister() and self.reuseOperand(inst, op, op_index, mcv.*)) {11502 if (unused.isSet(0) and mcv.isRegister() and self.reuseOperand(inst, op, op_index, mcv.*)) {
11521 order[op_index] = 1;11503 order[op_index] = 1;
...@@ -11539,99 +11521,97 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void {...@@ -11539,99 +11521,97 @@ fn airMulAdd(self: *Self, inst: Air.Inst.Index) !void {
11539 lock.* = self.register_manager.lockRegAssumeUnused(reg);11521 lock.* = self.register_manager.lockRegAssumeUnused(reg);
11540 }11522 }
1154111523
11542 const mir_tag = if (@as(11524 const mir_tag = @as(?Mir.Inst.FixedTag, if (mem.eql(u2, &order, &.{ 1, 3, 2 }) or
11543 ?Mir.Inst.FixedTag,11525 mem.eql(u2, &order, &.{ 3, 1, 2 }))
11544 if (mem.eql(u2, &order, &.{ 1, 3, 2 }) or mem.eql(u2, &order, &.{ 3, 1, 2 }))11526 switch (ty.zigTypeTag(mod)) {
11545 switch (ty.zigTypeTag(mod)) {11527 .Float => switch (ty.floatBits(self.target.*)) {
11546 .Float => switch (ty.floatBits(self.target.*)) {11528 32 => .{ .v_ss, .fmadd132 },
11547 32 => .{ .v_ss, .fmadd132 },11529 64 => .{ .v_sd, .fmadd132 },
11548 64 => .{ .v_sd, .fmadd132 },11530 16, 80, 128 => null,
11549 16, 80, 128 => null,
11550 else => unreachable,
11551 },
11552 .Vector => switch (ty.childType(mod).zigTypeTag(mod)) {
11553 .Float => switch (ty.childType(mod).floatBits(self.target.*)) {
11554 32 => switch (ty.vectorLen(mod)) {
11555 1 => .{ .v_ss, .fmadd132 },
11556 2...8 => .{ .v_ps, .fmadd132 },
11557 else => null,
11558 },
11559 64 => switch (ty.vectorLen(mod)) {
11560 1 => .{ .v_sd, .fmadd132 },
11561 2...4 => .{ .v_pd, .fmadd132 },
11562 else => null,
11563 },
11564 16, 80, 128 => null,
11565 else => unreachable,
11566 },
11567 else => unreachable,
11568 },
11569 else => unreachable,11531 else => unreachable,
11570 }11532 },
11571 else if (mem.eql(u2, &order, &.{ 2, 1, 3 }) or mem.eql(u2, &order, &.{ 1, 2, 3 }))11533 .Vector => switch (ty.childType(mod).zigTypeTag(mod)) {
11572 switch (ty.zigTypeTag(mod)) {11534 .Float => switch (ty.childType(mod).floatBits(self.target.*)) {
11573 .Float => switch (ty.floatBits(self.target.*)) {11535 32 => switch (ty.vectorLen(mod)) {
11574 32 => .{ .v_ss, .fmadd213 },11536 1 => .{ .v_ss, .fmadd132 },
11575 64 => .{ .v_sd, .fmadd213 },11537 2...8 => .{ .v_ps, .fmadd132 },
11576 16, 80, 128 => null,11538 else => null,
11577 else => unreachable,
11578 },
11579 .Vector => switch (ty.childType(mod).zigTypeTag(mod)) {
11580 .Float => switch (ty.childType(mod).floatBits(self.target.*)) {
11581 32 => switch (ty.vectorLen(mod)) {
11582 1 => .{ .v_ss, .fmadd213 },
11583 2...8 => .{ .v_ps, .fmadd213 },
11584 else => null,
11585 },
11586 64 => switch (ty.vectorLen(mod)) {
11587 1 => .{ .v_sd, .fmadd213 },
11588 2...4 => .{ .v_pd, .fmadd213 },
11589 else => null,
11590 },
11591 16, 80, 128 => null,
11592 else => unreachable,
11593 },11539 },
11540 64 => switch (ty.vectorLen(mod)) {
11541 1 => .{ .v_sd, .fmadd132 },
11542 2...4 => .{ .v_pd, .fmadd132 },
11543 else => null,
11544 },
11545 16, 80, 128 => null,
11594 else => unreachable,11546 else => unreachable,
11595 },11547 },
11596 else => unreachable,11548 else => unreachable,
11597 }11549 },
11598 else if (mem.eql(u2, &order, &.{ 2, 3, 1 }) or mem.eql(u2, &order, &.{ 3, 2, 1 }))11550 else => unreachable,
11599 switch (ty.zigTypeTag(mod)) {11551 }
11600 .Float => switch (ty.floatBits(self.target.*)) {11552 else if (mem.eql(u2, &order, &.{ 2, 1, 3 }) or mem.eql(u2, &order, &.{ 1, 2, 3 }))
11601 32 => .{ .v_ss, .fmadd231 },11553 switch (ty.zigTypeTag(mod)) {
11602 64 => .{ .v_sd, .fmadd231 },11554 .Float => switch (ty.floatBits(self.target.*)) {
11555 32 => .{ .v_ss, .fmadd213 },
11556 64 => .{ .v_sd, .fmadd213 },
11557 16, 80, 128 => null,
11558 else => unreachable,
11559 },
11560 .Vector => switch (ty.childType(mod).zigTypeTag(mod)) {
11561 .Float => switch (ty.childType(mod).floatBits(self.target.*)) {
11562 32 => switch (ty.vectorLen(mod)) {
11563 1 => .{ .v_ss, .fmadd213 },
11564 2...8 => .{ .v_ps, .fmadd213 },
11565 else => null,
11566 },
11567 64 => switch (ty.vectorLen(mod)) {
11568 1 => .{ .v_sd, .fmadd213 },
11569 2...4 => .{ .v_pd, .fmadd213 },
11570 else => null,
11571 },
11603 16, 80, 128 => null,11572 16, 80, 128 => null,
11604 else => unreachable,11573 else => unreachable,
11605 },11574 },
11606 .Vector => switch (ty.childType(mod).zigTypeTag(mod)) {11575 else => unreachable,
11607 .Float => switch (ty.childType(mod).floatBits(self.target.*)) {11576 },
11608 32 => switch (ty.vectorLen(mod)) {11577 else => unreachable,
11609 1 => .{ .v_ss, .fmadd231 },11578 }
11610 2...8 => .{ .v_ps, .fmadd231 },11579 else if (mem.eql(u2, &order, &.{ 2, 3, 1 }) or mem.eql(u2, &order, &.{ 3, 2, 1 }))
11611 else => null,11580 switch (ty.zigTypeTag(mod)) {
11612 },11581 .Float => switch (ty.floatBits(self.target.*)) {
11613 64 => switch (ty.vectorLen(mod)) {11582 32 => .{ .v_ss, .fmadd231 },
11614 1 => .{ .v_sd, .fmadd231 },11583 64 => .{ .v_sd, .fmadd231 },
11615 2...4 => .{ .v_pd, .fmadd231 },11584 16, 80, 128 => null,
11616 else => null,11585 else => unreachable,
11617 },11586 },
11618 16, 80, 128 => null,11587 .Vector => switch (ty.childType(mod).zigTypeTag(mod)) {
11619 else => unreachable,11588 .Float => switch (ty.childType(mod).floatBits(self.target.*)) {
11589 32 => switch (ty.vectorLen(mod)) {
11590 1 => .{ .v_ss, .fmadd231 },
11591 2...8 => .{ .v_ps, .fmadd231 },
11592 else => null,
11593 },
11594 64 => switch (ty.vectorLen(mod)) {
11595 1 => .{ .v_sd, .fmadd231 },
11596 2...4 => .{ .v_pd, .fmadd231 },
11597 else => null,
11620 },11598 },
11599 16, 80, 128 => null,
11621 else => unreachable,11600 else => unreachable,
11622 },11601 },
11623 else => unreachable,11602 else => unreachable,
11624 }11603 },
11625 else11604 else => unreachable,
11626 unreachable,11605 }
11627 )) |tag| tag else return self.fail("TODO implement airMulAdd for {}", .{11606 else
11607 unreachable) orelse return self.fail("TODO implement airMulAdd for {}", .{
11628 ty.fmt(self.bin_file.options.module.?),11608 ty.fmt(self.bin_file.options.module.?),
11629 });11609 });
1163011610
11631 var mops: [3]MCValue = undefined;11611 var mops: [3]MCValue = undefined;
11632 for (order, mcvs) |mop_index, mcv| mops[mop_index - 1] = mcv;11612 for (order, mcvs) |mop_index, mcv| mops[mop_index - 1] = mcv;
1163311613
11634 const abi_size = @as(u32, @intCast(ty.abiSize(mod)));11614 const abi_size: u32 = @intCast(ty.abiSize(mod));
11635 const mop1_reg = registerAlias(mops[0].getReg().?, abi_size);11615 const mop1_reg = registerAlias(mops[0].getReg().?, abi_size);
11636 const mop2_reg = registerAlias(mops[1].getReg().?, abi_size);11616 const mop2_reg = registerAlias(mops[1].getReg().?, abi_size);
11637 if (mops[2].isRegister()) try self.asmRegisterRegisterRegister(11617 if (mops[2].isRegister()) try self.asmRegisterRegisterRegister(
...@@ -11784,7 +11764,7 @@ fn resolveCallingConventionValues(...@@ -11784,7 +11764,7 @@ fn resolveCallingConventionValues(
11784 switch (self.target.os.tag) {11764 switch (self.target.os.tag) {
11785 .windows => {11765 .windows => {
11786 // Align the stack to 16bytes before allocating shadow stack space (if any).11766 // Align the stack to 16bytes before allocating shadow stack space (if any).
11787 result.stack_byte_count += @as(u31, @intCast(4 * Type.usize.abiSize(mod)));11767 result.stack_byte_count += @intCast(4 * Type.usize.abiSize(mod));
11788 },11768 },
11789 else => {},11769 else => {},
11790 }11770 }
...@@ -11807,7 +11787,7 @@ fn resolveCallingConventionValues(...@@ -11807,7 +11787,7 @@ fn resolveCallingConventionValues(
11807 result.return_value = switch (classes[0]) {11787 result.return_value = switch (classes[0]) {
11808 .integer => InstTracking.init(.{ .register = registerAlias(11788 .integer => InstTracking.init(.{ .register = registerAlias(
11809 ret_reg,11789 ret_reg,
11810 @as(u32, @intCast(ret_ty.abiSize(mod))),11790 @intCast(ret_ty.abiSize(mod)),
11811 ) }),11791 ) }),
11812 .float, .sse => InstTracking.init(.{ .register = .xmm0 }),11792 .float, .sse => InstTracking.init(.{ .register = .xmm0 }),
11813 .memory => ret: {11793 .memory => ret: {
...@@ -11843,18 +11823,16 @@ fn resolveCallingConventionValues(...@@ -11843,18 +11823,16 @@ fn resolveCallingConventionValues(
11843 },11823 },
11844 .float, .sse => switch (self.target.os.tag) {11824 .float, .sse => switch (self.target.os.tag) {
11845 .windows => if (param_reg_i < 4) {11825 .windows => if (param_reg_i < 4) {
11846 arg.* = .{ .register = @as(11826 arg.* = .{
11847 Register,11827 .register = @enumFromInt(@intFromEnum(Register.xmm0) + param_reg_i),
11848 @enumFromInt(@intFromEnum(Register.xmm0) + param_reg_i),11828 };
11849 ) };
11850 param_reg_i += 1;11829 param_reg_i += 1;
11851 continue;11830 continue;
11852 },11831 },
11853 else => if (param_sse_reg_i < 8) {11832 else => if (param_sse_reg_i < 8) {
11854 arg.* = .{ .register = @as(11833 arg.* = .{
11855 Register,11834 .register = @enumFromInt(@intFromEnum(Register.xmm0) + param_sse_reg_i),
11856 @enumFromInt(@intFromEnum(Register.xmm0) + param_sse_reg_i),11835 };
11857 ) };
11858 param_sse_reg_i += 1;11836 param_sse_reg_i += 1;
11859 continue;11837 continue;
11860 },11838 },
...@@ -11865,8 +11843,8 @@ fn resolveCallingConventionValues(...@@ -11865,8 +11843,8 @@ fn resolveCallingConventionValues(
11865 }),11843 }),
11866 }11844 }
1186711845
11868 const param_size = @as(u31, @intCast(ty.abiSize(mod)));11846 const param_size: u31 = @intCast(ty.abiSize(mod));
11869 const param_align = @as(u31, @intCast(ty.abiAlignment(mod)));11847 const param_align: u31 = @intCast(ty.abiAlignment(mod));
11870 result.stack_byte_count =11848 result.stack_byte_count =
11871 mem.alignForward(u31, result.stack_byte_count, param_align);11849 mem.alignForward(u31, result.stack_byte_count, param_align);
11872 arg.* = .{ .load_frame = .{11850 arg.* = .{ .load_frame = .{
...@@ -11886,7 +11864,7 @@ fn resolveCallingConventionValues(...@@ -11886,7 +11864,7 @@ fn resolveCallingConventionValues(
11886 result.return_value = InstTracking.init(.none);11864 result.return_value = InstTracking.init(.none);
11887 } else {11865 } else {
11888 const ret_reg = abi.getCAbiIntReturnRegs(self.target.*)[0];11866 const ret_reg = abi.getCAbiIntReturnRegs(self.target.*)[0];
11889 const ret_ty_size = @as(u31, @intCast(ret_ty.abiSize(mod)));11867 const ret_ty_size: u31 = @intCast(ret_ty.abiSize(mod));
11890 if (ret_ty_size <= 8 and !ret_ty.isRuntimeFloat()) {11868 if (ret_ty_size <= 8 and !ret_ty.isRuntimeFloat()) {
11891 const aliased_reg = registerAlias(ret_reg, ret_ty_size);11869 const aliased_reg = registerAlias(ret_reg, ret_ty_size);
11892 result.return_value = .{ .short = .{ .register = aliased_reg }, .long = .none };11870 result.return_value = .{ .short = .{ .register = aliased_reg }, .long = .none };
...@@ -11905,8 +11883,8 @@ fn resolveCallingConventionValues(...@@ -11905,8 +11883,8 @@ fn resolveCallingConventionValues(
11905 arg.* = .none;11883 arg.* = .none;
11906 continue;11884 continue;
11907 }11885 }
11908 const param_size = @as(u31, @intCast(ty.abiSize(mod)));11886 const param_size: u31 = @intCast(ty.abiSize(mod));
11909 const param_align = @as(u31, @intCast(ty.abiAlignment(mod)));11887 const param_align: u31 = @intCast(ty.abiAlignment(mod));
11910 result.stack_byte_count =11888 result.stack_byte_count =
11911 mem.alignForward(u31, result.stack_byte_count, param_align);11889 mem.alignForward(u31, result.stack_byte_count, param_align);
11912 arg.* = .{ .load_frame = .{11890 arg.* = .{ .load_frame = .{
...@@ -11993,12 +11971,12 @@ fn truncateRegister(self: *Self, ty: Type, reg: Register) !void {...@@ -11993,12 +11971,12 @@ fn truncateRegister(self: *Self, ty: Type, reg: Register) !void {
11993 const mod = self.bin_file.options.module.?;11971 const mod = self.bin_file.options.module.?;
11994 const int_info = if (ty.isAbiInt(mod)) ty.intInfo(mod) else std.builtin.Type.Int{11972 const int_info = if (ty.isAbiInt(mod)) ty.intInfo(mod) else std.builtin.Type.Int{
11995 .signedness = .unsigned,11973 .signedness = .unsigned,
11996 .bits = @as(u16, @intCast(ty.bitSize(mod))),11974 .bits = @intCast(ty.bitSize(mod)),
11997 };11975 };
11998 const max_reg_bit_width = Register.rax.bitSize();11976 const max_reg_bit_width = Register.rax.bitSize();
11999 switch (int_info.signedness) {11977 switch (int_info.signedness) {
12000 .signed => {11978 .signed => {
12001 const shift = @as(u6, @intCast(max_reg_bit_width - int_info.bits));11979 const shift: u6 = @intCast(max_reg_bit_width - int_info.bits);
12002 try self.genShiftBinOpMir(11980 try self.genShiftBinOpMir(
12003 .{ ._l, .sa },11981 .{ ._l, .sa },
12004 Type.isize,11982 Type.isize,
...@@ -12013,8 +11991,8 @@ fn truncateRegister(self: *Self, ty: Type, reg: Register) !void {...@@ -12013,8 +11991,8 @@ fn truncateRegister(self: *Self, ty: Type, reg: Register) !void {
12013 );11991 );
12014 },11992 },
12015 .unsigned => {11993 .unsigned => {
12016 const shift = @as(u6, @intCast(max_reg_bit_width - int_info.bits));11994 const shift: u6 = @intCast(max_reg_bit_width - int_info.bits);
12017 const mask = (~@as(u64, 0)) >> shift;11995 const mask = ~@as(u64, 0) >> shift;
12018 if (int_info.bits <= 32) {11996 if (int_info.bits <= 32) {
12019 try self.genBinOpMir(11997 try self.genBinOpMir(
12020 .{ ._, .@"and" },11998 .{ ._, .@"and" },