blob: ca6fbb16e557632ea5c73581b4d8d5ba3364f6bb [file] [log] [blame]
Alex Bradbury89718422017-10-19 21:37:38 +00001//===-- RISCVISelLowering.cpp - RISCV DAG Lowering Implementation --------===//
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// This file defines the interfaces that RISCV uses to lower LLVM code into a
11// selection DAG.
12//
13//===----------------------------------------------------------------------===//
14
15#include "RISCVISelLowering.h"
16#include "RISCV.h"
Alex Bradburyc85be0d2018-01-10 19:41:03 +000017#include "RISCVMachineFunctionInfo.h"
Alex Bradbury89718422017-10-19 21:37:38 +000018#include "RISCVRegisterInfo.h"
19#include "RISCVSubtarget.h"
20#include "RISCVTargetMachine.h"
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +000021#include "llvm/ADT/Statistic.h"
Alex Bradbury89718422017-10-19 21:37:38 +000022#include "llvm/CodeGen/CallingConvLower.h"
23#include "llvm/CodeGen/MachineFrameInfo.h"
24#include "llvm/CodeGen/MachineFunction.h"
25#include "llvm/CodeGen/MachineInstrBuilder.h"
26#include "llvm/CodeGen/MachineRegisterInfo.h"
27#include "llvm/CodeGen/SelectionDAGISel.h"
28#include "llvm/CodeGen/TargetLoweringObjectFileImpl.h"
Craig Topper2fa14362018-03-29 17:21:10 +000029#include "llvm/CodeGen/ValueTypes.h"
Alex Bradbury89718422017-10-19 21:37:38 +000030#include "llvm/IR/DiagnosticInfo.h"
31#include "llvm/IR/DiagnosticPrinter.h"
32#include "llvm/Support/Debug.h"
33#include "llvm/Support/ErrorHandling.h"
34#include "llvm/Support/raw_ostream.h"
35
36using namespace llvm;
37
38#define DEBUG_TYPE "riscv-lower"
39
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +000040STATISTIC(NumTailCalls, "Number of tail calls");
41
Alex Bradbury89718422017-10-19 21:37:38 +000042RISCVTargetLowering::RISCVTargetLowering(const TargetMachine &TM,
43 const RISCVSubtarget &STI)
44 : TargetLowering(TM), Subtarget(STI) {
45
46 MVT XLenVT = Subtarget.getXLenVT();
47
48 // Set up the register classes.
49 addRegisterClass(XLenVT, &RISCV::GPRRegClass);
50
Alex Bradbury76c29ee2018-03-20 12:45:35 +000051 if (Subtarget.hasStdExtF())
52 addRegisterClass(MVT::f32, &RISCV::FPR32RegClass);
Alex Bradbury0b4175f2018-04-12 05:34:25 +000053 if (Subtarget.hasStdExtD())
54 addRegisterClass(MVT::f64, &RISCV::FPR64RegClass);
Alex Bradbury76c29ee2018-03-20 12:45:35 +000055
Alex Bradbury89718422017-10-19 21:37:38 +000056 // Compute derived properties from the register classes.
57 computeRegisterProperties(STI.getRegisterInfo());
58
59 setStackPointerRegisterToSaveRestore(RISCV::X2);
60
Alex Bradburycfa62912017-11-08 12:20:01 +000061 for (auto N : {ISD::EXTLOAD, ISD::SEXTLOAD, ISD::ZEXTLOAD})
62 setLoadExtAction(N, XLenVT, MVT::i1, Promote);
63
Alex Bradbury89718422017-10-19 21:37:38 +000064 // TODO: add all necessary setOperationAction calls.
Alex Bradburybfb00d42017-12-11 12:38:17 +000065 setOperationAction(ISD::DYNAMIC_STACKALLOC, XLenVT, Expand);
66
Alex Bradburyffc435e2017-11-21 08:11:03 +000067 setOperationAction(ISD::BR_JT, MVT::Other, Expand);
Alex Bradbury74913e12017-11-08 13:31:40 +000068 setOperationAction(ISD::BR_CC, XLenVT, Expand);
Alex Bradbury65385162017-11-21 07:51:32 +000069 setOperationAction(ISD::SELECT, XLenVT, Custom);
70 setOperationAction(ISD::SELECT_CC, XLenVT, Expand);
71
Alex Bradburybfb00d42017-12-11 12:38:17 +000072 setOperationAction(ISD::STACKSAVE, MVT::Other, Expand);
73 setOperationAction(ISD::STACKRESTORE, MVT::Other, Expand);
74
Alex Bradburyc85be0d2018-01-10 19:41:03 +000075 setOperationAction(ISD::VASTART, MVT::Other, Custom);
76 setOperationAction(ISD::VAARG, MVT::Other, Expand);
77 setOperationAction(ISD::VACOPY, MVT::Other, Expand);
78 setOperationAction(ISD::VAEND, MVT::Other, Expand);
79
Alex Bradburyffc435e2017-11-21 08:11:03 +000080 for (auto VT : {MVT::i1, MVT::i8, MVT::i16})
81 setOperationAction(ISD::SIGN_EXTEND_INREG, VT, Expand);
82
Alex Bradburyd05eae72019-01-12 07:32:31 +000083 if (Subtarget.is64Bit()) {
84 setTargetDAGCombine(ISD::SHL);
85 setTargetDAGCombine(ISD::SRL);
86 setTargetDAGCombine(ISD::SRA);
87 setTargetDAGCombine(ISD::ANY_EXTEND);
88 }
89
Alex Bradbury92138382018-01-18 12:36:38 +000090 if (!Subtarget.hasStdExtM()) {
91 setOperationAction(ISD::MUL, XLenVT, Expand);
92 setOperationAction(ISD::MULHS, XLenVT, Expand);
93 setOperationAction(ISD::MULHU, XLenVT, Expand);
94 setOperationAction(ISD::SDIV, XLenVT, Expand);
95 setOperationAction(ISD::UDIV, XLenVT, Expand);
96 setOperationAction(ISD::SREM, XLenVT, Expand);
97 setOperationAction(ISD::UREM, XLenVT, Expand);
98 }
Alex Bradburyffc435e2017-11-21 08:11:03 +000099
Alex Bradbury92138382018-01-18 12:36:38 +0000100 setOperationAction(ISD::SDIVREM, XLenVT, Expand);
101 setOperationAction(ISD::UDIVREM, XLenVT, Expand);
Alex Bradburyffc435e2017-11-21 08:11:03 +0000102 setOperationAction(ISD::SMUL_LOHI, XLenVT, Expand);
103 setOperationAction(ISD::UMUL_LOHI, XLenVT, Expand);
Alex Bradburyffc435e2017-11-21 08:11:03 +0000104
105 setOperationAction(ISD::SHL_PARTS, XLenVT, Expand);
106 setOperationAction(ISD::SRL_PARTS, XLenVT, Expand);
107 setOperationAction(ISD::SRA_PARTS, XLenVT, Expand);
108
109 setOperationAction(ISD::ROTL, XLenVT, Expand);
110 setOperationAction(ISD::ROTR, XLenVT, Expand);
111 setOperationAction(ISD::BSWAP, XLenVT, Expand);
112 setOperationAction(ISD::CTTZ, XLenVT, Expand);
113 setOperationAction(ISD::CTLZ, XLenVT, Expand);
114 setOperationAction(ISD::CTPOP, XLenVT, Expand);
115
Alex Bradbury21d28fe2018-04-12 05:50:06 +0000116 ISD::CondCode FPCCToExtend[] = {
117 ISD::SETOGT, ISD::SETOGE, ISD::SETONE, ISD::SETO, ISD::SETUEQ,
118 ISD::SETUGT, ISD::SETUGE, ISD::SETULT, ISD::SETULE, ISD::SETUNE,
119 ISD::SETGT, ISD::SETGE, ISD::SETNE};
120
Alex Bradbury52c27782018-11-02 19:50:38 +0000121 ISD::NodeType FPOpToExtend[] = {
Alex Bradbury919f5fb2018-12-13 10:49:05 +0000122 ISD::FSIN, ISD::FCOS, ISD::FSINCOS, ISD::FPOW, ISD::FREM};
Alex Bradbury52c27782018-11-02 19:50:38 +0000123
Alex Bradbury76c29ee2018-03-20 12:45:35 +0000124 if (Subtarget.hasStdExtF()) {
125 setOperationAction(ISD::FMINNUM, MVT::f32, Legal);
126 setOperationAction(ISD::FMAXNUM, MVT::f32, Legal);
Alex Bradbury21d28fe2018-04-12 05:50:06 +0000127 for (auto CC : FPCCToExtend)
Alex Bradbury65d6ea52018-03-21 15:11:02 +0000128 setCondCodeAction(CC, MVT::f32, Expand);
129 setOperationAction(ISD::SELECT_CC, MVT::f32, Expand);
130 setOperationAction(ISD::SELECT, MVT::f32, Custom);
131 setOperationAction(ISD::BR_CC, MVT::f32, Expand);
Alex Bradbury52c27782018-11-02 19:50:38 +0000132 for (auto Op : FPOpToExtend)
133 setOperationAction(Op, MVT::f32, Expand);
Alex Bradbury76c29ee2018-03-20 12:45:35 +0000134 }
135
Alex Bradbury5d0dfa52018-04-12 05:42:42 +0000136 if (Subtarget.hasStdExtD()) {
137 setOperationAction(ISD::FMINNUM, MVT::f64, Legal);
138 setOperationAction(ISD::FMAXNUM, MVT::f64, Legal);
Alex Bradbury21d28fe2018-04-12 05:50:06 +0000139 for (auto CC : FPCCToExtend)
140 setCondCodeAction(CC, MVT::f64, Expand);
141 setOperationAction(ISD::SELECT_CC, MVT::f64, Expand);
142 setOperationAction(ISD::SELECT, MVT::f64, Custom);
143 setOperationAction(ISD::BR_CC, MVT::f64, Expand);
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000144 setLoadExtAction(ISD::EXTLOAD, MVT::f64, MVT::f32, Expand);
Alex Bradbury60baa2e2018-04-12 05:47:15 +0000145 setTruncStoreAction(MVT::f64, MVT::f32, Expand);
Alex Bradbury52c27782018-11-02 19:50:38 +0000146 for (auto Op : FPOpToExtend)
147 setOperationAction(Op, MVT::f64, Expand);
Alex Bradbury5d0dfa52018-04-12 05:42:42 +0000148 }
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000149
Alex Bradburyffc435e2017-11-21 08:11:03 +0000150 setOperationAction(ISD::GlobalAddress, XLenVT, Custom);
151 setOperationAction(ISD::BlockAddress, XLenVT, Custom);
Alex Bradbury80c8eb72018-03-20 13:26:12 +0000152 setOperationAction(ISD::ConstantPool, XLenVT, Custom);
Alex Bradburyffc435e2017-11-21 08:11:03 +0000153
Alex Bradbury21aea512018-09-19 10:54:22 +0000154 if (Subtarget.hasStdExtA()) {
Alex Bradbury96f492d2018-06-13 12:04:51 +0000155 setMaxAtomicSizeInBitsSupported(Subtarget.getXLen());
Alex Bradbury21aea512018-09-19 10:54:22 +0000156 setMinCmpXchgSizeInBits(32);
157 } else {
Alex Bradbury96f492d2018-06-13 12:04:51 +0000158 setMaxAtomicSizeInBitsSupported(0);
Alex Bradbury21aea512018-09-19 10:54:22 +0000159 }
Alex Bradburydc790dd2018-06-13 11:58:46 +0000160
Alex Bradbury89718422017-10-19 21:37:38 +0000161 setBooleanContents(ZeroOrOneBooleanContent);
162
163 // Function alignments (log2).
Shiva Chenb48b0272018-04-12 11:30:59 +0000164 unsigned FunctionAlignment = Subtarget.hasStdExtC() ? 1 : 2;
165 setMinFunctionAlignment(FunctionAlignment);
166 setPrefFunctionAlignment(FunctionAlignment);
Alex Bradburyffc435e2017-11-21 08:11:03 +0000167
168 // Effectively disable jump table generation.
169 setMinimumJumpTableEntries(INT_MAX);
Alex Bradbury89718422017-10-19 21:37:38 +0000170}
171
Shiva Chenbbf4c5c2018-02-02 02:43:18 +0000172EVT RISCVTargetLowering::getSetCCResultType(const DataLayout &DL, LLVMContext &,
173 EVT VT) const {
174 if (!VT.isVector())
175 return getPointerTy(DL);
176 return VT.changeVectorElementTypeToInteger();
177}
178
Alex Bradbury21aea512018-09-19 10:54:22 +0000179bool RISCVTargetLowering::getTgtMemIntrinsic(IntrinsicInfo &Info,
180 const CallInst &I,
181 MachineFunction &MF,
182 unsigned Intrinsic) const {
183 switch (Intrinsic) {
184 default:
185 return false;
186 case Intrinsic::riscv_masked_atomicrmw_xchg_i32:
187 case Intrinsic::riscv_masked_atomicrmw_add_i32:
188 case Intrinsic::riscv_masked_atomicrmw_sub_i32:
189 case Intrinsic::riscv_masked_atomicrmw_nand_i32:
190 case Intrinsic::riscv_masked_atomicrmw_max_i32:
191 case Intrinsic::riscv_masked_atomicrmw_min_i32:
192 case Intrinsic::riscv_masked_atomicrmw_umax_i32:
193 case Intrinsic::riscv_masked_atomicrmw_umin_i32:
Alex Bradbury66d9a752018-11-29 20:43:42 +0000194 case Intrinsic::riscv_masked_cmpxchg_i32:
Alex Bradbury21aea512018-09-19 10:54:22 +0000195 PointerType *PtrTy = cast<PointerType>(I.getArgOperand(0)->getType());
196 Info.opc = ISD::INTRINSIC_W_CHAIN;
197 Info.memVT = MVT::getVT(PtrTy->getElementType());
198 Info.ptrVal = I.getArgOperand(0);
199 Info.offset = 0;
200 Info.align = 4;
201 Info.flags = MachineMemOperand::MOLoad | MachineMemOperand::MOStore |
202 MachineMemOperand::MOVolatile;
203 return true;
204 }
205}
206
Alex Bradbury09926292018-04-26 12:13:48 +0000207bool RISCVTargetLowering::isLegalAddressingMode(const DataLayout &DL,
208 const AddrMode &AM, Type *Ty,
209 unsigned AS,
210 Instruction *I) const {
211 // No global is ever allowed as a base.
212 if (AM.BaseGV)
213 return false;
214
215 // Require a 12-bit signed offset.
216 if (!isInt<12>(AM.BaseOffs))
217 return false;
218
219 switch (AM.Scale) {
220 case 0: // "r+i" or just "i", depending on HasBaseReg.
221 break;
222 case 1:
223 if (!AM.HasBaseReg) // allow "r+i".
224 break;
225 return false; // disallow "r+r" or "r+r+i".
226 default:
227 return false;
228 }
229
230 return true;
231}
232
Alex Bradburydcbff632018-04-26 13:15:17 +0000233bool RISCVTargetLowering::isLegalICmpImmediate(int64_t Imm) const {
234 return isInt<12>(Imm);
235}
236
Alex Bradbury5c41ece2018-04-26 13:00:37 +0000237bool RISCVTargetLowering::isLegalAddImmediate(int64_t Imm) const {
238 return isInt<12>(Imm);
239}
240
Alex Bradbury130b8b32018-04-26 13:37:00 +0000241// On RV32, 64-bit integers are split into their high and low parts and held
242// in two different registers, so the trunc is free since the low register can
243// just be used.
244bool RISCVTargetLowering::isTruncateFree(Type *SrcTy, Type *DstTy) const {
245 if (Subtarget.is64Bit() || !SrcTy->isIntegerTy() || !DstTy->isIntegerTy())
246 return false;
247 unsigned SrcBits = SrcTy->getPrimitiveSizeInBits();
248 unsigned DestBits = DstTy->getPrimitiveSizeInBits();
249 return (SrcBits == 64 && DestBits == 32);
250}
251
252bool RISCVTargetLowering::isTruncateFree(EVT SrcVT, EVT DstVT) const {
253 if (Subtarget.is64Bit() || SrcVT.isVector() || DstVT.isVector() ||
254 !SrcVT.isInteger() || !DstVT.isInteger())
255 return false;
256 unsigned SrcBits = SrcVT.getSizeInBits();
257 unsigned DestBits = DstVT.getSizeInBits();
258 return (SrcBits == 64 && DestBits == 32);
259}
260
Alex Bradbury15e894b2018-04-26 14:04:18 +0000261bool RISCVTargetLowering::isZExtFree(SDValue Val, EVT VT2) const {
262 // Zexts are free if they can be combined with a load.
263 if (auto *LD = dyn_cast<LoadSDNode>(Val)) {
264 EVT MemVT = LD->getMemoryVT();
265 if ((MemVT == MVT::i8 || MemVT == MVT::i16 ||
266 (Subtarget.is64Bit() && MemVT == MVT::i32)) &&
267 (LD->getExtensionType() == ISD::NON_EXTLOAD ||
268 LD->getExtensionType() == ISD::ZEXTLOAD))
269 return true;
270 }
271
272 return TargetLowering::isZExtFree(Val, VT2);
273}
274
Alex Bradburye0e62e92018-11-30 09:56:54 +0000275bool RISCVTargetLowering::isSExtCheaperThanZExt(EVT SrcVT, EVT DstVT) const {
276 return Subtarget.is64Bit() && SrcVT == MVT::i32 && DstVT == MVT::i64;
277}
278
Alex Bradbury65385162017-11-21 07:51:32 +0000279// Changes the condition code and swaps operands if necessary, so the SetCC
280// operation matches one of the comparisons supported directly in the RISC-V
281// ISA.
282static void normaliseSetCC(SDValue &LHS, SDValue &RHS, ISD::CondCode &CC) {
283 switch (CC) {
284 default:
285 break;
286 case ISD::SETGT:
287 case ISD::SETLE:
288 case ISD::SETUGT:
289 case ISD::SETULE:
290 CC = ISD::getSetCCSwappedOperands(CC);
291 std::swap(LHS, RHS);
292 break;
293 }
294}
295
296// Return the RISC-V branch opcode that matches the given DAG integer
297// condition code. The CondCode must be one of those supported by the RISC-V
298// ISA (see normaliseSetCC).
299static unsigned getBranchOpcodeForIntCondCode(ISD::CondCode CC) {
300 switch (CC) {
301 default:
302 llvm_unreachable("Unsupported CondCode");
303 case ISD::SETEQ:
304 return RISCV::BEQ;
305 case ISD::SETNE:
306 return RISCV::BNE;
307 case ISD::SETLT:
308 return RISCV::BLT;
309 case ISD::SETGE:
310 return RISCV::BGE;
311 case ISD::SETULT:
312 return RISCV::BLTU;
313 case ISD::SETUGE:
314 return RISCV::BGEU;
315 }
316}
317
Alex Bradbury89718422017-10-19 21:37:38 +0000318SDValue RISCVTargetLowering::LowerOperation(SDValue Op,
319 SelectionDAG &DAG) const {
320 switch (Op.getOpcode()) {
321 default:
322 report_fatal_error("unimplemented operand");
Alex Bradburyec8aa912017-11-08 13:24:21 +0000323 case ISD::GlobalAddress:
324 return lowerGlobalAddress(Op, DAG);
Alex Bradburyffc435e2017-11-21 08:11:03 +0000325 case ISD::BlockAddress:
326 return lowerBlockAddress(Op, DAG);
Alex Bradbury80c8eb72018-03-20 13:26:12 +0000327 case ISD::ConstantPool:
328 return lowerConstantPool(Op, DAG);
Alex Bradbury65385162017-11-21 07:51:32 +0000329 case ISD::SELECT:
330 return lowerSELECT(Op, DAG);
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000331 case ISD::VASTART:
332 return lowerVASTART(Op, DAG);
Alex Bradbury70f137b2018-01-10 20:12:00 +0000333 case ISD::FRAMEADDR:
Alex Bradbury0e167662018-10-04 05:27:50 +0000334 return lowerFRAMEADDR(Op, DAG);
Alex Bradbury70f137b2018-01-10 20:12:00 +0000335 case ISD::RETURNADDR:
Alex Bradbury0e167662018-10-04 05:27:50 +0000336 return lowerRETURNADDR(Op, DAG);
Alex Bradburyec8aa912017-11-08 13:24:21 +0000337 }
338}
339
340SDValue RISCVTargetLowering::lowerGlobalAddress(SDValue Op,
341 SelectionDAG &DAG) const {
342 SDLoc DL(Op);
343 EVT Ty = Op.getValueType();
344 GlobalAddressSDNode *N = cast<GlobalAddressSDNode>(Op);
345 const GlobalValue *GV = N->getGlobal();
346 int64_t Offset = N->getOffset();
Sameer AbuAsal1dc0a8f2018-05-17 18:14:53 +0000347 MVT XLenVT = Subtarget.getXLenVT();
Alex Bradburyec8aa912017-11-08 13:24:21 +0000348
Alex Bradbury5bf3b202018-10-04 14:30:03 +0000349 if (isPositionIndependent())
Alex Bradburyec8aa912017-11-08 13:24:21 +0000350 report_fatal_error("Unable to lowerGlobalAddress");
Sameer AbuAsal1dc0a8f2018-05-17 18:14:53 +0000351 // In order to maximise the opportunity for common subexpression elimination,
352 // emit a separate ADD node for the global address offset instead of folding
353 // it in the global address node. Later peephole optimisations may choose to
354 // fold it back in when profitable.
355 SDValue GAHi = DAG.getTargetGlobalAddress(GV, DL, Ty, 0, RISCVII::MO_HI);
356 SDValue GALo = DAG.getTargetGlobalAddress(GV, DL, Ty, 0, RISCVII::MO_LO);
Alex Bradburyffc435e2017-11-21 08:11:03 +0000357 SDValue MNHi = SDValue(DAG.getMachineNode(RISCV::LUI, DL, Ty, GAHi), 0);
358 SDValue MNLo =
359 SDValue(DAG.getMachineNode(RISCV::ADDI, DL, Ty, MNHi, GALo), 0);
Sameer AbuAsal1dc0a8f2018-05-17 18:14:53 +0000360 if (Offset != 0)
361 return DAG.getNode(ISD::ADD, DL, Ty, MNLo,
362 DAG.getConstant(Offset, DL, XLenVT));
Alex Bradburyffc435e2017-11-21 08:11:03 +0000363 return MNLo;
364}
365
366SDValue RISCVTargetLowering::lowerBlockAddress(SDValue Op,
367 SelectionDAG &DAG) const {
368 SDLoc DL(Op);
369 EVT Ty = Op.getValueType();
370 BlockAddressSDNode *N = cast<BlockAddressSDNode>(Op);
371 const BlockAddress *BA = N->getBlockAddress();
372 int64_t Offset = N->getOffset();
373
Alex Bradbury5bf3b202018-10-04 14:30:03 +0000374 if (isPositionIndependent())
Alex Bradburyffc435e2017-11-21 08:11:03 +0000375 report_fatal_error("Unable to lowerBlockAddress");
376
377 SDValue BAHi = DAG.getTargetBlockAddress(BA, Ty, Offset, RISCVII::MO_HI);
378 SDValue BALo = DAG.getTargetBlockAddress(BA, Ty, Offset, RISCVII::MO_LO);
379 SDValue MNHi = SDValue(DAG.getMachineNode(RISCV::LUI, DL, Ty, BAHi), 0);
380 SDValue MNLo =
381 SDValue(DAG.getMachineNode(RISCV::ADDI, DL, Ty, MNHi, BALo), 0);
382 return MNLo;
383}
384
Alex Bradbury80c8eb72018-03-20 13:26:12 +0000385SDValue RISCVTargetLowering::lowerConstantPool(SDValue Op,
386 SelectionDAG &DAG) const {
387 SDLoc DL(Op);
388 EVT Ty = Op.getValueType();
389 ConstantPoolSDNode *N = cast<ConstantPoolSDNode>(Op);
390 const Constant *CPA = N->getConstVal();
391 int64_t Offset = N->getOffset();
392 unsigned Alignment = N->getAlignment();
393
394 if (!isPositionIndependent()) {
395 SDValue CPAHi =
396 DAG.getTargetConstantPool(CPA, Ty, Alignment, Offset, RISCVII::MO_HI);
397 SDValue CPALo =
398 DAG.getTargetConstantPool(CPA, Ty, Alignment, Offset, RISCVII::MO_LO);
399 SDValue MNHi = SDValue(DAG.getMachineNode(RISCV::LUI, DL, Ty, CPAHi), 0);
400 SDValue MNLo =
401 SDValue(DAG.getMachineNode(RISCV::ADDI, DL, Ty, MNHi, CPALo), 0);
402 return MNLo;
403 } else {
404 report_fatal_error("Unable to lowerConstantPool");
405 }
406}
407
Alex Bradbury65385162017-11-21 07:51:32 +0000408SDValue RISCVTargetLowering::lowerSELECT(SDValue Op, SelectionDAG &DAG) const {
409 SDValue CondV = Op.getOperand(0);
410 SDValue TrueV = Op.getOperand(1);
411 SDValue FalseV = Op.getOperand(2);
412 SDLoc DL(Op);
413 MVT XLenVT = Subtarget.getXLenVT();
414
415 // If the result type is XLenVT and CondV is the output of a SETCC node
416 // which also operated on XLenVT inputs, then merge the SETCC node into the
417 // lowered RISCVISD::SELECT_CC to take advantage of the integer
418 // compare+branch instructions. i.e.:
419 // (select (setcc lhs, rhs, cc), truev, falsev)
420 // -> (riscvisd::select_cc lhs, rhs, cc, truev, falsev)
421 if (Op.getSimpleValueType() == XLenVT && CondV.getOpcode() == ISD::SETCC &&
422 CondV.getOperand(0).getSimpleValueType() == XLenVT) {
423 SDValue LHS = CondV.getOperand(0);
424 SDValue RHS = CondV.getOperand(1);
425 auto CC = cast<CondCodeSDNode>(CondV.getOperand(2));
426 ISD::CondCode CCVal = CC->get();
427
428 normaliseSetCC(LHS, RHS, CCVal);
429
430 SDValue TargetCC = DAG.getConstant(CCVal, DL, XLenVT);
431 SDVTList VTs = DAG.getVTList(Op.getValueType(), MVT::Glue);
432 SDValue Ops[] = {LHS, RHS, TargetCC, TrueV, FalseV};
433 return DAG.getNode(RISCVISD::SELECT_CC, DL, VTs, Ops);
434 }
435
436 // Otherwise:
437 // (select condv, truev, falsev)
438 // -> (riscvisd::select_cc condv, zero, setne, truev, falsev)
439 SDValue Zero = DAG.getConstant(0, DL, XLenVT);
440 SDValue SetNE = DAG.getConstant(ISD::SETNE, DL, XLenVT);
441
442 SDVTList VTs = DAG.getVTList(Op.getValueType(), MVT::Glue);
443 SDValue Ops[] = {CondV, Zero, SetNE, TrueV, FalseV};
444
445 return DAG.getNode(RISCVISD::SELECT_CC, DL, VTs, Ops);
446}
447
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000448SDValue RISCVTargetLowering::lowerVASTART(SDValue Op, SelectionDAG &DAG) const {
449 MachineFunction &MF = DAG.getMachineFunction();
450 RISCVMachineFunctionInfo *FuncInfo = MF.getInfo<RISCVMachineFunctionInfo>();
451
452 SDLoc DL(Op);
453 SDValue FI = DAG.getFrameIndex(FuncInfo->getVarArgsFrameIndex(),
454 getPointerTy(MF.getDataLayout()));
455
456 // vastart just stores the address of the VarArgsFrameIndex slot into the
457 // memory location argument.
458 const Value *SV = cast<SrcValueSDNode>(Op.getOperand(2))->getValue();
459 return DAG.getStore(Op.getOperand(0), DL, FI, Op.getOperand(1),
460 MachinePointerInfo(SV));
461}
462
Alex Bradbury0e167662018-10-04 05:27:50 +0000463SDValue RISCVTargetLowering::lowerFRAMEADDR(SDValue Op,
Alex Bradbury70f137b2018-01-10 20:12:00 +0000464 SelectionDAG &DAG) const {
465 const RISCVRegisterInfo &RI = *Subtarget.getRegisterInfo();
466 MachineFunction &MF = DAG.getMachineFunction();
467 MachineFrameInfo &MFI = MF.getFrameInfo();
468 MFI.setFrameAddressIsTaken(true);
469 unsigned FrameReg = RI.getFrameRegister(MF);
470 int XLenInBytes = Subtarget.getXLen() / 8;
471
472 EVT VT = Op.getValueType();
473 SDLoc DL(Op);
474 SDValue FrameAddr = DAG.getCopyFromReg(DAG.getEntryNode(), DL, FrameReg, VT);
475 unsigned Depth = cast<ConstantSDNode>(Op.getOperand(0))->getZExtValue();
476 while (Depth--) {
477 int Offset = -(XLenInBytes * 2);
478 SDValue Ptr = DAG.getNode(ISD::ADD, DL, VT, FrameAddr,
479 DAG.getIntPtrConstant(Offset, DL));
480 FrameAddr =
481 DAG.getLoad(VT, DL, DAG.getEntryNode(), Ptr, MachinePointerInfo());
482 }
483 return FrameAddr;
484}
485
Alex Bradbury0e167662018-10-04 05:27:50 +0000486SDValue RISCVTargetLowering::lowerRETURNADDR(SDValue Op,
Alex Bradbury70f137b2018-01-10 20:12:00 +0000487 SelectionDAG &DAG) const {
488 const RISCVRegisterInfo &RI = *Subtarget.getRegisterInfo();
489 MachineFunction &MF = DAG.getMachineFunction();
490 MachineFrameInfo &MFI = MF.getFrameInfo();
491 MFI.setReturnAddressIsTaken(true);
492 MVT XLenVT = Subtarget.getXLenVT();
493 int XLenInBytes = Subtarget.getXLen() / 8;
494
495 if (verifyReturnAddressArgumentIsConstant(Op, DAG))
496 return SDValue();
497
498 EVT VT = Op.getValueType();
499 SDLoc DL(Op);
500 unsigned Depth = cast<ConstantSDNode>(Op.getOperand(0))->getZExtValue();
501 if (Depth) {
502 int Off = -XLenInBytes;
Alex Bradbury0e167662018-10-04 05:27:50 +0000503 SDValue FrameAddr = lowerFRAMEADDR(Op, DAG);
Alex Bradbury70f137b2018-01-10 20:12:00 +0000504 SDValue Offset = DAG.getConstant(Off, DL, VT);
505 return DAG.getLoad(VT, DL, DAG.getEntryNode(),
506 DAG.getNode(ISD::ADD, DL, VT, FrameAddr, Offset),
507 MachinePointerInfo());
508 }
509
510 // Return the value of the return address register, marking it an implicit
511 // live-in.
512 unsigned Reg = MF.addLiveIn(RI.getRARegister(), getRegClassFor(XLenVT));
513 return DAG.getCopyFromReg(DAG.getEntryNode(), DL, Reg, XLenVT);
514}
515
Alex Bradburyd05eae72019-01-12 07:32:31 +0000516// Return true if the given node is a shift with a non-constant shift amount.
517static bool isVariableShift(SDValue Val) {
518 switch (Val.getOpcode()) {
519 default:
520 return false;
521 case ISD::SHL:
522 case ISD::SRA:
523 case ISD::SRL:
524 return Val.getOperand(1).getOpcode() != ISD::Constant;
525 }
526}
527
Alex Bradbury5ac0a2f2018-10-03 23:30:16 +0000528SDValue RISCVTargetLowering::PerformDAGCombine(SDNode *N,
529 DAGCombinerInfo &DCI) const {
Alex Bradburyd05eae72019-01-12 07:32:31 +0000530 SelectionDAG &DAG = DCI.DAG;
531
Alex Bradbury5ac0a2f2018-10-03 23:30:16 +0000532 switch (N->getOpcode()) {
533 default:
534 break;
Alex Bradburyd05eae72019-01-12 07:32:31 +0000535 case ISD::SHL:
536 case ISD::SRL:
537 case ISD::SRA: {
538 assert(Subtarget.getXLen() == 64 && "Combine should be 64-bit only");
539 if (!DCI.isBeforeLegalize())
540 break;
541 SDValue RHS = N->getOperand(1);
542 if (N->getValueType(0) != MVT::i32 || RHS->getOpcode() == ISD::Constant ||
543 (RHS->getOpcode() == ISD::AssertZext &&
544 cast<VTSDNode>(RHS->getOperand(1))->getVT().getSizeInBits() <= 5))
545 break;
546 SDValue LHS = N->getOperand(0);
547 SDLoc DL(N);
548 SDValue NewRHS =
549 DAG.getNode(ISD::AssertZext, DL, RHS.getValueType(), RHS,
550 DAG.getValueType(EVT::getIntegerVT(*DAG.getContext(), 5)));
551 return DCI.CombineTo(
552 N, DAG.getNode(N->getOpcode(), DL, LHS.getValueType(), LHS, NewRHS));
553 }
554 case ISD::ANY_EXTEND: {
555 // If any-extending an i32 variable-length shift to i64, then instead
556 // sign-extend in order to increase the chance of being able to select the
557 // sllw/srlw/sraw instruction.
558 SDValue Src = N->getOperand(0);
559 if (N->getValueType(0) != MVT::i64 || Src.getValueType() != MVT::i32 ||
560 !isVariableShift(Src))
561 break;
562 SDLoc DL(N);
563 return DCI.CombineTo(N, DAG.getNode(ISD::SIGN_EXTEND, DL, MVT::i64, Src));
564 }
Alex Bradbury5ac0a2f2018-10-03 23:30:16 +0000565 case RISCVISD::SplitF64: {
566 // If the input to SplitF64 is just BuildPairF64 then the operation is
567 // redundant. Instead, use BuildPairF64's operands directly.
568 SDValue Op0 = N->getOperand(0);
569 if (Op0->getOpcode() != RISCVISD::BuildPairF64)
570 break;
571 return DCI.CombineTo(N, Op0.getOperand(0), Op0.getOperand(1));
572 }
573 }
574
575 return SDValue();
576}
577
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000578static MachineBasicBlock *emitSplitF64Pseudo(MachineInstr &MI,
579 MachineBasicBlock *BB) {
580 assert(MI.getOpcode() == RISCV::SplitF64Pseudo && "Unexpected instruction");
581
582 MachineFunction &MF = *BB->getParent();
583 DebugLoc DL = MI.getDebugLoc();
584 const TargetInstrInfo &TII = *MF.getSubtarget().getInstrInfo();
585 const TargetRegisterInfo *RI = MF.getSubtarget().getRegisterInfo();
586 unsigned LoReg = MI.getOperand(0).getReg();
587 unsigned HiReg = MI.getOperand(1).getReg();
588 unsigned SrcReg = MI.getOperand(2).getReg();
589 const TargetRegisterClass *SrcRC = &RISCV::FPR64RegClass;
590 int FI = MF.getInfo<RISCVMachineFunctionInfo>()->getMoveF64FrameIndex();
591
592 TII.storeRegToStackSlot(*BB, MI, SrcReg, MI.getOperand(2).isKill(), FI, SrcRC,
593 RI);
594 MachineMemOperand *MMO =
595 MF.getMachineMemOperand(MachinePointerInfo::getFixedStack(MF, FI),
596 MachineMemOperand::MOLoad, 8, 8);
597 BuildMI(*BB, MI, DL, TII.get(RISCV::LW), LoReg)
598 .addFrameIndex(FI)
599 .addImm(0)
600 .addMemOperand(MMO);
601 BuildMI(*BB, MI, DL, TII.get(RISCV::LW), HiReg)
602 .addFrameIndex(FI)
603 .addImm(4)
604 .addMemOperand(MMO);
605 MI.eraseFromParent(); // The pseudo instruction is gone now.
606 return BB;
607}
608
609static MachineBasicBlock *emitBuildPairF64Pseudo(MachineInstr &MI,
610 MachineBasicBlock *BB) {
611 assert(MI.getOpcode() == RISCV::BuildPairF64Pseudo &&
612 "Unexpected instruction");
613
614 MachineFunction &MF = *BB->getParent();
615 DebugLoc DL = MI.getDebugLoc();
616 const TargetInstrInfo &TII = *MF.getSubtarget().getInstrInfo();
617 const TargetRegisterInfo *RI = MF.getSubtarget().getRegisterInfo();
618 unsigned DstReg = MI.getOperand(0).getReg();
619 unsigned LoReg = MI.getOperand(1).getReg();
620 unsigned HiReg = MI.getOperand(2).getReg();
621 const TargetRegisterClass *DstRC = &RISCV::FPR64RegClass;
622 int FI = MF.getInfo<RISCVMachineFunctionInfo>()->getMoveF64FrameIndex();
623
624 MachineMemOperand *MMO =
625 MF.getMachineMemOperand(MachinePointerInfo::getFixedStack(MF, FI),
626 MachineMemOperand::MOStore, 8, 8);
627 BuildMI(*BB, MI, DL, TII.get(RISCV::SW))
628 .addReg(LoReg, getKillRegState(MI.getOperand(1).isKill()))
629 .addFrameIndex(FI)
630 .addImm(0)
631 .addMemOperand(MMO);
632 BuildMI(*BB, MI, DL, TII.get(RISCV::SW))
633 .addReg(HiReg, getKillRegState(MI.getOperand(2).isKill()))
634 .addFrameIndex(FI)
635 .addImm(4)
636 .addMemOperand(MMO);
637 TII.loadRegFromStackSlot(*BB, MI, DstReg, FI, DstRC, RI);
638 MI.eraseFromParent(); // The pseudo instruction is gone now.
639 return BB;
640}
641
Alex Bradbury65385162017-11-21 07:51:32 +0000642MachineBasicBlock *
643RISCVTargetLowering::EmitInstrWithCustomInserter(MachineInstr &MI,
644 MachineBasicBlock *BB) const {
Alex Bradbury65d6ea52018-03-21 15:11:02 +0000645 switch (MI.getOpcode()) {
646 default:
647 llvm_unreachable("Unexpected instr type to insert");
648 case RISCV::Select_GPR_Using_CC_GPR:
649 case RISCV::Select_FPR32_Using_CC_GPR:
Alex Bradbury21d28fe2018-04-12 05:50:06 +0000650 case RISCV::Select_FPR64_Using_CC_GPR:
Alex Bradbury65d6ea52018-03-21 15:11:02 +0000651 break;
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000652 case RISCV::BuildPairF64Pseudo:
653 return emitBuildPairF64Pseudo(MI, BB);
654 case RISCV::SplitF64Pseudo:
655 return emitSplitF64Pseudo(MI, BB);
Alex Bradbury65d6ea52018-03-21 15:11:02 +0000656 }
Alex Bradbury65385162017-11-21 07:51:32 +0000657
658 // To "insert" a SELECT instruction, we actually have to insert the triangle
659 // control-flow pattern. The incoming instruction knows the destination vreg
660 // to set, the condition code register to branch on, the true/false values to
661 // select between, and the condcode to use to select the appropriate branch.
662 //
663 // We produce the following control flow:
664 // HeadMBB
665 // | \
666 // | IfFalseMBB
667 // | /
668 // TailMBB
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000669 const TargetInstrInfo &TII = *BB->getParent()->getSubtarget().getInstrInfo();
Alex Bradbury65385162017-11-21 07:51:32 +0000670 const BasicBlock *LLVM_BB = BB->getBasicBlock();
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000671 DebugLoc DL = MI.getDebugLoc();
Alex Bradbury65385162017-11-21 07:51:32 +0000672 MachineFunction::iterator I = ++BB->getIterator();
673
674 MachineBasicBlock *HeadMBB = BB;
675 MachineFunction *F = BB->getParent();
676 MachineBasicBlock *TailMBB = F->CreateMachineBasicBlock(LLVM_BB);
677 MachineBasicBlock *IfFalseMBB = F->CreateMachineBasicBlock(LLVM_BB);
678
679 F->insert(I, IfFalseMBB);
680 F->insert(I, TailMBB);
681 // Move all remaining instructions to TailMBB.
682 TailMBB->splice(TailMBB->begin(), HeadMBB,
683 std::next(MachineBasicBlock::iterator(MI)), HeadMBB->end());
684 // Update machine-CFG edges by transferring all successors of the current
685 // block to the new block which will contain the Phi node for the select.
686 TailMBB->transferSuccessorsAndUpdatePHIs(HeadMBB);
687 // Set the successors for HeadMBB.
688 HeadMBB->addSuccessor(IfFalseMBB);
689 HeadMBB->addSuccessor(TailMBB);
690
691 // Insert appropriate branch.
692 unsigned LHS = MI.getOperand(1).getReg();
693 unsigned RHS = MI.getOperand(2).getReg();
694 auto CC = static_cast<ISD::CondCode>(MI.getOperand(3).getImm());
695 unsigned Opcode = getBranchOpcodeForIntCondCode(CC);
696
697 BuildMI(HeadMBB, DL, TII.get(Opcode))
698 .addReg(LHS)
699 .addReg(RHS)
700 .addMBB(TailMBB);
701
702 // IfFalseMBB just falls through to TailMBB.
703 IfFalseMBB->addSuccessor(TailMBB);
704
705 // %Result = phi [ %TrueValue, HeadMBB ], [ %FalseValue, IfFalseMBB ]
706 BuildMI(*TailMBB, TailMBB->begin(), DL, TII.get(RISCV::PHI),
707 MI.getOperand(0).getReg())
708 .addReg(MI.getOperand(4).getReg())
709 .addMBB(HeadMBB)
710 .addReg(MI.getOperand(5).getReg())
711 .addMBB(IfFalseMBB);
712
713 MI.eraseFromParent(); // The pseudo instruction is gone now.
714 return TailMBB;
715}
716
Alex Bradbury89718422017-10-19 21:37:38 +0000717// Calling Convention Implementation.
Alex Bradburydc31c612017-12-11 12:49:02 +0000718// The expectations for frontend ABI lowering vary from target to target.
719// Ideally, an LLVM frontend would be able to avoid worrying about many ABI
720// details, but this is a longer term goal. For now, we simply try to keep the
721// role of the frontend as simple and well-defined as possible. The rules can
722// be summarised as:
723// * Never split up large scalar arguments. We handle them here.
724// * If a hardfloat calling convention is being used, and the struct may be
725// passed in a pair of registers (fp+fp, int+fp), and both registers are
726// available, then pass as two separate arguments. If either the GPRs or FPRs
727// are exhausted, then pass according to the rule below.
728// * If a struct could never be passed in registers or directly in a stack
729// slot (as it is larger than 2*XLEN and the floating point rules don't
730// apply), then pass it using a pointer with the byval attribute.
731// * If a struct is less than 2*XLEN, then coerce to either a two-element
732// word-sized array or a 2*XLEN scalar (depending on alignment).
733// * The frontend can determine whether a struct is returned by reference or
734// not based on its size and fields. If it will be returned by reference, the
735// frontend must modify the prototype so a pointer with the sret annotation is
736// passed as the first argument. This is not necessary for large scalar
737// returns.
738// * Struct return values and varargs should be coerced to structs containing
739// register-size fields in the same situations they would be for fixed
740// arguments.
741
742static const MCPhysReg ArgGPRs[] = {
743 RISCV::X10, RISCV::X11, RISCV::X12, RISCV::X13,
744 RISCV::X14, RISCV::X15, RISCV::X16, RISCV::X17
745};
746
747// Pass a 2*XLEN argument that has been split into two XLEN values through
748// registers or the stack as necessary.
749static bool CC_RISCVAssign2XLen(unsigned XLen, CCState &State, CCValAssign VA1,
750 ISD::ArgFlagsTy ArgFlags1, unsigned ValNo2,
751 MVT ValVT2, MVT LocVT2,
752 ISD::ArgFlagsTy ArgFlags2) {
753 unsigned XLenInBytes = XLen / 8;
754 if (unsigned Reg = State.AllocateReg(ArgGPRs)) {
755 // At least one half can be passed via register.
756 State.addLoc(CCValAssign::getReg(VA1.getValNo(), VA1.getValVT(), Reg,
757 VA1.getLocVT(), CCValAssign::Full));
758 } else {
759 // Both halves must be passed on the stack, with proper alignment.
760 unsigned StackAlign = std::max(XLenInBytes, ArgFlags1.getOrigAlign());
761 State.addLoc(
762 CCValAssign::getMem(VA1.getValNo(), VA1.getValVT(),
763 State.AllocateStack(XLenInBytes, StackAlign),
764 VA1.getLocVT(), CCValAssign::Full));
765 State.addLoc(CCValAssign::getMem(
766 ValNo2, ValVT2, State.AllocateStack(XLenInBytes, XLenInBytes), LocVT2,
767 CCValAssign::Full));
768 return false;
769 }
770
771 if (unsigned Reg = State.AllocateReg(ArgGPRs)) {
772 // The second half can also be passed via register.
773 State.addLoc(
774 CCValAssign::getReg(ValNo2, ValVT2, Reg, LocVT2, CCValAssign::Full));
775 } else {
776 // The second half is passed via the stack, without additional alignment.
777 State.addLoc(CCValAssign::getMem(
778 ValNo2, ValVT2, State.AllocateStack(XLenInBytes, XLenInBytes), LocVT2,
779 CCValAssign::Full));
780 }
781
782 return false;
783}
784
785// Implements the RISC-V calling convention. Returns true upon failure.
786static bool CC_RISCV(const DataLayout &DL, unsigned ValNo, MVT ValVT, MVT LocVT,
787 CCValAssign::LocInfo LocInfo, ISD::ArgFlagsTy ArgFlags,
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000788 CCState &State, bool IsFixed, bool IsRet, Type *OrigTy) {
Alex Bradburydc31c612017-12-11 12:49:02 +0000789 unsigned XLen = DL.getLargestLegalIntTypeSizeInBits();
790 assert(XLen == 32 || XLen == 64);
791 MVT XLenVT = XLen == 32 ? MVT::i32 : MVT::i64;
Alex Bradbury76c29ee2018-03-20 12:45:35 +0000792 if (ValVT == MVT::f32) {
793 LocVT = MVT::i32;
794 LocInfo = CCValAssign::BCvt;
795 }
Alex Bradburydc31c612017-12-11 12:49:02 +0000796
797 // Any return value split in to more than two values can't be returned
798 // directly.
799 if (IsRet && ValNo > 1)
800 return true;
801
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000802 // If this is a variadic argument, the RISC-V calling convention requires
803 // that it is assigned an 'even' or 'aligned' register if it has 8-byte
804 // alignment (RV32) or 16-byte alignment (RV64). An aligned register should
805 // be used regardless of whether the original argument was split during
806 // legalisation or not. The argument will not be passed by registers if the
807 // original type is larger than 2*XLEN, so the register alignment rule does
808 // not apply.
809 unsigned TwoXLenInBytes = (2 * XLen) / 8;
810 if (!IsFixed && ArgFlags.getOrigAlign() == TwoXLenInBytes &&
811 DL.getTypeAllocSize(OrigTy) == TwoXLenInBytes) {
812 unsigned RegIdx = State.getFirstUnallocated(ArgGPRs);
813 // Skip 'odd' register if necessary.
814 if (RegIdx != array_lengthof(ArgGPRs) && RegIdx % 2 == 1)
815 State.AllocateReg(ArgGPRs);
816 }
817
Alex Bradburydc31c612017-12-11 12:49:02 +0000818 SmallVectorImpl<CCValAssign> &PendingLocs = State.getPendingLocs();
819 SmallVectorImpl<ISD::ArgFlagsTy> &PendingArgFlags =
820 State.getPendingArgFlags();
821
822 assert(PendingLocs.size() == PendingArgFlags.size() &&
823 "PendingLocs and PendingArgFlags out of sync");
824
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000825 // Handle passing f64 on RV32D with a soft float ABI.
826 if (XLen == 32 && ValVT == MVT::f64) {
Mandeep Singh Grang88a8b262018-04-16 18:56:10 +0000827 assert(!ArgFlags.isSplit() && PendingLocs.empty() &&
Alex Bradbury0b4175f2018-04-12 05:34:25 +0000828 "Can't lower f64 if it is split");
829 // Depending on available argument GPRS, f64 may be passed in a pair of
830 // GPRs, split between a GPR and the stack, or passed completely on the
831 // stack. LowerCall/LowerFormalArguments/LowerReturn must recognise these
832 // cases.
833 unsigned Reg = State.AllocateReg(ArgGPRs);
834 LocVT = MVT::i32;
835 if (!Reg) {
836 unsigned StackOffset = State.AllocateStack(8, 8);
837 State.addLoc(
838 CCValAssign::getMem(ValNo, ValVT, StackOffset, LocVT, LocInfo));
839 return false;
840 }
841 if (!State.AllocateReg(ArgGPRs))
842 State.AllocateStack(4, 4);
843 State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
844 return false;
845 }
846
Alex Bradburydc31c612017-12-11 12:49:02 +0000847 // Split arguments might be passed indirectly, so keep track of the pending
848 // values.
849 if (ArgFlags.isSplit() || !PendingLocs.empty()) {
850 LocVT = XLenVT;
851 LocInfo = CCValAssign::Indirect;
852 PendingLocs.push_back(
853 CCValAssign::getPending(ValNo, ValVT, LocVT, LocInfo));
854 PendingArgFlags.push_back(ArgFlags);
855 if (!ArgFlags.isSplitEnd()) {
856 return false;
857 }
858 }
859
860 // If the split argument only had two elements, it should be passed directly
861 // in registers or on the stack.
862 if (ArgFlags.isSplitEnd() && PendingLocs.size() <= 2) {
863 assert(PendingLocs.size() == 2 && "Unexpected PendingLocs.size()");
864 // Apply the normal calling convention rules to the first half of the
865 // split argument.
866 CCValAssign VA = PendingLocs[0];
867 ISD::ArgFlagsTy AF = PendingArgFlags[0];
868 PendingLocs.clear();
869 PendingArgFlags.clear();
870 return CC_RISCVAssign2XLen(XLen, State, VA, AF, ValNo, ValVT, LocVT,
871 ArgFlags);
872 }
873
874 // Allocate to a register if possible, or else a stack slot.
875 unsigned Reg = State.AllocateReg(ArgGPRs);
876 unsigned StackOffset = Reg ? 0 : State.AllocateStack(XLen / 8, XLen / 8);
877
878 // If we reach this point and PendingLocs is non-empty, we must be at the
879 // end of a split argument that must be passed indirectly.
880 if (!PendingLocs.empty()) {
881 assert(ArgFlags.isSplitEnd() && "Expected ArgFlags.isSplitEnd()");
882 assert(PendingLocs.size() > 2 && "Unexpected PendingLocs.size()");
883
884 for (auto &It : PendingLocs) {
885 if (Reg)
886 It.convertToReg(Reg);
887 else
888 It.convertToMem(StackOffset);
889 State.addLoc(It);
890 }
891 PendingLocs.clear();
892 PendingArgFlags.clear();
893 return false;
894 }
895
896 assert(LocVT == XLenVT && "Expected an XLenVT at this stage");
897
898 if (Reg) {
899 State.addLoc(CCValAssign::getReg(ValNo, ValVT, Reg, LocVT, LocInfo));
Alex Bradburye96b7c882018-10-04 07:28:49 +0000900 return false;
Alex Bradburydc31c612017-12-11 12:49:02 +0000901 }
Alex Bradburye96b7c882018-10-04 07:28:49 +0000902
903 if (ValVT == MVT::f32) {
904 LocVT = MVT::f32;
905 LocInfo = CCValAssign::Full;
906 }
907 State.addLoc(CCValAssign::getMem(ValNo, ValVT, StackOffset, LocVT, LocInfo));
Alex Bradburydc31c612017-12-11 12:49:02 +0000908 return false;
909}
910
911void RISCVTargetLowering::analyzeInputArgs(
912 MachineFunction &MF, CCState &CCInfo,
913 const SmallVectorImpl<ISD::InputArg> &Ins, bool IsRet) const {
914 unsigned NumArgs = Ins.size();
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000915 FunctionType *FType = MF.getFunction().getFunctionType();
Alex Bradburydc31c612017-12-11 12:49:02 +0000916
917 for (unsigned i = 0; i != NumArgs; ++i) {
918 MVT ArgVT = Ins[i].VT;
919 ISD::ArgFlagsTy ArgFlags = Ins[i].Flags;
920
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000921 Type *ArgTy = nullptr;
922 if (IsRet)
923 ArgTy = FType->getReturnType();
924 else if (Ins[i].isOrigArg())
925 ArgTy = FType->getParamType(Ins[i].getOrigArgIndex());
926
Alex Bradburydc31c612017-12-11 12:49:02 +0000927 if (CC_RISCV(MF.getDataLayout(), i, ArgVT, ArgVT, CCValAssign::Full,
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000928 ArgFlags, CCInfo, /*IsRet=*/true, IsRet, ArgTy)) {
Nicola Zaghend34e60c2018-05-14 12:53:11 +0000929 LLVM_DEBUG(dbgs() << "InputArg #" << i << " has unhandled type "
930 << EVT(ArgVT).getEVTString() << '\n');
Alex Bradburydc31c612017-12-11 12:49:02 +0000931 llvm_unreachable(nullptr);
932 }
933 }
934}
935
936void RISCVTargetLowering::analyzeOutputArgs(
937 MachineFunction &MF, CCState &CCInfo,
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000938 const SmallVectorImpl<ISD::OutputArg> &Outs, bool IsRet,
939 CallLoweringInfo *CLI) const {
Alex Bradburydc31c612017-12-11 12:49:02 +0000940 unsigned NumArgs = Outs.size();
941
942 for (unsigned i = 0; i != NumArgs; i++) {
943 MVT ArgVT = Outs[i].VT;
944 ISD::ArgFlagsTy ArgFlags = Outs[i].Flags;
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000945 Type *OrigTy = CLI ? CLI->getArgs()[Outs[i].OrigArgIndex].Ty : nullptr;
Alex Bradburydc31c612017-12-11 12:49:02 +0000946
947 if (CC_RISCV(MF.getDataLayout(), i, ArgVT, ArgVT, CCValAssign::Full,
Alex Bradburyc85be0d2018-01-10 19:41:03 +0000948 ArgFlags, CCInfo, Outs[i].IsFixed, IsRet, OrigTy)) {
Nicola Zaghend34e60c2018-05-14 12:53:11 +0000949 LLVM_DEBUG(dbgs() << "OutputArg #" << i << " has unhandled type "
950 << EVT(ArgVT).getEVTString() << "\n");
Alex Bradburydc31c612017-12-11 12:49:02 +0000951 llvm_unreachable(nullptr);
952 }
953 }
954}
955
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +0000956// Convert Val to a ValVT. Should not be called for CCValAssign::Indirect
957// values.
958static SDValue convertLocVTToValVT(SelectionDAG &DAG, SDValue Val,
959 const CCValAssign &VA, const SDLoc &DL) {
960 switch (VA.getLocInfo()) {
961 default:
962 llvm_unreachable("Unexpected CCValAssign::LocInfo");
963 case CCValAssign::Full:
964 break;
965 case CCValAssign::BCvt:
966 Val = DAG.getNode(ISD::BITCAST, DL, VA.getValVT(), Val);
967 break;
968 }
969 return Val;
970}
971
Alex Bradburydc31c612017-12-11 12:49:02 +0000972// The caller is responsible for loading the full value if the argument is
973// passed with CCValAssign::Indirect.
974static SDValue unpackFromRegLoc(SelectionDAG &DAG, SDValue Chain,
975 const CCValAssign &VA, const SDLoc &DL) {
976 MachineFunction &MF = DAG.getMachineFunction();
977 MachineRegisterInfo &RegInfo = MF.getRegInfo();
978 EVT LocVT = VA.getLocVT();
979 SDValue Val;
980
981 unsigned VReg = RegInfo.createVirtualRegister(&RISCV::GPRRegClass);
982 RegInfo.addLiveIn(VA.getLocReg(), VReg);
983 Val = DAG.getCopyFromReg(Chain, DL, VReg, LocVT);
984
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +0000985 if (VA.getLocInfo() == CCValAssign::Indirect)
986 return Val;
987
988 return convertLocVTToValVT(DAG, Val, VA, DL);
989}
990
991static SDValue convertValVTToLocVT(SelectionDAG &DAG, SDValue Val,
992 const CCValAssign &VA, const SDLoc &DL) {
993 EVT LocVT = VA.getLocVT();
994
Alex Bradburydc31c612017-12-11 12:49:02 +0000995 switch (VA.getLocInfo()) {
996 default:
997 llvm_unreachable("Unexpected CCValAssign::LocInfo");
998 case CCValAssign::Full:
Alex Bradbury76c29ee2018-03-20 12:45:35 +0000999 break;
1000 case CCValAssign::BCvt:
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +00001001 Val = DAG.getNode(ISD::BITCAST, DL, LocVT, Val);
Alex Bradbury76c29ee2018-03-20 12:45:35 +00001002 break;
Alex Bradburydc31c612017-12-11 12:49:02 +00001003 }
Alex Bradbury76c29ee2018-03-20 12:45:35 +00001004 return Val;
Alex Bradburydc31c612017-12-11 12:49:02 +00001005}
1006
1007// The caller is responsible for loading the full value if the argument is
1008// passed with CCValAssign::Indirect.
1009static SDValue unpackFromMemLoc(SelectionDAG &DAG, SDValue Chain,
1010 const CCValAssign &VA, const SDLoc &DL) {
1011 MachineFunction &MF = DAG.getMachineFunction();
1012 MachineFrameInfo &MFI = MF.getFrameInfo();
1013 EVT LocVT = VA.getLocVT();
1014 EVT ValVT = VA.getValVT();
1015 EVT PtrVT = MVT::getIntegerVT(DAG.getDataLayout().getPointerSizeInBits(0));
1016 int FI = MFI.CreateFixedObject(ValVT.getSizeInBits() / 8,
1017 VA.getLocMemOffset(), /*Immutable=*/true);
1018 SDValue FIN = DAG.getFrameIndex(FI, PtrVT);
1019 SDValue Val;
1020
1021 ISD::LoadExtType ExtType;
1022 switch (VA.getLocInfo()) {
1023 default:
1024 llvm_unreachable("Unexpected CCValAssign::LocInfo");
1025 case CCValAssign::Full:
1026 case CCValAssign::Indirect:
1027 ExtType = ISD::NON_EXTLOAD;
1028 break;
1029 }
1030 Val = DAG.getExtLoad(
1031 ExtType, DL, LocVT, Chain, FIN,
1032 MachinePointerInfo::getFixedStack(DAG.getMachineFunction(), FI), ValVT);
1033 return Val;
1034}
Alex Bradbury89718422017-10-19 21:37:38 +00001035
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001036static SDValue unpackF64OnRV32DSoftABI(SelectionDAG &DAG, SDValue Chain,
1037 const CCValAssign &VA, const SDLoc &DL) {
1038 assert(VA.getLocVT() == MVT::i32 && VA.getValVT() == MVT::f64 &&
1039 "Unexpected VA");
1040 MachineFunction &MF = DAG.getMachineFunction();
1041 MachineFrameInfo &MFI = MF.getFrameInfo();
1042 MachineRegisterInfo &RegInfo = MF.getRegInfo();
1043
1044 if (VA.isMemLoc()) {
1045 // f64 is passed on the stack.
1046 int FI = MFI.CreateFixedObject(8, VA.getLocMemOffset(), /*Immutable=*/true);
1047 SDValue FIN = DAG.getFrameIndex(FI, MVT::i32);
1048 return DAG.getLoad(MVT::f64, DL, Chain, FIN,
1049 MachinePointerInfo::getFixedStack(MF, FI));
1050 }
1051
1052 assert(VA.isRegLoc() && "Expected register VA assignment");
1053
1054 unsigned LoVReg = RegInfo.createVirtualRegister(&RISCV::GPRRegClass);
1055 RegInfo.addLiveIn(VA.getLocReg(), LoVReg);
1056 SDValue Lo = DAG.getCopyFromReg(Chain, DL, LoVReg, MVT::i32);
1057 SDValue Hi;
1058 if (VA.getLocReg() == RISCV::X17) {
1059 // Second half of f64 is passed on the stack.
1060 int FI = MFI.CreateFixedObject(4, 0, /*Immutable=*/true);
1061 SDValue FIN = DAG.getFrameIndex(FI, MVT::i32);
1062 Hi = DAG.getLoad(MVT::i32, DL, Chain, FIN,
1063 MachinePointerInfo::getFixedStack(MF, FI));
1064 } else {
1065 // Second half of f64 is passed in another GPR.
1066 unsigned HiVReg = RegInfo.createVirtualRegister(&RISCV::GPRRegClass);
1067 RegInfo.addLiveIn(VA.getLocReg() + 1, HiVReg);
1068 Hi = DAG.getCopyFromReg(Chain, DL, HiVReg, MVT::i32);
1069 }
1070 return DAG.getNode(RISCVISD::BuildPairF64, DL, MVT::f64, Lo, Hi);
1071}
1072
Alex Bradbury89718422017-10-19 21:37:38 +00001073// Transform physical registers into virtual registers.
1074SDValue RISCVTargetLowering::LowerFormalArguments(
1075 SDValue Chain, CallingConv::ID CallConv, bool IsVarArg,
1076 const SmallVectorImpl<ISD::InputArg> &Ins, const SDLoc &DL,
1077 SelectionDAG &DAG, SmallVectorImpl<SDValue> &InVals) const {
1078
1079 switch (CallConv) {
1080 default:
1081 report_fatal_error("Unsupported calling convention");
1082 case CallingConv::C:
Alex Bradburya3376752017-11-08 13:41:21 +00001083 case CallingConv::Fast:
Alex Bradbury89718422017-10-19 21:37:38 +00001084 break;
1085 }
1086
1087 MachineFunction &MF = DAG.getMachineFunction();
Ana Pazos2e4106b2018-07-26 17:49:43 +00001088
1089 const Function &Func = MF.getFunction();
1090 if (Func.hasFnAttribute("interrupt")) {
1091 if (!Func.arg_empty())
1092 report_fatal_error(
1093 "Functions with the interrupt attribute cannot have arguments!");
1094
1095 StringRef Kind =
1096 MF.getFunction().getFnAttribute("interrupt").getValueAsString();
1097
1098 if (!(Kind == "user" || Kind == "supervisor" || Kind == "machine"))
1099 report_fatal_error(
1100 "Function interrupt attribute argument not supported!");
1101 }
1102
Alex Bradburydc31c612017-12-11 12:49:02 +00001103 EVT PtrVT = getPointerTy(DAG.getDataLayout());
Alex Bradburyc85be0d2018-01-10 19:41:03 +00001104 MVT XLenVT = Subtarget.getXLenVT();
1105 unsigned XLenInBytes = Subtarget.getXLen() / 8;
1106 // Used with vargs to acumulate store chains.
1107 std::vector<SDValue> OutChains;
Alex Bradbury89718422017-10-19 21:37:38 +00001108
1109 // Assign locations to all of the incoming arguments.
1110 SmallVector<CCValAssign, 16> ArgLocs;
1111 CCState CCInfo(CallConv, IsVarArg, MF, ArgLocs, *DAG.getContext());
Alex Bradburydc31c612017-12-11 12:49:02 +00001112 analyzeInputArgs(MF, CCInfo, Ins, /*IsRet=*/false);
Alex Bradbury89718422017-10-19 21:37:38 +00001113
Alex Bradburydc31c612017-12-11 12:49:02 +00001114 for (unsigned i = 0, e = ArgLocs.size(); i != e; ++i) {
1115 CCValAssign &VA = ArgLocs[i];
Alex Bradburydc31c612017-12-11 12:49:02 +00001116 SDValue ArgValue;
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001117 // Passing f64 on RV32D with a soft float ABI must be handled as a special
1118 // case.
1119 if (VA.getLocVT() == MVT::i32 && VA.getValVT() == MVT::f64)
1120 ArgValue = unpackF64OnRV32DSoftABI(DAG, Chain, VA, DL);
1121 else if (VA.isRegLoc())
Alex Bradburydc31c612017-12-11 12:49:02 +00001122 ArgValue = unpackFromRegLoc(DAG, Chain, VA, DL);
1123 else
1124 ArgValue = unpackFromMemLoc(DAG, Chain, VA, DL);
Alex Bradbury89718422017-10-19 21:37:38 +00001125
Alex Bradburydc31c612017-12-11 12:49:02 +00001126 if (VA.getLocInfo() == CCValAssign::Indirect) {
1127 // If the original argument was split and passed by reference (e.g. i128
1128 // on RV32), we need to load all parts of it here (using the same
1129 // address).
1130 InVals.push_back(DAG.getLoad(VA.getValVT(), DL, Chain, ArgValue,
1131 MachinePointerInfo()));
1132 unsigned ArgIndex = Ins[i].OrigArgIndex;
1133 assert(Ins[i].PartOffset == 0);
1134 while (i + 1 != e && Ins[i + 1].OrigArgIndex == ArgIndex) {
1135 CCValAssign &PartVA = ArgLocs[i + 1];
1136 unsigned PartOffset = Ins[i + 1].PartOffset;
1137 SDValue Address = DAG.getNode(ISD::ADD, DL, PtrVT, ArgValue,
1138 DAG.getIntPtrConstant(PartOffset, DL));
1139 InVals.push_back(DAG.getLoad(PartVA.getValVT(), DL, Chain, Address,
1140 MachinePointerInfo()));
1141 ++i;
1142 }
1143 continue;
Alex Bradbury89718422017-10-19 21:37:38 +00001144 }
Alex Bradburydc31c612017-12-11 12:49:02 +00001145 InVals.push_back(ArgValue);
Alex Bradbury89718422017-10-19 21:37:38 +00001146 }
Alex Bradburyc85be0d2018-01-10 19:41:03 +00001147
1148 if (IsVarArg) {
1149 ArrayRef<MCPhysReg> ArgRegs = makeArrayRef(ArgGPRs);
1150 unsigned Idx = CCInfo.getFirstUnallocated(ArgRegs);
1151 const TargetRegisterClass *RC = &RISCV::GPRRegClass;
1152 MachineFrameInfo &MFI = MF.getFrameInfo();
1153 MachineRegisterInfo &RegInfo = MF.getRegInfo();
1154 RISCVMachineFunctionInfo *RVFI = MF.getInfo<RISCVMachineFunctionInfo>();
1155
1156 // Offset of the first variable argument from stack pointer, and size of
1157 // the vararg save area. For now, the varargs save area is either zero or
1158 // large enough to hold a0-a7.
1159 int VaArgOffset, VarArgsSaveSize;
1160
1161 // If all registers are allocated, then all varargs must be passed on the
1162 // stack and we don't need to save any argregs.
1163 if (ArgRegs.size() == Idx) {
1164 VaArgOffset = CCInfo.getNextStackOffset();
1165 VarArgsSaveSize = 0;
1166 } else {
1167 VarArgsSaveSize = XLenInBytes * (ArgRegs.size() - Idx);
1168 VaArgOffset = -VarArgsSaveSize;
1169 }
1170
1171 // Record the frame index of the first variable argument
1172 // which is a value necessary to VASTART.
1173 int FI = MFI.CreateFixedObject(XLenInBytes, VaArgOffset, true);
1174 RVFI->setVarArgsFrameIndex(FI);
1175
1176 // If saving an odd number of registers then create an extra stack slot to
1177 // ensure that the frame pointer is 2*XLEN-aligned, which in turn ensures
1178 // offsets to even-numbered registered remain 2*XLEN-aligned.
1179 if (Idx % 2) {
1180 FI = MFI.CreateFixedObject(XLenInBytes, VaArgOffset - (int)XLenInBytes,
1181 true);
1182 VarArgsSaveSize += XLenInBytes;
1183 }
1184
1185 // Copy the integer registers that may have been used for passing varargs
1186 // to the vararg save area.
1187 for (unsigned I = Idx; I < ArgRegs.size();
1188 ++I, VaArgOffset += XLenInBytes) {
1189 const unsigned Reg = RegInfo.createVirtualRegister(RC);
1190 RegInfo.addLiveIn(ArgRegs[I], Reg);
1191 SDValue ArgValue = DAG.getCopyFromReg(Chain, DL, Reg, XLenVT);
1192 FI = MFI.CreateFixedObject(XLenInBytes, VaArgOffset, true);
1193 SDValue PtrOff = DAG.getFrameIndex(FI, getPointerTy(DAG.getDataLayout()));
1194 SDValue Store = DAG.getStore(Chain, DL, ArgValue, PtrOff,
1195 MachinePointerInfo::getFixedStack(MF, FI));
1196 cast<StoreSDNode>(Store.getNode())
1197 ->getMemOperand()
1198 ->setValue((Value *)nullptr);
1199 OutChains.push_back(Store);
1200 }
1201 RVFI->setVarArgsSaveSize(VarArgsSaveSize);
1202 }
1203
1204 // All stores are grouped in one node to allow the matching between
1205 // the size of Ins and InVals. This only happens for vararg functions.
1206 if (!OutChains.empty()) {
1207 OutChains.push_back(Chain);
1208 Chain = DAG.getNode(ISD::TokenFactor, DL, MVT::Other, OutChains);
1209 }
1210
Alex Bradbury89718422017-10-19 21:37:38 +00001211 return Chain;
1212}
1213
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001214/// IsEligibleForTailCallOptimization - Check whether the call is eligible
1215/// for tail call optimization.
1216/// Note: This is modelled after ARM's IsEligibleForTailCallOptimization.
1217bool RISCVTargetLowering::IsEligibleForTailCallOptimization(
1218 CCState &CCInfo, CallLoweringInfo &CLI, MachineFunction &MF,
1219 const SmallVector<CCValAssign, 16> &ArgLocs) const {
1220
1221 auto &Callee = CLI.Callee;
1222 auto CalleeCC = CLI.CallConv;
1223 auto IsVarArg = CLI.IsVarArg;
1224 auto &Outs = CLI.Outs;
1225 auto &Caller = MF.getFunction();
1226 auto CallerCC = Caller.getCallingConv();
1227
1228 // Do not tail call opt functions with "disable-tail-calls" attribute.
1229 if (Caller.getFnAttribute("disable-tail-calls").getValueAsString() == "true")
1230 return false;
1231
1232 // Exception-handling functions need a special set of instructions to
1233 // indicate a return to the hardware. Tail-calling another function would
1234 // probably break this.
1235 // TODO: The "interrupt" attribute isn't currently defined by RISC-V. This
1236 // should be expanded as new function attributes are introduced.
1237 if (Caller.hasFnAttribute("interrupt"))
1238 return false;
1239
1240 // Do not tail call opt functions with varargs.
1241 if (IsVarArg)
1242 return false;
1243
1244 // Do not tail call opt if the stack is used to pass parameters.
1245 if (CCInfo.getNextStackOffset() != 0)
1246 return false;
1247
1248 // Do not tail call opt if any parameters need to be passed indirectly.
1249 // Since long doubles (fp128) and i128 are larger than 2*XLEN, they are
1250 // passed indirectly. So the address of the value will be passed in a
1251 // register, or if not available, then the address is put on the stack. In
1252 // order to pass indirectly, space on the stack often needs to be allocated
1253 // in order to store the value. In this case the CCInfo.getNextStackOffset()
1254 // != 0 check is not enough and we need to check if any CCValAssign ArgsLocs
1255 // are passed CCValAssign::Indirect.
1256 for (auto &VA : ArgLocs)
1257 if (VA.getLocInfo() == CCValAssign::Indirect)
1258 return false;
1259
1260 // Do not tail call opt if either caller or callee uses struct return
1261 // semantics.
1262 auto IsCallerStructRet = Caller.hasStructRetAttr();
1263 auto IsCalleeStructRet = Outs.empty() ? false : Outs[0].Flags.isSRet();
1264 if (IsCallerStructRet || IsCalleeStructRet)
1265 return false;
1266
1267 // Externally-defined functions with weak linkage should not be
1268 // tail-called. The behaviour of branch instructions in this situation (as
1269 // used for tail calls) is implementation-defined, so we cannot rely on the
1270 // linker replacing the tail call with a return.
1271 if (GlobalAddressSDNode *G = dyn_cast<GlobalAddressSDNode>(Callee)) {
1272 const GlobalValue *GV = G->getGlobal();
1273 if (GV->hasExternalWeakLinkage())
1274 return false;
1275 }
1276
1277 // The callee has to preserve all registers the caller needs to preserve.
1278 const RISCVRegisterInfo *TRI = Subtarget.getRegisterInfo();
1279 const uint32_t *CallerPreserved = TRI->getCallPreservedMask(MF, CallerCC);
1280 if (CalleeCC != CallerCC) {
1281 const uint32_t *CalleePreserved = TRI->getCallPreservedMask(MF, CalleeCC);
1282 if (!TRI->regmaskSubsetEqual(CallerPreserved, CalleePreserved))
1283 return false;
1284 }
1285
1286 // Byval parameters hand the function a pointer directly into the stack area
1287 // we want to reuse during a tail call. Working around this *is* possible
1288 // but less efficient and uglier in LowerCall.
1289 for (auto &Arg : Outs)
1290 if (Arg.Flags.isByVal())
1291 return false;
1292
1293 return true;
1294}
1295
Alex Bradburya3376752017-11-08 13:41:21 +00001296// Lower a call to a callseq_start + CALL + callseq_end chain, and add input
1297// and output parameter nodes.
1298SDValue RISCVTargetLowering::LowerCall(CallLoweringInfo &CLI,
1299 SmallVectorImpl<SDValue> &InVals) const {
1300 SelectionDAG &DAG = CLI.DAG;
1301 SDLoc &DL = CLI.DL;
1302 SmallVectorImpl<ISD::OutputArg> &Outs = CLI.Outs;
1303 SmallVectorImpl<SDValue> &OutVals = CLI.OutVals;
1304 SmallVectorImpl<ISD::InputArg> &Ins = CLI.Ins;
1305 SDValue Chain = CLI.Chain;
1306 SDValue Callee = CLI.Callee;
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001307 bool &IsTailCall = CLI.IsTailCall;
Alex Bradburya3376752017-11-08 13:41:21 +00001308 CallingConv::ID CallConv = CLI.CallConv;
1309 bool IsVarArg = CLI.IsVarArg;
1310 EVT PtrVT = getPointerTy(DAG.getDataLayout());
Alex Bradburydc31c612017-12-11 12:49:02 +00001311 MVT XLenVT = Subtarget.getXLenVT();
Alex Bradburya3376752017-11-08 13:41:21 +00001312
Alex Bradburya3376752017-11-08 13:41:21 +00001313 MachineFunction &MF = DAG.getMachineFunction();
1314
1315 // Analyze the operands of the call, assigning locations to each operand.
1316 SmallVector<CCValAssign, 16> ArgLocs;
1317 CCState ArgCCInfo(CallConv, IsVarArg, MF, ArgLocs, *DAG.getContext());
Alex Bradburyc85be0d2018-01-10 19:41:03 +00001318 analyzeOutputArgs(MF, ArgCCInfo, Outs, /*IsRet=*/false, &CLI);
Alex Bradburya3376752017-11-08 13:41:21 +00001319
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001320 // Check if it's really possible to do a tail call.
1321 if (IsTailCall)
1322 IsTailCall = IsEligibleForTailCallOptimization(ArgCCInfo, CLI, MF,
1323 ArgLocs);
1324
1325 if (IsTailCall)
1326 ++NumTailCalls;
1327 else if (CLI.CS && CLI.CS.isMustTailCall())
1328 report_fatal_error("failed to perform tail call elimination on a call "
1329 "site marked musttail");
1330
Alex Bradburya3376752017-11-08 13:41:21 +00001331 // Get a count of how many bytes are to be pushed on the stack.
1332 unsigned NumBytes = ArgCCInfo.getNextStackOffset();
1333
Alex Bradburydc31c612017-12-11 12:49:02 +00001334 // Create local copies for byval args
1335 SmallVector<SDValue, 8> ByValArgs;
1336 for (unsigned i = 0, e = Outs.size(); i != e; ++i) {
1337 ISD::ArgFlagsTy Flags = Outs[i].Flags;
1338 if (!Flags.isByVal())
Alex Bradburya3376752017-11-08 13:41:21 +00001339 continue;
Alex Bradburydc31c612017-12-11 12:49:02 +00001340
1341 SDValue Arg = OutVals[i];
1342 unsigned Size = Flags.getByValSize();
1343 unsigned Align = Flags.getByValAlign();
1344
1345 int FI = MF.getFrameInfo().CreateStackObject(Size, Align, /*isSS=*/false);
1346 SDValue FIPtr = DAG.getFrameIndex(FI, getPointerTy(DAG.getDataLayout()));
1347 SDValue SizeNode = DAG.getConstant(Size, DL, XLenVT);
1348
1349 Chain = DAG.getMemcpy(Chain, DL, FIPtr, Arg, SizeNode, Align,
1350 /*IsVolatile=*/false,
1351 /*AlwaysInline=*/false,
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001352 IsTailCall, MachinePointerInfo(),
Alex Bradburydc31c612017-12-11 12:49:02 +00001353 MachinePointerInfo());
1354 ByValArgs.push_back(FIPtr);
Alex Bradburya3376752017-11-08 13:41:21 +00001355 }
1356
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001357 if (!IsTailCall)
1358 Chain = DAG.getCALLSEQ_START(Chain, NumBytes, 0, CLI.DL);
Alex Bradburya3376752017-11-08 13:41:21 +00001359
1360 // Copy argument values to their designated locations.
1361 SmallVector<std::pair<unsigned, SDValue>, 8> RegsToPass;
Alex Bradburydc31c612017-12-11 12:49:02 +00001362 SmallVector<SDValue, 8> MemOpChains;
Alex Bradburya3376752017-11-08 13:41:21 +00001363 SDValue StackPtr;
Alex Bradburydc31c612017-12-11 12:49:02 +00001364 for (unsigned i = 0, j = 0, e = ArgLocs.size(); i != e; ++i) {
1365 CCValAssign &VA = ArgLocs[i];
1366 SDValue ArgValue = OutVals[i];
1367 ISD::ArgFlagsTy Flags = Outs[i].Flags;
Alex Bradburya3376752017-11-08 13:41:21 +00001368
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001369 // Handle passing f64 on RV32D with a soft float ABI as a special case.
1370 bool IsF64OnRV32DSoftABI =
1371 VA.getLocVT() == MVT::i32 && VA.getValVT() == MVT::f64;
1372 if (IsF64OnRV32DSoftABI && VA.isRegLoc()) {
1373 SDValue SplitF64 = DAG.getNode(
1374 RISCVISD::SplitF64, DL, DAG.getVTList(MVT::i32, MVT::i32), ArgValue);
1375 SDValue Lo = SplitF64.getValue(0);
1376 SDValue Hi = SplitF64.getValue(1);
1377
1378 unsigned RegLo = VA.getLocReg();
1379 RegsToPass.push_back(std::make_pair(RegLo, Lo));
1380
1381 if (RegLo == RISCV::X17) {
1382 // Second half of f64 is passed on the stack.
1383 // Work out the address of the stack slot.
1384 if (!StackPtr.getNode())
1385 StackPtr = DAG.getCopyFromReg(Chain, DL, RISCV::X2, PtrVT);
1386 // Emit the store.
1387 MemOpChains.push_back(
1388 DAG.getStore(Chain, DL, Hi, StackPtr, MachinePointerInfo()));
1389 } else {
1390 // Second half of f64 is passed in another GPR.
1391 unsigned RegHigh = RegLo + 1;
1392 RegsToPass.push_back(std::make_pair(RegHigh, Hi));
1393 }
1394 continue;
1395 }
1396
1397 // IsF64OnRV32DSoftABI && VA.isMemLoc() is handled below in the same way
1398 // as any other MemLoc.
1399
Alex Bradburya3376752017-11-08 13:41:21 +00001400 // Promote the value if needed.
Alex Bradburydc31c612017-12-11 12:49:02 +00001401 // For now, only handle fully promoted and indirect arguments.
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +00001402 if (VA.getLocInfo() == CCValAssign::Indirect) {
Alex Bradburydc31c612017-12-11 12:49:02 +00001403 // Store the argument in a stack slot and pass its address.
1404 SDValue SpillSlot = DAG.CreateStackTemporary(Outs[i].ArgVT);
1405 int FI = cast<FrameIndexSDNode>(SpillSlot)->getIndex();
1406 MemOpChains.push_back(
1407 DAG.getStore(Chain, DL, ArgValue, SpillSlot,
1408 MachinePointerInfo::getFixedStack(MF, FI)));
1409 // If the original argument was split (e.g. i128), we need
1410 // to store all parts of it here (and pass just one address).
1411 unsigned ArgIndex = Outs[i].OrigArgIndex;
1412 assert(Outs[i].PartOffset == 0);
1413 while (i + 1 != e && Outs[i + 1].OrigArgIndex == ArgIndex) {
1414 SDValue PartValue = OutVals[i + 1];
1415 unsigned PartOffset = Outs[i + 1].PartOffset;
1416 SDValue Address = DAG.getNode(ISD::ADD, DL, PtrVT, SpillSlot,
1417 DAG.getIntPtrConstant(PartOffset, DL));
1418 MemOpChains.push_back(
1419 DAG.getStore(Chain, DL, PartValue, Address,
1420 MachinePointerInfo::getFixedStack(MF, FI)));
1421 ++i;
1422 }
1423 ArgValue = SpillSlot;
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +00001424 } else {
1425 ArgValue = convertValVTToLocVT(DAG, ArgValue, VA, DL);
Alex Bradburya3376752017-11-08 13:41:21 +00001426 }
1427
Alex Bradburydc31c612017-12-11 12:49:02 +00001428 // Use local copy if it is a byval arg.
1429 if (Flags.isByVal())
1430 ArgValue = ByValArgs[j++];
1431
Alex Bradburya3376752017-11-08 13:41:21 +00001432 if (VA.isRegLoc()) {
1433 // Queue up the argument copies and emit them at the end.
1434 RegsToPass.push_back(std::make_pair(VA.getLocReg(), ArgValue));
1435 } else {
1436 assert(VA.isMemLoc() && "Argument not register or memory");
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001437 assert(!IsTailCall && "Tail call not allowed if stack is used "
1438 "for passing parameters");
Alex Bradburydc31c612017-12-11 12:49:02 +00001439
1440 // Work out the address of the stack slot.
1441 if (!StackPtr.getNode())
1442 StackPtr = DAG.getCopyFromReg(Chain, DL, RISCV::X2, PtrVT);
1443 SDValue Address =
1444 DAG.getNode(ISD::ADD, DL, PtrVT, StackPtr,
1445 DAG.getIntPtrConstant(VA.getLocMemOffset(), DL));
1446
1447 // Emit the store.
1448 MemOpChains.push_back(
1449 DAG.getStore(Chain, DL, ArgValue, Address, MachinePointerInfo()));
Alex Bradburya3376752017-11-08 13:41:21 +00001450 }
1451 }
1452
Alex Bradburydc31c612017-12-11 12:49:02 +00001453 // Join the stores, which are independent of one another.
1454 if (!MemOpChains.empty())
1455 Chain = DAG.getNode(ISD::TokenFactor, DL, MVT::Other, MemOpChains);
1456
Alex Bradburya3376752017-11-08 13:41:21 +00001457 SDValue Glue;
1458
1459 // Build a sequence of copy-to-reg nodes, chained and glued together.
1460 for (auto &Reg : RegsToPass) {
1461 Chain = DAG.getCopyToReg(Chain, DL, Reg.first, Reg.second, Glue);
1462 Glue = Chain.getValue(1);
1463 }
1464
Shiva Chend58bd8d2018-04-25 14:19:12 +00001465 // If the callee is a GlobalAddress/ExternalSymbol node, turn it into a
1466 // TargetGlobalAddress/TargetExternalSymbol node so that legalize won't
1467 // split it and then direct call can be matched by PseudoCALL.
1468 if (GlobalAddressSDNode *S = dyn_cast<GlobalAddressSDNode>(Callee)) {
1469 Callee = DAG.getTargetGlobalAddress(S->getGlobal(), DL, PtrVT, 0, 0);
1470 } else if (ExternalSymbolSDNode *S = dyn_cast<ExternalSymbolSDNode>(Callee)) {
1471 Callee = DAG.getTargetExternalSymbol(S->getSymbol(), PtrVT, 0);
Alex Bradburya3376752017-11-08 13:41:21 +00001472 }
1473
1474 // The first call operand is the chain and the second is the target address.
1475 SmallVector<SDValue, 8> Ops;
1476 Ops.push_back(Chain);
1477 Ops.push_back(Callee);
1478
1479 // Add argument registers to the end of the list so that they are
1480 // known live into the call.
1481 for (auto &Reg : RegsToPass)
1482 Ops.push_back(DAG.getRegister(Reg.first, Reg.second.getValueType()));
1483
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001484 if (!IsTailCall) {
1485 // Add a register mask operand representing the call-preserved registers.
1486 const TargetRegisterInfo *TRI = Subtarget.getRegisterInfo();
1487 const uint32_t *Mask = TRI->getCallPreservedMask(MF, CallConv);
1488 assert(Mask && "Missing call preserved mask for calling convention");
1489 Ops.push_back(DAG.getRegisterMask(Mask));
1490 }
Alex Bradburya3376752017-11-08 13:41:21 +00001491
1492 // Glue the call to the argument copies, if any.
1493 if (Glue.getNode())
1494 Ops.push_back(Glue);
1495
1496 // Emit the call.
1497 SDVTList NodeTys = DAG.getVTList(MVT::Other, MVT::Glue);
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001498
1499 if (IsTailCall) {
1500 MF.getFrameInfo().setHasTailCall();
1501 return DAG.getNode(RISCVISD::TAIL, DL, NodeTys, Ops);
1502 }
1503
Alex Bradburya3376752017-11-08 13:41:21 +00001504 Chain = DAG.getNode(RISCVISD::CALL, DL, NodeTys, Ops);
1505 Glue = Chain.getValue(1);
1506
1507 // Mark the end of the call, which is glued to the call itself.
1508 Chain = DAG.getCALLSEQ_END(Chain,
1509 DAG.getConstant(NumBytes, DL, PtrVT, true),
1510 DAG.getConstant(0, DL, PtrVT, true),
1511 Glue, DL);
1512 Glue = Chain.getValue(1);
1513
1514 // Assign locations to each value returned by this call.
1515 SmallVector<CCValAssign, 16> RVLocs;
1516 CCState RetCCInfo(CallConv, IsVarArg, MF, RVLocs, *DAG.getContext());
Alex Bradburydc31c612017-12-11 12:49:02 +00001517 analyzeInputArgs(MF, RetCCInfo, Ins, /*IsRet=*/true);
Alex Bradburya3376752017-11-08 13:41:21 +00001518
1519 // Copy all of the result registers out of their specified physreg.
1520 for (auto &VA : RVLocs) {
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001521 // Copy the value out
1522 SDValue RetValue =
1523 DAG.getCopyFromReg(Chain, DL, VA.getLocReg(), VA.getLocVT(), Glue);
1524 // Glue the RetValue to the end of the call sequence
Alex Bradburya3376752017-11-08 13:41:21 +00001525 Chain = RetValue.getValue(1);
1526 Glue = RetValue.getValue(2);
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +00001527
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001528 if (VA.getLocVT() == MVT::i32 && VA.getValVT() == MVT::f64) {
1529 assert(VA.getLocReg() == ArgGPRs[0] && "Unexpected reg assignment");
1530 SDValue RetValue2 =
1531 DAG.getCopyFromReg(Chain, DL, ArgGPRs[1], MVT::i32, Glue);
1532 Chain = RetValue2.getValue(1);
1533 Glue = RetValue2.getValue(2);
1534 RetValue = DAG.getNode(RISCVISD::BuildPairF64, DL, MVT::f64, RetValue,
1535 RetValue2);
1536 }
Alex Bradburya3376752017-11-08 13:41:21 +00001537
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +00001538 RetValue = convertLocVTToValVT(DAG, RetValue, VA, DL);
Alex Bradbury76c29ee2018-03-20 12:45:35 +00001539
Alex Bradburydc31c612017-12-11 12:49:02 +00001540 InVals.push_back(RetValue);
Alex Bradburya3376752017-11-08 13:41:21 +00001541 }
1542
1543 return Chain;
1544}
1545
Alex Bradburydc31c612017-12-11 12:49:02 +00001546bool RISCVTargetLowering::CanLowerReturn(
1547 CallingConv::ID CallConv, MachineFunction &MF, bool IsVarArg,
1548 const SmallVectorImpl<ISD::OutputArg> &Outs, LLVMContext &Context) const {
1549 SmallVector<CCValAssign, 16> RVLocs;
1550 CCState CCInfo(CallConv, IsVarArg, MF, RVLocs, Context);
1551 for (unsigned i = 0, e = Outs.size(); i != e; ++i) {
1552 MVT VT = Outs[i].VT;
1553 ISD::ArgFlagsTy ArgFlags = Outs[i].Flags;
1554 if (CC_RISCV(MF.getDataLayout(), i, VT, VT, CCValAssign::Full, ArgFlags,
Alex Bradburyc85be0d2018-01-10 19:41:03 +00001555 CCInfo, /*IsFixed=*/true, /*IsRet=*/true, nullptr))
Alex Bradburydc31c612017-12-11 12:49:02 +00001556 return false;
1557 }
1558 return true;
1559}
1560
Alex Bradbury89718422017-10-19 21:37:38 +00001561SDValue
1562RISCVTargetLowering::LowerReturn(SDValue Chain, CallingConv::ID CallConv,
1563 bool IsVarArg,
1564 const SmallVectorImpl<ISD::OutputArg> &Outs,
1565 const SmallVectorImpl<SDValue> &OutVals,
1566 const SDLoc &DL, SelectionDAG &DAG) const {
Alex Bradbury89718422017-10-19 21:37:38 +00001567 // Stores the assignment of the return value to a location.
1568 SmallVector<CCValAssign, 16> RVLocs;
1569
1570 // Info about the registers and stack slot.
1571 CCState CCInfo(CallConv, IsVarArg, DAG.getMachineFunction(), RVLocs,
1572 *DAG.getContext());
1573
Alex Bradburyc85be0d2018-01-10 19:41:03 +00001574 analyzeOutputArgs(DAG.getMachineFunction(), CCInfo, Outs, /*IsRet=*/true,
1575 nullptr);
Alex Bradbury89718422017-10-19 21:37:38 +00001576
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001577 SDValue Glue;
Alex Bradbury89718422017-10-19 21:37:38 +00001578 SmallVector<SDValue, 4> RetOps(1, Chain);
1579
1580 // Copy the result values into the output registers.
1581 for (unsigned i = 0, e = RVLocs.size(); i < e; ++i) {
Alex Bradburydc31c612017-12-11 12:49:02 +00001582 SDValue Val = OutVals[i];
Alex Bradbury89718422017-10-19 21:37:38 +00001583 CCValAssign &VA = RVLocs[i];
1584 assert(VA.isRegLoc() && "Can only return in registers!");
1585
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001586 if (VA.getLocVT() == MVT::i32 && VA.getValVT() == MVT::f64) {
1587 // Handle returning f64 on RV32D with a soft float ABI.
1588 assert(VA.isRegLoc() && "Expected return via registers");
1589 SDValue SplitF64 = DAG.getNode(RISCVISD::SplitF64, DL,
1590 DAG.getVTList(MVT::i32, MVT::i32), Val);
1591 SDValue Lo = SplitF64.getValue(0);
1592 SDValue Hi = SplitF64.getValue(1);
1593 unsigned RegLo = VA.getLocReg();
1594 unsigned RegHi = RegLo + 1;
1595 Chain = DAG.getCopyToReg(Chain, DL, RegLo, Lo, Glue);
1596 Glue = Chain.getValue(1);
1597 RetOps.push_back(DAG.getRegister(RegLo, MVT::i32));
1598 Chain = DAG.getCopyToReg(Chain, DL, RegHi, Hi, Glue);
1599 Glue = Chain.getValue(1);
1600 RetOps.push_back(DAG.getRegister(RegHi, MVT::i32));
1601 } else {
1602 // Handle a 'normal' return.
Alex Bradbury1dbfdeb2018-10-03 22:53:25 +00001603 Val = convertValVTToLocVT(DAG, Val, VA, DL);
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001604 Chain = DAG.getCopyToReg(Chain, DL, VA.getLocReg(), Val, Glue);
Alex Bradbury89718422017-10-19 21:37:38 +00001605
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001606 // Guarantee that all emitted copies are stuck together.
1607 Glue = Chain.getValue(1);
1608 RetOps.push_back(DAG.getRegister(VA.getLocReg(), VA.getLocVT()));
1609 }
Alex Bradbury89718422017-10-19 21:37:38 +00001610 }
1611
1612 RetOps[0] = Chain; // Update chain.
1613
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001614 // Add the glue node if we have it.
1615 if (Glue.getNode()) {
1616 RetOps.push_back(Glue);
Alex Bradbury89718422017-10-19 21:37:38 +00001617 }
1618
Ana Pazos2e4106b2018-07-26 17:49:43 +00001619 // Interrupt service routines use different return instructions.
1620 const Function &Func = DAG.getMachineFunction().getFunction();
1621 if (Func.hasFnAttribute("interrupt")) {
1622 if (!Func.getReturnType()->isVoidTy())
1623 report_fatal_error(
1624 "Functions with the interrupt attribute must have void return type!");
1625
1626 MachineFunction &MF = DAG.getMachineFunction();
1627 StringRef Kind =
1628 MF.getFunction().getFnAttribute("interrupt").getValueAsString();
1629
1630 unsigned RetOpc;
1631 if (Kind == "user")
1632 RetOpc = RISCVISD::URET_FLAG;
1633 else if (Kind == "supervisor")
1634 RetOpc = RISCVISD::SRET_FLAG;
1635 else
1636 RetOpc = RISCVISD::MRET_FLAG;
1637
1638 return DAG.getNode(RetOpc, DL, MVT::Other, RetOps);
1639 }
1640
Alex Bradbury89718422017-10-19 21:37:38 +00001641 return DAG.getNode(RISCVISD::RET_FLAG, DL, MVT::Other, RetOps);
1642}
1643
1644const char *RISCVTargetLowering::getTargetNodeName(unsigned Opcode) const {
1645 switch ((RISCVISD::NodeType)Opcode) {
1646 case RISCVISD::FIRST_NUMBER:
1647 break;
1648 case RISCVISD::RET_FLAG:
1649 return "RISCVISD::RET_FLAG";
Ana Pazos2e4106b2018-07-26 17:49:43 +00001650 case RISCVISD::URET_FLAG:
1651 return "RISCVISD::URET_FLAG";
1652 case RISCVISD::SRET_FLAG:
1653 return "RISCVISD::SRET_FLAG";
1654 case RISCVISD::MRET_FLAG:
1655 return "RISCVISD::MRET_FLAG";
Alex Bradburya3376752017-11-08 13:41:21 +00001656 case RISCVISD::CALL:
1657 return "RISCVISD::CALL";
Alex Bradbury65385162017-11-21 07:51:32 +00001658 case RISCVISD::SELECT_CC:
1659 return "RISCVISD::SELECT_CC";
Alex Bradbury0b4175f2018-04-12 05:34:25 +00001660 case RISCVISD::BuildPairF64:
1661 return "RISCVISD::BuildPairF64";
1662 case RISCVISD::SplitF64:
1663 return "RISCVISD::SplitF64";
Mandeep Singh Grangddcb9562018-05-23 22:44:08 +00001664 case RISCVISD::TAIL:
1665 return "RISCVISD::TAIL";
Alex Bradbury89718422017-10-19 21:37:38 +00001666 }
1667 return nullptr;
1668}
Alex Bradbury9330e642018-01-10 20:05:09 +00001669
1670std::pair<unsigned, const TargetRegisterClass *>
1671RISCVTargetLowering::getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,
1672 StringRef Constraint,
1673 MVT VT) const {
1674 // First, see if this is a constraint that directly corresponds to a
1675 // RISCV register class.
1676 if (Constraint.size() == 1) {
1677 switch (Constraint[0]) {
1678 case 'r':
1679 return std::make_pair(0U, &RISCV::GPRRegClass);
1680 default:
1681 break;
1682 }
1683 }
1684
1685 return TargetLowering::getRegForInlineAsmConstraint(TRI, Constraint, VT);
1686}
Alex Bradbury96f492d2018-06-13 12:04:51 +00001687
1688Instruction *RISCVTargetLowering::emitLeadingFence(IRBuilder<> &Builder,
1689 Instruction *Inst,
1690 AtomicOrdering Ord) const {
1691 if (isa<LoadInst>(Inst) && Ord == AtomicOrdering::SequentiallyConsistent)
1692 return Builder.CreateFence(Ord);
1693 if (isa<StoreInst>(Inst) && isReleaseOrStronger(Ord))
1694 return Builder.CreateFence(AtomicOrdering::Release);
1695 return nullptr;
1696}
1697
1698Instruction *RISCVTargetLowering::emitTrailingFence(IRBuilder<> &Builder,
1699 Instruction *Inst,
1700 AtomicOrdering Ord) const {
1701 if (isa<LoadInst>(Inst) && isAcquireOrStronger(Ord))
1702 return Builder.CreateFence(AtomicOrdering::Acquire);
1703 return nullptr;
1704}
Alex Bradbury21aea512018-09-19 10:54:22 +00001705
1706TargetLowering::AtomicExpansionKind
1707RISCVTargetLowering::shouldExpandAtomicRMWInIR(AtomicRMWInst *AI) const {
1708 unsigned Size = AI->getType()->getPrimitiveSizeInBits();
1709 if (Size == 8 || Size == 16)
1710 return AtomicExpansionKind::MaskedIntrinsic;
1711 return AtomicExpansionKind::None;
1712}
1713
1714static Intrinsic::ID
1715getIntrinsicForMaskedAtomicRMWBinOp32(AtomicRMWInst::BinOp BinOp) {
1716 switch (BinOp) {
1717 default:
1718 llvm_unreachable("Unexpected AtomicRMW BinOp");
1719 case AtomicRMWInst::Xchg:
1720 return Intrinsic::riscv_masked_atomicrmw_xchg_i32;
1721 case AtomicRMWInst::Add:
1722 return Intrinsic::riscv_masked_atomicrmw_add_i32;
1723 case AtomicRMWInst::Sub:
1724 return Intrinsic::riscv_masked_atomicrmw_sub_i32;
1725 case AtomicRMWInst::Nand:
1726 return Intrinsic::riscv_masked_atomicrmw_nand_i32;
1727 case AtomicRMWInst::Max:
1728 return Intrinsic::riscv_masked_atomicrmw_max_i32;
1729 case AtomicRMWInst::Min:
1730 return Intrinsic::riscv_masked_atomicrmw_min_i32;
1731 case AtomicRMWInst::UMax:
1732 return Intrinsic::riscv_masked_atomicrmw_umax_i32;
1733 case AtomicRMWInst::UMin:
1734 return Intrinsic::riscv_masked_atomicrmw_umin_i32;
1735 }
1736}
1737
1738Value *RISCVTargetLowering::emitMaskedAtomicRMWIntrinsic(
1739 IRBuilder<> &Builder, AtomicRMWInst *AI, Value *AlignedAddr, Value *Incr,
1740 Value *Mask, Value *ShiftAmt, AtomicOrdering Ord) const {
1741 Value *Ordering = Builder.getInt32(static_cast<uint32_t>(AI->getOrdering()));
1742 Type *Tys[] = {AlignedAddr->getType()};
1743 Function *LrwOpScwLoop = Intrinsic::getDeclaration(
1744 AI->getModule(),
1745 getIntrinsicForMaskedAtomicRMWBinOp32(AI->getOperation()), Tys);
1746
1747 // Must pass the shift amount needed to sign extend the loaded value prior
1748 // to performing a signed comparison for min/max. ShiftAmt is the number of
1749 // bits to shift the value into position. Pass XLen-ShiftAmt-ValWidth, which
1750 // is the number of bits to left+right shift the value in order to
1751 // sign-extend.
1752 if (AI->getOperation() == AtomicRMWInst::Min ||
1753 AI->getOperation() == AtomicRMWInst::Max) {
1754 const DataLayout &DL = AI->getModule()->getDataLayout();
1755 unsigned ValWidth =
1756 DL.getTypeStoreSizeInBits(AI->getValOperand()->getType());
1757 Value *SextShamt = Builder.CreateSub(
1758 Builder.getInt32(Subtarget.getXLen() - ValWidth), ShiftAmt);
1759 return Builder.CreateCall(LrwOpScwLoop,
1760 {AlignedAddr, Incr, Mask, SextShamt, Ordering});
1761 }
1762
1763 return Builder.CreateCall(LrwOpScwLoop, {AlignedAddr, Incr, Mask, Ordering});
1764}
Alex Bradbury66d9a752018-11-29 20:43:42 +00001765
1766TargetLowering::AtomicExpansionKind
1767RISCVTargetLowering::shouldExpandAtomicCmpXchgInIR(
1768 AtomicCmpXchgInst *CI) const {
1769 unsigned Size = CI->getCompareOperand()->getType()->getPrimitiveSizeInBits();
1770 if (Size == 8 || Size == 16)
1771 return AtomicExpansionKind::MaskedIntrinsic;
1772 return AtomicExpansionKind::None;
1773}
1774
1775Value *RISCVTargetLowering::emitMaskedAtomicCmpXchgIntrinsic(
1776 IRBuilder<> &Builder, AtomicCmpXchgInst *CI, Value *AlignedAddr,
1777 Value *CmpVal, Value *NewVal, Value *Mask, AtomicOrdering Ord) const {
1778 Value *Ordering = Builder.getInt32(static_cast<uint32_t>(Ord));
1779 Type *Tys[] = {AlignedAddr->getType()};
1780 Function *MaskedCmpXchg = Intrinsic::getDeclaration(
1781 CI->getModule(), Intrinsic::riscv_masked_cmpxchg_i32, Tys);
1782 return Builder.CreateCall(MaskedCmpXchg,
1783 {AlignedAddr, CmpVal, NewVal, Mask, Ordering});
1784}