LLVM: lib/Target/RISCV/RISCVVectorPeephole.cpp Source File (original) (raw)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
36
37using namespace llvm;
38
39#define DEBUG_TYPE "riscv-vector-peephole"
40
41namespace {
42
44public:
45 static char ID;
51
55 }
56
57 StringRef getPassName() const override {
58 return "RISC-V Vector Peephole Optimization";
59 }
60
61private:
66 bool convertAllOnesVMergeToVMv(MachineInstr &MI) const;
71
73 bool isAllOnesMask(const MachineInstr *MaskDef) const;
77};
78
79}
80
81char RISCVVectorPeephole::ID = 0;
82
84 false)
85
86
87
90 unsigned UserLog2SEW =
92 unsigned SrcLog2SEW =
96 return SrcLog2EEW == UserLog2SEW;
97}
98
99
100
101
102bool RISCVVectorPeephole::tryToReduceVL(MachineInstr &MI) const {
103
104
105
106
107
108
109
110
111
112
113
114
115
116 SmallVector<unsigned, 2> SrcIndices = {0};
118 default:
119 return false;
120 case RISCV::VSE8_V:
121 case RISCV::VSE16_V:
122 case RISCV::VSE32_V:
123 case RISCV::VSE64_V:
124 break;
125 case RISCV::VMV_V_V:
126 SrcIndices[0] = 2;
127 break;
128 case RISCV::VMERGE_VVM:
129 SrcIndices.assign({2, 3});
130 break;
131 case RISCV::VREDSUM_VS:
132 case RISCV::VREDMAXU_VS:
133 case RISCV::VREDMAX_VS:
134 case RISCV::VREDMINU_VS:
135 case RISCV::VREDMIN_VS:
136 case RISCV::VREDAND_VS:
137 case RISCV::VREDOR_VS:
138 case RISCV::VREDXOR_VS:
139 case RISCV::VWREDSUM_VS:
140 case RISCV::VWREDSUMU_VS:
141 case RISCV::VFREDUSUM_VS:
142 case RISCV::VFREDOSUM_VS:
143 case RISCV::VFREDMAX_VS:
144 case RISCV::VFREDMIN_VS:
145 case RISCV::VFWREDUSUM_VS:
146 case RISCV::VFWREDOSUM_VS:
147 SrcIndices[0] = 2;
148 break;
149 }
150
153 return false;
154
156 for (unsigned SrcIdx : SrcIndices) {
157 Register SrcReg = MI.getOperand(SrcIdx).getReg();
158
159 if (->hasOneUse(SrcReg))
160 continue;
161
162 MachineInstr *Src = MRI->getVRegDef(SrcReg);
163 if (!Src || Src->hasUnmodeledSideEffects() ||
164 Src->getParent() != MI.getParent() || Src->getNumDefs() != 1 ||
167 continue;
168
169
170 if (!hasSameEEW(MI, *Src))
171 continue;
172
175 if (ElementsDependOnVL || Src->mayRaiseFPException())
176 continue;
177
178 MachineOperand &SrcVL =
181 continue;
182
183 if (!ensureDominates(VL, *Src))
184 continue;
185
188 else if (VL.isReg())
190
192 }
193
194
195
197}
198
199
200std::optional
201RISCVVectorPeephole::getConstant(const MachineOperand &VL) const {
204
205 MachineInstr *Def = MRI->getVRegDef(VL.getReg());
206 if (!Def || Def->getOpcode() != RISCV::ADDI ||
207 Def->getOperand(1).getReg() != RISCV::X0)
208 return std::nullopt;
209 return Def->getOperand(2).getImm();
210}
211
212
213bool RISCVVectorPeephole::convertToVLMAX(MachineInstr &MI) const {
216 return false;
217
219
220 unsigned LMULFixed = LMUL.second ? (8 / LMUL.first) : 8 * LMUL.first;
222
223 unsigned SEW = Log2SEW ? 1 << Log2SEW : 8;
225 assert(8 * LMULFixed / SEW > 0);
226
227
230 VLen && AVL && (*VLen * LMULFixed) / SEW == *AVL * 8) {
232 return true;
233 }
234
235
236
238 return false;
239 MachineInstr *Def = MRI->getVRegDef(VL.getReg());
240 if (!Def)
241 return false;
242
243
244 uint64_t ScaleFixed = 8;
245
246 if (Def->getOpcode() == RISCV::SLLI) {
247 assert(Def->getOperand(2).getImm() < 64);
248 ScaleFixed <<= Def->getOperand(2).getImm();
249 Def = MRI->getVRegDef(Def->getOperand(1).getReg());
250 } else if (Def->getOpcode() == RISCV::SRLI) {
251 assert(Def->getOperand(2).getImm() < 64);
252 ScaleFixed >>= Def->getOperand(2).getImm();
253 Def = MRI->getVRegDef(Def->getOperand(1).getReg());
254 }
255
256 if (!Def || Def->getOpcode() != RISCV::PseudoReadVLENB)
257 return false;
258
259
260
261
262
263
264
265
266 if (ScaleFixed != 8 * LMULFixed / SEW)
267 return false;
268
270
271 return true;
272}
273
274bool RISCVVectorPeephole::isAllOnesMask(const MachineInstr *MaskDef) const {
277
278
279
280
282 case RISCV::PseudoVMSET_M_B1:
283 case RISCV::PseudoVMSET_M_B2:
284 case RISCV::PseudoVMSET_M_B4:
285 case RISCV::PseudoVMSET_M_B8:
286 case RISCV::PseudoVMSET_M_B16:
287 case RISCV::PseudoVMSET_M_B32:
288 case RISCV::PseudoVMSET_M_B64:
289 return true;
290 default:
291 return false;
292 }
293}
294
295
296
297
298
299
300
301
302
303
304
305bool RISCVVectorPeephole::convertToWholeRegister(MachineInstr &MI) const {
306#define CASE_WHOLE_REGISTER_LMUL_SEW(lmul, sew) \
307 case RISCV::PseudoVLE##sew##_V_M##lmul: \
308 NewOpc = RISCV::VL##lmul##RE##sew##_V; \
309 break; \
310 case RISCV::PseudoVSE##sew##_V_M##lmul: \
311 NewOpc = RISCV::VS##lmul##R_V; \
312 break;
313#define CASE_WHOLE_REGISTER_LMUL(lmul) \
314 CASE_WHOLE_REGISTER_LMUL_SEW(lmul, 8) \
315 CASE_WHOLE_REGISTER_LMUL_SEW(lmul, 16) \
316 CASE_WHOLE_REGISTER_LMUL_SEW(lmul, 32) \
317 CASE_WHOLE_REGISTER_LMUL_SEW(lmul, 64)
318
319 unsigned NewOpc;
320 switch (MI.getOpcode()) {
325 default:
326 return false;
327 }
328
329 MachineOperand &VLOp = MI.getOperand(RISCVII::getVLOpNum(MI.getDesc()));
330 if (!VLOp.isImm() || VLOp.getImm() != RISCV::VLMaxSentinel)
331 return false;
332
333
334
335 if (RISCVII::hasVecPolicyOp(MI.getDesc().TSFlags))
336 MI.removeOperand(RISCVII::getVecPolicyOpNum(MI.getDesc()));
337 MI.removeOperand(RISCVII::getSEWOpNum(MI.getDesc()));
338 MI.removeOperand(RISCVII::getVLOpNum(MI.getDesc()));
339 if (RISCVII::isFirstDefTiedToFirstUse(MI.getDesc()))
340 MI.removeOperand(1);
341
342 MI.setDesc(TII->get(NewOpc));
343
344 return true;
345}
346
347static unsigned getVMV_V_VOpcodeForVMERGE_VVM(const MachineInstr &MI) {
348#define CASE_VMERGE_TO_VMV(lmul) \
349 case RISCV::PseudoVMERGE_VVM_##lmul: \
350 return RISCV::PseudoVMV_V_V_##lmul;
351 switch (MI.getOpcode()) {
352 default:
353 return 0;
354 CASE_VMERGE_TO_VMV(MF8)
355 CASE_VMERGE_TO_VMV(MF4)
356 CASE_VMERGE_TO_VMV(MF2)
357 CASE_VMERGE_TO_VMV(M1)
358 CASE_VMERGE_TO_VMV(M2)
359 CASE_VMERGE_TO_VMV(M4)
360 CASE_VMERGE_TO_VMV(M8)
361 }
362}
363
364
365
366
367
368
369bool RISCVVectorPeephole::convertAllOnesVMergeToVMv(MachineInstr &MI) const {
370 unsigned NewOpc = getVMV_V_VOpcodeForVMERGE_VVM(MI);
371 if (!NewOpc)
372 return false;
373 if (!isAllOnesMask(MRI->getVRegDef(MI.getOperand(4).getReg())))
374 return false;
375
376 MI.setDesc(TII->get(NewOpc));
377 MI.removeOperand(2);
378 MI.removeOperand(3);
379 MI.addOperand(
381
382
383
384 MRI->recomputeRegClass(MI.getOperand(0).getReg());
385 if (MI.getOperand(1).getReg().isValid())
386 MRI->recomputeRegClass(MI.getOperand(1).getReg());
387 return true;
388}
389
390
391
393 bool OneUseOnly) const {
394 while (MachineInstr *Def = MRI->getUniqueVRegDef(Reg)) {
395 if (->isFullCopy())
396 break;
397 Register Src = Def->getOperand(1).getReg();
398 if (!Src.isVirtual())
399 break;
400 if (OneUseOnly && ->hasOneNonDBGUse(Reg))
401 break;
402 Reg = Src;
403 }
404 return Reg;
405}
406
407
408
409
410
411
412
413
414
415
416bool RISCVVectorPeephole::convertSameMaskVMergeToVMv(MachineInstr &MI) {
417 unsigned NewOpc = getVMV_V_VOpcodeForVMERGE_VVM(MI);
418 if (!NewOpc)
419 return false;
420 MachineInstr *True = MRI->getVRegDef(MI.getOperand(3).getReg());
421
422 if (!True || True->getParent() != MI.getParent())
423 return false;
424
425 auto *TrueMaskedInfo = RISCV::getMaskedPseudoInfo(True->getOpcode());
426 if (!TrueMaskedInfo || !hasSameEEW(MI, *True))
427 return false;
428
429 Register TrueMaskReg = lookThruCopies(
432 Register MIMaskReg = lookThruCopies(MI.getOperand(4).getReg());
433 if (!TrueMaskReg.isVirtual() || TrueMaskReg != MIMaskReg)
434 return false;
435
436
437
438
440 const MachineOperand &TrueVL =
443 return false;
444
445
447 Register FalseReg = MI.getOperand(2).getReg();
448 if (TruePassthruReg != FalseReg) {
449
450 if (TruePassthruReg.isValid() ||
451 ->hasOneUse(MI.getOperand(3).getReg()) ||
452 !ensureDominates(MI.getOperand(2), *True))
453 return false;
455
457 TII->getRegClass(True->getDesc(), 1));
458 }
459
460 MI.setDesc(TII->get(NewOpc));
461 MI.removeOperand(2);
462 MI.removeOperand(3);
463 MI.addOperand(
465
466
467
468 MRI->recomputeRegClass(MI.getOperand(0).getReg());
469 if (MI.getOperand(1).getReg().isValid())
470 MRI->recomputeRegClass(MI.getOperand(1).getReg());
471 return true;
472}
473
474bool RISCVVectorPeephole::convertToUnmasked(MachineInstr &MI) const {
475 const RISCV::RISCVMaskedPseudoInfo *I =
476 RISCV::getMaskedPseudoInfo(MI.getOpcode());
477 if ()
478 return false;
479
480 if (!isAllOnesMask(MRI->getVRegDef(
481 MI.getOperand(I->MaskOpIdx + MI.getNumExplicitDefs()).getReg())))
482 return false;
483
484
485
486 const unsigned Opc = I->UnmaskedPseudo;
487 const MCInstrDesc &MCID = TII->get(Opc);
488 [[maybe_unused]] const bool HasPolicyOp =
491 const MCInstrDesc &MaskedMCID = TII->get(MI.getOpcode());
494 "Unmasked pseudo has policy but masked pseudo doesn't?");
495 assert(HasPolicyOp == HasPassthru && "Unexpected pseudo structure");
497 "Unmasked with passthru but masked with no passthru?");
498 (void)HasPolicyOp;
499
500 MI.setDesc(MCID);
501
502
506
507
508 unsigned MaskOpIdx = I->MaskOpIdx + MI.getNumExplicitDefs();
509 MI.removeOperand(MaskOpIdx);
510
511
512
513 MRI->recomputeRegClass(MI.getOperand(0).getReg());
514
515
517 unsigned PassthruOpIdx = MI.getNumExplicitDefs();
518 if (HasPassthru) {
519 if (MI.getOperand(PassthruOpIdx).getReg())
520 MRI->recomputeRegClass(MI.getOperand(PassthruOpIdx).getReg());
521 } else
522 MI.removeOperand(PassthruOpIdx);
523 }
524
525 return true;
526}
527
528
529
534 if (MO.getReg().isPhysical())
537 if (MO.getReg().isPhysical())
539 bool SawStore = false;
541 for (Register PhysReg : PhysUses)
542 if (II->definesRegister(PhysReg, nullptr))
543 return false;
544 for (Register PhysReg : PhysDefs)
545 if (II->definesRegister(PhysReg, nullptr) ||
546 II->readsRegister(PhysReg, nullptr))
547 return false;
548 if (II->mayStore()) {
549 SawStore = true;
550 break;
551 }
552 }
554}
555
556
559 assert(A->getParent() == B->getParent());
561 auto MBBEnd = MBB->end();
562 if (B == MBBEnd)
563 return true;
564
566 for (; &*I != A && &*I != B; ++I)
567 ;
568
570}
571
572
573
574
575bool RISCVVectorPeephole::ensureDominates(const MachineOperand &MO,
576 MachineInstr &Src) const {
579 return true;
580
581 MachineInstr *Def = MRI->getVRegDef(MO.getReg());
582 if (Def->getParent() == Src.getParent() && (Def, Src)) {
584 return false;
585 Src.moveBefore(Def->getNextNode());
586 }
587
588 return true;
589}
590
591
592bool RISCVVectorPeephole::foldUndefPassthruVMV_V_V(MachineInstr &MI) {
594 return false;
595 if (MI.getOperand(1).getReg().isValid())
596 return false;
597
598
599
600 MachineInstr *Src = MRI->getVRegDef(MI.getOperand(2).getReg());
601 if (Src && !Src->hasUnmodeledSideEffects() &&
602 MRI->hasOneUse(MI.getOperand(2).getReg()) &&
605 const MachineOperand &MIVL = MI.getOperand(3);
606 const MachineOperand &SrcVL =
608
609 MachineOperand &SrcPolicy =
611
614 }
615
616 MRI->constrainRegClass(MI.getOperand(2).getReg(),
617 MRI->getRegClass(MI.getOperand(0).getReg()));
618 MRI->replaceRegWith(MI.getOperand(0).getReg(), MI.getOperand(2).getReg());
619 MRI->clearKillFlags(MI.getOperand(2).getReg());
620 MI.eraseFromParent();
621 return true;
622}
623
624
625
626
627
628
629
630
631
632
633
634bool RISCVVectorPeephole::foldVMV_V_V(MachineInstr &MI) {
636 return false;
637
638 MachineOperand &Passthru = MI.getOperand(1);
639
640 if (->hasOneUse(MI.getOperand(2).getReg()))
641 return false;
642
643 MachineInstr *Src = MRI->getVRegDef(MI.getOperand(2).getReg());
644 if (!Src || Src->hasUnmodeledSideEffects() ||
645 Src->getParent() != MI.getParent() ||
648 return false;
649
650
651 if (!hasSameEEW(MI, *Src))
652 return false;
653
654 std::optional<std::pair<unsigned, unsigned>> NeedsCommute;
655
656
657 MachineOperand &SrcPassthru = Src->getOperand(Src->getNumExplicitDefs());
660
661
662 int OtherIdx = Src->findRegisterUseOperandIdx(Passthru.getReg(), TRI);
663 if (OtherIdx == -1)
664 return false;
665 unsigned OpIdx1 = OtherIdx;
666 unsigned OpIdx2 = Src->getNumExplicitDefs();
667 if (->findCommutedOpIndices(*Src, OpIdx1, OpIdx2))
668 return false;
669 NeedsCommute = {OpIdx1, OpIdx2};
670 }
671
672
673
674
675 MachineOperand &SrcVL = Src->getOperand(RISCVII::getVLOpNum(Src->getDesc()));
677 return false;
678
679
680 if (!ensureDominates(Passthru, *Src))
681 return false;
682
683 if (NeedsCommute) {
684 auto [OpIdx1, OpIdx2] = *NeedsCommute;
685 [[maybe_unused]] bool Commuted =
686 TII->commuteInstruction(*Src, false, OpIdx1, OpIdx2);
687 assert(Commuted && "Failed to commute Src?");
688 }
689
690 if (SrcPassthru.getReg() != Passthru.getReg()) {
692
694 MRI->constrainRegClass(
696 TII->getRegClass(Src->getDesc(), SrcPassthru.getOperandNo()));
697 }
698
700
706 }
707
708 MRI->constrainRegClass(Src->getOperand(0).getReg(),
709 MRI->getRegClass(MI.getOperand(0).getReg()));
710 MRI->replaceRegWith(MI.getOperand(0).getReg(), Src->getOperand(0).getReg());
711 MI.eraseFromParent();
712
713 return true;
714}
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734bool RISCVVectorPeephole::foldVMergeToMask(MachineInstr &MI) const {
736 return false;
737
738 Register PassthruReg = lookThruCopies(MI.getOperand(1).getReg());
739 Register FalseReg = lookThruCopies(MI.getOperand(2).getReg());
741 lookThruCopies(MI.getOperand(3).getReg(), true);
742 if (!TrueReg.isVirtual() || ->hasOneUse(TrueReg))
743 return false;
744 MachineInstr &True = *MRI->getUniqueVRegDef(TrueReg);
746 return false;
747 const MachineOperand &MaskOp = MI.getOperand(4);
748 MachineInstr *Mask = MRI->getUniqueVRegDef(MaskOp.getReg());
750
751 const RISCV::RISCVMaskedPseudoInfo *Info =
752 RISCV::lookupMaskedIntrinsicByUnmasked(True.getOpcode());
754 return false;
755
756
757 if (!hasSameEEW(MI, True))
758 return false;
759
760
761
762 if (PassthruReg && !(PassthruReg.isVirtual() && PassthruReg == FalseReg))
763 return false;
764
765 std::optional<std::pair<unsigned, unsigned>> NeedsCommute;
766
767
768
772 !(TruePassthru.isVirtual() && TruePassthru == FalseReg)) {
773
774
776 if (OtherIdx == -1)
777 return false;
778 unsigned OpIdx1 = OtherIdx;
780 if (->findCommutedOpIndices(True, OpIdx1, OpIdx2))
781 return false;
782 NeedsCommute = {OpIdx1, OpIdx2};
783 }
784
785
786
788 return false;
789
790 const MachineOperand &VMergeVL =
792 const MachineOperand &TrueVL =
794
797 MinVL = TrueVL;
799 MinVL = VMergeVL;
800 else
801 return false;
802
803 unsigned RVVTSFlags =
806 return false;
808 return false;
809
810
811
812
813
814
815
816
820
822 "Foldable unmasked pseudo should have a policy op already");
823
824
825
826 if (!ensureDominates(MaskOp, True))
827 return false;
828
829 if (NeedsCommute) {
830 auto [OpIdx1, OpIdx2] = *NeedsCommute;
831 [[maybe_unused]] bool Commuted =
832 TII->commuteInstruction(True, false, OpIdx1, OpIdx2);
833 assert(Commuted && "Failed to commute True?");
834 Info = RISCV::lookupMaskedIntrinsicByUnmasked(True.getOpcode());
835 }
836
838
839
840
844
845
849 MinVL);
851
853
856 continue;
857 MRI->constrainRegClass(
859 }
860
861 MRI->clearKillFlags(FalseReg);
862 MI.eraseFromParent();
863
864 return true;
865}
866
867bool RISCVVectorPeephole::runOnMachineFunction(MachineFunction &MF) {
869 return false;
870
871
874 return false;
875
878 TRI = MRI->getTargetRegisterInfo();
879
881
882 for (MachineBasicBlock &MBB : MF) {
885
889 Changed |= convertToUnmasked(MI);
890 Changed |= convertToWholeRegister(MI);
891 Changed |= convertAllOnesVMergeToVMv(MI);
892 Changed |= convertSameMaskVMergeToVMv(MI);
893 if (foldUndefPassthruVMV_V_V(MI)) {
895 continue;
896 }
898 }
899 }
900
902}
903
905 return new RISCVVectorPeephole();
906}
unsigned const MachineRegisterInfo * MRI
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
static uint64_t getConstant(const Value *IndexValue)
static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
Analysis containing CSE Info
const HexagonInstrInfo * TII
Register const TargetRegisterInfo * TRI
Promote Memory to Register
uint64_t IntrinsicInst * II
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
#define CASE_WHOLE_REGISTER_LMUL(lmul)
static bool isSafeToMove(const MachineInstr &From, const MachineInstr &To)
Check if it's safe to move From down to To, checking that no physical registers are clobbered.
Definition RISCVVectorPeephole.cpp:530
static bool dominates(InstrPosIndexes &PosIndexes, const MachineInstr &A, const MachineInstr &B)
FunctionPass class - This class is used to implement most global optimizations.
MachineInstrBundleIterator< const MachineInstr > const_iterator
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
Properties which a MachineFunction may have at a given point in time.
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
MachineRegisterInfo & getRegInfo()
getRegInfo - Return information about the registers currently in use.
Function & getFunction()
Return the LLVM function that this machine code represents.
Representation of each machine instruction.
mop_iterator operands_begin()
bool mayRaiseFPException() const
Return true if this instruction could possibly raise a floating-point exception.
unsigned getOpcode() const
Returns the opcode of this MachineInstr.
const MachineBasicBlock * getParent() const
filtered_mop_range all_defs()
Returns an iterator range over all operands that are (explicit or implicit) register defs.
LLVM_ABI bool isSafeToMove(bool &SawStore) const
Return true if it is safe to move this instruction.
LLVM_ABI int findRegisterUseOperandIdx(Register Reg, const TargetRegisterInfo *TRI, bool isKill=false) const
Returns the operand index that is a use of the specific register or -1 if it is not found.
const MCInstrDesc & getDesc() const
Returns the target instruction descriptor of this MachineInstr.
LLVM_ABI bool hasUnmodeledSideEffects() const
Return true if this instruction has side effects that are not modeled by mayLoad / mayStore,...
LLVM_ABI void insert(mop_iterator InsertBefore, ArrayRef< MachineOperand > Ops)
Inserts Ops BEFORE It. Can untie/retie tied operands.
LLVM_ABI void setDesc(const MCInstrDesc &TID)
Replace the instruction descriptor (thus opcode) of the current instruction with a new one.
LLVM_ABI unsigned getNumExplicitDefs() const
Returns the number of non-implicit definitions.
mop_range explicit_operands()
LLVM_ABI void removeOperand(unsigned OpNo)
Erase an operand from an instruction, leaving it with one fewer operand than it started with.
filtered_mop_range all_uses()
Returns an iterator range over all operands that are (explicit or implicit) register uses.
const MachineOperand & getOperand(unsigned i) const
LLVM_ABI const TargetRegisterClass * getRegClassConstraint(unsigned OpIdx, const TargetInstrInfo *TII, const TargetRegisterInfo *TRI) const
Compute the static register class constraint for operand OpIdx.
MachineOperand class - Representation of each machine instruction operand.
LLVM_ABI unsigned getOperandNo() const
Returns the index of this operand in the instruction that it belongs to.
void setImm(int64_t immVal)
bool isReg() const
isReg - Tests if this is a MO_Register operand.
LLVM_ABI void setReg(Register Reg)
Change the register this operand corresponds to.
bool isImm() const
isImm - Tests if this is a MO_Immediate operand.
LLVM_ABI void ChangeToImmediate(int64_t ImmVal, unsigned TargetFlags=0)
ChangeToImmediate - Replace this operand with a new immediate operand of the specified value.
LLVM_ABI void ChangeToRegister(Register Reg, bool isDef, bool isImp=false, bool isKill=false, bool isDead=false, bool isUndef=false, bool isDebug=false)
ChangeToRegister - Replace this operand with a new register operand of the specified value.
MachineInstr * getParent()
getParent - Return the instruction that this operand belongs to.
static MachineOperand CreateImm(int64_t Val)
Register getReg() const
getReg - Returns the register number.
LLVM_ABI bool isIdenticalTo(const MachineOperand &Other) const
Returns true if this operand is identical to the specified operand except for liveness related flags ...
static MachineOperand CreateReg(Register Reg, bool isDef, bool isImp=false, bool isKill=false, bool isDead=false, bool isUndef=false, bool isEarlyClobber=false, unsigned SubReg=0, bool isDebug=false, bool isInternalRead=false, bool isRenamable=false)
MachineRegisterInfo - Keep track of information for virtual and physical registers,...
bool hasVInstructions() const
std::optional< unsigned > getRealVLen() const
const RISCVInstrInfo * getInstrInfo() const override
Wrapper class representing virtual and physical registers.
constexpr bool isValid() const
constexpr bool isVirtual() const
Return true if the specified register number is in the virtual register namespace.
void assign(size_type NumElts, ValueParamT Elt)
void push_back(const T &Elt)
This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.
StringRef - Represent a constant reference to a string, i.e.
TargetInstrInfo - Interface to description of machine instruction set.
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
A Use represents the edge between a Value definition and its users.
Value * getOperand(unsigned i) const
self_iterator getIterator()
constexpr std::underlying_type_t< E > Mask()
Get a bitmask with 1s in all places up to the high-order bit of E's largest value.
unsigned ID
LLVM IR allows to use arbitrary numbers as calling convention identifiers.
static unsigned getVecPolicyOpNum(const MCInstrDesc &Desc)
static RISCVVType::VLMUL getLMul(uint64_t TSFlags)
static unsigned getVLOpNum(const MCInstrDesc &Desc)
static bool hasVLOp(uint64_t TSFlags)
static bool elementsDependOnMask(uint64_t TSFlags)
static bool hasVecPolicyOp(uint64_t TSFlags)
static unsigned getSEWOpNum(const MCInstrDesc &Desc)
static bool elementsDependOnVL(uint64_t TSFlags)
static bool hasSEWOp(uint64_t TSFlags)
static bool isFirstDefTiedToFirstUse(const MCInstrDesc &Desc)
@ TAIL_UNDISTURBED_MASK_UNDISTURBED
LLVM_ABI std::pair< unsigned, bool > decodeVLMUL(VLMUL VLMul)
static bool isValidSEW(unsigned SEW)
bool isVLKnownLE(const MachineOperand &LHS, const MachineOperand &RHS)
Given two VL operands, do we know that LHS <= RHS?
unsigned getRVVMCOpcode(unsigned RVVPseudoOpcode)
unsigned getDestLog2EEW(const MCInstrDesc &Desc, unsigned Log2SEW)
static constexpr int64_t VLMaxSentinel
NodeAddr< DefNode * > Def
This is an optimization pass for GlobalISel generic memory operations.
iterator_range< early_inc_iterator_impl< detail::IterOfRange< RangeT > > > make_early_inc_range(RangeT &&Range)
Make a range that does early increment to allow mutation of the underlying range without disrupting i...
MachineInstr * getImm(const MachineOperand &MO, const MachineRegisterInfo *MRI)
decltype(auto) get(const PointerIntPair< PointerTy, IntBits, IntType, PtrTraits, Info > &Pair)
FunctionPass * createRISCVVectorPeepholePass()
Definition RISCVVectorPeephole.cpp:904