LLVM 24.0.0git
VPlanConstruction.cpp
Go to the documentation of this file.
1//===-- VPlanConstruction.cpp - Transforms for initial VPlan construction -===//
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//===----------------------------------------------------------------------===//
8///
9/// \file
10/// This file implements transforms for initial VPlan construction.
11///
12//===----------------------------------------------------------------------===//
13
15#include "VPlan.h"
16#include "VPlanAnalysis.h"
17#include "VPlanCFG.h"
18#include "VPlanDominatorTree.h"
19#include "VPlanHelpers.h"
20#include "VPlanPatternMatch.h"
21#include "VPlanTransforms.h"
22#include "VPlanUtils.h"
23#include "llvm/ADT/Sequence.h"
26#include "llvm/Analysis/Loads.h"
33#include "llvm/IR/InstrTypes.h"
34#include "llvm/IR/MDBuilder.h"
35#include "llvm/Support/Debug.h"
39
40#define DEBUG_TYPE "vplan"
41
42using namespace llvm;
43using namespace LoopVectorizationUtils;
44using namespace VPlanPatternMatch;
45
46namespace {
47// Class that is used to build the plain CFG for the incoming IR.
48class PlainCFGBuilder {
49 // The outermost loop of the input loop nest considered for vectorization.
50 Loop *TheLoop;
51
52 // Loop Info analysis.
53 LoopInfo *LI;
54
55 // Loop versioning for alias metadata.
56 LoopVersioning *LVer;
57
58 // Lazily provides branch probabilities for the incoming IR.
59 function_ref<const BranchProbabilityInfo &()> GetBPI;
60
61 // The BranchProbabilityInfo returned by GetBPI, cached on first use.
62 const BranchProbabilityInfo *BPI = nullptr;
63
64 // Vectorization plan that we are working on.
65 std::unique_ptr<VPlan> Plan;
66
67 // Builder of the VPlan instruction-level representation.
68 VPBuilder VPIRBuilder;
69
70 // NOTE: The following maps are intentionally destroyed after the plain CFG
71 // construction because subsequent VPlan-to-VPlan transformation may
72 // invalidate them.
73 // Map incoming BasicBlocks to their newly-created VPBasicBlocks.
75 // Map incoming Value definitions to their newly-created VPValues.
76 DenseMap<Value *, VPValue *> IRDef2VPValue;
77
78 // Hold phi node's that need to be fixed once the plain CFG has been built.
80
81 // Utility functions.
82 void setVPBBPredsFromBB(VPBasicBlock *VPBB, BasicBlock *BB);
83 void fixHeaderPhis();
84 VPBasicBlock *getOrCreateVPBB(BasicBlock *BB);
85#ifndef NDEBUG
86 bool isExternalDef(Value *Val);
87#endif
88 VPValue *getOrCreateVPOperand(Value *IRVal);
89 void createVPInstructionsForVPBB(VPBasicBlock *VPBB, BasicBlock *BB);
90 VPIRMetadata getTerminatorMetadata(Instruction &Term);
91
92public:
93 PlainCFGBuilder(Loop *Lp, LoopInfo *LI, LoopVersioning *LVer, Type *IdxTy,
94 function_ref<const BranchProbabilityInfo &()> GetBPI)
95 : TheLoop(Lp), LI(LI), LVer(LVer), GetBPI(GetBPI),
96 Plan(std::make_unique<VPlan>(Lp, IdxTy)) {}
97
98 /// Build plain CFG for TheLoop and connect it to Plan's entry.
99 std::unique_ptr<VPlan> buildPlainCFG();
100};
101} // anonymous namespace
102
103// Set predecessors of \p VPBB in the same order as they are in \p BB. \p VPBB
104// must have no predecessors.
105void PlainCFGBuilder::setVPBBPredsFromBB(VPBasicBlock *VPBB, BasicBlock *BB) {
106 // Collect VPBB predecessors.
108 for (BasicBlock *Pred : predecessors(BB))
109 VPBBPreds.push_back(getOrCreateVPBB(Pred));
110 VPBB->setPredecessors(VPBBPreds);
111}
112
113static bool isHeaderBB(BasicBlock *BB, Loop *L) {
114 return L && BB == L->getHeader();
115}
116
117// Add operands to VPInstructions representing phi nodes from the input IR.
118void PlainCFGBuilder::fixHeaderPhis() {
119 for (auto *Phi : PhisToFix) {
120 assert(IRDef2VPValue.count(Phi) && "Missing VPInstruction for PHINode.");
121 VPValue *VPVal = IRDef2VPValue[Phi];
122 assert(isa<VPPhi>(VPVal) && "Expected VPPhi for phi node.");
123 auto *PhiR = cast<VPPhi>(VPVal);
124 assert(PhiR->getNumOperands() == 0 && "Expected VPPhi with no operands.");
125 assert(isHeaderBB(Phi->getParent(), LI->getLoopFor(Phi->getParent())) &&
126 "Expected Phi in header block.");
127 assert(Phi->getNumOperands() == 2 &&
128 "header phi must have exactly 2 operands");
129 for (BasicBlock *Pred : predecessors(Phi->getParent()))
130 PhiR->addIncoming(
131 getOrCreateVPOperand(Phi->getIncomingValueForBlock(Pred)));
132 }
133}
134
135// Create a new empty VPBasicBlock for an incoming BasicBlock or retrieve an
136// existing one if it was already created.
137VPBasicBlock *PlainCFGBuilder::getOrCreateVPBB(BasicBlock *BB) {
138 if (auto *VPBB = BB2VPBB.lookup(BB)) {
139 // Retrieve existing VPBB.
140 return VPBB;
141 }
142
143 // Create new VPBB.
144 StringRef Name = BB->getName();
145 LLVM_DEBUG(dbgs() << "Creating VPBasicBlock for " << Name << "\n");
146 VPBasicBlock *VPBB = Plan->createVPBasicBlock(Name);
147 BB2VPBB[BB] = VPBB;
148 return VPBB;
149}
150
151#ifndef NDEBUG
152// Return true if \p Val is considered an external definition. An external
153// definition is either:
154// 1. A Value that is not an Instruction. This will be refined in the future.
155// 2. An Instruction that is outside of the IR region represented in VPlan,
156// i.e., is not part of the loop nest.
157bool PlainCFGBuilder::isExternalDef(Value *Val) {
158 // All the Values that are not Instructions are considered external
159 // definitions for now.
161 if (!Inst)
162 return true;
163
164 // Check whether Instruction definition is in loop body.
165 return !TheLoop->contains(Inst);
166}
167#endif
168
169// Create a new VPValue or retrieve an existing one for the Instruction's
170// operand \p IRVal. This function must only be used to create/retrieve VPValues
171// for *Instruction's operands* and not to create regular VPInstruction's. For
172// the latter, please, look at 'createVPInstructionsForVPBB'.
173VPValue *PlainCFGBuilder::getOrCreateVPOperand(Value *IRVal) {
174 auto VPValIt = IRDef2VPValue.find(IRVal);
175 if (VPValIt != IRDef2VPValue.end())
176 // Operand has an associated VPInstruction or VPValue that was previously
177 // created.
178 return VPValIt->second;
179
180 // Operand doesn't have a previously created VPInstruction/VPValue. This
181 // means that operand is:
182 // A) a definition external to VPlan,
183 // B) any other Value without specific representation in VPlan.
184 // For now, we use VPValue to represent A and B and classify both as external
185 // definitions. We may introduce specific VPValue subclasses for them in the
186 // future.
187 assert(isExternalDef(IRVal) && "Expected external definition as operand.");
188
189 // A and B: Create VPValue and add it to the pool of external definitions and
190 // to the Value->VPValue map.
191 VPValue *NewVPVal = Plan->getOrAddLiveIn(IRVal);
192 IRDef2VPValue[IRVal] = NewVPVal;
193 return NewVPVal;
194}
195
196// Returns the metadata to preserve for terminator \p Term.
197VPIRMetadata PlainCFGBuilder::getTerminatorMetadata(Instruction &Term) {
198 VPIRMetadata MD(Term);
199 if (MD.getMetadata(LLVMContext::MD_prof))
200 return MD;
201 // Estimates are only read for edges inside the loop region.
202 if (!TheLoop->isInnermost() || Term.getParent() == TheLoop->getLoopLatch())
203 return MD;
204 // The weights describe the edges leaving Term in the order of its successors,
205 // matching the successor order of the VPBasicBlock created for Term's parent.
206 if (!BPI)
207 BPI = &GetBPI();
208 auto Weights = map_to_vector(seq(Term.getNumSuccessors()), [&](unsigned I) {
209 return BPI->getEdgeProbability(Term.getParent(), I).getNumerator();
210 });
211 MD.setEstimatedBranchWeights(
212 MDBuilder(Plan->getContext()).createBranchWeights(Weights));
213 return MD;
214}
215
216// Create new VPInstructions in a VPBasicBlock, given its BasicBlock
217// counterpart. This function must be invoked in RPO so that the operands of a
218// VPInstruction in \p BB have been visited before (except for Phi nodes).
219void PlainCFGBuilder::createVPInstructionsForVPBB(VPBasicBlock *VPBB,
220 BasicBlock *BB) {
221 VPIRBuilder.setInsertPoint(VPBB);
222 // TODO: Model and preserve debug intrinsics in VPlan.
223 for (Instruction &InstRef : *BB) {
224 Instruction *Inst = &InstRef;
225
226 // There shouldn't be any VPValue for Inst at this point. Otherwise, we
227 // visited Inst when we shouldn't, breaking the RPO traversal order.
228 assert(!IRDef2VPValue.count(Inst) &&
229 "Instruction shouldn't have been visited.");
230
231 if (isa<UncondBrInst>(Inst))
232 // Skip the rest of the Instruction processing for Branch instructions.
233 continue;
234
235 if (auto *Br = dyn_cast<CondBrInst>(Inst)) {
236 // Conditional branch instruction are represented using BranchOnCond
237 // recipes.
238 VPValue *Cond = getOrCreateVPOperand(Br->getCondition());
239 VPIRBuilder.createNaryOp(VPInstruction::BranchOnCond, {Cond}, Inst, {},
240 getTerminatorMetadata(*Inst),
241 Inst->getDebugLoc());
242 continue;
243 }
244
245 if (auto *SI = dyn_cast<SwitchInst>(Inst)) {
246 // Don't emit recipes for unconditional switch instructions.
247 if (SI->getNumCases() == 0)
248 continue;
249 SmallVector<VPValue *> Ops = {getOrCreateVPOperand(SI->getCondition())};
250 for (auto Case : SI->cases())
251 Ops.push_back(getOrCreateVPOperand(Case.getCaseValue()));
252 VPIRBuilder.createNaryOp(Instruction::Switch, Ops, Inst, {},
253 getTerminatorMetadata(*Inst),
254 Inst->getDebugLoc());
255 continue;
256 }
257
258 VPSingleDefRecipe *NewR;
259 if (auto *Phi = dyn_cast<PHINode>(Inst)) {
260 // Phi node's operands may not have been visited at this point. We create
261 // an empty VPInstruction that we will fix once the whole plain CFG has
262 // been built.
263 NewR = VPIRBuilder.createScalarPhi({}, Phi->getDebugLoc(), "vec.phi",
264 *Phi, Phi->getType());
265 NewR->setUnderlyingValue(Phi);
266 if (isHeaderBB(Phi->getParent(), LI->getLoopFor(Phi->getParent()))) {
267 // Header phis need to be fixed after the VPBB for the latch has been
268 // created.
269 PhisToFix.push_back(Phi);
270 } else {
271 // Add operands for VPPhi in the order matching its predecessors in
272 // VPlan.
273 DenseMap<const VPBasicBlock *, VPValue *> VPPredToIncomingValue;
274 for (unsigned I = 0; I != Phi->getNumOperands(); ++I) {
275 VPPredToIncomingValue[BB2VPBB[Phi->getIncomingBlock(I)]] =
276 getOrCreateVPOperand(Phi->getIncomingValue(I));
277 }
278 for (VPBlockBase *Pred : VPBB->getPredecessors())
279 cast<VPPhi>(NewR)->addIncoming(
280 VPPredToIncomingValue.lookup(Pred->getExitingBasicBlock()));
281 }
282 } else {
283 // Build VPIRMetadata from the instruction and add loop versioning
284 // metadata for loads and stores.
285 VPIRMetadata MD(*Inst);
286 if (isa<LoadInst, StoreInst>(Inst) && LVer) {
287 const auto &[AliasScopeMD, NoAliasMD] =
288 LVer->getNoAliasMetadataFor(Inst);
289 if (AliasScopeMD)
290 MD.setMetadata(LLVMContext::MD_alias_scope, AliasScopeMD);
291 if (NoAliasMD)
292 MD.setMetadata(LLVMContext::MD_noalias, NoAliasMD);
293 }
294
295 // Translate LLVM-IR operands into VPValue operands and set them in the
296 // new VPInstruction.
297 SmallVector<VPValue *, 4> VPOperands;
298 for (Value *Op : Inst->operands())
299 VPOperands.push_back(getOrCreateVPOperand(Op));
300 if (auto *EVI = dyn_cast<ExtractValueInst>(Inst))
301 for (unsigned Idx : EVI->indices())
302 VPOperands.push_back(Plan->getConstantInt(32, Idx));
303 NewR = VPIRBuilder.createNaryOp(Inst->getOpcode(), VPOperands, Inst,
304 VPIRFlags(*Inst), MD, Inst->getDebugLoc(),
305 "", Inst->getType());
306 }
307
308 IRDef2VPValue[Inst] = NewR;
309 }
310}
311
312// Main interface to build the plain CFG.
313std::unique_ptr<VPlan> PlainCFGBuilder::buildPlainCFG() {
314 VPIRBasicBlock *Entry = cast<VPIRBasicBlock>(Plan->getEntry());
315 BB2VPBB[Entry->getIRBasicBlock()] = Entry;
316 for (VPIRBasicBlock *ExitVPBB : Plan->getExitBlocks())
317 BB2VPBB[ExitVPBB->getIRBasicBlock()] = ExitVPBB;
318
319 // 1. Scan the body of the loop in a topological order to visit each basic
320 // block after having visited its predecessor basic blocks. Create a VPBB for
321 // each BB and link it to its successor and predecessor VPBBs. Note that
322 // predecessors must be set in the same order as they are in the incomming IR.
323 // Otherwise, there might be problems with existing phi nodes and algorithm
324 // based on predecessors traversal.
325
326 // Loop PH needs to be explicitly visited since it's not taken into account by
327 // LoopBlocksDFS.
328 BasicBlock *ThePreheaderBB = TheLoop->getLoopPreheader();
329 assert((ThePreheaderBB->getTerminator()->getNumSuccessors() == 1) &&
330 "Unexpected loop preheader");
331 for (auto &I : *ThePreheaderBB) {
332 if (I.getType()->isVoidTy())
333 continue;
334 IRDef2VPValue[&I] = Plan->getOrAddLiveIn(&I);
335 }
336
337 LoopBlocksRPO RPO(TheLoop);
338 RPO.perform(LI);
339
340 for (BasicBlock *BB : RPO) {
341 // Create or retrieve the VPBasicBlock for this BB.
342 VPBasicBlock *VPBB = getOrCreateVPBB(BB);
343 // Set VPBB predecessors in the same order as they are in the incoming BB.
344 setVPBBPredsFromBB(VPBB, BB);
345
346 // Create VPInstructions for BB.
347 createVPInstructionsForVPBB(VPBB, BB);
348
349 // Set VPBB successors. We create empty VPBBs for successors if they don't
350 // exist already. Recipes will be created when the successor is visited
351 // during the RPO traversal.
352 if (auto *SI = dyn_cast<SwitchInst>(BB->getTerminator())) {
354 getOrCreateVPBB(SI->getDefaultDest())};
355 for (auto Case : SI->cases())
356 Succs.push_back(getOrCreateVPBB(Case.getCaseSuccessor()));
357 VPBB->setSuccessors(Succs);
358 continue;
359 }
360 if (auto *BI = dyn_cast<UncondBrInst>(BB->getTerminator())) {
361 VPBB->setOneSuccessor(getOrCreateVPBB(BI->getSuccessor()));
362 continue;
363 }
364 auto *BI = cast<CondBrInst>(BB->getTerminator());
365 BasicBlock *IRSucc0 = BI->getSuccessor(0);
366 BasicBlock *IRSucc1 = BI->getSuccessor(1);
367 VPBasicBlock *Successor0 = getOrCreateVPBB(IRSucc0);
368 VPBasicBlock *Successor1 = getOrCreateVPBB(IRSucc1);
369 VPBB->setTwoSuccessors(Successor0, Successor1);
370 }
371
372 for (auto *EB : Plan->getExitBlocks())
373 setVPBBPredsFromBB(EB, EB->getIRBasicBlock());
374
375 // 2. The whole CFG has been built at this point so all the input Values must
376 // have a VPlan counterpart. Fix VPlan header phi by adding their
377 // corresponding VPlan operands.
378 fixHeaderPhis();
379
380 Plan->getEntry()->setOneSuccessor(getOrCreateVPBB(TheLoop->getHeader()));
381 Plan->getEntry()->setPlan(&*Plan);
382
383 // Fix VPlan loop-closed-ssa exit phi's by adding incoming operands to the
384 // VPIRInstructions wrapping them.
385 // // Note that the operand order corresponds to IR predecessor order, and may
386 // need adjusting when VPlan predecessors are added, if an exit block has
387 // multiple predecessor.
388 for (auto *EB : Plan->getExitBlocks()) {
389 for (VPRecipeBase &R : EB->phis()) {
390 auto *PhiR = cast<VPIRPhi>(&R);
391 PHINode &Phi = PhiR->getIRPhi();
392 assert(PhiR->getNumOperands() == 0 &&
393 "no phi operands should be added yet");
394 for (BasicBlock *Pred : predecessors(EB->getIRBasicBlock()))
395 PhiR->addIncoming(
396 getOrCreateVPOperand(Phi.getIncomingValueForBlock(Pred)));
397 }
398 }
399
400 LLVM_DEBUG(Plan->setName("Plain CFG\n"); dbgs() << *Plan);
401 return std::move(Plan);
402}
403
404/// Checks if \p HeaderVPB is a loop header block in the plain CFG; that is, it
405/// has exactly 2 predecessors (preheader and latch), where the block
406/// dominates the latch and the preheader dominates the block. If it is a
407/// header block return true and canonicalize the predecessors of the header
408/// (making sure the preheader appears first and the latch second) and the
409/// successors of the latch (making sure the loop exit comes first). Otherwise
410/// return false.
412 const VPDominatorTree &VPDT) {
413 ArrayRef<VPBlockBase *> Preds = HeaderVPB->getPredecessors();
414 if (Preds.size() != 2)
415 return false;
416
417 auto *PreheaderVPBB = Preds[0];
418 auto *LatchVPBB = Preds[1];
419 if (!VPDT.dominates(PreheaderVPBB, HeaderVPB) ||
420 !VPDT.dominates(HeaderVPB, LatchVPBB)) {
421 std::swap(PreheaderVPBB, LatchVPBB);
422
423 if (!VPDT.dominates(PreheaderVPBB, HeaderVPB) ||
424 !VPDT.dominates(HeaderVPB, LatchVPBB))
425 return false;
426
427 // Canonicalize predecessors of header so that preheader is first and
428 // latch second.
429 HeaderVPB->swapPredecessors();
430 for (VPRecipeBase &R : cast<VPBasicBlock>(HeaderVPB)->phis())
431 R.swapOperands();
432 }
433
434 // The two successors of conditional branch match the condition, with the
435 // first successor corresponding to true and the second to false. We
436 // canonicalize the successors of the latch when introducing the region, such
437 // that the latch exits the region when its condition is true; invert the
438 // original condition if the original CFG branches to the header on true.
439 // Note that the exit edge is not yet connected for top-level loops.
440 if (LatchVPBB->getSingleSuccessor() ||
441 LatchVPBB->getSuccessors()[0] != HeaderVPB)
442 return true;
443
444 assert(LatchVPBB->getNumSuccessors() == 2 && "Must have 2 successors");
445 auto *Term = cast<VPBasicBlock>(LatchVPBB)->getTerminator();
446 assert(cast<VPInstruction>(Term)->getOpcode() ==
448 "terminator must be a BranchOnCond");
449 auto *Not = new VPInstruction(VPInstruction::Not, {Term->getOperand(0)});
450 Not->insertBefore(Term);
451 Term->setOperand(0, Not);
452 LatchVPBB->swapSuccessors();
453
454 return true;
455}
456
457/// Create a new VPRegionBlock for the loop starting at \p HeaderVPB. For the
458/// outermost loop adjust the regions exiting terminator to be based on the
459/// canonical IV.
460static void createLoopRegion(VPlan &Plan, VPBlockBase *HeaderVPB, DebugLoc DL) {
461 auto *PreheaderVPBB = HeaderVPB->getPredecessors()[0];
462 auto *LatchVPBB = cast<VPBasicBlock>(HeaderVPB->getPredecessors()[1]);
463 auto *OutermostHeaderVPBB =
465
466 VPBlockUtils::disconnectBlocks(PreheaderVPBB, HeaderVPB);
467 VPBlockUtils::disconnectBlocks(LatchVPBB, HeaderVPB);
468
469 // Create an empty region first and insert it between PreheaderVPBB and
470 // the exit blocks, taking care to preserve the original predecessor &
471 // successor order of blocks. Set region entry and exiting after both
472 // HeaderVPB and LatchVPBB have been disconnected from their
473 // predecessors/successors. Only the outermost loop has a canonical IV. Nested
474 // loops are assigned a canonical IV of null type and unknown debug location.
475 bool IsOutermost = HeaderVPB == OutermostHeaderVPBB;
476 Type *CanIVTy = nullptr;
477 if (IsOutermost)
478 CanIVTy = Plan.getVectorTripCount().getType();
479 else
481 auto *R = Plan.createLoopRegion(CanIVTy, DL);
482
483 // Transfer latch's successors to the region.
485
486 VPBlockUtils::connectBlocks(PreheaderVPBB, R);
487 R->setEntry(HeaderVPB);
488 R->setExiting(LatchVPBB);
489
490 // All VPBB's reachable shallowly from HeaderVPB belong to the current region.
491 for (VPBlockBase *VPBB : vp_depth_first_shallow(HeaderVPB))
492 VPBB->setParent(R);
493
494 if (!IsOutermost)
495 return;
496
497 auto *LatchTerm = LatchVPBB->getTerminator();
498 VPBuilder Builder(LatchTerm);
499 // Add a VPInstruction to increment the scalar canonical IV by VF * UF.
500 // Initially the induction increment is guaranteed to not wrap, but that may
501 // change later, e.g. when tail-folding, when the flags need to be dropped.
502 auto *CanonicalIVIncrement = Builder.createAdd(
503 R->getCanonicalIV(), &Plan.getVFxUF(), DL, "index.next", {true, false});
504
505 if (match(LatchTerm, m_BranchOnTwoConds())) {
506 auto *IsLatchExitTaken = Builder.createICmp(
507 CmpInst::ICMP_EQ, CanonicalIVIncrement, &Plan.getVectorTripCount());
508 LatchTerm->setOperand(1, IsLatchExitTaken);
509 } else {
510 // We are replacing the branch to exit the region. Remove the original
511 // BranchOnCond.
512 assert(match(LatchTerm, m_BranchOnCond()) && "Unexpected terminator");
513 DebugLoc LatchDL = LatchTerm->getDebugLoc();
514 Builder.createNaryOp(VPInstruction::BranchOnCount,
515 {CanonicalIVIncrement, &Plan.getVectorTripCount()},
516 LatchDL);
517 LatchTerm->eraseFromParent();
518 }
519}
520
521/// Creates extracts for values in \p Plan defined in a loop region and used
522/// outside a loop region.
523static void createExtractsForLiveOuts(VPlan &Plan, VPBasicBlock *MiddleVPBB) {
524 VPBuilder B(MiddleVPBB, MiddleVPBB->getFirstNonPhi());
525 for (VPBasicBlock *EB : Plan.getExitBlocks()) {
526 if (!is_contained(EB->predecessors(), MiddleVPBB))
527 continue;
528
529 for (VPRecipeBase &R : EB->phis()) {
530 auto *ExitIRI = cast<VPIRPhi>(&R);
531 VPValue *Exiting = ExitIRI->getIncomingValueForBlock(MiddleVPBB);
532 if (isa<VPIRValue>(Exiting))
533 continue;
534 Exiting = B.createNaryOp(VPInstruction::ExtractLastPart, Exiting);
535 Exiting = B.createNaryOp(VPInstruction::ExtractLastLane, Exiting);
536 ExitIRI->setIncomingValueForBlock(MiddleVPBB, Exiting);
537 }
538 }
539}
540
541static void addInitialSkeleton(VPlan &Plan, Type *InductionTy,
542 PredicatedScalarEvolution &PSE, Loop *TheLoop) {
543 VPDominatorTree VPDT(Plan);
544
545 auto *HeaderVPBB = cast<VPBasicBlock>(Plan.getEntry()->getSingleSuccessor());
546 if (TheLoop->isInnermost()) {
547 canonicalHeaderAndLatch(HeaderVPBB, VPDT);
548 } else {
549 // When vectorizing outer loops, canonicalize all loops up front.
551 for (VPBlockBase *VPB : Blocks)
552 canonicalHeaderAndLatch(VPB, VPDT);
553 }
554 auto *LatchVPBB = cast<VPBasicBlock>(HeaderVPBB->getPredecessors()[1]);
555
556 VPBasicBlock *VecPreheader = Plan.createVPBasicBlock("vector.ph");
557 VPBlockUtils::insertBlockAfter(VecPreheader, Plan.getEntry());
558
559 VPBasicBlock *MiddleVPBB = Plan.createVPBasicBlock("middle.block");
560 // The canonical LatchVPBB has the header block as last successor. If it has
561 // another successor, this successor is an exit block - insert middle block on
562 // its edge. Otherwise, add middle block as another successor retaining header
563 // as last. In the latter case, the latch has no conditional terminator yet,
564 // so insert a placeholder BranchOnCond that always continues to the header.
565 // It will be canonicalized to a BranchOnCount later
566 if (LatchVPBB->getNumSuccessors() == 2) {
567 VPBlockBase *LatchExitVPB = LatchVPBB->getSuccessors()[0];
568 VPBlockUtils::insertOnEdge(LatchVPBB, LatchExitVPB, MiddleVPBB);
569 } else {
570 VPBlockUtils::connectBlocks(LatchVPBB, MiddleVPBB);
571 LatchVPBB->swapSuccessors();
573 {Plan.getFalse()});
574 }
575
576 // Create SCEV and VPValue for the trip count.
577 // We use the symbolic max backedge-taken-count, which works also when
578 // vectorizing loops with uncountable early exits.
579 const SCEV *BackedgeTakenCountSCEV = PSE.getSymbolicMaxBackedgeTakenCount();
580 assert(!isa<SCEVCouldNotCompute>(BackedgeTakenCountSCEV) &&
581 "Invalid backedge-taken count");
582 ScalarEvolution &SE = *PSE.getSE();
583 const SCEV *TripCount = SE.getTripCountFromExitCount(BackedgeTakenCountSCEV,
584 InductionTy, TheLoop);
586
587 VPBasicBlock *ScalarPH = Plan.createVPBasicBlock("scalar.ph");
589
590 // The connection order corresponds to the operands of the conditional branch,
591 // with the middle block already connected to the exit block.
592 VPBlockUtils::connectBlocks(MiddleVPBB, ScalarPH);
593 // Also connect the entry block to the scalar preheader.
594 // TODO: Also introduce a branch recipe together with the minimum trip count
595 // check.
596 VPBlockUtils::connectBlocks(Plan.getEntry(), ScalarPH);
597 Plan.getEntry()->swapSuccessors();
598
599 createExtractsForLiveOuts(Plan, MiddleVPBB);
600
601 // Create resume phis in the scalar preheader for each phi in the scalar loop.
602 // Their incoming value from the vector loop will be the last lane of the
603 // corresponding vector loop header phi.
604 VPBuilder MiddleBuilder(MiddleVPBB, MiddleVPBB->getFirstNonPhi());
605 VPBuilder ScalarPHBuilder(ScalarPH);
606 assert(equal(ScalarPH->getPredecessors(),
607 ArrayRef<VPBlockBase *>({MiddleVPBB, Plan.getEntry()})) &&
608 "unexpected predecessor order of scalar ph");
609 for (const auto &[PhiR, ScalarPhiR] :
610 zip_equal(HeaderVPBB->phis(), Plan.getScalarHeader()->phis())) {
611 auto *VectorPhiR = cast<VPPhi>(&PhiR);
612 VPValue *BackedgeVal = VectorPhiR->getOperand(1);
613 VPValue *ResumeFromVectorLoop =
614 MiddleBuilder.createNaryOp(VPInstruction::ExtractLastPart, BackedgeVal);
615 ResumeFromVectorLoop = MiddleBuilder.createNaryOp(
616 VPInstruction::ExtractLastLane, ResumeFromVectorLoop);
617 // Create scalar resume phi, with the first operand being the incoming value
618 // from the middle block and the second operand coming from the entry block.
619 auto *ResumePhiR = ScalarPHBuilder.createScalarPhi(
620 {ResumeFromVectorLoop, VectorPhiR->getOperand(0)},
621 VectorPhiR->getDebugLoc());
622 cast<VPIRPhi>(&ScalarPhiR)->addIncoming(ResumePhiR);
623 }
624}
625
626/// To make RUN_VPLAN_PASS print initial VPlan.
628
629std::unique_ptr<VPlan> VPlanTransforms::buildVPlan0(
630 Loop *TheLoop, LoopInfo &LI, Type *InductionTy,
632 function_ref<const BranchProbabilityInfo &()> GetBPI) {
633 PlainCFGBuilder Builder(TheLoop, &LI, LVer, InductionTy, GetBPI);
634 std::unique_ptr<VPlan> VPlan0 = Builder.buildPlainCFG();
635 addInitialSkeleton(*VPlan0, InductionTy, PSE, TheLoop);
636 simplifyLiveInsWithSCEV(*VPlan0, PSE);
637
639 return VPlan0;
640}
641
645 auto Frequencies = vputils::computeExecutionFrequencies(Blocks);
646 LLVMContext &Ctx = Plan.getContext();
647 for (VPBasicBlock *VPBB : Blocks) {
648 std::optional<VPExecutionFrequency> Freq = Frequencies.lookup(VPBB);
650 VPI.setExecutionFrequency(Freq, Ctx);
651 }
652}
653
654/// Creates a VPWidenIntOrFpInductionRecipe or VPWidenPointerInductionRecipe
655/// for \p Phi based on \p IndDesc.
656static VPHeaderPHIRecipe *
658 const InductionDescriptor &IndDesc, VPlan &Plan,
659 PredicatedScalarEvolution &PSE, Loop &OrigLoop,
660 DebugLoc DL) {
661 [[maybe_unused]] ScalarEvolution &SE = *PSE.getSE();
662 assert(SE.isLoopInvariant(IndDesc.getStep(), &OrigLoop) &&
663 "step must be loop invariant");
664 assert((Plan.getLiveIn(IndDesc.getStartValue()) == Start ||
665 (SE.isSCEVable(IndDesc.getStartValue()->getType()) &&
666 PSE.getSCEV(IndDesc.getStartValue()) ==
667 vputils::getSCEVExprForVPValue(Start, PSE))) &&
668 "Start VPValue must match IndDesc's start value");
669
670 VPValue *Step =
672
673 VPValue *BackedgeVal = PhiR->getOperand(1);
674 // Replace live-out extracts of WideIV's backedge value by ExitingIVValue
675 // recipes. optimizeInductionLiveOutUsers will later compute the proper
676 // DerivedIV.
677 //
678 // For an IV that requires SCEV predicate, keep extracting the exit values
679 // from the loop directly, as the pre-computed exit value as-is would be
680 // incorrect outside the loop.
681 auto ReplaceExtractsWithExitingIVValueIfPossible = [&](VPWidenInductionRecipe
682 *WideIV) {
683 bool IsPredicated = !WideIV->getNoWrapPredicates().empty();
684 for (VPUser *U : to_vector(BackedgeVal->users())) {
686 continue;
687 auto *ExtractLastPart = cast<VPInstruction>(U);
688 VPUser *ExtractLastPartUser = ExtractLastPart->getSingleUser();
689 assert(ExtractLastPartUser && "must have a single user");
690 if (!match(ExtractLastPartUser, m_ExtractLastLane(m_VPValue())))
691 continue;
692 auto *ExtractLastLane = cast<VPInstruction>(ExtractLastPartUser);
693 assert(is_contained(ExtractLastLane->getParent()->successors(),
694 Plan.getScalarPreheader()) &&
695 "last lane must be extracted in the middle block");
696 // Keep the vector extract for exit-block live-out uses of a predicated
697 // IV.
698 if (IsPredicated &&
699 any_of(ExtractLastLane->users(), [&](VPUser *LaneUser) {
700 auto *R = cast<VPRecipeBase>(LaneUser);
701 return Plan.isExitBlock(R->getParent());
702 }))
703 continue;
704 VPBuilder Builder(ExtractLastLane);
705 ExtractLastLane->replaceAllUsesWith(
706 Builder.createNaryOp(VPInstruction::ExitingIVValue, {WideIV}));
707 ExtractLastLane->eraseFromParent();
708 ExtractLastPart->eraseFromParent();
709 }
710 };
711
713 auto *WideIV = new VPWidenPointerInductionRecipe(
714 Phi, Start, Step, &Plan.getVFxUF(), IndDesc, DL);
715 ReplaceExtractsWithExitingIVValueIfPossible(WideIV);
716 return WideIV;
717 }
718
721 "must have an integer or float induction at this point");
722
723 // Update wide induction increments to use the same step as the corresponding
724 // wide induction. This enables detecting induction increments directly in
725 // VPlan and removes redundant splats.
726 if (match(BackedgeVal, m_Add(m_Specific(PhiR), m_VPValue())))
727 BackedgeVal->getDefiningRecipe()->setOperand(1, Step);
728
729 // It is always safe to copy over the NoWrap and FastMath flags. In
730 // particular, when folding tail by masking, the masked-off lanes are never
731 // used, so it is safe.
732 VPIRFlags Flags = vputils::getFlagsForInduction(IndDesc, PhiR);
733
734 auto *WideIV = new VPWidenIntOrFpInductionRecipe(
735 Phi, Start, Step, &Plan.getVF(), IndDesc, Flags, DL);
736
737 ReplaceExtractsWithExitingIVValueIfPossible(WideIV);
738 return WideIV;
739}
740
741/// Try to sink users of \p FOR after \p Previous. \returns true if sinking
742/// succeeded or was not necessary, and false otherwise.
743static bool
745 VPRecipeBase *Previous,
746 const VPDominatorTree &VPDT) {
747 // Collect recipes that need sinking.
750 Seen.insert(Previous);
751 auto TryToPushSinkCandidate = [&](VPRecipeBase *SinkCandidate) {
752 // The previous value must not depend on the users of the recurrence phi.
753 // In that case, FOR is not a fixed order recurrence.
754 if (SinkCandidate == Previous)
755 return false;
756
757 if (isa<VPHeaderPHIRecipe>(SinkCandidate) ||
758 !Seen.insert(SinkCandidate).second ||
759 VPDT.properlyDominates(Previous, SinkCandidate))
760 return true;
761
762 if (vputils::cannotHoistOrSinkRecipe(*SinkCandidate, /*Sinking=*/true))
763 return false;
764
765 WorkList.push_back(SinkCandidate);
766 return true;
767 };
768
769 // Recursively sink users of FOR after Previous.
770 WorkList.push_back(FOR);
771 for (unsigned I = 0; I != WorkList.size(); ++I) {
772 VPRecipeBase *Current = WorkList[I];
773 assert(Current->getNumDefinedValues() == 1 &&
774 "only recipes with a single defined value expected");
775
776 for (VPUser *User : Current->getVPSingleValue()->users()) {
777 if (!TryToPushSinkCandidate(cast<VPRecipeBase>(User)))
778 return false;
779 }
780 }
781
782 // Keep recipes to sink ordered by dominance so earlier instructions are
783 // processed first.
784 sort(WorkList, [&VPDT](const VPRecipeBase *A, const VPRecipeBase *B) {
785 return VPDT.properlyDominates(A, B);
786 });
787
788 for (VPRecipeBase *SinkCandidate : WorkList) {
789 if (SinkCandidate == FOR)
790 continue;
791
792 SinkCandidate->moveAfter(Previous);
793 Previous = SinkCandidate;
794 }
795 return true;
796}
797
798/// Try to hoist \p Previous and its operands before all users of \p FOR.
799/// \returns true if hoisting succeeded or was not necessary, and false
800/// otherwise.
802 VPRecipeBase *Previous,
803 const VPDominatorTree &VPDT) {
805 return false;
806
807 // Collect recipes that need hoisting.
808 SmallVector<VPRecipeBase *> HoistCandidates;
810 // Find the closest hoist point by looking at all users of FOR and selecting
811 // the recipe dominating all other users.
812 VPRecipeBase *HoistPoint = nullptr;
813 for (VPUser *U : FOR->users()) {
814 auto *R = cast<VPRecipeBase>(U);
815 if (!HoistPoint || VPDT.properlyDominates(R, HoistPoint))
816 HoistPoint = R;
817 }
818 // Dominance is only a partial order, so the users of FOR may not have a
819 // single user dominating all others. Bail out in that case.
820 if (!HoistPoint || HoistPoint->isPhi() ||
821 any_of(FOR->users(), [&VPDT, HoistPoint](VPUser *U) {
822 auto *R = cast<VPRecipeBase>(U);
823 return HoistPoint != R && !VPDT.properlyDominates(HoistPoint, R);
824 }))
825 return false;
826
827 auto NeedsHoisting = [HoistPoint, &VPDT,
828 &Visited](VPValue *HoistCandidateV) -> VPRecipeBase * {
829 VPRecipeBase *HoistCandidate = HoistCandidateV->getDefiningRecipe();
830 if (!HoistCandidate)
831 return nullptr;
832 // Hoist candidate was already visited, no need to hoist.
833 if (!Visited.insert(HoistCandidate).second)
834 return nullptr;
835 // If we reached a recipe that dominates HoistPoint, we don't need to
836 // hoist the recipe.
837 if (VPDT.properlyDominates(HoistCandidate, HoistPoint))
838 return nullptr;
839 return HoistCandidate;
840 };
841
842 if (!NeedsHoisting(Previous->getVPSingleValue()))
843 return true;
844
845 // Recursively try to hoist Previous and its operands before all users of
846 // FOR.
847 HoistCandidates.push_back(Previous);
848
849 for (unsigned I = 0; I != HoistCandidates.size(); ++I) {
850 VPRecipeBase *Current = HoistCandidates[I];
851 assert(Current->getNumDefinedValues() == 1 &&
852 "only recipes with a single defined value expected");
854 return false;
855
856 for (VPValue *Op : Current->operands()) {
857 // If we reach FOR, it means the original Previous depends on some other
858 // recurrence that in turn depends on FOR. If that is the case, we would
859 // also need to hoist recipes involving the other FOR, which may break
860 // dependencies.
861 if (Op == FOR)
862 return false;
863
864 if (auto *R = NeedsHoisting(Op)) {
865 // Bail out if the recipe defines multiple values.
866 // TODO: Hoisting such recipes requires additional handling.
867 if (R->getNumDefinedValues() != 1)
868 return false;
869 HoistCandidates.push_back(R);
870 }
871 }
872 }
873
874 // Moving a candidate to HoistPoint keeps it dominating its other users only
875 // if HoistPoint dominates the candidate's current position.
876 if (any_of(HoistCandidates, [&VPDT, HoistPoint](VPRecipeBase *R) {
877 return !VPDT.properlyDominates(HoistPoint, R);
878 }))
879 return false;
880
881 // Order recipes to hoist by dominance so earlier instructions are processed
882 // first.
883 sort(HoistCandidates, [&VPDT](const VPRecipeBase *A, const VPRecipeBase *B) {
884 return VPDT.properlyDominates(A, B);
885 });
886
887 for (VPRecipeBase *HoistCandidate : HoistCandidates) {
888 HoistCandidate->moveBefore(*HoistPoint->getParent(),
889 HoistPoint->getIterator());
890 }
891
892 return true;
893}
894
895/// Sink users of fixed-order recurrences past or hoist before the recipe
896/// defining the previous value, introduce FirstOrderRecurrenceSplice
897/// VPInstructions, and replace FOR uses. Returns false if hoisting or sinking
898/// fails.
900 const VPDominatorTree &VPDT) {
901 auto FORs =
904 [](VPRecipeBase &R) {
905 return cast<VPFirstOrderRecurrencePHIRecipe>(&R);
906 });
907 for (VPFirstOrderRecurrencePHIRecipe *FOR : FORs) {
908 // Follow through FOR phi chains to find the actual Previous recipe.
909 // Fixed-order recurrences do not contain cycles, so this loop is
910 // guaranteed to terminate.
912 VPRecipeBase *Previous = FOR->getBackedgeValue()->getDefiningRecipe();
913 while (auto *PrevPhi =
915 assert(PrevPhi->getParent() == FOR->getParent() &&
916 "PrevPhi must be in same block as FOR");
917 assert(SeenPhis.insert(PrevPhi).second &&
918 "PrevPhi must not be visited multiple times");
919 Previous = PrevPhi->getBackedgeValue()->getDefiningRecipe();
920 }
921
922 VPBasicBlock *InsertBlock = FOR->getParent();
923 VPBasicBlock::iterator InsertPt = InsertBlock->getFirstNonPhi();
924 if (Previous) {
925 // Sink FOR users after Previous or hoist Previous before FOR users.
926 if (!sinkRecurrenceUsersAfterPrevious(FOR, Previous, VPDT) &&
927 !hoistPreviousBeforeFORUsers(FOR, Previous, VPDT))
928 return false;
929 InsertBlock = Previous->getParent();
930 InsertPt = isa<VPHeaderPHIRecipe>(Previous)
931 ? InsertBlock->getFirstNonPhi()
932 : std::next(Previous->getIterator());
933 }
934
935 // Create FirstOrderRecurrenceSplice and replace FOR uses.
936 VPBuilder LoopBuilder(InsertBlock, InsertPt);
937 auto *RecurSplice =
939 {FOR, FOR->getBackedgeValue()});
940 FOR->replaceUsesWithIf(RecurSplice, not_equal_to(RecurSplice));
941 }
942
943 return true;
944}
945
947 VPlan &Plan, PredicatedScalarEvolution &PSE, Loop &OrigLoop,
951 const SmallPtrSetImpl<const PHINode *> &FixedOrderRecurrences,
952 const SmallPtrSetImpl<PHINode *> &InLoopReductions, bool AllowReordering) {
953 // Retrieve the header manually from the intial plain-CFG VPlan.
954 auto [HeaderVPBB, LatchVPBB] = VPBlockUtils::getPlainCFGHeaderAndLatch(Plan);
955 assert(VPDT.dominates(HeaderVPBB, LatchVPBB) &&
956 "header must dominate its latch");
957
958 auto CreateHeaderPhiRecipe = [&](VPPhi *PhiR) -> VPHeaderPHIRecipe * {
959 // TODO: Gradually replace uses of underlying instruction by analyses on
960 // VPlan.
961 auto *Phi = cast<PHINode>(PhiR->getUnderlyingInstr());
962 assert(PhiR->getNumOperands() == 2 &&
963 "Must have 2 operands for header phis");
964
965 // Extract common values once.
966 VPIRValue *Start = cast<VPIRValue>(PhiR->getOperand(0));
967 VPValue *BackedgeValue = PhiR->getOperand(1);
968
969 if (FixedOrderRecurrences.contains(Phi)) {
970 // TODO: Currently fixed-order recurrences are modeled as chains of
971 // first-order recurrences. If there are no users of the intermediate
972 // recurrences in the chain, the fixed order recurrence should be
973 // modeled directly, enabling more efficient codegen.
974 return new VPFirstOrderRecurrencePHIRecipe(Phi, *Start, *BackedgeValue);
975 }
976
977 auto InductionIt = Inductions.find(Phi);
978 if (InductionIt != Inductions.end())
979 return createWidenInductionRecipe(Phi, PhiR, Start, InductionIt->second,
980 Plan, PSE, OrigLoop,
981 PhiR->getDebugLoc());
982
983 assert(Reductions.contains(Phi) && "only reductions are expected now");
984 const RecurrenceDescriptor &RdxDesc = Reductions.lookup(Phi);
986 Phi->getIncomingValueForBlock(OrigLoop.getLoopPreheader()) &&
987 "incoming value must match start value");
988 // Will be updated later to >1 if reduction is partial.
989 unsigned ScaleFactor = 1;
990 bool UseOrderedReductions = !AllowReordering && RdxDesc.isOrdered();
991 return new VPReductionPHIRecipe(
992 Phi, RdxDesc.getRecurrenceKind(), *Start, *BackedgeValue,
993 getReductionStyle(InLoopReductions.contains(Phi), UseOrderedReductions,
994 ScaleFactor),
995 Phi->getType()->isFloatingPointTy() ? RdxDesc.getFastMathFlags()
996 : VPIRFlags(),
998 };
999
1000 for (VPRecipeBase &R : make_early_inc_range(HeaderVPBB->phis())) {
1001 auto *PhiR = cast<VPPhi>(&R);
1002 VPHeaderPHIRecipe *HeaderPhiR = CreateHeaderPhiRecipe(PhiR);
1003 HeaderPhiR->insertBefore(PhiR);
1004 PhiR->replaceAllUsesWith(HeaderPhiR);
1005 PhiR->eraseFromParent();
1006 }
1007
1008 if (!tryToSinkOrHoistRecurrenceUsers(HeaderVPBB, VPDT)) {
1010 "Failed to sink or hoist user of first-order recurrence",
1011 "CannotSinkHoistFORUser", ORE, &OrigLoop);
1012 return false;
1013 }
1014
1015 // Skip renaming resume phi recipes, if any header phi has been removed.
1016 if (range_size(HeaderVPBB->phis()) !=
1018 return true;
1019 for (const auto &[HeaderPhiR, ScalarPhiR] :
1020 zip_equal(HeaderVPBB->phis(), Plan.getScalarPreheader()->phis())) {
1021 auto *ResumePhiR = cast<VPPhi>(&ScalarPhiR);
1022 if (isa<VPFirstOrderRecurrencePHIRecipe>(&HeaderPhiR)) {
1023 ResumePhiR->setName("scalar.recur.init");
1024 auto *ExtractLastLane = cast<VPInstruction>(ResumePhiR->getOperand(0));
1025 ExtractLastLane->setName("vector.recur.extract");
1026 continue;
1027 }
1028 ResumePhiR->setName(isa<VPWidenInductionRecipe>(HeaderPhiR)
1029 ? "bc.resume.val"
1030 : "bc.merge.rdx");
1031 }
1032 return true;
1033}
1034
1037 bool OptForSize,
1038 unsigned SCEVCheckThreshold,
1040 Loop *TheLoop) {
1041 // Collect which wide IVs have predicates and add them to PSE.
1042 auto [HeaderVPBB, _] = VPBlockUtils::getPlainCFGHeaderAndLatch(Plan);
1044 for (VPWidenInductionRecipe &WideIV :
1045 make_isa_range<VPWidenInductionRecipe>(HeaderVPBB->phis())) {
1046 if (WideIV.getNoWrapPredicates().empty())
1047 continue;
1048 PredicatedIVs.insert(&WideIV);
1049 for (const auto *P : WideIV.getNoWrapPredicates())
1050 PSE.addPredicate(*P);
1051 }
1052
1053 unsigned TotalComplexity = PSE.getPredicate().getComplexity();
1054 if (TotalComplexity && OptForSize) {
1055 LLVM_DEBUG(
1056 dbgs() << "LV: Not vectorizing: SCEV predicates needed for induction "
1057 "but optimizing for size\n");
1059 "Runtime SCEV check is required with -Os/-Oz",
1060 "runtime SCEV checks needed but optimizing for size",
1061 "CantVersionLoopWithOptForSize", ORE, TheLoop);
1062 return false;
1063 }
1064
1065 if (TotalComplexity > SCEVCheckThreshold) {
1066 LLVM_DEBUG(dbgs() << "LV: Not vectorizing: Too many SCEV checks needed ("
1067 << TotalComplexity << " > " << SCEVCheckThreshold
1068 << ")\n");
1070 "Too many SCEV checks needed",
1071 "Too many SCEV assumptions need to be made and checked at runtime",
1072 "TooManySCEVRunTimeChecks", ORE, TheLoop);
1073 return false;
1074 }
1075
1076 return true;
1077}
1078
1080 ElementCount MinVF) {
1083
1084 for (VPRecipeBase &R : Header->phis()) {
1085 auto *PhiR = dyn_cast<VPReductionPHIRecipe>(&R);
1086 if (!PhiR || !PhiR->isInLoop() || (MinVF.isScalar() && !PhiR->isOrdered()))
1087 continue;
1088
1089 RecurKind Kind = PhiR->getRecurrenceKind();
1093 "AnyOf and Find reductions are not allowed for in-loop reductions");
1094
1095 bool IsFPRecurrence =
1097 FastMathFlags FMFs =
1098 IsFPRecurrence ? FastMathFlags::getFast() : FastMathFlags();
1099
1100 // Collect the chain of "link" recipes for the reduction starting at PhiR.
1102 Worklist.insert(PhiR);
1103 for (unsigned I = 0; I != Worklist.size(); ++I) {
1104 VPSingleDefRecipe *Cur = Worklist[I];
1105 for (VPUser *U : Cur->users()) {
1106 auto *UserRecipe = cast<VPSingleDefRecipe>(U);
1107 if (!UserRecipe->getParent()->getEnclosingLoopRegion()) {
1108 assert((UserRecipe->getParent() == Plan.getMiddleBlock() ||
1109 UserRecipe->getParent() == Plan.getScalarPreheader()) &&
1110 "U must be either in the loop region, the middle block or the "
1111 "scalar preheader.");
1112 continue;
1113 }
1114
1115 // Stores using instructions will be sunk later.
1116 if (match(UserRecipe, m_VPInstruction<Instruction::Store>()))
1117 continue;
1118 Worklist.insert(UserRecipe);
1119 }
1120 }
1121
1122 // Visit operation "Links" along the reduction chain top-down starting from
1123 // the phi until LoopExitValue. We keep track of the previous item
1124 // (PreviousLink) to tell which of the two operands of a Link will remain
1125 // scalar and which will be reduced. For minmax by select(cmp), Link will be
1126 // the select instructions. Blend recipes of in-loop reduction phi's will
1127 // get folded to their non-phi operand, as the reduction recipe handles the
1128 // condition directly.
1129 VPSingleDefRecipe *PreviousLink = PhiR; // Aka Worklist[0].
1130 for (VPSingleDefRecipe *CurrentLink : drop_begin(Worklist)) {
1131 if (auto *Blend = dyn_cast<VPBlendRecipe>(CurrentLink)) {
1132 assert(Blend->getNumIncomingValues() == 2 &&
1133 "Blend must have 2 incoming values");
1134 unsigned PhiRIdx = Blend->getIncomingValue(0) == PhiR ? 0 : 1;
1135 assert(Blend->getIncomingValue(PhiRIdx) == PhiR &&
1136 "PhiR must be an operand of the blend");
1137 Blend->replaceAllUsesWith(Blend->getIncomingValue(1 - PhiRIdx));
1138 continue;
1139 }
1140
1141 if (IsFPRecurrence) {
1142 FastMathFlags CurFMF =
1143 cast<VPRecipeWithIRFlags>(CurrentLink)->getFastMathFlagsOrNone();
1144 if (match(CurrentLink, m_Select(m_VPValue(), m_VPValue(), m_VPValue())))
1145 CurFMF |= cast<VPRecipeWithIRFlags>(CurrentLink->getOperand(0))
1146 ->getFastMathFlagsOrNone();
1147 FMFs &= CurFMF;
1148 }
1149
1150 Instruction *CurrentLinkI = CurrentLink->getUnderlyingInstr();
1151
1152 // Recognize a call to the llvm.fmuladd intrinsic.
1153 bool IsFMulAdd = Kind == RecurKind::FMulAdd;
1154 VPValue *VecOp;
1155 VPBasicBlock *LinkVPBB = CurrentLink->getParent();
1156 if (IsFMulAdd) {
1158 "Expected current VPInstruction to be a call to the "
1159 "llvm.fmuladd intrinsic");
1160 assert(CurrentLink->getOperand(2) == PreviousLink &&
1161 "expected a call where the previous link is the added operand");
1162
1163 // If the instruction is a call to the llvm.fmuladd intrinsic then we
1164 // need to create an fmul recipe (multiplying the first two operands of
1165 // the fmuladd together) to use as the vector operand for the fadd
1166 // reduction.
1167 auto *FMulRecipe = new VPInstruction(
1168 Instruction::FMul,
1169 {CurrentLink->getOperand(0), CurrentLink->getOperand(1)},
1170 CurrentLinkI->getFastMathFlags());
1171 LinkVPBB->insert(FMulRecipe, CurrentLink->getIterator());
1172 VecOp = FMulRecipe;
1173 } else if (Kind == RecurKind::AddChainWithSubs &&
1174 match(CurrentLink, m_Sub(m_VPValue(), m_VPValue()))) {
1175 Type *PhiTy = PhiR->getScalarType();
1176 auto *Zero = Plan.getConstantInt(PhiTy, 0);
1177 VPBuilder Builder(LinkVPBB, CurrentLink->getIterator());
1178 auto *Sub = Builder.createSub(Zero, CurrentLink->getOperand(1),
1179 CurrentLinkI->getDebugLoc());
1180 Sub->setUnderlyingValue(CurrentLinkI);
1181 VecOp = Sub;
1182 } else {
1183 // Index of the first operand which holds a non-mask vector operand.
1184 unsigned IndexOfFirstOperand = 0;
1186 if (match(CurrentLink, m_Cmp(m_VPValue(), m_VPValue())))
1187 continue;
1188 assert(match(CurrentLink,
1190 "must be a select recipe");
1191 IndexOfFirstOperand = 1;
1192 }
1193 // Note that for non-commutable operands (cmp-selects), the semantics of
1194 // the cmp-select are captured in the recurrence kind.
1195 unsigned VecOpId =
1196 CurrentLink->getOperand(IndexOfFirstOperand) == PreviousLink
1197 ? IndexOfFirstOperand + 1
1198 : IndexOfFirstOperand;
1199 VecOp = CurrentLink->getOperand(VecOpId);
1200 assert(
1201 VecOp != PreviousLink &&
1202 CurrentLink->getOperand(
1203 cast<VPInstruction>(CurrentLink)->getNumOperandsWithoutMask() -
1204 1 - (VecOpId - IndexOfFirstOperand)) == PreviousLink &&
1205 "PreviousLink must be the operand other than VecOp");
1206 }
1207
1208 assert(PhiR->getVFScaleFactor() == 1 &&
1209 "inloop reductions must be unscaled");
1210 VPValue *CondOp = cast<VPInstruction>(CurrentLink)->getMask();
1211 auto *RedRecipe = new VPReductionRecipe(
1212 Kind, FMFs, CurrentLinkI, PreviousLink, VecOp, CondOp,
1213 getReductionStyle(/*IsInLoop=*/true, PhiR->isOrdered(), 1),
1214 CurrentLinkI->getDebugLoc());
1215 // Append the recipe to the end of the VPBasicBlock because we need to
1216 // ensure that it comes after all of it's inputs, including CondOp.
1217 // Delete CurrentLink as it will be invalid if its operand is replaced
1218 // with a reduction defined at the bottom of the block in the next link.
1219 if (LinkVPBB->getNumSuccessors() == 0)
1220 RedRecipe->insertBefore(&*std::prev(std::prev(LinkVPBB->end())));
1221 else
1222 LinkVPBB->appendRecipe(RedRecipe);
1223
1224 CurrentLink->replaceAllUsesWith(RedRecipe);
1225 // Move any store recipes using the RedRecipe that appear before it in the
1226 // same block to just after the RedRecipe.
1227 for (VPRecipeBase *UserR : make_early_inc_range(
1228 make_isa_range<VPRecipeBase>(RedRecipe->users()))) {
1229 if (UserR->getParent() != LinkVPBB)
1230 continue;
1232 continue;
1233 UserR->moveAfter(RedRecipe);
1234 }
1235 ToDelete.push_back(CurrentLink);
1236 PreviousLink = RedRecipe;
1237 }
1238 }
1239
1240 for (VPRecipeBase *R : ToDelete)
1241 R->eraseFromParent();
1242}
1243
1245 Loop *TheLoop,
1247 DominatorTree &DT,
1248 AssumptionCache *AC) {
1249 ScalarEvolution &SE = *PSE.getSE();
1250 const DataLayout &DL = TheLoop->getHeader()->getDataLayout();
1251 for (VPBasicBlock *VPBB : vp_rpo_plain_cfg_loop_body(HeaderVPBB)) {
1252 for (VPRecipeBase &R : *VPBB) {
1253 auto *VPI = dyn_cast<VPInstruction>(&R);
1254 if (!VPI || VPI->getOpcode() != Instruction::Load) {
1255 assert(!R.mayReadFromMemory() && "unexpected recipe reading memory");
1256 continue;
1257 }
1258
1259 // Get the pointer SCEV for dereferenceability checking.
1260 VPValue *Ptr = VPI->getOperand(0);
1261 const SCEV *PtrSCEV = vputils::getSCEVExprForVPValue(Ptr, PSE, TheLoop);
1262 if (isa<SCEVCouldNotCompute>(PtrSCEV)) {
1263 LLVM_DEBUG(dbgs() << "LV: Not vectorizing: Found non-dereferenceable "
1264 "load with SCEVCouldNotCompute pointer\n");
1265 return false;
1266 }
1267
1268 // Check dereferenceability using the SCEV-based version.
1269 Type *LoadTy = VPI->getScalarType();
1270 const SCEV *SizeSCEV =
1271 SE.getStoreSizeOfExpr(DL.getIndexType(PtrSCEV->getType()), LoadTy);
1272 auto *Load = cast<LoadInst>(VPI->getUnderlyingValue());
1274 if (isDereferenceableAndAlignedInLoop(PtrSCEV, Load->getAlign(), SizeSCEV,
1275 TheLoop, SE, DT, AC, &Preds))
1276 continue;
1277
1278 return false;
1279 }
1280 }
1281 return true;
1282}
1283
1285 auto *MiddleVPBB = VPBlockUtils::getPlainCFGMiddleBlock(Plan);
1286 // Disconnect countable early exits from the loop, leaving it with a single
1287 // exit from the latch. Countable early exits are left for a scalar epilog.
1288 for (auto [EarlyExitingVPBB, EB] : vputils::getEarlyExits(Plan, MiddleVPBB)) {
1289 // Remove phi operands for the early exiting block.
1290 for (VPRecipeBase &R : EB->phis())
1291 cast<VPIRPhi>(&R)->removeIncomingValueFor(EarlyExitingVPBB);
1292 EarlyExitingVPBB->getTerminator()->eraseFromParent();
1293 VPBlockUtils::disconnectBlocks(EarlyExitingVPBB, EB);
1294 }
1295}
1296
1298 auto *MiddleVPBB = VPBlockUtils::getPlainCFGMiddleBlock(Plan);
1299 // If MiddleVPBB has a single successor then the original loop does not exit
1300 // via the latch and the single successor must be the scalar preheader.
1301 // There's no need to add a runtime check to MiddleVPBB.
1302 if (MiddleVPBB->getNumSuccessors() == 1) {
1303 assert(MiddleVPBB->getSingleSuccessor() == Plan.getScalarPreheader() &&
1304 "must have ScalarPH as single successor");
1305 return;
1306 }
1307
1308 assert(MiddleVPBB->getNumSuccessors() == 2 && "must have 2 successors");
1309
1310 // Add a check in the middle block to see if we have completed all of the
1311 // iterations in the first vector loop.
1312 //
1313 // Three cases:
1314 // 1) If we require a scalar epilogue, the scalar ph must execute. Set the
1315 // condition to false.
1316 // 2) If (N - N%VF) == N, then we *don't* need to run the
1317 // remainder. Thus if tail is to be folded, we know we don't need to run
1318 // the remainder and we can set the condition to true.
1319 // 3) Otherwise, construct a runtime check.
1320
1321 // We use the same DebugLoc as the scalar loop latch terminator instead of
1322 // the corresponding compare because they may have ended up with different
1323 // line numbers and we want to avoid awkward line stepping while debugging.
1324 // E.g., if the compare has got a line number inside the loop.
1325 auto *LatchVPBB = cast<VPBasicBlock>(MiddleVPBB->getSinglePredecessor());
1326 DebugLoc LatchDL = LatchVPBB->getTerminator()->getDebugLoc();
1327 VPBuilder Builder(MiddleVPBB);
1328 VPValue *Cmp =
1329 Builder.createICmp(CmpInst::ICMP_EQ, Plan.getTripCount(),
1330 &Plan.getVectorTripCount(), LatchDL, "cmp.n");
1331 Builder.createNaryOp(VPInstruction::BranchOnCond, {Cmp}, LatchDL);
1332}
1333
1335 VPDominatorTree VPDT(Plan);
1337 Plan.getEntry());
1338 // Headers and latches have been canonicalized by addInitialSkeleton.
1339 for (VPBlockBase *HeaderVPB : POT) {
1340 if (!VPBlockUtils::isHeader(HeaderVPB, VPDT))
1341 continue;
1342 assert(HeaderVPB->getPredecessors()[1]->getSuccessors().back() ==
1343 HeaderVPB &&
1344 "latch must have the header as last successor");
1345 createLoopRegion(Plan, HeaderVPB, DL);
1346 }
1347
1348 VPRegionBlock *TopRegion = Plan.getVectorLoopRegion();
1349 TopRegion->setName("vector loop");
1350 TopRegion->getEntryBasicBlock()->setName("vector.body");
1351}
1352
1354 assert(Plan.getExitBlocks().size() == 1 &&
1355 "only a single-exit block is supported currently");
1356 assert(Plan.getExitBlocks().front()->getSinglePredecessor() ==
1357 Plan.getMiddleBlock() &&
1358 "the exit block must have middle block as single predecessor");
1359
1360 VPRegionBlock *LoopRegion = Plan.getVectorLoopRegion();
1361 assert(LoopRegion->getSingleSuccessor() == Plan.getMiddleBlock() &&
1362 "The vector loop region must have the middle block as its single "
1363 "successor for now");
1364 VPBasicBlock *Header = LoopRegion->getEntryBasicBlock();
1365
1366 Header->splitAt(Header->getFirstNonPhi());
1367
1368 // Abstract header mask, materialized into concrete recipes later.
1369 VPValue *HeaderMask = LoopRegion->createHeaderMask();
1370 VPBuilder Builder(Header, Header->getFirstNonPhi());
1371 Builder.createNaryOp(VPInstruction::BranchOnCond, HeaderMask);
1372
1373 VPBasicBlock *OrigLatch = LoopRegion->getExitingBasicBlock();
1374 VPValue *IVInc;
1375 [[maybe_unused]] bool TermBranchOnCount =
1376 match(OrigLatch->getTerminator(),
1378 m_Specific(&Plan.getVectorTripCount())));
1379 assert(TermBranchOnCount &&
1380 match(IVInc, m_Add(m_Specific(LoopRegion->getCanonicalIV()),
1381 m_Specific(&Plan.getVFxUF()))) &&
1382 std::next(IVInc->getDefiningRecipe()->getIterator()) ==
1383 OrigLatch->getTerminator()->getIterator() &&
1384 "Unexpected canonical iv increment");
1385
1386 // Split the latch at the IV update, and branch to it from the header mask.
1387 VPBasicBlock *Latch =
1388 OrigLatch->splitAt(IVInc->getDefiningRecipe()->getIterator());
1389 Latch->setName("vector.latch");
1390 VPBlockUtils::connectBlocks(Header, Latch);
1391
1392 // Collect any values defined in the loop that need a phi. Currently this
1393 // includes header phi backedges and live-outs extracted in the middle block.
1394 // TODO: Handle early exits via Plan.getExitBlocks()
1396 for (VPRecipeBase &R : Header->phis())
1398 NeedsPhi[cast<VPHeaderPHIRecipe>(R).getBackedgeValue()].push_back(&R);
1399
1400 VPValue *V;
1401 for (VPRecipeBase &R : *Plan.getMiddleBlock())
1402 if (match(&R, m_ExtractLastPart(m_VPValue(V))))
1403 NeedsPhi[V].push_back(&R);
1404
1405 // Insert phis for values coming past the end of the tail.
1406 Builder.setInsertPoint(Latch, Latch->begin());
1407 for (const auto &[V, Users] : NeedsPhi) {
1408 if (isa<VPIRValue>(V))
1409 continue;
1410 VPValue *TailVal = Plan.getPoison(V->getScalarType());
1411 std::optional<VPIRFlags> Flags;
1413 "Value used by more than two reduction phis?");
1415 auto *RdxPhi =
1416 RedIt != Users.end() ? cast<VPReductionPHIRecipe>(*RedIt) : nullptr;
1417 if (RdxPhi && !RdxPhi->isInLoop()) {
1418 TailVal = RdxPhi;
1419 Flags = *RdxPhi;
1420 }
1421
1422 VPInstruction *Phi = Builder.createScalarPhi({V, TailVal}, {}, "", Flags);
1423 for (VPUser *U : Users)
1424 U->replaceUsesOfWith(V, Phi);
1425 }
1426
1427 // Any extract of the last element must be updated to extract from the last
1428 // active lane of the header mask instead (i.e., the lane corresponding to the
1429 // last active iteration).
1430 Builder.setInsertPoint(Plan.getMiddleBlock()->getTerminator());
1431 for (VPRecipeBase &R : *Plan.getMiddleBlock()) {
1432 VPValue *Op;
1434 continue;
1435
1436 // Compute the index of the last active lane.
1437 VPValue *LastActiveLane = Builder.createLastActiveLane(HeaderMask);
1438 auto *Ext =
1439 Builder.createNaryOp(VPInstruction::ExtractLane, {LastActiveLane, Op});
1440 R.getVPSingleValue()->replaceAllUsesWith(Ext);
1441 }
1442
1443 // VectorTripCount now equals TripCount so simplify the MiddleVPBB branch.
1447 m_Specific(&Plan.getVectorTripCount())))) &&
1448 "Unexpected MiddleVPBB branch");
1449 Plan.getMiddleBlock()->getTerminator()->setOperand(0, Plan.getTrue());
1450}
1451
1452/// Add an incoming value to all phis in \p VPBB for its just-added last
1453/// predecessor, re-using the value of the previously last one.
1455 for (VPRecipeBase &R : VPBB->phis()) {
1456 auto *Phi = cast<VPPhi>(&R);
1457 assert(Phi->getNumIncoming() == VPBB->getNumPredecessors() - 1 &&
1458 "must have incoming values for all predecessors but the new one");
1459 Phi->addIncoming(Phi->getIncomingValue(Phi->getNumIncoming() - 1));
1460 }
1461}
1462
1463/// Insert \p CheckBlockVPBB on the edge leading to the vector preheader,
1464/// connecting it to both vector and scalar preheaders. Updates scalar
1465/// preheader phis to account for the new predecessor.
1467 VPBasicBlock *CheckBlockVPBB) {
1468 VPBlockBase *VectorPH = Plan.getVectorPreheader();
1469 auto *ScalarPH = cast<VPBasicBlock>(Plan.getScalarPreheader());
1470 VPBlockBase *PreVectorPH = VectorPH->getSinglePredecessor();
1471 VPBlockUtils::insertOnEdge(PreVectorPH, VectorPH, CheckBlockVPBB);
1472 VPBlockUtils::connectBlocks(CheckBlockVPBB, ScalarPH);
1473 CheckBlockVPBB->swapSuccessors();
1475}
1476
1478 VPlan &EpiPlan, VPlan &MainPlan, VPIRBasicBlock *EnteredFrom) {
1479 // Map blocks from MainPlan to new, empty VPIRBasicBlocks in EpiPlan, so the
1480 // skeleton CFG can be modeled explicitly. MainPlan's entry maps to EpiPlan's
1481 // now-disconnected entry and its scalar PH to EnteredFrom.
1482 VPBlockBase *MainEntry = MainPlan.getEntry();
1483 VPBlockBase *MainScalarPH = MainPlan.getScalarPreheader();
1485 MainToEpiVPBB[MainEntry] = EpiPlan.getEntry();
1487 MainEntry);
1489 // Skip entry block and exit blocks/scalar loop header; they are already
1490 // modeled in the epilogue plan.
1491 if (VPBB != MainEntry && VPBB != MainScalarPH && VPBB->hasSuccessors())
1492 MainToEpiVPBB[VPBB] =
1493 EpiPlan.createEmptyVPIRBasicBlock(VPBB->getIRBasicBlock());
1494 MainToEpiVPBB[MainScalarPH] = EnteredFrom;
1495
1496 // First, connect the edges from the bypass blocks (minimum iteration checks,
1497 // runtime checks) to the scalar preheader, in reverse order, to preserve the
1498 // predecessor order of the generated IR.
1499 VPBasicBlock *EpiScalarPH = EpiPlan.getScalarPreheader();
1500 for (VPBlockBase *MainVPBB :
1501 reverse(drop_end(drop_begin(MainScalarPH->predecessors())))) {
1502 VPBlockUtils::connectBlocks(MainToEpiVPBB.lookup(MainVPBB), EpiScalarPH);
1503 addIncomingForLastPredecessor(EpiScalarPH);
1504 }
1505
1506 // Mirror MainPlan's CFG, skipping the bypass edges connected above, which
1507 // come first, and edges to blocks not modeled in EpiPlan.
1508 for (auto &[MainVPBB, EpiVPBB] : drop_end(MainToEpiVPBB))
1509 for (VPBlockBase *Succ :
1510 drop_begin(MainVPBB->getSuccessors(), EpiVPBB->getNumSuccessors()))
1511 if (auto *SuccVPBB = MainToEpiVPBB.lookup(Succ))
1512 VPBlockUtils::connectBlocks(EpiVPBB, SuccVPBB);
1513
1514 // EnteredFrom is the only modeled block with phis; re-use the incoming values
1515 // its IR phis already have for the new predecessors.
1516 for (VPRecipeBase &R : EnteredFrom->phis()) {
1517 auto *PhiR = cast<VPIRPhi>(&R);
1518 for (VPIRBasicBlock *Pred :
1520 PhiR->addIncoming(EpiPlan.getOrAddLiveIn(
1521 PhiR->getIRPhi().getIncomingValueForBlock(Pred->getIRBasicBlock())));
1522 }
1523}
1524
1525// Likelyhood of bypassing the vectorized loop due to a runtime check block,
1526// including memory overlap checks block and wrapping/unit-stride checks block.
1527static constexpr uint32_t CheckBypassWeights[] = {1, 127};
1528
1529/// Create a BranchOnCond terminator in \p CheckBlockVPBB. Optionally adds
1530/// branch weights.
1531static void addBypassBranch(VPlan &Plan, VPBasicBlock *CheckBlockVPBB,
1532 VPValue *Cond, bool AddBranchWeights) {
1534 auto *Term = VPBuilder(CheckBlockVPBB)
1536 if (AddBranchWeights) {
1537 MDBuilder MDB(Plan.getContext());
1538 MDNode *BranchWeights =
1539 MDB.createBranchWeights(CheckBypassWeights, /*IsExpected=*/false);
1540 Term->setMetadata(LLVMContext::MD_prof, BranchWeights);
1541 }
1542}
1543
1545 VPBasicBlock *CheckBlock,
1546 bool AddBranchWeights) {
1547 insertCheckBlockBeforeVectorLoop(Plan, CheckBlock);
1548 addBypassBranch(Plan, CheckBlock, Cond, AddBranchWeights);
1549}
1550
1552 BasicBlock *CheckBlock,
1553 bool AddBranchWeights) {
1554 VPValue *CondVPV = Plan.getOrAddLiveIn(Cond);
1555 VPBasicBlock *CheckBlockVPBB = Plan.createVPIRBasicBlock(CheckBlock);
1556 attachVPCheckBlock(Plan, CondVPV, CheckBlockVPBB, AddBranchWeights);
1557}
1558
1562 bool AddBranchWeights) {
1563 assert(!Checks.empty() && "No checks to generate");
1564
1565 auto *MemCheckVPBB = Plan.createVPBasicBlock("vector.memcheck");
1566 VPBuilder Builder(MemCheckVPBB);
1567 VPSCEVExpander Expander(Builder, SE, DL);
1568
1569 // Expand each group's bounds once so all checks reuse the same frozen values.
1571 std::pair<VPValue *, VPValue *>>
1572 GroupToBounds;
1573 for (const auto &[A, B] : Checks)
1574 for (const RuntimeCheckingPtrGroup *CG : {A, B}) {
1575 auto &[Start, End] = GroupToBounds[CG];
1576 if (Start)
1577 continue;
1578 Start = Expander.expand(CG->Low);
1579 End = Expander.expand(CG->High);
1580 if (CG->NeedsFreeze) {
1581 Start = Builder.createFreeze(Start, DL);
1582 End = Builder.createFreeze(End, DL);
1583 }
1584 }
1585
1586 VPValue *Cond = Plan.getFalse();
1587 for (const auto &[A, B] : Checks) {
1588 auto [AStart, AEnd] = GroupToBounds[A];
1589 auto [BStart, BEnd] = GroupToBounds[B];
1590 VPValue *Bound0 =
1591 Builder.createICmp(CmpInst::ICMP_ULT, AStart, BEnd, DL, "bound0");
1592 VPValue *Bound1 =
1593 Builder.createICmp(CmpInst::ICMP_ULT, BStart, AEnd, DL, "bound1");
1594 VPValue *IsConflict =
1595 Builder.createAnd(Bound0, Bound1, DL, "found.conflict");
1596 Cond = Builder.createOr(Cond, IsConflict, DL, "conflict.rdx");
1597 }
1598 attachVPCheckBlock(Plan, Cond, MemCheckVPBB, AddBranchWeights);
1599}
1600
1602 VPlan &Plan, ElementCount VF, unsigned UF,
1603 ElementCount MinProfitableTripCount, bool RequiresScalarEpilogue,
1604 bool TailFolded, Loop *OrigLoop, const uint32_t *MinItersBypassWeights,
1606 // Generate code to check if the loop's trip count is less than VF * UF, or
1607 // equal to it in case a scalar epilogue is required; this implies that the
1608 // vector trip count is zero. This check also covers the case where adding one
1609 // to the backedge-taken count overflowed leading to an incorrect trip count
1610 // of zero. In this case we will also jump to the scalar loop.
1611 CmpInst::Predicate CmpPred =
1612 RequiresScalarEpilogue ? ICmpInst::ICMP_ULE : ICmpInst::ICMP_ULT;
1613 // If tail is to be folded, vector loop takes care of all iterations.
1614 VPValue *TripCountVPV = Plan.getTripCount();
1615 const SCEV *TripCount = vputils::getSCEVExprForVPValue(TripCountVPV, PSE);
1616 Type *TripCountTy = TripCount->getType();
1617 ScalarEvolution &SE = *PSE.getSE();
1618 auto GetMinTripCount = [&]() -> const SCEV * {
1619 // Compute max(MinProfitableTripCount, UF * VF) and return it.
1620 const SCEV *VFxUF =
1621 SE.getElementCount(TripCountTy, (VF * UF), SCEV::FlagNUW);
1622 if (UF * VF.getKnownMinValue() >=
1623 MinProfitableTripCount.getKnownMinValue()) {
1624 // TODO: SCEV should be able to simplify test.
1625 return VFxUF;
1626 }
1627 const SCEV *MinProfitableTripCountSCEV =
1628 SE.getElementCount(TripCountTy, MinProfitableTripCount, SCEV::FlagNUW);
1629 return SE.getUMaxExpr(MinProfitableTripCountSCEV, VFxUF);
1630 };
1631
1632 VPBuilder Builder(CheckBlock);
1633 VPValue *TripCountCheck = Plan.getFalse();
1634 const SCEV *Step = GetMinTripCount();
1635 // TripCountCheck = false, folding tail implies positive vector trip
1636 // count.
1637 if (!TailFolded) {
1638 // TODO: Emit unconditional branch to vector preheader instead of
1639 // conditional branch with known condition.
1640 TripCount = SE.applyLoopGuards(TripCount, OrigLoop);
1641 // Check if the trip count is < the step.
1642 if (SE.isKnownPredicate(CmpPred, TripCount, Step)) {
1643 // TODO: Ensure step is at most the trip count when determining max VF and
1644 // UF, w/o tail folding.
1645 TripCountCheck = Plan.getTrue();
1646 } else if (!SE.isKnownPredicate(CmpInst::getInversePredicate(CmpPred),
1647 TripCount, Step)) {
1648 // Generate the minimum iteration check only if we cannot prove the
1649 // check is known to be true, or known to be false.
1650 VPValue *MinTripCountVPV =
1651 VPSCEVExpander(Builder, *PSE.getSE(), DL).expand(Step);
1652 TripCountCheck = Builder.createICmp(
1653 CmpPred, TripCountVPV, MinTripCountVPV, DL, "min.iters.check");
1654 } // else step known to be < trip count, use TripCountCheck preset to false.
1655 }
1656 VPInstruction *Term =
1657 Builder.createNaryOp(VPInstruction::BranchOnCond, {TripCountCheck}, DL);
1659 MDBuilder MDB(Plan.getContext());
1660 MDNode *BranchWeights = MDB.createBranchWeights(
1661 ArrayRef(MinItersBypassWeights, 2), /*IsExpected=*/false);
1662 Term->setMetadata(LLVMContext::MD_prof, BranchWeights);
1663 }
1664}
1665
1667 VPlan &Plan, ElementCount VF, unsigned UF, bool RequiresScalarEpilogue,
1668 Loop *OrigLoop, const uint32_t *MinItersBypassWeights, DebugLoc DL,
1670 auto *CheckBlock = Plan.createVPBasicBlock("vector.main.loop.iter.check");
1671 insertCheckBlockBeforeVectorLoop(Plan, CheckBlock);
1673 RequiresScalarEpilogue, /*TailFolded=*/false,
1674 OrigLoop, MinItersBypassWeights, DL, PSE,
1675 CheckBlock);
1676}
1677
1679 VPlan &Plan, VPValue *MainVectorTripCount, bool RequiresScalarEpilogue,
1680 ElementCount EpilogueVF, unsigned MainLoopStep, unsigned EpilogueLoopStep,
1681 ScalarEvolution &SE) {
1682 // Add the minimum iteration check for the epilogue vector loop.
1683 VPValue *TC = Plan.getTripCount();
1684 VPBuilder Builder(cast<VPBasicBlock>(Plan.getEntry()));
1685 VPValue *VFxUF = Builder.createExpandSCEV(
1686 SE.getElementCount(TC->getScalarType(), EpilogueVF, SCEV::FlagNUW));
1687 VPValue *Count = Builder.createSub(TC, MainVectorTripCount,
1688 DebugLoc::getUnknown(), "n.vec.remaining");
1689
1690 // Generate code to check if the loop's trip count is less than VF * UF of
1691 // the vector epilogue loop.
1692 auto P = RequiresScalarEpilogue ? ICmpInst::ICMP_ULE : ICmpInst::ICMP_ULT;
1693 auto *CheckMinIters = Builder.createICmp(
1694 P, Count, VFxUF, DebugLoc::getUnknown(), "min.epilog.iters.check");
1695 VPInstruction *Branch =
1696 Builder.createNaryOp(VPInstruction::BranchOnCond, CheckMinIters);
1697
1698 // We assume the remaining `Count` is equally distributed in
1699 // [0, MainLoopStep)
1700 // So the probability for `Count < EpilogueLoopStep` should be
1701 // min(MainLoopStep, EpilogueLoopStep) / MainLoopStep
1702 // TODO: Improve the estimate by taking the estimated trip count into
1703 // consideration.
1704 unsigned EstimatedSkipCount = std::min(MainLoopStep, EpilogueLoopStep);
1705 const uint32_t Weights[] = {EstimatedSkipCount,
1706 MainLoopStep - EstimatedSkipCount};
1707 MDBuilder MDB(Plan.getContext());
1708 MDNode *BranchWeights =
1709 MDB.createBranchWeights(Weights, /*IsExpected=*/false);
1710 Branch->setMetadata(LLVMContext::MD_prof, BranchWeights);
1711}
1712
1713/// Find and return the final select instruction of the FindIV result pattern
1714/// for the given \p BackedgeVal:
1715/// select(icmp ne ComputeReductionResult(ReducedIV), Sentinel),
1716/// ComputeReductionResult(ReducedIV), Start.
1718 return cast<VPInstruction>(
1719 vputils::findRecipe(BackedgeVal, [BackedgeVal](VPRecipeBase *R) {
1720 auto *VPI = dyn_cast<VPInstruction>(R);
1721 return VPI &&
1722 matchFindIVResult(VPI, m_Specific(BackedgeVal), m_VPValue());
1723 }));
1724}
1725
1727 auto GetMinOrMaxCompareValue =
1728 [](VPReductionPHIRecipe *RedPhiR) -> VPValue * {
1729 auto *MinOrMaxR =
1730 dyn_cast_or_null<VPRecipeWithIRFlags>(RedPhiR->getBackedgeValue());
1731 if (!MinOrMaxR)
1732 return nullptr;
1733
1734 // Check that MinOrMaxR is a VPWidenIntrinsicRecipe or VPReplicateRecipe
1735 // with an intrinsic that matches the reduction kind.
1736 Intrinsic::ID ExpectedIntrinsicID =
1737 getMinMaxReductionIntrinsicOp(RedPhiR->getRecurrenceKind());
1738 if (!match(MinOrMaxR, m_Intrinsic(ExpectedIntrinsicID)))
1739 return nullptr;
1740
1741 // MinOrMaxR must combine RedPhiR directly with the new element, as the NaN
1742 // check added below only covers the other operand.
1743 // TODO: Support multi-step min/max chains (e.g. maxnum(l, maxnum(k, phi)))
1744 // by checking all operands feeding the chain for NaNs.
1745 if (MinOrMaxR->getOperand(0) == RedPhiR)
1746 return MinOrMaxR->getOperand(1);
1747 if (MinOrMaxR->getOperand(1) == RedPhiR)
1748 return MinOrMaxR->getOperand(0);
1749 return nullptr;
1750 };
1751
1752 VPRegionBlock *LoopRegion = Plan.getVectorLoopRegion();
1754 MinOrMaxNumReductionsToHandle;
1755 bool HasUnsupportedPhi = false;
1756 for (auto &R : LoopRegion->getEntryBasicBlock()->phis()) {
1758 continue;
1759 auto *Cur = dyn_cast<VPReductionPHIRecipe>(&R);
1760 if (!Cur) {
1761 // TODO: Also support fixed-order recurrence phis.
1762 HasUnsupportedPhi = true;
1763 continue;
1764 }
1766 Cur->getRecurrenceKind())) {
1767 HasUnsupportedPhi = true;
1768 continue;
1769 }
1770
1771 VPValue *MinOrMaxOp = GetMinOrMaxCompareValue(Cur);
1772 if (!MinOrMaxOp)
1773 return false;
1774
1775 MinOrMaxNumReductionsToHandle.emplace_back(Cur, MinOrMaxOp);
1776 }
1777
1778 if (MinOrMaxNumReductionsToHandle.empty())
1779 return true;
1780
1781 // We won't be able to resume execution in the scalar tail, if there are
1782 // unsupported header phis or there is no scalar tail at all, due to
1783 // tail-folding.
1784 if (HasUnsupportedPhi || !Plan.hasScalarTail())
1785 return false;
1786
1787 /// Check if the vector loop of \p Plan can early exit and restart
1788 /// execution of last vector iteration in the scalar loop. This requires all
1789 /// recipes up to early exit point be side-effect free as they are
1790 /// re-executed. Currently we check that the loop is free of any recipe that
1791 /// may write to memory. Expected to operate on an early VPlan w/o nested
1792 /// regions.
1795 auto *VPBB = cast<VPBasicBlock>(VPB);
1796 for (auto &R : *VPBB) {
1797 if (R.mayWriteToMemory() && !match(&R, m_BranchOnCount()))
1798 return false;
1799 }
1800 }
1801
1802 // Freeze MinOrMaxOps since:
1803 // * multiple uses are introduced and the value may be undef
1804 // * they feed into a branch condition, so block poison propagation to
1805 // prevent immediate UB
1806 for (auto &[Phi, MinOrMaxOp] : MinOrMaxNumReductionsToHandle) {
1807 VPRecipeBase *MinOrMaxR = Phi->getBackedgeValue()->getDefiningRecipe();
1808 VPInstruction *Freeze = VPBuilder(MinOrMaxR).createFreeze(MinOrMaxOp);
1809 MinOrMaxR->replaceUsesOfWith(MinOrMaxOp, Freeze);
1810 MinOrMaxOp = Freeze;
1811 }
1812
1813 VPBasicBlock *LatchVPBB = LoopRegion->getExitingBasicBlock();
1814 VPBuilder LatchBuilder(LatchVPBB->getTerminator());
1815 VPValue *AllNaNLanes = nullptr;
1816 SmallPtrSet<VPValue *, 2> RdxResults;
1817 for (const auto &[_, MinOrMaxOp] : MinOrMaxNumReductionsToHandle) {
1818 VPValue *RedNaNLanes =
1819 LatchBuilder.createFCmp(CmpInst::FCMP_UNO, MinOrMaxOp, MinOrMaxOp);
1820 AllNaNLanes = AllNaNLanes ? LatchBuilder.createOr(AllNaNLanes, RedNaNLanes)
1821 : RedNaNLanes;
1822 }
1823
1824 VPValue *AnyNaNLane =
1825 LatchBuilder.createNaryOp(VPInstruction::AnyOf, {AllNaNLanes});
1826 VPBasicBlock *MiddleVPBB = Plan.getMiddleBlock();
1827 VPBuilder MiddleBuilder(MiddleVPBB, MiddleVPBB->begin());
1828 for (const auto &[RedPhiR, _] : MinOrMaxNumReductionsToHandle) {
1830 RedPhiR->getRecurrenceKind()) &&
1831 "unsupported reduction");
1832
1833 // If we exit early due to NaNs, compute the final reduction result based on
1834 // the reduction phi at the beginning of the last vector iteration.
1835 auto *RdxResult = vputils::findComputeReductionResult(RedPhiR);
1836 assert(RdxResult && "must find a ComputeReductionResult");
1837
1838 auto *NewSel = MiddleBuilder.createSelect(AnyNaNLane, RedPhiR,
1839 RdxResult->getOperand(0));
1840 RdxResult->setOperand(0, NewSel);
1841 assert(!RdxResults.contains(RdxResult) && "RdxResult already used");
1842 RdxResults.insert(RdxResult);
1843 }
1844
1845 auto *LatchExitingBranch = LatchVPBB->getTerminator();
1846 assert(match(LatchExitingBranch, m_BranchOnCount(m_VPValue(), m_VPValue())) &&
1847 "Unexpected terminator");
1848 auto *IsLatchExitTaken = LatchBuilder.createICmp(
1849 CmpInst::ICMP_EQ, LatchExitingBranch->getOperand(0),
1850 LatchExitingBranch->getOperand(1));
1851 auto *AnyExitTaken = LatchBuilder.createOr(AnyNaNLane, IsLatchExitTaken);
1852 LatchBuilder.createNaryOp(VPInstruction::BranchOnCond, AnyExitTaken);
1853 LatchExitingBranch->eraseFromParent();
1854
1855 // Update resume phis for inductions in the scalar preheader. If AnyNaNLane is
1856 // true, the resume from the start of the last vector iteration via the
1857 // canonical IV, otherwise from the original value.
1858 auto IsTC = [&Plan](VPValue *V) {
1859 return V == &Plan.getVectorTripCount() || V == Plan.getTripCount();
1860 };
1861 for (auto &R : Plan.getScalarPreheader()->phis()) {
1862 auto *ResumeR = cast<VPPhi>(&R);
1863 VPValue *VecV = ResumeR->getOperand(0);
1864 if (RdxResults.contains(VecV))
1865 continue;
1866 if (auto *DerivedIV = dyn_cast<VPDerivedIVRecipe>(VecV)) {
1867 VPValue *DIVTC = DerivedIV->getOperand(1);
1868 if (DerivedIV->hasOneUse() && IsTC(DIVTC)) {
1869 auto *NewSel = MiddleBuilder.createSelect(
1870 AnyNaNLane, LoopRegion->getCanonicalIV(), DIVTC);
1871 DerivedIV->moveAfter(MiddleBuilder.getRecipeAtInsertPoint());
1872 DerivedIV->setOperand(1, NewSel);
1873 continue;
1874 }
1875 }
1876 // Bail out and abandon the current, partially modified, VPlan if we
1877 // encounter resume phi that cannot be updated yet.
1878 if (!IsTC(VecV)) {
1879 LLVM_DEBUG(dbgs() << "Found resume phi we cannot update for VPlan with "
1880 "FMaxNum/FMinNum reduction.\n");
1881 return false;
1882 }
1883 auto *NewSel = MiddleBuilder.createSelect(
1884 AnyNaNLane, LoopRegion->getCanonicalIV(), VecV);
1885 ResumeR->setOperand(0, NewSel);
1886 }
1887
1888 auto *MiddleTerm = MiddleVPBB->getTerminator();
1889 MiddleBuilder.setInsertPoint(MiddleTerm);
1890 VPValue *MiddleCond = MiddleTerm->getOperand(0);
1891 VPValue *NewCond =
1892 MiddleBuilder.createAnd(MiddleCond, MiddleBuilder.createNot(AnyNaNLane));
1893 MiddleTerm->setOperand(0, NewCond);
1894 return true;
1895}
1896
1898 if (Plan.hasScalarVFOnly())
1899 return false;
1900
1901 // We want to create the following nodes:
1902 // vector.body:
1903 // ...new WidenPHI recipe introduced to keep the mask value for the latest
1904 // iteration where any lane was active.
1905 // mask.phi = phi [ ir<false>, vector.ph ], [ vp<new.mask>, vector.body ]
1906 // ...data.phi (a VPReductionPHIRecipe for a FindLast reduction) already
1907 // exists, but needs updating to use 'new.data' for the backedge value.
1908 // data.phi = phi ir<default.val>, vp<new.data>
1909 //
1910 // ...'data' and 'compare' created by existing nodes...
1911 //
1912 // ...new recipes introduced to determine whether to update the reduction
1913 // values or keep the current one.
1914 // any.active = i1 any-of ir<compare>
1915 // new.mask = select vp<any.active>, ir<compare>, vp<mask.phi>
1916 // new.data = select vp<any.active>, ir<data>, ir<data.phi>
1917 //
1918 // middle.block:
1919 // ...extract-last-active replaces compute-reduction-result.
1920 // result = extract-last-active vp<new.data>, vp<new.mask>, ir<default.val>
1921
1926 PhiR.getRecurrenceKind()))
1927 Phis.push_back(&PhiR);
1928 }
1929
1930 if (Phis.empty())
1931 return true;
1932
1933 VPValue *HeaderMask = Plan.getVectorLoopRegion()->getHeaderMask();
1934 for (VPReductionPHIRecipe *PhiR : Phis) {
1935 // Find the condition for the select/blend.
1936 VPValue *BackedgeSelect = PhiR->getBackedgeValue();
1937 VPValue *CondSelect = BackedgeSelect;
1938
1939 // If there's a header mask, the backedge select will not be the find-last
1940 // select.
1941 if (HeaderMask &&
1942 !match(BackedgeSelect,
1943 m_SelectLike(m_Specific(HeaderMask), m_VPValue(CondSelect),
1944 m_Specific(PhiR))))
1945 return false;
1946
1947 VPValue *Cond = nullptr, *Op1 = nullptr, *Op2 = nullptr;
1948
1949 // If we're matching a blend rather than a select, there should be one
1950 // incoming value which is the data, then all other incoming values should
1951 // be the phi.
1952 auto MatchBlend = [&](VPRecipeBase *R) {
1953 auto *Blend = dyn_cast<VPBlendRecipe>(R);
1954 if (!Blend)
1955 return false;
1956 assert(!Blend->isNormalized() && "must run before blend normalizaion");
1957 unsigned NumIncomingDataValues = 0;
1958 for (unsigned I = 0; I < Blend->getNumIncomingValues(); ++I) {
1959 VPValue *Incoming = Blend->getIncomingValue(I);
1960 if (Incoming != PhiR) {
1961 ++NumIncomingDataValues;
1962 Cond = Blend->getMask(I);
1963 Op1 = Incoming;
1964 Op2 = PhiR;
1965 }
1966 }
1967 return NumIncomingDataValues == 1;
1968 };
1969
1970 VPSingleDefRecipe *SelectR =
1972 if (!match(SelectR,
1973 m_Select(m_VPValue(Cond), m_VPValue(Op1), m_VPValue(Op2))) &&
1974 !MatchBlend(SelectR))
1975 return false;
1976
1977 // Bail out if PhiR has users other than the find-last select/blend and the
1978 // header mask select, e.g. nested blends. Then the data operand may be PhiR
1979 // on some paths and Cond does not determine the lanes to update.
1980 if (any_of(PhiR->users(), [&](VPUser *U) {
1981 return U != SelectR && U != BackedgeSelect->getDefiningRecipe();
1982 }))
1983 return false;
1984
1985 assert(Cond != HeaderMask && "Cond must not be HeaderMask");
1986
1987 // Find final reduction computation and replace it with an
1988 // extract.last.active intrinsic.
1989 auto *RdxResult =
1991 assert(RdxResult && "Could not find reduction result");
1992
1993 // Add mask phi.
1994 VPBuilder Builder = VPBuilder::getToInsertAfter(PhiR);
1995 auto *MaskPHI = Builder.createWidenPhi(Plan.getFalse());
1996
1997 // Add select for mask.
1998 Builder.setInsertPoint(SelectR);
1999
2000 if (Op1 == PhiR) {
2001 // Normalize to selecting the data operand when the condition is true by
2002 // swapping operands and negating the condition.
2003 std::swap(Op1, Op2);
2004 Cond = Builder.createNot(Cond);
2005 }
2006 assert(Op2 == PhiR && "data value must be selected if Cond is true");
2007
2008 if (HeaderMask)
2009 Cond = Builder.createLogicalAnd(HeaderMask, Cond);
2010
2011 Cond = Builder.createFreeze(Cond);
2012 VPValue *AnyOf = Builder.createNaryOp(VPInstruction::AnyOf, Cond);
2013 VPValue *MaskSelect = Builder.createSelect(AnyOf, Cond, MaskPHI);
2014 MaskPHI->addIncoming(MaskSelect);
2015
2016 // Replace select for data.
2017 VPValue *DataSelect =
2018 Builder.createSelect(AnyOf, Op1, Op2, SelectR->getDebugLoc());
2019 SelectR->replaceAllUsesWith(DataSelect);
2020 PhiR->setBackedgeValue(DataSelect);
2021 SelectR->eraseFromParent();
2022
2023 Builder.setInsertPoint(RdxResult);
2024 auto *ExtractLastActive =
2025 Builder.createNaryOp(VPInstruction::ExtractLastActive,
2026 {PhiR->getStartValue(), DataSelect, MaskSelect},
2027 RdxResult->getDebugLoc());
2028 RdxResult->replaceAllUsesWith(ExtractLastActive);
2029 RdxResult->eraseFromParent();
2030 }
2031
2032 return true;
2033}
2034
2035/// Given a first argmin/argmax pattern with strict predicate consisting of
2036/// 1) a MinOrMax reduction \p MinOrMaxPhiR producing \p MinOrMaxResult,
2037/// 2) a wide induction \p WideIV,
2038/// 3) a FindLastIV reduction \p FindLastIVPhiR using \p WideIV,
2039/// return the smallest index of the FindLastIV reduction result using UMin,
2040/// unless \p MinOrMaxResult equals the start value of its MinOrMax reduction.
2041/// In that case, return the start value of the FindLastIV reduction instead.
2042/// If \p WideIV is not canonical, a new canonical wide IV is added, and the
2043/// final result is scaled back to the non-canonical \p WideIV.
2044/// The final value of the FindLastIV reduction is originally computed using
2045/// \p FindIVSelect, \p FindIVCmp, and \p FindIVRdxResult, which are replaced
2046/// and removed.
2047/// Returns true if the pattern was handled successfully, false otherwise.
2049 VPlan &Plan, VPReductionPHIRecipe *MinOrMaxPhiR,
2050 VPReductionPHIRecipe *FindLastIVPhiR, VPWidenIntOrFpInductionRecipe *WideIV,
2051 VPInstruction *MinOrMaxResult, VPInstruction *FindIVSelect,
2052 VPRecipeBase *FindIVCmp, VPInstruction *FindIVRdxResult) {
2053 assert(!FindLastIVPhiR->isInLoop() && !FindLastIVPhiR->isOrdered() &&
2054 "inloop and ordered reductions not supported");
2055 assert(FindLastIVPhiR->getVFScaleFactor() == 1 &&
2056 "FindIV reduction must not be scaled");
2057
2058 // TODO: support for FP in handleFirstArgMinOrMax
2060 MinOrMaxPhiR->getRecurrenceKind()))
2061 return false;
2062
2064 // TODO: Support non (i.e., narrower than) canonical IV types.
2065 // TODO: Emit remarks for failed transformations.
2066 if (Ty != WideIV->getScalarType())
2067 return false;
2068
2069 VPValue *HeaderMask = Plan.getVectorLoopRegion()->getHeaderMask();
2070 auto *BackedgeVal = FindLastIVPhiR->getBackedgeValue();
2071 auto *FindIVSelectVal = BackedgeVal;
2072 if (HeaderMask && !match(BackedgeVal, m_Select(m_Specific(HeaderMask),
2073 m_VPValue(FindIVSelectVal),
2074 m_Specific(FindLastIVPhiR))))
2075 return false;
2076 auto *FindIVSelectR =
2077 cast<VPSingleDefRecipe>(FindIVSelectVal->getDefiningRecipe());
2078
2079 assert(
2080 match(FindIVSelectR, m_Select(m_VPValue(), m_VPValue(), m_VPValue())) &&
2081 "backedge value must be a select");
2082 if (FindIVSelectR->getOperand(1) != WideIV &&
2083 FindIVSelectR->getOperand(2) != WideIV)
2084 return false;
2085
2086 // If the original wide IV is not canonical, create a new one. The canonical
2087 // wide IV is guaranteed to not wrap for all lanes that are active in the
2088 // vector loop.
2089 if (!WideIV->isCanonical()) {
2090 VPIRValue *Zero = Plan.getConstantInt(Ty, 0);
2091 VPIRValue *One = Plan.getConstantInt(Ty, 1);
2092 auto *WidenCanIV = new VPWidenIntOrFpInductionRecipe(
2093 nullptr, Zero, One, WideIV->getVFValue(),
2094 WideIV->getInductionDescriptor(),
2095 VPIRFlags::WrapFlagsTy(/*HasNUW=*/true, /*HasNSW=*/false),
2096 WideIV->getDebugLoc());
2097 WidenCanIV->insertBefore(WideIV);
2098
2099 // Update the select to use the wide canonical IV.
2100 FindIVSelectR->setOperand(FindIVSelectR->getOperand(1) == WideIV ? 1 : 2,
2101 WidenCanIV);
2102 }
2103 FindLastIVPhiR->setOperand(0, Plan.getPoison(Ty));
2104
2105 // The reduction using MinOrMaxPhiR needs adjusting to compute the correct
2106 // result:
2107 // 1. Find the first canonical indices corresponding to partial min/max
2108 // values, using loop reductions.
2109 // 2. Find which of the partial min/max values are equal to the overall
2110 // min/max value.
2111 // 3. Select among the canonical indices those corresponding to the overall
2112 // min/max value.
2113 // 4. Find the first canonical index of overall min/max and scale it back to
2114 // the original IV using VPDerivedIVRecipe.
2115 // 5. If the overall min/max equals the starting min/max, the condition in
2116 // the loop was always false, due to being strict; return the start value
2117 // of FindLastIVPhiR in that case.
2118 //
2119 // For example, we transforms two independent reduction result computations
2120 // for
2121 //
2122 // <x1> vector loop: {
2123 // vector.body:
2124 // ...
2125 // ir<%iv> = WIDEN-INDUCTION nuw nsw ir<10>, ir<1>, vp<%0>
2126 // WIDEN-REDUCTION-PHI ir<%min.idx> = phi ir<sentinel.min.start>,
2127 // ir<%min.idx.next>
2128 // WIDEN-REDUCTION-PHI ir<%min.val> = phi ir<100>, ir<%min.val.next>
2129 // ....
2130 // WIDEN-INTRINSIC ir<%min.val.next> = call llvm.umin(ir<%min.val>, ir<%l>)
2131 // WIDEN ir<%min.idx.next> = select ir<%cmp>, ir<%iv>, ir<%min.idx>
2132 // ...
2133 // }
2134 // Successor(s): middle.block
2135 //
2136 // middle.block:
2137 // vp<%iv.rdx> = compute-reduction-result (smax) vp<%min.idx.next>
2138 // vp<%min.result> = compute-reduction-result (umin) ir<%min.val.next>
2139 // vp<%cmp> = icmp ne vp<%iv.rdx>, ir<sentinel.min.start>
2140 // vp<%find.iv.result> = select vp<%cmp>, vp<%iv.rdx>, ir<10>
2141 //
2142 //
2143 // Into:
2144 //
2145 // vp<%reduced.min> = compute-reduction-result (umin) ir<%min.val.next>
2146 // vp<%reduced.mins.mask> = icmp eq ir<%min.val.next>, vp<%reduced.min>
2147 // vp<%idxs2reduce> = select vp<%reduced.mins.mask>, ir<%min.idx.next>,
2148 // ir<MaxUInt>
2149 // vp<%reduced.idx> = compute-reduction-result (umin) vp<%idxs2reduce>
2150 // vp<%scaled.idx> = DERIVED-IV ir<20> + vp<%reduced.idx> * ir<1>
2151 // vp<%always.false> = icmp eq vp<%reduced.min>, ir<100>
2152 // vp<%final.idx> = select vp<%always.false>, ir<10>,
2153 // vp<%scaled.idx>
2154
2155 VPBuilder Builder(FindIVRdxResult);
2156 VPValue *MinOrMaxExiting = MinOrMaxResult->getOperand(0);
2157 auto *FinalMinOrMaxCmp =
2158 Builder.createICmp(CmpInst::ICMP_EQ, MinOrMaxExiting, MinOrMaxResult);
2159 VPValue *LastIVExiting = FindIVRdxResult->getOperand(0);
2160 VPValue *MaxIV =
2161 Plan.getConstantInt(APInt::getMaxValue(Ty->getIntegerBitWidth()));
2162 auto *FinalIVSelect =
2163 Builder.createSelect(FinalMinOrMaxCmp, LastIVExiting, MaxIV);
2164 VPIRFlags RdxFlags(RecurKind::UMin, false, false, FastMathFlags());
2165 VPSingleDefRecipe *FinalCanIV = Builder.createNaryOp(
2166 VPInstruction::ComputeReductionResult, {FinalIVSelect}, RdxFlags,
2167 FindIVRdxResult->getDebugLoc());
2168
2169 // If we used a new wide canonical IV convert the reduction result back to the
2170 // original IV scale before the final select.
2171 if (!WideIV->isCanonical()) {
2172 auto *DerivedIVRecipe = new VPDerivedIVRecipe(
2174 nullptr, // No FPBinOp for integer induction
2175 WideIV->getStartValue(), FinalCanIV, WideIV->getStepValue());
2176 DerivedIVRecipe->insertBefore(Builder.getRecipeAtInsertPoint());
2177 FinalCanIV = DerivedIVRecipe;
2178 }
2179
2180 // If the final min/max value matches its start value, the condition in the
2181 // loop was always false, i.e. no induction value has been selected. If that's
2182 // the case, set the result of the IV reduction to its start value.
2183 VPValue *AlwaysFalse = Builder.createICmp(CmpInst::ICMP_EQ, MinOrMaxResult,
2184 MinOrMaxPhiR->getStartValue());
2185 VPValue *FinalIV = Builder.createSelect(
2186 AlwaysFalse, FindIVSelect->getOperand(2), FinalCanIV);
2187 FindIVSelect->replaceAllUsesWith(FinalIV);
2188
2189 // Erase the old FindIV result pattern which is now dead.
2190 FindIVSelect->eraseFromParent();
2191 FindIVCmp->eraseFromParent();
2192 FindIVRdxResult->eraseFromParent();
2193 return true;
2194}
2195
2198 Loop *TheLoop) {
2199 for (auto &PhiR : make_early_inc_range(
2201 auto *MinOrMaxPhiR = dyn_cast<VPReductionPHIRecipe>(&PhiR);
2202 // TODO: check for multi-uses in VPlan directly.
2203 if (!MinOrMaxPhiR || !MinOrMaxPhiR->hasUsesOutsideReductionChain())
2204 continue;
2205
2206 // MinOrMaxPhiR has users outside the reduction cycle in the loop. Check if
2207 // the only other user is a FindLastIV reduction. MinOrMaxPhiR must have
2208 // exactly 2 users if not tailfolded:
2209 // 1) the min/max operation of the reduction cycle, and
2210 // 2) the compare of a FindLastIV reduction cycle. This compare must match
2211 // the min/max operation - comparing MinOrMaxPhiR with the operand of the
2212 // min/max operation, and be used only by the select of the FindLastIV
2213 // reduction cycle.
2214 // There is an additional user if the tail was folded:
2215 // 3) the select operation of the vector.latch block. This select uses the
2216 // original MinOrMaxPhiR if the mask is zero.
2217 RecurKind RdxKind = MinOrMaxPhiR->getRecurrenceKind();
2218 assert(
2220 "only min/max recurrences support users outside the reduction chain");
2221
2222 auto *MinOrMaxBackedgeR =
2223 dyn_cast<VPRecipeWithIRFlags>(MinOrMaxPhiR->getBackedgeValue());
2224 if (!MinOrMaxBackedgeR)
2225 return false;
2226
2227 // If the tail was folded then the backedge won't be the
2228 // reduction-intrinsic but the select in the vector.latch block that wraps
2229 // the reduction-intrinsic.
2230 auto *MinOrMaxOp = MinOrMaxBackedgeR;
2231 VPValue *HeaderMask = Plan.getVectorLoopRegion()->getHeaderMask();
2232 VPValue *MinOrMaxTailfold;
2233 if (HeaderMask) {
2234 if (!match(MinOrMaxBackedgeR, m_SelectLike(m_Specific(HeaderMask),
2235 m_VPValue(MinOrMaxTailfold),
2236 m_Specific(MinOrMaxPhiR))))
2237 return false;
2238
2239 MinOrMaxOp = dyn_cast<VPRecipeWithIRFlags>(MinOrMaxTailfold);
2240 if (!MinOrMaxOp)
2241 return false;
2242 }
2243
2244 // Check that MinOrMaxOp is a VPWidenIntrinsicRecipe or
2245 // VPReplicateRecipe with an intrinsic that matches the reduction kind.
2246 Intrinsic::ID ExpectedIntrinsicID = getMinMaxReductionIntrinsicOp(RdxKind);
2247 if (!match(MinOrMaxOp, m_Intrinsic(ExpectedIntrinsicID)))
2248 return false;
2249
2250 // Tailfolded MinOrMaxOp should only feed into the predicated
2251 // select MinOrMaxBackedgeR.
2252 assert((!HeaderMask || MinOrMaxOp->getNumUsers() == 1) &&
2253 "Tailfolded MinOrMaxOp must have exactly 1 user");
2254 // MinOrMaxBackedgeR must have 2 users: 1) MinOrMaxPhiR and 2)
2255 // ComputeReductionResult.
2256 assert(MinOrMaxBackedgeR->getNumUsers() == 2 &&
2257 "MinOrMaxBackedgeR must have exactly 2 users");
2258 // MinOrMaxOp must combine MinOrMaxPhiR directly with the new element;
2259 // reject multi-step min/max chains (e.g. max(l, max(k, phi))), which
2260 // this transform does not handle.
2261 VPValue *MinOrMaxOpValue;
2262 if (MinOrMaxOp->getOperand(0) == MinOrMaxPhiR)
2263 MinOrMaxOpValue = MinOrMaxOp->getOperand(1);
2264 else if (MinOrMaxOp->getOperand(1) == MinOrMaxPhiR)
2265 MinOrMaxOpValue = MinOrMaxOp->getOperand(0);
2266 else
2267 return false;
2268
2269 VPValue *CmpOpA;
2270 VPValue *CmpOpB;
2271 CmpPredicate Pred;
2273 MinOrMaxPhiR, m_Cmp(Pred, m_VPValue(CmpOpA), m_VPValue(CmpOpB))));
2274 if (!Cmp || Cmp->getNumUsers() != 1 ||
2275 (CmpOpA != MinOrMaxOpValue && CmpOpB != MinOrMaxOpValue))
2276 return false;
2277
2278 if (MinOrMaxOpValue != CmpOpB)
2279 Pred = CmpInst::getSwappedPredicate(Pred);
2280
2281 // MinOrMaxPhiR must have exactly 2 users if not tailfolded:
2282 // * MinOrMaxOp,
2283 // * Cmp (that's part of a FindLastIV chain).
2284 // Also an additional third user if it is tailfolded:
2285 // * Predicated HEADER-MASK select in the vector.latch block.
2286 if (MinOrMaxPhiR->getNumUsers() != (HeaderMask ? 3 : 2))
2287 return false;
2288
2289 VPInstruction *MinOrMaxResult =
2291 assert(MinOrMaxResult &&
2292 "MinOrMaxResult must be a user of MinOrMaxBackedgeR");
2293
2294 // Cmp must be used by the select of a FindLastIV chain.
2295 VPValue *Sel = dyn_cast<VPSingleDefRecipe>(Cmp->getSingleUser());
2296 VPValue *IVOp, *FindIV;
2297 if (!Sel || (Sel->getNumUsers() != (HeaderMask ? 1 : 2)) ||
2298 !match(Sel,
2300 return false;
2301
2303 std::swap(FindIV, IVOp);
2304 Pred = CmpInst::getInversePredicate(Pred);
2305 }
2306
2307 auto *FindIVPhiR = dyn_cast<VPReductionPHIRecipe>(FindIV);
2309 FindIVPhiR->getRecurrenceKind()))
2310 return false;
2311
2312 assert(!FindIVPhiR->isInLoop() && !FindIVPhiR->isOrdered() &&
2313 "cannot handle inloop/ordered reductions yet");
2314
2315 // Check if FindIVPhiR is a FindLast pattern by checking the MinMaxKind
2316 // on its ComputeReductionResult. SMax/UMax indicates FindLast.
2317 VPInstruction *FindIVResult =
2319 FindIVPhiR->getBackedgeValue());
2320 assert(FindIVResult &&
2321 "must be able to retrieve the FindIVResult VPInstruction");
2322 RecurKind FindIVMinMaxKind = FindIVResult->getRecurKind();
2323 if (FindIVMinMaxKind != RecurKind::SMax &&
2324 FindIVMinMaxKind != RecurKind::UMax)
2325 return false;
2326
2327 // TODO: Support cases where IVOp is the IV increment.
2328 if (!match(IVOp, m_TruncOrSelf(m_VPValue(IVOp))) ||
2330 return false;
2331
2332 // Check if the predicate is compatible with the reduction kind.
2333 bool IsValidKindPred = [RdxKind, Pred]() {
2334 switch (RdxKind) {
2335 case RecurKind::UMin:
2336 return Pred == CmpInst::ICMP_UGE || Pred == CmpInst::ICMP_UGT;
2337 case RecurKind::UMax:
2338 return Pred == CmpInst::ICMP_ULE || Pred == CmpInst::ICMP_ULT;
2339 case RecurKind::SMax:
2340 return Pred == CmpInst::ICMP_SLE || Pred == CmpInst::ICMP_SLT;
2341 case RecurKind::SMin:
2342 return Pred == CmpInst::ICMP_SGE || Pred == CmpInst::ICMP_SGT;
2343 case RecurKind::FMax:
2345 return Pred == CmpInst::FCMP_OLE || Pred == CmpInst::FCMP_OLT;
2346 case RecurKind::FMin:
2348 return Pred == CmpInst::FCMP_OGE || Pred == CmpInst::FCMP_OGT;
2349 // minnum and maxnum need special handling due to expected sNaN behaviour
2350 // minimum and maximum return NaN if either input is a NAN
2351 case RecurKind::FMinNum:
2352 case RecurKind::FMaxNum:
2355 return false;
2356 default:
2357 llvm_unreachable("unhandled recurrence kind");
2358 }
2359 }();
2360 if (!IsValidKindPred) {
2361 ORE->emit([&]() {
2363 DEBUG_TYPE, "VectorizationMultiUseReductionPredicate",
2364 TheLoop->getStartLoc(), TheLoop->getHeader())
2365 << "Multi-use reduction with predicate "
2367 << " incompatible with reduction kind";
2368 });
2369 return false;
2370 }
2371
2372 if (RdxKind == RecurKind::FMaximumNum ||
2373 RdxKind == RecurKind::FMinimumNum) {
2374 auto *StartC = dyn_cast<VPConstant>(MinOrMaxPhiR->getStartValue());
2375 if (!StartC || StartC->getConstant()->isNaN())
2376 return false;
2377 }
2378
2379 auto *FindIVSelect = findFindIVSelect(FindIVPhiR->getBackedgeValue());
2380 auto *FindIVCmp = FindIVSelect->getOperand(0)->getDefiningRecipe();
2381 auto *FindIVRdxResult = cast<VPInstruction>(FindIVCmp->getOperand(0));
2382 assert(FindIVSelect->getParent() == MinOrMaxResult->getParent() &&
2383 "both results must be computed in the same block");
2384 // Reducing to a scalar min or max value is placed right before reducing to
2385 // its scalar iteration, in order to generate instructions that use both
2386 // their operands.
2387 MinOrMaxResult->moveBefore(*FindIVRdxResult->getParent(),
2388 FindIVRdxResult->getIterator());
2389
2390 bool IsStrictPredicate = CmpInst::isStrictPredicate(Pred);
2391 if (IsStrictPredicate) {
2392 if (!handleFirstArgMinOrMax(Plan, MinOrMaxPhiR, FindIVPhiR,
2394 MinOrMaxResult, FindIVSelect, FindIVCmp,
2395 FindIVRdxResult))
2396 return false;
2397 continue;
2398 }
2399
2400 // The reduction using MinOrMaxPhiR needs adjusting to compute the correct
2401 // result:
2402 // 1. We need to find the last IV for which the condition based on the
2403 // min/max recurrence is true,
2404 // 2. Compare the partial min/max reduction result to its final value and,
2405 // 3. Select the lanes of the partial FindLastIV reductions which
2406 // correspond to the lanes matching the min/max reduction result.
2407 //
2408 // For example, this transforms
2409 // vp<%min.result> = compute-reduction-result ir<%min.val.next>
2410 // vp<%iv.rdx> = compute-reduction-result (smax) vp<%min.idx.next>
2411 // vp<%cmp> = icmp ne vp<%iv.rdx>, SENTINEL
2412 // vp<%find.iv.result> = select vp<%cmp>, vp<%iv.rdx>, ir<0>
2413 //
2414 // into:
2415 //
2416 // vp<min.result> = compute-reduction-result ir<%min.val.next>
2417 // vp<%final.min.cmp> = icmp eq ir<%min.val.next>, vp<min.result>
2418 // vp<%final.iv> = select vp<%final.min.cmp>, vp<%min.idx.next>, SENTINEL
2419 // vp<%iv.rdx> = compute-reduction-result (smax) vp<%final.iv>
2420 // vp<%cmp> = icmp ne vp<%iv.rdx>, SENTINEL
2421 // vp<%find.iv.result> = select vp<%cmp>, vp<%iv.rdx>, ir<0>
2422 //
2423 VPBuilder B(FindIVRdxResult);
2424 VPValue *MinOrMaxExiting = MinOrMaxResult->getOperand(0);
2425 auto *FinalMinOrMaxCmp =
2427 ? B.createICmp(CmpInst::ICMP_EQ, MinOrMaxExiting, MinOrMaxResult)
2428 : B.createFCmp(CmpInst::FCMP_OEQ, MinOrMaxExiting, MinOrMaxResult);
2429 VPValue *Sentinel = FindIVCmp->getOperand(1);
2430 VPValue *LastIVExiting = FindIVRdxResult->getOperand(0);
2431 auto *FinalIVSelect =
2432 B.createSelect(FinalMinOrMaxCmp, LastIVExiting, Sentinel);
2433 FindIVRdxResult->setOperand(0, FinalIVSelect);
2434 }
2435 return true;
2436}
2437
2439 VPRegionBlock *LoopRegion = Plan.getVectorLoopRegion();
2440 VPValue *HeaderMask = LoopRegion->getHeaderMask();
2441 Type *I1Ty = IntegerType::getInt1Ty(Plan.getContext());
2442
2443 VPBuilder Builder(Plan.getVectorPreheader());
2444 auto *AliasMask = Builder.createNaryOp(
2445 VPInstruction::IncomingAliasMask, {}, nullptr, {}, {},
2446 DebugLoc::getUnknown(), "incoming.alias.mask", I1Ty);
2447
2448 VPBasicBlock *Header = LoopRegion->getEntryBasicBlock();
2449 Builder = VPBuilder(Header, Header->getFirstNonPhi());
2450
2451 // Update all existing users of the header mask to "HeaderMask & AliasMask".
2452 auto *ClampedHeaderMask = Builder.createAnd(HeaderMask, AliasMask);
2453 HeaderMask->replaceUsesWithIf(ClampedHeaderMask,
2454 not_equal_to(ClampedHeaderMask));
2455}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
#define DEBUG_TYPE
#define _
iv Induction Variable Users
Definition IVUsers.cpp:48
const AbstractManglingParser< Derived, Alloc >::OperatorInfo AbstractManglingParser< Derived, Alloc >::Ops[]
This file provides a LoopVectorizationPlanner class.
static constexpr uint32_t MinItersBypassWeights[]
#define I(x, y, z)
Definition MD5.cpp:57
#define P(N)
const SmallVectorImpl< MachineOperand > & Cond
Provides some synthesis utilities to produce sequences of values.
This file defines less commonly used SmallVector utilities.
#define LLVM_DEBUG(...)
Definition Debug.h:119
This pass exposes codegen information to IR-level passes.
static bool isHeaderBB(BasicBlock *BB, Loop *L)
static bool handleFirstArgMinOrMax(VPlan &Plan, VPReductionPHIRecipe *MinOrMaxPhiR, VPReductionPHIRecipe *FindLastIVPhiR, VPWidenIntOrFpInductionRecipe *WideIV, VPInstruction *MinOrMaxResult, VPInstruction *FindIVSelect, VPRecipeBase *FindIVCmp, VPInstruction *FindIVRdxResult)
Given a first argmin/argmax pattern with strict predicate consisting of 1) a MinOrMax reduction MinOr...
static VPHeaderPHIRecipe * createWidenInductionRecipe(PHINode *Phi, VPPhi *PhiR, VPIRValue *Start, const InductionDescriptor &IndDesc, VPlan &Plan, PredicatedScalarEvolution &PSE, Loop &OrigLoop, DebugLoc DL)
Creates a VPWidenIntOrFpInductionRecipe or VPWidenPointerInductionRecipe for Phi based on IndDesc.
static void addIncomingForLastPredecessor(VPBasicBlock *VPBB)
Add an incoming value to all phis in VPBB for its just-added last predecessor, re-using the value of ...
static void insertCheckBlockBeforeVectorLoop(VPlan &Plan, VPBasicBlock *CheckBlockVPBB)
Insert CheckBlockVPBB on the edge leading to the vector preheader, connecting it to both vector and s...
static void addBypassBranch(VPlan &Plan, VPBasicBlock *CheckBlockVPBB, VPValue *Cond, bool AddBranchWeights)
Create a BranchOnCond terminator in CheckBlockVPBB.
static bool sinkRecurrenceUsersAfterPrevious(VPFirstOrderRecurrencePHIRecipe *FOR, VPRecipeBase *Previous, const VPDominatorTree &VPDT)
Try to sink users of FOR after Previous.
static bool canonicalHeaderAndLatch(VPBlockBase *HeaderVPB, const VPDominatorTree &VPDT)
Checks if HeaderVPB is a loop header block in the plain CFG; that is, it has exactly 2 predecessors (...
static void addInitialSkeleton(VPlan &Plan, Type *InductionTy, PredicatedScalarEvolution &PSE, Loop *TheLoop)
static bool hoistPreviousBeforeFORUsers(VPFirstOrderRecurrencePHIRecipe *FOR, VPRecipeBase *Previous, const VPDominatorTree &VPDT)
Try to hoist Previous and its operands before all users of FOR.
static void createLoopRegion(VPlan &Plan, VPBlockBase *HeaderVPB, DebugLoc DL)
Create a new VPRegionBlock for the loop starting at HeaderVPB.
static VPInstruction * findFindIVSelect(VPValue *BackedgeVal)
Find and return the final select instruction of the FindIV result pattern for the given BackedgeVal: ...
static bool tryToSinkOrHoistRecurrenceUsers(VPBasicBlock *HeaderVPBB, const VPDominatorTree &VPDT)
Sink users of fixed-order recurrences past or hoist before the recipe defining the previous value,...
static constexpr uint32_t CheckBypassWeights[]
static void printAfterInitialConstruction(VPlan &)
To make RUN_VPLAN_PASS print initial VPlan.
static void createExtractsForLiveOuts(VPlan &Plan, VPBasicBlock *MiddleVPBB)
Creates extracts for values in Plan defined in a loop region and used outside a loop region.
This file implements dominator tree analysis for a single level of a VPlan's H-CFG.
This file contains the declarations of different VPlan-related auxiliary helpers.
This file provides utility VPlan to VPlan transformations.
#define RUN_VPLAN_PASS_NO_VERIFY(PASS,...)
This file contains the declarations of the Vectorization Plan base classes:
static APInt getMaxValue(unsigned numBits)
Gets maximum unsigned value of APInt for specific bit width.
Definition APInt.h:202
Represent a constant reference to an array (0 or more elements consecutively in memory),...
Definition ArrayRef.h:40
size_t size() const
Get the array size.
Definition ArrayRef.h:141
bool empty() const
Check if the array is empty.
Definition ArrayRef.h:136
A cache of @llvm.assume calls within a function.
LLVM Basic Block Representation.
Definition BasicBlock.h:62
LLVM_ABI const DataLayout & getDataLayout() const
Get the data layout of the module this basic block belongs to.
const Instruction * getTerminator() const LLVM_READONLY
Returns the terminator instruction; assumes that the block is well-formed.
Definition BasicBlock.h:237
Analysis providing branch probability information.
Predicate
This enumeration lists the possible predicates for CmpInst subclasses.
Definition InstrTypes.h:740
@ FCMP_OEQ
0 0 0 1 True if ordered and equal
Definition InstrTypes.h:743
@ ICMP_SLT
signed less than
Definition InstrTypes.h:769
@ ICMP_SLE
signed less or equal
Definition InstrTypes.h:770
@ FCMP_OLT
0 1 0 0 True if ordered and less than
Definition InstrTypes.h:746
@ FCMP_OGT
0 0 1 0 True if ordered and greater than
Definition InstrTypes.h:744
@ FCMP_OGE
0 0 1 1 True if ordered and greater than or equal
Definition InstrTypes.h:745
@ ICMP_UGE
unsigned greater or equal
Definition InstrTypes.h:764
@ ICMP_UGT
unsigned greater than
Definition InstrTypes.h:763
@ ICMP_SGT
signed greater than
Definition InstrTypes.h:767
@ ICMP_ULT
unsigned less than
Definition InstrTypes.h:765
@ FCMP_OLE
0 1 0 1 True if ordered and less than or equal
Definition InstrTypes.h:747
@ ICMP_SGE
signed greater or equal
Definition InstrTypes.h:768
@ ICMP_ULE
unsigned less or equal
Definition InstrTypes.h:766
@ FCMP_UNO
1 0 0 0 True if unordered: isnan(X) | isnan(Y)
Definition InstrTypes.h:750
Predicate getSwappedPredicate() const
For example, EQ->EQ, SLE->SGE, ULT->UGT, OEQ->OEQ, ULE->UGE, OLT->OGT, etc.
Definition InstrTypes.h:890
Predicate getInversePredicate() const
For example, EQ -> NE, UGT -> ULE, SLT -> SGE, OEQ -> UNE, UGT -> OLE, OLT -> UGE,...
Definition InstrTypes.h:852
static LLVM_ABI StringRef getPredicateName(Predicate P)
bool isStrictPredicate() const
Definition InstrTypes.h:906
An abstraction over a floating-point predicate, and a pack of an integer predicate with samesign info...
A parsed version of the target data layout string in and methods for querying it.
Definition DataLayout.h:64
A debug info location.
Definition DebugLoc.h:126
static DebugLoc getUnknown()
Definition DebugLoc.h:153
ValueT lookup(const_arg_type_t< KeyT > Val) const
Return the entry for the specified key, or a default constructed value if no such entry exists.
Definition DenseMap.h:794
bool dominates(const DomTreeNodeBase< NodeT > *A, const DomTreeNodeBase< NodeT > *B) const
dominates - Returns true iff A dominates B.
Concrete subclass of DominatorTreeBase that is used to compute a normal dominator tree.
Definition Dominators.h:122
static constexpr ElementCount getFixed(ScalarTy MinVal)
Definition TypeSize.h:305
constexpr bool isScalar() const
Exactly one element.
Definition TypeSize.h:316
Convenience struct for specifying and reasoning about fast-math flags.
Definition FMF.h:23
static FastMathFlags getFast()
Definition FMF.h:50
A struct for saving information about induction variables.
InductionKind getKind() const
const SCEV * getStep() const
@ IK_FpInduction
Floating point induction variable.
@ IK_PtrInduction
Pointer induction var. Step = C.
@ IK_IntInduction
Integer induction variable. Step = C.
Value * getStartValue() const
LLVM_ABI unsigned getNumSuccessors() const LLVM_READONLY
Return the number of successors that this instruction has.
const DebugLoc & getDebugLoc() const
Return the debug location for this node as a DebugLoc.
LLVM_ABI FastMathFlags getFastMathFlags() const LLVM_READONLY
Convenience function for getting all the fast-math flags, which must be an operator which supports th...
unsigned getOpcode() const
Returns a member of one of the enums like Instruction::Add.
This is an important class for using LLVM in a threaded context.
Definition LLVMContext.h:71
bool contains(const LoopT *L) const
Return true if the specified loop is contained within this loop.
BlockT * getLoopLatch() const
If there is a single latch block for this loop, return it.
bool isInnermost() const
Return true if the loop does not contain any (natural) loops.
BlockT * getHeader() const
BlockT * getLoopPreheader() const
If there is a preheader for this loop, return it.
LoopT * getLoopFor(const BlockT *BB) const
Return the inner most loop that BB lives in.
This class emits a version of the loop where run-time checks ensure that may-alias pointers can't ove...
LLVM_ABI std::pair< MDNode *, MDNode * > getNoAliasMetadataFor(const Instruction *OrigInst) const
Returns a pair containing the alias_scope and noalias metadata nodes for OrigInst,...
Represents a single loop in the control flow graph.
Definition LoopInfo.h:40
DebugLoc getStartLoc() const
Return the debug location of the start of this loop.
Definition LoopInfo.cpp:695
LLVM_ABI MDNode * createBranchWeights(uint32_t TrueWeight, uint32_t FalseWeight, bool IsExpected=false)
Return metadata containing two branch weights.
Definition MDBuilder.cpp:38
Metadata node.
Definition Metadata.h:1081
This class implements a map that also provides access to all stored values in a deterministic order.
Definition MapVector.h:38
ValueT lookup(const KeyT &Key) const
Definition MapVector.h:110
iterator find(const KeyT &Key)
Definition MapVector.h:156
iterator end()
Definition MapVector.h:69
The optimization diagnostic interface.
LLVM_ABI void emit(DiagnosticInfoOptimizationBase &OptDiag)
Output the remark via the diagnostic handler and to the optimization record file.
Diagnostic information for missed-optimization remarks.
Post-order traversal of a graph.
An interface layer with SCEV used to manage how we see SCEV expressions for values in the context of ...
LLVM_ABI void addPredicate(const SCEVPredicate &Pred)
Adds a new predicate.
ScalarEvolution * getSE() const
Returns the ScalarEvolution analysis used.
LLVM_ABI const SCEVPredicate & getPredicate() const
LLVM_ABI const SCEV * getSymbolicMaxBackedgeTakenCount()
Get the (predicated) symbolic max backedge count for the analyzed loop.
LLVM_ABI const SCEV * getSCEV(Value *V)
Returns the SCEV expression of V, in the context of the current SCEV predicate.
The RecurrenceDescriptor is used to identify recurrences variables in a loop.
static bool isFMulAddIntrinsic(Instruction *I)
Returns true if the instruction is a call to the llvm.fmuladd intrinsic.
FastMathFlags getFastMathFlags() const
static bool isFPMinMaxNumRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is a floating-point minnum/maxnum kind.
bool hasUsesOutsideReductionChain() const
Returns true if the reduction PHI has any uses outside the reduction chain.
static bool isFindLastRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is of the form select(cmp(),x,y) where one of (x,...
TrackingVH< Value > getRecurrenceStartValue() const
static bool isAnyOfRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is of the form select(cmp(),x,y) where one of (x,...
RecurKind getRecurrenceKind() const
bool isOrdered() const
Expose an ordered FP reduction to the instance users.
static LLVM_ABI bool isFloatingPointRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is a floating point kind.
static bool isFindIVRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is of the form select(cmp(),x,y) where one of (x,...
static LLVM_ABI bool isIntegerRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is an integer kind.
static bool isMinMaxRecurrenceKind(RecurKind Kind)
Returns true if the recurrence kind is any min/max kind.
virtual unsigned getComplexity() const
Returns the estimated complexity of this predicate.
This class represents an analyzed expression in the program.
static constexpr auto FlagNUW
Type * getType() const
Return the LLVM type of this SCEV expression.
The main scalar evolution driver.
LLVM_ABI const SCEV * getElementCount(Type *Ty, ElementCount EC, SCEVFlags Flags=SCEV::FlagNone)
LLVM_ABI const SCEV * getTripCountFromExitCount(const SCEV *ExitCount)
A version of getTripCountFromExitCount below which always picks an evaluation type which can not resu...
LLVM_ABI bool isLoopInvariant(const SCEV *S, const Loop *L)
Return true if the value of the given SCEV is unchanging in the specified loop.
LLVM_ABI bool isSCEVable(Type *Ty) const
Test if values of the given type are analyzable within the SCEV framework.
LLVM_ABI const SCEV * getUMaxExpr(SCEVUse LHS, SCEVUse RHS)
LLVM_ABI const SCEV * getStoreSizeOfExpr(Type *IntTy, Type *StoreTy)
Return an expression for the store size of StoreTy that is type IntTy.
LLVM_ABI bool isKnownPredicate(CmpPredicate Pred, SCEVUse LHS, SCEVUse RHS)
Test if the given expression is known to satisfy the condition described by Pred, LHS,...
LLVM_ABI const SCEV * applyLoopGuards(const SCEV *Expr, const Loop *L)
Try to apply information from loop guards for L to Expr.
A vector that has set insertion semantics.
Definition SetVector.h:57
size_type size() const
Determine the number of elements in the SetVector.
Definition SetVector.h:103
bool insert(const value_type &X)
Insert a new element into the SetVector.
Definition SetVector.h:157
A templated base class for SmallPtrSet which provides the typesafe interface that is common across al...
std::pair< iterator, bool > insert(PtrType Ptr)
Inserts Ptr if and only if there is no element in the container equal to Ptr.
bool contains(ConstPtrType Ptr) const
SmallPtrSet - This class implements a set which is optimized for holding SmallSize or less elements.
reference emplace_back(ArgTypes &&... Args)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
The instances of the Type class are immutable: once they are created, they are never changed.
Definition Type.h:46
Type * getScalarType() const
If this is a vector type, return the element type, otherwise return 'this'.
Definition Type.h:363
static LLVM_ABI IntegerType * getInt1Ty(LLVMContext &C)
Definition Type.cpp:296
op_range operands()
Definition User.h:267
VPBasicBlock serves as the leaf of the Hierarchical Control-Flow Graph.
Definition VPlan.h:4429
void appendRecipe(VPRecipeBase *Recipe)
Augment the existing recipes of a VPBasicBlock with an additional Recipe as the last recipe.
Definition VPlan.h:4504
RecipeListTy::iterator iterator
Instruction iterators...
Definition VPlan.h:4456
iterator end()
Definition VPlan.h:4466
iterator begin()
Recipe iterator methods.
Definition VPlan.h:4464
iterator_range< iterator > phis()
Returns an iterator range over the PHI-like recipes in the block.
Definition VPlan.h:4517
iterator getFirstNonPhi()
Return the position of the first non-phi node recipe in the block.
Definition VPlan.cpp:228
VPBasicBlock * splitAt(iterator SplitAt)
Split current block at SplitAt by inserting a new block between the current block and its successors ...
Definition VPlan.cpp:528
VPRecipeBase * getTerminator()
If the block has multiple successors, return the branch recipe terminating the block.
Definition VPlan.cpp:607
void insert(VPRecipeBase *Recipe, iterator InsertPt)
Definition VPlan.h:4495
VPBlockBase is the building block of the Hierarchical Control-Flow Graph.
Definition VPlan.h:97
void setSuccessors(ArrayRef< VPBlockBase * > NewSuccs)
Set each VPBasicBlock in NewSuccss as successor of this VPBlockBase.
Definition VPlan.h:307
VPRegionBlock * getParent()
Definition VPlan.h:195
iterator_range< VPBlockBase ** > predecessors()
Definition VPlan.h:228
const VPBasicBlock * getExitingBasicBlock() const
Definition VPlan.cpp:198
void setName(const Twine &newName)
Definition VPlan.h:188
size_t getNumSuccessors() const
Definition VPlan.h:245
void swapSuccessors()
Swap successors of the block. The block must have exactly 2 successors.
Definition VPlan.h:329
size_t getNumPredecessors() const
Definition VPlan.h:246
void setPredecessors(ArrayRef< VPBlockBase * > NewPreds)
Set each VPBasicBlock in NewPreds as predecessor of this VPBlockBase.
Definition VPlan.h:298
bool hasSuccessors() const
Returns true if this block has any successors.
Definition VPlan.h:223
const VPBlocksTy & getPredecessors() const
Definition VPlan.h:230
void setTwoSuccessors(VPBlockBase *IfTrue, VPBlockBase *IfFalse)
Set two given VPBlockBases IfTrue and IfFalse to be the two successors of this VPBlockBase.
Definition VPlan.h:289
VPBlockBase * getSinglePredecessor() const
Definition VPlan.h:241
void swapPredecessors()
Swap predecessors of the block.
Definition VPlan.h:321
const VPBasicBlock * getEntryBasicBlock() const
Definition VPlan.cpp:183
void setOneSuccessor(VPBlockBase *Successor)
Set a given VPBlockBase Successor as the single successor of this VPBlockBase.
Definition VPlan.h:278
void setParent(VPRegionBlock *P)
Definition VPlan.h:205
VPBlockBase * getSingleSuccessor() const
Definition VPlan.h:235
const VPBlocksTy & getSuccessors() const
Definition VPlan.h:219
static auto blocksAs(T &&Range)
Return an iterator range over Range with each block cast to BlockTy.
Definition VPlanUtils.h:421
static void insertBlockAfter(VPBlockBase *NewBlock, VPBlockBase *BlockPtr)
Insert disconnected VPBlockBase NewBlock after BlockPtr.
Definition VPlanUtils.h:303
static void insertOnEdge(VPBlockBase *From, VPBlockBase *To, VPBlockBase *BlockPtr)
Inserts BlockPtr on the edge between From and To.
Definition VPlanUtils.h:440
static VPBasicBlock * getPlainCFGMiddleBlock(const VPlan &Plan)
Returns the middle block of Plan in plain CFG form (before regions are formed).
static bool isHeader(const VPBlockBase *VPB, const VPDominatorTree &VPDT)
Returns true if VPB is a loop header, based on regions or VPDT in their absence.
static void connectBlocks(VPBlockBase *From, VPBlockBase *To, unsigned PredIdx=-1u, unsigned SuccIdx=-1u)
Connect VPBlockBases From and To bi-directionally.
Definition VPlanUtils.h:348
static void disconnectBlocks(VPBlockBase *From, VPBlockBase *To)
Disconnect VPBlockBases From and To bi-directionally.
Definition VPlanUtils.h:366
static std::pair< VPBasicBlock *, VPBasicBlock * > getPlainCFGHeaderAndLatch(const VPlan &Plan)
Returns the header and latch of the outermost loop of Plan in plain CFG form (before regions are form...
static void transferSuccessors(VPBlockBase *Old, VPBlockBase *New)
Transfer successors from Old to New. New must have no successors.
Definition VPlanUtils.h:398
VPInstruction * createFreeze(VPValue *Op, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="")
static VPBuilderBase getToInsertAfter(VPRecipeBase *R)
VPPhi * createScalarPhi(ArrayRef< VPValue * > IncomingValues, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="", std::optional< VPIRFlags > Flags=std::nullopt, Type *ResultTy=nullptr)
Create a phi with IncomingValues, using the default flags for the result type, unless Flags is set.
VPInstruction * createAnd(VPValue *LHS, VPValue *RHS, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="")
VPRecipeBase * getRecipeAtInsertPoint() const
Get the recipe at the current insert point or nullptr if the insert point is the end of the block.
VPInstruction * createSelect(VPValue *Cond, VPValue *TrueVal, VPValue *FalseVal, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="", std::optional< VPIRFlags > Flags=std::nullopt)
Create a select of TrueVal and FalseVal based on Cond, using the default flags for the result type,...
VPInstruction * createNot(VPValue *Operand, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="")
void setInsertPoint(const VPInsertPoint &IP)
Set the current insert point.
VPInstruction * createNaryOp(unsigned Opcode, ArrayRef< VPValue * > Operands, Instruction *Inst=nullptr, const VPIRFlags &Flags={}, const VPIRMetadata &MD={}, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="", Type *ResultTy=nullptr)
Create an N-ary operation with Opcode, Operands and set Inst as its underlying Instruction.
VPInstruction * createFCmp(CmpInst::Predicate Pred, VPValue *A, VPValue *B, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="")
Create a new FCmp VPInstruction with predicate Pred and operands A and B.
VPInstruction * createOr(VPValue *LHS, VPValue *RHS, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="")
VPInstruction * createICmp(CmpInst::Predicate Pred, VPValue *A, VPValue *B, DebugLoc DL=DebugLoc::getUnknown(), const Twine &Name="")
Create a new ICmp VPInstruction with predicate Pred and operands A and B.
unsigned getNumDefinedValues() const
Returns the number of values defined by the VPDef.
Definition VPlanValue.h:577
VPValue * getVPSingleValue()
Returns the only VPValue defined by the VPDef.
Definition VPlanValue.h:550
A recipe for converting Current into Start + Current * Step.
Definition VPlan.h:4210
Template specialization of the standard LLVM dominator tree utility for VPBlockBases.
LLVM_ABI_FOR_TEST bool properlyDominates(const VPRecipeBase *A, const VPRecipeBase *B) const
A pure virtual base class for all recipes modeling header phis, including phis for first order recurr...
Definition VPlan.h:2459
virtual VPValue * getBackedgeValue()
Returns the incoming value from the loop backedge.
Definition VPlan.h:2502
VPValue * getStartValue()
Returns the start value of the phi, if one is set.
Definition VPlan.h:2491
A special type of VPBasicBlock that wraps an existing IR basic block.
Definition VPlan.h:4582
Class to record and manage LLVM IR flags.
Definition VPlan.h:688
RecurKind getRecurKind() const
Definition VPlan.h:1038
Helper to manage IR metadata for recipes.
Definition VPlan.h:1163
This is a concrete Recipe that models a single VPlan-level instruction.
Definition VPlan.h:1282
@ ExtractLastActive
Extracts the last active lane from a set of vectors.
Definition VPlan.h:1396
@ ExtractLane
Extracts a single lane (first operand) from a set of vector operands.
Definition VPlan.h:1387
@ ExitingIVValue
Compute the exiting value of a wide induction after vectorization, that is the value of the last lane...
Definition VPlan.h:1400
@ ComputeReductionResult
Reduce the operands to the final reduction result using the operation specified via the operation's V...
Definition VPlan.h:1341
void addIncoming(VPValue *IncomingV)
Append IncomingV as an incoming value to the phi-like recipe.
Definition VPlan.h:1654
VPRecipeBase is a base class modeling a sequence of one or more output IR instructions.
Definition VPlan.h:403
bool isPhi() const
Returns true for PHI-like recipes.
VPBasicBlock * getParent()
Definition VPlan.h:475
DebugLoc getDebugLoc() const
Returns the debug location of the recipe.
Definition VPlan.h:553
void moveBefore(VPBasicBlock &BB, iplist< VPRecipeBase >::iterator I)
Unlink this recipe and insert into BB before I.
void insertBefore(VPRecipeBase *InsertPos)
Insert an unlinked recipe into a basic block immediately before the specified recipe.
iplist< VPRecipeBase >::iterator eraseFromParent()
This method unlinks 'this' from the containing basic block and deletes it.
void moveAfter(VPRecipeBase *MovePos)
Unlink this recipe from its current VPBasicBlock and insert it into the VPBasicBlock that MovePos liv...
Type * getScalarType() const
Returns the scalar type of this VPRecipeValue.
Definition VPlanValue.h:349
A recipe for handling reduction phis.
Definition VPlan.h:2862
bool isOrdered() const
Returns true, if the phi is part of an ordered reduction.
Definition VPlan.h:2934
unsigned getVFScaleFactor() const
Get the factor that the VF of this recipe's output should be scaled by, or 1 if it isn't scaled.
Definition VPlan.h:2918
bool isInLoop() const
Returns true if the phi is part of an in-loop reduction.
Definition VPlan.h:2937
RecurKind getRecurrenceKind() const
Returns the recurrence kind of the reduction.
Definition VPlan.h:2931
A recipe to represent inloop, ordered or partial reduction operations.
Definition VPlan.h:3245
VPRegionBlock represents a collection of VPBasicBlocks and VPRegionBlocks which form a Single-Entry-S...
Definition VPlan.h:4654
VPRegionValue * createHeaderMask()
Create the header mask for the region and return it.
Definition VPlan.h:4801
Type * getCanonicalIVType() const
Return the type of the canonical IV for loop regions.
Definition VPlan.h:4782
VPRegionValue * getCanonicalIV()
Return the canonical induction variable of the region, null for replicating regions.
Definition VPlan.h:4774
VPRegionValue * getHeaderMask() const
Return the header mask of the region, or null if not set.
Definition VPlan.h:4787
DebugLoc getDebugLoc() const
Returns the debug location of the VPRegionValue.
Definition VPlanValue.h:262
Lightweight SCEV-to-VPlan expander.
Definition VPlanUtils.h:268
VPValue * expand(const SCEV *S)
Expand S into recipes and live-ins using the builder.
VPSingleDefRecipe is a base class for recipes that model a sequence of one or more output IR that def...
Definition VPlan.h:611
Type * getType() const
Returns the scalar type of this symbolic value.
Definition VPlanValue.h:227
This class augments VPValue with operands which provide the inverse def-use edges from VPValue's user...
Definition VPlanValue.h:396
void replaceUsesOfWith(VPValue *From, VPValue *To)
Replaces all uses of From in the VPUser with To.
Definition VPlan.cpp:1485
operand_range operands()
Definition VPlanValue.h:472
void setOperand(unsigned I, VPValue *New)
Definition VPlanValue.h:445
VPValue * getOperand(unsigned N) const
Definition VPlanValue.h:437
This is the base class of the VPlan Def/Use graph, used for modeling the data flow into,...
Definition VPlanValue.h:50
Type * getScalarType() const
Returns the scalar type of this VPValue, dispatching based on the concrete subclass.
Definition VPlan.cpp:142
VPRecipeBase * getDefiningRecipe()
Returns the recipe defining this VPValue or nullptr if it is not defined by a recipe,...
Definition VPlan.cpp:123
void replaceUsesWithIf(VPValue *New, llvm::function_ref< bool(VPUser *U)> ShouldReplace)
Go through the uses list for this VPValue and make each use point to New if the callback ShouldReplac...
Definition VPlan.cpp:1458
void setUnderlyingValue(Value *Val)
Definition VPlanValue.h:204
void replaceAllUsesWith(VPValue *New)
Definition VPlan.cpp:1452
unsigned getNumUsers() const
Definition VPlanValue.h:115
user_range users()
Definition VPlanValue.h:157
Base class for widened induction (VPWidenIntOrFpInductionRecipe and VPWidenPointerInductionRecipe),...
Definition VPlan.h:2527
VPValue * getStepValue()
Returns the step value of the induction.
Definition VPlan.h:2569
const InductionDescriptor & getInductionDescriptor() const
Returns the induction descriptor for the recipe.
Definition VPlan.h:2586
A recipe for handling phi nodes of integer and floating-point inductions, producing their vector valu...
Definition VPlan.h:2615
bool isCanonical() const
Returns true if the induction is canonical, i.e.
VPlan models a candidate for vectorization, encoding various decisions take to produce efficient outp...
Definition VPlan.h:4841
VPIRValue * getLiveIn(Value *V) const
Return the live-in VPIRValue for V, if there is one or nullptr otherwise.
Definition VPlan.h:5184
LLVMContext & getContext() const
Definition VPlan.h:5051
VPBasicBlock * getEntry()
Definition VPlan.h:4937
VPValue * getTripCount() const
The trip count of the original loop.
Definition VPlan.h:5009
VPIRValue * getFalse()
Return a VPIRValue wrapping i1 false.
Definition VPlan.h:5150
VPSymbolicValue & getVFxUF()
Returns VF * UF of the vector loop region.
Definition VPlan.h:5049
VPIRBasicBlock * createEmptyVPIRBasicBlock(BasicBlock *IRBB)
Create a VPIRBasicBlock wrapping IRBB, but do not create VPIRInstructions wrapping the instructions i...
Definition VPlan.cpp:1288
VPIRValue * getPoison(Type *Ty)
Return a VPIRValue wrapping a poison value of type Ty.
Definition VPlan.h:5178
ArrayRef< VPIRBasicBlock * > getExitBlocks() const
Return an ArrayRef containing VPIRBasicBlocks wrapping the exit blocks of the original scalar loop.
Definition VPlan.h:5003
VPSymbolicValue & getVectorTripCount()
The vector trip count.
Definition VPlan.h:5039
VPIRValue * getOrAddLiveIn(Value *V)
Gets the live-in VPIRValue for V or adds a new live-in (if none exists yet) for V.
Definition VPlan.h:5127
VPRegionBlock * createLoopRegion(Type *CanIVTy, DebugLoc DL, const std::string &Name="", VPBlockBase *Entry=nullptr, VPBlockBase *Exiting=nullptr)
Create a new loop region with a canonical IV using CanIVTy and DL.
Definition VPlan.h:5223
LLVM_ABI_FOR_TEST VPRegionBlock * getVectorLoopRegion()
Returns the VPRegionBlock of the vector loop.
Definition VPlan.cpp:1030
void setTripCount(VPValue *NewTripCount)
Set the trip count assuming it is currently null; if it is not - use resetTripCount().
Definition VPlan.h:5016
VPBasicBlock * getMiddleBlock()
Returns the 'middle' block of the plan, that is the block that selects whether to execute the scalar ...
Definition VPlan.h:4979
VPBasicBlock * createVPBasicBlock(const Twine &Name, VPRecipeBase *Recipe=nullptr)
Create a new VPBasicBlock with Name and containing Recipe if present.
Definition VPlan.h:5210
LLVM_ABI_FOR_TEST VPIRBasicBlock * createVPIRBasicBlock(BasicBlock *IRBB)
Create a VPIRBasicBlock from IRBB containing VPIRInstructions for all instructions in IRBB,...
Definition VPlan.cpp:1296
VPIRValue * getTrue()
Return a VPIRValue wrapping i1 true.
Definition VPlan.h:5147
VPBasicBlock * getVectorPreheader() const
Returns the preheader of the vector loop region, if one exists, or null otherwise.
Definition VPlan.h:4942
bool hasScalarVFOnly() const
Definition VPlan.h:5095
VPBasicBlock * getScalarPreheader() const
Return the VPBasicBlock for the preheader of the scalar loop.
Definition VPlan.h:4993
VPIRBasicBlock * getScalarHeader() const
Return the VPIRBasicBlock wrapping the header of the scalar loop.
Definition VPlan.h:4999
VPSymbolicValue & getVF()
Returns the VF of the vector loop region.
Definition VPlan.h:5042
bool hasScalarTail() const
Returns true if the scalar tail may execute after the vector loop, i.e.
Definition VPlan.h:5283
VPIRValue * getConstantInt(Type *Ty, uint64_t Val, bool IsSigned=false)
Return a VPIRValue wrapping a ConstantInt with the given type and value.
Definition VPlan.h:5161
LLVM Value Representation.
Definition Value.h:75
Type * getType() const
All values are typed, get the type of this value.
Definition Value.h:257
LLVM_ABI StringRef getName() const
Return a constant reference to the value's name.
Definition Value.cpp:319
constexpr ScalarTy getKnownMinValue() const
Returns the minimum value this quantity can represent.
Definition TypeSize.h:165
An efficient, type-erasing, non-owning reference to a callable.
self_iterator getIterator()
Definition ilist_node.h:123
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ Entry
Definition COFF.h:862
@ BasicBlock
Various leaf nodes.
Definition ISDOpcodes.h:83
void reportVectorizationFailure(const StringRef DebugMsg, const StringRef OREMsg, const StringRef ORETag, OptimizationRemarkEmitter *ORE, const Loop *TheLoop, Instruction *I=nullptr)
Reports a vectorization failure: print DebugMsg for debugging purposes along with the corresponding o...
auto m_Cmp()
Matches any compare instruction and ignore it.
BinaryOp_match< LHS, RHS, Instruction::Add > m_Add(const LHS &L, const RHS &R)
match_combine_or< CastInst_match< OpTy, TruncInst >, OpTy > m_TruncOrSelf(const OpTy &Op)
bool match(Val *V, const Pattern &P)
specificval_ty m_Specific(const Value *V)
Match if we have a specific specified value.
ThreeOps_match< Cond, LHS, RHS, Instruction::Select > m_Select(const Cond &C, const LHS &L, const RHS &R)
Matches SelectInst.
SpecificCmpClass_match< LHS, RHS, ICmpInst > m_SpecificICmp(CmpPredicate MatchPred, const LHS &L, const RHS &R)
SelectLike_match< CondTy, LTy, RTy > m_SelectLike(const CondTy &C, const LTy &TrueC, const RTy &FalseC)
Matches a value that behaves like a boolean-controlled select, i.e.
auto m_Intrinsic(const Ts &...Ops)
Match intrinsic calls like this: m_Intrinsic<Intrinsic::fabs>(m_Value(X))
BinaryOp_match< LHS, RHS, Instruction::Sub > m_Sub(const LHS &L, const RHS &R)
VPInstruction_match< VPInstruction::ExtractLastLane, VPInstruction_match< VPInstruction::ExtractLastPart, Op0_t > > m_ExtractLastLaneOfLastPart(const Op0_t &Op0)
bool matchFindIVResult(VPInstruction *VPI, Op0_t ReducedIV, Op1_t Start)
Match FindIV result pattern: select(icmp ne ComputeReductionResult(ReducedIV), Sentinel),...
VPInstruction_match< VPInstruction::BranchOnTwoConds > m_BranchOnTwoConds()
VPInstruction_match< VPInstruction::ExtractLastLane, Op0_t > m_ExtractLastLane(const Op0_t &Op0)
VPInstruction_match< VPInstruction::BranchOnCount > m_BranchOnCount()
auto m_VPValue()
Match an arbitrary VPValue and ignore it.
VPInstruction_match< VPInstruction::ExtractLastPart, Op0_t > m_ExtractLastPart(const Op0_t &Op0)
VPRecipeBase * findUserOf(VPValue *V, const MatchT &P)
If V is used by a recipe matching pattern P, return it.
match_bind< VPInstruction > m_VPInstruction(VPInstruction *&V)
Match a VPInstruction, capturing if we match.
VPInstruction_match< VPInstruction::BranchOnCond > m_BranchOnCond()
NodeAddr< PhiNode * > Phi
Definition RDFGraph.h:390
friend class Instruction
Iterator for Instructions in a `BasicBlock.
Definition BasicBlock.h:73
VPValue * getOrCreateVPValueForSCEVExpr(VPlan &Plan, const SCEV *Expr)
Get or create a VPValue that corresponds to the expansion of Expr.
bool cannotHoistOrSinkRecipe(const VPRecipeBase &R, bool Sinking=false)
Return true if we do not know how to (mechanically) hoist or sink R.
VPInstruction * findComputeReductionResult(VPReductionPHIRecipe *PhiR)
Find the ComputeReductionResult recipe for PhiR, looking through selects inserted for predicated redu...
SmallVector< std::pair< VPBasicBlock *, VPIRBasicBlock * > > getEarlyExits(const VPlan &Plan, const VPBlockBase *MiddleVPBB)
Returns the (early exiting block, exit block) pairs of Plan, i.e.
DenseMap< const VPBasicBlock *, std::optional< VPExecutionFrequency > > computeExecutionFrequencies(ArrayRef< VPBasicBlock * > Blocks)
Computes for each block in Blocks, which must be in reverse post-order, the frequency with which it e...
VPIRFlags getFlagsForInduction(const InductionDescriptor &ID, const VPPhi *PhiR)
Extracts and returns NoWrap flags from PhiR and fast-math flags from ID.
VPRecipeBase * findRecipe(VPValue *Start, PredT Pred)
Search Start's users for a recipe satisfying Pred, looking through recipes with definitions.
Definition VPlanUtils.h:145
LLVM_ABI_FOR_TEST const SCEV * getSCEVExprForVPValue(const VPValue *V, PredicatedScalarEvolution &PSE, const Loop *L=nullptr)
Return the SCEV expression for V.
This is an optimization pass for GlobalISel generic memory operations.
auto drop_begin(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the first N elements excluded.
Definition STLExtras.h:316
SmallVector< VPBasicBlock * > vp_rpo_plain_cfg_loop_body(VPBasicBlock *Header)
Returns the VPBasicBlocks forming the loop body of a plain (pre-region) VPlan in reverse post-order s...
Definition VPlanCFG.h:262
constexpr auto not_equal_to(T &&Arg)
Functor variant of std::not_equal_to that can be used as a UnaryPredicate in functional algorithms li...
Definition STLExtras.h:2196
LLVM_ABI Intrinsic::ID getMinMaxReductionIntrinsicOp(Intrinsic::ID RdxID)
Returns the min/max intrinsic used when expanding a min/max reduction.
detail::zippy< detail::zip_first, T, U, Args... > zip_equal(T &&t, U &&u, Args &&...args)
zip iterator that assumes that all iteratees have the same length.
Definition STLExtras.h:856
ReductionStyle getReductionStyle(bool InLoop, bool Ordered, unsigned ScaleFactor)
Definition VPlan.h:2849
decltype(auto) dyn_cast(const From &Val)
dyn_cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:643
@ Load
The value being inserted comes from a load (InsertElement only).
VPBuilderBase<> VPBuilder
Definition VPlan.h:67
auto map_to_vector(ContainerTy &&C, FuncTy &&F)
Map a range to a SmallVector with element types deduced from the mapping.
iterator_range< early_inc_iterator_impl< detail::IterOfRange< RangeT > > > make_early_inc_range(RangeT &&Range)
Make a range that does early increment to allow mutation of the underlying range without disrupting i...
Definition STLExtras.h:649
iterator_range< df_iterator< VPBlockShallowTraversalWrapper< VPBlockBase * > > > vp_depth_first_shallow(VPBlockBase *G)
Returns an iterator range to traverse the graph starting at G in depth-first order.
Definition VPlanCFG.h:250
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Value
Definition InstrProf.h:143
auto make_isa_range(RangeT &&Range)
Return a range over Range containing only elements for which isa<T> holds, casting each of them to T.
Definition STLExtras.h:567
auto dyn_cast_or_null(const Y &Val)
Definition Casting.h:753
bool any_of(R &&range, UnaryPredicate P)
Provide wrappers to std::any_of which take ranges instead of having to pass begin/end explicitly.
Definition STLExtras.h:1762
auto reverse(ContainerTy &&C)
Definition STLExtras.h:408
constexpr size_t range_size(R &&Range)
Returns the size of the Range, i.e., the number of elements.
Definition STLExtras.h:1710
void sort(IteratorTy Start, IteratorTy End)
Definition STLExtras.h:1652
LLVM_ABI raw_ostream & dbgs()
dbgs() - This returns a reference to a raw_ostream for debugging messages.
Definition Debug.cpp:209
SmallVector< ValueTypeFromRangeType< R >, Size > to_vector(R &&Range)
Given a range of type R, iterate the entire range and return a SmallVector with elements of the vecto...
iterator_range< filter_iterator< detail::IterOfRange< RangeT >, PredicateT > > make_filter_range(RangeT &&Range, PredicateT Pred)
Convenience function that takes a range of elements and a predicate, and return a new filter_iterator...
Definition STLExtras.h:552
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
bool isa(const From &Val)
isa<X> - Return true if the parameter to the template is an instance of one of the template type argu...
Definition Casting.h:547
auto drop_end(T &&RangeOrContainer, size_t N=1)
Return a range covering RangeOrContainer with the last N elements excluded.
Definition STLExtras.h:323
RecurKind
These are the kinds of recurrences that we support.
@ UMin
Unsigned integer min implemented in terms of select(cmp()).
@ FMinimumNum
FP min with llvm.minimumnum semantics.
@ FindIV
FindIV reduction with select(icmp(),x,y) where one of (x,y) is a loop induction variable (increasing ...
@ FMinimum
FP min with llvm.minimum semantics.
@ FMaxNum
FP max with llvm.maxnum semantics including NaNs.
@ AnyOf
AnyOf reduction with select(cmp(),x,y) where one of (x,y) is loop invariant, and both x and y are int...
@ FMax
FP max implemented in terms of select(cmp()).
@ FMaximum
FP max with llvm.maximum semantics.
@ FMulAdd
Sum of float products with llvm.fmuladd(a * b + sum).
@ SMax
Signed integer max implemented in terms of select(cmp()).
@ SMin
Signed integer min implemented in terms of select(cmp()).
@ FMin
FP min implemented in terms of select(cmp()).
@ FMinNum
FP min with llvm.minnum semantics including NaNs.
@ Sub
Subtraction of integers.
@ AddChainWithSubs
A chain of adds and subs.
@ FMaximumNum
FP max with llvm.maximumnum semantics.
@ UMax
Unsigned integer max implemented in terms of select(cmp()).
RelativeUniformCounterPtr ValuesPtrExpr VTableAddr Count
Definition InstrProf.h:145
DWARFExpression::Operation Op
ArrayRef(const T &OneElt) -> ArrayRef< T >
auto count_if(R &&Range, UnaryPredicate P)
Wrapper function around std::count_if to count the number of times an element satisfying a given pred...
Definition STLExtras.h:2035
decltype(auto) cast(const From &Val)
cast<X> - Return the argument parameter cast to the specified type.
Definition Casting.h:559
auto find_if(R &&Range, UnaryPredicate P)
Provide wrappers to std::find_if which take ranges instead of having to pass begin/end explicitly.
Definition STLExtras.h:1788
constexpr auto seq(T Begin, T End)
Iterate over an integral type from Begin up to - but not including - End.
Definition Sequence.h:341
auto predecessors(const MachineBasicBlock *BB)
bool is_contained(R &&Range, const E &Element)
Returns true if Element is found in Range.
Definition STLExtras.h:1963
bool equal(L &&LRange, R &&RRange)
Wrapper function around std::equal to detect if pair-wise elements between two ranges are the same.
Definition STLExtras.h:2162
@ End
Run the machine verifier once, at the end of the pipeline.
Definition CodeGen.h:267
LLVM_ABI bool isDereferenceableAndAlignedInLoop(LoadInst *LI, Loop *L, ScalarEvolution &SE, DominatorTree &DT, AssumptionCache *AC=nullptr, SmallVectorImpl< const SCEVPredicate * > *Predicates=nullptr)
Return true if we can prove that the given load (which is assumed to be within the specified loop) wo...
Definition Loads.cpp:304
constexpr detail::IsaCheckPredicate< Types... > IsaPred
Function object wrapper for the llvm::isa type check.
Definition Casting.h:866
void swap(llvm::BitVector &LHS, llvm::BitVector &RHS)
Implement std::swap in terms of BitVector swap.
Definition BitVector.h:880
A MapVector that performs no allocations if smaller than a certain size.
Definition MapVector.h:342
A recipe for handling first-order recurrence phis.
Definition VPlan.h:2800
A VPValue representing a live-in from the input IR or a constant.
Definition VPlanValue.h:274
static void simplifyLiveInsWithSCEV(VPlan &Plan, PredicatedScalarEvolution &PSE)
Check Plan's live-ins and replace them with constants, if they can be simplified via SCEV.
static void addMinimumVectorEpilogueIterationCheck(VPlan &Plan, VPValue *MainVectorTripCount, bool RequiresScalarEpilogue, ElementCount EpilogueVF, unsigned MainLoopStep, unsigned EpilogueLoopStep, ScalarEvolution &SE)
Add a check to Plan to see if the epilogue vector loop should be executed.
static void foldTailByMasking(VPlan &Plan)
Adapts the vector loop region for tail folding by introducing a header mask and conditionally executi...
static bool handleMultiUseReductions(VPlan &Plan, OptimizationRemarkEmitter *ORE, Loop *TheLoop)
Try to legalize reductions with multiple in-loop uses.
static void recordExecutionFrequencies(VPlan &Plan)
Add execution frequencies to each recipe in the loop body of Plan.
static bool handleFindLastReductions(VPlan &Plan)
Check if Plan contains any FindLast reductions.
static void createInLoopReductionRecipes(VPlan &Plan, ElementCount MinVF)
Create VPReductionRecipes for in-loop reductions.
static void modelGeneratedMainLoopBlocks(VPlan &EpiPlan, VPlan &MainPlan, VPIRBasicBlock *EnteredFrom)
Model the blocks the executed MainPlan generated for the main vector loop in EpiPlan during epilogue ...
static LLVM_ABI_FOR_TEST void createLoopRegions(VPlan &Plan, DebugLoc DL)
Replace loops in Plan's flat CFG with VPRegionBlocks, turning Plan's flat CFG into a hierarchical CFG...
static LLVM_ABI_FOR_TEST void addMiddleCheck(VPlan &Plan)
If a check is needed to guard executing the scalar epilogue loop, it will be added to the middle bloc...
static void attachAliasMaskToHeaderMask(VPlan &Plan)
Attaches the alias-mask to the existing header-mask.
static bool areAllLoadsDereferenceable(VPBasicBlock *HeaderVPBB, Loop *TheLoop, PredicatedScalarEvolution &PSE, DominatorTree &DT, AssumptionCache *AC)
Check if all loads in the loop are dereferenceable.
static LLVM_ABI_FOR_TEST std::unique_ptr< VPlan > buildVPlan0(Loop *TheLoop, LoopInfo &LI, Type *InductionTy, PredicatedScalarEvolution &PSE, LoopVersioning *LVer=nullptr, function_ref< const BranchProbabilityInfo &()> GetBPI=nullptr)
Create a base VPlan0, serving as the common starting point for all later candidates.
static bool handleMaxMinNumReductions(VPlan &Plan)
Check if Plan contains any FMaxNum or FMinNum reductions.
static void attachCheckBlock(VPlan &Plan, Value *Cond, BasicBlock *CheckBlock, bool AddBranchWeights)
static LLVM_ABI_FOR_TEST void handleCountableEarlyExits(VPlan &Plan)
Disconnect countable early exits from the loop.
static bool finalizeSCEVPredicates(VPlan &Plan, PredicatedScalarEvolution &PSE, bool OptForSize, unsigned SCEVCheckThreshold, OptimizationRemarkEmitter *ORE, Loop *TheLoop)
Finalize SCEV predicates by adding induction predicates from Plan to PSE and checking constraints.
static void addIterationCountCheckBlock(VPlan &Plan, ElementCount VF, unsigned UF, bool RequiresScalarEpilogue, Loop *OrigLoop, const uint32_t *MinItersBypassWeights, DebugLoc DL, PredicatedScalarEvolution &PSE)
Add a new check block before the vector preheader to Plan to check if the main vector loop should be ...
static void addMinimumIterationCheck(VPlan &Plan, ElementCount VF, unsigned UF, ElementCount MinProfitableTripCount, bool RequiresScalarEpilogue, bool TailFolded, Loop *OrigLoop, const uint32_t *MinItersBypassWeights, DebugLoc DL, PredicatedScalarEvolution &PSE, VPBasicBlock *CheckBlock)
static void attachVPCheckBlock(VPlan &Plan, VPValue *Cond, VPBasicBlock *CheckBlock, bool AddBranchWeights)
Connect CheckBlock to Plan, branching on Cond.
static LLVM_ABI_FOR_TEST bool createHeaderPhiRecipes(VPlan &Plan, PredicatedScalarEvolution &PSE, Loop &OrigLoop, OptimizationRemarkEmitter *ORE, const VPDominatorTree &VPDT, const MapVector< PHINode *, InductionDescriptor > &Inductions, const MapVector< PHINode *, RecurrenceDescriptor > &Reductions, const SmallPtrSetImpl< const PHINode * > &FixedOrderRecurrences, const SmallPtrSetImpl< PHINode * > &InLoopReductions, bool AllowReordering)
Replace VPPhi recipes in Plan's header with corresponding VPHeaderPHIRecipe subclasses for inductions...
static void attachMemoryChecks(VPlan &Plan, ArrayRef< RuntimePointerCheck > Checks, ScalarEvolution &SE, DebugLoc DL, bool AddBranchWeights)
Generate Checks as recipes and attach the check block to Plan.