| ... | ... | @@ -4004,10 +4004,10 @@ fn genBody(cg: *CodeGen, body: []const Air.Inst.Index) InnerError!void { |
| 4004 | 4004 | } }); |
| 4005 | 4005 | try slot.moveTo(inst, cg); |
| 4006 | 4006 | }, |
| 4007 | | .call => try cg.airCall(inst, .auto), |
| 4008 | | .call_always_tail => try cg.airCall(inst, .always_tail), |
| 4009 | | .call_never_tail => try cg.airCall(inst, .never_tail), |
| 4010 | | .call_never_inline => try cg.airCall(inst, .never_inline), |
| 4007 | .call => try cg.airCall(inst, .auto, .{ .safety = true }), |
| 4008 | .call_always_tail => try cg.airCall(inst, .always_tail, .{ .safety = true }), |
| 4009 | .call_never_tail => try cg.airCall(inst, .never_tail, .{ .safety = true }), |
| 4010 | .call_never_inline => try cg.airCall(inst, .never_inline, .{ .safety = true }), |
| 4011 | 4011 | |
| 4012 | 4012 | .clz => |air_tag| if (use_old) try cg.airClz(inst) else { |
| 4013 | 4013 | const ty_op = air_datas[@intFromEnum(inst)].ty_op; |
| ... | ... | @@ -10136,7 +10136,7 @@ fn airFptrunc(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 10136 | 10136 | floatCompilerRtAbiName(src_bits), |
| 10137 | 10137 | floatCompilerRtAbiName(dst_bits), |
| 10138 | 10138 | }) catch unreachable, |
| 10139 | | } }, &.{src_ty}, &.{.{ .air_ref = ty_op.operand }}); |
| 10139 | } }, &.{src_ty}, &.{.{ .air_ref = ty_op.operand }}, .{}); |
| 10140 | 10140 | } |
| 10141 | 10141 | |
| 10142 | 10142 | const src_mcv = try self.resolveInst(ty_op.operand); |
| ... | ... | @@ -10240,7 +10240,7 @@ fn airFpext(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 10240 | 10240 | floatCompilerRtAbiName(src_bits), |
| 10241 | 10241 | floatCompilerRtAbiName(dst_bits), |
| 10242 | 10242 | }) catch unreachable, |
| 10243 | | } }, &.{src_scalar_ty}, &.{.{ .air_ref = ty_op.operand }}); |
| 10243 | } }, &.{src_scalar_ty}, &.{.{ .air_ref = ty_op.operand }}, .{}); |
| 10244 | 10244 | } |
| 10245 | 10245 | |
| 10246 | 10246 | const src_abi_size: u32 = @intCast(src_ty.abiSize(zcu)); |
| ... | ... | @@ -10969,6 +10969,7 @@ fn airMulDivBinOp(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 10969 | 10969 | } }, |
| 10970 | 10970 | &.{ src_ty, src_ty }, |
| 10971 | 10971 | &.{ .{ .air_ref = bin_op.lhs }, .{ .air_ref = bin_op.rhs } }, |
| 10972 | .{}, |
| 10972 | 10973 | ); |
| 10973 | 10974 | break :result if (signed) switch (tag) { |
| 10974 | 10975 | .div_floor => { |
| ... | ... | @@ -10998,6 +10999,7 @@ fn airMulDivBinOp(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 10998 | 10999 | } }, |
| 10999 | 11000 | &.{ src_ty, src_ty }, |
| 11000 | 11001 | &.{ .{ .air_ref = bin_op.lhs }, .{ .air_ref = bin_op.rhs } }, |
| 11002 | .{}, |
| 11001 | 11003 | ); |
| 11002 | 11004 | try self.asmRegisterMemory( |
| 11003 | 11005 | .{ ._, .sub }, |
| ... | ... | @@ -11247,7 +11249,7 @@ fn airMulSat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 11247 | 11249 | .{ .air_ref = bin_op.lhs }, |
| 11248 | 11250 | .{ .air_ref = bin_op.rhs }, |
| 11249 | 11251 | overflow.address(), |
| 11250 | | }); |
| 11252 | }, .{}); |
| 11251 | 11253 | const dst_locks = self.register_manager.lockRegsAssumeUnused(2, dst_mcv.register_pair); |
| 11252 | 11254 | defer for (dst_locks) |lock| self.register_manager.unlockReg(lock); |
| 11253 | 11255 | |
| ... | ... | @@ -11748,7 +11750,7 @@ fn airMulWithOverflow(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 11748 | 11750 | .{ .air_ref = bin_op.lhs }, |
| 11749 | 11751 | .{ .air_ref = bin_op.rhs }, |
| 11750 | 11752 | overflow.address(), |
| 11751 | | }); |
| 11753 | }, .{}); |
| 11752 | 11754 | |
| 11753 | 11755 | const dst_mcv = try self.allocRegOrMem(inst, false); |
| 11754 | 11756 | try self.genSetMem( |
| ... | ... | @@ -14413,7 +14415,7 @@ fn genRoundLibcall(self: *CodeGen, ty: Type, src_mcv: MCValue, mode: RoundMode) |
| 14413 | 14415 | }, |
| 14414 | 14416 | floatLibcAbiSuffix(ty), |
| 14415 | 14417 | }) catch unreachable, |
| 14416 | | } }, &.{ty}, &.{src_mcv}); |
| 14418 | } }, &.{ty}, &.{src_mcv}, .{}); |
| 14417 | 14419 | } |
| 14418 | 14420 | |
| 14419 | 14421 | fn genRound(self: *CodeGen, ty: Type, dst_reg: Register, src_mcv: MCValue, mode: RoundMode) !void { |
| ... | ... | @@ -14684,7 +14686,7 @@ fn airSqrt(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 14684 | 14686 | floatLibcAbiPrefix(ty), |
| 14685 | 14687 | floatLibcAbiSuffix(ty), |
| 14686 | 14688 | }) catch unreachable, |
| 14687 | | } }, &.{ty}, &.{.{ .air_ref = un_op }}); |
| 14689 | } }, &.{ty}, &.{.{ .air_ref = un_op }}, .{}); |
| 14688 | 14690 | } |
| 14689 | 14691 | }, |
| 14690 | 14692 | else => {}, |
| ... | ... | @@ -14850,7 +14852,7 @@ fn airUnaryMath(self: *CodeGen, inst: Air.Inst.Index, tag: Air.Inst.Tag) !void { |
| 14850 | 14852 | }, |
| 14851 | 14853 | floatLibcAbiSuffix(ty), |
| 14852 | 14854 | }) catch unreachable, |
| 14853 | | } }, &.{ty}, &.{.{ .air_ref = un_op }}); |
| 14855 | } }, &.{ty}, &.{.{ .air_ref = un_op }}, .{}); |
| 14854 | 14856 | return self.finishAir(inst, result, .{ un_op, .none, .none }); |
| 14855 | 14857 | } |
| 14856 | 14858 | |
| ... | ... | @@ -16689,7 +16691,7 @@ fn genMulDivBinOp( |
| 16689 | 16691 | lhs_mcv.address(), |
| 16690 | 16692 | rhs_mcv.address(), |
| 16691 | 16693 | .{ .immediate = src_info.bits }, |
| 16692 | | }); |
| 16694 | }, .{}); |
| 16693 | 16695 | return dst_mcv; |
| 16694 | 16696 | }, |
| 16695 | 16697 | }, |
| ... | ... | @@ -16913,7 +16915,7 @@ fn genBinOp( |
| 16913 | 16915 | .return_type = lhs_ty.toIntern(), |
| 16914 | 16916 | .param_types = &.{ lhs_ty.toIntern(), rhs_ty.toIntern() }, |
| 16915 | 16917 | .callee = callee, |
| 16916 | | } }, &.{ lhs_ty, rhs_ty }, &.{ .{ .air_ref = lhs_air }, .{ .air_ref = rhs_air } }); |
| 16918 | } }, &.{ lhs_ty, rhs_ty }, &.{ .{ .air_ref = lhs_air }, .{ .air_ref = rhs_air } }, .{}); |
| 16917 | 16919 | return switch (air_tag) { |
| 16918 | 16920 | .mod => result: { |
| 16919 | 16921 | const adjusted: MCValue = if (type_needs_libcall) adjusted: { |
| ... | ... | @@ -16927,7 +16929,7 @@ fn genBinOp( |
| 16927 | 16929 | .callee = std.fmt.bufPrint(&add_callee_buf, "__add{c}f3", .{ |
| 16928 | 16930 | floatCompilerRtAbiName(float_bits), |
| 16929 | 16931 | }) catch unreachable, |
| 16930 | | } }, &.{ lhs_ty, rhs_ty }, &.{ result, .{ .air_ref = rhs_air } }); |
| 16932 | } }, &.{ lhs_ty, rhs_ty }, &.{ result, .{ .air_ref = rhs_air } }, .{}); |
| 16931 | 16933 | } else switch (float_bits) { |
| 16932 | 16934 | 16, 32, 64 => adjusted: { |
| 16933 | 16935 | const dst_reg = switch (result) { |
| ... | ... | @@ -17026,7 +17028,7 @@ fn genBinOp( |
| 17026 | 17028 | .return_type = lhs_ty.toIntern(), |
| 17027 | 17029 | .param_types = &.{ lhs_ty.toIntern(), rhs_ty.toIntern() }, |
| 17028 | 17030 | .callee = callee, |
| 17029 | | } }, &.{ lhs_ty, rhs_ty }, &.{ adjusted, .{ .air_ref = rhs_air } }); |
| 17031 | } }, &.{ lhs_ty, rhs_ty }, &.{ adjusted, .{ .air_ref = rhs_air } }, .{}); |
| 17030 | 17032 | }, |
| 17031 | 17033 | .div_trunc, .div_floor => try self.genRoundLibcall(lhs_ty, result, .{ |
| 17032 | 17034 | .mode = switch (air_tag) { |
| ... | ... | @@ -19305,7 +19307,7 @@ fn airFrameAddress(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 19305 | 19307 | return self.finishAir(inst, dst_mcv, .{ .none, .none, .none }); |
| 19306 | 19308 | } |
| 19307 | 19309 | |
| 19308 | | fn airCall(self: *CodeGen, inst: Air.Inst.Index, modifier: std.builtin.CallModifier) !void { |
| 19310 | fn airCall(self: *CodeGen, inst: Air.Inst.Index, modifier: std.builtin.CallModifier, opts: CopyOptions) !void { |
| 19309 | 19311 | if (modifier == .always_tail) return self.fail("TODO implement tail calls for x86_64", .{}); |
| 19310 | 19312 | |
| 19311 | 19313 | const pl_op = self.air.instructions.items(.data)[@intFromEnum(inst)].pl_op; |
| ... | ... | @@ -19329,7 +19331,7 @@ fn airCall(self: *CodeGen, inst: Air.Inst.Index, modifier: std.builtin.CallModif |
| 19329 | 19331 | defer allocator.free(arg_vals); |
| 19330 | 19332 | for (arg_vals, arg_refs) |*arg_val, arg_ref| arg_val.* = .{ .air_ref = arg_ref }; |
| 19331 | 19333 | |
| 19332 | | const ret = try self.genCall(.{ .air = pl_op.operand }, arg_tys, arg_vals); |
| 19334 | const ret = try self.genCall(.{ .air = pl_op.operand }, arg_tys, arg_vals, opts); |
| 19333 | 19335 | |
| 19334 | 19336 | var bt = self.liveness.iterateBigTomb(inst); |
| 19335 | 19337 | try self.feed(&bt, pl_op.operand); |
| ... | ... | @@ -19347,7 +19349,7 @@ fn genCall(self: *CodeGen, info: union(enum) { |
| 19347 | 19349 | lib: ?[]const u8 = null, |
| 19348 | 19350 | callee: []const u8, |
| 19349 | 19351 | }, |
| 19350 | | }, arg_types: []const Type, args: []const MCValue) !MCValue { |
| 19352 | }, arg_types: []const Type, args: []const MCValue, opts: CopyOptions) !MCValue { |
| 19351 | 19353 | const pt = self.pt; |
| 19352 | 19354 | const zcu = pt.zcu; |
| 19353 | 19355 | const ip = &zcu.intern_pool; |
| ... | ... | @@ -19431,12 +19433,12 @@ fn genCall(self: *CodeGen, info: union(enum) { |
| 19431 | 19433 | }, |
| 19432 | 19434 | .indirect => |reg_off| { |
| 19433 | 19435 | frame_index.* = try self.allocFrameIndex(.initType(arg_ty, zcu)); |
| 19434 | | try self.genSetMem(.{ .frame = frame_index.* }, 0, arg_ty, src_arg, .{}); |
| 19436 | try self.genSetMem(.{ .frame = frame_index.* }, 0, arg_ty, src_arg, opts); |
| 19435 | 19437 | try self.register_manager.getReg(reg_off.reg, null); |
| 19436 | 19438 | try reg_locks.append(self.register_manager.lockReg(reg_off.reg)); |
| 19437 | 19439 | }, |
| 19438 | 19440 | .load_frame => { |
| 19439 | | try self.genCopy(arg_ty, dst_arg, src_arg, .{}); |
| 19441 | try self.genCopy(arg_ty, dst_arg, src_arg, opts); |
| 19440 | 19442 | try self.freeValue(src_arg); |
| 19441 | 19443 | }, |
| 19442 | 19444 | .elementwise_regs_then_frame => |regs_frame_addr| { |
| ... | ... | @@ -19513,22 +19515,20 @@ fn genCall(self: *CodeGen, info: union(enum) { |
| 19513 | 19515 | switch (dst_arg) { |
| 19514 | 19516 | .none, .load_frame => {}, |
| 19515 | 19517 | .register => |dst_reg| switch (fn_info.cc) { |
| 19516 | | else => try self.genSetReg( |
| 19517 | | registerAlias(dst_reg, @intCast(arg_ty.abiSize(zcu))), |
| 19518 | | arg_ty, |
| 19519 | | src_arg, |
| 19520 | | .{}, |
| 19521 | | ), |
| 19518 | else => try self.genSetReg(registerAlias( |
| 19519 | dst_reg, |
| 19520 | @intCast(arg_ty.abiSize(zcu)), |
| 19521 | ), arg_ty, src_arg, opts), |
| 19522 | 19522 | .x86_64_sysv, .x86_64_win => { |
| 19523 | 19523 | const promoted_ty = self.promoteInt(arg_ty); |
| 19524 | 19524 | const promoted_abi_size: u32 = @intCast(promoted_ty.abiSize(zcu)); |
| 19525 | 19525 | const dst_alias = registerAlias(dst_reg, promoted_abi_size); |
| 19526 | | try self.genSetReg(dst_alias, promoted_ty, src_arg, .{}); |
| 19526 | try self.genSetReg(dst_alias, promoted_ty, src_arg, opts); |
| 19527 | 19527 | if (promoted_ty.toIntern() != arg_ty.toIntern()) |
| 19528 | 19528 | try self.truncateRegister(arg_ty, dst_alias); |
| 19529 | 19529 | }, |
| 19530 | 19530 | }, |
| 19531 | | .register_pair => try self.genCopy(arg_ty, dst_arg, src_arg, .{}), |
| 19531 | .register_pair => try self.genCopy(arg_ty, dst_arg, src_arg, opts), |
| 19532 | 19532 | .indirect => |reg_off| try self.genSetReg(reg_off.reg, .usize, .{ |
| 19533 | 19533 | .lea_frame = .{ .index = frame_index, .off = -reg_off.off }, |
| 19534 | 19534 | }, .{}), |
| ... | ... | @@ -19756,7 +19756,7 @@ fn airCmp(self: *CodeGen, inst: Air.Inst.Index, op: std.math.CompareOperator) !v |
| 19756 | 19756 | }, |
| 19757 | 19757 | floatCompilerRtAbiName(float_bits), |
| 19758 | 19758 | }) catch unreachable, |
| 19759 | | } }, &.{ ty, ty }, &.{ .{ .air_ref = bin_op.lhs }, .{ .air_ref = bin_op.rhs } }); |
| 19759 | } }, &.{ ty, ty }, &.{ .{ .air_ref = bin_op.lhs }, .{ .air_ref = bin_op.rhs } }, .{}); |
| 19760 | 19760 | try self.genBinOpMir(.{ ._, .@"test" }, .i32, ret, ret); |
| 19761 | 19761 | break :result switch (op) { |
| 19762 | 19762 | .eq => .e, |
| ... | ... | @@ -22305,6 +22305,7 @@ fn genCopy(self: *CodeGen, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: C |
| 22305 | 22305 | }, opts), |
| 22306 | 22306 | inline .register_pair, .register_triple, .register_quadruple => |dst_regs, dst_tag| { |
| 22307 | 22307 | const src_info: ?struct { addr_reg: Register, addr_lock: RegisterLock } = src_info: switch (src_mcv) { |
| 22308 | .undef, .memory, .indirect, .load_frame => null, |
| 22308 | 22309 | .register => |src_reg| switch (dst_regs[0].class()) { |
| 22309 | 22310 | .general_purpose => switch (src_reg.class()) { |
| 22310 | 22311 | else => unreachable, |
| ... | ... | @@ -22344,7 +22345,6 @@ fn genCopy(self: *CodeGen, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: C |
| 22344 | 22345 | } |
| 22345 | 22346 | return; |
| 22346 | 22347 | }, |
| 22347 | | .memory, .indirect, .load_frame => null, |
| 22348 | 22348 | .load_symbol, .load_direct, .load_got, .load_tlv => { |
| 22349 | 22349 | const src_addr_reg = |
| 22350 | 22350 | (try self.register_manager.allocReg(null, abi.RegisterClass.gp)).to64(); |
| ... | ... | @@ -22375,6 +22375,7 @@ fn genCopy(self: *CodeGen, ty: Type, dst_mcv: MCValue, src_mcv: MCValue, opts: C |
| 22375 | 22375 | if (is_hazard) hazard_count += 1; |
| 22376 | 22376 | if (is_hazard != emit_hazard) continue; |
| 22377 | 22377 | try self.genSetReg(dst_reg, dst_ty, switch (src_mcv) { |
| 22378 | .undef => if (opts.safety and part_i > 0) .{ .register = dst_regs[0] } else .undef, |
| 22378 | 22379 | dst_tag => |src_regs| .{ .register = src_regs[part_i] }, |
| 22379 | 22380 | .memory, .indirect, .load_frame => src_mcv.address().offset(part_disp).deref(), |
| 22380 | 22381 | .load_symbol, .load_direct, .load_got, .load_tlv => .{ .indirect = .{ |
| ... | ... | @@ -23410,7 +23411,7 @@ fn airFloatFromInt(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 23410 | 23411 | intCompilerRtAbiName(src_bits), |
| 23411 | 23412 | floatCompilerRtAbiName(dst_bits), |
| 23412 | 23413 | }) catch unreachable, |
| 23413 | | } }, &.{src_ty}, &.{.{ .air_ref = ty_op.operand }}); |
| 23414 | } }, &.{src_ty}, &.{.{ .air_ref = ty_op.operand }}, .{}); |
| 23414 | 23415 | } |
| 23415 | 23416 | |
| 23416 | 23417 | const src_mcv = try self.resolveInst(ty_op.operand); |
| ... | ... | @@ -23490,7 +23491,7 @@ fn airIntFromFloat(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 23490 | 23491 | floatCompilerRtAbiName(src_bits), |
| 23491 | 23492 | intCompilerRtAbiName(dst_bits), |
| 23492 | 23493 | }) catch unreachable, |
| 23493 | | } }, &.{src_ty}, &.{.{ .air_ref = ty_op.operand }}); |
| 23494 | } }, &.{src_ty}, &.{.{ .air_ref = ty_op.operand }}, .{}); |
| 23494 | 23495 | } |
| 23495 | 23496 | |
| 23496 | 23497 | const src_mcv = try self.resolveInst(ty_op.operand); |
| ... | ... | @@ -26230,7 +26231,7 @@ fn airMulAdd(self: *CodeGen, inst: Air.Inst.Index) !void { |
| 26230 | 26231 | }) catch unreachable, |
| 26231 | 26232 | } }, &.{ ty, ty, ty }, &.{ |
| 26232 | 26233 | .{ .air_ref = extra.lhs }, .{ .air_ref = extra.rhs }, .{ .air_ref = pl_op.operand }, |
| 26233 | | }); |
| 26234 | }, .{}); |
| 26234 | 26235 | } |
| 26235 | 26236 | |
| 26236 | 26237 | var mcvs: [3]MCValue = undefined; |