[mips] Reapply r179420 and r179421.
[oota-llvm.git] / lib / Target / Mips / MipsSEISelLowering.cpp
1 //===-- MipsSEISelLowering.cpp - MipsSE DAG Lowering Interface --*- C++ -*-===//
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 // Subclass of MipsTargetLowering specialized for mips32/64.
11 //
12 //===----------------------------------------------------------------------===//
13 #include "MipsSEISelLowering.h"
14 #include "MipsRegisterInfo.h"
15 #include "MipsTargetMachine.h"
16 #include "llvm/CodeGen/MachineInstrBuilder.h"
17 #include "llvm/CodeGen/MachineRegisterInfo.h"
18 #include "llvm/Support/CommandLine.h"
19 #include "llvm/Target/TargetInstrInfo.h"
20
21 using namespace llvm;
22
23 static cl::opt<bool>
24 EnableMipsTailCalls("enable-mips-tail-calls", cl::Hidden,
25                     cl::desc("MIPS: Enable tail calls."), cl::init(false));
26
27 MipsSETargetLowering::MipsSETargetLowering(MipsTargetMachine &TM)
28   : MipsTargetLowering(TM) {
29   // Set up the register classes
30
31   clearRegisterClasses();
32
33   addRegisterClass(MVT::i32, &Mips::CPURegsRegClass);
34
35   if (HasMips64)
36     addRegisterClass(MVT::i64, &Mips::CPU64RegsRegClass);
37
38   if (Subtarget->hasDSP()) {
39     MVT::SimpleValueType VecTys[2] = {MVT::v2i16, MVT::v4i8};
40
41     for (unsigned i = 0; i < array_lengthof(VecTys); ++i) {
42       addRegisterClass(VecTys[i], &Mips::DSPRegsRegClass);
43
44       // Expand all builtin opcodes.
45       for (unsigned Opc = 0; Opc < ISD::BUILTIN_OP_END; ++Opc)
46         setOperationAction(Opc, VecTys[i], Expand);
47
48       setOperationAction(ISD::ADD, VecTys[i], Legal);
49       setOperationAction(ISD::SUB, VecTys[i], Legal);
50       setOperationAction(ISD::LOAD, VecTys[i], Legal);
51       setOperationAction(ISD::STORE, VecTys[i], Legal);
52       setOperationAction(ISD::BITCAST, VecTys[i], Legal);
53     }
54   }
55
56   if (Subtarget->hasDSPR2())
57     setOperationAction(ISD::MUL, MVT::v2i16, Legal);
58
59   if (!TM.Options.UseSoftFloat) {
60     addRegisterClass(MVT::f32, &Mips::FGR32RegClass);
61
62     // When dealing with single precision only, use libcalls
63     if (!Subtarget->isSingleFloat()) {
64       if (HasMips64)
65         addRegisterClass(MVT::f64, &Mips::FGR64RegClass);
66       else
67         addRegisterClass(MVT::f64, &Mips::AFGR64RegClass);
68     }
69   }
70
71   setOperationAction(ISD::SMUL_LOHI,          MVT::i32, Custom);
72   setOperationAction(ISD::UMUL_LOHI,          MVT::i32, Custom);
73   setOperationAction(ISD::MULHS,              MVT::i32, Custom);
74   setOperationAction(ISD::MULHU,              MVT::i32, Custom);
75
76   if (HasMips64) {
77     setOperationAction(ISD::MULHS,            MVT::i64, Custom);
78     setOperationAction(ISD::MULHU,            MVT::i64, Custom);
79     setOperationAction(ISD::MUL,              MVT::i64, Custom);
80   }
81
82   setOperationAction(ISD::SDIVREM, MVT::i32, Custom);
83   setOperationAction(ISD::UDIVREM, MVT::i32, Custom);
84   setOperationAction(ISD::SDIVREM, MVT::i64, Custom);
85   setOperationAction(ISD::UDIVREM, MVT::i64, Custom);
86   setOperationAction(ISD::MEMBARRIER,         MVT::Other, Custom);
87   setOperationAction(ISD::ATOMIC_FENCE,       MVT::Other, Custom);
88   setOperationAction(ISD::LOAD,               MVT::i32, Custom);
89   setOperationAction(ISD::STORE,              MVT::i32, Custom);
90
91   setTargetDAGCombine(ISD::ADDE);
92   setTargetDAGCombine(ISD::SUBE);
93
94   computeRegisterProperties();
95 }
96
97 const MipsTargetLowering *
98 llvm::createMipsSETargetLowering(MipsTargetMachine &TM) {
99   return new MipsSETargetLowering(TM);
100 }
101
102
103 bool
104 MipsSETargetLowering::allowsUnalignedMemoryAccesses(EVT VT, bool *Fast) const {
105   MVT::SimpleValueType SVT = VT.getSimpleVT().SimpleTy;
106
107   switch (SVT) {
108   case MVT::i64:
109   case MVT::i32:
110     if (Fast)
111       *Fast = true;
112     return true;
113   default:
114     return false;
115   }
116 }
117
118 SDValue MipsSETargetLowering::LowerOperation(SDValue Op,
119                                              SelectionDAG &DAG) const {
120   switch(Op.getOpcode()) {
121   case ISD::SMUL_LOHI: return lowerMulDiv(Op, MipsISD::Mult, true, true, DAG);
122   case ISD::UMUL_LOHI: return lowerMulDiv(Op, MipsISD::Multu, true, true, DAG);
123   case ISD::MULHS:     return lowerMulDiv(Op, MipsISD::Mult, false, true, DAG);
124   case ISD::MULHU:     return lowerMulDiv(Op, MipsISD::Multu, false, true, DAG);
125   case ISD::MUL:       return lowerMulDiv(Op, MipsISD::Mult, true, false, DAG);
126   case ISD::SDIVREM:   return lowerMulDiv(Op, MipsISD::DivRem, true, true, DAG);
127   case ISD::UDIVREM:   return lowerMulDiv(Op, MipsISD::DivRemU, true, true, DAG);
128   }
129
130   return MipsTargetLowering::LowerOperation(Op, DAG);
131 }
132
133 // selectMADD -
134 // Transforms a subgraph in CurDAG if the following pattern is found:
135 //  (addc multLo, Lo0), (adde multHi, Hi0),
136 // where,
137 //  multHi/Lo: product of multiplication
138 //  Lo0: initial value of Lo register
139 //  Hi0: initial value of Hi register
140 // Return true if pattern matching was successful.
141 static bool selectMADD(SDNode *ADDENode, SelectionDAG *CurDAG) {
142   // ADDENode's second operand must be a flag output of an ADDC node in order
143   // for the matching to be successful.
144   SDNode *ADDCNode = ADDENode->getOperand(2).getNode();
145
146   if (ADDCNode->getOpcode() != ISD::ADDC)
147     return false;
148
149   SDValue MultHi = ADDENode->getOperand(0);
150   SDValue MultLo = ADDCNode->getOperand(0);
151   SDNode *MultNode = MultHi.getNode();
152   unsigned MultOpc = MultHi.getOpcode();
153
154   // MultHi and MultLo must be generated by the same node,
155   if (MultLo.getNode() != MultNode)
156     return false;
157
158   // and it must be a multiplication.
159   if (MultOpc != ISD::SMUL_LOHI && MultOpc != ISD::UMUL_LOHI)
160     return false;
161
162   // MultLo amd MultHi must be the first and second output of MultNode
163   // respectively.
164   if (MultHi.getResNo() != 1 || MultLo.getResNo() != 0)
165     return false;
166
167   // Transform this to a MADD only if ADDENode and ADDCNode are the only users
168   // of the values of MultNode, in which case MultNode will be removed in later
169   // phases.
170   // If there exist users other than ADDENode or ADDCNode, this function returns
171   // here, which will result in MultNode being mapped to a single MULT
172   // instruction node rather than a pair of MULT and MADD instructions being
173   // produced.
174   if (!MultHi.hasOneUse() || !MultLo.hasOneUse())
175     return false;
176
177   DebugLoc DL = ADDENode->getDebugLoc();
178
179   // Initialize accumulator.
180   SDValue ACCIn = CurDAG->getNode(MipsISD::InsertLOHI, DL, MVT::Untyped,
181                                   ADDCNode->getOperand(1),
182                                   ADDENode->getOperand(1));
183
184   // create MipsMAdd(u) node
185   MultOpc = MultOpc == ISD::UMUL_LOHI ? MipsISD::MAddu : MipsISD::MAdd;
186
187   SDValue MAdd = CurDAG->getNode(MultOpc, DL, MVT::Untyped,
188                                  MultNode->getOperand(0),// Factor 0
189                                  MultNode->getOperand(1),// Factor 1
190                                  ACCIn);
191
192   // replace uses of adde and addc here
193   if (!SDValue(ADDCNode, 0).use_empty()) {
194     SDValue LoIdx = CurDAG->getConstant(Mips::sub_lo, MVT::i32);
195     SDValue LoOut = CurDAG->getNode(MipsISD::ExtractLOHI, DL, MVT::i32, MAdd,
196                                     LoIdx);
197     CurDAG->ReplaceAllUsesOfValueWith(SDValue(ADDCNode, 0), LoOut);
198   }
199   if (!SDValue(ADDENode, 0).use_empty()) {
200     SDValue HiIdx = CurDAG->getConstant(Mips::sub_hi, MVT::i32);
201     SDValue HiOut = CurDAG->getNode(MipsISD::ExtractLOHI, DL, MVT::i32, MAdd,
202                                     HiIdx);
203     CurDAG->ReplaceAllUsesOfValueWith(SDValue(ADDENode, 0), HiOut);
204   }
205
206   return true;
207 }
208
209 // selectMSUB -
210 // Transforms a subgraph in CurDAG if the following pattern is found:
211 //  (addc Lo0, multLo), (sube Hi0, multHi),
212 // where,
213 //  multHi/Lo: product of multiplication
214 //  Lo0: initial value of Lo register
215 //  Hi0: initial value of Hi register
216 // Return true if pattern matching was successful.
217 static bool selectMSUB(SDNode *SUBENode, SelectionDAG *CurDAG) {
218   // SUBENode's second operand must be a flag output of an SUBC node in order
219   // for the matching to be successful.
220   SDNode *SUBCNode = SUBENode->getOperand(2).getNode();
221
222   if (SUBCNode->getOpcode() != ISD::SUBC)
223     return false;
224
225   SDValue MultHi = SUBENode->getOperand(1);
226   SDValue MultLo = SUBCNode->getOperand(1);
227   SDNode *MultNode = MultHi.getNode();
228   unsigned MultOpc = MultHi.getOpcode();
229
230   // MultHi and MultLo must be generated by the same node,
231   if (MultLo.getNode() != MultNode)
232     return false;
233
234   // and it must be a multiplication.
235   if (MultOpc != ISD::SMUL_LOHI && MultOpc != ISD::UMUL_LOHI)
236     return false;
237
238   // MultLo amd MultHi must be the first and second output of MultNode
239   // respectively.
240   if (MultHi.getResNo() != 1 || MultLo.getResNo() != 0)
241     return false;
242
243   // Transform this to a MSUB only if SUBENode and SUBCNode are the only users
244   // of the values of MultNode, in which case MultNode will be removed in later
245   // phases.
246   // If there exist users other than SUBENode or SUBCNode, this function returns
247   // here, which will result in MultNode being mapped to a single MULT
248   // instruction node rather than a pair of MULT and MSUB instructions being
249   // produced.
250   if (!MultHi.hasOneUse() || !MultLo.hasOneUse())
251     return false;
252
253   DebugLoc DL = SUBENode->getDebugLoc();
254
255   // Initialize accumulator.
256   SDValue ACCIn = CurDAG->getNode(MipsISD::InsertLOHI, DL, MVT::Untyped,
257                                   SUBCNode->getOperand(0),
258                                   SUBENode->getOperand(0));
259
260   // create MipsSub(u) node
261   MultOpc = MultOpc == ISD::UMUL_LOHI ? MipsISD::MSubu : MipsISD::MSub;
262
263   SDValue MSub = CurDAG->getNode(MultOpc, DL, MVT::Glue,
264                                  MultNode->getOperand(0),// Factor 0
265                                  MultNode->getOperand(1),// Factor 1
266                                  ACCIn);
267
268   // replace uses of sube and subc here
269   if (!SDValue(SUBCNode, 0).use_empty()) {
270     SDValue LoIdx = CurDAG->getConstant(Mips::sub_lo, MVT::i32);
271     SDValue LoOut = CurDAG->getNode(MipsISD::ExtractLOHI, DL, MVT::i32, MSub,
272                                     LoIdx);
273     CurDAG->ReplaceAllUsesOfValueWith(SDValue(SUBCNode, 0), LoOut);
274   }
275   if (!SDValue(SUBENode, 0).use_empty()) {
276     SDValue HiIdx = CurDAG->getConstant(Mips::sub_hi, MVT::i32);
277     SDValue HiOut = CurDAG->getNode(MipsISD::ExtractLOHI, DL, MVT::i32, MSub,
278                                     HiIdx);
279     CurDAG->ReplaceAllUsesOfValueWith(SDValue(SUBENode, 0), HiOut);
280   }
281
282   return true;
283 }
284
285 static SDValue performADDECombine(SDNode *N, SelectionDAG &DAG,
286                                   TargetLowering::DAGCombinerInfo &DCI,
287                                   const MipsSubtarget *Subtarget) {
288   if (DCI.isBeforeLegalize())
289     return SDValue();
290
291   if (Subtarget->hasMips32() && N->getValueType(0) == MVT::i32 &&
292       selectMADD(N, &DAG))
293     return SDValue(N, 0);
294
295   return SDValue();
296 }
297
298 static SDValue performSUBECombine(SDNode *N, SelectionDAG &DAG,
299                                   TargetLowering::DAGCombinerInfo &DCI,
300                                   const MipsSubtarget *Subtarget) {
301   if (DCI.isBeforeLegalize())
302     return SDValue();
303
304   if (Subtarget->hasMips32() && N->getValueType(0) == MVT::i32 &&
305       selectMSUB(N, &DAG))
306     return SDValue(N, 0);
307
308   return SDValue();
309 }
310
311 SDValue
312 MipsSETargetLowering::PerformDAGCombine(SDNode *N, DAGCombinerInfo &DCI) const {
313   SelectionDAG &DAG = DCI.DAG;
314
315   switch (N->getOpcode()) {
316   case ISD::ADDE:
317     return performADDECombine(N, DAG, DCI, Subtarget);
318   case ISD::SUBE:
319     return performSUBECombine(N, DAG, DCI, Subtarget);
320   default:
321     return MipsTargetLowering::PerformDAGCombine(N, DCI);
322   }
323 }
324
325 MachineBasicBlock *
326 MipsSETargetLowering::EmitInstrWithCustomInserter(MachineInstr *MI,
327                                                   MachineBasicBlock *BB) const {
328   switch (MI->getOpcode()) {
329   default:
330     return MipsTargetLowering::EmitInstrWithCustomInserter(MI, BB);
331   case Mips::BPOSGE32_PSEUDO:
332     return emitBPOSGE32(MI, BB);
333   }
334 }
335
336 bool MipsSETargetLowering::
337 isEligibleForTailCallOptimization(const MipsCC &MipsCCInfo,
338                                   unsigned NextStackOffset,
339                                   const MipsFunctionInfo& FI) const {
340   if (!EnableMipsTailCalls)
341     return false;
342
343   // Return false if either the callee or caller has a byval argument.
344   if (MipsCCInfo.hasByValArg() || FI.hasByvalArg())
345     return false;
346
347   // Return true if the callee's argument area is no larger than the
348   // caller's.
349   return NextStackOffset <= FI.getIncomingArgSize();
350 }
351
352 void MipsSETargetLowering::
353 getOpndList(SmallVectorImpl<SDValue> &Ops,
354             std::deque< std::pair<unsigned, SDValue> > &RegsToPass,
355             bool IsPICCall, bool GlobalOrExternal, bool InternalLinkage,
356             CallLoweringInfo &CLI, SDValue Callee, SDValue Chain) const {
357   // T9 should contain the address of the callee function if
358   // -reloction-model=pic or it is an indirect call.
359   if (IsPICCall || !GlobalOrExternal) {
360     unsigned T9Reg = IsN64 ? Mips::T9_64 : Mips::T9;
361     RegsToPass.push_front(std::make_pair(T9Reg, Callee));
362   } else
363     Ops.push_back(Callee);
364
365   MipsTargetLowering::getOpndList(Ops, RegsToPass, IsPICCall, GlobalOrExternal,
366                                   InternalLinkage, CLI, Callee, Chain);
367 }
368
369 SDValue MipsSETargetLowering::lowerMulDiv(SDValue Op, unsigned NewOpc,
370                                           bool HasLo, bool HasHi,
371                                           SelectionDAG &DAG) const {
372   EVT Ty = Op.getOperand(0).getValueType();
373   DebugLoc DL = Op.getDebugLoc();
374   SDValue Mult = DAG.getNode(NewOpc, DL, MVT::Untyped,
375                              Op.getOperand(0), Op.getOperand(1));
376   SDValue Lo, Hi;
377
378   if (HasLo)
379     Lo = DAG.getNode(MipsISD::ExtractLOHI, DL, Ty, Mult,
380                      DAG.getConstant(Mips::sub_lo, MVT::i32));
381   if (HasHi)
382     Hi = DAG.getNode(MipsISD::ExtractLOHI, DL, Ty, Mult,
383                      DAG.getConstant(Mips::sub_hi, MVT::i32));
384
385   if (!HasLo || !HasHi)
386     return HasLo ? Lo : Hi;
387
388   SDValue Vals[] = { Lo, Hi };
389   return DAG.getMergeValues(Vals, 2, DL);
390 }
391
392 MachineBasicBlock * MipsSETargetLowering::
393 emitBPOSGE32(MachineInstr *MI, MachineBasicBlock *BB) const{
394   // $bb:
395   //  bposge32_pseudo $vr0
396   //  =>
397   // $bb:
398   //  bposge32 $tbb
399   // $fbb:
400   //  li $vr2, 0
401   //  b $sink
402   // $tbb:
403   //  li $vr1, 1
404   // $sink:
405   //  $vr0 = phi($vr2, $fbb, $vr1, $tbb)
406
407   MachineRegisterInfo &RegInfo = BB->getParent()->getRegInfo();
408   const TargetInstrInfo *TII = getTargetMachine().getInstrInfo();
409   const TargetRegisterClass *RC = &Mips::CPURegsRegClass;
410   DebugLoc DL = MI->getDebugLoc();
411   const BasicBlock *LLVM_BB = BB->getBasicBlock();
412   MachineFunction::iterator It = llvm::next(MachineFunction::iterator(BB));
413   MachineFunction *F = BB->getParent();
414   MachineBasicBlock *FBB = F->CreateMachineBasicBlock(LLVM_BB);
415   MachineBasicBlock *TBB = F->CreateMachineBasicBlock(LLVM_BB);
416   MachineBasicBlock *Sink  = F->CreateMachineBasicBlock(LLVM_BB);
417   F->insert(It, FBB);
418   F->insert(It, TBB);
419   F->insert(It, Sink);
420
421   // Transfer the remainder of BB and its successor edges to Sink.
422   Sink->splice(Sink->begin(), BB, llvm::next(MachineBasicBlock::iterator(MI)),
423                BB->end());
424   Sink->transferSuccessorsAndUpdatePHIs(BB);
425
426   // Add successors.
427   BB->addSuccessor(FBB);
428   BB->addSuccessor(TBB);
429   FBB->addSuccessor(Sink);
430   TBB->addSuccessor(Sink);
431
432   // Insert the real bposge32 instruction to $BB.
433   BuildMI(BB, DL, TII->get(Mips::BPOSGE32)).addMBB(TBB);
434
435   // Fill $FBB.
436   unsigned VR2 = RegInfo.createVirtualRegister(RC);
437   BuildMI(*FBB, FBB->end(), DL, TII->get(Mips::ADDiu), VR2)
438     .addReg(Mips::ZERO).addImm(0);
439   BuildMI(*FBB, FBB->end(), DL, TII->get(Mips::B)).addMBB(Sink);
440
441   // Fill $TBB.
442   unsigned VR1 = RegInfo.createVirtualRegister(RC);
443   BuildMI(*TBB, TBB->end(), DL, TII->get(Mips::ADDiu), VR1)
444     .addReg(Mips::ZERO).addImm(1);
445
446   // Insert phi function to $Sink.
447   BuildMI(*Sink, Sink->begin(), DL, TII->get(Mips::PHI),
448           MI->getOperand(0).getReg())
449     .addReg(VR2).addMBB(FBB).addReg(VR1).addMBB(TBB);
450
451   MI->eraseFromParent();   // The pseudo instruction is gone now.
452   return Sink;
453 }