| ... | ... | @@ -428,6 +428,28 @@ fn gen(self: *Self) !void { |
| 428 | 428 | self.ret_mcv = MCValue{ .stack_offset = stack_offset }; |
| 429 | 429 | } |
| 430 | 430 | |
| 431 | for (self.args) |*arg, arg_index| { |
| 432 | // Copy register arguments to the stack |
| 433 | switch (arg.*) { |
| 434 | .register => |reg| { |
| 435 | // The first AIR instructions of the main body are guaranteed |
| 436 | // to be the functions arguments |
| 437 | const inst = self.air.getMainBody()[arg_index]; |
| 438 | assert(self.air.instructions.items(.tag)[inst] == .arg); |
| 439 | |
| 440 | const ty = self.air.typeOfIndex(inst); |
| 441 | |
| 442 | const abi_size = @intCast(u32, ty.abiSize(self.target.*)); |
| 443 | const abi_align = ty.abiAlignment(self.target.*); |
| 444 | const stack_offset = try self.allocMem(abi_size, abi_align, inst); |
| 445 | try self.genSetStack(ty, stack_offset, MCValue{ .register = reg }); |
| 446 | |
| 447 | arg.* = MCValue{ .stack_offset = stack_offset }; |
| 448 | }, |
| 449 | else => {}, |
| 450 | } |
| 451 | } |
| 452 | |
| 431 | 453 | _ = try self.addInst(.{ |
| 432 | 454 | .tag = .dbg_prologue_end, |
| 433 | 455 | .cond = undefined, |
| ... | ... | @@ -3766,7 +3788,8 @@ fn genStrRegister(self: *Self, source_reg: Register, addr_reg: Register, ty: Typ |
| 3766 | 3788 | const tag: Mir.Inst.Tag = switch (abi_size) { |
| 3767 | 3789 | 1 => .strb, |
| 3768 | 3790 | 2 => .strh, |
| 3769 | | 3, 4 => .str, |
| 3791 | 4 => .str, |
| 3792 | 3 => return self.fail("TODO: genStrRegister for abi_size={}", .{abi_size}), |
| 3770 | 3793 | else => unreachable, |
| 3771 | 3794 | }; |
| 3772 | 3795 | |
| ... | ... | @@ -3782,7 +3805,7 @@ fn genStrRegister(self: *Self, source_reg: Register, addr_reg: Register, ty: Typ |
| 3782 | 3805 | } }; |
| 3783 | 3806 | |
| 3784 | 3807 | const data: Mir.Inst.Data = switch (abi_size) { |
| 3785 | | 1, 3, 4 => rr_offset, |
| 3808 | 1, 4 => rr_offset, |
| 3786 | 3809 | 2 => rr_extra_offset, |
| 3787 | 3810 | else => unreachable, |
| 3788 | 3811 | }; |
| ... | ... | @@ -4047,38 +4070,13 @@ fn airArg(self: *Self, inst: Air.Inst.Index) !void { |
| 4047 | 4070 | const arg_index = self.arg_index; |
| 4048 | 4071 | self.arg_index += 1; |
| 4049 | 4072 | |
| 4050 | | const ty = self.air.typeOfIndex(inst); |
| 4051 | | |
| 4052 | | const result = self.args[arg_index]; |
| 4053 | | const mcv = switch (result) { |
| 4054 | | // Copy registers to the stack |
| 4055 | | .register => |reg| blk: { |
| 4056 | | const abi_size = @intCast(u32, ty.abiSize(self.target.*)); |
| 4057 | | const abi_align = ty.abiAlignment(self.target.*); |
| 4058 | | const stack_offset = try self.allocMem(abi_size, abi_align, inst); |
| 4059 | | try self.genSetStack(ty, stack_offset, MCValue{ .register = reg }); |
| 4060 | | |
| 4061 | | break :blk MCValue{ .stack_offset = stack_offset }; |
| 4062 | | }, |
| 4063 | | else => result, |
| 4064 | | }; |
| 4065 | | |
| 4066 | 4073 | try self.dbg_arg_relocs.append(self.gpa, .{ |
| 4067 | 4074 | .inst = inst, |
| 4068 | 4075 | .index = arg_index, |
| 4069 | 4076 | }); |
| 4070 | 4077 | |
| 4071 | | if (self.liveness.isUnused(inst)) |
| 4072 | | return self.finishAirBookkeeping(); |
| 4073 | | |
| 4074 | | switch (mcv) { |
| 4075 | | .register => |reg| { |
| 4076 | | self.register_manager.getRegAssumeFree(reg, inst); |
| 4077 | | }, |
| 4078 | | else => {}, |
| 4079 | | } |
| 4080 | | |
| 4081 | | return self.finishAir(inst, mcv, .{ .none, .none, .none }); |
| 4078 | const result: MCValue = if (self.liveness.isUnused(inst)) .dead else self.args[arg_index]; |
| 4079 | return self.finishAir(inst, result, .{ .none, .none, .none }); |
| 4082 | 4080 | } |
| 4083 | 4081 | |
| 4084 | 4082 | fn airBreakpoint(self: *Self) !void { |