1 //==- HexagonTargetTransformInfo.cpp - Hexagon specific TTI pass -*- 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-exception 6 // 7 /// \file 8 /// This file implements a TargetTransformInfo analysis pass specific to the 9 /// Hexagon target machine. It uses the target's detailed information to provide 10 /// more precise answers to certain TTI queries, while letting the target 11 /// independent and default TTI implementations handle the rest. 12 /// 13 //===----------------------------------------------------------------------===// 14 15 #ifndef LLVM_LIB_TARGET_HEXAGON_HEXAGONTARGETTRANSFORMINFO_H 16 #define LLVM_LIB_TARGET_HEXAGON_HEXAGONTARGETTRANSFORMINFO_H 17 18 #include "Hexagon.h" 19 #include "HexagonSubtarget.h" 20 #include "HexagonTargetMachine.h" 21 #include "llvm/ADT/ArrayRef.h" 22 #include "llvm/Analysis/TargetTransformInfo.h" 23 #include "llvm/CodeGen/BasicTTIImpl.h" 24 #include "llvm/IR/Function.h" 25 26 namespace llvm { 27 28 class Loop; 29 class ScalarEvolution; 30 class User; 31 class Value; 32 33 class HexagonTTIImpl final : public BasicTTIImplBase<HexagonTTIImpl> { 34 using BaseT = BasicTTIImplBase<HexagonTTIImpl>; 35 using TTI = TargetTransformInfo; 36 37 friend BaseT; 38 39 const HexagonSubtarget &ST; 40 const HexagonTargetLowering &TLI; 41 getST()42 const HexagonSubtarget *getST() const { return &ST; } getTLI()43 const HexagonTargetLowering *getTLI() const { return &TLI; } 44 45 bool useHVX() const; 46 bool isHVXVectorType(Type *Ty) const; 47 48 // Returns the number of vector elements of Ty, if Ty is a vector type, 49 // or 1 if Ty is a scalar type. It is incorrect to call this function 50 // with any other type. 51 unsigned getTypeNumElements(Type *Ty) const; 52 53 public: HexagonTTIImpl(const HexagonTargetMachine * TM,const Function & F)54 explicit HexagonTTIImpl(const HexagonTargetMachine *TM, const Function &F) 55 : BaseT(TM, F.getDataLayout()), 56 ST(*TM->getSubtargetImpl(F)), TLI(*ST.getTargetLowering()) {} 57 58 /// \name Scalar TTI Implementations 59 /// @{ 60 61 TTI::PopcntSupportKind 62 getPopcntSupport(unsigned IntTyWidthInBit) const override; 63 64 // The Hexagon target can unroll loops with run-time trip counts. 65 void getUnrollingPreferences(Loop *L, ScalarEvolution &SE, 66 TTI::UnrollingPreferences &UP, 67 OptimizationRemarkEmitter *ORE) const override; 68 69 void getPeelingPreferences(Loop *L, ScalarEvolution &SE, 70 TTI::PeelingPreferences &PP) const override; 71 72 /// Bias LSR towards creating post-increment opportunities. 73 TTI::AddressingModeKind 74 getPreferredAddressingMode(const Loop *L, ScalarEvolution *SE) const override; 75 76 // L1 cache prefetch. 77 unsigned getPrefetchDistance() const override; 78 unsigned getCacheLineSize() const override; 79 80 /// @} 81 82 /// \name Vector TTI Implementations 83 /// @{ 84 85 unsigned getNumberOfRegisters(unsigned ClassID) const override; 86 unsigned getMaxInterleaveFactor(ElementCount VF) const override; 87 TypeSize 88 getRegisterBitWidth(TargetTransformInfo::RegisterKind K) const override; 89 unsigned getMinVectorRegisterBitWidth() const override; 90 ElementCount getMinimumVF(unsigned ElemWidth, bool IsScalable) const override; 91 shouldMaximizeVectorBandwidth(TargetTransformInfo::RegisterKind K)92 bool shouldMaximizeVectorBandwidth( 93 TargetTransformInfo::RegisterKind K) const override { 94 return true; 95 } supportsEfficientVectorElementLoadStore()96 bool supportsEfficientVectorElementLoadStore() const override { 97 return false; 98 } 99 bool hasBranchDivergence(const Function *F = nullptr) const override { 100 return false; 101 } enableAggressiveInterleaving(bool LoopHasReductions)102 bool enableAggressiveInterleaving(bool LoopHasReductions) const override { 103 return false; 104 } prefersVectorizedAddressing()105 bool prefersVectorizedAddressing() const override { return false; } enableInterleavedAccessVectorization()106 bool enableInterleavedAccessVectorization() const override { return true; } 107 108 InstructionCost getCallInstrCost(Function *F, Type *RetTy, 109 ArrayRef<Type *> Tys, 110 TTI::TargetCostKind CostKind) const override; 111 InstructionCost 112 getIntrinsicInstrCost(const IntrinsicCostAttributes &ICA, 113 TTI::TargetCostKind CostKind) const override; 114 InstructionCost getAddressComputationCost(Type *Tp, ScalarEvolution *SE, 115 const SCEV *S) const override; 116 InstructionCost getMemoryOpCost( 117 unsigned Opcode, Type *Src, Align Alignment, unsigned AddressSpace, 118 TTI::TargetCostKind CostKind, 119 TTI::OperandValueInfo OpInfo = {TTI::OK_AnyValue, TTI::OP_None}, 120 const Instruction *I = nullptr) const override; 121 InstructionCost 122 getMaskedMemoryOpCost(unsigned Opcode, Type *Src, Align Alignment, 123 unsigned AddressSpace, 124 TTI::TargetCostKind CostKind) const override; 125 InstructionCost 126 getShuffleCost(TTI::ShuffleKind Kind, VectorType *DstTy, VectorType *SrcTy, 127 ArrayRef<int> Mask, TTI::TargetCostKind CostKind, int Index, 128 VectorType *SubTp, ArrayRef<const Value *> Args = {}, 129 const Instruction *CxtI = nullptr) const override; 130 InstructionCost getGatherScatterOpCost(unsigned Opcode, Type *DataTy, 131 const Value *Ptr, bool VariableMask, 132 Align Alignment, 133 TTI::TargetCostKind CostKind, 134 const Instruction *I) const override; 135 InstructionCost getInterleavedMemoryOpCost( 136 unsigned Opcode, Type *VecTy, unsigned Factor, ArrayRef<unsigned> Indices, 137 Align Alignment, unsigned AddressSpace, TTI::TargetCostKind CostKind, 138 bool UseMaskForCond = false, bool UseMaskForGaps = false) const override; 139 InstructionCost getCmpSelInstrCost( 140 unsigned Opcode, Type *ValTy, Type *CondTy, CmpInst::Predicate VecPred, 141 TTI::TargetCostKind CostKind, 142 TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, 143 TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, 144 const Instruction *I = nullptr) const override; 145 InstructionCost getArithmeticInstrCost( 146 unsigned Opcode, Type *Ty, TTI::TargetCostKind CostKind, 147 TTI::OperandValueInfo Op1Info = {TTI::OK_AnyValue, TTI::OP_None}, 148 TTI::OperandValueInfo Op2Info = {TTI::OK_AnyValue, TTI::OP_None}, 149 ArrayRef<const Value *> Args = {}, 150 const Instruction *CxtI = nullptr) const override; 151 InstructionCost 152 getCastInstrCost(unsigned Opcode, Type *Dst, Type *Src, 153 TTI::CastContextHint CCH, TTI::TargetCostKind CostKind, 154 const Instruction *I = nullptr) const override; 155 using BaseT::getVectorInstrCost; 156 InstructionCost getVectorInstrCost(unsigned Opcode, Type *Val, 157 TTI::TargetCostKind CostKind, 158 unsigned Index, const Value *Op0, 159 const Value *Op1) const override; 160 161 InstructionCost 162 getCFInstrCost(unsigned Opcode, TTI::TargetCostKind CostKind, 163 const Instruction *I = nullptr) const override { 164 return 1; 165 } 166 167 bool isLegalMaskedStore(Type *DataType, Align Alignment, 168 unsigned AddressSpace) const override; 169 bool isLegalMaskedLoad(Type *DataType, Align Alignment, 170 unsigned AddressSpace) const override; 171 172 /// @} 173 174 InstructionCost 175 getInstructionCost(const User *U, ArrayRef<const Value *> Operands, 176 TTI::TargetCostKind CostKind) const override; 177 178 // Hexagon specific decision to generate a lookup table. 179 bool shouldBuildLookupTables() const override; 180 }; 181 182 } // end namespace llvm 183 #endif // LLVM_LIB_TARGET_HEXAGON_HEXAGONTARGETTRANSFORMINFO_H 184