1 //===- RISCVInsertVSETVLI.cpp - Insert VSETVLI instructions ---------------===// 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 // This file implements a function pass that inserts VSETVLI instructions where 10 // needed. 11 // 12 // This pass consists of 3 phases: 13 // 14 // Phase 1 collects how each basic block affects VL/VTYPE. 15 // 16 // Phase 2 uses the information from phase 1 to do a data flow analysis to 17 // propagate the VL/VTYPE changes through the function. This gives us the 18 // VL/VTYPE at the start of each basic block. 19 // 20 // Phase 3 inserts VSETVLI instructions in each basic block. Information from 21 // phase 2 is used to prevent inserting a VSETVLI before the first vector 22 // instruction in the block if possible. 23 // 24 //===----------------------------------------------------------------------===// 25 26 #include "RISCV.h" 27 #include "RISCVSubtarget.h" 28 #include "llvm/CodeGen/LiveIntervals.h" 29 #include "llvm/CodeGen/MachineFunctionPass.h" 30 #include <queue> 31 using namespace llvm; 32 33 #define DEBUG_TYPE "riscv-insert-vsetvli" 34 #define RISCV_INSERT_VSETVLI_NAME "RISCV Insert VSETVLI pass" 35 36 static cl::opt<bool> DisableInsertVSETVLPHIOpt( 37 "riscv-disable-insert-vsetvl-phi-opt", cl::init(false), cl::Hidden, 38 cl::desc("Disable looking through phis when inserting vsetvlis.")); 39 40 static cl::opt<bool> UseStrictAsserts( 41 "riscv-insert-vsetvl-strict-asserts", cl::init(true), cl::Hidden, 42 cl::desc("Enable strict assertion checking for the dataflow algorithm")); 43 44 namespace { 45 46 static unsigned getVLOpNum(const MachineInstr &MI) { 47 return RISCVII::getVLOpNum(MI.getDesc()); 48 } 49 50 static unsigned getSEWOpNum(const MachineInstr &MI) { 51 return RISCVII::getSEWOpNum(MI.getDesc()); 52 } 53 54 static bool isScalarMoveInstr(const MachineInstr &MI) { 55 switch (MI.getOpcode()) { 56 default: 57 return false; 58 case RISCV::PseudoVMV_S_X_M1: 59 case RISCV::PseudoVMV_S_X_M2: 60 case RISCV::PseudoVMV_S_X_M4: 61 case RISCV::PseudoVMV_S_X_M8: 62 case RISCV::PseudoVMV_S_X_MF2: 63 case RISCV::PseudoVMV_S_X_MF4: 64 case RISCV::PseudoVMV_S_X_MF8: 65 case RISCV::PseudoVFMV_S_F16_M1: 66 case RISCV::PseudoVFMV_S_F16_M2: 67 case RISCV::PseudoVFMV_S_F16_M4: 68 case RISCV::PseudoVFMV_S_F16_M8: 69 case RISCV::PseudoVFMV_S_F16_MF2: 70 case RISCV::PseudoVFMV_S_F16_MF4: 71 case RISCV::PseudoVFMV_S_F32_M1: 72 case RISCV::PseudoVFMV_S_F32_M2: 73 case RISCV::PseudoVFMV_S_F32_M4: 74 case RISCV::PseudoVFMV_S_F32_M8: 75 case RISCV::PseudoVFMV_S_F32_MF2: 76 case RISCV::PseudoVFMV_S_F64_M1: 77 case RISCV::PseudoVFMV_S_F64_M2: 78 case RISCV::PseudoVFMV_S_F64_M4: 79 case RISCV::PseudoVFMV_S_F64_M8: 80 return true; 81 } 82 } 83 84 85 class VSETVLIInfo { 86 union { 87 Register AVLReg; 88 unsigned AVLImm; 89 }; 90 91 enum : uint8_t { 92 Uninitialized, 93 AVLIsReg, 94 AVLIsImm, 95 Unknown, 96 } State = Uninitialized; 97 98 // Fields from VTYPE. 99 RISCVII::VLMUL VLMul = RISCVII::LMUL_1; 100 uint8_t SEW = 0; 101 uint8_t TailAgnostic : 1; 102 uint8_t MaskAgnostic : 1; 103 uint8_t SEWLMULRatioOnly : 1; 104 105 public: 106 VSETVLIInfo() 107 : AVLImm(0), TailAgnostic(false), MaskAgnostic(false), 108 SEWLMULRatioOnly(false) {} 109 110 static VSETVLIInfo getUnknown() { 111 VSETVLIInfo Info; 112 Info.setUnknown(); 113 return Info; 114 } 115 116 bool isValid() const { return State != Uninitialized; } 117 void setUnknown() { State = Unknown; } 118 bool isUnknown() const { return State == Unknown; } 119 120 void setAVLReg(Register Reg) { 121 AVLReg = Reg; 122 State = AVLIsReg; 123 } 124 125 void setAVLImm(unsigned Imm) { 126 AVLImm = Imm; 127 State = AVLIsImm; 128 } 129 130 bool hasAVLImm() const { return State == AVLIsImm; } 131 bool hasAVLReg() const { return State == AVLIsReg; } 132 Register getAVLReg() const { 133 assert(hasAVLReg()); 134 return AVLReg; 135 } 136 unsigned getAVLImm() const { 137 assert(hasAVLImm()); 138 return AVLImm; 139 } 140 141 unsigned getSEW() const { return SEW; } 142 RISCVII::VLMUL getVLMUL() const { return VLMul; } 143 144 bool hasZeroAVL() const { 145 if (hasAVLImm()) 146 return getAVLImm() == 0; 147 return false; 148 } 149 bool hasNonZeroAVL() const { 150 if (hasAVLImm()) 151 return getAVLImm() > 0; 152 if (hasAVLReg()) 153 return getAVLReg() == RISCV::X0; 154 return false; 155 } 156 157 bool hasSameAVL(const VSETVLIInfo &Other) const { 158 assert(isValid() && Other.isValid() && 159 "Can't compare invalid VSETVLIInfos"); 160 assert(!isUnknown() && !Other.isUnknown() && 161 "Can't compare AVL in unknown state"); 162 if (hasAVLReg() && Other.hasAVLReg()) 163 return getAVLReg() == Other.getAVLReg(); 164 165 if (hasAVLImm() && Other.hasAVLImm()) 166 return getAVLImm() == Other.getAVLImm(); 167 168 return false; 169 } 170 171 void setVTYPE(unsigned VType) { 172 assert(isValid() && !isUnknown() && 173 "Can't set VTYPE for uninitialized or unknown"); 174 VLMul = RISCVVType::getVLMUL(VType); 175 SEW = RISCVVType::getSEW(VType); 176 TailAgnostic = RISCVVType::isTailAgnostic(VType); 177 MaskAgnostic = RISCVVType::isMaskAgnostic(VType); 178 } 179 void setVTYPE(RISCVII::VLMUL L, unsigned S, bool TA, bool MA) { 180 assert(isValid() && !isUnknown() && 181 "Can't set VTYPE for uninitialized or unknown"); 182 VLMul = L; 183 SEW = S; 184 TailAgnostic = TA; 185 MaskAgnostic = MA; 186 } 187 188 unsigned encodeVTYPE() const { 189 assert(isValid() && !isUnknown() && !SEWLMULRatioOnly && 190 "Can't encode VTYPE for uninitialized or unknown"); 191 return RISCVVType::encodeVTYPE(VLMul, SEW, TailAgnostic, MaskAgnostic); 192 } 193 194 bool hasSEWLMULRatioOnly() const { return SEWLMULRatioOnly; } 195 196 bool hasSameSEW(const VSETVLIInfo &Other) const { 197 assert(isValid() && Other.isValid() && 198 "Can't compare invalid VSETVLIInfos"); 199 assert(!isUnknown() && !Other.isUnknown() && 200 "Can't compare VTYPE in unknown state"); 201 assert(!SEWLMULRatioOnly && !Other.SEWLMULRatioOnly && 202 "Can't compare when only LMUL/SEW ratio is valid."); 203 return SEW == Other.SEW; 204 } 205 206 bool hasSameVTYPE(const VSETVLIInfo &Other) const { 207 assert(isValid() && Other.isValid() && 208 "Can't compare invalid VSETVLIInfos"); 209 assert(!isUnknown() && !Other.isUnknown() && 210 "Can't compare VTYPE in unknown state"); 211 assert(!SEWLMULRatioOnly && !Other.SEWLMULRatioOnly && 212 "Can't compare when only LMUL/SEW ratio is valid."); 213 return std::tie(VLMul, SEW, TailAgnostic, MaskAgnostic) == 214 std::tie(Other.VLMul, Other.SEW, Other.TailAgnostic, 215 Other.MaskAgnostic); 216 } 217 218 static unsigned getSEWLMULRatio(unsigned SEW, RISCVII::VLMUL VLMul) { 219 unsigned LMul; 220 bool Fractional; 221 std::tie(LMul, Fractional) = RISCVVType::decodeVLMUL(VLMul); 222 223 // Convert LMul to a fixed point value with 3 fractional bits. 224 LMul = Fractional ? (8 / LMul) : (LMul * 8); 225 226 assert(SEW >= 8 && "Unexpected SEW value"); 227 return (SEW * 8) / LMul; 228 } 229 230 unsigned getSEWLMULRatio() const { 231 assert(isValid() && !isUnknown() && 232 "Can't use VTYPE for uninitialized or unknown"); 233 return getSEWLMULRatio(SEW, VLMul); 234 } 235 236 // Check if the VTYPE for these two VSETVLIInfos produce the same VLMAX. 237 // Note that having the same VLMAX ensures that both share the same 238 // function from AVL to VL; that is, they must produce the same VL value 239 // for any given AVL value. 240 bool hasSameVLMAX(const VSETVLIInfo &Other) const { 241 assert(isValid() && Other.isValid() && 242 "Can't compare invalid VSETVLIInfos"); 243 assert(!isUnknown() && !Other.isUnknown() && 244 "Can't compare VTYPE in unknown state"); 245 return getSEWLMULRatio() == Other.getSEWLMULRatio(); 246 } 247 248 bool hasSamePolicy(const VSETVLIInfo &Other) const { 249 assert(isValid() && Other.isValid() && 250 "Can't compare invalid VSETVLIInfos"); 251 assert(!isUnknown() && !Other.isUnknown() && 252 "Can't compare VTYPE in unknown state"); 253 return TailAgnostic == Other.TailAgnostic && 254 MaskAgnostic == Other.MaskAgnostic; 255 } 256 257 bool hasCompatibleVTYPE(const MachineInstr &MI, 258 const VSETVLIInfo &Require) const { 259 // Simple case, see if full VTYPE matches. 260 if (hasSameVTYPE(Require)) 261 return true; 262 263 // If this is a mask reg operation, it only cares about VLMAX. 264 // FIXME: Mask reg operations are probably ok if "this" VLMAX is larger 265 // than "Require". 266 // FIXME: The policy bits can probably be ignored for mask reg operations. 267 const unsigned Log2SEW = MI.getOperand(getSEWOpNum(MI)).getImm(); 268 // A Log2SEW of 0 is an operation on mask registers only. 269 const bool MaskRegOp = Log2SEW == 0; 270 if (MaskRegOp && hasSameVLMAX(Require) && 271 TailAgnostic == Require.TailAgnostic && 272 MaskAgnostic == Require.MaskAgnostic) 273 return true; 274 275 return false; 276 } 277 278 // Determine whether the vector instructions requirements represented by 279 // Require are compatible with the previous vsetvli instruction represented 280 // by this. MI is the instruction whose requirements we're considering. 281 bool isCompatible(const MachineInstr &MI, const VSETVLIInfo &Require) const { 282 assert(isValid() && Require.isValid() && 283 "Can't compare invalid VSETVLIInfos"); 284 assert(!Require.SEWLMULRatioOnly && 285 "Expected a valid VTYPE for instruction!"); 286 // Nothing is compatible with Unknown. 287 if (isUnknown() || Require.isUnknown()) 288 return false; 289 290 // If only our VLMAX ratio is valid, then this isn't compatible. 291 if (SEWLMULRatioOnly) 292 return false; 293 294 // If the instruction doesn't need an AVLReg and the SEW matches, consider 295 // it compatible. 296 if (Require.hasAVLReg() && Require.AVLReg == RISCV::NoRegister) 297 if (SEW == Require.SEW) 298 return true; 299 300 // For vmv.s.x and vfmv.s.f, there is only two behaviors, VL = 0 and VL > 0. 301 // So it's compatible when we could make sure that both VL be the same 302 // situation. 303 if (isScalarMoveInstr(MI) && Require.hasAVLImm() && 304 ((hasNonZeroAVL() && Require.hasNonZeroAVL()) || 305 (hasZeroAVL() && Require.hasZeroAVL())) && 306 hasSameSEW(Require) && hasSamePolicy(Require)) 307 return true; 308 309 // The AVL must match. 310 if (!hasSameAVL(Require)) 311 return false; 312 313 if (hasCompatibleVTYPE(MI, Require)) 314 return true; 315 316 // Store instructions don't use the policy fields. 317 const bool StoreOp = MI.getNumExplicitDefs() == 0; 318 if (StoreOp && VLMul == Require.VLMul && SEW == Require.SEW) 319 return true; 320 321 // Anything else is not compatible. 322 return false; 323 } 324 325 bool isCompatibleWithLoadStoreEEW(unsigned EEW, 326 const VSETVLIInfo &Require) const { 327 assert(isValid() && Require.isValid() && 328 "Can't compare invalid VSETVLIInfos"); 329 assert(!Require.SEWLMULRatioOnly && 330 "Expected a valid VTYPE for instruction!"); 331 assert(EEW == Require.SEW && "Mismatched EEW/SEW for store"); 332 333 if (isUnknown() || hasSEWLMULRatioOnly()) 334 return false; 335 336 if (!hasSameAVL(Require)) 337 return false; 338 339 return getSEWLMULRatio() == getSEWLMULRatio(EEW, Require.VLMul); 340 } 341 342 bool operator==(const VSETVLIInfo &Other) const { 343 // Uninitialized is only equal to another Uninitialized. 344 if (!isValid()) 345 return !Other.isValid(); 346 if (!Other.isValid()) 347 return !isValid(); 348 349 // Unknown is only equal to another Unknown. 350 if (isUnknown()) 351 return Other.isUnknown(); 352 if (Other.isUnknown()) 353 return isUnknown(); 354 355 if (!hasSameAVL(Other)) 356 return false; 357 358 // If the SEWLMULRatioOnly bits are different, then they aren't equal. 359 if (SEWLMULRatioOnly != Other.SEWLMULRatioOnly) 360 return false; 361 362 // If only the VLMAX is valid, check that it is the same. 363 if (SEWLMULRatioOnly) 364 return hasSameVLMAX(Other); 365 366 // If the full VTYPE is valid, check that it is the same. 367 return hasSameVTYPE(Other); 368 } 369 370 bool operator!=(const VSETVLIInfo &Other) const { 371 return !(*this == Other); 372 } 373 374 // Calculate the VSETVLIInfo visible to a block assuming this and Other are 375 // both predecessors. 376 VSETVLIInfo intersect(const VSETVLIInfo &Other) const { 377 // If the new value isn't valid, ignore it. 378 if (!Other.isValid()) 379 return *this; 380 381 // If this value isn't valid, this must be the first predecessor, use it. 382 if (!isValid()) 383 return Other; 384 385 // If either is unknown, the result is unknown. 386 if (isUnknown() || Other.isUnknown()) 387 return VSETVLIInfo::getUnknown(); 388 389 // If we have an exact, match return this. 390 if (*this == Other) 391 return *this; 392 393 // Not an exact match, but maybe the AVL and VLMAX are the same. If so, 394 // return an SEW/LMUL ratio only value. 395 if (hasSameAVL(Other) && hasSameVLMAX(Other)) { 396 VSETVLIInfo MergeInfo = *this; 397 MergeInfo.SEWLMULRatioOnly = true; 398 return MergeInfo; 399 } 400 401 // Otherwise the result is unknown. 402 return VSETVLIInfo::getUnknown(); 403 } 404 405 #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) 406 /// Support for debugging, callable in GDB: V->dump() 407 LLVM_DUMP_METHOD void dump() const { 408 print(dbgs()); 409 dbgs() << "\n"; 410 } 411 412 /// Implement operator<<. 413 /// @{ 414 void print(raw_ostream &OS) const { 415 OS << "{"; 416 if (!isValid()) 417 OS << "Uninitialized"; 418 if (isUnknown()) 419 OS << "unknown";; 420 if (hasAVLReg()) 421 OS << "AVLReg=" << (unsigned)AVLReg; 422 if (hasAVLImm()) 423 OS << "AVLImm=" << (unsigned)AVLImm; 424 OS << ", " 425 << "VLMul=" << (unsigned)VLMul << ", " 426 << "SEW=" << (unsigned)SEW << ", " 427 << "TailAgnostic=" << (bool)TailAgnostic << ", " 428 << "MaskAgnostic=" << (bool)MaskAgnostic << ", " 429 << "SEWLMULRatioOnly=" << (bool)SEWLMULRatioOnly << "}"; 430 } 431 #endif 432 }; 433 434 #if !defined(NDEBUG) || defined(LLVM_ENABLE_DUMP) 435 LLVM_ATTRIBUTE_USED 436 inline raw_ostream &operator<<(raw_ostream &OS, const VSETVLIInfo &V) { 437 V.print(OS); 438 return OS; 439 } 440 #endif 441 442 struct BlockData { 443 // The VSETVLIInfo that represents the net changes to the VL/VTYPE registers 444 // made by this block. Calculated in Phase 1. 445 VSETVLIInfo Change; 446 447 // The VSETVLIInfo that represents the VL/VTYPE settings on exit from this 448 // block. Calculated in Phase 2. 449 VSETVLIInfo Exit; 450 451 // The VSETVLIInfo that represents the VL/VTYPE settings from all predecessor 452 // blocks. Calculated in Phase 2, and used by Phase 3. 453 VSETVLIInfo Pred; 454 455 // Keeps track of whether the block is already in the queue. 456 bool InQueue = false; 457 458 BlockData() = default; 459 }; 460 461 class RISCVInsertVSETVLI : public MachineFunctionPass { 462 const TargetInstrInfo *TII; 463 MachineRegisterInfo *MRI; 464 465 std::vector<BlockData> BlockInfo; 466 std::queue<const MachineBasicBlock *> WorkList; 467 468 public: 469 static char ID; 470 471 RISCVInsertVSETVLI() : MachineFunctionPass(ID) { 472 initializeRISCVInsertVSETVLIPass(*PassRegistry::getPassRegistry()); 473 } 474 bool runOnMachineFunction(MachineFunction &MF) override; 475 476 void getAnalysisUsage(AnalysisUsage &AU) const override { 477 AU.setPreservesCFG(); 478 MachineFunctionPass::getAnalysisUsage(AU); 479 } 480 481 StringRef getPassName() const override { return RISCV_INSERT_VSETVLI_NAME; } 482 483 private: 484 bool needVSETVLI(const MachineInstr &MI, const VSETVLIInfo &Require, 485 const VSETVLIInfo &CurInfo) const; 486 bool needVSETVLIPHI(const VSETVLIInfo &Require, 487 const MachineBasicBlock &MBB) const; 488 void insertVSETVLI(MachineBasicBlock &MBB, MachineInstr &MI, 489 const VSETVLIInfo &Info, const VSETVLIInfo &PrevInfo); 490 void insertVSETVLI(MachineBasicBlock &MBB, 491 MachineBasicBlock::iterator InsertPt, DebugLoc DL, 492 const VSETVLIInfo &Info, const VSETVLIInfo &PrevInfo); 493 494 bool computeVLVTYPEChanges(const MachineBasicBlock &MBB); 495 void computeIncomingVLVTYPE(const MachineBasicBlock &MBB); 496 void emitVSETVLIs(MachineBasicBlock &MBB); 497 void doLocalPrepass(MachineBasicBlock &MBB); 498 void doLocalPostpass(MachineBasicBlock &MBB); 499 void doPRE(MachineBasicBlock &MBB); 500 }; 501 502 } // end anonymous namespace 503 504 char RISCVInsertVSETVLI::ID = 0; 505 506 INITIALIZE_PASS(RISCVInsertVSETVLI, DEBUG_TYPE, RISCV_INSERT_VSETVLI_NAME, 507 false, false) 508 509 static bool isVectorConfigInstr(const MachineInstr &MI) { 510 return MI.getOpcode() == RISCV::PseudoVSETVLI || 511 MI.getOpcode() == RISCV::PseudoVSETVLIX0 || 512 MI.getOpcode() == RISCV::PseudoVSETIVLI; 513 } 514 515 /// Return true if this is 'vsetvli x0, x0, vtype' which preserves 516 /// VL and only sets VTYPE. 517 static bool isVLPreservingConfig(const MachineInstr &MI) { 518 if (MI.getOpcode() != RISCV::PseudoVSETVLIX0) 519 return false; 520 assert(RISCV::X0 == MI.getOperand(1).getReg()); 521 return RISCV::X0 == MI.getOperand(0).getReg(); 522 } 523 524 static MachineInstr *elideCopies(MachineInstr *MI, 525 const MachineRegisterInfo *MRI) { 526 while (true) { 527 if (!MI->isFullCopy()) 528 return MI; 529 if (!Register::isVirtualRegister(MI->getOperand(1).getReg())) 530 return nullptr; 531 MI = MRI->getVRegDef(MI->getOperand(1).getReg()); 532 if (!MI) 533 return nullptr; 534 } 535 } 536 537 static VSETVLIInfo computeInfoForInstr(const MachineInstr &MI, uint64_t TSFlags, 538 const MachineRegisterInfo *MRI) { 539 VSETVLIInfo InstrInfo; 540 541 // If the instruction has policy argument, use the argument. 542 // If there is no policy argument, default to tail agnostic unless the 543 // destination is tied to a source. Unless the source is undef. In that case 544 // the user would have some control over the policy values. 545 bool TailAgnostic = true; 546 bool UsesMaskPolicy = RISCVII::usesMaskPolicy(TSFlags); 547 // FIXME: Could we look at the above or below instructions to choose the 548 // matched mask policy to reduce vsetvli instructions? Default mask policy is 549 // agnostic if instructions use mask policy, otherwise is undisturbed. Because 550 // most mask operations are mask undisturbed, so we could possibly reduce the 551 // vsetvli between mask and nomasked instruction sequence. 552 bool MaskAgnostic = UsesMaskPolicy; 553 unsigned UseOpIdx; 554 if (RISCVII::hasVecPolicyOp(TSFlags)) { 555 const MachineOperand &Op = MI.getOperand(MI.getNumExplicitOperands() - 1); 556 uint64_t Policy = Op.getImm(); 557 assert(Policy <= (RISCVII::TAIL_AGNOSTIC | RISCVII::MASK_AGNOSTIC) && 558 "Invalid Policy Value"); 559 // Although in some cases, mismatched passthru/maskedoff with policy value 560 // does not make sense (ex. tied operand is IMPLICIT_DEF with non-TAMA 561 // policy, or tied operand is not IMPLICIT_DEF with TAMA policy), but users 562 // have set the policy value explicitly, so compiler would not fix it. 563 TailAgnostic = Policy & RISCVII::TAIL_AGNOSTIC; 564 MaskAgnostic = Policy & RISCVII::MASK_AGNOSTIC; 565 } else if (MI.isRegTiedToUseOperand(0, &UseOpIdx)) { 566 TailAgnostic = false; 567 if (UsesMaskPolicy) 568 MaskAgnostic = false; 569 // If the tied operand is an IMPLICIT_DEF we can keep TailAgnostic. 570 const MachineOperand &UseMO = MI.getOperand(UseOpIdx); 571 MachineInstr *UseMI = MRI->getVRegDef(UseMO.getReg()); 572 if (UseMI) { 573 UseMI = elideCopies(UseMI, MRI); 574 if (UseMI && UseMI->isImplicitDef()) { 575 TailAgnostic = true; 576 if (UsesMaskPolicy) 577 MaskAgnostic = true; 578 } 579 } 580 // Some pseudo instructions force a tail agnostic policy despite having a 581 // tied def. 582 if (RISCVII::doesForceTailAgnostic(TSFlags)) 583 TailAgnostic = true; 584 } 585 586 RISCVII::VLMUL VLMul = RISCVII::getLMul(TSFlags); 587 588 unsigned Log2SEW = MI.getOperand(getSEWOpNum(MI)).getImm(); 589 // A Log2SEW of 0 is an operation on mask registers only. 590 unsigned SEW = Log2SEW ? 1 << Log2SEW : 8; 591 assert(RISCVVType::isValidSEW(SEW) && "Unexpected SEW"); 592 593 if (RISCVII::hasVLOp(TSFlags)) { 594 const MachineOperand &VLOp = MI.getOperand(getVLOpNum(MI)); 595 if (VLOp.isImm()) { 596 int64_t Imm = VLOp.getImm(); 597 // Conver the VLMax sentintel to X0 register. 598 if (Imm == RISCV::VLMaxSentinel) 599 InstrInfo.setAVLReg(RISCV::X0); 600 else 601 InstrInfo.setAVLImm(Imm); 602 } else { 603 InstrInfo.setAVLReg(VLOp.getReg()); 604 } 605 } else { 606 InstrInfo.setAVLReg(RISCV::NoRegister); 607 } 608 InstrInfo.setVTYPE(VLMul, SEW, TailAgnostic, MaskAgnostic); 609 610 return InstrInfo; 611 } 612 613 void RISCVInsertVSETVLI::insertVSETVLI(MachineBasicBlock &MBB, MachineInstr &MI, 614 const VSETVLIInfo &Info, 615 const VSETVLIInfo &PrevInfo) { 616 DebugLoc DL = MI.getDebugLoc(); 617 insertVSETVLI(MBB, MachineBasicBlock::iterator(&MI), DL, Info, PrevInfo); 618 } 619 620 void RISCVInsertVSETVLI::insertVSETVLI(MachineBasicBlock &MBB, 621 MachineBasicBlock::iterator InsertPt, DebugLoc DL, 622 const VSETVLIInfo &Info, const VSETVLIInfo &PrevInfo) { 623 624 // Use X0, X0 form if the AVL is the same and the SEW+LMUL gives the same 625 // VLMAX. 626 if (PrevInfo.isValid() && !PrevInfo.isUnknown() && 627 Info.hasSameAVL(PrevInfo) && Info.hasSameVLMAX(PrevInfo)) { 628 BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETVLIX0)) 629 .addReg(RISCV::X0, RegState::Define | RegState::Dead) 630 .addReg(RISCV::X0, RegState::Kill) 631 .addImm(Info.encodeVTYPE()) 632 .addReg(RISCV::VL, RegState::Implicit); 633 return; 634 } 635 636 if (Info.hasAVLImm()) { 637 BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETIVLI)) 638 .addReg(RISCV::X0, RegState::Define | RegState::Dead) 639 .addImm(Info.getAVLImm()) 640 .addImm(Info.encodeVTYPE()); 641 return; 642 } 643 644 Register AVLReg = Info.getAVLReg(); 645 if (AVLReg == RISCV::NoRegister) { 646 // We can only use x0, x0 if there's no chance of the vtype change causing 647 // the previous vl to become invalid. 648 if (PrevInfo.isValid() && !PrevInfo.isUnknown() && 649 Info.hasSameVLMAX(PrevInfo)) { 650 BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETVLIX0)) 651 .addReg(RISCV::X0, RegState::Define | RegState::Dead) 652 .addReg(RISCV::X0, RegState::Kill) 653 .addImm(Info.encodeVTYPE()) 654 .addReg(RISCV::VL, RegState::Implicit); 655 return; 656 } 657 // Otherwise use an AVL of 0 to avoid depending on previous vl. 658 BuildMI(MBB, InsertPt, DL, TII->get(RISCV::PseudoVSETIVLI)) 659 .addReg(RISCV::X0, RegState::Define | RegState::Dead) 660 .addImm(0) 661 .addImm(Info.encodeVTYPE()); 662 return; 663 } 664 665 if (AVLReg.isVirtual()) 666 MRI->constrainRegClass(AVLReg, &RISCV::GPRNoX0RegClass); 667 668 // Use X0 as the DestReg unless AVLReg is X0. We also need to change the 669 // opcode if the AVLReg is X0 as they have different register classes for 670 // the AVL operand. 671 Register DestReg = RISCV::X0; 672 unsigned Opcode = RISCV::PseudoVSETVLI; 673 if (AVLReg == RISCV::X0) { 674 DestReg = MRI->createVirtualRegister(&RISCV::GPRRegClass); 675 Opcode = RISCV::PseudoVSETVLIX0; 676 } 677 BuildMI(MBB, InsertPt, DL, TII->get(Opcode)) 678 .addReg(DestReg, RegState::Define | RegState::Dead) 679 .addReg(AVLReg) 680 .addImm(Info.encodeVTYPE()); 681 } 682 683 // Return a VSETVLIInfo representing the changes made by this VSETVLI or 684 // VSETIVLI instruction. 685 static VSETVLIInfo getInfoForVSETVLI(const MachineInstr &MI) { 686 VSETVLIInfo NewInfo; 687 if (MI.getOpcode() == RISCV::PseudoVSETIVLI) { 688 NewInfo.setAVLImm(MI.getOperand(1).getImm()); 689 } else { 690 assert(MI.getOpcode() == RISCV::PseudoVSETVLI || 691 MI.getOpcode() == RISCV::PseudoVSETVLIX0); 692 Register AVLReg = MI.getOperand(1).getReg(); 693 assert((AVLReg != RISCV::X0 || MI.getOperand(0).getReg() != RISCV::X0) && 694 "Can't handle X0, X0 vsetvli yet"); 695 NewInfo.setAVLReg(AVLReg); 696 } 697 NewInfo.setVTYPE(MI.getOperand(2).getImm()); 698 699 return NewInfo; 700 } 701 702 bool canSkipVSETVLIForLoadStore(const MachineInstr &MI, 703 const VSETVLIInfo &Require, 704 const VSETVLIInfo &CurInfo) { 705 unsigned EEW; 706 switch (MI.getOpcode()) { 707 default: 708 return false; 709 case RISCV::PseudoVLE8_V_M1: 710 case RISCV::PseudoVLE8_V_M1_MASK: 711 case RISCV::PseudoVLE8_V_M2: 712 case RISCV::PseudoVLE8_V_M2_MASK: 713 case RISCV::PseudoVLE8_V_M4: 714 case RISCV::PseudoVLE8_V_M4_MASK: 715 case RISCV::PseudoVLE8_V_M8: 716 case RISCV::PseudoVLE8_V_M8_MASK: 717 case RISCV::PseudoVLE8_V_MF2: 718 case RISCV::PseudoVLE8_V_MF2_MASK: 719 case RISCV::PseudoVLE8_V_MF4: 720 case RISCV::PseudoVLE8_V_MF4_MASK: 721 case RISCV::PseudoVLE8_V_MF8: 722 case RISCV::PseudoVLE8_V_MF8_MASK: 723 case RISCV::PseudoVLSE8_V_M1: 724 case RISCV::PseudoVLSE8_V_M1_MASK: 725 case RISCV::PseudoVLSE8_V_M2: 726 case RISCV::PseudoVLSE8_V_M2_MASK: 727 case RISCV::PseudoVLSE8_V_M4: 728 case RISCV::PseudoVLSE8_V_M4_MASK: 729 case RISCV::PseudoVLSE8_V_M8: 730 case RISCV::PseudoVLSE8_V_M8_MASK: 731 case RISCV::PseudoVLSE8_V_MF2: 732 case RISCV::PseudoVLSE8_V_MF2_MASK: 733 case RISCV::PseudoVLSE8_V_MF4: 734 case RISCV::PseudoVLSE8_V_MF4_MASK: 735 case RISCV::PseudoVLSE8_V_MF8: 736 case RISCV::PseudoVLSE8_V_MF8_MASK: 737 case RISCV::PseudoVSE8_V_M1: 738 case RISCV::PseudoVSE8_V_M1_MASK: 739 case RISCV::PseudoVSE8_V_M2: 740 case RISCV::PseudoVSE8_V_M2_MASK: 741 case RISCV::PseudoVSE8_V_M4: 742 case RISCV::PseudoVSE8_V_M4_MASK: 743 case RISCV::PseudoVSE8_V_M8: 744 case RISCV::PseudoVSE8_V_M8_MASK: 745 case RISCV::PseudoVSE8_V_MF2: 746 case RISCV::PseudoVSE8_V_MF2_MASK: 747 case RISCV::PseudoVSE8_V_MF4: 748 case RISCV::PseudoVSE8_V_MF4_MASK: 749 case RISCV::PseudoVSE8_V_MF8: 750 case RISCV::PseudoVSE8_V_MF8_MASK: 751 case RISCV::PseudoVSSE8_V_M1: 752 case RISCV::PseudoVSSE8_V_M1_MASK: 753 case RISCV::PseudoVSSE8_V_M2: 754 case RISCV::PseudoVSSE8_V_M2_MASK: 755 case RISCV::PseudoVSSE8_V_M4: 756 case RISCV::PseudoVSSE8_V_M4_MASK: 757 case RISCV::PseudoVSSE8_V_M8: 758 case RISCV::PseudoVSSE8_V_M8_MASK: 759 case RISCV::PseudoVSSE8_V_MF2: 760 case RISCV::PseudoVSSE8_V_MF2_MASK: 761 case RISCV::PseudoVSSE8_V_MF4: 762 case RISCV::PseudoVSSE8_V_MF4_MASK: 763 case RISCV::PseudoVSSE8_V_MF8: 764 case RISCV::PseudoVSSE8_V_MF8_MASK: 765 EEW = 8; 766 break; 767 case RISCV::PseudoVLE16_V_M1: 768 case RISCV::PseudoVLE16_V_M1_MASK: 769 case RISCV::PseudoVLE16_V_M2: 770 case RISCV::PseudoVLE16_V_M2_MASK: 771 case RISCV::PseudoVLE16_V_M4: 772 case RISCV::PseudoVLE16_V_M4_MASK: 773 case RISCV::PseudoVLE16_V_M8: 774 case RISCV::PseudoVLE16_V_M8_MASK: 775 case RISCV::PseudoVLE16_V_MF2: 776 case RISCV::PseudoVLE16_V_MF2_MASK: 777 case RISCV::PseudoVLE16_V_MF4: 778 case RISCV::PseudoVLE16_V_MF4_MASK: 779 case RISCV::PseudoVLSE16_V_M1: 780 case RISCV::PseudoVLSE16_V_M1_MASK: 781 case RISCV::PseudoVLSE16_V_M2: 782 case RISCV::PseudoVLSE16_V_M2_MASK: 783 case RISCV::PseudoVLSE16_V_M4: 784 case RISCV::PseudoVLSE16_V_M4_MASK: 785 case RISCV::PseudoVLSE16_V_M8: 786 case RISCV::PseudoVLSE16_V_M8_MASK: 787 case RISCV::PseudoVLSE16_V_MF2: 788 case RISCV::PseudoVLSE16_V_MF2_MASK: 789 case RISCV::PseudoVLSE16_V_MF4: 790 case RISCV::PseudoVLSE16_V_MF4_MASK: 791 case RISCV::PseudoVSE16_V_M1: 792 case RISCV::PseudoVSE16_V_M1_MASK: 793 case RISCV::PseudoVSE16_V_M2: 794 case RISCV::PseudoVSE16_V_M2_MASK: 795 case RISCV::PseudoVSE16_V_M4: 796 case RISCV::PseudoVSE16_V_M4_MASK: 797 case RISCV::PseudoVSE16_V_M8: 798 case RISCV::PseudoVSE16_V_M8_MASK: 799 case RISCV::PseudoVSE16_V_MF2: 800 case RISCV::PseudoVSE16_V_MF2_MASK: 801 case RISCV::PseudoVSE16_V_MF4: 802 case RISCV::PseudoVSE16_V_MF4_MASK: 803 case RISCV::PseudoVSSE16_V_M1: 804 case RISCV::PseudoVSSE16_V_M1_MASK: 805 case RISCV::PseudoVSSE16_V_M2: 806 case RISCV::PseudoVSSE16_V_M2_MASK: 807 case RISCV::PseudoVSSE16_V_M4: 808 case RISCV::PseudoVSSE16_V_M4_MASK: 809 case RISCV::PseudoVSSE16_V_M8: 810 case RISCV::PseudoVSSE16_V_M8_MASK: 811 case RISCV::PseudoVSSE16_V_MF2: 812 case RISCV::PseudoVSSE16_V_MF2_MASK: 813 case RISCV::PseudoVSSE16_V_MF4: 814 case RISCV::PseudoVSSE16_V_MF4_MASK: 815 EEW = 16; 816 break; 817 case RISCV::PseudoVLE32_V_M1: 818 case RISCV::PseudoVLE32_V_M1_MASK: 819 case RISCV::PseudoVLE32_V_M2: 820 case RISCV::PseudoVLE32_V_M2_MASK: 821 case RISCV::PseudoVLE32_V_M4: 822 case RISCV::PseudoVLE32_V_M4_MASK: 823 case RISCV::PseudoVLE32_V_M8: 824 case RISCV::PseudoVLE32_V_M8_MASK: 825 case RISCV::PseudoVLE32_V_MF2: 826 case RISCV::PseudoVLE32_V_MF2_MASK: 827 case RISCV::PseudoVLSE32_V_M1: 828 case RISCV::PseudoVLSE32_V_M1_MASK: 829 case RISCV::PseudoVLSE32_V_M2: 830 case RISCV::PseudoVLSE32_V_M2_MASK: 831 case RISCV::PseudoVLSE32_V_M4: 832 case RISCV::PseudoVLSE32_V_M4_MASK: 833 case RISCV::PseudoVLSE32_V_M8: 834 case RISCV::PseudoVLSE32_V_M8_MASK: 835 case RISCV::PseudoVLSE32_V_MF2: 836 case RISCV::PseudoVLSE32_V_MF2_MASK: 837 case RISCV::PseudoVSE32_V_M1: 838 case RISCV::PseudoVSE32_V_M1_MASK: 839 case RISCV::PseudoVSE32_V_M2: 840 case RISCV::PseudoVSE32_V_M2_MASK: 841 case RISCV::PseudoVSE32_V_M4: 842 case RISCV::PseudoVSE32_V_M4_MASK: 843 case RISCV::PseudoVSE32_V_M8: 844 case RISCV::PseudoVSE32_V_M8_MASK: 845 case RISCV::PseudoVSE32_V_MF2: 846 case RISCV::PseudoVSE32_V_MF2_MASK: 847 case RISCV::PseudoVSSE32_V_M1: 848 case RISCV::PseudoVSSE32_V_M1_MASK: 849 case RISCV::PseudoVSSE32_V_M2: 850 case RISCV::PseudoVSSE32_V_M2_MASK: 851 case RISCV::PseudoVSSE32_V_M4: 852 case RISCV::PseudoVSSE32_V_M4_MASK: 853 case RISCV::PseudoVSSE32_V_M8: 854 case RISCV::PseudoVSSE32_V_M8_MASK: 855 case RISCV::PseudoVSSE32_V_MF2: 856 case RISCV::PseudoVSSE32_V_MF2_MASK: 857 EEW = 32; 858 break; 859 case RISCV::PseudoVLE64_V_M1: 860 case RISCV::PseudoVLE64_V_M1_MASK: 861 case RISCV::PseudoVLE64_V_M2: 862 case RISCV::PseudoVLE64_V_M2_MASK: 863 case RISCV::PseudoVLE64_V_M4: 864 case RISCV::PseudoVLE64_V_M4_MASK: 865 case RISCV::PseudoVLE64_V_M8: 866 case RISCV::PseudoVLE64_V_M8_MASK: 867 case RISCV::PseudoVLSE64_V_M1: 868 case RISCV::PseudoVLSE64_V_M1_MASK: 869 case RISCV::PseudoVLSE64_V_M2: 870 case RISCV::PseudoVLSE64_V_M2_MASK: 871 case RISCV::PseudoVLSE64_V_M4: 872 case RISCV::PseudoVLSE64_V_M4_MASK: 873 case RISCV::PseudoVLSE64_V_M8: 874 case RISCV::PseudoVLSE64_V_M8_MASK: 875 case RISCV::PseudoVSE64_V_M1: 876 case RISCV::PseudoVSE64_V_M1_MASK: 877 case RISCV::PseudoVSE64_V_M2: 878 case RISCV::PseudoVSE64_V_M2_MASK: 879 case RISCV::PseudoVSE64_V_M4: 880 case RISCV::PseudoVSE64_V_M4_MASK: 881 case RISCV::PseudoVSE64_V_M8: 882 case RISCV::PseudoVSE64_V_M8_MASK: 883 case RISCV::PseudoVSSE64_V_M1: 884 case RISCV::PseudoVSSE64_V_M1_MASK: 885 case RISCV::PseudoVSSE64_V_M2: 886 case RISCV::PseudoVSSE64_V_M2_MASK: 887 case RISCV::PseudoVSSE64_V_M4: 888 case RISCV::PseudoVSSE64_V_M4_MASK: 889 case RISCV::PseudoVSSE64_V_M8: 890 case RISCV::PseudoVSSE64_V_M8_MASK: 891 EEW = 64; 892 break; 893 } 894 895 // Stores can ignore the tail and mask policies. 896 const bool StoreOp = MI.getNumExplicitDefs() == 0; 897 if (!StoreOp && !CurInfo.hasSamePolicy(Require)) 898 return false; 899 900 return CurInfo.isCompatibleWithLoadStoreEEW(EEW, Require); 901 } 902 903 /// Return true if a VSETVLI is required to transition from CurInfo to Require 904 /// before MI. Require corresponds to the result of computeInfoForInstr(MI...) 905 /// *before* we clear VLOp in phase3. We can't recompute and assert it here due 906 /// to that muation. 907 bool RISCVInsertVSETVLI::needVSETVLI(const MachineInstr &MI, 908 const VSETVLIInfo &Require, 909 const VSETVLIInfo &CurInfo) const { 910 if (CurInfo.isCompatible(MI, Require)) 911 return false; 912 913 // We didn't find a compatible value. If our AVL is a virtual register, 914 // it might be defined by a VSET(I)VLI. If it has the same VLMAX we need 915 // and the last VL/VTYPE we observed is the same, we don't need a 916 // VSETVLI here. 917 if (!CurInfo.isUnknown() && Require.hasAVLReg() && 918 Require.getAVLReg().isVirtual() && !CurInfo.hasSEWLMULRatioOnly() && 919 CurInfo.hasCompatibleVTYPE(MI, Require)) { 920 if (MachineInstr *DefMI = MRI->getVRegDef(Require.getAVLReg())) { 921 if (isVectorConfigInstr(*DefMI)) { 922 VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); 923 if (DefInfo.hasSameAVL(CurInfo) && DefInfo.hasSameVLMAX(CurInfo)) 924 return false; 925 } 926 } 927 } 928 929 // If this is a unit-stride or strided load/store, we may be able to use the 930 // EMUL=(EEW/SEW)*LMUL relationship to avoid changing VTYPE. 931 return CurInfo.isUnknown() || !canSkipVSETVLIForLoadStore(MI, Require, CurInfo); 932 } 933 934 bool RISCVInsertVSETVLI::computeVLVTYPEChanges(const MachineBasicBlock &MBB) { 935 bool HadVectorOp = false; 936 937 BlockData &BBInfo = BlockInfo[MBB.getNumber()]; 938 BBInfo.Change = BBInfo.Pred; 939 for (const MachineInstr &MI : MBB) { 940 // If this is an explicit VSETVLI or VSETIVLI, update our state. 941 if (isVectorConfigInstr(MI)) { 942 HadVectorOp = true; 943 BBInfo.Change = getInfoForVSETVLI(MI); 944 continue; 945 } 946 947 uint64_t TSFlags = MI.getDesc().TSFlags; 948 if (RISCVII::hasSEWOp(TSFlags)) { 949 HadVectorOp = true; 950 951 VSETVLIInfo NewInfo = computeInfoForInstr(MI, TSFlags, MRI); 952 953 if (!BBInfo.Change.isValid()) { 954 BBInfo.Change = NewInfo; 955 } else { 956 // If this instruction isn't compatible with the previous VL/VTYPE 957 // we need to insert a VSETVLI. 958 // NOTE: We only do this if the vtype we're comparing against was 959 // created in this block. We need the first and third phase to treat 960 // the store the same way. 961 if (needVSETVLI(MI, NewInfo, BBInfo.Change)) 962 BBInfo.Change = NewInfo; 963 } 964 } 965 966 // If this is something that updates VL/VTYPE that we don't know about, set 967 // the state to unknown. 968 if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VL) || 969 MI.modifiesRegister(RISCV::VTYPE)) 970 BBInfo.Change = VSETVLIInfo::getUnknown(); 971 } 972 973 return HadVectorOp; 974 } 975 976 void RISCVInsertVSETVLI::computeIncomingVLVTYPE(const MachineBasicBlock &MBB) { 977 978 BlockData &BBInfo = BlockInfo[MBB.getNumber()]; 979 980 BBInfo.InQueue = false; 981 982 VSETVLIInfo InInfo; 983 if (MBB.pred_empty()) { 984 // There are no predecessors, so use the default starting status. 985 InInfo.setUnknown(); 986 } else { 987 for (MachineBasicBlock *P : MBB.predecessors()) 988 InInfo = InInfo.intersect(BlockInfo[P->getNumber()].Exit); 989 } 990 991 // If we don't have any valid predecessor value, wait until we do. 992 if (!InInfo.isValid()) 993 return; 994 995 // If no change, no need to rerun block 996 if (InInfo == BBInfo.Pred) 997 return; 998 999 BBInfo.Pred = InInfo; 1000 LLVM_DEBUG(dbgs() << "Entry state of " << printMBBReference(MBB) 1001 << " changed to " << BBInfo.Pred << "\n"); 1002 1003 // Note: It's tempting to cache the state changes here, but due to the 1004 // compatibility checks performed a blocks output state can change based on 1005 // the input state. To cache, we'd have to add logic for finding 1006 // never-compatible state changes. 1007 computeVLVTYPEChanges(MBB); 1008 VSETVLIInfo TmpStatus = BBInfo.Change; 1009 1010 // If the new exit value matches the old exit value, we don't need to revisit 1011 // any blocks. 1012 if (BBInfo.Exit == TmpStatus) 1013 return; 1014 1015 BBInfo.Exit = TmpStatus; 1016 LLVM_DEBUG(dbgs() << "Exit state of " << printMBBReference(MBB) 1017 << " changed to " << BBInfo.Exit << "\n"); 1018 1019 // Add the successors to the work list so we can propagate the changed exit 1020 // status. 1021 for (MachineBasicBlock *S : MBB.successors()) 1022 if (!BlockInfo[S->getNumber()].InQueue) 1023 WorkList.push(S); 1024 } 1025 1026 // If we weren't able to prove a vsetvli was directly unneeded, it might still 1027 // be unneeded if the AVL is a phi node where all incoming values are VL 1028 // outputs from the last VSETVLI in their respective basic blocks. 1029 bool RISCVInsertVSETVLI::needVSETVLIPHI(const VSETVLIInfo &Require, 1030 const MachineBasicBlock &MBB) const { 1031 if (DisableInsertVSETVLPHIOpt) 1032 return true; 1033 1034 if (!Require.hasAVLReg()) 1035 return true; 1036 1037 Register AVLReg = Require.getAVLReg(); 1038 if (!AVLReg.isVirtual()) 1039 return true; 1040 1041 // We need the AVL to be produce by a PHI node in this basic block. 1042 MachineInstr *PHI = MRI->getVRegDef(AVLReg); 1043 if (!PHI || PHI->getOpcode() != RISCV::PHI || PHI->getParent() != &MBB) 1044 return true; 1045 1046 for (unsigned PHIOp = 1, NumOps = PHI->getNumOperands(); PHIOp != NumOps; 1047 PHIOp += 2) { 1048 Register InReg = PHI->getOperand(PHIOp).getReg(); 1049 MachineBasicBlock *PBB = PHI->getOperand(PHIOp + 1).getMBB(); 1050 const BlockData &PBBInfo = BlockInfo[PBB->getNumber()]; 1051 // If the exit from the predecessor has the VTYPE we are looking for 1052 // we might be able to avoid a VSETVLI. 1053 if (PBBInfo.Exit.isUnknown() || !PBBInfo.Exit.hasSameVTYPE(Require)) 1054 return true; 1055 1056 // We need the PHI input to the be the output of a VSET(I)VLI. 1057 MachineInstr *DefMI = MRI->getVRegDef(InReg); 1058 if (!DefMI || !isVectorConfigInstr(*DefMI)) 1059 return true; 1060 1061 // We found a VSET(I)VLI make sure it matches the output of the 1062 // predecessor block. 1063 VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); 1064 if (!DefInfo.hasSameAVL(PBBInfo.Exit) || 1065 !DefInfo.hasSameVTYPE(PBBInfo.Exit)) 1066 return true; 1067 } 1068 1069 // If all the incoming values to the PHI checked out, we don't need 1070 // to insert a VSETVLI. 1071 return false; 1072 } 1073 1074 void RISCVInsertVSETVLI::emitVSETVLIs(MachineBasicBlock &MBB) { 1075 VSETVLIInfo CurInfo; 1076 for (MachineInstr &MI : MBB) { 1077 // If this is an explicit VSETVLI or VSETIVLI, update our state. 1078 if (isVectorConfigInstr(MI)) { 1079 // Conservatively, mark the VL and VTYPE as live. 1080 assert(MI.getOperand(3).getReg() == RISCV::VL && 1081 MI.getOperand(4).getReg() == RISCV::VTYPE && 1082 "Unexpected operands where VL and VTYPE should be"); 1083 MI.getOperand(3).setIsDead(false); 1084 MI.getOperand(4).setIsDead(false); 1085 CurInfo = getInfoForVSETVLI(MI); 1086 continue; 1087 } 1088 1089 uint64_t TSFlags = MI.getDesc().TSFlags; 1090 if (RISCVII::hasSEWOp(TSFlags)) { 1091 VSETVLIInfo NewInfo = computeInfoForInstr(MI, TSFlags, MRI); 1092 if (RISCVII::hasVLOp(TSFlags)) { 1093 MachineOperand &VLOp = MI.getOperand(getVLOpNum(MI)); 1094 if (VLOp.isReg()) { 1095 // Erase the AVL operand from the instruction. 1096 VLOp.setReg(RISCV::NoRegister); 1097 VLOp.setIsKill(false); 1098 } 1099 MI.addOperand(MachineOperand::CreateReg(RISCV::VL, /*isDef*/ false, 1100 /*isImp*/ true)); 1101 } 1102 MI.addOperand(MachineOperand::CreateReg(RISCV::VTYPE, /*isDef*/ false, 1103 /*isImp*/ true)); 1104 1105 if (!CurInfo.isValid()) { 1106 // We haven't found any vector instructions or VL/VTYPE changes yet, 1107 // use the predecessor information. 1108 CurInfo = BlockInfo[MBB.getNumber()].Pred; 1109 assert(CurInfo.isValid() && "Expected a valid predecessor state."); 1110 if (needVSETVLI(MI, NewInfo, CurInfo)) { 1111 // If this is the first implicit state change, and the state change 1112 // requested can be proven to produce the same register contents, we 1113 // can skip emitting the actual state change and continue as if we 1114 // had since we know the GPR result of the implicit state change 1115 // wouldn't be used and VL/VTYPE registers are correct. Note that 1116 // we *do* need to model the state as if it changed as while the 1117 // register contents are unchanged, the abstract model can change. 1118 if (needVSETVLIPHI(NewInfo, MBB)) 1119 insertVSETVLI(MBB, MI, NewInfo, CurInfo); 1120 CurInfo = NewInfo; 1121 } 1122 } else { 1123 // If this instruction isn't compatible with the previous VL/VTYPE 1124 // we need to insert a VSETVLI. 1125 // NOTE: We can't use predecessor information for the store. We must 1126 // treat it the same as the first phase so that we produce the correct 1127 // vl/vtype for succesor blocks. 1128 if (needVSETVLI(MI, NewInfo, CurInfo)) { 1129 insertVSETVLI(MBB, MI, NewInfo, CurInfo); 1130 CurInfo = NewInfo; 1131 } 1132 } 1133 } 1134 1135 // If this is something that updates VL/VTYPE that we don't know about, set 1136 // the state to unknown. 1137 if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VL) || 1138 MI.modifiesRegister(RISCV::VTYPE)) { 1139 CurInfo = VSETVLIInfo::getUnknown(); 1140 } 1141 } 1142 1143 // If we reach the end of the block and our current info doesn't match the 1144 // expected info, insert a vsetvli to correct. 1145 if (!UseStrictAsserts) { 1146 const VSETVLIInfo &ExitInfo = BlockInfo[MBB.getNumber()].Exit; 1147 if (CurInfo.isValid() && ExitInfo.isValid() && !ExitInfo.isUnknown() && 1148 CurInfo != ExitInfo) { 1149 // Note there's an implicit assumption here that terminators never use 1150 // or modify VL or VTYPE. Also, fallthrough will return end(). 1151 auto InsertPt = MBB.getFirstInstrTerminator(); 1152 insertVSETVLI(MBB, InsertPt, MBB.findDebugLoc(InsertPt), ExitInfo, 1153 CurInfo); 1154 CurInfo = ExitInfo; 1155 } 1156 } 1157 1158 if (UseStrictAsserts && CurInfo.isValid()) { 1159 const auto &Info = BlockInfo[MBB.getNumber()]; 1160 if (CurInfo != Info.Exit) { 1161 LLVM_DEBUG(dbgs() << "in block " << printMBBReference(MBB) << "\n"); 1162 LLVM_DEBUG(dbgs() << " begin state: " << Info.Pred << "\n"); 1163 LLVM_DEBUG(dbgs() << " expected end state: " << Info.Exit << "\n"); 1164 LLVM_DEBUG(dbgs() << " actual end state: " << CurInfo << "\n"); 1165 } 1166 assert(CurInfo == Info.Exit && 1167 "InsertVSETVLI dataflow invariant violated"); 1168 } 1169 } 1170 1171 void RISCVInsertVSETVLI::doLocalPrepass(MachineBasicBlock &MBB) { 1172 VSETVLIInfo CurInfo = VSETVLIInfo::getUnknown(); 1173 for (MachineInstr &MI : MBB) { 1174 // If this is an explicit VSETVLI or VSETIVLI, update our state. 1175 if (isVectorConfigInstr(MI)) { 1176 CurInfo = getInfoForVSETVLI(MI); 1177 continue; 1178 } 1179 1180 const uint64_t TSFlags = MI.getDesc().TSFlags; 1181 if (isScalarMoveInstr(MI)) { 1182 assert(RISCVII::hasSEWOp(TSFlags) && RISCVII::hasVLOp(TSFlags)); 1183 const VSETVLIInfo NewInfo = computeInfoForInstr(MI, TSFlags, MRI); 1184 1185 // For vmv.s.x and vfmv.s.f, there are only two behaviors, VL = 0 and 1186 // VL > 0. We can discard the user requested AVL and just use the last 1187 // one if we can prove it equally zero. This removes a vsetvli entirely 1188 // if the types match or allows use of cheaper avl preserving variant 1189 // if VLMAX doesn't change. If VLMAX might change, we couldn't use 1190 // the 'vsetvli x0, x0, vtype" variant, so we avoid the transform to 1191 // prevent extending live range of an avl register operand. 1192 // TODO: We can probably relax this for immediates. 1193 if (((CurInfo.hasNonZeroAVL() && NewInfo.hasNonZeroAVL()) || 1194 (CurInfo.hasZeroAVL() && NewInfo.hasZeroAVL())) && 1195 NewInfo.hasSameVLMAX(CurInfo)) { 1196 MachineOperand &VLOp = MI.getOperand(getVLOpNum(MI)); 1197 if (CurInfo.hasAVLImm()) 1198 VLOp.ChangeToImmediate(CurInfo.getAVLImm()); 1199 else 1200 VLOp.ChangeToRegister(CurInfo.getAVLReg(), /*IsDef*/ false); 1201 CurInfo = computeInfoForInstr(MI, TSFlags, MRI); 1202 continue; 1203 } 1204 } 1205 1206 if (RISCVII::hasSEWOp(TSFlags)) { 1207 if (RISCVII::hasVLOp(TSFlags)) { 1208 const auto Require = computeInfoForInstr(MI, TSFlags, MRI); 1209 // If the AVL is the result of a previous vsetvli which has the 1210 // same AVL and VLMAX as our current state, we can reuse the AVL 1211 // from the current state for the new one. This allows us to 1212 // generate 'vsetvli x0, x0, vtype" or possible skip the transition 1213 // entirely. 1214 if (!CurInfo.isUnknown() && Require.hasAVLReg() && 1215 Require.getAVLReg().isVirtual()) { 1216 if (MachineInstr *DefMI = MRI->getVRegDef(Require.getAVLReg())) { 1217 if (isVectorConfigInstr(*DefMI)) { 1218 VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); 1219 if (DefInfo.hasSameAVL(CurInfo) && 1220 DefInfo.hasSameVLMAX(CurInfo)) { 1221 MachineOperand &VLOp = MI.getOperand(getVLOpNum(MI)); 1222 if (CurInfo.hasAVLImm()) 1223 VLOp.ChangeToImmediate(CurInfo.getAVLImm()); 1224 else { 1225 MRI->clearKillFlags(CurInfo.getAVLReg()); 1226 VLOp.ChangeToRegister(CurInfo.getAVLReg(), /*IsDef*/ false); 1227 } 1228 CurInfo = computeInfoForInstr(MI, TSFlags, MRI); 1229 continue; 1230 } 1231 } 1232 } 1233 } 1234 1235 // If AVL is defined by a vsetvli with the same VLMAX, we can 1236 // replace the AVL operand with the AVL of the defining vsetvli. 1237 // We avoid general register AVLs to avoid extending live ranges 1238 // without being sure we can kill the original source reg entirely. 1239 // TODO: We can ignore policy bits here, we only need VL to be the same. 1240 if (Require.hasAVLReg() && Require.getAVLReg().isVirtual()) { 1241 if (MachineInstr *DefMI = MRI->getVRegDef(Require.getAVLReg())) { 1242 if (isVectorConfigInstr(*DefMI)) { 1243 VSETVLIInfo DefInfo = getInfoForVSETVLI(*DefMI); 1244 if (DefInfo.hasSameVLMAX(Require) && 1245 (DefInfo.hasAVLImm() || DefInfo.getAVLReg() == RISCV::X0)) { 1246 MachineOperand &VLOp = MI.getOperand(getVLOpNum(MI)); 1247 if (DefInfo.hasAVLImm()) 1248 VLOp.ChangeToImmediate(DefInfo.getAVLImm()); 1249 else 1250 VLOp.ChangeToRegister(DefInfo.getAVLReg(), /*IsDef*/ false); 1251 CurInfo = computeInfoForInstr(MI, TSFlags, MRI); 1252 continue; 1253 } 1254 } 1255 } 1256 } 1257 } 1258 CurInfo = computeInfoForInstr(MI, TSFlags, MRI); 1259 continue; 1260 } 1261 1262 // If this is something that updates VL/VTYPE that we don't know about, 1263 // set the state to unknown. 1264 if (MI.isCall() || MI.isInlineAsm() || MI.modifiesRegister(RISCV::VL) || 1265 MI.modifiesRegister(RISCV::VTYPE)) 1266 CurInfo = VSETVLIInfo::getUnknown(); 1267 } 1268 } 1269 1270 /// Return true if the VL value configured must be equal to the requested one. 1271 static bool hasFixedResult(const VSETVLIInfo &Info, const RISCVSubtarget &ST) { 1272 if (!Info.hasAVLImm()) 1273 // VLMAX is always the same value. 1274 // TODO: Could extend to other registers by looking at the associated vreg 1275 // def placement. 1276 return RISCV::X0 == Info.getAVLReg(); 1277 1278 unsigned AVL = Info.getAVLImm(); 1279 unsigned SEW = Info.getSEW(); 1280 unsigned AVLInBits = AVL * SEW; 1281 1282 unsigned LMul; 1283 bool Fractional; 1284 std::tie(LMul, Fractional) = RISCVVType::decodeVLMUL(Info.getVLMUL()); 1285 1286 if (Fractional) 1287 return ST.getRealMinVLen() / LMul >= AVLInBits; 1288 return ST.getRealMinVLen() * LMul >= AVLInBits; 1289 } 1290 1291 /// Perform simple partial redundancy elimination of the VSETVLI instructions 1292 /// we're about to insert by looking for cases where we can PRE from the 1293 /// beginning of one block to the end of one of its predecessors. Specifically, 1294 /// this is geared to catch the common case of a fixed length vsetvl in a single 1295 /// block loop when it could execute once in the preheader instead. 1296 void RISCVInsertVSETVLI::doPRE(MachineBasicBlock &MBB) { 1297 const MachineFunction &MF = *MBB.getParent(); 1298 const RISCVSubtarget &ST = MF.getSubtarget<RISCVSubtarget>(); 1299 1300 if (!BlockInfo[MBB.getNumber()].Pred.isUnknown()) 1301 return; 1302 1303 MachineBasicBlock *UnavailablePred = nullptr; 1304 VSETVLIInfo AvailableInfo; 1305 for (MachineBasicBlock *P : MBB.predecessors()) { 1306 const VSETVLIInfo &PredInfo = BlockInfo[P->getNumber()].Exit; 1307 if (PredInfo.isUnknown()) { 1308 if (UnavailablePred) 1309 return; 1310 UnavailablePred = P; 1311 } else if (!AvailableInfo.isValid()) { 1312 AvailableInfo = PredInfo; 1313 } else if (AvailableInfo != PredInfo) { 1314 return; 1315 } 1316 } 1317 1318 // Unreachable, single pred, or full redundancy. Note that FRE is handled by 1319 // phase 3. 1320 if (!UnavailablePred || !AvailableInfo.isValid()) 1321 return; 1322 1323 // Critical edge - TODO: consider splitting? 1324 if (UnavailablePred->succ_size() != 1) 1325 return; 1326 1327 // If VL can be less than AVL, then we can't reduce the frequency of exec. 1328 if (!hasFixedResult(AvailableInfo, ST)) 1329 return; 1330 1331 // Does it actually let us remove an implicit transition in MBB? 1332 bool Found = false; 1333 for (auto &MI : MBB) { 1334 if (isVectorConfigInstr(MI)) 1335 return; 1336 1337 const uint64_t TSFlags = MI.getDesc().TSFlags; 1338 if (RISCVII::hasSEWOp(TSFlags)) { 1339 if (AvailableInfo != computeInfoForInstr(MI, TSFlags, MRI)) 1340 return; 1341 Found = true; 1342 break; 1343 } 1344 } 1345 if (!Found) 1346 return; 1347 1348 // Finally, update both data flow state and insert the actual vsetvli. 1349 // Doing both keeps the code in sync with the dataflow results, which 1350 // is critical for correctness of phase 3. 1351 auto OldInfo = BlockInfo[UnavailablePred->getNumber()].Exit; 1352 LLVM_DEBUG(dbgs() << "PRE VSETVLI from " << MBB.getName() << " to " 1353 << UnavailablePred->getName() << " with state " 1354 << AvailableInfo << "\n"); 1355 BlockInfo[UnavailablePred->getNumber()].Exit = AvailableInfo; 1356 BlockInfo[MBB.getNumber()].Pred = AvailableInfo; 1357 1358 // Note there's an implicit assumption here that terminators never use 1359 // or modify VL or VTYPE. Also, fallthrough will return end(). 1360 auto InsertPt = UnavailablePred->getFirstInstrTerminator(); 1361 insertVSETVLI(*UnavailablePred, InsertPt, 1362 UnavailablePred->findDebugLoc(InsertPt), 1363 AvailableInfo, OldInfo); 1364 } 1365 1366 void RISCVInsertVSETVLI::doLocalPostpass(MachineBasicBlock &MBB) { 1367 MachineInstr *PrevMI = nullptr; 1368 bool UsedVL = false, UsedVTYPE = false; 1369 SmallVector<MachineInstr*> ToDelete; 1370 for (MachineInstr &MI : MBB) { 1371 // Note: Must be *before* vsetvli handling to account for config cases 1372 // which only change some subfields. 1373 if (MI.isCall() || MI.isInlineAsm() || MI.readsRegister(RISCV::VL)) 1374 UsedVL = true; 1375 if (MI.isCall() || MI.isInlineAsm() || MI.readsRegister(RISCV::VTYPE)) 1376 UsedVTYPE = true; 1377 1378 if (!isVectorConfigInstr(MI)) 1379 continue; 1380 1381 if (PrevMI) { 1382 if (!UsedVL && !UsedVTYPE) { 1383 ToDelete.push_back(PrevMI); 1384 // fallthrough 1385 } else if (!UsedVTYPE && isVLPreservingConfig(MI)) { 1386 // Note: `vsetvli x0, x0, vtype' is the canonical instruction 1387 // for this case. If you find yourself wanting to add other forms 1388 // to this "unused VTYPE" case, we're probably missing a 1389 // canonicalization earlier. 1390 // Note: We don't need to explicitly check vtype compatibility 1391 // here because this form is only legal (per ISA) when not 1392 // changing VL. 1393 PrevMI->getOperand(2).setImm(MI.getOperand(2).getImm()); 1394 ToDelete.push_back(&MI); 1395 // Leave PrevMI unchanged 1396 continue; 1397 } 1398 } 1399 PrevMI = &MI; 1400 UsedVL = false; 1401 UsedVTYPE = false; 1402 Register VRegDef = MI.getOperand(0).getReg(); 1403 if (VRegDef != RISCV::X0 && 1404 !(VRegDef.isVirtual() && MRI->use_nodbg_empty(VRegDef))) 1405 UsedVL = true; 1406 } 1407 1408 for (auto *MI : ToDelete) 1409 MI->eraseFromParent(); 1410 } 1411 1412 bool RISCVInsertVSETVLI::runOnMachineFunction(MachineFunction &MF) { 1413 // Skip if the vector extension is not enabled. 1414 const RISCVSubtarget &ST = MF.getSubtarget<RISCVSubtarget>(); 1415 if (!ST.hasVInstructions()) 1416 return false; 1417 1418 LLVM_DEBUG(dbgs() << "Entering InsertVSETVLI for " << MF.getName() << "\n"); 1419 1420 TII = ST.getInstrInfo(); 1421 MRI = &MF.getRegInfo(); 1422 1423 assert(BlockInfo.empty() && "Expect empty block infos"); 1424 BlockInfo.resize(MF.getNumBlockIDs()); 1425 1426 // Scan the block locally for cases where we can mutate the operands 1427 // of the instructions to reduce state transitions. Critically, this 1428 // must be done before we start propagating data flow states as these 1429 // transforms are allowed to change the contents of VTYPE and VL so 1430 // long as the semantics of the program stays the same. 1431 for (MachineBasicBlock &MBB : MF) 1432 doLocalPrepass(MBB); 1433 1434 bool HaveVectorOp = false; 1435 1436 // Phase 1 - determine how VL/VTYPE are affected by the each block. 1437 for (const MachineBasicBlock &MBB : MF) { 1438 HaveVectorOp |= computeVLVTYPEChanges(MBB); 1439 // Initial exit state is whatever change we found in the block. 1440 BlockData &BBInfo = BlockInfo[MBB.getNumber()]; 1441 BBInfo.Exit = BBInfo.Change; 1442 LLVM_DEBUG(dbgs() << "Initial exit state of " << printMBBReference(MBB) 1443 << " is " << BBInfo.Exit << "\n"); 1444 1445 } 1446 1447 // If we didn't find any instructions that need VSETVLI, we're done. 1448 if (!HaveVectorOp) { 1449 BlockInfo.clear(); 1450 return false; 1451 } 1452 1453 // Phase 2 - determine the exit VL/VTYPE from each block. We add all 1454 // blocks to the list here, but will also add any that need to be revisited 1455 // during Phase 2 processing. 1456 for (const MachineBasicBlock &MBB : MF) { 1457 WorkList.push(&MBB); 1458 BlockInfo[MBB.getNumber()].InQueue = true; 1459 } 1460 while (!WorkList.empty()) { 1461 const MachineBasicBlock &MBB = *WorkList.front(); 1462 WorkList.pop(); 1463 computeIncomingVLVTYPE(MBB); 1464 } 1465 1466 // Perform partial redundancy elimination of vsetvli transitions. 1467 for (MachineBasicBlock &MBB : MF) 1468 doPRE(MBB); 1469 1470 // Phase 3 - add any vsetvli instructions needed in the block. Use the 1471 // Phase 2 information to avoid adding vsetvlis before the first vector 1472 // instruction in the block if the VL/VTYPE is satisfied by its 1473 // predecessors. 1474 for (MachineBasicBlock &MBB : MF) 1475 emitVSETVLIs(MBB); 1476 1477 // Now that all vsetvlis are explicit, go through and do block local 1478 // DSE and peephole based demanded fields based transforms. Note that 1479 // this *must* be done outside the main dataflow so long as we allow 1480 // any cross block analysis within the dataflow. We can't have both 1481 // demanded fields based mutation and non-local analysis in the 1482 // dataflow at the same time without introducing inconsistencies. 1483 for (MachineBasicBlock &MBB : MF) 1484 doLocalPostpass(MBB); 1485 1486 // Once we're fully done rewriting all the instructions, do a final pass 1487 // through to check for VSETVLIs which write to an unused destination. 1488 // For the non X0, X0 variant, we can replace the destination register 1489 // with X0 to reduce register pressure. This is really a generic 1490 // optimization which can be applied to any dead def (TODO: generalize). 1491 for (MachineBasicBlock &MBB : MF) { 1492 for (MachineInstr &MI : MBB) { 1493 if (MI.getOpcode() == RISCV::PseudoVSETVLI || 1494 MI.getOpcode() == RISCV::PseudoVSETIVLI) { 1495 Register VRegDef = MI.getOperand(0).getReg(); 1496 if (VRegDef != RISCV::X0 && MRI->use_nodbg_empty(VRegDef)) 1497 MI.getOperand(0).setReg(RISCV::X0); 1498 } 1499 } 1500 } 1501 1502 BlockInfo.clear(); 1503 return HaveVectorOp; 1504 } 1505 1506 /// Returns an instance of the Insert VSETVLI pass. 1507 FunctionPass *llvm::createRISCVInsertVSETVLIPass() { 1508 return new RISCVInsertVSETVLI(); 1509 } 1510