blob: 9d1d24f3349c33ac4e39fa449651a80a55873da8 [file] [log] [blame]
Zvi Rackover76dbf262016-11-15 06:34:33 +00001//===-- llvm/lib/Target/X86/X86CallLowering.cpp - Call lowering -----------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9///
10/// \file
11/// This file implements the lowering of LLVM calls to machine code calls for
12/// GlobalISel.
13///
14//===----------------------------------------------------------------------===//
15
16#include "X86CallLowering.h"
Igor Breger8a924be2017-03-23 12:13:29 +000017#include "X86CallingConv.h"
Zvi Rackover76dbf262016-11-15 06:34:33 +000018#include "X86ISelLowering.h"
19#include "X86InstrInfo.h"
Igor Breger9ea154d2017-01-29 08:35:42 +000020#include "X86TargetMachine.h"
Igor Breger9ea154d2017-01-29 08:35:42 +000021
Igor Breger9d5571a2017-07-05 06:24:13 +000022#include "llvm/CodeGen/Analysis.h"
Zvi Rackover76dbf262016-11-15 06:34:33 +000023#include "llvm/CodeGen/GlobalISel/MachineIRBuilder.h"
Igor Breger88a3d5c2017-08-20 09:25:22 +000024#include "llvm/CodeGen/GlobalISel/Utils.h"
Igor Breger9ea154d2017-01-29 08:35:42 +000025#include "llvm/CodeGen/MachineRegisterInfo.h"
Igor Breger8a924be2017-03-23 12:13:29 +000026#include "llvm/CodeGen/MachineValueType.h"
Igor Breger9ea154d2017-01-29 08:35:42 +000027#include "llvm/Target/TargetSubtargetInfo.h"
Zvi Rackover76dbf262016-11-15 06:34:33 +000028
29using namespace llvm;
30
Igor Breger9ea154d2017-01-29 08:35:42 +000031#include "X86GenCallingConv.inc"
32
Zvi Rackover76dbf262016-11-15 06:34:33 +000033X86CallLowering::X86CallLowering(const X86TargetLowering &TLI)
34 : CallLowering(&TLI) {}
35
Igor Breger9d5571a2017-07-05 06:24:13 +000036bool X86CallLowering::splitToValueTypes(const ArgInfo &OrigArg,
Igor Breger5c31a4c2017-02-06 08:37:41 +000037 SmallVectorImpl<ArgInfo> &SplitArgs,
38 const DataLayout &DL,
39 MachineRegisterInfo &MRI,
40 SplitArgTy PerformArgSplit) const {
41
42 const X86TargetLowering &TLI = *getTLI<X86TargetLowering>();
43 LLVMContext &Context = OrigArg.Ty->getContext();
Igor Breger9d5571a2017-07-05 06:24:13 +000044
45 SmallVector<EVT, 4> SplitVTs;
46 SmallVector<uint64_t, 4> Offsets;
47 ComputeValueVTs(TLI, DL, OrigArg.Ty, SplitVTs, &Offsets, 0);
48
49 if (SplitVTs.size() != 1) {
50 // TODO: support struct/array split
51 return false;
52 }
53
54 EVT VT = SplitVTs[0];
Igor Breger5c31a4c2017-02-06 08:37:41 +000055 unsigned NumParts = TLI.getNumRegisters(Context, VT);
56
57 if (NumParts == 1) {
Igor Bregera8ba5722017-03-23 15:25:57 +000058 // replace the original type ( pointer -> GPR ).
59 SplitArgs.emplace_back(OrigArg.Reg, VT.getTypeForEVT(Context),
60 OrigArg.Flags, OrigArg.IsFixed);
Igor Breger9d5571a2017-07-05 06:24:13 +000061 return true;
Igor Breger5c31a4c2017-02-06 08:37:41 +000062 }
63
Igor Breger5c31a4c2017-02-06 08:37:41 +000064 SmallVector<unsigned, 8> SplitRegs;
65
66 EVT PartVT = TLI.getRegisterType(Context, VT);
67 Type *PartTy = PartVT.getTypeForEVT(Context);
68
69 for (unsigned i = 0; i < NumParts; ++i) {
Daniel Sanders52b4ce72017-03-07 23:20:35 +000070 ArgInfo Info =
71 ArgInfo{MRI.createGenericVirtualRegister(getLLTForType(*PartTy, DL)),
72 PartTy, OrigArg.Flags};
Igor Breger5c31a4c2017-02-06 08:37:41 +000073 SplitArgs.push_back(Info);
Igor Breger87aafa02017-04-24 17:05:52 +000074 SplitRegs.push_back(Info.Reg);
Igor Breger5c31a4c2017-02-06 08:37:41 +000075 }
Igor Breger87aafa02017-04-24 17:05:52 +000076
77 PerformArgSplit(SplitRegs);
Igor Breger9d5571a2017-07-05 06:24:13 +000078 return true;
Igor Breger5c31a4c2017-02-06 08:37:41 +000079}
80
81namespace {
Igor Breger88a3d5c2017-08-20 09:25:22 +000082struct OutgoingValueHandler : public CallLowering::ValueHandler {
83 OutgoingValueHandler(MachineIRBuilder &MIRBuilder, MachineRegisterInfo &MRI,
84 MachineInstrBuilder &MIB, CCAssignFn *AssignFn)
85 : ValueHandler(MIRBuilder, MRI, AssignFn), MIB(MIB), StackSize(0),
86 DL(MIRBuilder.getMF().getDataLayout()),
Igor Breger36d447d2017-08-30 15:10:15 +000087 STI(MIRBuilder.getMF().getSubtarget<X86Subtarget>()), NumXMMRegs(0) {}
Igor Breger5c31a4c2017-02-06 08:37:41 +000088
89 unsigned getStackAddress(uint64_t Size, int64_t Offset,
90 MachinePointerInfo &MPO) override {
Igor Breger88a3d5c2017-08-20 09:25:22 +000091
92 LLT p0 = LLT::pointer(0, DL.getPointerSizeInBits(0));
93 LLT SType = LLT::scalar(DL.getPointerSizeInBits(0));
94 unsigned SPReg = MRI.createGenericVirtualRegister(p0);
95 MIRBuilder.buildCopy(SPReg, STI.getRegisterInfo()->getStackRegister());
96
97 unsigned OffsetReg = MRI.createGenericVirtualRegister(SType);
98 MIRBuilder.buildConstant(OffsetReg, Offset);
99
100 unsigned AddrReg = MRI.createGenericVirtualRegister(p0);
101 MIRBuilder.buildGEP(AddrReg, SPReg, OffsetReg);
102
103 MPO = MachinePointerInfo::getStack(MIRBuilder.getMF(), Offset);
104 return AddrReg;
Igor Breger5c31a4c2017-02-06 08:37:41 +0000105 }
106
107 void assignValueToReg(unsigned ValVReg, unsigned PhysReg,
108 CCValAssign &VA) override {
109 MIB.addUse(PhysReg, RegState::Implicit);
110 unsigned ExtReg = extendRegister(ValVReg, VA);
111 MIRBuilder.buildCopy(PhysReg, ExtReg);
112 }
113
114 void assignValueToAddress(unsigned ValVReg, unsigned Addr, uint64_t Size,
115 MachinePointerInfo &MPO, CCValAssign &VA) override {
Igor Breger88a3d5c2017-08-20 09:25:22 +0000116
117 unsigned ExtReg = extendRegister(ValVReg, VA);
118 auto MMO = MIRBuilder.getMF().getMachineMemOperand(
119 MPO, MachineMemOperand::MOStore, VA.getLocVT().getStoreSize(),
120 /* Alignment */ 0);
121 MIRBuilder.buildStore(ExtReg, Addr, *MMO);
Igor Breger5c31a4c2017-02-06 08:37:41 +0000122 }
123
Igor Breger88a3d5c2017-08-20 09:25:22 +0000124 bool assignArg(unsigned ValNo, MVT ValVT, MVT LocVT,
125 CCValAssign::LocInfo LocInfo,
126 const CallLowering::ArgInfo &Info, CCState &State) override {
127
Igor Breger88a3d5c2017-08-20 09:25:22 +0000128 bool Res = AssignFn(ValNo, ValVT, LocVT, LocInfo, Info.Flags, State);
129 StackSize = State.getNextStackOffset();
Igor Breger36d447d2017-08-30 15:10:15 +0000130
131 static const MCPhysReg XMMArgRegs[] = {X86::XMM0, X86::XMM1, X86::XMM2,
132 X86::XMM3, X86::XMM4, X86::XMM5,
133 X86::XMM6, X86::XMM7};
134 if (!Info.IsFixed)
135 NumXMMRegs = State.getFirstUnallocated(XMMArgRegs);
136
Igor Breger88a3d5c2017-08-20 09:25:22 +0000137 return Res;
138 }
139
140 uint64_t getStackSize() { return StackSize; }
Igor Breger36d447d2017-08-30 15:10:15 +0000141 uint64_t getNumXmmRegs() { return NumXMMRegs; }
Igor Breger88a3d5c2017-08-20 09:25:22 +0000142
143protected:
Igor Breger5c31a4c2017-02-06 08:37:41 +0000144 MachineInstrBuilder &MIB;
Igor Breger88a3d5c2017-08-20 09:25:22 +0000145 uint64_t StackSize;
146 const DataLayout &DL;
147 const X86Subtarget &STI;
Igor Breger36d447d2017-08-30 15:10:15 +0000148 unsigned NumXMMRegs;
Igor Breger5c31a4c2017-02-06 08:37:41 +0000149};
150} // End anonymous namespace.
151
Zvi Rackover76dbf262016-11-15 06:34:33 +0000152bool X86CallLowering::lowerReturn(MachineIRBuilder &MIRBuilder,
153 const Value *Val, unsigned VReg) const {
Zvi Rackover76dbf262016-11-15 06:34:33 +0000154
Igor Breger5c31a4c2017-02-06 08:37:41 +0000155 assert(((Val && VReg) || (!Val && !VReg)) && "Return value without a vreg");
Igor Breger9ea154d2017-01-29 08:35:42 +0000156
Igor Breger5c31a4c2017-02-06 08:37:41 +0000157 auto MIB = MIRBuilder.buildInstrNoInsert(X86::RET).addImm(0);
Zvi Rackover76dbf262016-11-15 06:34:33 +0000158
Igor Breger5c31a4c2017-02-06 08:37:41 +0000159 if (VReg) {
160 MachineFunction &MF = MIRBuilder.getMF();
161 MachineRegisterInfo &MRI = MF.getRegInfo();
162 auto &DL = MF.getDataLayout();
163 const Function &F = *MF.getFunction();
164
165 ArgInfo OrigArg{VReg, Val->getType()};
Reid Klecknerb5180542017-03-21 16:57:19 +0000166 setArgFlags(OrigArg, AttributeList::ReturnIndex, DL, F);
Igor Breger5c31a4c2017-02-06 08:37:41 +0000167
168 SmallVector<ArgInfo, 8> SplitArgs;
Igor Breger9d5571a2017-07-05 06:24:13 +0000169 if (!splitToValueTypes(OrigArg, SplitArgs, DL, MRI,
170 [&](ArrayRef<unsigned> Regs) {
171 MIRBuilder.buildUnmerge(Regs, VReg);
172 }))
173 return false;
Igor Breger5c31a4c2017-02-06 08:37:41 +0000174
Igor Breger88a3d5c2017-08-20 09:25:22 +0000175 OutgoingValueHandler Handler(MIRBuilder, MRI, MIB, RetCC_X86);
Igor Breger8a924be2017-03-23 12:13:29 +0000176 if (!handleAssignments(MIRBuilder, SplitArgs, Handler))
Igor Breger5c31a4c2017-02-06 08:37:41 +0000177 return false;
178 }
179
180 MIRBuilder.insertInstr(MIB);
Zvi Rackover76dbf262016-11-15 06:34:33 +0000181 return true;
182}
183
Igor Breger9ea154d2017-01-29 08:35:42 +0000184namespace {
Igor Breger88a3d5c2017-08-20 09:25:22 +0000185struct IncomingValueHandler : public CallLowering::ValueHandler {
186 IncomingValueHandler(MachineIRBuilder &MIRBuilder, MachineRegisterInfo &MRI,
187 CCAssignFn *AssignFn)
188 : ValueHandler(MIRBuilder, MRI, AssignFn),
189 DL(MIRBuilder.getMF().getDataLayout()) {}
Igor Breger9ea154d2017-01-29 08:35:42 +0000190
191 unsigned getStackAddress(uint64_t Size, int64_t Offset,
192 MachinePointerInfo &MPO) override {
193
194 auto &MFI = MIRBuilder.getMF().getFrameInfo();
195 int FI = MFI.CreateFixedObject(Size, Offset, true);
196 MPO = MachinePointerInfo::getFixedStack(MIRBuilder.getMF(), FI);
197
Igor Breger8a924be2017-03-23 12:13:29 +0000198 unsigned AddrReg = MRI.createGenericVirtualRegister(
199 LLT::pointer(0, DL.getPointerSizeInBits(0)));
Igor Breger9ea154d2017-01-29 08:35:42 +0000200 MIRBuilder.buildFrameIndex(AddrReg, FI);
201 return AddrReg;
202 }
203
204 void assignValueToAddress(unsigned ValVReg, unsigned Addr, uint64_t Size,
205 MachinePointerInfo &MPO, CCValAssign &VA) override {
206
207 auto MMO = MIRBuilder.getMF().getMachineMemOperand(
208 MPO, MachineMemOperand::MOLoad | MachineMemOperand::MOInvariant, Size,
209 0);
210 MIRBuilder.buildLoad(ValVReg, Addr, *MMO);
211 }
212
Igor Breger88a3d5c2017-08-20 09:25:22 +0000213protected:
214 const DataLayout &DL;
215};
216
217struct FormalArgHandler : public IncomingValueHandler {
218 FormalArgHandler(MachineIRBuilder &MIRBuilder, MachineRegisterInfo &MRI,
219 CCAssignFn *AssignFn)
220 : IncomingValueHandler(MIRBuilder, MRI, AssignFn) {}
221
Igor Breger9ea154d2017-01-29 08:35:42 +0000222 void assignValueToReg(unsigned ValVReg, unsigned PhysReg,
223 CCValAssign &VA) override {
224 MIRBuilder.getMBB().addLiveIn(PhysReg);
225 MIRBuilder.buildCopy(ValVReg, PhysReg);
226 }
Igor Breger9ea154d2017-01-29 08:35:42 +0000227};
Igor Breger88a3d5c2017-08-20 09:25:22 +0000228
229struct CallReturnHandler : public IncomingValueHandler {
230 CallReturnHandler(MachineIRBuilder &MIRBuilder, MachineRegisterInfo &MRI,
231 CCAssignFn *AssignFn, MachineInstrBuilder &MIB)
232 : IncomingValueHandler(MIRBuilder, MRI, AssignFn), MIB(MIB) {}
233
234 void assignValueToReg(unsigned ValVReg, unsigned PhysReg,
235 CCValAssign &VA) override {
236 MIB.addDef(PhysReg, RegState::Implicit);
237 MIRBuilder.buildCopy(ValVReg, PhysReg);
238 }
239
240protected:
241 MachineInstrBuilder &MIB;
242};
243
Igor Breger8a924be2017-03-23 12:13:29 +0000244} // namespace
Igor Breger9ea154d2017-01-29 08:35:42 +0000245
Zvi Rackover76dbf262016-11-15 06:34:33 +0000246bool X86CallLowering::lowerFormalArguments(MachineIRBuilder &MIRBuilder,
247 const Function &F,
248 ArrayRef<unsigned> VRegs) const {
Igor Breger9ea154d2017-01-29 08:35:42 +0000249 if (F.arg_empty())
250 return true;
251
Igor Breger8a924be2017-03-23 12:13:29 +0000252 // TODO: handle variadic function
Igor Breger9ea154d2017-01-29 08:35:42 +0000253 if (F.isVarArg())
254 return false;
255
Igor Breger5c31a4c2017-02-06 08:37:41 +0000256 MachineFunction &MF = MIRBuilder.getMF();
257 MachineRegisterInfo &MRI = MF.getRegInfo();
258 auto DL = MF.getDataLayout();
Igor Breger9ea154d2017-01-29 08:35:42 +0000259
Igor Breger5c31a4c2017-02-06 08:37:41 +0000260 SmallVector<ArgInfo, 8> SplitArgs;
Igor Breger9ea154d2017-01-29 08:35:42 +0000261 unsigned Idx = 0;
Reid Kleckner45707d42017-03-16 22:59:15 +0000262 for (auto &Arg : F.args()) {
Igor Breger0c979d42017-07-05 11:40:35 +0000263
264 // TODO: handle not simple cases.
265 if (Arg.hasAttribute(Attribute::ByVal) ||
266 Arg.hasAttribute(Attribute::InReg) ||
267 Arg.hasAttribute(Attribute::StructRet) ||
268 Arg.hasAttribute(Attribute::SwiftSelf) ||
269 Arg.hasAttribute(Attribute::SwiftError) ||
270 Arg.hasAttribute(Attribute::Nest))
271 return false;
272
Igor Breger5c31a4c2017-02-06 08:37:41 +0000273 ArgInfo OrigArg(VRegs[Idx], Arg.getType());
Igor Breger0c979d42017-07-05 11:40:35 +0000274 setArgFlags(OrigArg, Idx + AttributeList::FirstArgIndex, DL, F);
Igor Breger9d5571a2017-07-05 06:24:13 +0000275 if (!splitToValueTypes(OrigArg, SplitArgs, DL, MRI,
276 [&](ArrayRef<unsigned> Regs) {
277 MIRBuilder.buildMerge(VRegs[Idx], Regs);
278 }))
279 return false;
Igor Breger9ea154d2017-01-29 08:35:42 +0000280 Idx++;
281 }
282
Igor Breger5c31a4c2017-02-06 08:37:41 +0000283 MachineBasicBlock &MBB = MIRBuilder.getMBB();
284 if (!MBB.empty())
Igor Breger8a924be2017-03-23 12:13:29 +0000285 MIRBuilder.setInstr(*MBB.begin());
Igor Breger5c31a4c2017-02-06 08:37:41 +0000286
Igor Breger88a3d5c2017-08-20 09:25:22 +0000287 FormalArgHandler Handler(MIRBuilder, MRI, CC_X86);
Igor Breger5c31a4c2017-02-06 08:37:41 +0000288 if (!handleAssignments(MIRBuilder, SplitArgs, Handler))
289 return false;
290
291 // Move back to the end of the basic block.
292 MIRBuilder.setMBB(MBB);
293
294 return true;
Zvi Rackover76dbf262016-11-15 06:34:33 +0000295}
Igor Breger88a3d5c2017-08-20 09:25:22 +0000296
297bool X86CallLowering::lowerCall(MachineIRBuilder &MIRBuilder,
298 CallingConv::ID CallConv,
299 const MachineOperand &Callee,
300 const ArgInfo &OrigRet,
301 ArrayRef<ArgInfo> OrigArgs) const {
302
303 MachineFunction &MF = MIRBuilder.getMF();
304 const Function &F = *MF.getFunction();
305 MachineRegisterInfo &MRI = MF.getRegInfo();
306 auto &DL = F.getParent()->getDataLayout();
307 const X86Subtarget &STI = MF.getSubtarget<X86Subtarget>();
308 const TargetInstrInfo &TII = *STI.getInstrInfo();
309 auto TRI = STI.getRegisterInfo();
310
311 // Handle only Linux C, X86_64_SysV calling conventions for now.
312 if (!STI.isTargetLinux() ||
313 !(CallConv == CallingConv::C || CallConv == CallingConv::X86_64_SysV))
314 return false;
315
316 unsigned AdjStackDown = TII.getCallFrameSetupOpcode();
317 auto CallSeqStart = MIRBuilder.buildInstr(AdjStackDown);
318
319 // Create a temporarily-floating call instruction so we can add the implicit
320 // uses of arg registers.
321 bool Is64Bit = STI.is64Bit();
322 unsigned CallOpc = Callee.isReg()
323 ? (Is64Bit ? X86::CALL64r : X86::CALL32r)
324 : (Is64Bit ? X86::CALL64pcrel32 : X86::CALLpcrel32);
325
326 auto MIB = MIRBuilder.buildInstrNoInsert(CallOpc).add(Callee).addRegMask(
327 TRI->getCallPreservedMask(MF, CallConv));
328
329 SmallVector<ArgInfo, 8> SplitArgs;
330 for (const auto &OrigArg : OrigArgs) {
Igor Breger1b5e3d32017-08-21 08:59:59 +0000331
332 // TODO: handle not simple cases.
333 if (OrigArg.Flags.isByVal())
334 return false;
335
Igor Breger88a3d5c2017-08-20 09:25:22 +0000336 if (!splitToValueTypes(OrigArg, SplitArgs, DL, MRI,
337 [&](ArrayRef<unsigned> Regs) {
338 MIRBuilder.buildUnmerge(Regs, OrigArg.Reg);
339 }))
340 return false;
341 }
342 // Do the actual argument marshalling.
343 OutgoingValueHandler Handler(MIRBuilder, MRI, MIB, CC_X86);
344 if (!handleAssignments(MIRBuilder, SplitArgs, Handler))
345 return false;
346
Igor Breger36d447d2017-08-30 15:10:15 +0000347 bool IsFixed = OrigArgs.empty() ? true : OrigArgs.back().IsFixed;
348 if (STI.is64Bit() && !IsFixed && !STI.isCallingConvWin64(CallConv)) {
349 // From AMD64 ABI document:
350 // For calls that may call functions that use varargs or stdargs
351 // (prototype-less calls or calls to functions containing ellipsis (...) in
352 // the declaration) %al is used as hidden argument to specify the number
353 // of SSE registers used. The contents of %al do not need to match exactly
354 // the number of registers, but must be an ubound on the number of SSE
355 // registers used and is in the range 0 - 8 inclusive.
356
357 MIRBuilder.buildInstr(X86::MOV8ri)
358 .addDef(X86::AL)
359 .addImm(Handler.getNumXmmRegs());
360 MIB.addUse(X86::AL, RegState::Implicit);
361 }
362
Igor Breger88a3d5c2017-08-20 09:25:22 +0000363 // Now we can add the actual call instruction to the correct basic block.
364 MIRBuilder.insertInstr(MIB);
365
366 // If Callee is a reg, since it is used by a target specific
367 // instruction, it must have a register class matching the
368 // constraint of that instruction.
369 if (Callee.isReg())
370 MIB->getOperand(0).setReg(constrainOperandRegClass(
371 MF, *TRI, MRI, *MF.getSubtarget().getInstrInfo(),
372 *MF.getSubtarget().getRegBankInfo(), *MIB, MIB->getDesc(),
373 Callee.getReg(), 0));
374
375 // Finally we can copy the returned value back into its virtual-register. In
376 // symmetry with the arguments, the physical register must be an
377 // implicit-define of the call instruction.
378
379 if (OrigRet.Reg) {
380 SplitArgs.clear();
381 SmallVector<unsigned, 8> NewRegs;
382
383 if (!splitToValueTypes(OrigRet, SplitArgs, DL, MRI,
384 [&](ArrayRef<unsigned> Regs) {
385 NewRegs.assign(Regs.begin(), Regs.end());
386 }))
387 return false;
388
389 CallReturnHandler Handler(MIRBuilder, MRI, RetCC_X86, MIB);
390 if (!handleAssignments(MIRBuilder, SplitArgs, Handler))
391 return false;
392
393 if (!NewRegs.empty())
394 MIRBuilder.buildMerge(OrigRet.Reg, NewRegs);
395 }
396
397 CallSeqStart.addImm(Handler.getStackSize())
398 .addImm(0 /* see getFrameTotalSize */)
399 .addImm(0 /* see getFrameAdjustment */);
400
401 unsigned AdjStackUp = TII.getCallFrameDestroyOpcode();
402 MIRBuilder.buildInstr(AdjStackUp)
403 .addImm(Handler.getStackSize())
404 .addImm(0 /* NumBytesForCalleeToPop */);
405
406 return true;
407}