1 //===- VPlan.h - Represent A Vectorizer Plan --------------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 /// \file 10 /// This file contains the declarations of the Vectorization Plan base classes: 11 /// 1. VPBasicBlock and VPRegionBlock that inherit from a common pure virtual 12 /// VPBlockBase, together implementing a Hierarchical CFG; 13 /// 2. Specializations of GraphTraits that allow VPBlockBase graphs to be 14 /// treated as proper graphs for generic algorithms; 15 /// 3. Pure virtual VPRecipeBase serving as the base class for recipes contained 16 /// within VPBasicBlocks; 17 /// 4. VPInstruction, a concrete Recipe and VPUser modeling a single planned 18 /// instruction; 19 /// 5. The VPlan class holding a candidate for vectorization; 20 /// 6. The VPlanPrinter class providing a way to print a plan in dot format; 21 /// These are documented in docs/VectorizationPlan.rst. 22 // 23 //===----------------------------------------------------------------------===// 24 25 #ifndef LLVM_TRANSFORMS_VECTORIZE_VPLAN_H 26 #define LLVM_TRANSFORMS_VECTORIZE_VPLAN_H 27 28 #include "VPlanLoopInfo.h" 29 #include "VPlanValue.h" 30 #include "llvm/ADT/DenseMap.h" 31 #include "llvm/ADT/DepthFirstIterator.h" 32 #include "llvm/ADT/GraphTraits.h" 33 #include "llvm/ADT/Optional.h" 34 #include "llvm/ADT/SmallBitVector.h" 35 #include "llvm/ADT/SmallPtrSet.h" 36 #include "llvm/ADT/SmallSet.h" 37 #include "llvm/ADT/SmallVector.h" 38 #include "llvm/ADT/Twine.h" 39 #include "llvm/ADT/ilist.h" 40 #include "llvm/ADT/ilist_node.h" 41 #include "llvm/Analysis/VectorUtils.h" 42 #include "llvm/IR/IRBuilder.h" 43 #include <algorithm> 44 #include <cassert> 45 #include <cstddef> 46 #include <map> 47 #include <string> 48 49 namespace llvm { 50 51 class BasicBlock; 52 class DominatorTree; 53 class InnerLoopVectorizer; 54 class LoopInfo; 55 class raw_ostream; 56 class RecurrenceDescriptor; 57 class Value; 58 class VPBasicBlock; 59 class VPRegionBlock; 60 class VPlan; 61 class VPlanSlp; 62 63 /// A range of powers-of-2 vectorization factors with fixed start and 64 /// adjustable end. The range includes start and excludes end, e.g.,: 65 /// [1, 9) = {1, 2, 4, 8} 66 struct VFRange { 67 // A power of 2. 68 const unsigned Start; 69 70 // Need not be a power of 2. If End <= Start range is empty. 71 unsigned End; 72 }; 73 74 using VPlanPtr = std::unique_ptr<VPlan>; 75 76 /// In what follows, the term "input IR" refers to code that is fed into the 77 /// vectorizer whereas the term "output IR" refers to code that is generated by 78 /// the vectorizer. 79 80 /// VPIteration represents a single point in the iteration space of the output 81 /// (vectorized and/or unrolled) IR loop. 82 struct VPIteration { 83 /// in [0..UF) 84 unsigned Part; 85 86 /// in [0..VF) 87 unsigned Lane; 88 }; 89 90 /// This is a helper struct for maintaining vectorization state. It's used for 91 /// mapping values from the original loop to their corresponding values in 92 /// the new loop. Two mappings are maintained: one for vectorized values and 93 /// one for scalarized values. Vectorized values are represented with UF 94 /// vector values in the new loop, and scalarized values are represented with 95 /// UF x VF scalar values in the new loop. UF and VF are the unroll and 96 /// vectorization factors, respectively. 97 /// 98 /// Entries can be added to either map with setVectorValue and setScalarValue, 99 /// which assert that an entry was not already added before. If an entry is to 100 /// replace an existing one, call resetVectorValue and resetScalarValue. This is 101 /// currently needed to modify the mapped values during "fix-up" operations that 102 /// occur once the first phase of widening is complete. These operations include 103 /// type truncation and the second phase of recurrence widening. 104 /// 105 /// Entries from either map can be retrieved using the getVectorValue and 106 /// getScalarValue functions, which assert that the desired value exists. 107 struct VectorizerValueMap { 108 friend struct VPTransformState; 109 110 private: 111 /// The unroll factor. Each entry in the vector map contains UF vector values. 112 unsigned UF; 113 114 /// The vectorization factor. Each entry in the scalar map contains UF x VF 115 /// scalar values. 116 ElementCount VF; 117 118 /// The vector and scalar map storage. We use std::map and not DenseMap 119 /// because insertions to DenseMap invalidate its iterators. 120 using VectorParts = SmallVector<Value *, 2>; 121 using ScalarParts = SmallVector<SmallVector<Value *, 4>, 2>; 122 std::map<Value *, VectorParts> VectorMapStorage; 123 std::map<Value *, ScalarParts> ScalarMapStorage; 124 125 public: 126 /// Construct an empty map with the given unroll and vectorization factors. 127 VectorizerValueMap(unsigned UF, ElementCount VF) : UF(UF), VF(VF) {} 128 129 /// \return True if the map has any vector entry for \p Key. 130 bool hasAnyVectorValue(Value *Key) const { 131 return VectorMapStorage.count(Key); 132 } 133 134 /// \return True if the map has a vector entry for \p Key and \p Part. 135 bool hasVectorValue(Value *Key, unsigned Part) const { 136 assert(Part < UF && "Queried Vector Part is too large."); 137 if (!hasAnyVectorValue(Key)) 138 return false; 139 const VectorParts &Entry = VectorMapStorage.find(Key)->second; 140 assert(Entry.size() == UF && "VectorParts has wrong dimensions."); 141 return Entry[Part] != nullptr; 142 } 143 144 /// \return True if the map has any scalar entry for \p Key. 145 bool hasAnyScalarValue(Value *Key) const { 146 return ScalarMapStorage.count(Key); 147 } 148 149 /// \return True if the map has a scalar entry for \p Key and \p Instance. 150 bool hasScalarValue(Value *Key, const VPIteration &Instance) const { 151 assert(Instance.Part < UF && "Queried Scalar Part is too large."); 152 assert(Instance.Lane < VF.getKnownMinValue() && 153 "Queried Scalar Lane is too large."); 154 assert(!VF.isScalable() && "VF is assumed to be non scalable."); 155 156 if (!hasAnyScalarValue(Key)) 157 return false; 158 const ScalarParts &Entry = ScalarMapStorage.find(Key)->second; 159 assert(Entry.size() == UF && "ScalarParts has wrong dimensions."); 160 assert(Entry[Instance.Part].size() == VF.getKnownMinValue() && 161 "ScalarParts has wrong dimensions."); 162 return Entry[Instance.Part][Instance.Lane] != nullptr; 163 } 164 165 /// Retrieve the existing vector value that corresponds to \p Key and 166 /// \p Part. 167 Value *getVectorValue(Value *Key, unsigned Part) { 168 assert(hasVectorValue(Key, Part) && "Getting non-existent value."); 169 return VectorMapStorage[Key][Part]; 170 } 171 172 /// Retrieve the existing scalar value that corresponds to \p Key and 173 /// \p Instance. 174 Value *getScalarValue(Value *Key, const VPIteration &Instance) { 175 assert(hasScalarValue(Key, Instance) && "Getting non-existent value."); 176 return ScalarMapStorage[Key][Instance.Part][Instance.Lane]; 177 } 178 179 /// Set a vector value associated with \p Key and \p Part. Assumes such a 180 /// value is not already set. If it is, use resetVectorValue() instead. 181 void setVectorValue(Value *Key, unsigned Part, Value *Vector) { 182 assert(!hasVectorValue(Key, Part) && "Vector value already set for part"); 183 if (!VectorMapStorage.count(Key)) { 184 VectorParts Entry(UF); 185 VectorMapStorage[Key] = Entry; 186 } 187 VectorMapStorage[Key][Part] = Vector; 188 } 189 190 /// Set a scalar value associated with \p Key and \p Instance. Assumes such a 191 /// value is not already set. 192 void setScalarValue(Value *Key, const VPIteration &Instance, Value *Scalar) { 193 assert(!hasScalarValue(Key, Instance) && "Scalar value already set"); 194 if (!ScalarMapStorage.count(Key)) { 195 ScalarParts Entry(UF); 196 // TODO: Consider storing uniform values only per-part, as they occupy 197 // lane 0 only, keeping the other VF-1 redundant entries null. 198 for (unsigned Part = 0; Part < UF; ++Part) 199 Entry[Part].resize(VF.getKnownMinValue(), nullptr); 200 ScalarMapStorage[Key] = Entry; 201 } 202 ScalarMapStorage[Key][Instance.Part][Instance.Lane] = Scalar; 203 } 204 205 /// Reset the vector value associated with \p Key for the given \p Part. 206 /// This function can be used to update values that have already been 207 /// vectorized. This is the case for "fix-up" operations including type 208 /// truncation and the second phase of recurrence vectorization. 209 void resetVectorValue(Value *Key, unsigned Part, Value *Vector) { 210 assert(hasVectorValue(Key, Part) && "Vector value not set for part"); 211 VectorMapStorage[Key][Part] = Vector; 212 } 213 214 /// Reset the scalar value associated with \p Key for \p Part and \p Lane. 215 /// This function can be used to update values that have already been 216 /// scalarized. This is the case for "fix-up" operations including scalar phi 217 /// nodes for scalarized and predicated instructions. 218 void resetScalarValue(Value *Key, const VPIteration &Instance, 219 Value *Scalar) { 220 assert(hasScalarValue(Key, Instance) && 221 "Scalar value not set for part and lane"); 222 ScalarMapStorage[Key][Instance.Part][Instance.Lane] = Scalar; 223 } 224 }; 225 226 /// This class is used to enable the VPlan to invoke a method of ILV. This is 227 /// needed until the method is refactored out of ILV and becomes reusable. 228 struct VPCallback { 229 virtual ~VPCallback() {} 230 virtual Value *getOrCreateVectorValues(Value *V, unsigned Part) = 0; 231 virtual Value *getOrCreateScalarValue(Value *V, 232 const VPIteration &Instance) = 0; 233 }; 234 235 /// VPTransformState holds information passed down when "executing" a VPlan, 236 /// needed for generating the output IR. 237 struct VPTransformState { 238 VPTransformState(ElementCount VF, unsigned UF, LoopInfo *LI, 239 DominatorTree *DT, IRBuilder<> &Builder, 240 VectorizerValueMap &ValueMap, InnerLoopVectorizer *ILV, 241 VPCallback &Callback) 242 : VF(VF), UF(UF), Instance(), LI(LI), DT(DT), Builder(Builder), 243 ValueMap(ValueMap), ILV(ILV), Callback(Callback) {} 244 245 /// The chosen Vectorization and Unroll Factors of the loop being vectorized. 246 ElementCount VF; 247 unsigned UF; 248 249 /// Hold the indices to generate specific scalar instructions. Null indicates 250 /// that all instances are to be generated, using either scalar or vector 251 /// instructions. 252 Optional<VPIteration> Instance; 253 254 struct DataState { 255 /// A type for vectorized values in the new loop. Each value from the 256 /// original loop, when vectorized, is represented by UF vector values in 257 /// the new unrolled loop, where UF is the unroll factor. 258 typedef SmallVector<Value *, 2> PerPartValuesTy; 259 260 DenseMap<VPValue *, PerPartValuesTy> PerPartOutput; 261 } Data; 262 263 /// Get the generated Value for a given VPValue and a given Part. Note that 264 /// as some Defs are still created by ILV and managed in its ValueMap, this 265 /// method will delegate the call to ILV in such cases in order to provide 266 /// callers a consistent API. 267 /// \see set. 268 Value *get(VPValue *Def, unsigned Part) { 269 // If Values have been set for this Def return the one relevant for \p Part. 270 if (Data.PerPartOutput.count(Def)) 271 return Data.PerPartOutput[Def][Part]; 272 // Def is managed by ILV: bring the Values from ValueMap. 273 return Callback.getOrCreateVectorValues(VPValue2Value[Def], Part); 274 } 275 276 /// Get the generated Value for a given VPValue and given Part and Lane. 277 Value *get(VPValue *Def, const VPIteration &Instance) { 278 // If the Def is managed directly by VPTransformState, extract the lane from 279 // the relevant part. Note that currently only VPInstructions and external 280 // defs are managed by VPTransformState. Other Defs are still created by ILV 281 // and managed in its ValueMap. For those this method currently just 282 // delegates the call to ILV below. 283 if (Data.PerPartOutput.count(Def)) { 284 auto *VecPart = Data.PerPartOutput[Def][Instance.Part]; 285 // TODO: Cache created scalar values. 286 return Builder.CreateExtractElement(VecPart, 287 Builder.getInt32(Instance.Lane)); 288 } 289 290 return Callback.getOrCreateScalarValue(VPValue2Value[Def], Instance); 291 } 292 293 /// Set the generated Value for a given VPValue and a given Part. 294 void set(VPValue *Def, Value *V, unsigned Part) { 295 if (!Data.PerPartOutput.count(Def)) { 296 DataState::PerPartValuesTy Entry(UF); 297 Data.PerPartOutput[Def] = Entry; 298 } 299 Data.PerPartOutput[Def][Part] = V; 300 } 301 302 /// Hold state information used when constructing the CFG of the output IR, 303 /// traversing the VPBasicBlocks and generating corresponding IR BasicBlocks. 304 struct CFGState { 305 /// The previous VPBasicBlock visited. Initially set to null. 306 VPBasicBlock *PrevVPBB = nullptr; 307 308 /// The previous IR BasicBlock created or used. Initially set to the new 309 /// header BasicBlock. 310 BasicBlock *PrevBB = nullptr; 311 312 /// The last IR BasicBlock in the output IR. Set to the new latch 313 /// BasicBlock, used for placing the newly created BasicBlocks. 314 BasicBlock *LastBB = nullptr; 315 316 /// A mapping of each VPBasicBlock to the corresponding BasicBlock. In case 317 /// of replication, maps the BasicBlock of the last replica created. 318 SmallDenseMap<VPBasicBlock *, BasicBlock *> VPBB2IRBB; 319 320 /// Vector of VPBasicBlocks whose terminator instruction needs to be fixed 321 /// up at the end of vector code generation. 322 SmallVector<VPBasicBlock *, 8> VPBBsToFix; 323 324 CFGState() = default; 325 } CFG; 326 327 /// Hold a pointer to LoopInfo to register new basic blocks in the loop. 328 LoopInfo *LI; 329 330 /// Hold a pointer to Dominator Tree to register new basic blocks in the loop. 331 DominatorTree *DT; 332 333 /// Hold a reference to the IRBuilder used to generate output IR code. 334 IRBuilder<> &Builder; 335 336 /// Hold a reference to the Value state information used when generating the 337 /// Values of the output IR. 338 VectorizerValueMap &ValueMap; 339 340 /// Hold a reference to a mapping between VPValues in VPlan and original 341 /// Values they correspond to. 342 VPValue2ValueTy VPValue2Value; 343 344 /// Hold the canonical scalar IV of the vector loop (start=0, step=VF*UF). 345 Value *CanonicalIV = nullptr; 346 347 /// Hold the trip count of the scalar loop. 348 Value *TripCount = nullptr; 349 350 /// Hold a pointer to InnerLoopVectorizer to reuse its IR generation methods. 351 InnerLoopVectorizer *ILV; 352 353 VPCallback &Callback; 354 }; 355 356 /// VPBlockBase is the building block of the Hierarchical Control-Flow Graph. 357 /// A VPBlockBase can be either a VPBasicBlock or a VPRegionBlock. 358 class VPBlockBase { 359 friend class VPBlockUtils; 360 361 const unsigned char SubclassID; ///< Subclass identifier (for isa/dyn_cast). 362 363 /// An optional name for the block. 364 std::string Name; 365 366 /// The immediate VPRegionBlock which this VPBlockBase belongs to, or null if 367 /// it is a topmost VPBlockBase. 368 VPRegionBlock *Parent = nullptr; 369 370 /// List of predecessor blocks. 371 SmallVector<VPBlockBase *, 1> Predecessors; 372 373 /// List of successor blocks. 374 SmallVector<VPBlockBase *, 1> Successors; 375 376 /// Successor selector, null for zero or single successor blocks. 377 VPValue *CondBit = nullptr; 378 379 /// Current block predicate - null if the block does not need a predicate. 380 VPValue *Predicate = nullptr; 381 382 /// VPlan containing the block. Can only be set on the entry block of the 383 /// plan. 384 VPlan *Plan = nullptr; 385 386 /// Add \p Successor as the last successor to this block. 387 void appendSuccessor(VPBlockBase *Successor) { 388 assert(Successor && "Cannot add nullptr successor!"); 389 Successors.push_back(Successor); 390 } 391 392 /// Add \p Predecessor as the last predecessor to this block. 393 void appendPredecessor(VPBlockBase *Predecessor) { 394 assert(Predecessor && "Cannot add nullptr predecessor!"); 395 Predecessors.push_back(Predecessor); 396 } 397 398 /// Remove \p Predecessor from the predecessors of this block. 399 void removePredecessor(VPBlockBase *Predecessor) { 400 auto Pos = std::find(Predecessors.begin(), Predecessors.end(), Predecessor); 401 assert(Pos && "Predecessor does not exist"); 402 Predecessors.erase(Pos); 403 } 404 405 /// Remove \p Successor from the successors of this block. 406 void removeSuccessor(VPBlockBase *Successor) { 407 auto Pos = std::find(Successors.begin(), Successors.end(), Successor); 408 assert(Pos && "Successor does not exist"); 409 Successors.erase(Pos); 410 } 411 412 protected: 413 VPBlockBase(const unsigned char SC, const std::string &N) 414 : SubclassID(SC), Name(N) {} 415 416 public: 417 /// An enumeration for keeping track of the concrete subclass of VPBlockBase 418 /// that are actually instantiated. Values of this enumeration are kept in the 419 /// SubclassID field of the VPBlockBase objects. They are used for concrete 420 /// type identification. 421 using VPBlockTy = enum { VPBasicBlockSC, VPRegionBlockSC }; 422 423 using VPBlocksTy = SmallVectorImpl<VPBlockBase *>; 424 425 virtual ~VPBlockBase() = default; 426 427 const std::string &getName() const { return Name; } 428 429 void setName(const Twine &newName) { Name = newName.str(); } 430 431 /// \return an ID for the concrete type of this object. 432 /// This is used to implement the classof checks. This should not be used 433 /// for any other purpose, as the values may change as LLVM evolves. 434 unsigned getVPBlockID() const { return SubclassID; } 435 436 VPRegionBlock *getParent() { return Parent; } 437 const VPRegionBlock *getParent() const { return Parent; } 438 439 /// \return A pointer to the plan containing the current block. 440 VPlan *getPlan(); 441 const VPlan *getPlan() const; 442 443 /// Sets the pointer of the plan containing the block. The block must be the 444 /// entry block into the VPlan. 445 void setPlan(VPlan *ParentPlan); 446 447 void setParent(VPRegionBlock *P) { Parent = P; } 448 449 /// \return the VPBasicBlock that is the entry of this VPBlockBase, 450 /// recursively, if the latter is a VPRegionBlock. Otherwise, if this 451 /// VPBlockBase is a VPBasicBlock, it is returned. 452 const VPBasicBlock *getEntryBasicBlock() const; 453 VPBasicBlock *getEntryBasicBlock(); 454 455 /// \return the VPBasicBlock that is the exit of this VPBlockBase, 456 /// recursively, if the latter is a VPRegionBlock. Otherwise, if this 457 /// VPBlockBase is a VPBasicBlock, it is returned. 458 const VPBasicBlock *getExitBasicBlock() const; 459 VPBasicBlock *getExitBasicBlock(); 460 461 const VPBlocksTy &getSuccessors() const { return Successors; } 462 VPBlocksTy &getSuccessors() { return Successors; } 463 464 const VPBlocksTy &getPredecessors() const { return Predecessors; } 465 VPBlocksTy &getPredecessors() { return Predecessors; } 466 467 /// \return the successor of this VPBlockBase if it has a single successor. 468 /// Otherwise return a null pointer. 469 VPBlockBase *getSingleSuccessor() const { 470 return (Successors.size() == 1 ? *Successors.begin() : nullptr); 471 } 472 473 /// \return the predecessor of this VPBlockBase if it has a single 474 /// predecessor. Otherwise return a null pointer. 475 VPBlockBase *getSinglePredecessor() const { 476 return (Predecessors.size() == 1 ? *Predecessors.begin() : nullptr); 477 } 478 479 size_t getNumSuccessors() const { return Successors.size(); } 480 size_t getNumPredecessors() const { return Predecessors.size(); } 481 482 /// An Enclosing Block of a block B is any block containing B, including B 483 /// itself. \return the closest enclosing block starting from "this", which 484 /// has successors. \return the root enclosing block if all enclosing blocks 485 /// have no successors. 486 VPBlockBase *getEnclosingBlockWithSuccessors(); 487 488 /// \return the closest enclosing block starting from "this", which has 489 /// predecessors. \return the root enclosing block if all enclosing blocks 490 /// have no predecessors. 491 VPBlockBase *getEnclosingBlockWithPredecessors(); 492 493 /// \return the successors either attached directly to this VPBlockBase or, if 494 /// this VPBlockBase is the exit block of a VPRegionBlock and has no 495 /// successors of its own, search recursively for the first enclosing 496 /// VPRegionBlock that has successors and return them. If no such 497 /// VPRegionBlock exists, return the (empty) successors of the topmost 498 /// VPBlockBase reached. 499 const VPBlocksTy &getHierarchicalSuccessors() { 500 return getEnclosingBlockWithSuccessors()->getSuccessors(); 501 } 502 503 /// \return the hierarchical successor of this VPBlockBase if it has a single 504 /// hierarchical successor. Otherwise return a null pointer. 505 VPBlockBase *getSingleHierarchicalSuccessor() { 506 return getEnclosingBlockWithSuccessors()->getSingleSuccessor(); 507 } 508 509 /// \return the predecessors either attached directly to this VPBlockBase or, 510 /// if this VPBlockBase is the entry block of a VPRegionBlock and has no 511 /// predecessors of its own, search recursively for the first enclosing 512 /// VPRegionBlock that has predecessors and return them. If no such 513 /// VPRegionBlock exists, return the (empty) predecessors of the topmost 514 /// VPBlockBase reached. 515 const VPBlocksTy &getHierarchicalPredecessors() { 516 return getEnclosingBlockWithPredecessors()->getPredecessors(); 517 } 518 519 /// \return the hierarchical predecessor of this VPBlockBase if it has a 520 /// single hierarchical predecessor. Otherwise return a null pointer. 521 VPBlockBase *getSingleHierarchicalPredecessor() { 522 return getEnclosingBlockWithPredecessors()->getSinglePredecessor(); 523 } 524 525 /// \return the condition bit selecting the successor. 526 VPValue *getCondBit() { return CondBit; } 527 528 const VPValue *getCondBit() const { return CondBit; } 529 530 void setCondBit(VPValue *CV) { CondBit = CV; } 531 532 VPValue *getPredicate() { return Predicate; } 533 534 const VPValue *getPredicate() const { return Predicate; } 535 536 void setPredicate(VPValue *Pred) { Predicate = Pred; } 537 538 /// Set a given VPBlockBase \p Successor as the single successor of this 539 /// VPBlockBase. This VPBlockBase is not added as predecessor of \p Successor. 540 /// This VPBlockBase must have no successors. 541 void setOneSuccessor(VPBlockBase *Successor) { 542 assert(Successors.empty() && "Setting one successor when others exist."); 543 appendSuccessor(Successor); 544 } 545 546 /// Set two given VPBlockBases \p IfTrue and \p IfFalse to be the two 547 /// successors of this VPBlockBase. \p Condition is set as the successor 548 /// selector. This VPBlockBase is not added as predecessor of \p IfTrue or \p 549 /// IfFalse. This VPBlockBase must have no successors. 550 void setTwoSuccessors(VPBlockBase *IfTrue, VPBlockBase *IfFalse, 551 VPValue *Condition) { 552 assert(Successors.empty() && "Setting two successors when others exist."); 553 assert(Condition && "Setting two successors without condition!"); 554 CondBit = Condition; 555 appendSuccessor(IfTrue); 556 appendSuccessor(IfFalse); 557 } 558 559 /// Set each VPBasicBlock in \p NewPreds as predecessor of this VPBlockBase. 560 /// This VPBlockBase must have no predecessors. This VPBlockBase is not added 561 /// as successor of any VPBasicBlock in \p NewPreds. 562 void setPredecessors(ArrayRef<VPBlockBase *> NewPreds) { 563 assert(Predecessors.empty() && "Block predecessors already set."); 564 for (auto *Pred : NewPreds) 565 appendPredecessor(Pred); 566 } 567 568 /// Remove all the predecessor of this block. 569 void clearPredecessors() { Predecessors.clear(); } 570 571 /// Remove all the successors of this block and set to null its condition bit 572 void clearSuccessors() { 573 Successors.clear(); 574 CondBit = nullptr; 575 } 576 577 /// The method which generates the output IR that correspond to this 578 /// VPBlockBase, thereby "executing" the VPlan. 579 virtual void execute(struct VPTransformState *State) = 0; 580 581 /// Delete all blocks reachable from a given VPBlockBase, inclusive. 582 static void deleteCFG(VPBlockBase *Entry); 583 584 void printAsOperand(raw_ostream &OS, bool PrintType) const { 585 OS << getName(); 586 } 587 588 void print(raw_ostream &OS) const { 589 // TODO: Only printing VPBB name for now since we only have dot printing 590 // support for VPInstructions/Recipes. 591 printAsOperand(OS, false); 592 } 593 594 /// Return true if it is legal to hoist instructions into this block. 595 bool isLegalToHoistInto() { 596 // There are currently no constraints that prevent an instruction to be 597 // hoisted into a VPBlockBase. 598 return true; 599 } 600 }; 601 602 /// VPRecipeBase is a base class modeling a sequence of one or more output IR 603 /// instructions. 604 class VPRecipeBase : public ilist_node_with_parent<VPRecipeBase, VPBasicBlock> { 605 friend VPBasicBlock; 606 friend class VPBlockUtils; 607 608 const unsigned char SubclassID; ///< Subclass identifier (for isa/dyn_cast). 609 610 /// Each VPRecipe belongs to a single VPBasicBlock. 611 VPBasicBlock *Parent = nullptr; 612 613 public: 614 /// An enumeration for keeping track of the concrete subclass of VPRecipeBase 615 /// that is actually instantiated. Values of this enumeration are kept in the 616 /// SubclassID field of the VPRecipeBase objects. They are used for concrete 617 /// type identification. 618 using VPRecipeTy = enum { 619 VPBlendSC, 620 VPBranchOnMaskSC, 621 VPInstructionSC, 622 VPInterleaveSC, 623 VPPredInstPHISC, 624 VPReductionSC, 625 VPReplicateSC, 626 VPWidenCallSC, 627 VPWidenCanonicalIVSC, 628 VPWidenGEPSC, 629 VPWidenIntOrFpInductionSC, 630 VPWidenMemoryInstructionSC, 631 VPWidenPHISC, 632 VPWidenSC, 633 VPWidenSelectSC 634 }; 635 636 VPRecipeBase(const unsigned char SC) : SubclassID(SC) {} 637 virtual ~VPRecipeBase() = default; 638 639 /// \return an ID for the concrete type of this object. 640 /// This is used to implement the classof checks. This should not be used 641 /// for any other purpose, as the values may change as LLVM evolves. 642 unsigned getVPRecipeID() const { return SubclassID; } 643 644 /// \return the VPBasicBlock which this VPRecipe belongs to. 645 VPBasicBlock *getParent() { return Parent; } 646 const VPBasicBlock *getParent() const { return Parent; } 647 648 /// The method which generates the output IR instructions that correspond to 649 /// this VPRecipe, thereby "executing" the VPlan. 650 virtual void execute(struct VPTransformState &State) = 0; 651 652 /// Each recipe prints itself. 653 virtual void print(raw_ostream &O, const Twine &Indent, 654 VPSlotTracker &SlotTracker) const = 0; 655 656 /// Dump the recipe to stderr (for debugging). 657 void dump() const; 658 659 /// Insert an unlinked recipe into a basic block immediately before 660 /// the specified recipe. 661 void insertBefore(VPRecipeBase *InsertPos); 662 663 /// Insert an unlinked Recipe into a basic block immediately after 664 /// the specified Recipe. 665 void insertAfter(VPRecipeBase *InsertPos); 666 667 /// Unlink this recipe from its current VPBasicBlock and insert it into 668 /// the VPBasicBlock that MovePos lives in, right after MovePos. 669 void moveAfter(VPRecipeBase *MovePos); 670 671 /// This method unlinks 'this' from the containing basic block, but does not 672 /// delete it. 673 void removeFromParent(); 674 675 /// This method unlinks 'this' from the containing basic block and deletes it. 676 /// 677 /// \returns an iterator pointing to the element after the erased one 678 iplist<VPRecipeBase>::iterator eraseFromParent(); 679 }; 680 681 /// This is a concrete Recipe that models a single VPlan-level instruction. 682 /// While as any Recipe it may generate a sequence of IR instructions when 683 /// executed, these instructions would always form a single-def expression as 684 /// the VPInstruction is also a single def-use vertex. 685 class VPInstruction : public VPUser, public VPRecipeBase { 686 friend class VPlanSlp; 687 688 public: 689 /// VPlan opcodes, extending LLVM IR with idiomatics instructions. 690 enum { 691 Not = Instruction::OtherOpsEnd + 1, 692 ICmpULE, 693 SLPLoad, 694 SLPStore, 695 ActiveLaneMask, 696 }; 697 698 private: 699 typedef unsigned char OpcodeTy; 700 OpcodeTy Opcode; 701 702 /// Utility method serving execute(): generates a single instance of the 703 /// modeled instruction. 704 void generateInstruction(VPTransformState &State, unsigned Part); 705 706 protected: 707 Instruction *getUnderlyingInstr() { 708 return cast_or_null<Instruction>(getUnderlyingValue()); 709 } 710 711 void setUnderlyingInstr(Instruction *I) { setUnderlyingValue(I); } 712 713 public: 714 VPInstruction(unsigned Opcode, ArrayRef<VPValue *> Operands) 715 : VPUser(VPValue::VPInstructionSC, Operands), 716 VPRecipeBase(VPRecipeBase::VPInstructionSC), Opcode(Opcode) {} 717 718 VPInstruction(unsigned Opcode, std::initializer_list<VPValue *> Operands) 719 : VPInstruction(Opcode, ArrayRef<VPValue *>(Operands)) {} 720 721 /// Method to support type inquiry through isa, cast, and dyn_cast. 722 static inline bool classof(const VPValue *V) { 723 return V->getVPValueID() == VPValue::VPInstructionSC; 724 } 725 726 VPInstruction *clone() const { 727 SmallVector<VPValue *, 2> Operands(operands()); 728 return new VPInstruction(Opcode, Operands); 729 } 730 731 /// Method to support type inquiry through isa, cast, and dyn_cast. 732 static inline bool classof(const VPRecipeBase *R) { 733 return R->getVPRecipeID() == VPRecipeBase::VPInstructionSC; 734 } 735 736 unsigned getOpcode() const { return Opcode; } 737 738 /// Generate the instruction. 739 /// TODO: We currently execute only per-part unless a specific instance is 740 /// provided. 741 void execute(VPTransformState &State) override; 742 743 /// Print the Recipe. 744 void print(raw_ostream &O, const Twine &Indent, 745 VPSlotTracker &SlotTracker) const override; 746 747 /// Print the VPInstruction. 748 void print(raw_ostream &O) const; 749 void print(raw_ostream &O, VPSlotTracker &SlotTracker) const; 750 751 /// Return true if this instruction may modify memory. 752 bool mayWriteToMemory() const { 753 // TODO: we can use attributes of the called function to rule out memory 754 // modifications. 755 return Opcode == Instruction::Store || Opcode == Instruction::Call || 756 Opcode == Instruction::Invoke || Opcode == SLPStore; 757 } 758 759 bool hasResult() const { 760 // CallInst may or may not have a result, depending on the called function. 761 // Conservatively return calls have results for now. 762 switch (getOpcode()) { 763 case Instruction::Ret: 764 case Instruction::Br: 765 case Instruction::Store: 766 case Instruction::Switch: 767 case Instruction::IndirectBr: 768 case Instruction::Resume: 769 case Instruction::CatchRet: 770 case Instruction::Unreachable: 771 case Instruction::Fence: 772 case Instruction::AtomicRMW: 773 return false; 774 default: 775 return true; 776 } 777 } 778 }; 779 780 /// VPWidenRecipe is a recipe for producing a copy of vector type its 781 /// ingredient. This recipe covers most of the traditional vectorization cases 782 /// where each ingredient transforms into a vectorized version of itself. 783 class VPWidenRecipe : public VPRecipeBase { 784 /// Hold the instruction to be widened. 785 Instruction &Ingredient; 786 787 /// Hold VPValues for the operands of the ingredient. 788 VPUser User; 789 790 public: 791 template <typename IterT> 792 VPWidenRecipe(Instruction &I, iterator_range<IterT> Operands) 793 : VPRecipeBase(VPWidenSC), Ingredient(I), User(Operands) {} 794 795 ~VPWidenRecipe() override = default; 796 797 /// Method to support type inquiry through isa, cast, and dyn_cast. 798 static inline bool classof(const VPRecipeBase *V) { 799 return V->getVPRecipeID() == VPRecipeBase::VPWidenSC; 800 } 801 802 /// Produce widened copies of all Ingredients. 803 void execute(VPTransformState &State) override; 804 805 /// Print the recipe. 806 void print(raw_ostream &O, const Twine &Indent, 807 VPSlotTracker &SlotTracker) const override; 808 }; 809 810 /// A recipe for widening Call instructions. 811 class VPWidenCallRecipe : public VPRecipeBase { 812 /// Hold the call to be widened. 813 CallInst &Ingredient; 814 815 /// Hold VPValues for the arguments of the call. 816 VPUser User; 817 818 public: 819 template <typename IterT> 820 VPWidenCallRecipe(CallInst &I, iterator_range<IterT> CallArguments) 821 : VPRecipeBase(VPWidenCallSC), Ingredient(I), User(CallArguments) {} 822 823 ~VPWidenCallRecipe() override = default; 824 825 /// Method to support type inquiry through isa, cast, and dyn_cast. 826 static inline bool classof(const VPRecipeBase *V) { 827 return V->getVPRecipeID() == VPRecipeBase::VPWidenCallSC; 828 } 829 830 /// Produce a widened version of the call instruction. 831 void execute(VPTransformState &State) override; 832 833 /// Print the recipe. 834 void print(raw_ostream &O, const Twine &Indent, 835 VPSlotTracker &SlotTracker) const override; 836 }; 837 838 /// A recipe for widening select instructions. 839 class VPWidenSelectRecipe : public VPRecipeBase { 840 private: 841 /// Hold the select to be widened. 842 SelectInst &Ingredient; 843 844 /// Hold VPValues for the operands of the select. 845 VPUser User; 846 847 /// Is the condition of the select loop invariant? 848 bool InvariantCond; 849 850 public: 851 template <typename IterT> 852 VPWidenSelectRecipe(SelectInst &I, iterator_range<IterT> Operands, 853 bool InvariantCond) 854 : VPRecipeBase(VPWidenSelectSC), Ingredient(I), User(Operands), 855 InvariantCond(InvariantCond) {} 856 857 ~VPWidenSelectRecipe() override = default; 858 859 /// Method to support type inquiry through isa, cast, and dyn_cast. 860 static inline bool classof(const VPRecipeBase *V) { 861 return V->getVPRecipeID() == VPRecipeBase::VPWidenSelectSC; 862 } 863 864 /// Produce a widened version of the select instruction. 865 void execute(VPTransformState &State) override; 866 867 /// Print the recipe. 868 void print(raw_ostream &O, const Twine &Indent, 869 VPSlotTracker &SlotTracker) const override; 870 }; 871 872 /// A recipe for handling GEP instructions. 873 class VPWidenGEPRecipe : public VPRecipeBase { 874 GetElementPtrInst *GEP; 875 876 /// Hold VPValues for the base and indices of the GEP. 877 VPUser User; 878 879 bool IsPtrLoopInvariant; 880 SmallBitVector IsIndexLoopInvariant; 881 882 public: 883 template <typename IterT> 884 VPWidenGEPRecipe(GetElementPtrInst *GEP, iterator_range<IterT> Operands, 885 Loop *OrigLoop) 886 : VPRecipeBase(VPWidenGEPSC), GEP(GEP), User(Operands), 887 IsIndexLoopInvariant(GEP->getNumIndices(), false) { 888 IsPtrLoopInvariant = OrigLoop->isLoopInvariant(GEP->getPointerOperand()); 889 for (auto Index : enumerate(GEP->indices())) 890 IsIndexLoopInvariant[Index.index()] = 891 OrigLoop->isLoopInvariant(Index.value().get()); 892 } 893 ~VPWidenGEPRecipe() override = default; 894 895 /// Method to support type inquiry through isa, cast, and dyn_cast. 896 static inline bool classof(const VPRecipeBase *V) { 897 return V->getVPRecipeID() == VPRecipeBase::VPWidenGEPSC; 898 } 899 900 /// Generate the gep nodes. 901 void execute(VPTransformState &State) override; 902 903 /// Print the recipe. 904 void print(raw_ostream &O, const Twine &Indent, 905 VPSlotTracker &SlotTracker) const override; 906 }; 907 908 /// A recipe for handling phi nodes of integer and floating-point inductions, 909 /// producing their vector and scalar values. 910 class VPWidenIntOrFpInductionRecipe : public VPRecipeBase { 911 PHINode *IV; 912 TruncInst *Trunc; 913 914 public: 915 VPWidenIntOrFpInductionRecipe(PHINode *IV, TruncInst *Trunc = nullptr) 916 : VPRecipeBase(VPWidenIntOrFpInductionSC), IV(IV), Trunc(Trunc) {} 917 ~VPWidenIntOrFpInductionRecipe() override = default; 918 919 /// Method to support type inquiry through isa, cast, and dyn_cast. 920 static inline bool classof(const VPRecipeBase *V) { 921 return V->getVPRecipeID() == VPRecipeBase::VPWidenIntOrFpInductionSC; 922 } 923 924 /// Generate the vectorized and scalarized versions of the phi node as 925 /// needed by their users. 926 void execute(VPTransformState &State) override; 927 928 /// Print the recipe. 929 void print(raw_ostream &O, const Twine &Indent, 930 VPSlotTracker &SlotTracker) const override; 931 }; 932 933 /// A recipe for handling all phi nodes except for integer and FP inductions. 934 class VPWidenPHIRecipe : public VPRecipeBase { 935 PHINode *Phi; 936 937 public: 938 VPWidenPHIRecipe(PHINode *Phi) : VPRecipeBase(VPWidenPHISC), Phi(Phi) {} 939 ~VPWidenPHIRecipe() override = default; 940 941 /// Method to support type inquiry through isa, cast, and dyn_cast. 942 static inline bool classof(const VPRecipeBase *V) { 943 return V->getVPRecipeID() == VPRecipeBase::VPWidenPHISC; 944 } 945 946 /// Generate the phi/select nodes. 947 void execute(VPTransformState &State) override; 948 949 /// Print the recipe. 950 void print(raw_ostream &O, const Twine &Indent, 951 VPSlotTracker &SlotTracker) const override; 952 }; 953 954 /// A recipe for vectorizing a phi-node as a sequence of mask-based select 955 /// instructions. 956 class VPBlendRecipe : public VPRecipeBase { 957 PHINode *Phi; 958 959 /// The blend operation is a User of the incoming values and of their 960 /// respective masks, ordered [I0, M0, I1, M1, ...]. Note that a single value 961 /// might be incoming with a full mask for which there is no VPValue. 962 VPUser User; 963 964 public: 965 VPBlendRecipe(PHINode *Phi, ArrayRef<VPValue *> Operands) 966 : VPRecipeBase(VPBlendSC), Phi(Phi), User(Operands) { 967 assert(Operands.size() > 0 && 968 ((Operands.size() == 1) || (Operands.size() % 2 == 0)) && 969 "Expected either a single incoming value or a positive even number " 970 "of operands"); 971 } 972 973 /// Method to support type inquiry through isa, cast, and dyn_cast. 974 static inline bool classof(const VPRecipeBase *V) { 975 return V->getVPRecipeID() == VPRecipeBase::VPBlendSC; 976 } 977 978 /// Return the number of incoming values, taking into account that a single 979 /// incoming value has no mask. 980 unsigned getNumIncomingValues() const { 981 return (User.getNumOperands() + 1) / 2; 982 } 983 984 /// Return incoming value number \p Idx. 985 VPValue *getIncomingValue(unsigned Idx) const { 986 return User.getOperand(Idx * 2); 987 } 988 989 /// Return mask number \p Idx. 990 VPValue *getMask(unsigned Idx) const { return User.getOperand(Idx * 2 + 1); } 991 992 /// Generate the phi/select nodes. 993 void execute(VPTransformState &State) override; 994 995 /// Print the recipe. 996 void print(raw_ostream &O, const Twine &Indent, 997 VPSlotTracker &SlotTracker) const override; 998 }; 999 1000 /// VPInterleaveRecipe is a recipe for transforming an interleave group of load 1001 /// or stores into one wide load/store and shuffles. 1002 class VPInterleaveRecipe : public VPRecipeBase { 1003 const InterleaveGroup<Instruction> *IG; 1004 VPUser User; 1005 1006 public: 1007 VPInterleaveRecipe(const InterleaveGroup<Instruction> *IG, VPValue *Addr, 1008 VPValue *Mask) 1009 : VPRecipeBase(VPInterleaveSC), IG(IG), User({Addr}) { 1010 if (Mask) 1011 User.addOperand(Mask); 1012 } 1013 ~VPInterleaveRecipe() override = default; 1014 1015 /// Method to support type inquiry through isa, cast, and dyn_cast. 1016 static inline bool classof(const VPRecipeBase *V) { 1017 return V->getVPRecipeID() == VPRecipeBase::VPInterleaveSC; 1018 } 1019 1020 /// Return the address accessed by this recipe. 1021 VPValue *getAddr() const { 1022 return User.getOperand(0); // Address is the 1st, mandatory operand. 1023 } 1024 1025 /// Return the mask used by this recipe. Note that a full mask is represented 1026 /// by a nullptr. 1027 VPValue *getMask() const { 1028 // Mask is optional and therefore the last, currently 2nd operand. 1029 return User.getNumOperands() == 2 ? User.getOperand(1) : nullptr; 1030 } 1031 1032 /// Generate the wide load or store, and shuffles. 1033 void execute(VPTransformState &State) override; 1034 1035 /// Print the recipe. 1036 void print(raw_ostream &O, const Twine &Indent, 1037 VPSlotTracker &SlotTracker) const override; 1038 1039 const InterleaveGroup<Instruction> *getInterleaveGroup() { return IG; } 1040 }; 1041 1042 /// A recipe to represent inloop reduction operations, performing a reduction on 1043 /// a vector operand into a scalar value, and adding the result to a chain. 1044 class VPReductionRecipe : public VPRecipeBase { 1045 /// The recurrence decriptor for the reduction in question. 1046 RecurrenceDescriptor *RdxDesc; 1047 /// The original instruction being converted to a reduction. 1048 Instruction *I; 1049 /// The VPValue of the vector value to be reduced. 1050 VPValue *VecOp; 1051 /// The VPValue of the scalar Chain being accumulated. 1052 VPValue *ChainOp; 1053 /// Fast math flags to use for the resulting reduction operation. 1054 bool NoNaN; 1055 /// Pointer to the TTI, needed to create the target reduction 1056 const TargetTransformInfo *TTI; 1057 1058 public: 1059 VPReductionRecipe(RecurrenceDescriptor *R, Instruction *I, VPValue *ChainOp, 1060 VPValue *VecOp, bool NoNaN, const TargetTransformInfo *TTI) 1061 : VPRecipeBase(VPReductionSC), RdxDesc(R), I(I), VecOp(VecOp), 1062 ChainOp(ChainOp), NoNaN(NoNaN), TTI(TTI) {} 1063 1064 ~VPReductionRecipe() override = default; 1065 1066 /// Method to support type inquiry through isa, cast, and dyn_cast. 1067 static inline bool classof(const VPRecipeBase *V) { 1068 return V->getVPRecipeID() == VPRecipeBase::VPReductionSC; 1069 } 1070 1071 /// Generate the reduction in the loop 1072 void execute(VPTransformState &State) override; 1073 1074 /// Print the recipe. 1075 void print(raw_ostream &O, const Twine &Indent, 1076 VPSlotTracker &SlotTracker) const override; 1077 }; 1078 1079 /// VPReplicateRecipe replicates a given instruction producing multiple scalar 1080 /// copies of the original scalar type, one per lane, instead of producing a 1081 /// single copy of widened type for all lanes. If the instruction is known to be 1082 /// uniform only one copy, per lane zero, will be generated. 1083 class VPReplicateRecipe : public VPRecipeBase { 1084 /// The instruction being replicated. 1085 Instruction *Ingredient; 1086 1087 /// Hold VPValues for the operands of the ingredient. 1088 VPUser User; 1089 1090 /// Indicator if only a single replica per lane is needed. 1091 bool IsUniform; 1092 1093 /// Indicator if the replicas are also predicated. 1094 bool IsPredicated; 1095 1096 /// Indicator if the scalar values should also be packed into a vector. 1097 bool AlsoPack; 1098 1099 public: 1100 template <typename IterT> 1101 VPReplicateRecipe(Instruction *I, iterator_range<IterT> Operands, 1102 bool IsUniform, bool IsPredicated = false) 1103 : VPRecipeBase(VPReplicateSC), Ingredient(I), User(Operands), 1104 IsUniform(IsUniform), IsPredicated(IsPredicated) { 1105 // Retain the previous behavior of predicateInstructions(), where an 1106 // insert-element of a predicated instruction got hoisted into the 1107 // predicated basic block iff it was its only user. This is achieved by 1108 // having predicated instructions also pack their values into a vector by 1109 // default unless they have a replicated user which uses their scalar value. 1110 AlsoPack = IsPredicated && !I->use_empty(); 1111 } 1112 1113 ~VPReplicateRecipe() override = default; 1114 1115 /// Method to support type inquiry through isa, cast, and dyn_cast. 1116 static inline bool classof(const VPRecipeBase *V) { 1117 return V->getVPRecipeID() == VPRecipeBase::VPReplicateSC; 1118 } 1119 1120 /// Generate replicas of the desired Ingredient. Replicas will be generated 1121 /// for all parts and lanes unless a specific part and lane are specified in 1122 /// the \p State. 1123 void execute(VPTransformState &State) override; 1124 1125 void setAlsoPack(bool Pack) { AlsoPack = Pack; } 1126 1127 /// Print the recipe. 1128 void print(raw_ostream &O, const Twine &Indent, 1129 VPSlotTracker &SlotTracker) const override; 1130 }; 1131 1132 /// A recipe for generating conditional branches on the bits of a mask. 1133 class VPBranchOnMaskRecipe : public VPRecipeBase { 1134 VPUser User; 1135 1136 public: 1137 VPBranchOnMaskRecipe(VPValue *BlockInMask) : VPRecipeBase(VPBranchOnMaskSC) { 1138 if (BlockInMask) // nullptr means all-one mask. 1139 User.addOperand(BlockInMask); 1140 } 1141 1142 /// Method to support type inquiry through isa, cast, and dyn_cast. 1143 static inline bool classof(const VPRecipeBase *V) { 1144 return V->getVPRecipeID() == VPRecipeBase::VPBranchOnMaskSC; 1145 } 1146 1147 /// Generate the extraction of the appropriate bit from the block mask and the 1148 /// conditional branch. 1149 void execute(VPTransformState &State) override; 1150 1151 /// Print the recipe. 1152 void print(raw_ostream &O, const Twine &Indent, 1153 VPSlotTracker &SlotTracker) const override { 1154 O << " +\n" << Indent << "\"BRANCH-ON-MASK "; 1155 if (VPValue *Mask = getMask()) 1156 Mask->print(O, SlotTracker); 1157 else 1158 O << " All-One"; 1159 O << "\\l\""; 1160 } 1161 1162 /// Return the mask used by this recipe. Note that a full mask is represented 1163 /// by a nullptr. 1164 VPValue *getMask() const { 1165 assert(User.getNumOperands() <= 1 && "should have either 0 or 1 operands"); 1166 // Mask is optional. 1167 return User.getNumOperands() == 1 ? User.getOperand(0) : nullptr; 1168 } 1169 }; 1170 1171 /// VPPredInstPHIRecipe is a recipe for generating the phi nodes needed when 1172 /// control converges back from a Branch-on-Mask. The phi nodes are needed in 1173 /// order to merge values that are set under such a branch and feed their uses. 1174 /// The phi nodes can be scalar or vector depending on the users of the value. 1175 /// This recipe works in concert with VPBranchOnMaskRecipe. 1176 class VPPredInstPHIRecipe : public VPRecipeBase { 1177 Instruction *PredInst; 1178 1179 public: 1180 /// Construct a VPPredInstPHIRecipe given \p PredInst whose value needs a phi 1181 /// nodes after merging back from a Branch-on-Mask. 1182 VPPredInstPHIRecipe(Instruction *PredInst) 1183 : VPRecipeBase(VPPredInstPHISC), PredInst(PredInst) {} 1184 ~VPPredInstPHIRecipe() override = default; 1185 1186 /// Method to support type inquiry through isa, cast, and dyn_cast. 1187 static inline bool classof(const VPRecipeBase *V) { 1188 return V->getVPRecipeID() == VPRecipeBase::VPPredInstPHISC; 1189 } 1190 1191 /// Generates phi nodes for live-outs as needed to retain SSA form. 1192 void execute(VPTransformState &State) override; 1193 1194 /// Print the recipe. 1195 void print(raw_ostream &O, const Twine &Indent, 1196 VPSlotTracker &SlotTracker) const override; 1197 }; 1198 1199 /// A Recipe for widening load/store operations. 1200 /// The recipe uses the following VPValues: 1201 /// - For load: Address, optional mask 1202 /// - For store: Address, stored value, optional mask 1203 /// TODO: We currently execute only per-part unless a specific instance is 1204 /// provided. 1205 class VPWidenMemoryInstructionRecipe : public VPRecipeBase { 1206 Instruction &Instr; 1207 VPUser User; 1208 1209 void setMask(VPValue *Mask) { 1210 if (!Mask) 1211 return; 1212 User.addOperand(Mask); 1213 } 1214 1215 bool isMasked() const { 1216 return (isa<LoadInst>(Instr) && User.getNumOperands() == 2) || 1217 (isa<StoreInst>(Instr) && User.getNumOperands() == 3); 1218 } 1219 1220 public: 1221 VPWidenMemoryInstructionRecipe(LoadInst &Load, VPValue *Addr, VPValue *Mask) 1222 : VPRecipeBase(VPWidenMemoryInstructionSC), Instr(Load), User({Addr}) { 1223 setMask(Mask); 1224 } 1225 1226 VPWidenMemoryInstructionRecipe(StoreInst &Store, VPValue *Addr, 1227 VPValue *StoredValue, VPValue *Mask) 1228 : VPRecipeBase(VPWidenMemoryInstructionSC), Instr(Store), 1229 User({Addr, StoredValue}) { 1230 setMask(Mask); 1231 } 1232 1233 /// Method to support type inquiry through isa, cast, and dyn_cast. 1234 static inline bool classof(const VPRecipeBase *V) { 1235 return V->getVPRecipeID() == VPRecipeBase::VPWidenMemoryInstructionSC; 1236 } 1237 1238 /// Return the address accessed by this recipe. 1239 VPValue *getAddr() const { 1240 return User.getOperand(0); // Address is the 1st, mandatory operand. 1241 } 1242 1243 /// Return the mask used by this recipe. Note that a full mask is represented 1244 /// by a nullptr. 1245 VPValue *getMask() const { 1246 // Mask is optional and therefore the last operand. 1247 return isMasked() ? User.getOperand(User.getNumOperands() - 1) : nullptr; 1248 } 1249 1250 /// Return the address accessed by this recipe. 1251 VPValue *getStoredValue() const { 1252 assert(isa<StoreInst>(Instr) && 1253 "Stored value only available for store instructions"); 1254 return User.getOperand(1); // Stored value is the 2nd, mandatory operand. 1255 } 1256 1257 /// Generate the wide load/store. 1258 void execute(VPTransformState &State) override; 1259 1260 /// Print the recipe. 1261 void print(raw_ostream &O, const Twine &Indent, 1262 VPSlotTracker &SlotTracker) const override; 1263 }; 1264 1265 /// A Recipe for widening the canonical induction variable of the vector loop. 1266 class VPWidenCanonicalIVRecipe : public VPRecipeBase { 1267 /// A VPValue representing the canonical vector IV. 1268 VPValue Val; 1269 1270 public: 1271 VPWidenCanonicalIVRecipe() : VPRecipeBase(VPWidenCanonicalIVSC) {} 1272 ~VPWidenCanonicalIVRecipe() override = default; 1273 1274 /// Return the VPValue representing the canonical vector induction variable of 1275 /// the vector loop. 1276 const VPValue *getVPValue() const { return &Val; } 1277 VPValue *getVPValue() { return &Val; } 1278 1279 /// Method to support type inquiry through isa, cast, and dyn_cast. 1280 static inline bool classof(const VPRecipeBase *V) { 1281 return V->getVPRecipeID() == VPRecipeBase::VPWidenCanonicalIVSC; 1282 } 1283 1284 /// Generate a canonical vector induction variable of the vector loop, with 1285 /// start = {<Part*VF, Part*VF+1, ..., Part*VF+VF-1> for 0 <= Part < UF}, and 1286 /// step = <VF*UF, VF*UF, ..., VF*UF>. 1287 void execute(VPTransformState &State) override; 1288 1289 /// Print the recipe. 1290 void print(raw_ostream &O, const Twine &Indent, 1291 VPSlotTracker &SlotTracker) const override; 1292 }; 1293 1294 /// VPBasicBlock serves as the leaf of the Hierarchical Control-Flow Graph. It 1295 /// holds a sequence of zero or more VPRecipe's each representing a sequence of 1296 /// output IR instructions. 1297 class VPBasicBlock : public VPBlockBase { 1298 public: 1299 using RecipeListTy = iplist<VPRecipeBase>; 1300 1301 private: 1302 /// The VPRecipes held in the order of output instructions to generate. 1303 RecipeListTy Recipes; 1304 1305 public: 1306 VPBasicBlock(const Twine &Name = "", VPRecipeBase *Recipe = nullptr) 1307 : VPBlockBase(VPBasicBlockSC, Name.str()) { 1308 if (Recipe) 1309 appendRecipe(Recipe); 1310 } 1311 1312 ~VPBasicBlock() override { Recipes.clear(); } 1313 1314 /// Instruction iterators... 1315 using iterator = RecipeListTy::iterator; 1316 using const_iterator = RecipeListTy::const_iterator; 1317 using reverse_iterator = RecipeListTy::reverse_iterator; 1318 using const_reverse_iterator = RecipeListTy::const_reverse_iterator; 1319 1320 //===--------------------------------------------------------------------===// 1321 /// Recipe iterator methods 1322 /// 1323 inline iterator begin() { return Recipes.begin(); } 1324 inline const_iterator begin() const { return Recipes.begin(); } 1325 inline iterator end() { return Recipes.end(); } 1326 inline const_iterator end() const { return Recipes.end(); } 1327 1328 inline reverse_iterator rbegin() { return Recipes.rbegin(); } 1329 inline const_reverse_iterator rbegin() const { return Recipes.rbegin(); } 1330 inline reverse_iterator rend() { return Recipes.rend(); } 1331 inline const_reverse_iterator rend() const { return Recipes.rend(); } 1332 1333 inline size_t size() const { return Recipes.size(); } 1334 inline bool empty() const { return Recipes.empty(); } 1335 inline const VPRecipeBase &front() const { return Recipes.front(); } 1336 inline VPRecipeBase &front() { return Recipes.front(); } 1337 inline const VPRecipeBase &back() const { return Recipes.back(); } 1338 inline VPRecipeBase &back() { return Recipes.back(); } 1339 1340 /// Returns a reference to the list of recipes. 1341 RecipeListTy &getRecipeList() { return Recipes; } 1342 1343 /// Returns a pointer to a member of the recipe list. 1344 static RecipeListTy VPBasicBlock::*getSublistAccess(VPRecipeBase *) { 1345 return &VPBasicBlock::Recipes; 1346 } 1347 1348 /// Method to support type inquiry through isa, cast, and dyn_cast. 1349 static inline bool classof(const VPBlockBase *V) { 1350 return V->getVPBlockID() == VPBlockBase::VPBasicBlockSC; 1351 } 1352 1353 void insert(VPRecipeBase *Recipe, iterator InsertPt) { 1354 assert(Recipe && "No recipe to append."); 1355 assert(!Recipe->Parent && "Recipe already in VPlan"); 1356 Recipe->Parent = this; 1357 Recipes.insert(InsertPt, Recipe); 1358 } 1359 1360 /// Augment the existing recipes of a VPBasicBlock with an additional 1361 /// \p Recipe as the last recipe. 1362 void appendRecipe(VPRecipeBase *Recipe) { insert(Recipe, end()); } 1363 1364 /// The method which generates the output IR instructions that correspond to 1365 /// this VPBasicBlock, thereby "executing" the VPlan. 1366 void execute(struct VPTransformState *State) override; 1367 1368 private: 1369 /// Create an IR BasicBlock to hold the output instructions generated by this 1370 /// VPBasicBlock, and return it. Update the CFGState accordingly. 1371 BasicBlock *createEmptyBasicBlock(VPTransformState::CFGState &CFG); 1372 }; 1373 1374 /// VPRegionBlock represents a collection of VPBasicBlocks and VPRegionBlocks 1375 /// which form a Single-Entry-Single-Exit subgraph of the output IR CFG. 1376 /// A VPRegionBlock may indicate that its contents are to be replicated several 1377 /// times. This is designed to support predicated scalarization, in which a 1378 /// scalar if-then code structure needs to be generated VF * UF times. Having 1379 /// this replication indicator helps to keep a single model for multiple 1380 /// candidate VF's. The actual replication takes place only once the desired VF 1381 /// and UF have been determined. 1382 class VPRegionBlock : public VPBlockBase { 1383 /// Hold the Single Entry of the SESE region modelled by the VPRegionBlock. 1384 VPBlockBase *Entry; 1385 1386 /// Hold the Single Exit of the SESE region modelled by the VPRegionBlock. 1387 VPBlockBase *Exit; 1388 1389 /// An indicator whether this region is to generate multiple replicated 1390 /// instances of output IR corresponding to its VPBlockBases. 1391 bool IsReplicator; 1392 1393 public: 1394 VPRegionBlock(VPBlockBase *Entry, VPBlockBase *Exit, 1395 const std::string &Name = "", bool IsReplicator = false) 1396 : VPBlockBase(VPRegionBlockSC, Name), Entry(Entry), Exit(Exit), 1397 IsReplicator(IsReplicator) { 1398 assert(Entry->getPredecessors().empty() && "Entry block has predecessors."); 1399 assert(Exit->getSuccessors().empty() && "Exit block has successors."); 1400 Entry->setParent(this); 1401 Exit->setParent(this); 1402 } 1403 VPRegionBlock(const std::string &Name = "", bool IsReplicator = false) 1404 : VPBlockBase(VPRegionBlockSC, Name), Entry(nullptr), Exit(nullptr), 1405 IsReplicator(IsReplicator) {} 1406 1407 ~VPRegionBlock() override { 1408 if (Entry) 1409 deleteCFG(Entry); 1410 } 1411 1412 /// Method to support type inquiry through isa, cast, and dyn_cast. 1413 static inline bool classof(const VPBlockBase *V) { 1414 return V->getVPBlockID() == VPBlockBase::VPRegionBlockSC; 1415 } 1416 1417 const VPBlockBase *getEntry() const { return Entry; } 1418 VPBlockBase *getEntry() { return Entry; } 1419 1420 /// Set \p EntryBlock as the entry VPBlockBase of this VPRegionBlock. \p 1421 /// EntryBlock must have no predecessors. 1422 void setEntry(VPBlockBase *EntryBlock) { 1423 assert(EntryBlock->getPredecessors().empty() && 1424 "Entry block cannot have predecessors."); 1425 Entry = EntryBlock; 1426 EntryBlock->setParent(this); 1427 } 1428 1429 // FIXME: DominatorTreeBase is doing 'A->getParent()->front()'. 'front' is a 1430 // specific interface of llvm::Function, instead of using 1431 // GraphTraints::getEntryNode. We should add a new template parameter to 1432 // DominatorTreeBase representing the Graph type. 1433 VPBlockBase &front() const { return *Entry; } 1434 1435 const VPBlockBase *getExit() const { return Exit; } 1436 VPBlockBase *getExit() { return Exit; } 1437 1438 /// Set \p ExitBlock as the exit VPBlockBase of this VPRegionBlock. \p 1439 /// ExitBlock must have no successors. 1440 void setExit(VPBlockBase *ExitBlock) { 1441 assert(ExitBlock->getSuccessors().empty() && 1442 "Exit block cannot have successors."); 1443 Exit = ExitBlock; 1444 ExitBlock->setParent(this); 1445 } 1446 1447 /// An indicator whether this region is to generate multiple replicated 1448 /// instances of output IR corresponding to its VPBlockBases. 1449 bool isReplicator() const { return IsReplicator; } 1450 1451 /// The method which generates the output IR instructions that correspond to 1452 /// this VPRegionBlock, thereby "executing" the VPlan. 1453 void execute(struct VPTransformState *State) override; 1454 }; 1455 1456 //===----------------------------------------------------------------------===// 1457 // GraphTraits specializations for VPlan Hierarchical Control-Flow Graphs // 1458 //===----------------------------------------------------------------------===// 1459 1460 // The following set of template specializations implement GraphTraits to treat 1461 // any VPBlockBase as a node in a graph of VPBlockBases. It's important to note 1462 // that VPBlockBase traits don't recurse into VPRegioBlocks, i.e., if the 1463 // VPBlockBase is a VPRegionBlock, this specialization provides access to its 1464 // successors/predecessors but not to the blocks inside the region. 1465 1466 template <> struct GraphTraits<VPBlockBase *> { 1467 using NodeRef = VPBlockBase *; 1468 using ChildIteratorType = SmallVectorImpl<VPBlockBase *>::iterator; 1469 1470 static NodeRef getEntryNode(NodeRef N) { return N; } 1471 1472 static inline ChildIteratorType child_begin(NodeRef N) { 1473 return N->getSuccessors().begin(); 1474 } 1475 1476 static inline ChildIteratorType child_end(NodeRef N) { 1477 return N->getSuccessors().end(); 1478 } 1479 }; 1480 1481 template <> struct GraphTraits<const VPBlockBase *> { 1482 using NodeRef = const VPBlockBase *; 1483 using ChildIteratorType = SmallVectorImpl<VPBlockBase *>::const_iterator; 1484 1485 static NodeRef getEntryNode(NodeRef N) { return N; } 1486 1487 static inline ChildIteratorType child_begin(NodeRef N) { 1488 return N->getSuccessors().begin(); 1489 } 1490 1491 static inline ChildIteratorType child_end(NodeRef N) { 1492 return N->getSuccessors().end(); 1493 } 1494 }; 1495 1496 // Inverse order specialization for VPBasicBlocks. Predecessors are used instead 1497 // of successors for the inverse traversal. 1498 template <> struct GraphTraits<Inverse<VPBlockBase *>> { 1499 using NodeRef = VPBlockBase *; 1500 using ChildIteratorType = SmallVectorImpl<VPBlockBase *>::iterator; 1501 1502 static NodeRef getEntryNode(Inverse<NodeRef> B) { return B.Graph; } 1503 1504 static inline ChildIteratorType child_begin(NodeRef N) { 1505 return N->getPredecessors().begin(); 1506 } 1507 1508 static inline ChildIteratorType child_end(NodeRef N) { 1509 return N->getPredecessors().end(); 1510 } 1511 }; 1512 1513 // The following set of template specializations implement GraphTraits to 1514 // treat VPRegionBlock as a graph and recurse inside its nodes. It's important 1515 // to note that the blocks inside the VPRegionBlock are treated as VPBlockBases 1516 // (i.e., no dyn_cast is performed, VPBlockBases specialization is used), so 1517 // there won't be automatic recursion into other VPBlockBases that turn to be 1518 // VPRegionBlocks. 1519 1520 template <> 1521 struct GraphTraits<VPRegionBlock *> : public GraphTraits<VPBlockBase *> { 1522 using GraphRef = VPRegionBlock *; 1523 using nodes_iterator = df_iterator<NodeRef>; 1524 1525 static NodeRef getEntryNode(GraphRef N) { return N->getEntry(); } 1526 1527 static nodes_iterator nodes_begin(GraphRef N) { 1528 return nodes_iterator::begin(N->getEntry()); 1529 } 1530 1531 static nodes_iterator nodes_end(GraphRef N) { 1532 // df_iterator::end() returns an empty iterator so the node used doesn't 1533 // matter. 1534 return nodes_iterator::end(N); 1535 } 1536 }; 1537 1538 template <> 1539 struct GraphTraits<const VPRegionBlock *> 1540 : public GraphTraits<const VPBlockBase *> { 1541 using GraphRef = const VPRegionBlock *; 1542 using nodes_iterator = df_iterator<NodeRef>; 1543 1544 static NodeRef getEntryNode(GraphRef N) { return N->getEntry(); } 1545 1546 static nodes_iterator nodes_begin(GraphRef N) { 1547 return nodes_iterator::begin(N->getEntry()); 1548 } 1549 1550 static nodes_iterator nodes_end(GraphRef N) { 1551 // df_iterator::end() returns an empty iterator so the node used doesn't 1552 // matter. 1553 return nodes_iterator::end(N); 1554 } 1555 }; 1556 1557 template <> 1558 struct GraphTraits<Inverse<VPRegionBlock *>> 1559 : public GraphTraits<Inverse<VPBlockBase *>> { 1560 using GraphRef = VPRegionBlock *; 1561 using nodes_iterator = df_iterator<NodeRef>; 1562 1563 static NodeRef getEntryNode(Inverse<GraphRef> N) { 1564 return N.Graph->getExit(); 1565 } 1566 1567 static nodes_iterator nodes_begin(GraphRef N) { 1568 return nodes_iterator::begin(N->getExit()); 1569 } 1570 1571 static nodes_iterator nodes_end(GraphRef N) { 1572 // df_iterator::end() returns an empty iterator so the node used doesn't 1573 // matter. 1574 return nodes_iterator::end(N); 1575 } 1576 }; 1577 1578 /// VPlan models a candidate for vectorization, encoding various decisions take 1579 /// to produce efficient output IR, including which branches, basic-blocks and 1580 /// output IR instructions to generate, and their cost. VPlan holds a 1581 /// Hierarchical-CFG of VPBasicBlocks and VPRegionBlocks rooted at an Entry 1582 /// VPBlock. 1583 class VPlan { 1584 friend class VPlanPrinter; 1585 friend class VPSlotTracker; 1586 1587 /// Hold the single entry to the Hierarchical CFG of the VPlan. 1588 VPBlockBase *Entry; 1589 1590 /// Holds the VFs applicable to this VPlan. 1591 SmallSetVector<ElementCount, 2> VFs; 1592 1593 /// Holds the name of the VPlan, for printing. 1594 std::string Name; 1595 1596 /// Holds all the external definitions created for this VPlan. 1597 // TODO: Introduce a specific representation for external definitions in 1598 // VPlan. External definitions must be immutable and hold a pointer to its 1599 // underlying IR that will be used to implement its structural comparison 1600 // (operators '==' and '<'). 1601 SmallPtrSet<VPValue *, 16> VPExternalDefs; 1602 1603 /// Represents the backedge taken count of the original loop, for folding 1604 /// the tail. 1605 VPValue *BackedgeTakenCount = nullptr; 1606 1607 /// Holds a mapping between Values and their corresponding VPValue inside 1608 /// VPlan. 1609 Value2VPValueTy Value2VPValue; 1610 1611 /// Holds the VPLoopInfo analysis for this VPlan. 1612 VPLoopInfo VPLInfo; 1613 1614 /// Holds the condition bit values built during VPInstruction to VPRecipe transformation. 1615 SmallVector<VPValue *, 4> VPCBVs; 1616 1617 public: 1618 VPlan(VPBlockBase *Entry = nullptr) : Entry(Entry) { 1619 if (Entry) 1620 Entry->setPlan(this); 1621 } 1622 1623 ~VPlan() { 1624 if (Entry) 1625 VPBlockBase::deleteCFG(Entry); 1626 for (auto &MapEntry : Value2VPValue) 1627 delete MapEntry.second; 1628 if (BackedgeTakenCount) 1629 delete BackedgeTakenCount; 1630 for (VPValue *Def : VPExternalDefs) 1631 delete Def; 1632 for (VPValue *CBV : VPCBVs) 1633 delete CBV; 1634 } 1635 1636 /// Generate the IR code for this VPlan. 1637 void execute(struct VPTransformState *State); 1638 1639 VPBlockBase *getEntry() { return Entry; } 1640 const VPBlockBase *getEntry() const { return Entry; } 1641 1642 VPBlockBase *setEntry(VPBlockBase *Block) { 1643 Entry = Block; 1644 Block->setPlan(this); 1645 return Entry; 1646 } 1647 1648 /// The backedge taken count of the original loop. 1649 VPValue *getOrCreateBackedgeTakenCount() { 1650 if (!BackedgeTakenCount) 1651 BackedgeTakenCount = new VPValue(); 1652 return BackedgeTakenCount; 1653 } 1654 1655 void addVF(ElementCount VF) { VFs.insert(VF); } 1656 1657 bool hasVF(ElementCount VF) { return VFs.count(VF); } 1658 1659 const std::string &getName() const { return Name; } 1660 1661 void setName(const Twine &newName) { Name = newName.str(); } 1662 1663 /// Add \p VPVal to the pool of external definitions if it's not already 1664 /// in the pool. 1665 void addExternalDef(VPValue *VPVal) { 1666 VPExternalDefs.insert(VPVal); 1667 } 1668 1669 /// Add \p CBV to the vector of condition bit values. 1670 void addCBV(VPValue *CBV) { 1671 VPCBVs.push_back(CBV); 1672 } 1673 1674 void addVPValue(Value *V) { 1675 assert(V && "Trying to add a null Value to VPlan"); 1676 assert(!Value2VPValue.count(V) && "Value already exists in VPlan"); 1677 Value2VPValue[V] = new VPValue(V); 1678 } 1679 1680 VPValue *getVPValue(Value *V) { 1681 assert(V && "Trying to get the VPValue of a null Value"); 1682 assert(Value2VPValue.count(V) && "Value does not exist in VPlan"); 1683 return Value2VPValue[V]; 1684 } 1685 1686 VPValue *getOrAddVPValue(Value *V) { 1687 assert(V && "Trying to get or add the VPValue of a null Value"); 1688 if (!Value2VPValue.count(V)) 1689 addVPValue(V); 1690 return getVPValue(V); 1691 } 1692 1693 /// Return the VPLoopInfo analysis for this VPlan. 1694 VPLoopInfo &getVPLoopInfo() { return VPLInfo; } 1695 const VPLoopInfo &getVPLoopInfo() const { return VPLInfo; } 1696 1697 /// Dump the plan to stderr (for debugging). 1698 void dump() const; 1699 1700 /// Returns a range mapping the values the range \p Operands to their 1701 /// corresponding VPValues. 1702 iterator_range<mapped_iterator<Use *, std::function<VPValue *(Value *)>>> 1703 mapToVPValues(User::op_range Operands) { 1704 std::function<VPValue *(Value *)> Fn = [this](Value *Op) { 1705 return getOrAddVPValue(Op); 1706 }; 1707 return map_range(Operands, Fn); 1708 } 1709 1710 private: 1711 /// Add to the given dominator tree the header block and every new basic block 1712 /// that was created between it and the latch block, inclusive. 1713 static void updateDominatorTree(DominatorTree *DT, BasicBlock *LoopLatchBB, 1714 BasicBlock *LoopPreHeaderBB, 1715 BasicBlock *LoopExitBB); 1716 }; 1717 1718 /// VPlanPrinter prints a given VPlan to a given output stream. The printing is 1719 /// indented and follows the dot format. 1720 class VPlanPrinter { 1721 friend inline raw_ostream &operator<<(raw_ostream &OS, const VPlan &Plan); 1722 friend inline raw_ostream &operator<<(raw_ostream &OS, 1723 const struct VPlanIngredient &I); 1724 1725 private: 1726 raw_ostream &OS; 1727 const VPlan &Plan; 1728 unsigned Depth = 0; 1729 unsigned TabWidth = 2; 1730 std::string Indent; 1731 unsigned BID = 0; 1732 SmallDenseMap<const VPBlockBase *, unsigned> BlockID; 1733 1734 VPSlotTracker SlotTracker; 1735 1736 VPlanPrinter(raw_ostream &O, const VPlan &P) 1737 : OS(O), Plan(P), SlotTracker(&P) {} 1738 1739 /// Handle indentation. 1740 void bumpIndent(int b) { Indent = std::string((Depth += b) * TabWidth, ' '); } 1741 1742 /// Print a given \p Block of the Plan. 1743 void dumpBlock(const VPBlockBase *Block); 1744 1745 /// Print the information related to the CFG edges going out of a given 1746 /// \p Block, followed by printing the successor blocks themselves. 1747 void dumpEdges(const VPBlockBase *Block); 1748 1749 /// Print a given \p BasicBlock, including its VPRecipes, followed by printing 1750 /// its successor blocks. 1751 void dumpBasicBlock(const VPBasicBlock *BasicBlock); 1752 1753 /// Print a given \p Region of the Plan. 1754 void dumpRegion(const VPRegionBlock *Region); 1755 1756 unsigned getOrCreateBID(const VPBlockBase *Block) { 1757 return BlockID.count(Block) ? BlockID[Block] : BlockID[Block] = BID++; 1758 } 1759 1760 const Twine getOrCreateName(const VPBlockBase *Block); 1761 1762 const Twine getUID(const VPBlockBase *Block); 1763 1764 /// Print the information related to a CFG edge between two VPBlockBases. 1765 void drawEdge(const VPBlockBase *From, const VPBlockBase *To, bool Hidden, 1766 const Twine &Label); 1767 1768 void dump(); 1769 1770 static void printAsIngredient(raw_ostream &O, Value *V); 1771 }; 1772 1773 struct VPlanIngredient { 1774 Value *V; 1775 1776 VPlanIngredient(Value *V) : V(V) {} 1777 }; 1778 1779 inline raw_ostream &operator<<(raw_ostream &OS, const VPlanIngredient &I) { 1780 VPlanPrinter::printAsIngredient(OS, I.V); 1781 return OS; 1782 } 1783 1784 inline raw_ostream &operator<<(raw_ostream &OS, const VPlan &Plan) { 1785 VPlanPrinter Printer(OS, Plan); 1786 Printer.dump(); 1787 return OS; 1788 } 1789 1790 //===----------------------------------------------------------------------===// 1791 // VPlan Utilities 1792 //===----------------------------------------------------------------------===// 1793 1794 /// Class that provides utilities for VPBlockBases in VPlan. 1795 class VPBlockUtils { 1796 public: 1797 VPBlockUtils() = delete; 1798 1799 /// Insert disconnected VPBlockBase \p NewBlock after \p BlockPtr. Add \p 1800 /// NewBlock as successor of \p BlockPtr and \p BlockPtr as predecessor of \p 1801 /// NewBlock, and propagate \p BlockPtr parent to \p NewBlock. If \p BlockPtr 1802 /// has more than one successor, its conditional bit is propagated to \p 1803 /// NewBlock. \p NewBlock must have neither successors nor predecessors. 1804 static void insertBlockAfter(VPBlockBase *NewBlock, VPBlockBase *BlockPtr) { 1805 assert(NewBlock->getSuccessors().empty() && 1806 "Can't insert new block with successors."); 1807 // TODO: move successors from BlockPtr to NewBlock when this functionality 1808 // is necessary. For now, setBlockSingleSuccessor will assert if BlockPtr 1809 // already has successors. 1810 BlockPtr->setOneSuccessor(NewBlock); 1811 NewBlock->setPredecessors({BlockPtr}); 1812 NewBlock->setParent(BlockPtr->getParent()); 1813 } 1814 1815 /// Insert disconnected VPBlockBases \p IfTrue and \p IfFalse after \p 1816 /// BlockPtr. Add \p IfTrue and \p IfFalse as succesors of \p BlockPtr and \p 1817 /// BlockPtr as predecessor of \p IfTrue and \p IfFalse. Propagate \p BlockPtr 1818 /// parent to \p IfTrue and \p IfFalse. \p Condition is set as the successor 1819 /// selector. \p BlockPtr must have no successors and \p IfTrue and \p IfFalse 1820 /// must have neither successors nor predecessors. 1821 static void insertTwoBlocksAfter(VPBlockBase *IfTrue, VPBlockBase *IfFalse, 1822 VPValue *Condition, VPBlockBase *BlockPtr) { 1823 assert(IfTrue->getSuccessors().empty() && 1824 "Can't insert IfTrue with successors."); 1825 assert(IfFalse->getSuccessors().empty() && 1826 "Can't insert IfFalse with successors."); 1827 BlockPtr->setTwoSuccessors(IfTrue, IfFalse, Condition); 1828 IfTrue->setPredecessors({BlockPtr}); 1829 IfFalse->setPredecessors({BlockPtr}); 1830 IfTrue->setParent(BlockPtr->getParent()); 1831 IfFalse->setParent(BlockPtr->getParent()); 1832 } 1833 1834 /// Connect VPBlockBases \p From and \p To bi-directionally. Append \p To to 1835 /// the successors of \p From and \p From to the predecessors of \p To. Both 1836 /// VPBlockBases must have the same parent, which can be null. Both 1837 /// VPBlockBases can be already connected to other VPBlockBases. 1838 static void connectBlocks(VPBlockBase *From, VPBlockBase *To) { 1839 assert((From->getParent() == To->getParent()) && 1840 "Can't connect two block with different parents"); 1841 assert(From->getNumSuccessors() < 2 && 1842 "Blocks can't have more than two successors."); 1843 From->appendSuccessor(To); 1844 To->appendPredecessor(From); 1845 } 1846 1847 /// Disconnect VPBlockBases \p From and \p To bi-directionally. Remove \p To 1848 /// from the successors of \p From and \p From from the predecessors of \p To. 1849 static void disconnectBlocks(VPBlockBase *From, VPBlockBase *To) { 1850 assert(To && "Successor to disconnect is null."); 1851 From->removeSuccessor(To); 1852 To->removePredecessor(From); 1853 } 1854 1855 /// Returns true if the edge \p FromBlock -> \p ToBlock is a back-edge. 1856 static bool isBackEdge(const VPBlockBase *FromBlock, 1857 const VPBlockBase *ToBlock, const VPLoopInfo *VPLI) { 1858 assert(FromBlock->getParent() == ToBlock->getParent() && 1859 FromBlock->getParent() && "Must be in same region"); 1860 const VPLoop *FromLoop = VPLI->getLoopFor(FromBlock); 1861 const VPLoop *ToLoop = VPLI->getLoopFor(ToBlock); 1862 if (!FromLoop || !ToLoop || FromLoop != ToLoop) 1863 return false; 1864 1865 // A back-edge is a branch from the loop latch to its header. 1866 return ToLoop->isLoopLatch(FromBlock) && ToBlock == ToLoop->getHeader(); 1867 } 1868 1869 /// Returns true if \p Block is a loop latch 1870 static bool blockIsLoopLatch(const VPBlockBase *Block, 1871 const VPLoopInfo *VPLInfo) { 1872 if (const VPLoop *ParentVPL = VPLInfo->getLoopFor(Block)) 1873 return ParentVPL->isLoopLatch(Block); 1874 1875 return false; 1876 } 1877 1878 /// Count and return the number of succesors of \p PredBlock excluding any 1879 /// backedges. 1880 static unsigned countSuccessorsNoBE(VPBlockBase *PredBlock, 1881 VPLoopInfo *VPLI) { 1882 unsigned Count = 0; 1883 for (VPBlockBase *SuccBlock : PredBlock->getSuccessors()) { 1884 if (!VPBlockUtils::isBackEdge(PredBlock, SuccBlock, VPLI)) 1885 Count++; 1886 } 1887 return Count; 1888 } 1889 }; 1890 1891 class VPInterleavedAccessInfo { 1892 DenseMap<VPInstruction *, InterleaveGroup<VPInstruction> *> 1893 InterleaveGroupMap; 1894 1895 /// Type for mapping of instruction based interleave groups to VPInstruction 1896 /// interleave groups 1897 using Old2NewTy = DenseMap<InterleaveGroup<Instruction> *, 1898 InterleaveGroup<VPInstruction> *>; 1899 1900 /// Recursively \p Region and populate VPlan based interleave groups based on 1901 /// \p IAI. 1902 void visitRegion(VPRegionBlock *Region, Old2NewTy &Old2New, 1903 InterleavedAccessInfo &IAI); 1904 /// Recursively traverse \p Block and populate VPlan based interleave groups 1905 /// based on \p IAI. 1906 void visitBlock(VPBlockBase *Block, Old2NewTy &Old2New, 1907 InterleavedAccessInfo &IAI); 1908 1909 public: 1910 VPInterleavedAccessInfo(VPlan &Plan, InterleavedAccessInfo &IAI); 1911 1912 ~VPInterleavedAccessInfo() { 1913 SmallPtrSet<InterleaveGroup<VPInstruction> *, 4> DelSet; 1914 // Avoid releasing a pointer twice. 1915 for (auto &I : InterleaveGroupMap) 1916 DelSet.insert(I.second); 1917 for (auto *Ptr : DelSet) 1918 delete Ptr; 1919 } 1920 1921 /// Get the interleave group that \p Instr belongs to. 1922 /// 1923 /// \returns nullptr if doesn't have such group. 1924 InterleaveGroup<VPInstruction> * 1925 getInterleaveGroup(VPInstruction *Instr) const { 1926 if (InterleaveGroupMap.count(Instr)) 1927 return InterleaveGroupMap.find(Instr)->second; 1928 return nullptr; 1929 } 1930 }; 1931 1932 /// Class that maps (parts of) an existing VPlan to trees of combined 1933 /// VPInstructions. 1934 class VPlanSlp { 1935 enum class OpMode { Failed, Load, Opcode }; 1936 1937 /// A DenseMapInfo implementation for using SmallVector<VPValue *, 4> as 1938 /// DenseMap keys. 1939 struct BundleDenseMapInfo { 1940 static SmallVector<VPValue *, 4> getEmptyKey() { 1941 return {reinterpret_cast<VPValue *>(-1)}; 1942 } 1943 1944 static SmallVector<VPValue *, 4> getTombstoneKey() { 1945 return {reinterpret_cast<VPValue *>(-2)}; 1946 } 1947 1948 static unsigned getHashValue(const SmallVector<VPValue *, 4> &V) { 1949 return static_cast<unsigned>(hash_combine_range(V.begin(), V.end())); 1950 } 1951 1952 static bool isEqual(const SmallVector<VPValue *, 4> &LHS, 1953 const SmallVector<VPValue *, 4> &RHS) { 1954 return LHS == RHS; 1955 } 1956 }; 1957 1958 /// Mapping of values in the original VPlan to a combined VPInstruction. 1959 DenseMap<SmallVector<VPValue *, 4>, VPInstruction *, BundleDenseMapInfo> 1960 BundleToCombined; 1961 1962 VPInterleavedAccessInfo &IAI; 1963 1964 /// Basic block to operate on. For now, only instructions in a single BB are 1965 /// considered. 1966 const VPBasicBlock &BB; 1967 1968 /// Indicates whether we managed to combine all visited instructions or not. 1969 bool CompletelySLP = true; 1970 1971 /// Width of the widest combined bundle in bits. 1972 unsigned WidestBundleBits = 0; 1973 1974 using MultiNodeOpTy = 1975 typename std::pair<VPInstruction *, SmallVector<VPValue *, 4>>; 1976 1977 // Input operand bundles for the current multi node. Each multi node operand 1978 // bundle contains values not matching the multi node's opcode. They will 1979 // be reordered in reorderMultiNodeOps, once we completed building a 1980 // multi node. 1981 SmallVector<MultiNodeOpTy, 4> MultiNodeOps; 1982 1983 /// Indicates whether we are building a multi node currently. 1984 bool MultiNodeActive = false; 1985 1986 /// Check if we can vectorize Operands together. 1987 bool areVectorizable(ArrayRef<VPValue *> Operands) const; 1988 1989 /// Add combined instruction \p New for the bundle \p Operands. 1990 void addCombined(ArrayRef<VPValue *> Operands, VPInstruction *New); 1991 1992 /// Indicate we hit a bundle we failed to combine. Returns nullptr for now. 1993 VPInstruction *markFailed(); 1994 1995 /// Reorder operands in the multi node to maximize sequential memory access 1996 /// and commutative operations. 1997 SmallVector<MultiNodeOpTy, 4> reorderMultiNodeOps(); 1998 1999 /// Choose the best candidate to use for the lane after \p Last. The set of 2000 /// candidates to choose from are values with an opcode matching \p Last's 2001 /// or loads consecutive to \p Last. 2002 std::pair<OpMode, VPValue *> getBest(OpMode Mode, VPValue *Last, 2003 SmallPtrSetImpl<VPValue *> &Candidates, 2004 VPInterleavedAccessInfo &IAI); 2005 2006 /// Print bundle \p Values to dbgs(). 2007 void dumpBundle(ArrayRef<VPValue *> Values); 2008 2009 public: 2010 VPlanSlp(VPInterleavedAccessInfo &IAI, VPBasicBlock &BB) : IAI(IAI), BB(BB) {} 2011 2012 ~VPlanSlp() { 2013 for (auto &KV : BundleToCombined) 2014 delete KV.second; 2015 } 2016 2017 /// Tries to build an SLP tree rooted at \p Operands and returns a 2018 /// VPInstruction combining \p Operands, if they can be combined. 2019 VPInstruction *buildGraph(ArrayRef<VPValue *> Operands); 2020 2021 /// Return the width of the widest combined bundle in bits. 2022 unsigned getWidestBundleBits() const { return WidestBundleBits; } 2023 2024 /// Return true if all visited instruction can be combined. 2025 bool isCompletelySLP() const { return CompletelySLP; } 2026 }; 2027 } // end namespace llvm 2028 2029 #endif // LLVM_TRANSFORMS_VECTORIZE_VPLAN_H 2030