1//===-- XCoreISelLowering.h - XCore 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// This file defines the interfaces that XCore uses to lower LLVM code into a
11// selection DAG.
12//
13//===----------------------------------------------------------------------===//
14
15#ifndef LLVM_LIB_TARGET_XCORE_XCOREISELLOWERING_H
16#define LLVM_LIB_TARGET_XCORE_XCOREISELLOWERING_H
17
18#include "XCore.h"
19#include "llvm/CodeGen/SelectionDAG.h"
20#include "llvm/Target/TargetLowering.h"
21
22namespace llvm {
23
24  // Forward delcarations
25  class XCoreSubtarget;
26  class XCoreTargetMachine;
27
28  namespace XCoreISD {
29    enum NodeType : unsigned {
30      // Start the numbering where the builtin ops and target ops leave off.
31      FIRST_NUMBER = ISD::BUILTIN_OP_END,
32
33      // Branch and link (call)
34      BL,
35
36      // pc relative address
37      PCRelativeWrapper,
38
39      // dp relative address
40      DPRelativeWrapper,
41
42      // cp relative address
43      CPRelativeWrapper,
44
45      // Load word from stack
46      LDWSP,
47
48      // Store word to stack
49      STWSP,
50
51      // Corresponds to retsp instruction
52      RETSP,
53
54      // Corresponds to LADD instruction
55      LADD,
56
57      // Corresponds to LSUB instruction
58      LSUB,
59
60      // Corresponds to LMUL instruction
61      LMUL,
62
63      // Corresponds to MACCU instruction
64      MACCU,
65
66      // Corresponds to MACCS instruction
67      MACCS,
68
69      // Corresponds to CRC8 instruction
70      CRC8,
71
72      // Jumptable branch.
73      BR_JT,
74
75      // Jumptable branch using long branches for each entry.
76      BR_JT32,
77
78      // Offset from frame pointer to the first (possible) on-stack argument
79      FRAME_TO_ARGS_OFFSET,
80
81      // Exception handler return. The stack is restored to the first
82      // followed by a jump to the second argument.
83      EH_RETURN,
84
85      // Memory barrier.
86      MEMBARRIER
87    };
88  }
89
90  //===--------------------------------------------------------------------===//
91  // TargetLowering Implementation
92  //===--------------------------------------------------------------------===//
93  class XCoreTargetLowering : public TargetLowering
94  {
95  public:
96    explicit XCoreTargetLowering(const TargetMachine &TM,
97                                 const XCoreSubtarget &Subtarget);
98
99    using TargetLowering::isZExtFree;
100    bool isZExtFree(SDValue Val, EVT VT2) const override;
101
102
103    unsigned getJumpTableEncoding() const override;
104    MVT getScalarShiftAmountTy(const DataLayout &DL, EVT) const override {
105      return MVT::i32;
106    }
107
108    /// LowerOperation - Provide custom lowering hooks for some operations.
109    SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override;
110
111    /// ReplaceNodeResults - Replace the results of node with an illegal result
112    /// type with new values built out of custom code.
113    ///
114    void ReplaceNodeResults(SDNode *N, SmallVectorImpl<SDValue>&Results,
115                            SelectionDAG &DAG) const override;
116
117    /// getTargetNodeName - This method returns the name of a target specific
118    //  DAG node.
119    const char *getTargetNodeName(unsigned Opcode) const override;
120
121    MachineBasicBlock *
122      EmitInstrWithCustomInserter(MachineInstr *MI,
123                                  MachineBasicBlock *MBB) const override;
124
125    bool isLegalAddressingMode(const DataLayout &DL, const AddrMode &AM,
126                               Type *Ty, unsigned AS) const override;
127
128    /// If a physical register, this returns the register that receives the
129    /// exception address on entry to an EH pad.
130    unsigned
131    getExceptionPointerRegister(const Constant *PersonalityFn) const override {
132      return XCore::R0;
133    }
134
135    /// If a physical register, this returns the register that receives the
136    /// exception typeid on entry to a landing pad.
137    unsigned
138    getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
139      return XCore::R1;
140    }
141
142  private:
143    const TargetMachine &TM;
144    const XCoreSubtarget &Subtarget;
145
146    // Lower Operand helpers
147    SDValue LowerCCCArguments(SDValue Chain,
148                              CallingConv::ID CallConv,
149                              bool isVarArg,
150                              const SmallVectorImpl<ISD::InputArg> &Ins,
151                              SDLoc dl, SelectionDAG &DAG,
152                              SmallVectorImpl<SDValue> &InVals) const;
153    SDValue LowerCCCCallTo(SDValue Chain, SDValue Callee,
154                           CallingConv::ID CallConv, bool isVarArg,
155                           bool isTailCall,
156                           const SmallVectorImpl<ISD::OutputArg> &Outs,
157                           const SmallVectorImpl<SDValue> &OutVals,
158                           const SmallVectorImpl<ISD::InputArg> &Ins,
159                           SDLoc dl, SelectionDAG &DAG,
160                           SmallVectorImpl<SDValue> &InVals) const;
161    SDValue getReturnAddressFrameIndex(SelectionDAG &DAG) const;
162    SDValue getGlobalAddressWrapper(SDValue GA, const GlobalValue *GV,
163                                    SelectionDAG &DAG) const;
164    SDValue lowerLoadWordFromAlignedBasePlusOffset(SDLoc DL, SDValue Chain,
165                                                   SDValue Base, int64_t Offset,
166                                                   SelectionDAG &DAG) const;
167
168    // Lower Operand specifics
169    SDValue LowerLOAD(SDValue Op, SelectionDAG &DAG) const;
170    SDValue LowerSTORE(SDValue Op, SelectionDAG &DAG) const;
171    SDValue LowerEH_RETURN(SDValue Op, SelectionDAG &DAG) const;
172    SDValue LowerGlobalAddress(SDValue Op, SelectionDAG &DAG) const;
173    SDValue LowerGlobalTLSAddress(SDValue Op, SelectionDAG &DAG) const;
174    SDValue LowerBlockAddress(SDValue Op, SelectionDAG &DAG) const;
175    SDValue LowerConstantPool(SDValue Op, SelectionDAG &DAG) const;
176    SDValue LowerBR_JT(SDValue Op, SelectionDAG &DAG) const;
177    SDValue LowerVAARG(SDValue Op, SelectionDAG &DAG) const;
178    SDValue LowerVASTART(SDValue Op, SelectionDAG &DAG) const;
179    SDValue LowerUMUL_LOHI(SDValue Op, SelectionDAG &DAG) const;
180    SDValue LowerSMUL_LOHI(SDValue Op, SelectionDAG &DAG) const;
181    SDValue LowerFRAMEADDR(SDValue Op, SelectionDAG &DAG) const;
182    SDValue LowerFRAME_TO_ARGS_OFFSET(SDValue Op, SelectionDAG &DAG) const;
183    SDValue LowerRETURNADDR(SDValue Op, SelectionDAG &DAG) const;
184    SDValue LowerINIT_TRAMPOLINE(SDValue Op, SelectionDAG &DAG) const;
185    SDValue LowerADJUST_TRAMPOLINE(SDValue Op, SelectionDAG &DAG) const;
186    SDValue LowerINTRINSIC_WO_CHAIN(SDValue Op, SelectionDAG &DAG) const;
187    SDValue LowerATOMIC_FENCE(SDValue Op, SelectionDAG &DAG) const;
188    SDValue LowerATOMIC_LOAD(SDValue Op, SelectionDAG &DAG) const;
189    SDValue LowerATOMIC_STORE(SDValue Op, SelectionDAG &DAG) const;
190
191    // Inline asm support
192    std::pair<unsigned, const TargetRegisterClass *>
193    getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,
194                                 StringRef Constraint, MVT VT) const override;
195
196    // Expand specifics
197    SDValue TryExpandADDWithMul(SDNode *Op, SelectionDAG &DAG) const;
198    SDValue ExpandADDSUB(SDNode *Op, SelectionDAG &DAG) const;
199
200    SDValue PerformDAGCombine(SDNode *N, DAGCombinerInfo &DCI) const override;
201
202    void computeKnownBitsForTargetNode(const SDValue Op,
203                                       APInt &KnownZero,
204                                       APInt &KnownOne,
205                                       const SelectionDAG &DAG,
206                                       unsigned Depth = 0) const override;
207
208    SDValue
209      LowerFormalArguments(SDValue Chain,
210                           CallingConv::ID CallConv,
211                           bool isVarArg,
212                           const SmallVectorImpl<ISD::InputArg> &Ins,
213                           SDLoc dl, SelectionDAG &DAG,
214                           SmallVectorImpl<SDValue> &InVals) const override;
215
216    SDValue
217      LowerCall(TargetLowering::CallLoweringInfo &CLI,
218                SmallVectorImpl<SDValue> &InVals) const override;
219
220    SDValue
221      LowerReturn(SDValue Chain,
222                  CallingConv::ID CallConv, bool isVarArg,
223                  const SmallVectorImpl<ISD::OutputArg> &Outs,
224                  const SmallVectorImpl<SDValue> &OutVals,
225                  SDLoc dl, SelectionDAG &DAG) const override;
226
227    bool
228      CanLowerReturn(CallingConv::ID CallConv, MachineFunction &MF,
229                     bool isVarArg,
230                     const SmallVectorImpl<ISD::OutputArg> &ArgsFlags,
231                     LLVMContext &Context) const override;
232  };
233}
234
235#endif
236