xref: /aosp_15_r20/external/llvm/lib/Target/Sparc/SparcISelLowering.h (revision 9880d6810fe72a1726cb53787c6711e909410d58)
1*9880d681SAndroid Build Coastguard Worker //===-- SparcISelLowering.h - Sparc DAG Lowering Interface ------*- C++ -*-===//
2*9880d681SAndroid Build Coastguard Worker //
3*9880d681SAndroid Build Coastguard Worker //                     The LLVM Compiler Infrastructure
4*9880d681SAndroid Build Coastguard Worker //
5*9880d681SAndroid Build Coastguard Worker // This file is distributed under the University of Illinois Open Source
6*9880d681SAndroid Build Coastguard Worker // License. See LICENSE.TXT for details.
7*9880d681SAndroid Build Coastguard Worker //
8*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
9*9880d681SAndroid Build Coastguard Worker //
10*9880d681SAndroid Build Coastguard Worker // This file defines the interfaces that Sparc uses to lower LLVM code into a
11*9880d681SAndroid Build Coastguard Worker // selection DAG.
12*9880d681SAndroid Build Coastguard Worker //
13*9880d681SAndroid Build Coastguard Worker //===----------------------------------------------------------------------===//
14*9880d681SAndroid Build Coastguard Worker 
15*9880d681SAndroid Build Coastguard Worker #ifndef LLVM_LIB_TARGET_SPARC_SPARCISELLOWERING_H
16*9880d681SAndroid Build Coastguard Worker #define LLVM_LIB_TARGET_SPARC_SPARCISELLOWERING_H
17*9880d681SAndroid Build Coastguard Worker 
18*9880d681SAndroid Build Coastguard Worker #include "Sparc.h"
19*9880d681SAndroid Build Coastguard Worker #include "llvm/Target/TargetLowering.h"
20*9880d681SAndroid Build Coastguard Worker 
21*9880d681SAndroid Build Coastguard Worker namespace llvm {
22*9880d681SAndroid Build Coastguard Worker   class SparcSubtarget;
23*9880d681SAndroid Build Coastguard Worker 
24*9880d681SAndroid Build Coastguard Worker   namespace SPISD {
25*9880d681SAndroid Build Coastguard Worker     enum NodeType : unsigned {
26*9880d681SAndroid Build Coastguard Worker       FIRST_NUMBER = ISD::BUILTIN_OP_END,
27*9880d681SAndroid Build Coastguard Worker       CMPICC,      // Compare two GPR operands, set icc+xcc.
28*9880d681SAndroid Build Coastguard Worker       CMPFCC,      // Compare two FP operands, set fcc.
29*9880d681SAndroid Build Coastguard Worker       BRICC,       // Branch to dest on icc condition
30*9880d681SAndroid Build Coastguard Worker       BRXCC,       // Branch to dest on xcc condition (64-bit only).
31*9880d681SAndroid Build Coastguard Worker       BRFCC,       // Branch to dest on fcc condition
32*9880d681SAndroid Build Coastguard Worker       SELECT_ICC,  // Select between two values using the current ICC flags.
33*9880d681SAndroid Build Coastguard Worker       SELECT_XCC,  // Select between two values using the current XCC flags.
34*9880d681SAndroid Build Coastguard Worker       SELECT_FCC,  // Select between two values using the current FCC flags.
35*9880d681SAndroid Build Coastguard Worker 
36*9880d681SAndroid Build Coastguard Worker       EH_SJLJ_SETJMP,  // builtin setjmp operation
37*9880d681SAndroid Build Coastguard Worker       EH_SJLJ_LONGJMP, // builtin longjmp operation
38*9880d681SAndroid Build Coastguard Worker 
39*9880d681SAndroid Build Coastguard Worker       Hi, Lo,      // Hi/Lo operations, typically on a global address.
40*9880d681SAndroid Build Coastguard Worker 
41*9880d681SAndroid Build Coastguard Worker       FTOI,        // FP to Int within a FP register.
42*9880d681SAndroid Build Coastguard Worker       ITOF,        // Int to FP within a FP register.
43*9880d681SAndroid Build Coastguard Worker       FTOX,        // FP to Int64 within a FP register.
44*9880d681SAndroid Build Coastguard Worker       XTOF,        // Int64 to FP within a FP register.
45*9880d681SAndroid Build Coastguard Worker 
46*9880d681SAndroid Build Coastguard Worker       CALL,        // A call instruction.
47*9880d681SAndroid Build Coastguard Worker       RET_FLAG,    // Return with a flag operand.
48*9880d681SAndroid Build Coastguard Worker       GLOBAL_BASE_REG, // Global base reg for PIC.
49*9880d681SAndroid Build Coastguard Worker       FLUSHW,      // FLUSH register windows to stack.
50*9880d681SAndroid Build Coastguard Worker 
51*9880d681SAndroid Build Coastguard Worker       TLS_ADD,     // For Thread Local Storage (TLS).
52*9880d681SAndroid Build Coastguard Worker       TLS_LD,
53*9880d681SAndroid Build Coastguard Worker       TLS_CALL
54*9880d681SAndroid Build Coastguard Worker     };
55*9880d681SAndroid Build Coastguard Worker   }
56*9880d681SAndroid Build Coastguard Worker 
57*9880d681SAndroid Build Coastguard Worker   class SparcTargetLowering : public TargetLowering {
58*9880d681SAndroid Build Coastguard Worker     const SparcSubtarget *Subtarget;
59*9880d681SAndroid Build Coastguard Worker   public:
60*9880d681SAndroid Build Coastguard Worker     SparcTargetLowering(const TargetMachine &TM, const SparcSubtarget &STI);
61*9880d681SAndroid Build Coastguard Worker     SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override;
62*9880d681SAndroid Build Coastguard Worker 
63*9880d681SAndroid Build Coastguard Worker     bool useSoftFloat() const override;
64*9880d681SAndroid Build Coastguard Worker 
65*9880d681SAndroid Build Coastguard Worker     /// computeKnownBitsForTargetNode - Determine which of the bits specified
66*9880d681SAndroid Build Coastguard Worker     /// in Mask are known to be either zero or one and return them in the
67*9880d681SAndroid Build Coastguard Worker     /// KnownZero/KnownOne bitsets.
68*9880d681SAndroid Build Coastguard Worker     void computeKnownBitsForTargetNode(const SDValue Op,
69*9880d681SAndroid Build Coastguard Worker                                        APInt &KnownZero,
70*9880d681SAndroid Build Coastguard Worker                                        APInt &KnownOne,
71*9880d681SAndroid Build Coastguard Worker                                        const SelectionDAG &DAG,
72*9880d681SAndroid Build Coastguard Worker                                        unsigned Depth = 0) const override;
73*9880d681SAndroid Build Coastguard Worker 
74*9880d681SAndroid Build Coastguard Worker     MachineBasicBlock *
75*9880d681SAndroid Build Coastguard Worker     EmitInstrWithCustomInserter(MachineInstr &MI,
76*9880d681SAndroid Build Coastguard Worker                                 MachineBasicBlock *MBB) const override;
77*9880d681SAndroid Build Coastguard Worker 
78*9880d681SAndroid Build Coastguard Worker     const char *getTargetNodeName(unsigned Opcode) const override;
79*9880d681SAndroid Build Coastguard Worker 
80*9880d681SAndroid Build Coastguard Worker     ConstraintType getConstraintType(StringRef Constraint) const override;
81*9880d681SAndroid Build Coastguard Worker     ConstraintWeight
82*9880d681SAndroid Build Coastguard Worker     getSingleConstraintMatchWeight(AsmOperandInfo &info,
83*9880d681SAndroid Build Coastguard Worker                                    const char *constraint) const override;
84*9880d681SAndroid Build Coastguard Worker     void LowerAsmOperandForConstraint(SDValue Op,
85*9880d681SAndroid Build Coastguard Worker                                       std::string &Constraint,
86*9880d681SAndroid Build Coastguard Worker                                       std::vector<SDValue> &Ops,
87*9880d681SAndroid Build Coastguard Worker                                       SelectionDAG &DAG) const override;
88*9880d681SAndroid Build Coastguard Worker 
89*9880d681SAndroid Build Coastguard Worker     unsigned
getInlineAsmMemConstraint(StringRef ConstraintCode)90*9880d681SAndroid Build Coastguard Worker     getInlineAsmMemConstraint(StringRef ConstraintCode) const override {
91*9880d681SAndroid Build Coastguard Worker       if (ConstraintCode == "o")
92*9880d681SAndroid Build Coastguard Worker         return InlineAsm::Constraint_o;
93*9880d681SAndroid Build Coastguard Worker       return TargetLowering::getInlineAsmMemConstraint(ConstraintCode);
94*9880d681SAndroid Build Coastguard Worker     }
95*9880d681SAndroid Build Coastguard Worker 
96*9880d681SAndroid Build Coastguard Worker     std::pair<unsigned, const TargetRegisterClass *>
97*9880d681SAndroid Build Coastguard Worker     getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,
98*9880d681SAndroid Build Coastguard Worker                                  StringRef Constraint, MVT VT) const override;
99*9880d681SAndroid Build Coastguard Worker 
100*9880d681SAndroid Build Coastguard Worker     bool isOffsetFoldingLegal(const GlobalAddressSDNode *GA) const override;
getScalarShiftAmountTy(const DataLayout &,EVT)101*9880d681SAndroid Build Coastguard Worker     MVT getScalarShiftAmountTy(const DataLayout &, EVT) const override {
102*9880d681SAndroid Build Coastguard Worker       return MVT::i32;
103*9880d681SAndroid Build Coastguard Worker     }
104*9880d681SAndroid Build Coastguard Worker 
105*9880d681SAndroid Build Coastguard Worker     unsigned getRegisterByName(const char* RegName, EVT VT,
106*9880d681SAndroid Build Coastguard Worker                                SelectionDAG &DAG) const override;
107*9880d681SAndroid Build Coastguard Worker 
108*9880d681SAndroid Build Coastguard Worker     /// If a physical register, this returns the register that receives the
109*9880d681SAndroid Build Coastguard Worker     /// exception address on entry to an EH pad.
110*9880d681SAndroid Build Coastguard Worker     unsigned
getExceptionPointerRegister(const Constant * PersonalityFn)111*9880d681SAndroid Build Coastguard Worker     getExceptionPointerRegister(const Constant *PersonalityFn) const override {
112*9880d681SAndroid Build Coastguard Worker       return SP::I0;
113*9880d681SAndroid Build Coastguard Worker     }
114*9880d681SAndroid Build Coastguard Worker 
115*9880d681SAndroid Build Coastguard Worker     /// If a physical register, this returns the register that receives the
116*9880d681SAndroid Build Coastguard Worker     /// exception typeid on entry to a landing pad.
117*9880d681SAndroid Build Coastguard Worker     unsigned
getExceptionSelectorRegister(const Constant * PersonalityFn)118*9880d681SAndroid Build Coastguard Worker     getExceptionSelectorRegister(const Constant *PersonalityFn) const override {
119*9880d681SAndroid Build Coastguard Worker       return SP::I1;
120*9880d681SAndroid Build Coastguard Worker     }
121*9880d681SAndroid Build Coastguard Worker 
122*9880d681SAndroid Build Coastguard Worker     /// Override to support customized stack guard loading.
123*9880d681SAndroid Build Coastguard Worker     bool useLoadStackGuardNode() const override;
124*9880d681SAndroid Build Coastguard Worker     void insertSSPDeclarations(Module &M) const override;
125*9880d681SAndroid Build Coastguard Worker 
126*9880d681SAndroid Build Coastguard Worker     /// getSetCCResultType - Return the ISD::SETCC ValueType
127*9880d681SAndroid Build Coastguard Worker     EVT getSetCCResultType(const DataLayout &DL, LLVMContext &Context,
128*9880d681SAndroid Build Coastguard Worker                            EVT VT) const override;
129*9880d681SAndroid Build Coastguard Worker 
130*9880d681SAndroid Build Coastguard Worker     SDValue
131*9880d681SAndroid Build Coastguard Worker     LowerFormalArguments(SDValue Chain, CallingConv::ID CallConv, bool isVarArg,
132*9880d681SAndroid Build Coastguard Worker                          const SmallVectorImpl<ISD::InputArg> &Ins,
133*9880d681SAndroid Build Coastguard Worker                          const SDLoc &dl, SelectionDAG &DAG,
134*9880d681SAndroid Build Coastguard Worker                          SmallVectorImpl<SDValue> &InVals) const override;
135*9880d681SAndroid Build Coastguard Worker     SDValue LowerFormalArguments_32(SDValue Chain, CallingConv::ID CallConv,
136*9880d681SAndroid Build Coastguard Worker                                     bool isVarArg,
137*9880d681SAndroid Build Coastguard Worker                                     const SmallVectorImpl<ISD::InputArg> &Ins,
138*9880d681SAndroid Build Coastguard Worker                                     const SDLoc &dl, SelectionDAG &DAG,
139*9880d681SAndroid Build Coastguard Worker                                     SmallVectorImpl<SDValue> &InVals) const;
140*9880d681SAndroid Build Coastguard Worker     SDValue LowerFormalArguments_64(SDValue Chain, CallingConv::ID CallConv,
141*9880d681SAndroid Build Coastguard Worker                                     bool isVarArg,
142*9880d681SAndroid Build Coastguard Worker                                     const SmallVectorImpl<ISD::InputArg> &Ins,
143*9880d681SAndroid Build Coastguard Worker                                     const SDLoc &dl, SelectionDAG &DAG,
144*9880d681SAndroid Build Coastguard Worker                                     SmallVectorImpl<SDValue> &InVals) const;
145*9880d681SAndroid Build Coastguard Worker 
146*9880d681SAndroid Build Coastguard Worker     SDValue
147*9880d681SAndroid Build Coastguard Worker       LowerCall(TargetLowering::CallLoweringInfo &CLI,
148*9880d681SAndroid Build Coastguard Worker                 SmallVectorImpl<SDValue> &InVals) const override;
149*9880d681SAndroid Build Coastguard Worker     SDValue LowerCall_32(TargetLowering::CallLoweringInfo &CLI,
150*9880d681SAndroid Build Coastguard Worker                          SmallVectorImpl<SDValue> &InVals) const;
151*9880d681SAndroid Build Coastguard Worker     SDValue LowerCall_64(TargetLowering::CallLoweringInfo &CLI,
152*9880d681SAndroid Build Coastguard Worker                          SmallVectorImpl<SDValue> &InVals) const;
153*9880d681SAndroid Build Coastguard Worker 
154*9880d681SAndroid Build Coastguard Worker     SDValue LowerReturn(SDValue Chain, CallingConv::ID CallConv, bool isVarArg,
155*9880d681SAndroid Build Coastguard Worker                         const SmallVectorImpl<ISD::OutputArg> &Outs,
156*9880d681SAndroid Build Coastguard Worker                         const SmallVectorImpl<SDValue> &OutVals,
157*9880d681SAndroid Build Coastguard Worker                         const SDLoc &dl, SelectionDAG &DAG) const override;
158*9880d681SAndroid Build Coastguard Worker     SDValue LowerReturn_32(SDValue Chain, CallingConv::ID CallConv,
159*9880d681SAndroid Build Coastguard Worker                            bool IsVarArg,
160*9880d681SAndroid Build Coastguard Worker                            const SmallVectorImpl<ISD::OutputArg> &Outs,
161*9880d681SAndroid Build Coastguard Worker                            const SmallVectorImpl<SDValue> &OutVals,
162*9880d681SAndroid Build Coastguard Worker                            const SDLoc &DL, SelectionDAG &DAG) const;
163*9880d681SAndroid Build Coastguard Worker     SDValue LowerReturn_64(SDValue Chain, CallingConv::ID CallConv,
164*9880d681SAndroid Build Coastguard Worker                            bool IsVarArg,
165*9880d681SAndroid Build Coastguard Worker                            const SmallVectorImpl<ISD::OutputArg> &Outs,
166*9880d681SAndroid Build Coastguard Worker                            const SmallVectorImpl<SDValue> &OutVals,
167*9880d681SAndroid Build Coastguard Worker                            const SDLoc &DL, SelectionDAG &DAG) const;
168*9880d681SAndroid Build Coastguard Worker 
169*9880d681SAndroid Build Coastguard Worker     SDValue LowerGlobalAddress(SDValue Op, SelectionDAG &DAG) const;
170*9880d681SAndroid Build Coastguard Worker     SDValue LowerGlobalTLSAddress(SDValue Op, SelectionDAG &DAG) const;
171*9880d681SAndroid Build Coastguard Worker     SDValue LowerConstantPool(SDValue Op, SelectionDAG &DAG) const;
172*9880d681SAndroid Build Coastguard Worker     SDValue LowerBlockAddress(SDValue Op, SelectionDAG &DAG) const;
173*9880d681SAndroid Build Coastguard Worker 
174*9880d681SAndroid Build Coastguard Worker     SDValue LowerEH_SJLJ_SETJMP(SDValue Op, SelectionDAG &DAG,
175*9880d681SAndroid Build Coastguard Worker                                 const SparcTargetLowering &TLI) const ;
176*9880d681SAndroid Build Coastguard Worker     SDValue LowerEH_SJLJ_LONGJMP(SDValue Op, SelectionDAG &DAG,
177*9880d681SAndroid Build Coastguard Worker                                  const SparcTargetLowering &TLI) const ;
178*9880d681SAndroid Build Coastguard Worker 
179*9880d681SAndroid Build Coastguard Worker     unsigned getSRetArgSize(SelectionDAG &DAG, SDValue Callee) const;
180*9880d681SAndroid Build Coastguard Worker     SDValue withTargetFlags(SDValue Op, unsigned TF, SelectionDAG &DAG) const;
181*9880d681SAndroid Build Coastguard Worker     SDValue makeHiLoPair(SDValue Op, unsigned HiTF, unsigned LoTF,
182*9880d681SAndroid Build Coastguard Worker                          SelectionDAG &DAG) const;
183*9880d681SAndroid Build Coastguard Worker     SDValue makeAddress(SDValue Op, SelectionDAG &DAG) const;
184*9880d681SAndroid Build Coastguard Worker 
185*9880d681SAndroid Build Coastguard Worker     SDValue LowerF128_LibCallArg(SDValue Chain, ArgListTy &Args, SDValue Arg,
186*9880d681SAndroid Build Coastguard Worker                                  const SDLoc &DL, SelectionDAG &DAG) const;
187*9880d681SAndroid Build Coastguard Worker     SDValue LowerF128Op(SDValue Op, SelectionDAG &DAG,
188*9880d681SAndroid Build Coastguard Worker                         const char *LibFuncName,
189*9880d681SAndroid Build Coastguard Worker                         unsigned numArgs) const;
190*9880d681SAndroid Build Coastguard Worker     SDValue LowerF128Compare(SDValue LHS, SDValue RHS, unsigned &SPCC,
191*9880d681SAndroid Build Coastguard Worker                              const SDLoc &DL, SelectionDAG &DAG) const;
192*9880d681SAndroid Build Coastguard Worker 
193*9880d681SAndroid Build Coastguard Worker     SDValue LowerINTRINSIC_WO_CHAIN(SDValue Op, SelectionDAG &DAG) const;
194*9880d681SAndroid Build Coastguard Worker 
ShouldShrinkFPConstant(EVT VT)195*9880d681SAndroid Build Coastguard Worker     bool ShouldShrinkFPConstant(EVT VT) const override {
196*9880d681SAndroid Build Coastguard Worker       // Do not shrink FP constpool if VT == MVT::f128.
197*9880d681SAndroid Build Coastguard Worker       // (ldd, call _Q_fdtoq) is more expensive than two ldds.
198*9880d681SAndroid Build Coastguard Worker       return VT != MVT::f128;
199*9880d681SAndroid Build Coastguard Worker     }
200*9880d681SAndroid Build Coastguard Worker 
shouldInsertFencesForAtomic(const Instruction * I)201*9880d681SAndroid Build Coastguard Worker     bool shouldInsertFencesForAtomic(const Instruction *I) const override {
202*9880d681SAndroid Build Coastguard Worker       // FIXME: We insert fences for each atomics and generate
203*9880d681SAndroid Build Coastguard Worker       // sub-optimal code for PSO/TSO. (Approximately nobody uses any
204*9880d681SAndroid Build Coastguard Worker       // mode but TSO, which makes this even more silly)
205*9880d681SAndroid Build Coastguard Worker       return true;
206*9880d681SAndroid Build Coastguard Worker     }
207*9880d681SAndroid Build Coastguard Worker 
208*9880d681SAndroid Build Coastguard Worker     AtomicExpansionKind shouldExpandAtomicRMWInIR(AtomicRMWInst *AI) const override;
209*9880d681SAndroid Build Coastguard Worker 
210*9880d681SAndroid Build Coastguard Worker     void ReplaceNodeResults(SDNode *N,
211*9880d681SAndroid Build Coastguard Worker                             SmallVectorImpl<SDValue>& Results,
212*9880d681SAndroid Build Coastguard Worker                             SelectionDAG &DAG) const override;
213*9880d681SAndroid Build Coastguard Worker 
214*9880d681SAndroid Build Coastguard Worker     MachineBasicBlock *expandSelectCC(MachineInstr &MI, MachineBasicBlock *BB,
215*9880d681SAndroid Build Coastguard Worker                                       unsigned BROpcode) const;
216*9880d681SAndroid Build Coastguard Worker     MachineBasicBlock *emitEHSjLjSetJmp(MachineInstr &MI,
217*9880d681SAndroid Build Coastguard Worker                                         MachineBasicBlock *MBB) const;
218*9880d681SAndroid Build Coastguard Worker     MachineBasicBlock *emitEHSjLjLongJmp(MachineInstr &MI,
219*9880d681SAndroid Build Coastguard Worker                                          MachineBasicBlock *MBB) const;
220*9880d681SAndroid Build Coastguard Worker   };
221*9880d681SAndroid Build Coastguard Worker } // end namespace llvm
222*9880d681SAndroid Build Coastguard Worker 
223*9880d681SAndroid Build Coastguard Worker #endif    // SPARC_ISELLOWERING_H
224