640 lines · c
1//===-- SIISelLowering.h - SI 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/// \file10/// SI DAG Lowering interface definition11//12//===----------------------------------------------------------------------===//13 14#ifndef LLVM_LIB_TARGET_AMDGPU_SIISELLOWERING_H15#define LLVM_LIB_TARGET_AMDGPU_SIISELLOWERING_H16 17#include "AMDGPUArgumentUsageInfo.h"18#include "AMDGPUISelLowering.h"19#include "SIDefines.h"20#include "llvm/CodeGen/MachineFunction.h"21 22namespace llvm {23 24class GCNSubtarget;25class SIMachineFunctionInfo;26class SIRegisterInfo;27 28namespace AMDGPU {29struct ImageDimIntrinsicInfo;30}31 32class SITargetLowering final : public AMDGPUTargetLowering {33private:34 const GCNSubtarget *Subtarget;35 36public:37 MVT getRegisterTypeForCallingConv(LLVMContext &Context,38 CallingConv::ID CC,39 EVT VT) const override;40 unsigned getNumRegistersForCallingConv(LLVMContext &Context,41 CallingConv::ID CC,42 EVT VT) const override;43 44 unsigned getVectorTypeBreakdownForCallingConv(45 LLVMContext &Context, CallingConv::ID CC, EVT VT, EVT &IntermediateVT,46 unsigned &NumIntermediates, MVT &RegisterVT) const override;47 48private:49 SDValue lowerKernArgParameterPtr(SelectionDAG &DAG, const SDLoc &SL,50 SDValue Chain, uint64_t Offset) const;51 SDValue getImplicitArgPtr(SelectionDAG &DAG, const SDLoc &SL) const;52 SDValue getLDSKernelId(SelectionDAG &DAG, const SDLoc &SL) const;53 SDValue lowerKernargMemParameter(SelectionDAG &DAG, EVT VT, EVT MemVT,54 const SDLoc &SL, SDValue Chain,55 uint64_t Offset, Align Alignment,56 bool Signed,57 const ISD::InputArg *Arg = nullptr) const;58 SDValue loadImplicitKernelArgument(SelectionDAG &DAG, MVT VT, const SDLoc &DL,59 Align Alignment,60 ImplicitParameter Param) const;61 62 SDValue convertABITypeToValueType(SelectionDAG &DAG, SDValue Val,63 CCValAssign &VA, const SDLoc &SL) const;64 65 SDValue lowerStackParameter(SelectionDAG &DAG, CCValAssign &VA,66 const SDLoc &SL, SDValue Chain,67 const ISD::InputArg &Arg) const;68 SDValue lowerWorkGroupId(69 SelectionDAG &DAG, const SIMachineFunctionInfo &MFI, EVT VT,70 AMDGPUFunctionArgInfo::PreloadedValue ClusterIdPV,71 AMDGPUFunctionArgInfo::PreloadedValue ClusterMaxIdPV,72 AMDGPUFunctionArgInfo::PreloadedValue ClusterWorkGroupIdPV) const;73 SDValue getPreloadedValue(SelectionDAG &DAG,74 const SIMachineFunctionInfo &MFI,75 EVT VT,76 AMDGPUFunctionArgInfo::PreloadedValue) const;77 78 SDValue LowerGlobalAddress(AMDGPUMachineFunction *MFI, SDValue Op,79 SelectionDAG &DAG) const override;80 SDValue lowerImplicitZextParam(SelectionDAG &DAG, SDValue Op,81 MVT VT, unsigned Offset) const;82 SDValue lowerImage(SDValue Op, const AMDGPU::ImageDimIntrinsicInfo *Intr,83 SelectionDAG &DAG, bool WithChain) const;84 SDValue lowerSBuffer(EVT VT, SDLoc DL, SDValue Rsrc, SDValue Offset,85 SDValue CachePolicy, SelectionDAG &DAG) const;86 87 SDValue lowerRawBufferAtomicIntrin(SDValue Op, SelectionDAG &DAG,88 unsigned NewOpcode) const;89 SDValue lowerStructBufferAtomicIntrin(SDValue Op, SelectionDAG &DAG,90 unsigned NewOpcode) const;91 92 SDValue lowerWaveID(SelectionDAG &DAG, SDValue Op) const;93 SDValue lowerConstHwRegRead(SelectionDAG &DAG, SDValue Op,94 AMDGPU::Hwreg::Id HwReg, unsigned LowBit,95 unsigned Width) const;96 SDValue lowerWorkitemID(SelectionDAG &DAG, SDValue Op, unsigned Dim,97 const ArgDescriptor &ArgDesc) const;98 99 SDValue LowerINTRINSIC_WO_CHAIN(SDValue Op, SelectionDAG &DAG) const;100 SDValue LowerINTRINSIC_W_CHAIN(SDValue Op, SelectionDAG &DAG) const;101 SDValue LowerINTRINSIC_VOID(SDValue Op, SelectionDAG &DAG) const;102 103 // The raw.tbuffer and struct.tbuffer intrinsics have two offset args: offset104 // (the offset that is included in bounds checking and swizzling, to be split105 // between the instruction's voffset and immoffset fields) and soffset (the106 // offset that is excluded from bounds checking and swizzling, to go in the107 // instruction's soffset field). This function takes the first kind of108 // offset and figures out how to split it between voffset and immoffset.109 std::pair<SDValue, SDValue> splitBufferOffsets(SDValue Offset,110 SelectionDAG &DAG) const;111 112 SDValue widenLoad(LoadSDNode *Ld, DAGCombinerInfo &DCI) const;113 SDValue LowerLOAD(SDValue Op, SelectionDAG &DAG) const;114 SDValue LowerSELECT(SDValue Op, SelectionDAG &DAG) const;115 SDValue lowerFastUnsafeFDIV(SDValue Op, SelectionDAG &DAG) const;116 SDValue lowerFastUnsafeFDIV64(SDValue Op, SelectionDAG &DAG) const;117 SDValue lowerFDIV_FAST(SDValue Op, SelectionDAG &DAG) const;118 SDValue LowerFDIV16(SDValue Op, SelectionDAG &DAG) const;119 SDValue LowerFDIV32(SDValue Op, SelectionDAG &DAG) const;120 SDValue LowerFDIV64(SDValue Op, SelectionDAG &DAG) const;121 SDValue LowerFDIV(SDValue Op, SelectionDAG &DAG) const;122 SDValue LowerFFREXP(SDValue Op, SelectionDAG &DAG) const;123 SDValue LowerSTORE(SDValue Op, SelectionDAG &DAG) const;124 SDValue LowerTrig(SDValue Op, SelectionDAG &DAG) const;125 SDValue lowerFSQRTF16(SDValue Op, SelectionDAG &DAG) const;126 SDValue lowerFSQRTF32(SDValue Op, SelectionDAG &DAG) const;127 SDValue lowerFSQRTF64(SDValue Op, SelectionDAG &DAG) const;128 SDValue LowerATOMIC_CMP_SWAP(SDValue Op, SelectionDAG &DAG) const;129 SDValue LowerBRCOND(SDValue Op, SelectionDAG &DAG) const;130 SDValue LowerRETURNADDR(SDValue Op, SelectionDAG &DAG) const;131 SDValue adjustLoadValueType(unsigned Opcode, MemSDNode *M,132 SelectionDAG &DAG, ArrayRef<SDValue> Ops,133 bool IsIntrinsic = false) const;134 135 SDValue lowerIntrinsicLoad(MemSDNode *M, bool IsFormat, SelectionDAG &DAG,136 ArrayRef<SDValue> Ops) const;137 138 // Call DAG.getMemIntrinsicNode for a load, but first widen a dwordx3 type to139 // dwordx4 if on SI.140 SDValue getMemIntrinsicNode(unsigned Opcode, const SDLoc &DL, SDVTList VTList,141 ArrayRef<SDValue> Ops, EVT MemVT,142 MachineMemOperand *MMO, SelectionDAG &DAG) const;143 144 SDValue handleD16VData(SDValue VData, SelectionDAG &DAG,145 bool ImageStore = false) const;146 147 /// Converts \p Op, which must be of floating point type, to the148 /// floating point type \p VT, by either extending or truncating it.149 SDValue getFPExtOrFPRound(SelectionDAG &DAG,150 SDValue Op,151 const SDLoc &DL,152 EVT VT) const;153 154 SDValue convertArgType(155 SelectionDAG &DAG, EVT VT, EVT MemVT, const SDLoc &SL, SDValue Val,156 bool Signed, const ISD::InputArg *Arg = nullptr) const;157 158 /// Custom lowering for ISD::FP_ROUND for MVT::f16.159 SDValue lowerFP_ROUND(SDValue Op, SelectionDAG &DAG) const;160 SDValue splitFP_ROUNDVectorOp(SDValue Op, SelectionDAG &DAG) const;161 SDValue lowerFMINNUM_FMAXNUM(SDValue Op, SelectionDAG &DAG) const;162 SDValue lowerFMINIMUMNUM_FMAXIMUMNUM(SDValue Op, SelectionDAG &DAG) const;163 SDValue lowerFMINIMUM_FMAXIMUM(SDValue Op, SelectionDAG &DAG) const;164 SDValue lowerFLDEXP(SDValue Op, SelectionDAG &DAG) const;165 SDValue promoteUniformOpToI32(SDValue Op, DAGCombinerInfo &DCI) const;166 SDValue lowerFCOPYSIGN(SDValue Op, SelectionDAG &DAG) const;167 SDValue lowerMUL(SDValue Op, SelectionDAG &DAG) const;168 SDValue lowerXMULO(SDValue Op, SelectionDAG &DAG) const;169 SDValue lowerXMUL_LOHI(SDValue Op, SelectionDAG &DAG) const;170 171 SDValue getSegmentAperture(unsigned AS, const SDLoc &DL,172 SelectionDAG &DAG) const;173 174 SDValue lowerADDRSPACECAST(SDValue Op, SelectionDAG &DAG) const;175 SDValue lowerINSERT_SUBVECTOR(SDValue Op, SelectionDAG &DAG) const;176 SDValue lowerINSERT_VECTOR_ELT(SDValue Op, SelectionDAG &DAG) const;177 SDValue lowerEXTRACT_VECTOR_ELT(SDValue Op, SelectionDAG &DAG) const;178 SDValue lowerVECTOR_SHUFFLE(SDValue Op, SelectionDAG &DAG) const;179 SDValue lowerSCALAR_TO_VECTOR(SDValue Op, SelectionDAG &DAG) const;180 SDValue lowerBUILD_VECTOR(SDValue Op, SelectionDAG &DAG) const;181 182 SDValue lowerTRAP(SDValue Op, SelectionDAG &DAG) const;183 SDValue lowerTrapEndpgm(SDValue Op, SelectionDAG &DAG) const;184 SDValue lowerTrapHsaQueuePtr(SDValue Op, SelectionDAG &DAG) const;185 SDValue lowerTrapHsa(SDValue Op, SelectionDAG &DAG) const;186 SDValue lowerDEBUGTRAP(SDValue Op, SelectionDAG &DAG) const;187 188 SDNode *adjustWritemask(MachineSDNode *&N, SelectionDAG &DAG) const;189 190 SDValue performUCharToFloatCombine(SDNode *N,191 DAGCombinerInfo &DCI) const;192 SDValue performFCopySignCombine(SDNode *N, DAGCombinerInfo &DCI) const;193 194 SDValue performSHLPtrCombine(SDNode *N,195 unsigned AS,196 EVT MemVT,197 DAGCombinerInfo &DCI) const;198 199 SDValue performMemSDNodeCombine(MemSDNode *N, DAGCombinerInfo &DCI) const;200 201 SDValue splitBinaryBitConstantOp(DAGCombinerInfo &DCI, const SDLoc &SL,202 unsigned Opc, SDValue LHS,203 const ConstantSDNode *CRHS) const;204 205 SDValue performAndCombine(SDNode *N, DAGCombinerInfo &DCI) const;206 SDValue performOrCombine(SDNode *N, DAGCombinerInfo &DCI) const;207 SDValue performXorCombine(SDNode *N, DAGCombinerInfo &DCI) const;208 SDValue performZeroExtendCombine(SDNode *N, DAGCombinerInfo &DCI) const;209 SDValue performSignExtendInRegCombine(SDNode *N, DAGCombinerInfo &DCI) const;210 SDValue performClassCombine(SDNode *N, DAGCombinerInfo &DCI) const;211 SDValue getCanonicalConstantFP(SelectionDAG &DAG, const SDLoc &SL, EVT VT,212 const APFloat &C) const;213 SDValue performFCanonicalizeCombine(SDNode *N, DAGCombinerInfo &DCI) const;214 215 SDValue performFPMed3ImmCombine(SelectionDAG &DAG, const SDLoc &SL,216 SDValue Op0, SDValue Op1) const;217 SDValue performIntMed3ImmCombine(SelectionDAG &DAG, const SDLoc &SL,218 SDValue Src, SDValue MinVal, SDValue MaxVal,219 bool Signed) const;220 SDValue performMinMaxCombine(SDNode *N, DAGCombinerInfo &DCI) const;221 SDValue performFMed3Combine(SDNode *N, DAGCombinerInfo &DCI) const;222 SDValue performCvtPkRTZCombine(SDNode *N, DAGCombinerInfo &DCI) const;223 SDValue performExtractVectorEltCombine(SDNode *N, DAGCombinerInfo &DCI) const;224 SDValue performInsertVectorEltCombine(SDNode *N, DAGCombinerInfo &DCI) const;225 SDValue performFPRoundCombine(SDNode *N, DAGCombinerInfo &DCI) const;226 SDValue performSelectCombine(SDNode *N, DAGCombinerInfo &DCI) const;227 228 SDValue reassociateScalarOps(SDNode *N, SelectionDAG &DAG) const;229 unsigned getFusedOpcode(const SelectionDAG &DAG,230 const SDNode *N0, const SDNode *N1) const;231 SDValue tryFoldToMad64_32(SDNode *N, DAGCombinerInfo &DCI) const;232 SDValue foldAddSub64WithZeroLowBitsTo32(SDNode *N,233 DAGCombinerInfo &DCI) const;234 235 SDValue performAddCombine(SDNode *N, DAGCombinerInfo &DCI) const;236 SDValue performPtrAddCombine(SDNode *N, DAGCombinerInfo &DCI) const;237 SDValue performAddCarrySubCarryCombine(SDNode *N, DAGCombinerInfo &DCI) const;238 SDValue performSubCombine(SDNode *N, DAGCombinerInfo &DCI) const;239 SDValue performFAddCombine(SDNode *N, DAGCombinerInfo &DCI) const;240 SDValue performFSubCombine(SDNode *N, DAGCombinerInfo &DCI) const;241 SDValue performFDivCombine(SDNode *N, DAGCombinerInfo &DCI) const;242 SDValue performFMulCombine(SDNode *N, DAGCombinerInfo &DCI) const;243 SDValue performFMACombine(SDNode *N, DAGCombinerInfo &DCI) const;244 SDValue performSetCCCombine(SDNode *N, DAGCombinerInfo &DCI) const;245 SDValue performCvtF32UByteNCombine(SDNode *N, DAGCombinerInfo &DCI) const;246 SDValue performClampCombine(SDNode *N, DAGCombinerInfo &DCI) const;247 SDValue performRcpCombine(SDNode *N, DAGCombinerInfo &DCI) const;248 249 bool isLegalMUBUFAddressingMode(const AddrMode &AM) const;250 251 unsigned isCFIntrinsic(const SDNode *Intr) const;252 253public:254 /// \returns True if fixup needs to be emitted for given global value \p GV,255 /// false otherwise.256 bool shouldEmitFixup(const GlobalValue *GV) const;257 258 /// \returns True if GOT relocation needs to be emitted for given global value259 /// \p GV, false otherwise.260 bool shouldEmitGOTReloc(const GlobalValue *GV) const;261 262 /// \returns True if PC-relative relocation needs to be emitted for given263 /// global value \p GV, false otherwise.264 bool shouldEmitPCReloc(const GlobalValue *GV) const;265 266 /// \returns true if this should use a literal constant for an LDS address,267 /// and not emit a relocation for an LDS global.268 bool shouldUseLDSConstAddress(const GlobalValue *GV) const;269 270 /// Check if EXTRACT_VECTOR_ELT/INSERT_VECTOR_ELT (<n x e>, var-idx) should be271 /// expanded into a set of cmp/select instructions.272 static bool shouldExpandVectorDynExt(unsigned EltSize, unsigned NumElem,273 bool IsDivergentIdx,274 const GCNSubtarget *Subtarget);275 276 bool shouldExpandVectorDynExt(SDNode *N) const;277 278 bool shouldPreservePtrArith(const Function &F, EVT PtrVT) const override;279 280 bool canTransformPtrArithOutOfBounds(const Function &F,281 EVT PtrVT) const override;282 283private:284 // Analyze a combined offset from an amdgcn_s_buffer_load intrinsic and store285 // the three offsets (voffset, soffset and instoffset) into the SDValue[3]286 // array pointed to by Offsets.287 void setBufferOffsets(SDValue CombinedOffset, SelectionDAG &DAG,288 SDValue *Offsets, Align Alignment = Align(4)) const;289 290 // Convert the i128 that an addrspace(8) pointer is natively represented as291 // into the v4i32 that all the buffer intrinsics expect to receive. We can't292 // add register classes for i128 on pain of the promotion logic going haywire,293 // so this slightly ugly hack is what we've got. If passed a non-pointer294 // argument (as would be seen in older buffer intrinsics), does nothing.295 SDValue bufferRsrcPtrToVector(SDValue MaybePointer, SelectionDAG &DAG) const;296 297 // Wrap a 64-bit pointer into a v4i32 (which is how all SelectionDAG code298 // represents ptr addrspace(8)) using the flags specified in the intrinsic.299 SDValue lowerPointerAsRsrcIntrin(SDNode *Op, SelectionDAG &DAG) const;300 301 // Handle 8 bit and 16 bit buffer loads302 SDValue handleByteShortBufferLoads(SelectionDAG &DAG, EVT LoadVT, SDLoc DL,303 ArrayRef<SDValue> Ops,304 MachineMemOperand *MMO,305 bool IsTFE = false) const;306 307 // Handle 8 bit and 16 bit buffer stores308 SDValue handleByteShortBufferStores(SelectionDAG &DAG, EVT VDataType,309 SDLoc DL, SDValue Ops[],310 MemSDNode *M) const;311 312public:313 SITargetLowering(const TargetMachine &tm, const GCNSubtarget &STI);314 315 const GCNSubtarget *getSubtarget() const;316 317 ArrayRef<MCPhysReg> getRoundingControlRegisters() const override;318 319 bool isFPExtFoldable(const SelectionDAG &DAG, unsigned Opcode, EVT DestVT,320 EVT SrcVT) const override;321 322 bool isFPExtFoldable(const MachineInstr &MI, unsigned Opcode, LLT DestTy,323 LLT SrcTy) const override;324 325 bool isShuffleMaskLegal(ArrayRef<int> /*Mask*/, EVT /*VT*/) const override;326 327 // While address space 7 should never make it to codegen, it still needs to328 // have a MVT to prevent some analyses that query this function from breaking.329 // We use the custum MVT::amdgpuBufferFatPointer and330 // amdgpu::amdgpuBufferStridedPointer for this, though we use v8i32 for the331 // memory type (which is probably unused).332 MVT getPointerTy(const DataLayout &DL, unsigned AS) const override;333 MVT getPointerMemTy(const DataLayout &DL, unsigned AS) const override;334 335 bool getTgtMemIntrinsic(IntrinsicInfo &, const CallInst &,336 MachineFunction &MF,337 unsigned IntrinsicID) const override;338 339 void CollectTargetIntrinsicOperands(const CallInst &I,340 SmallVectorImpl<SDValue> &Ops,341 SelectionDAG &DAG) const override;342 343 bool getAddrModeArguments(const IntrinsicInst *I,344 SmallVectorImpl<Value *> &Ops,345 Type *&AccessTy) const override;346 347 bool isLegalFlatAddressingMode(const AddrMode &AM, unsigned AddrSpace) const;348 bool isLegalGlobalAddressingMode(const AddrMode &AM) const;349 bool isLegalAddressingMode(const DataLayout &DL, const AddrMode &AM, Type *Ty,350 unsigned AS,351 Instruction *I = nullptr) const override;352 353 bool canMergeStoresTo(unsigned AS, EVT MemVT,354 const MachineFunction &MF) const override;355 356 bool allowsMisalignedMemoryAccessesImpl(357 unsigned Size, unsigned AddrSpace, Align Alignment,358 MachineMemOperand::Flags Flags = MachineMemOperand::MONone,359 unsigned *IsFast = nullptr) const;360 361 bool allowsMisalignedMemoryAccesses(362 LLT Ty, unsigned AddrSpace, Align Alignment,363 MachineMemOperand::Flags Flags = MachineMemOperand::MONone,364 unsigned *IsFast = nullptr) const override {365 if (IsFast)366 *IsFast = 0;367 return allowsMisalignedMemoryAccessesImpl(Ty.getSizeInBits(), AddrSpace,368 Alignment, Flags, IsFast);369 }370 371 bool allowsMisalignedMemoryAccesses(372 EVT VT, unsigned AS, Align Alignment,373 MachineMemOperand::Flags Flags = MachineMemOperand::MONone,374 unsigned *IsFast = nullptr) const override;375 376 EVT getOptimalMemOpType(LLVMContext &Context, const MemOp &Op,377 const AttributeList &FuncAttributes) const override;378 379 bool isMemOpHasNoClobberedMemOperand(const SDNode *N) const;380 381 static bool isNonGlobalAddrSpace(unsigned AS);382 383 bool isFreeAddrSpaceCast(unsigned SrcAS, unsigned DestAS) const override;384 385 TargetLoweringBase::LegalizeTypeAction386 getPreferredVectorAction(MVT VT) const override;387 388 bool shouldConvertConstantLoadToIntImm(const APInt &Imm,389 Type *Ty) const override;390 391 bool isExtractSubvectorCheap(EVT ResVT, EVT SrcVT,392 unsigned Index) const override;393 bool isExtractVecEltCheap(EVT VT, unsigned Index) const override;394 395 bool isTypeDesirableForOp(unsigned Op, EVT VT) const override;396 397 bool isOffsetFoldingLegal(const GlobalAddressSDNode *GA) const override;398 399 unsigned combineRepeatedFPDivisors() const override {400 // Combine multiple FDIVs with the same divisor into multiple FMULs by the401 // reciprocal.402 return 2;403 }404 405 bool supportSplitCSR(MachineFunction *MF) const override;406 void initializeSplitCSR(MachineBasicBlock *Entry) const override;407 void insertCopiesSplitCSR(408 MachineBasicBlock *Entry,409 const SmallVectorImpl<MachineBasicBlock *> &Exits) const override;410 411 SDValue LowerFormalArguments(SDValue Chain, CallingConv::ID CallConv,412 bool isVarArg,413 const SmallVectorImpl<ISD::InputArg> &Ins,414 const SDLoc &DL, SelectionDAG &DAG,415 SmallVectorImpl<SDValue> &InVals) const override;416 417 bool CanLowerReturn(CallingConv::ID CallConv,418 MachineFunction &MF, bool isVarArg,419 const SmallVectorImpl<ISD::OutputArg> &Outs,420 LLVMContext &Context, const Type *RetTy) const override;421 422 SDValue LowerReturn(SDValue Chain, CallingConv::ID CallConv, bool IsVarArg,423 const SmallVectorImpl<ISD::OutputArg> &Outs,424 const SmallVectorImpl<SDValue> &OutVals, const SDLoc &DL,425 SelectionDAG &DAG) const override;426 427 void passSpecialInputs(428 CallLoweringInfo &CLI,429 CCState &CCInfo,430 const SIMachineFunctionInfo &Info,431 SmallVectorImpl<std::pair<unsigned, SDValue>> &RegsToPass,432 SmallVectorImpl<SDValue> &MemOpChains,433 SDValue Chain) const;434 435 SDValue LowerCallResult(SDValue Chain, SDValue InGlue,436 CallingConv::ID CallConv, bool isVarArg,437 const SmallVectorImpl<ISD::InputArg> &Ins,438 const SDLoc &DL, SelectionDAG &DAG,439 SmallVectorImpl<SDValue> &InVals, bool isThisReturn,440 SDValue ThisVal) const;441 442 bool mayBeEmittedAsTailCall(const CallInst *) const override;443 444 bool isEligibleForTailCallOptimization(445 SDValue Callee, CallingConv::ID CalleeCC, bool isVarArg,446 const SmallVectorImpl<ISD::OutputArg> &Outs,447 const SmallVectorImpl<SDValue> &OutVals,448 const SmallVectorImpl<ISD::InputArg> &Ins, SelectionDAG &DAG) const;449 450 SDValue LowerCall(CallLoweringInfo &CLI,451 SmallVectorImpl<SDValue> &InVals) const override;452 453 SDValue LowerDYNAMIC_STACKALLOC(SDValue Op, SelectionDAG &DAG) const;454 SDValue LowerSTACKSAVE(SDValue Op, SelectionDAG &DAG) const;455 SDValue lowerGET_ROUNDING(SDValue Op, SelectionDAG &DAG) const;456 SDValue lowerSET_ROUNDING(SDValue Op, SelectionDAG &DAG) const;457 458 SDValue lowerPREFETCH(SDValue Op, SelectionDAG &DAG) const;459 SDValue lowerFP_EXTEND(SDValue Op, SelectionDAG &DAG) const;460 SDValue lowerGET_FPENV(SDValue Op, SelectionDAG &DAG) const;461 SDValue lowerSET_FPENV(SDValue Op, SelectionDAG &DAG) const;462 SDValue lowerROTR(SDValue Op, SelectionDAG &DAG) const;463 464 Register getRegisterByName(const char* RegName, LLT VT,465 const MachineFunction &MF) const override;466 467 MachineBasicBlock *splitKillBlock(MachineInstr &MI,468 MachineBasicBlock *BB) const;469 470 void bundleInstWithWaitcnt(MachineInstr &MI) const;471 MachineBasicBlock *emitGWSMemViolTestLoop(MachineInstr &MI,472 MachineBasicBlock *BB) const;473 474 MachineBasicBlock *475 EmitInstrWithCustomInserter(MachineInstr &MI,476 MachineBasicBlock *BB) const override;477 478 bool enableAggressiveFMAFusion(EVT VT) const override;479 bool enableAggressiveFMAFusion(LLT Ty) const override;480 EVT getSetCCResultType(const DataLayout &DL, LLVMContext &Context,481 EVT VT) const override;482 MVT getScalarShiftAmountTy(const DataLayout &, EVT) const override;483 LLT getPreferredShiftAmountTy(LLT Ty) const override;484 485 bool isFMAFasterThanFMulAndFAdd(const MachineFunction &MF,486 EVT VT) const override;487 bool isFMAFasterThanFMulAndFAdd(const MachineFunction &MF,488 const LLT Ty) const override;489 bool isFMADLegal(const SelectionDAG &DAG, const SDNode *N) const override;490 bool isFMADLegal(const MachineInstr &MI, const LLT Ty) const override;491 492 SDValue splitUnaryVectorOp(SDValue Op, SelectionDAG &DAG) const;493 SDValue splitBinaryVectorOp(SDValue Op, SelectionDAG &DAG) const;494 SDValue splitTernaryVectorOp(SDValue Op, SelectionDAG &DAG) const;495 SDValue LowerOperation(SDValue Op, SelectionDAG &DAG) const override;496 void ReplaceNodeResults(SDNode *N, SmallVectorImpl<SDValue> &Results,497 SelectionDAG &DAG) const override;498 499 SDValue PerformDAGCombine(SDNode *N, DAGCombinerInfo &DCI) const override;500 SDNode *PostISelFolding(MachineSDNode *N, SelectionDAG &DAG) const override;501 void AddMemOpInit(MachineInstr &MI) const;502 void AdjustInstrPostInstrSelection(MachineInstr &MI,503 SDNode *Node) const override;504 505 SDNode *legalizeTargetIndependentNode(SDNode *Node, SelectionDAG &DAG) const;506 507 MachineSDNode *wrapAddr64Rsrc(SelectionDAG &DAG, const SDLoc &DL,508 SDValue Ptr) const;509 MachineSDNode *buildRSRC(SelectionDAG &DAG, const SDLoc &DL, SDValue Ptr,510 uint32_t RsrcDword1, uint64_t RsrcDword2And3) const;511 std::pair<unsigned, const TargetRegisterClass *>512 getRegForInlineAsmConstraint(const TargetRegisterInfo *TRI,513 StringRef Constraint, MVT VT) const override;514 ConstraintType getConstraintType(StringRef Constraint) const override;515 void LowerAsmOperandForConstraint(SDValue Op, StringRef Constraint,516 std::vector<SDValue> &Ops,517 SelectionDAG &DAG) const override;518 bool getAsmOperandConstVal(SDValue Op, uint64_t &Val) const;519 bool checkAsmConstraintVal(SDValue Op, StringRef Constraint,520 uint64_t Val) const;521 bool checkAsmConstraintValA(SDValue Op,522 uint64_t Val,523 unsigned MaxSize = 64) const;524 SDValue copyToM0(SelectionDAG &DAG, SDValue Chain, const SDLoc &DL,525 SDValue V) const;526 527 void finalizeLowering(MachineFunction &MF) const override;528 529 void computeKnownBitsForTargetNode(const SDValue Op, KnownBits &Known,530 const APInt &DemandedElts,531 const SelectionDAG &DAG,532 unsigned Depth = 0) const override;533 void computeKnownBitsForFrameIndex(int FrameIdx,534 KnownBits &Known,535 const MachineFunction &MF) const override;536 void computeKnownBitsForTargetInstr(GISelValueTracking &Analysis, Register R,537 KnownBits &Known,538 const APInt &DemandedElts,539 const MachineRegisterInfo &MRI,540 unsigned Depth = 0) const override;541 542 Align computeKnownAlignForTargetInstr(GISelValueTracking &Analysis,543 Register R,544 const MachineRegisterInfo &MRI,545 unsigned Depth = 0) const override;546 bool isSDNodeSourceOfDivergence(const SDNode *N, FunctionLoweringInfo *FLI,547 UniformityInfo *UA) const override;548 549 bool hasMemSDNodeUser(SDNode *N) const;550 551 bool isReassocProfitable(SelectionDAG &DAG, SDValue N0,552 SDValue N1) const override;553 554 bool isReassocProfitable(MachineRegisterInfo &MRI, Register N0,555 Register N1) const override;556 557 bool isCanonicalized(SelectionDAG &DAG, SDValue Op,558 unsigned MaxDepth = 5) const;559 bool isCanonicalized(Register Reg, const MachineFunction &MF,560 unsigned MaxDepth = 5) const;561 bool denormalsEnabledForType(const SelectionDAG &DAG, EVT VT) const;562 bool denormalsEnabledForType(LLT Ty, const MachineFunction &MF) const;563 564 bool isKnownNeverNaNForTargetNode(SDValue Op, const APInt &DemandedElts,565 const SelectionDAG &DAG, bool SNaN = false,566 unsigned Depth = 0) const override;567 AtomicExpansionKind shouldExpandAtomicRMWInIR(AtomicRMWInst *) const override;568 AtomicExpansionKind shouldExpandAtomicLoadInIR(LoadInst *LI) const override;569 AtomicExpansionKind shouldExpandAtomicStoreInIR(StoreInst *SI) const override;570 AtomicExpansionKind571 shouldExpandAtomicCmpXchgInIR(AtomicCmpXchgInst *AI) const override;572 573 void emitExpandAtomicAddrSpacePredicate(Instruction *AI) const;574 void emitExpandAtomicRMW(AtomicRMWInst *AI) const override;575 void emitExpandAtomicCmpXchg(AtomicCmpXchgInst *CI) const override;576 void emitExpandAtomicLoad(LoadInst *LI) const override;577 void emitExpandAtomicStore(StoreInst *SI) const override;578 579 LoadInst *580 lowerIdempotentRMWIntoFencedLoad(AtomicRMWInst *AI) const override;581 582 const TargetRegisterClass *getRegClassFor(MVT VT,583 bool isDivergent) const override;584 bool requiresUniformRegister(MachineFunction &MF,585 const Value *V) const override;586 Align getPrefLoopAlignment(MachineLoop *ML) const override;587 588 void allocateHSAUserSGPRs(CCState &CCInfo,589 MachineFunction &MF,590 const SIRegisterInfo &TRI,591 SIMachineFunctionInfo &Info) const;592 593 void allocatePreloadKernArgSGPRs(CCState &CCInfo,594 SmallVectorImpl<CCValAssign> &ArgLocs,595 const SmallVectorImpl<ISD::InputArg> &Ins,596 MachineFunction &MF,597 const SIRegisterInfo &TRI,598 SIMachineFunctionInfo &Info) const;599 600 void allocateLDSKernelId(CCState &CCInfo, MachineFunction &MF,601 const SIRegisterInfo &TRI,602 SIMachineFunctionInfo &Info) const;603 604 void allocateSystemSGPRs(CCState &CCInfo,605 MachineFunction &MF,606 SIMachineFunctionInfo &Info,607 CallingConv::ID CallConv,608 bool IsShader) const;609 610 void allocateSpecialEntryInputVGPRs(CCState &CCInfo,611 MachineFunction &MF,612 const SIRegisterInfo &TRI,613 SIMachineFunctionInfo &Info) const;614 void allocateSpecialInputSGPRs(615 CCState &CCInfo,616 MachineFunction &MF,617 const SIRegisterInfo &TRI,618 SIMachineFunctionInfo &Info) const;619 620 void allocateSpecialInputVGPRs(CCState &CCInfo,621 MachineFunction &MF,622 const SIRegisterInfo &TRI,623 SIMachineFunctionInfo &Info) const;624 void allocateSpecialInputVGPRsFixed(CCState &CCInfo,625 MachineFunction &MF,626 const SIRegisterInfo &TRI,627 SIMachineFunctionInfo &Info) const;628 629 MachineMemOperand::Flags630 getTargetMMOFlags(const Instruction &I) const override;631};632 633// Returns true if argument is a boolean value which is not serialized into634// memory or argument and does not require v_cndmask_b32 to be deserialized.635bool isBoolSGPR(SDValue V);636 637} // End namespace llvm638 639#endif640