brintos

brintos / llvm-project-archived public Read only

0
0
Text · 11.7 KiB · dd8e49d Raw
269 lines · c
1//===-- NVPTXISelLowering.h - NVPTX DAG Lowering Interface ------*- C++ -*-===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9// This file defines the interfaces that NVPTX uses to lower LLVM code into a10// selection DAG.11//12//===----------------------------------------------------------------------===//13 14#ifndef LLVM_LIB_TARGET_NVPTX_NVPTXISELLOWERING_H15#define LLVM_LIB_TARGET_NVPTX_NVPTXISELLOWERING_H16 17#include "NVPTX.h"18#include "llvm/CodeGen/SelectionDAG.h"19#include "llvm/CodeGen/TargetLowering.h"20#include "llvm/Support/AtomicOrdering.h"21 22namespace llvm {23 24class NVPTXSubtarget;25 26//===--------------------------------------------------------------------===//27// TargetLowering Implementation28//===--------------------------------------------------------------------===//29class NVPTXTargetLowering : public TargetLowering {30public:31  explicit NVPTXTargetLowering(const NVPTXTargetMachine &TM,32                               const NVPTXSubtarget &STI);33  SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override;34 35  bool getTgtMemIntrinsic(IntrinsicInfo &Info, const CallInst &I,36                          MachineFunction &MF,37                          unsigned Intrinsic) const override;38 39  Align getFunctionArgumentAlignment(const Function *F, Type *Ty, unsigned Idx,40                                     const DataLayout &DL) const;41 42  /// getFunctionParamOptimizedAlign - since function arguments are passed via43  /// .param space, we may want to increase their alignment in a way that44  /// ensures that we can effectively vectorize their loads & stores. We can45  /// increase alignment only if the function has internal or has private46  /// linkage as for other linkage types callers may already rely on default47  /// alignment. To allow using 128-bit vectorized loads/stores, this function48  /// ensures that alignment is 16 or greater.49  Align getFunctionParamOptimizedAlign(const Function *F, Type *ArgTy,50                                       const DataLayout &DL) const;51 52  /// Helper for computing alignment of a device function byval parameter.53  Align getFunctionByValParamAlign(const Function *F, Type *ArgTy,54                                   Align InitialAlign,55                                   const DataLayout &DL) const;56 57  // Helper for getting a function parameter name. Name is composed from58  // its index and the function name. Negative index corresponds to special59  // parameter (unsized array) used for passing variable arguments.60  std::string getParamName(const Function *F, int Idx) const;61 62  /// isLegalAddressingMode - Return true if the addressing mode represented63  /// by AM is legal for this target, for a load/store of the specified type64  /// Used to guide target specific optimizations, like loop strength65  /// reduction (LoopStrengthReduce.cpp) and memory optimization for66  /// address mode (CodeGenPrepare.cpp)67  bool isLegalAddressingMode(const DataLayout &DL, const AddrMode &AM, Type *Ty,68                             unsigned AS,69                             Instruction *I = nullptr) const override;70 71  bool isTruncateFree(Type *SrcTy, Type *DstTy) const override {72    // Truncating 64-bit to 32-bit is free in SASS.73    if (!SrcTy->isIntegerTy() || !DstTy->isIntegerTy())74      return false;75    return SrcTy->getPrimitiveSizeInBits() == 64 &&76           DstTy->getPrimitiveSizeInBits() == 32;77  }78 79  EVT getSetCCResultType(const DataLayout &DL, LLVMContext &Ctx,80                         EVT VT) const override {81    if (VT.isVector())82      return EVT::getVectorVT(Ctx, MVT::i1, VT.getVectorNumElements());83    return MVT::i1;84  }85 86  ConstraintType getConstraintType(StringRef Constraint) const override;87  std::pair<unsigned, const TargetRegisterClass *>88  getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,89                               StringRef Constraint, MVT VT) const override;90 91  SDValue LowerFormalArguments(SDValue Chain, CallingConv::ID CallConv,92                               bool isVarArg,93                               const SmallVectorImpl<ISD::InputArg> &Ins,94                               const SDLoc &dl, SelectionDAG &DAG,95                               SmallVectorImpl<SDValue> &InVals) const override;96 97  SDValue LowerCall(CallLoweringInfo &CLI,98                    SmallVectorImpl<SDValue> &InVals) const override;99 100  SDValue LowerDYNAMIC_STACKALLOC(SDValue Op, SelectionDAG &DAG) const;101  SDValue LowerSTACKSAVE(SDValue Op, SelectionDAG &DAG) const;102  SDValue LowerSTACKRESTORE(SDValue Op, SelectionDAG &DAG) const;103 104  std::string getPrototype(const DataLayout &DL, Type *, const ArgListTy &,105                           const SmallVectorImpl<ISD::OutputArg> &,106                           std::optional<unsigned> FirstVAArg,107                           const CallBase &CB, unsigned UniqueCallSite) const;108 109  SDValue LowerReturn(SDValue Chain, CallingConv::ID CallConv, bool isVarArg,110                      const SmallVectorImpl<ISD::OutputArg> &Outs,111                      const SmallVectorImpl<SDValue> &OutVals, const SDLoc &dl,112                      SelectionDAG &DAG) const override;113 114  void LowerAsmOperandForConstraint(SDValue Op, StringRef Constraint,115                                    std::vector<SDValue> &Ops,116                                    SelectionDAG &DAG) const override;117 118  const NVPTXTargetMachine *nvTM;119 120  // PTX always uses 32-bit shift amounts121  MVT getScalarShiftAmountTy(const DataLayout &, EVT) const override {122    return MVT::i32;123  }124 125  TargetLoweringBase::LegalizeTypeAction126  getPreferredVectorAction(MVT VT) const override;127 128  // Get the degree of precision we want from 32-bit floating point division129  // operations.130  NVPTX::DivPrecisionLevel getDivF32Level(const MachineFunction &MF,131                                          const SDNode &N) const;132 133  // Get whether we should use a precise or approximate 32-bit floating point134  // sqrt instruction.135  bool usePrecSqrtF32(const SDNode *N = nullptr) const;136 137  // Get whether we should use instructions that flush floating-point denormals138  // to sign-preserving zero.139  bool useF32FTZ(const MachineFunction &MF) const;140 141  SDValue getSqrtEstimate(SDValue Operand, SelectionDAG &DAG, int Enabled,142                          int &ExtraSteps, bool &UseOneConst,143                          bool Reciprocal) const override;144 145  unsigned combineRepeatedFPDivisors() const override { return 2; }146 147  bool allowFMA(MachineFunction &MF, CodeGenOptLevel OptLevel) const;148 149  bool isFMAFasterThanFMulAndFAdd(const MachineFunction &MF,150                                  EVT) const override {151    return true;152  }153 154  // The default is the same as pointer type, but brx.idx only accepts i32155  MVT getJumpTableRegTy(const DataLayout &) const override { return MVT::i32; }156 157  unsigned getJumpTableEncoding() const override;158 159  bool enableAggressiveFMAFusion(EVT VT) const override { return true; }160 161  // The default is to transform llvm.ctlz(x, false) (where false indicates that162  // x == 0 is not undefined behavior) into a branch that checks whether x is 0163  // and avoids calling ctlz in that case.  We have a dedicated ctlz164  // instruction, so we say that ctlz is cheap to speculate.165  bool isCheapToSpeculateCtlz(Type *Ty) const override { return true; }166 167  AtomicExpansionKind shouldCastAtomicLoadInIR(LoadInst *LI) const override {168    return AtomicExpansionKind::None;169  }170 171  AtomicExpansionKind shouldCastAtomicStoreInIR(StoreInst *SI) const override {172    return AtomicExpansionKind::None;173  }174 175  AtomicExpansionKind176  shouldExpandAtomicRMWInIR(AtomicRMWInst *AI) const override;177 178  bool aggressivelyPreferBuildVectorSources(EVT VecVT) const override {179    // There's rarely any point of packing something into a vector type if we180    // already have the source data.181    return true;182  }183 184  bool shouldInsertFencesForAtomic(const Instruction *) const override;185 186  AtomicOrdering187  atomicOperationOrderAfterFenceSplit(const Instruction *I) const override;188 189  Instruction *emitLeadingFence(IRBuilderBase &Builder, Instruction *Inst,190                                AtomicOrdering Ord) const override;191  Instruction *emitTrailingFence(IRBuilderBase &Builder, Instruction *Inst,192                                 AtomicOrdering Ord) const override;193 194  unsigned getPreferredFPToIntOpcode(unsigned Op, EVT FromVT,195                                     EVT ToVT) const override;196 197  void computeKnownBitsForTargetNode(const SDValue Op, KnownBits &Known,198                                     const APInt &DemandedElts,199                                     const SelectionDAG &DAG,200                                     unsigned Depth = 0) const override;201  bool SimplifyDemandedBitsForTargetNode(SDValue Op, const APInt &DemandedBits,202                                         const APInt &DemandedElts,203                                         KnownBits &Known,204                                         TargetLoweringOpt &TLO,205                                         unsigned Depth = 0) const override;206 207private:208  const NVPTXSubtarget &STI; // cache the subtarget here209  mutable unsigned GlobalUniqueCallSite;210 211  SDValue getParamSymbol(SelectionDAG &DAG, int I, EVT T) const;212  SDValue getCallParamSymbol(SelectionDAG &DAG, int I, EVT T) const;213  SDValue LowerADDRSPACECAST(SDValue Op, SelectionDAG &DAG) const;214  SDValue LowerBITCAST(SDValue Op, SelectionDAG &DAG) const;215 216  SDValue LowerBUILD_VECTOR(SDValue Op, SelectionDAG &DAG) const;217  SDValue LowerCONCAT_VECTORS(SDValue Op, SelectionDAG &DAG) const;218  SDValue LowerVECREDUCE(SDValue Op, SelectionDAG &DAG) const;219  SDValue LowerEXTRACT_VECTOR_ELT(SDValue Op, SelectionDAG &DAG) const;220  SDValue LowerINSERT_VECTOR_ELT(SDValue Op, SelectionDAG &DAG) const;221  SDValue LowerVECTOR_SHUFFLE(SDValue Op, SelectionDAG &DAG) const;222 223  SDValue LowerFCOPYSIGN(SDValue Op, SelectionDAG &DAG) const;224 225  SDValue LowerFROUND(SDValue Op, SelectionDAG &DAG) const;226  SDValue LowerFROUND32(SDValue Op, SelectionDAG &DAG) const;227  SDValue LowerFROUND64(SDValue Op, SelectionDAG &DAG) const;228 229  SDValue PromoteBinOpIfF32FTZ(SDValue Op, SelectionDAG &DAG) const;230 231  SDValue LowerINT_TO_FP(SDValue Op, SelectionDAG &DAG) const;232  SDValue LowerFP_TO_INT(SDValue Op, SelectionDAG &DAG) const;233 234  SDValue LowerFP_ROUND(SDValue Op, SelectionDAG &DAG) const;235  SDValue LowerFP_EXTEND(SDValue Op, SelectionDAG &DAG) const;236 237  SDValue LowerLOAD(SDValue Op, SelectionDAG &DAG) const;238  SDValue LowerMLOAD(SDValue Op, SelectionDAG &DAG) const;239  SDValue LowerSTORE(SDValue Op, SelectionDAG &DAG) const;240  SDValue LowerSTOREi1(SDValue Op, SelectionDAG &DAG) const;241 242  SDValue LowerShiftRightParts(SDValue Op, SelectionDAG &DAG) const;243  SDValue LowerShiftLeftParts(SDValue Op, SelectionDAG &DAG) const;244 245  SDValue LowerBR_JT(SDValue Op, SelectionDAG &DAG) const;246 247  SDValue LowerVAARG(SDValue Op, SelectionDAG &DAG) const;248  SDValue LowerVASTART(SDValue Op, SelectionDAG &DAG) const;249 250  SDValue LowerCopyToReg_128(SDValue Op, SelectionDAG &DAG) const;251  unsigned getNumRegisters(LLVMContext &Context, EVT VT,252                           std::optional<MVT> RegisterVT) const override;253  bool254  splitValueIntoRegisterParts(SelectionDAG &DAG, const SDLoc &DL, SDValue Val,255                              SDValue *Parts, unsigned NumParts, MVT PartVT,256                              std::optional<CallingConv::ID> CC) const override;257 258  void ReplaceNodeResults(SDNode *N, SmallVectorImpl<SDValue> &Results,259                          SelectionDAG &DAG) const override;260  SDValue PerformDAGCombine(SDNode *N, DAGCombinerInfo &DCI) const override;261 262  Align getArgumentAlignment(const CallBase *CB, Type *Ty, unsigned Idx,263                             const DataLayout &DL) const;264};265 266} // namespace llvm267 268#endif269