Index: llvm/include/llvm/Analysis/TargetTransformInfo.h =================================================================== --- llvm/include/llvm/Analysis/TargetTransformInfo.h +++ llvm/include/llvm/Analysis/TargetTransformInfo.h @@ -202,43 +202,15 @@ TCC_Expensive = 4 ///< The cost of a 'div' instruction on x86. }; - /// Estimate the cost of a specific operation when lowered. - /// - /// Note that this is designed to work on an arbitrary synthetic opcode, and - /// thus work for hypothetical queries before an instruction has even been - /// formed. However, this does *not* work for GEPs, and must not be called - /// for a GEP instruction. Instead, use the dedicated getGEPCost interface as - /// analyzing a GEP's cost required more information. - /// - /// Typically only the result type is required, and the operand type can be - /// omitted. However, if the opcode is one of the cast instructions, the - /// operand type is required. - /// - /// The returned cost is defined in terms of \c TargetCostConstants, see its - /// comments for a detailed explanation of the cost values. - int getOperationCost(unsigned Opcode, Type *Ty, Type *OpTy = nullptr) const; - /// Estimate the cost of a GEP operation when lowered. - /// - /// The contract for this function is the same as \c getOperationCost except - /// that it supports an interface that provides extra information specific to - /// the GEP operation. int getGEPCost(Type *PointeeType, const Value *Ptr, ArrayRef Operands) const; /// Estimate the cost of a EXT operation when lowered. - /// - /// The contract for this function is the same as \c getOperationCost except - /// that it supports an interface that provides extra information specific to - /// the EXT operation. int getExtCost(const Instruction *I, const Value *Src) const; /// Estimate the cost of a function call when lowered. /// - /// The contract for this is the same as \c getOperationCost except that it - /// supports an interface that provides extra information specific to call - /// instructions. - /// /// This is the most basic query for estimating call cost: it only knows the /// function type and (potentially) the number of arguments at the call site. /// The latter is only interesting for varargs function types. @@ -307,15 +279,7 @@ /// Estimate the cost of a given IR user when lowered. /// /// This can estimate the cost of either a ConstantExpr or Instruction when - /// lowered. It has two primary advantages over the \c getOperationCost and - /// \c getGEPCost above, and one significant disadvantage: it can only be - /// used when the IR construct has already been formed. - /// - /// The advantages are that it can inspect the SSA use graph to reason more - /// accurately about the cost. For example, all-constant-GEPs can often be - /// folded into a load or other instruction, but if they are used in some - /// other context they may not be folded. This routine can distinguish such - /// cases. + /// lowered. /// /// \p Operands is a list of operands which can be a result of transformations /// of the current operands. The number of the operands on the list must equal @@ -1202,7 +1166,6 @@ public: virtual ~Concept() = 0; virtual const DataLayout &getDataLayout() const = 0; - virtual int getOperationCost(unsigned Opcode, Type *Ty, Type *OpTy) = 0; virtual int getGEPCost(Type *PointeeType, const Value *Ptr, ArrayRef Operands) = 0; virtual int getExtCost(const Instruction *I, const Value *Src) = 0; @@ -1445,9 +1408,6 @@ return Impl.getDataLayout(); } - int getOperationCost(unsigned Opcode, Type *Ty, Type *OpTy) override { - return Impl.getOperationCost(Opcode, Ty, OpTy); - } int getGEPCost(Type *PointeeType, const Value *Ptr, ArrayRef Operands) override { return Impl.getGEPCost(PointeeType, Ptr, Operands); Index: llvm/include/llvm/Analysis/TargetTransformInfoImpl.h =================================================================== --- llvm/include/llvm/Analysis/TargetTransformInfoImpl.h +++ llvm/include/llvm/Analysis/TargetTransformInfoImpl.h @@ -44,69 +44,6 @@ const DataLayout &getDataLayout() const { return DL; } - unsigned getOperationCost(unsigned Opcode, Type *Ty, Type *OpTy) { - switch (Opcode) { - default: - // By default, just classify everything as 'basic'. - return TTI::TCC_Basic; - - case Instruction::GetElementPtr: - llvm_unreachable("Use getGEPCost for GEP operations!"); - - case Instruction::BitCast: - assert(OpTy && "Cast instructions must provide the operand type"); - if (Ty == OpTy || (Ty->isPointerTy() && OpTy->isPointerTy())) - // Identity and pointer-to-pointer casts are free. - return TTI::TCC_Free; - - // Otherwise, the default basic cost is used. - return TTI::TCC_Basic; - - case Instruction::Freeze: - // Freeze operation is free because it should be lowered into a register - // use without any register copy in assembly code. - return TTI::TCC_Free; - - case Instruction::FDiv: - case Instruction::FRem: - case Instruction::SDiv: - case Instruction::SRem: - case Instruction::UDiv: - case Instruction::URem: - return TTI::TCC_Expensive; - - case Instruction::IntToPtr: { - // An inttoptr cast is free so long as the input is a legal integer type - // which doesn't contain values outside the range of a pointer. - unsigned OpSize = OpTy->getScalarSizeInBits(); - if (DL.isLegalInteger(OpSize) && - OpSize <= DL.getPointerTypeSizeInBits(Ty)) - return TTI::TCC_Free; - - // Otherwise it's not a no-op. - return TTI::TCC_Basic; - } - case Instruction::PtrToInt: { - // A ptrtoint cast is free so long as the result is large enough to store - // the pointer, and a legal integer type. - unsigned DestSize = Ty->getScalarSizeInBits(); - if (DL.isLegalInteger(DestSize) && - DestSize >= DL.getPointerTypeSizeInBits(OpTy)) - return TTI::TCC_Free; - - // Otherwise it's not a no-op. - return TTI::TCC_Basic; - } - case Instruction::Trunc: - // trunc to a native type is free (assuming the target has compare and - // shift-right of the same width). - if (DL.isLegalInteger(DL.getTypeSizeInBits(Ty))) - return TTI::TCC_Free; - - return TTI::TCC_Basic; - } - } - int getGEPCost(Type *PointeeType, const Value *Ptr, ArrayRef Operands) { // In the basic model, we just assume that all-constant GEPs will be folded @@ -452,7 +389,27 @@ } unsigned getCastInstrCost(unsigned Opcode, Type *Dst, Type *Src, - const Instruction *I) { return 1; } + const Instruction *I) { + switch (Opcode) { + default: + break; + case Instruction::IntToPtr: { + unsigned SrcSize = Src->getScalarSizeInBits(); + if (DL.isLegalInteger(SrcSize) && + SrcSize <= DL.getPointerTypeSizeInBits(Dst)) + return 0; + break; + } + case Instruction::PtrToInt: { + unsigned DstSize = Dst->getScalarSizeInBits(); + if (DL.isLegalInteger(DstSize) && + DstSize >= DL.getPointerTypeSizeInBits(Src)) + return 0; + break; + } + } + return 1; + } unsigned getExtractWithExtendCost(unsigned Opcode, Type *Dst, VectorType *VecTy, unsigned Index) { @@ -875,27 +832,7 @@ } unsigned getUserCost(const User *U, ArrayRef Operands) { - if (isa(U)) - return TTI::TCC_Free; // Model all PHI nodes as free. - - if (isa(U)) - return TTI::TCC_Free; // Model all ExtractValue nodes as free. - - if (isa(U)) - return TTI::TCC_Free; // Model all Freeze nodes as free. - - // Static alloca doesn't generate target instructions. - if (auto *A = dyn_cast(U)) - if (A->isStaticAlloca()) - return TTI::TCC_Free; - auto *TargetTTI = static_cast(this); - - if (const GEPOperator *GEP = dyn_cast(U)) - return TargetTTI->getGEPCost(GEP->getSourceElementType(), - GEP->getPointerOperand(), - Operands.drop_front()); - if (auto CS = ImmutableCallSite(U)) { const Function *F = CS.getCalledFunction(); if (!F) { @@ -909,13 +846,55 @@ return TargetTTI->getCallCost(F, Arguments, U); } - if (isa(U) || isa(U) || isa(U)) - // The old behaviour of generally treating extensions of icmp to be free - // has been removed. A target that needs it should override getUserCost(). - return TargetTTI->getExtCost(cast(U), Operands.back()); - - return TargetTTI->getOperationCost(Operator::getOpcode(U), U->getType(), - U->getNumOperands() == 1 ? U->getOperand(0)->getType() : nullptr); + Type *Ty = U->getType(); + Type *OpTy = + U->getNumOperands() == 1 ? U->getOperand(0)->getType() : nullptr; + unsigned Opcode = Operator::getOpcode(U); + switch (Opcode) { + default: + break; + case Instruction::PHI: + case Instruction::ExtractValue: + case Instruction::Freeze: + return TTI::TCC_Free; + case Instruction::Alloca: + if (cast(U)->isStaticAlloca()) + return TTI::TCC_Free; + break; + case Instruction::GetElementPtr: { + const GEPOperator *GEP = cast(U); + return TargetTTI->getGEPCost(GEP->getSourceElementType(), + GEP->getPointerOperand(), + Operands.drop_front()); + } + case Instruction::FDiv: + case Instruction::FRem: + case Instruction::SDiv: + case Instruction::SRem: + case Instruction::UDiv: + case Instruction::URem: + return TTI::TCC_Expensive; + case Instruction::IntToPtr: + case Instruction::PtrToInt: + if (getCastInstrCost(Opcode, Ty, OpTy, dyn_cast(U)) == + TargetTransformInfo::TCC_Free) + return 0; + return TargetTTI->getCastInstrCost(Opcode, Ty, OpTy, + dyn_cast(U)); + case Instruction::FPExt: + case Instruction::SExt: + case Instruction::ZExt: + if (TargetTTI->getExtCost(cast(U), Operands.back()) == + TargetTransformInfo::TCC_Free) + return 0; + LLVM_FALLTHROUGH; + case Instruction::BitCast: + case Instruction::Trunc: + return TargetTTI->getCastInstrCost(Opcode, Ty, OpTy, + cast(U)); + } + // By default, just classify everything as 'basic'. + return TTI::TCC_Basic; } int getInstructionLatency(const Instruction *I) { Index: llvm/include/llvm/CodeGen/BasicTTIImpl.h =================================================================== --- llvm/include/llvm/CodeGen/BasicTTIImpl.h +++ llvm/include/llvm/CodeGen/BasicTTIImpl.h @@ -413,29 +413,6 @@ return TargetTransformInfo::TCC_Expensive; } - unsigned getOperationCost(unsigned Opcode, Type *Ty, Type *OpTy) { - const TargetLoweringBase *TLI = getTLI(); - switch (Opcode) { - default: break; - case Instruction::Trunc: - if (TLI->isTruncateFree(OpTy, Ty)) - return TargetTransformInfo::TCC_Free; - return TargetTransformInfo::TCC_Basic; - case Instruction::ZExt: - if (TLI->isZExtFree(OpTy, Ty)) - return TargetTransformInfo::TCC_Free; - return TargetTransformInfo::TCC_Basic; - - case Instruction::AddrSpaceCast: - if (TLI->isFreeAddrSpaceCast(OpTy->getPointerAddressSpace(), - Ty->getPointerAddressSpace())) - return TargetTransformInfo::TCC_Free; - return TargetTransformInfo::TCC_Basic; - } - - return BaseT::getOperationCost(Opcode, Ty, OpTy); - } - unsigned getInliningThresholdMultiplier() { return 1; } int getInlinerVectorBonusPercent() { return 150; } Index: llvm/lib/Analysis/TargetTransformInfo.cpp =================================================================== --- llvm/lib/Analysis/TargetTransformInfo.cpp +++ llvm/lib/Analysis/TargetTransformInfo.cpp @@ -146,13 +146,6 @@ return *this; } -int TargetTransformInfo::getOperationCost(unsigned Opcode, Type *Ty, - Type *OpTy) const { - int Cost = TTIImpl->getOperationCost(Opcode, Ty, OpTy); - assert(Cost >= 0 && "TTI should not produce negative costs!"); - return Cost; -} - int TargetTransformInfo::getCallCost(FunctionType *FTy, int NumArgs, const User *U) const { int Cost = TTIImpl->getCallCost(FTy, NumArgs, U); Index: llvm/test/Analysis/CostModel/SystemZ/ext-of-icmp-cost.ll =================================================================== --- llvm/test/Analysis/CostModel/SystemZ/ext-of-icmp-cost.ll +++ llvm/test/Analysis/CostModel/SystemZ/ext-of-icmp-cost.ll @@ -7,7 +7,7 @@ define i64 @fun1(i64 %v) { ; CHECK-LABEL: 'fun1' ; CHECK: Cost Model: Found an estimated cost of 1 for instruction: %cmp = icmp eq i64 %v, 0 -; CHECK: Cost Model: Found an estimated cost of 1 for instruction: %z = zext i1 %cmp to i64 +; CHECK: Cost Model: Found an estimated cost of 2 for instruction: %z = zext i1 %cmp to i64 ; CHECK: Cost Model: Found an estimated cost of 1 for instruction: ret i64 %z %cmp = icmp eq i64 %v, 0 %z = zext i1 %cmp to i64 @@ -17,7 +17,7 @@ define i64 @fun2(i64 %v) { ; CHECK-LABEL: 'fun2' ; CHECK: Cost Model: Found an estimated cost of 1 for instruction: %cmp = icmp eq i64 %v, 0 -; CHECK: Cost Model: Found an estimated cost of 1 for instruction: %z = sext i1 %cmp to i64 +; CHECK: Cost Model: Found an estimated cost of 2 for instruction: %z = sext i1 %cmp to i64 ; CHECK: Cost Model: Found an estimated cost of 1 for instruction: ret i64 %z %cmp = icmp eq i64 %v, 0 %z = sext i1 %cmp to i64 @@ -46,7 +46,7 @@ define i64 @fun5(i1 %v) { ; CHECK-LABEL: 'fun5' -; CHECK: Cost Model: Found an estimated cost of 1 for instruction: %z = zext i1 %v to i64 +; CHECK: Cost Model: Found an estimated cost of 2 for instruction: %z = zext i1 %v to i64 ; CHECK: Cost Model: Found an estimated cost of 1 for instruction: ret i64 %z %z = zext i1 %v to i64 ret i64 %z