@@ -2071,6 +2071,40 @@ void VPReductionEVLRecipe::execute(VPTransformState &State) {
20712071 State.set (this , NewRed, /* IsScalar*/ true );
20722072}
20732073
2074+ InstructionCost VPReductionRecipe::computeCost (ElementCount VF,
2075+ VPCostContext &Ctx) const {
2076+ RecurKind RdxKind = RdxDesc.getRecurrenceKind ();
2077+ Type *ElementTy = Ctx.Types .inferScalarType (this );
2078+ auto *VectorTy = cast<VectorType>(ToVectorTy (ElementTy, VF));
2079+ TTI::TargetCostKind CostKind = TTI::TCK_RecipThroughput;
2080+ unsigned Opcode = RdxDesc.getOpcode ();
2081+
2082+ // TODO: Support any-of and in-loop reductions.
2083+ assert (
2084+ (!RecurrenceDescriptor::isAnyOfRecurrenceKind (RdxKind) ||
2085+ ForceTargetInstructionCost.getNumOccurrences () > 0 ) &&
2086+ " Any-of reduction not implemented in VPlan-based cost model currently." );
2087+ assert (
2088+ (!cast<VPReductionPHIRecipe>(getOperand (0 ))->isInLoop () ||
2089+ ForceTargetInstructionCost.getNumOccurrences () > 0 ) &&
2090+ " In-loop reduction not implemented in VPlan-based cost model currently." );
2091+
2092+ assert (ElementTy->getTypeID () == RdxDesc.getRecurrenceType ()->getTypeID () &&
2093+ " Inferred type and recurrence type mismatch." );
2094+
2095+ // Cost = Reduction cost + BinOp cost
2096+ InstructionCost Cost =
2097+ Ctx.TTI .getArithmeticInstrCost (Opcode, ElementTy, CostKind);
2098+ if (RecurrenceDescriptor::isMinMaxRecurrenceKind (RdxKind)) {
2099+ Intrinsic::ID Id = getMinMaxReductionIntrinsicOp (RdxKind);
2100+ return Cost + Ctx.TTI .getMinMaxReductionCost (
2101+ Id, VectorTy, RdxDesc.getFastMathFlags (), CostKind);
2102+ }
2103+
2104+ return Cost + Ctx.TTI .getArithmeticReductionCost (
2105+ Opcode, VectorTy, RdxDesc.getFastMathFlags (), CostKind);
2106+ }
2107+
20742108#if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
20752109void VPReductionRecipe::print (raw_ostream &O, const Twine &Indent,
20762110 VPSlotTracker &SlotTracker) const {
0 commit comments