[llvm] [VPlan] Expand WideCanIV into executable recipes (PR #191219)

Ramkumar Ramachandra via llvm-commits llvm-commits at lists.llvm.org
Tue May 5 05:22:04 PDT 2026


https://github.com/artagnon updated https://github.com/llvm/llvm-project/pull/191219

>From 72b039f169832d0af160bd07316755f9e7d3b45a Mon Sep 17 00:00:00 2001
From: Ramkumar Ramachandra <artagnon at tenstorrent.com>
Date: Thu, 9 Apr 2026 12:54:23 +0100
Subject: [PATCH] [VPlan] Expand WideCanIV into executable recipes

Convert VPWidenCanonicalIVRecipe into executable recipes via
convertToConcreteRecipes, making the necessary adjustments to
VPlanUnroll, eliminating VPUnrollAccessor and
VPWidenCanonicalIVRecipe::execute entirely.
---
 llvm/lib/Transforms/Vectorize/VPlan.h         | 33 +++++------
 .../lib/Transforms/Vectorize/VPlanRecipes.cpp | 40 -------------
 .../Transforms/Vectorize/VPlanTransforms.cpp  | 23 +++++++-
 llvm/lib/Transforms/Vectorize/VPlanUnroll.cpp | 18 ++++--
 ...ave-conditional-scalar-assignment-vplan.ll | 48 ++++++++--------
 .../widen-canonical-iv-register-pressure.ll   | 56 +++++++++++--------
 6 files changed, 106 insertions(+), 112 deletions(-)

diff --git a/llvm/lib/Transforms/Vectorize/VPlan.h b/llvm/lib/Transforms/Vectorize/VPlan.h
index 4a5420185224b..072fd0551979a 100644
--- a/llvm/lib/Transforms/Vectorize/VPlan.h
+++ b/llvm/lib/Transforms/Vectorize/VPlan.h
@@ -1150,18 +1150,6 @@ struct VPRecipeWithIRFlags : public VPSingleDefRecipe, public VPIRFlags {
                                              VPCostContext &Ctx) const;
 };
 
-/// Helper to access the operand that contains the unroll part for this recipe
-/// after unrolling.
-template <unsigned PartOpIdx> class LLVM_ABI_FOR_TEST VPUnrollPartAccessor {
-protected:
-  /// Return the VPValue operand containing the unroll part or null if there is
-  /// no such operand.
-  VPValue *getUnrollPartOperand(const VPUser &U) const;
-
-  /// Return the unroll part.
-  unsigned getUnrollPart(const VPUser &U) const;
-};
-
 /// Helper to manage IR metadata for recipes. It filters out metadata that
 /// cannot be propagated.
 class VPIRMetadata {
@@ -3853,8 +3841,9 @@ class VPCurrentIterationPHIRecipe : public VPHeaderPHIRecipe {
 };
 
 /// A Recipe for widening the canonical induction variable of the vector loop.
-class VPWidenCanonicalIVRecipe : public VPSingleDefRecipe,
-                                 public VPUnrollPartAccessor<1> {
+/// First operand is the canonical IV recipe, a second step operand is added by
+/// the unroller as VFxPart. The step for part 0 is 0.
+class VPWidenCanonicalIVRecipe : public VPSingleDefRecipe {
 public:
   VPWidenCanonicalIVRecipe(VPRegionValue *CanonicalIV)
       : VPSingleDefRecipe(VPRecipeBase::VPWidenCanonicalIVSC, {CanonicalIV}) {}
@@ -3862,15 +3851,17 @@ class VPWidenCanonicalIVRecipe : public VPSingleDefRecipe,
   ~VPWidenCanonicalIVRecipe() override = default;
 
   VPWidenCanonicalIVRecipe *clone() override {
-    return new VPWidenCanonicalIVRecipe(getCanonicalIV());
+    auto *WideCanIV = new VPWidenCanonicalIVRecipe(getCanonicalIV());
+    if (VPValue *Step = getStepValue())
+      WideCanIV->addOperand(Step);
+    return WideCanIV;
   }
 
   VP_CLASSOF_IMPL(VPRecipeBase::VPWidenCanonicalIVSC)
 
-  /// Generate a canonical vector induction variable of the vector loop, with
-  /// start = {<Part*VF, Part*VF+1, ..., Part*VF+VF-1> for 0 <= Part < UF}, and
-  /// step = <VF*UF, VF*UF, ..., VF*UF>.
-  void execute(VPTransformState &State) override;
+  void execute(VPTransformState &State) override {
+    llvm_unreachable("Expected prior expansion of WidenCanonicalIV recipes");
+  }
 
   /// Return the cost of this VPWidenCanonicalIVPHIRecipe.
   InstructionCost computeCost(ElementCount VF,
@@ -3884,6 +3875,10 @@ class VPWidenCanonicalIVRecipe : public VPSingleDefRecipe,
     return cast<VPRegionValue>(getOperand(0));
   }
 
+  VPValue *getStepValue() const {
+    return getNumOperands() == 2 ? getOperand(1) : nullptr;
+  }
+
 protected:
 #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
   /// Print the recipe.
diff --git a/llvm/lib/Transforms/Vectorize/VPlanRecipes.cpp b/llvm/lib/Transforms/Vectorize/VPlanRecipes.cpp
index 2225dfa310c6c..59129ae5b5b06 100644
--- a/llvm/lib/Transforms/Vectorize/VPlanRecipes.cpp
+++ b/llvm/lib/Transforms/Vectorize/VPlanRecipes.cpp
@@ -402,27 +402,6 @@ void VPRecipeBase::print(raw_ostream &O, const Twine &Indent,
 }
 #endif
 
-template <unsigned PartOpIdx>
-VPValue *
-VPUnrollPartAccessor<PartOpIdx>::getUnrollPartOperand(const VPUser &U) const {
-  if (U.getNumOperands() == PartOpIdx + 1)
-    return U.getOperand(PartOpIdx);
-  return nullptr;
-}
-
-template <unsigned PartOpIdx>
-unsigned VPUnrollPartAccessor<PartOpIdx>::getUnrollPart(const VPUser &U) const {
-  if (auto *UnrollPartOp = getUnrollPartOperand(U))
-    return cast<VPConstantInt>(UnrollPartOp)->getZExtValue();
-  return 0;
-}
-
-namespace llvm {
-template class VPUnrollPartAccessor<1>;
-template class VPUnrollPartAccessor<2>;
-template class VPUnrollPartAccessor<3>;
-}
-
 VPInstruction::VPInstruction(unsigned Opcode, ArrayRef<VPValue *> Operands,
                              const VPIRFlags &Flags, const VPIRMetadata &MD,
                              DebugLoc DL, const Twine &Name)
@@ -4443,25 +4422,6 @@ void VPExpandSCEVRecipe::printRecipe(raw_ostream &O, const Twine &Indent,
 }
 #endif
 
-void VPWidenCanonicalIVRecipe::execute(VPTransformState &State) {
-  Value *CanonicalIV = State.get(getOperand(0), /*IsScalar*/ true);
-  Type *STy = CanonicalIV->getType();
-  IRBuilder<> Builder(State.CFG.PrevBB->getTerminator());
-  ElementCount VF = State.VF;
-  Value *VStart = VF.isScalar()
-                      ? CanonicalIV
-                      : Builder.CreateVectorSplat(VF, CanonicalIV, "broadcast");
-  Value *VStep = Builder.CreateElementCount(
-      STy, VF.multiplyCoefficientBy(getUnrollPart(*this)));
-  if (VF.isVector()) {
-    VStep = Builder.CreateVectorSplat(VF, VStep);
-    VStep =
-        Builder.CreateAdd(VStep, Builder.CreateStepVector(VStep->getType()));
-  }
-  Value *CanonicalVectorIV = Builder.CreateAdd(VStart, VStep, "vec.iv");
-  State.set(this, CanonicalVectorIV);
-}
-
 #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP)
 void VPWidenCanonicalIVRecipe::printRecipe(raw_ostream &O, const Twine &Indent,
                                            VPSlotTracker &SlotTracker) const {
diff --git a/llvm/lib/Transforms/Vectorize/VPlanTransforms.cpp b/llvm/lib/Transforms/Vectorize/VPlanTransforms.cpp
index 98b468452dbc5..14015a92f0a17 100644
--- a/llvm/lib/Transforms/Vectorize/VPlanTransforms.cpp
+++ b/llvm/lib/Transforms/Vectorize/VPlanTransforms.cpp
@@ -3902,6 +3902,7 @@ void VPlanTransforms::convertToConcreteRecipes(VPlan &Plan) {
   for (VPBasicBlock *VPBB : VPBlockUtils::blocksOnly<VPBasicBlock>(
            vp_depth_first_deep(Plan.getEntry()))) {
     for (VPRecipeBase &R : make_early_inc_range(*VPBB)) {
+      VPBuilder Builder(&R);
       if (auto *WidenIVR = dyn_cast<VPWidenIntOrFpInductionRecipe>(&R)) {
         expandVPWidenIntOrFpInduction(WidenIVR, TypeInfo);
         ToRemove.push_back(WidenIVR);
@@ -3912,7 +3913,6 @@ void VPlanTransforms::convertToConcreteRecipes(VPlan &Plan) {
         // If the recipe only generates scalars, scalarize it instead of
         // expanding it.
         if (WidenIVR->onlyScalarsGenerated(Plan.hasScalableVF())) {
-          VPBuilder Builder(WidenIVR);
           VPValue *PtrAdd =
               scalarizeVPWidenPointerInduction(WidenIVR, Plan, Builder);
           WidenIVR->replaceAllUsesWith(PtrAdd);
@@ -3930,8 +3930,27 @@ void VPlanTransforms::convertToConcreteRecipes(VPlan &Plan) {
         continue;
       }
 
+      if (auto *WideCanIV = dyn_cast<VPWidenCanonicalIVRecipe>(&R)) {
+        VPValue *CanIV = WideCanIV->getCanonicalIV();
+        Type *CanIVTy = TypeInfo.inferScalarType(CanIV);
+        VPValue *Step = WideCanIV->getStepValue();
+        if (!Step) {
+          assert(Plan.getConcreteUF() == 1 &&
+                 "Expected unroller to have materialized step for UF != 1");
+          Step = Plan.getZero(CanIVTy);
+        }
+        CanIV = Builder.createNaryOp(VPInstruction::Broadcast, CanIV);
+        Step = Builder.createNaryOp(VPInstruction::Broadcast, Step);
+        Step = Builder.createAdd(
+            Step, Builder.createNaryOp(VPInstruction::StepVector, {}, CanIVTy));
+        VPValue *CanVecIV =
+            Builder.createAdd(CanIV, Step, WideCanIV->getDebugLoc(), "vec.iv");
+        WideCanIV->replaceAllUsesWith(CanVecIV);
+        ToRemove.push_back(WideCanIV);
+        continue;
+      }
+
       // Expand VPBlendRecipe into VPInstruction::Select.
-      VPBuilder Builder(&R);
       if (auto *Blend = dyn_cast<VPBlendRecipe>(&R)) {
         VPValue *Select = Blend->getIncomingValue(0);
         for (unsigned I = 1; I != Blend->getNumIncomingValues(); ++I)
diff --git a/llvm/lib/Transforms/Vectorize/VPlanUnroll.cpp b/llvm/lib/Transforms/Vectorize/VPlanUnroll.cpp
index f1b9efae08377..f433e70aee4ca 100644
--- a/llvm/lib/Transforms/Vectorize/VPlanUnroll.cpp
+++ b/llvm/lib/Transforms/Vectorize/VPlanUnroll.cpp
@@ -368,6 +368,15 @@ void UnrollState::unrollRecipeByUF(VPRecipeBase &R) {
         Phi->setOperand(1, Copy->getVPSingleValue());
       }
     }
+    if (auto *WideCanIV = dyn_cast<VPWidenCanonicalIVRecipe>(&R)) {
+      VPBuilder Builder(WideCanIV);
+      VPValue *VFxPart = Builder.createOverflowingOp(
+          Instruction::Mul, {&Plan.getVF(), getConstantInt(Part)},
+          {true, true});
+      Copy->setOperand(0, WideCanIV->getOperand(0));
+      Copy->addOperand(VFxPart);
+      continue;
+    }
     if (auto *VEPR = dyn_cast<VPVectorEndPointerRecipe>(Copy)) {
       // Materialize PartN offset for VectorEndPointer.
       VEPR->setOperand(0, R.getOperand(0));
@@ -381,11 +390,6 @@ void UnrollState::unrollRecipeByUF(VPRecipeBase &R) {
     if (auto *ScalarIVSteps = dyn_cast<VPScalarIVStepsRecipe>(Copy))
       addStartIndexForScalarSteps(ScalarIVSteps, Part, Plan, TypeInfo);
 
-    // Add operand indicating the part to generate code for, to recipes still
-    // requiring it.
-    if (isa<VPWidenCanonicalIVRecipe>(Copy))
-      Copy->addOperand(getConstantInt(Part));
-
     if (match(Copy,
               m_VPInstruction<VPInstruction::CanonicalIVIncrementForPart>())) {
       VPBuilder Builder(Copy);
@@ -398,6 +402,10 @@ void UnrollState::unrollRecipeByUF(VPRecipeBase &R) {
     // Materialize Part0 offset for VectorEndPointer.
     VEPR->materializeOffset();
   }
+  if (auto *WideCanIV = dyn_cast<VPWidenCanonicalIVRecipe>(&R)) {
+    // Set Part0 step for WidenCanonicalIV.
+    WideCanIV->addOperand(getConstantInt(0));
+  }
 }
 
 void UnrollState::unrollBlock(VPBlockBase *VPB) {
diff --git a/llvm/test/Transforms/LoopVectorize/VPlan/interleave-conditional-scalar-assignment-vplan.ll b/llvm/test/Transforms/LoopVectorize/VPlan/interleave-conditional-scalar-assignment-vplan.ll
index b4266483f2aa3..f86838f4a4f0f 100644
--- a/llvm/test/Transforms/LoopVectorize/VPlan/interleave-conditional-scalar-assignment-vplan.ll
+++ b/llvm/test/Transforms/LoopVectorize/VPlan/interleave-conditional-scalar-assignment-vplan.ll
@@ -97,38 +97,42 @@ define i32 @find_last_int_select(i64 %N, ptr %data, i32 %a) {
 ; IC2-TF-EMPTY:
 ; IC2-TF-NEXT:  vector.body:
 ; IC2-TF-NEXT:    EMIT-SCALAR vp<%index> = phi [ ir<0>, vector.ph ], [ vp<%index.next>, vector.body ]
-; IC2-TF-NEXT:    WIDEN-REDUCTION-PHI ir<%data.phi> = phi ir<-1>, vp<[[VP16:%[0-9]+]]>
-; IC2-TF-NEXT:    WIDEN-REDUCTION-PHI ir<%data.phi>.1 = phi ir<-1>, vp<[[VP17:%[0-9]+]]>
-; IC2-TF-NEXT:    WIDEN-PHI vp<[[VP4:%[0-9]+]]> = phi [ ir<false>, vector.ph ], [ vp<[[VP14:%[0-9]+]]>, vector.body ]
-; IC2-TF-NEXT:    WIDEN-PHI vp<[[VP5:%[0-9]+]]> = phi [ ir<false>, vector.ph ], [ vp<[[VP15:%[0-9]+]]>, vector.body ]
-; IC2-TF-NEXT:    EMIT vp<[[VP6:%[0-9]+]]> = WIDEN-CANONICAL-INDUCTION vp<%index>
-; IC2-TF-NEXT:    EMIT vp<[[VP7:%[0-9]+]]> = WIDEN-CANONICAL-INDUCTION vp<%index>, ir<1>
-; IC2-TF-NEXT:    EMIT vp<[[VP8:%[0-9]+]]> = icmp ule vp<[[VP6]]>, vp<[[VP2]]>
-; IC2-TF-NEXT:    EMIT vp<[[VP9:%[0-9]+]]> = icmp ule vp<[[VP7]]>, vp<[[VP2]]>
+; IC2-TF-NEXT:    WIDEN-REDUCTION-PHI ir<%data.phi> = phi ir<-1>, vp<[[VP18:%[0-9]+]]>
+; IC2-TF-NEXT:    WIDEN-REDUCTION-PHI ir<%data.phi>.1 = phi ir<-1>, vp<[[VP19:%[0-9]+]]>
+; IC2-TF-NEXT:    WIDEN-PHI vp<[[VP4:%[0-9]+]]> = phi [ ir<false>, vector.ph ], [ vp<[[VP16:%[0-9]+]]>, vector.body ]
+; IC2-TF-NEXT:    WIDEN-PHI vp<[[VP5:%[0-9]+]]> = phi [ ir<false>, vector.ph ], [ vp<[[VP17:%[0-9]+]]>, vector.body ]
+; IC2-TF-NEXT:    EMIT vp<[[VP6:%[0-9]+]]> = broadcast vp<%index>
+; IC2-TF-NEXT:    EMIT vp<[[VP7:%[0-9]+]]> = step-vector i64
+; IC2-TF-NEXT:    EMIT vp<%vec.iv> = add vp<[[VP6]]>, vp<[[VP7]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP8:%[0-9]+]]> = broadcast ir<4>
+; IC2-TF-NEXT:    EMIT vp<[[VP9:%[0-9]+]]> = add vp<[[VP8]]>, vp<[[VP7]]>
+; IC2-TF-NEXT:    EMIT vp<%vec.iv>.1 = add vp<[[VP6]]>, vp<[[VP9]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP10:%[0-9]+]]> = icmp ule vp<%vec.iv>, vp<[[VP2]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP11:%[0-9]+]]> = icmp ule vp<%vec.iv>.1, vp<[[VP2]]>
 ; IC2-TF-NEXT:    CLONE ir<%ld.addr> = getelementptr inbounds ir<%data>, vp<%index>
-; IC2-TF-NEXT:    vp<[[VP10:%[0-9]+]]> = vector-pointer inbounds ir<%ld.addr>, ir<4>
-; IC2-TF-NEXT:    WIDEN ir<%ld> = load ir<%ld.addr>, vp<[[VP8]]>
-; IC2-TF-NEXT:    WIDEN ir<%ld>.1 = load vp<[[VP10]]>, vp<[[VP9]]>
+; IC2-TF-NEXT:    vp<[[VP12:%[0-9]+]]> = vector-pointer inbounds ir<%ld.addr>, ir<4>
+; IC2-TF-NEXT:    WIDEN ir<%ld> = load ir<%ld.addr>, vp<[[VP10]]>
+; IC2-TF-NEXT:    WIDEN ir<%ld>.1 = load vp<[[VP12]]>, vp<[[VP11]]>
 ; IC2-TF-NEXT:    WIDEN ir<%select.cmp> = icmp slt vp<[[VP3]]>, ir<%ld>
 ; IC2-TF-NEXT:    WIDEN ir<%select.cmp>.1 = icmp slt vp<[[VP3]]>, ir<%ld>.1
-; IC2-TF-NEXT:    EMIT vp<[[VP11:%[0-9]+]]> = logical-and vp<[[VP8]]>, ir<%select.cmp>
-; IC2-TF-NEXT:    EMIT vp<[[VP12:%[0-9]+]]> = logical-and vp<[[VP9]]>, ir<%select.cmp>.1
-; IC2-TF-NEXT:    EMIT vp<[[VP13:%[0-9]+]]> = any-of vp<[[VP11]]>, vp<[[VP12]]>
-; IC2-TF-NEXT:    EMIT vp<[[VP14]]> = select vp<[[VP13]]>, vp<[[VP11]]>, vp<[[VP4]]>
-; IC2-TF-NEXT:    EMIT vp<[[VP15]]> = select vp<[[VP13]]>, vp<[[VP12]]>, vp<[[VP5]]>
-; IC2-TF-NEXT:    EMIT vp<[[VP16]]> = select vp<[[VP13]]>, ir<%ld>, ir<%data.phi>
-; IC2-TF-NEXT:    EMIT vp<[[VP17]]> = select vp<[[VP13]]>, ir<%ld>.1, ir<%data.phi>.1
+; IC2-TF-NEXT:    EMIT vp<[[VP13:%[0-9]+]]> = logical-and vp<[[VP10]]>, ir<%select.cmp>
+; IC2-TF-NEXT:    EMIT vp<[[VP14:%[0-9]+]]> = logical-and vp<[[VP11]]>, ir<%select.cmp>.1
+; IC2-TF-NEXT:    EMIT vp<[[VP15:%[0-9]+]]> = any-of vp<[[VP13]]>, vp<[[VP14]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP16]]> = select vp<[[VP15]]>, vp<[[VP13]]>, vp<[[VP4]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP17]]> = select vp<[[VP15]]>, vp<[[VP14]]>, vp<[[VP5]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP18]]> = select vp<[[VP15]]>, ir<%ld>, ir<%data.phi>
+; IC2-TF-NEXT:    EMIT vp<[[VP19]]> = select vp<[[VP15]]>, ir<%ld>.1, ir<%data.phi>.1
 ; IC2-TF-NEXT:    EMIT vp<%index.next> = add vp<%index>, ir<8>
-; IC2-TF-NEXT:    EMIT vp<[[VP18:%[0-9]+]]> = icmp eq vp<%index.next>, vp<%n.vec>
-; IC2-TF-NEXT:    EMIT branch-on-cond vp<[[VP18]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP20:%[0-9]+]]> = icmp eq vp<%index.next>, vp<%n.vec>
+; IC2-TF-NEXT:    EMIT branch-on-cond vp<[[VP20]]>
 ; IC2-TF-NEXT:  Successor(s): middle.block, vector.body
 ; IC2-TF-EMPTY:
 ; IC2-TF-NEXT:  middle.block:
-; IC2-TF-NEXT:    EMIT vp<[[VP20:%[0-9]+]]> = extract-last-active ir<-1>, vp<[[VP16]]>, vp<[[VP14]]>, vp<[[VP17]]>, vp<[[VP15]]>
+; IC2-TF-NEXT:    EMIT vp<[[VP22:%[0-9]+]]> = extract-last-active ir<-1>, vp<[[VP18]]>, vp<[[VP16]]>, vp<[[VP19]]>, vp<[[VP17]]>
 ; IC2-TF-NEXT:  Successor(s): ir-bb<exit>
 ; IC2-TF-EMPTY:
 ; IC2-TF-NEXT:  ir-bb<exit>:
-; IC2-TF-NEXT:    IR   %select.data.lcssa = phi i32 [ %select.data, %loop ] (extra operand: vp<[[VP20]]> from middle.block)
+; IC2-TF-NEXT:    IR   %select.data.lcssa = phi i32 [ %select.data, %loop ] (extra operand: vp<[[VP22]]> from middle.block)
 ; IC2-TF-NEXT:  No successors
 ; IC2-TF-NEXT:  }
 ;
diff --git a/llvm/test/Transforms/LoopVectorize/VPlan/widen-canonical-iv-register-pressure.ll b/llvm/test/Transforms/LoopVectorize/VPlan/widen-canonical-iv-register-pressure.ll
index b823144f8e398..0a1b3c39b0a7c 100644
--- a/llvm/test/Transforms/LoopVectorize/VPlan/widen-canonical-iv-register-pressure.ll
+++ b/llvm/test/Transforms/LoopVectorize/VPlan/widen-canonical-iv-register-pressure.ll
@@ -73,30 +73,38 @@ define i32 @two_reductions(i64 %N, ptr %a, ptr %b) {
 ; UF4-NEXT:    WIDEN-REDUCTION-PHI ir<%sum.b>.1 = phi ir<0>, ir<%sum.b.next>.1
 ; UF4-NEXT:    WIDEN-REDUCTION-PHI ir<%sum.b>.2 = phi ir<0>, ir<%sum.b.next>.2
 ; UF4-NEXT:    WIDEN-REDUCTION-PHI ir<%sum.b>.3 = phi ir<0>, ir<%sum.b.next>.3
-; UF4-NEXT:    EMIT vp<[[VP4:%[0-9]+]]> = WIDEN-CANONICAL-INDUCTION vp<%index>
-; UF4-NEXT:    EMIT vp<[[VP5:%[0-9]+]]> = WIDEN-CANONICAL-INDUCTION vp<%index>, ir<1>
-; UF4-NEXT:    EMIT vp<[[VP6:%[0-9]+]]> = WIDEN-CANONICAL-INDUCTION vp<%index>, ir<2>
-; UF4-NEXT:    EMIT vp<[[VP7:%[0-9]+]]> = WIDEN-CANONICAL-INDUCTION vp<%index>, ir<3>
-; UF4-NEXT:    EMIT vp<[[VP8:%[0-9]+]]> = icmp ule vp<[[VP4]]>, vp<[[VP3]]>
-; UF4-NEXT:    EMIT vp<[[VP9:%[0-9]+]]> = icmp ule vp<[[VP5]]>, vp<[[VP3]]>
-; UF4-NEXT:    EMIT vp<[[VP10:%[0-9]+]]> = icmp ule vp<[[VP6]]>, vp<[[VP3]]>
-; UF4-NEXT:    EMIT vp<[[VP11:%[0-9]+]]> = icmp ule vp<[[VP7]]>, vp<[[VP3]]>
+; UF4-NEXT:    EMIT vp<[[VP4:%[0-9]+]]> = broadcast vp<%index>
+; UF4-NEXT:    EMIT vp<[[VP5:%[0-9]+]]> = step-vector i64
+; UF4-NEXT:    EMIT vp<%vec.iv> = add vp<[[VP4]]>, vp<[[VP5]]>
+; UF4-NEXT:    EMIT vp<[[VP6:%[0-9]+]]> = broadcast ir<4>
+; UF4-NEXT:    EMIT vp<[[VP7:%[0-9]+]]> = add vp<[[VP6]]>, vp<[[VP5]]>
+; UF4-NEXT:    EMIT vp<%vec.iv>.1 = add vp<[[VP4]]>, vp<[[VP7]]>
+; UF4-NEXT:    EMIT vp<[[VP8:%[0-9]+]]> = broadcast ir<8>
+; UF4-NEXT:    EMIT vp<[[VP9:%[0-9]+]]> = add vp<[[VP8]]>, vp<[[VP5]]>
+; UF4-NEXT:    EMIT vp<%vec.iv>.2 = add vp<[[VP4]]>, vp<[[VP9]]>
+; UF4-NEXT:    EMIT vp<[[VP10:%[0-9]+]]> = broadcast ir<12>
+; UF4-NEXT:    EMIT vp<[[VP11:%[0-9]+]]> = add vp<[[VP10]]>, vp<[[VP5]]>
+; UF4-NEXT:    EMIT vp<%vec.iv>.3 = add vp<[[VP4]]>, vp<[[VP11]]>
+; UF4-NEXT:    EMIT vp<[[VP12:%[0-9]+]]> = icmp ule vp<%vec.iv>, vp<[[VP3]]>
+; UF4-NEXT:    EMIT vp<[[VP13:%[0-9]+]]> = icmp ule vp<%vec.iv>.1, vp<[[VP3]]>
+; UF4-NEXT:    EMIT vp<[[VP14:%[0-9]+]]> = icmp ule vp<%vec.iv>.2, vp<[[VP3]]>
+; UF4-NEXT:    EMIT vp<[[VP15:%[0-9]+]]> = icmp ule vp<%vec.iv>.3, vp<[[VP3]]>
 ; UF4-NEXT:    CLONE ir<%ga> = getelementptr inbounds ir<%a>, vp<%index>
 ; UF4-NEXT:    CLONE ir<%gb> = getelementptr inbounds ir<%b>, vp<%index>
-; UF4-NEXT:    vp<[[VP12:%[0-9]+]]> = vector-pointer inbounds ir<%ga>, ir<4>
-; UF4-NEXT:    vp<[[VP13:%[0-9]+]]> = vector-pointer inbounds ir<%ga>, ir<8>
-; UF4-NEXT:    vp<[[VP14:%[0-9]+]]> = vector-pointer inbounds ir<%ga>, ir<12>
-; UF4-NEXT:    WIDEN ir<%la> = load ir<%ga>, vp<[[VP8]]>
-; UF4-NEXT:    WIDEN ir<%la>.1 = load vp<[[VP12]]>, vp<[[VP9]]>
-; UF4-NEXT:    WIDEN ir<%la>.2 = load vp<[[VP13]]>, vp<[[VP10]]>
-; UF4-NEXT:    WIDEN ir<%la>.3 = load vp<[[VP14]]>, vp<[[VP11]]>
-; UF4-NEXT:    vp<[[VP15:%[0-9]+]]> = vector-pointer inbounds ir<%gb>, ir<4>
-; UF4-NEXT:    vp<[[VP16:%[0-9]+]]> = vector-pointer inbounds ir<%gb>, ir<8>
-; UF4-NEXT:    vp<[[VP17:%[0-9]+]]> = vector-pointer inbounds ir<%gb>, ir<12>
-; UF4-NEXT:    WIDEN ir<%lb> = load ir<%gb>, vp<[[VP8]]>
-; UF4-NEXT:    WIDEN ir<%lb>.1 = load vp<[[VP15]]>, vp<[[VP9]]>
-; UF4-NEXT:    WIDEN ir<%lb>.2 = load vp<[[VP16]]>, vp<[[VP10]]>
-; UF4-NEXT:    WIDEN ir<%lb>.3 = load vp<[[VP17]]>, vp<[[VP11]]>
+; UF4-NEXT:    vp<[[VP16:%[0-9]+]]> = vector-pointer inbounds ir<%ga>, ir<4>
+; UF4-NEXT:    vp<[[VP17:%[0-9]+]]> = vector-pointer inbounds ir<%ga>, ir<8>
+; UF4-NEXT:    vp<[[VP18:%[0-9]+]]> = vector-pointer inbounds ir<%ga>, ir<12>
+; UF4-NEXT:    WIDEN ir<%la> = load ir<%ga>, vp<[[VP12]]>
+; UF4-NEXT:    WIDEN ir<%la>.1 = load vp<[[VP16]]>, vp<[[VP13]]>
+; UF4-NEXT:    WIDEN ir<%la>.2 = load vp<[[VP17]]>, vp<[[VP14]]>
+; UF4-NEXT:    WIDEN ir<%la>.3 = load vp<[[VP18]]>, vp<[[VP15]]>
+; UF4-NEXT:    vp<[[VP19:%[0-9]+]]> = vector-pointer inbounds ir<%gb>, ir<4>
+; UF4-NEXT:    vp<[[VP20:%[0-9]+]]> = vector-pointer inbounds ir<%gb>, ir<8>
+; UF4-NEXT:    vp<[[VP21:%[0-9]+]]> = vector-pointer inbounds ir<%gb>, ir<12>
+; UF4-NEXT:    WIDEN ir<%lb> = load ir<%gb>, vp<[[VP12]]>
+; UF4-NEXT:    WIDEN ir<%lb>.1 = load vp<[[VP19]]>, vp<[[VP13]]>
+; UF4-NEXT:    WIDEN ir<%lb>.2 = load vp<[[VP20]]>, vp<[[VP14]]>
+; UF4-NEXT:    WIDEN ir<%lb>.3 = load vp<[[VP21]]>, vp<[[VP15]]>
 ; UF4-NEXT:    WIDEN ir<%sum.a.next> = add ir<%sum.a>, ir<%la>
 ; UF4-NEXT:    WIDEN ir<%sum.a.next>.1 = add ir<%sum.a>.1, ir<%la>.1
 ; UF4-NEXT:    WIDEN ir<%sum.a.next>.2 = add ir<%sum.a>.2, ir<%la>.2
@@ -106,8 +114,8 @@ define i32 @two_reductions(i64 %N, ptr %a, ptr %b) {
 ; UF4-NEXT:    WIDEN ir<%sum.b.next>.2 = add ir<%sum.b>.2, ir<%lb>.2
 ; UF4-NEXT:    WIDEN ir<%sum.b.next>.3 = add ir<%sum.b>.3, ir<%lb>.3
 ; UF4-NEXT:    EMIT vp<%index.next> = add vp<%index>, ir<16>
-; UF4-NEXT:    EMIT vp<[[VP18:%[0-9]+]]> = icmp eq vp<%index.next>, vp<%n.vec>
-; UF4-NEXT:    EMIT branch-on-cond vp<[[VP18]]>
+; UF4-NEXT:    EMIT vp<[[VP22:%[0-9]+]]> = icmp eq vp<%index.next>, vp<%n.vec>
+; UF4-NEXT:    EMIT branch-on-cond vp<[[VP22]]>
 ; UF4-NEXT:  Successor(s): middle.block, vector.body
 ; UF4-EMPTY:
 ; UF4-NEXT:  middle.block:



More information about the llvm-commits mailing list