xref: /freebsd/contrib/llvm-project/llvm/lib/Target/PowerPC/PPCTargetTransformInfo.h (revision 0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583)
10b57cec5SDimitry Andric //===-- PPCTargetTransformInfo.h - PPC specific TTI -------------*- C++ -*-===//
20b57cec5SDimitry Andric //
30b57cec5SDimitry Andric // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
40b57cec5SDimitry Andric // See https://llvm.org/LICENSE.txt for license information.
50b57cec5SDimitry Andric // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
60b57cec5SDimitry Andric //
70b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
80b57cec5SDimitry Andric /// \file
90b57cec5SDimitry Andric /// This file a TargetTransformInfo::Concept conforming object specific to the
100b57cec5SDimitry Andric /// PPC target machine. It uses the target's detailed information to
110b57cec5SDimitry Andric /// provide more precise answers to certain TTI queries, while letting the
120b57cec5SDimitry Andric /// target independent and default TTI implementations handle the rest.
130b57cec5SDimitry Andric ///
140b57cec5SDimitry Andric //===----------------------------------------------------------------------===//
150b57cec5SDimitry Andric 
160b57cec5SDimitry Andric #ifndef LLVM_LIB_TARGET_POWERPC_PPCTARGETTRANSFORMINFO_H
170b57cec5SDimitry Andric #define LLVM_LIB_TARGET_POWERPC_PPCTARGETTRANSFORMINFO_H
180b57cec5SDimitry Andric 
190b57cec5SDimitry Andric #include "PPCTargetMachine.h"
200b57cec5SDimitry Andric #include "llvm/Analysis/TargetTransformInfo.h"
210b57cec5SDimitry Andric #include "llvm/CodeGen/BasicTTIImpl.h"
220b57cec5SDimitry Andric #include "llvm/CodeGen/TargetLowering.h"
23bdd1243dSDimitry Andric #include <optional>
240b57cec5SDimitry Andric 
250b57cec5SDimitry Andric namespace llvm {
260b57cec5SDimitry Andric 
270b57cec5SDimitry Andric class PPCTTIImpl : public BasicTTIImplBase<PPCTTIImpl> {
280b57cec5SDimitry Andric   typedef BasicTTIImplBase<PPCTTIImpl> BaseT;
290b57cec5SDimitry Andric   typedef TargetTransformInfo TTI;
300b57cec5SDimitry Andric   friend BaseT;
310b57cec5SDimitry Andric 
320b57cec5SDimitry Andric   const PPCSubtarget *ST;
330b57cec5SDimitry Andric   const PPCTargetLowering *TLI;
340b57cec5SDimitry Andric 
getST()350b57cec5SDimitry Andric   const PPCSubtarget *getST() const { return ST; }
getTLI()360b57cec5SDimitry Andric   const PPCTargetLowering *getTLI() const { return TLI; }
370b57cec5SDimitry Andric 
380b57cec5SDimitry Andric public:
PPCTTIImpl(const PPCTargetMachine * TM,const Function & F)390b57cec5SDimitry Andric   explicit PPCTTIImpl(const PPCTargetMachine *TM, const Function &F)
40*0fca6ea1SDimitry Andric       : BaseT(TM, F.getDataLayout()), ST(TM->getSubtargetImpl(F)),
410b57cec5SDimitry Andric         TLI(ST->getTargetLowering()) {}
420b57cec5SDimitry Andric 
43bdd1243dSDimitry Andric   std::optional<Instruction *> instCombineIntrinsic(InstCombiner & IC,
44e8d8bef9SDimitry Andric                                                     IntrinsicInst & II) const;
45e8d8bef9SDimitry Andric 
460b57cec5SDimitry Andric   /// \name Scalar TTI Implementations
470b57cec5SDimitry Andric   /// @{
480b57cec5SDimitry Andric 
490b57cec5SDimitry Andric   using BaseT::getIntImmCost;
50fe6060f1SDimitry Andric   InstructionCost getIntImmCost(const APInt &Imm, Type *Ty,
515ffd83dbSDimitry Andric                                 TTI::TargetCostKind CostKind);
520b57cec5SDimitry Andric 
53fe6060f1SDimitry Andric   InstructionCost getIntImmCostInst(unsigned Opcode, unsigned Idx,
54fe6060f1SDimitry Andric                                     const APInt &Imm, Type *Ty,
55fe6060f1SDimitry Andric                                     TTI::TargetCostKind CostKind,
56e8d8bef9SDimitry Andric                                     Instruction *Inst = nullptr);
57fe6060f1SDimitry Andric   InstructionCost getIntImmCostIntrin(Intrinsic::ID IID, unsigned Idx,
58fe6060f1SDimitry Andric                                       const APInt &Imm, Type *Ty,
59fe6060f1SDimitry Andric                                       TTI::TargetCostKind CostKind);
600b57cec5SDimitry Andric 
61bdd1243dSDimitry Andric   InstructionCost getInstructionCost(const User *U,
62bdd1243dSDimitry Andric                                      ArrayRef<const Value *> Operands,
635ffd83dbSDimitry Andric                                      TTI::TargetCostKind CostKind);
640b57cec5SDimitry Andric 
650b57cec5SDimitry Andric   TTI::PopcntSupportKind getPopcntSupport(unsigned TyWidth);
660b57cec5SDimitry Andric   bool isHardwareLoopProfitable(Loop *L, ScalarEvolution &SE,
670b57cec5SDimitry Andric                                 AssumptionCache &AC,
680b57cec5SDimitry Andric                                 TargetLibraryInfo *LibInfo,
690b57cec5SDimitry Andric                                 HardwareLoopInfo &HWLoopInfo);
700b57cec5SDimitry Andric   bool canSaveCmp(Loop *L, BranchInst **BI, ScalarEvolution *SE, LoopInfo *LI,
710b57cec5SDimitry Andric                   DominatorTree *DT, AssumptionCache *AC,
720b57cec5SDimitry Andric                   TargetLibraryInfo *LibInfo);
73e8d8bef9SDimitry Andric   bool getTgtMemIntrinsic(IntrinsicInst *Inst, MemIntrinsicInfo &Info);
740b57cec5SDimitry Andric   void getUnrollingPreferences(Loop *L, ScalarEvolution &SE,
75349cc55cSDimitry Andric                                TTI::UnrollingPreferences &UP,
76349cc55cSDimitry Andric                                OptimizationRemarkEmitter *ORE);
775ffd83dbSDimitry Andric   void getPeelingPreferences(Loop *L, ScalarEvolution &SE,
785ffd83dbSDimitry Andric                              TTI::PeelingPreferences &PP);
7981ad6265SDimitry Andric   bool isLSRCostLess(const TargetTransformInfo::LSRCost &C1,
8081ad6265SDimitry Andric                      const TargetTransformInfo::LSRCost &C2);
81e8d8bef9SDimitry Andric   bool isNumRegsMajorCostOfLSR();
82fe6060f1SDimitry Andric   bool shouldBuildRelLookupTables() const;
830b57cec5SDimitry Andric   /// @}
840b57cec5SDimitry Andric 
850b57cec5SDimitry Andric   /// \name Vector TTI Implementations
860b57cec5SDimitry Andric   /// @{
870b57cec5SDimitry Andric   bool useColdCCForColdCall(Function &F);
880b57cec5SDimitry Andric   bool enableAggressiveInterleaving(bool LoopHasReductions);
890b57cec5SDimitry Andric   TTI::MemCmpExpansionOptions enableMemCmpExpansion(bool OptSize,
900b57cec5SDimitry Andric                                                     bool IsZeroCmp) const;
910b57cec5SDimitry Andric   bool enableInterleavedAccessVectorization();
928bcb0991SDimitry Andric 
938bcb0991SDimitry Andric   enum PPCRegisterClass {
948bcb0991SDimitry Andric     GPRRC, FPRRC, VRRC, VSXRC
958bcb0991SDimitry Andric   };
968bcb0991SDimitry Andric   unsigned getNumberOfRegisters(unsigned ClassID) const;
978bcb0991SDimitry Andric   unsigned getRegisterClassForType(bool Vector, Type *Ty = nullptr) const;
988bcb0991SDimitry Andric   const char* getRegisterClassName(unsigned ClassID) const;
99fe6060f1SDimitry Andric   TypeSize getRegisterBitWidth(TargetTransformInfo::RegisterKind K) const;
1008bcb0991SDimitry Andric   unsigned getCacheLineSize() const override;
1018bcb0991SDimitry Andric   unsigned getPrefetchDistance() const override;
10206c3fb27SDimitry Andric   unsigned getMaxInterleaveFactor(ElementCount VF);
1034824e7fdSDimitry Andric   InstructionCost vectorCostAdjustmentFactor(unsigned Opcode, Type *Ty1,
1044824e7fdSDimitry Andric                                              Type *Ty2);
105fe6060f1SDimitry Andric   InstructionCost getArithmeticInstrCost(
106349cc55cSDimitry Andric       unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind,
107bdd1243dSDimitry Andric       TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None},
108bdd1243dSDimitry Andric       TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None},
109*0fca6ea1SDimitry Andric       ArrayRef<const Value *> Args = std::nullopt,
110480093f4SDimitry Andric       const Instruction *CxtI = nullptr);
111fe6060f1SDimitry Andric   InstructionCost getShuffleCost(TTI::ShuffleKind Kind, Type *Tp,
112bdd1243dSDimitry Andric                                  ArrayRef<int> Mask,
113bdd1243dSDimitry Andric                                  TTI::TargetCostKind CostKind, int Index,
114bdd1243dSDimitry Andric                                  Type *SubTp,
115*0fca6ea1SDimitry Andric                                  ArrayRef<const Value *> Args = std::nullopt,
116*0fca6ea1SDimitry Andric                                  const Instruction *CxtI = nullptr);
117fe6060f1SDimitry Andric   InstructionCost getCastInstrCost(unsigned Opcode, Type *Dst, Type *Src,
118fe6060f1SDimitry Andric                                    TTI::CastContextHint CCH,
119fe6060f1SDimitry Andric                                    TTI::TargetCostKind CostKind,
1200b57cec5SDimitry Andric                                    const Instruction *I = nullptr);
121fe6060f1SDimitry Andric   InstructionCost getCFInstrCost(unsigned Opcode, TTI::TargetCostKind CostKind,
122fe6060f1SDimitry Andric                                  const Instruction *I = nullptr);
123fe6060f1SDimitry Andric   InstructionCost getCmpSelInstrCost(unsigned Opcode, Type *ValTy, Type *CondTy,
124e8d8bef9SDimitry Andric                                      CmpInst::Predicate VecPred,
1255ffd83dbSDimitry Andric                                      TTI::TargetCostKind CostKind,
1260b57cec5SDimitry Andric                                      const Instruction *I = nullptr);
127bdd1243dSDimitry Andric   using BaseT::getVectorInstrCost;
128fe6060f1SDimitry Andric   InstructionCost getVectorInstrCost(unsigned Opcode, Type *Val,
1295ffd83dbSDimitry Andric                                      TTI::TargetCostKind CostKind,
130bdd1243dSDimitry Andric                                      unsigned Index, Value *Op0, Value *Op1);
131bdd1243dSDimitry Andric   InstructionCost
132bdd1243dSDimitry Andric   getMemoryOpCost(unsigned Opcode, Type *Src, MaybeAlign Alignment,
133bdd1243dSDimitry Andric                   unsigned AddressSpace, TTI::TargetCostKind CostKind,
134bdd1243dSDimitry Andric                   TTI::OperandValueInfo OpInfo = {TTI::OK_AnyValue, TTI::OP_None},
1355ffd83dbSDimitry Andric                   const Instruction *I = nullptr);
136fe6060f1SDimitry Andric   InstructionCost getInterleavedMemoryOpCost(
1375ffd83dbSDimitry Andric       unsigned Opcode, Type *VecTy, unsigned Factor, ArrayRef<unsigned> Indices,
138349cc55cSDimitry Andric       Align Alignment, unsigned AddressSpace, TTI::TargetCostKind CostKind,
1395ffd83dbSDimitry Andric       bool UseMaskForCond = false, bool UseMaskForGaps = false);
140fe6060f1SDimitry Andric   InstructionCost getIntrinsicInstrCost(const IntrinsicCostAttributes &ICA,
1415ffd83dbSDimitry Andric                                         TTI::TargetCostKind CostKind);
1420eae32dcSDimitry Andric   bool areTypesABICompatible(const Function *Caller, const Function *Callee,
1430eae32dcSDimitry Andric                              const ArrayRef<Type *> &Types) const;
1440eae32dcSDimitry Andric   bool hasActiveVectorLength(unsigned Opcode, Type *DataType,
1450eae32dcSDimitry Andric                              Align Alignment) const;
1460eae32dcSDimitry Andric   InstructionCost getVPMemoryOpCost(unsigned Opcode, Type *Src, Align Alignment,
1470eae32dcSDimitry Andric                                     unsigned AddressSpace,
1480eae32dcSDimitry Andric                                     TTI::TargetCostKind CostKind,
1490eae32dcSDimitry Andric                                     const Instruction *I = nullptr);
150bdd1243dSDimitry Andric   bool supportsTailCallFor(const CallBase *CB) const;
1510eae32dcSDimitry Andric 
1520eae32dcSDimitry Andric private:
1530eae32dcSDimitry Andric   // The following constant is used for estimating costs on power9.
1540eae32dcSDimitry Andric   static const InstructionCost::CostType P9PipelineFlushEstimate = 80;
1550eae32dcSDimitry Andric 
1560b57cec5SDimitry Andric   /// @}
1570b57cec5SDimitry Andric };
1580b57cec5SDimitry Andric 
1590b57cec5SDimitry Andric } // end namespace llvm
1600b57cec5SDimitry Andric 
1610b57cec5SDimitry Andric #endif
162