LLVM: lib/Target/Mips/MipsBranchExpansion.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
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
98#include
99#include
100#include
101#include
102#include
103
104using namespace llvm;
105
106#define DEBUG_TYPE "mips-branch-expansion"
107
108STATISTIC(NumInsertedNops, "Number of nops inserted");
109STATISTIC(LongBranches, "Number of long branches.");
110
114
117 cl::desc("MIPS: Expand all branches to long format."),
119
120namespace {
121
124
125struct MBBInfo {
127 bool HasLongBranch = false;
130 MBBInfo() = default;
131};
132
134public:
135 static char ID;
136
137 MipsBranchExpansion()
138 : MachineFunctionPass(ID), ABI(MipsABIInfo::Unknown()) {}
139
140 StringRef getPassName() const override {
141 return "Mips Branch Expansion Pass";
142 }
143
144 bool runOnMachineFunction(MachineFunction &F) override;
145
146 MachineFunctionProperties getRequiredProperties() const override {
147 return MachineFunctionProperties().setNoVRegs();
148 }
149
150private:
152 void initMBBInfo();
153 int64_t computeOffset(const MachineInstr *Br);
154 uint64_t computeOffsetFromTheBeginning(int MBB);
155 void replaceBranch(MachineBasicBlock &MBB, Iter Br, const DebugLoc &DL,
156 MachineBasicBlock *MBBOpnd);
157 bool buildProperJumpMI(MachineBasicBlock *MBB,
159 void expandToLongBranch(MBBInfo &Info);
160 template <typename Pred, typename Safe>
161 bool handleSlot(Pred Predicate, Safe SafeInSlot);
162 bool handleForbiddenSlot();
163 bool handleFPUDelaySlot();
164 bool handleLoadDelaySlot();
165 bool handlePossibleLongBranch();
166 bool handleMFLO();
167 template <typename Pred, typename Safe>
168 bool handleMFLOSlot(Pred Predicate, Safe SafeInSlot);
169
170 const MipsSubtarget *STI;
171 const MipsInstrInfo *TII;
172
173 MachineFunction *MFp;
175 bool IsPIC;
176 MipsABIInfo ABI;
177 bool ForceLongBranchFirstPass = false;
178};
179
180}
181
182char MipsBranchExpansion::ID = 0;
183
185 "Expand out of range branch instructions and fix forbidden"
186 " slot hazards",
187 false, false)
188
189
191 return new MipsBranchExpansion();
192}
193
194
195
197 Iter I = Position, E = Position->getParent()->end();
198 I = std::find_if_not(I, E,
199 [](const Iter &Insn) { return Insn->isTransient(); });
200
201 return I;
202}
203
204
205
208 if (Position == Parent->end()) {
209 do {
211 if (Succ != nullptr && Parent->isSuccessor(Succ)) {
212 Position = Succ->begin();
213 Parent = Succ;
214 } else {
215 return std::make_pair(Position, true);
216 }
217 } while (Parent->empty());
218 }
219
221 if (Instr == Parent->end()) {
223 }
224 return std::make_pair(Instr, false);
225}
226
227
228
232
235 }
236
237 llvm_unreachable("This instruction does not have an MBB operand.");
238}
239
240
241
244 if (->isDebugInstr())
245 return B;
246
247 return E;
248}
249
250
252 ReverseIter End = MBB->rend();
254
255
256 if ((LastBr == End) ||
257 (!LastBr->isConditionalBranch() && !LastBr->isUnconditionalBranch()))
258 return;
259
260 ReverseIter FirstBr = getNonDebugInstr(std::next(LastBr), End);
261
262
263
264 if ((FirstBr == End) ||
265 (!FirstBr->isConditionalBranch() && !FirstBr->isUnconditionalBranch()))
266 return;
267
268 assert(!FirstBr->isIndirectBranch() && "Unexpected indirect branch found.");
269
270
271 MachineBasicBlock *NewMBB =
273
274
275 MachineBasicBlock *Tgt = getTargetMBB(*FirstBr);
282
284}
285
286
287void MipsBranchExpansion::initMBBInfo() {
288
289
290 for (auto &MBB : *MFp)
292
293 MFp->RenumberBlocks();
294 MBBInfos.clear();
295 MBBInfos.resize(MFp->size());
296
297 for (unsigned I = 0, E = MBBInfos.size(); I < E; ++I) {
298 MachineBasicBlock *MBB = MFp->getBlockNumbered(I);
299
300
302 MBBInfos[I].Size += TII->getInstSizeInBytes(MI);
303 }
304}
305
306
307int64_t MipsBranchExpansion::computeOffset(const MachineInstr *Br) {
311
312
313 if (ThisMBB < TargetMBB) {
314 for (int N = ThisMBB + 1; N < TargetMBB; ++N)
316
318 }
319
320
321 for (int N = ThisMBB; N >= TargetMBB; --N)
323
325}
326
327
328uint64_t MipsBranchExpansion::computeOffsetFromTheBeginning(int MBB) {
330 for (int N = 0; N < MBB; ++N)
333}
334
335
336
337void MipsBranchExpansion::replaceBranch(MachineBasicBlock &MBB, Iter Br,
339 MachineBasicBlock *MBBOpnd) {
340 unsigned NewOpc = TII->getOppositeBranchOpc(Br->getOpcode());
341 const MCInstrDesc &NewDesc = TII->get(NewOpc);
342
343 MachineInstrBuilder MIB = BuildMI(MBB, Br, DL, NewDesc);
344
345 for (unsigned I = 0, E = Br->getDesc().getNumOperands(); I < E; ++I) {
346 MachineOperand &MO = Br->getOperand(I);
347
351 break;
353
354
355 if (->isBranchWithImm(Br->getOpcode()))
356 llvm_unreachable("Unexpected immediate in branch instruction");
358 break;
361 break;
362 default:
363 llvm_unreachable("Unexpected operand type in branch instruction");
364 }
365 }
366
367 if (Br->hasDelaySlot()) {
368
369
370 assert(Br->isBundledWithSucc());
372 MIBundleBuilder(&*MIB).append((++II)->removeFromBundle());
373 }
374 Br->eraseFromParent();
375}
376
377bool MipsBranchExpansion::buildProperJumpMI(MachineBasicBlock *MBB,
382
383 unsigned JR = ABI.IsN64() ? Mips::JR64 : Mips::JR;
384 unsigned JIC = ABI.IsN64() ? Mips::JIC64 : Mips::JIC;
385 unsigned JR_HB = ABI.IsN64() ? Mips::JR_HB64 : Mips::JR_HB;
386 unsigned JR_HB_R6 = ABI.IsN64() ? Mips::JR_HB64_R6 : Mips::JR_HB_R6;
387
388 unsigned JumpOp;
390 JumpOp = HasR6 ? JR_HB_R6 : JR_HB;
391 else
392 JumpOp = HasR6 ? JIC : JR;
393
395 JumpOp = Mips::JIC_MMR6;
396
397 unsigned ATReg = ABI.IsN64() ? Mips::AT_64 : Mips::AT;
398 MachineInstrBuilder Instr =
400 if (AddImm)
402
403 return !AddImm;
404}
405
406
407
408
409
410
411void MipsBranchExpansion::expandToLongBranch(MBBInfo &I) {
417 MachineBasicBlock *LongBrMBB = MFp->CreateMachineBasicBlock(BB);
418
419 MFp->insert(FallThroughMBB, LongBrMBB);
421
422 if (IsPIC) {
423 MachineBasicBlock *BalTgtMBB = MFp->CreateMachineBasicBlock(BB);
424 MFp->insert(FallThroughMBB, BalTgtMBB);
427
428
429
430
431 const unsigned BalOp =
434 : STI->inMicroMipsMode() ? Mips::BAL_BR_MM : Mips::BAL_BR;
435
436 if (!ABI.IsN64()) {
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466 Pos = LongBrMBB->begin();
467
468 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::ADDiu), Mips::SP)
471 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::SW))
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_LUi), Mips::AT)
495
496 MachineInstrBuilder BalInstr =
498 MachineInstrBuilder ADDiuInstr =
499 BuildMI(*MFp, DL, TII->get(Mips::LONG_BRANCH_ADDiu), Mips::AT)
504 LongBrMBB->insert(Pos, ADDiuInstr);
505 LongBrMBB->insert(Pos, BalInstr);
506 } else {
507 LongBrMBB->insert(Pos, BalInstr);
508 LongBrMBB->insert(Pos, ADDiuInstr);
509 LongBrMBB->rbegin()->bundleWithPred();
510 }
511
512 Pos = BalTgtMBB->begin();
513
514 BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDu), Mips::AT)
517 BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::LW), Mips::RA)
520
521
522 bool hasDelaySlot = buildProperJumpMI(BalTgtMBB, Pos, DL);
523
524 if (!hasDelaySlot) {
525 BuildMI(*BalTgtMBB, std::prev(Pos), DL, TII->get(Mips::ADDiu), Mips::SP)
528 }
529 if (hasDelaySlot) {
530 BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::ADDiu), Mips::SP)
533 BalTgtMBB->rbegin()->bundleWithPred();
534 }
535 } else {
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581 Pos = LongBrMBB->begin();
582
583 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::DADDiu), Mips::SP_64)
586 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::SD))
590 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_DADDiu),
591 Mips::AT_64)
592 .addReg(Mips::ZERO_64)
595 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::DSLL), Mips::AT_64)
598
599 MachineInstrBuilder BalInstr =
601 MachineInstrBuilder DADDiuInstr =
602 BuildMI(*MFp, DL, TII->get(Mips::LONG_BRANCH_DADDiu), Mips::AT_64)
607 LongBrMBB->insert(Pos, DADDiuInstr);
608 LongBrMBB->insert(Pos, BalInstr);
609 } else {
610 LongBrMBB->insert(Pos, BalInstr);
611 LongBrMBB->insert(Pos, DADDiuInstr);
612 LongBrMBB->rbegin()->bundleWithPred();
613 }
614
615 Pos = BalTgtMBB->begin();
616
617 BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::DADDu), Mips::AT_64)
619 .addReg(Mips::AT_64);
620 BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::LD), Mips::RA_64)
623
624 bool hasDelaySlot = buildProperJumpMI(BalTgtMBB, Pos, DL);
625
626 if (!hasDelaySlot) {
627 BuildMI(*BalTgtMBB, std::prev(Pos), DL, TII->get(Mips::DADDiu),
628 Mips::SP_64)
631 } else {
632 BuildMI(*BalTgtMBB, Pos, DL, TII->get(Mips::DADDiu), Mips::SP_64)
635 BalTgtMBB->rbegin()->bundleWithPred();
636 }
637 }
638 } else {
639 Pos = LongBrMBB->begin();
641
642
643
644 uint64_t JOffset = computeOffsetFromTheBeginning(MBB->getNumber()) +
646 uint64_t TgtMBBOffset = computeOffsetFromTheBeginning(TgtMBB->getNumber());
647
648
649 if (JOffset < TgtMBBOffset)
650 TgtMBBOffset += 2 * 4;
651
652 bool SameSegmentJump = JOffset >> 28 == TgtMBBOffset >> 28;
653
654 if (STI->hasMips32r6() && TII->isBranchOffsetInRange(Mips::BC, I.Offset)) {
655
656
657
658
659
663 } else if (SameSegmentJump) {
664
665
666
667
668
669
671 TII->insertNop(*LongBrMBB, Pos, DL)->bundleWithPred();
672 } else {
673
674
675
676
677
678 if (ABI.IsN64()) {
679 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_LUi2Op_64),
680 Mips::AT_64)
682 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_DADDiu2Op),
683 Mips::AT_64)
686 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::DSLL), Mips::AT_64)
689 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_DADDiu2Op),
690 Mips::AT_64)
693 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::DSLL), Mips::AT_64)
696 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_DADDiu2Op),
697 Mips::AT_64)
700 } else {
701 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_LUi2Op),
702 Mips::AT)
704 BuildMI(*LongBrMBB, Pos, DL, TII->get(Mips::LONG_BRANCH_ADDiu2Op),
705 Mips::AT)
708 }
709 buildProperJumpMI(LongBrMBB, Pos, DL);
710 }
711 }
712
713 if (I.Br->isUnconditionalBranch()) {
714
715 assert(I.Br->getDesc().getNumOperands() == 1);
716 I.Br->removeOperand(0);
718 } else
719
720 replaceBranch(*MBB, I.Br, DL, &*FallThroughMBB);
721}
722
732 MBB.removeLiveIn(Mips::V0);
733}
734
735template <typename Pred, typename Safe>
736bool MipsBranchExpansion::handleMFLOSlot(Pred Predicate, Safe SafeInSlot) {
738 bool hasPendingMFLO = false;
739
741 for (Iter I = FI->begin(); I != FI->end(); ++I) {
742
743 if ((*I) && !hasPendingMFLO) {
744 continue;
745 }
746
747 Iter IInSlot;
748 bool LastInstInFunction =
749 std::next(I) == FI->end() && std::next(FI) == MFp->end();
750
751
752
753
754
755 if (!LastInstInFunction) {
757 LastInstInFunction |= Res.second;
758 IInSlot = Res.first;
759 if (LastInstInFunction)
760 continue;
761 if (!SafeInSlot(*IInSlot, *I)) {
763 TII->insertNop(*(I->getParent()), std::next(I), I->getDebugLoc())
764 ->bundleWithPred();
765 NumInsertedNops++;
767 TII->insertNop(*(I->getParent()), std::next(I), I->getDebugLoc())
768 ->bundleWithPred();
769 NumInsertedNops++;
770 }
771 if (hasPendingMFLO)
772 hasPendingMFLO = false;
773 } else if (hasPendingMFLO)
774 hasPendingMFLO = false;
776 hasPendingMFLO = true;
777 }
778 }
779 }
780
782}
783
784template <typename Pred, typename Safe>
785bool MipsBranchExpansion::handleSlot(Pred Predicate, Safe SafeInSlot) {
787
789 for (Iter I = FI->begin(); I != FI->end(); ++I) {
790
791
793 continue;
794
795 Iter IInSlot;
796 bool LastInstInFunction =
797 std::next(I) == FI->end() && std::next(FI) == MFp->end();
798 if (!LastInstInFunction) {
800 LastInstInFunction |= Res.second;
801 IInSlot = Res.first;
802 }
803
804 if (LastInstInFunction || !SafeInSlot(*IInSlot, *I)) {
806 if (std::next(Iit) == FI->end() ||
807 std::next(Iit)->getOpcode() != Mips::NOP) {
809 TII->insertNop(*(I->getParent()), std::next(I), I->getDebugLoc())
810 ->bundleWithPred();
811 NumInsertedNops++;
812 }
813 }
814 }
815 }
816
818}
819
820bool MipsBranchExpansion::handleMFLO() {
821
822
824 return false;
825
826 return handleMFLOSlot(
827 [this](auto &I) -> bool { return TII->IsMfloOrMfhi(I); },
828 [this](auto &IInSlot, auto &I) -> bool {
829 return TII->SafeAfterMflo(IInSlot);
830 });
831}
832
833bool MipsBranchExpansion::handleForbiddenSlot() {
834
836 return false;
837
838 return handleSlot(
839 [this](auto &I) -> bool { return TII->HasForbiddenSlot(I); },
840 [this](auto &IInSlot, auto &I) -> bool {
841 return TII->SafeInForbiddenSlot(IInSlot);
842 });
843}
844
845bool MipsBranchExpansion::handleFPUDelaySlot() {
846
848 return false;
849
850 return handleSlot([this](auto &I) -> bool { return TII->HasFPUDelaySlot(I); },
851 [this](auto &IInSlot, auto &I) -> bool {
852 return TII->SafeInFPUDelaySlot(IInSlot, I);
853 });
854}
855
856bool MipsBranchExpansion::handleLoadDelaySlot() {
857
859 return false;
860
861 return handleSlot(
862 [this](auto &I) -> bool { return TII->HasLoadDelaySlot(I); },
863 [this](auto &IInSlot, auto &I) -> bool {
864 return TII->SafeInLoadDelaySlot(IInSlot, I);
865 });
866}
867
868bool MipsBranchExpansion::handlePossibleLongBranch() {
870 return false;
871
873 return false;
874
875 bool EverMadeChange = false, MadeChange = true;
876
877 while (MadeChange) {
878 MadeChange = false;
879
880 initMBBInfo();
881
882 for (unsigned I = 0, E = MBBInfos.size(); I < E; ++I) {
883 MachineBasicBlock *MBB = MFp->getBlockNumbered(I);
884
885 ReverseIter End = MBB->rend();
887
888 if ((Br != End) && Br->isBranch() && !Br->isIndirectBranch() &&
889 (Br->isConditionalBranch() ||
890 (Br->isUnconditionalBranch() && IsPIC))) {
891 int64_t Offset = computeOffset(&*Br);
892
893 if (ForceLongBranchFirstPass ||
894 ->isBranchOffsetInRange(Br->getOpcode(), Offset)) {
895 MBBInfos[I].Offset = Offset;
896 MBBInfos[I].Br = &*Br;
897 }
898 }
899 }
900
901 ForceLongBranchFirstPass = false;
902
904
905 for (I = MBBInfos.begin(); I != E; ++I) {
906
907
908 if (->Br)
909 continue;
910
911 expandToLongBranch(*I);
912 ++LongBranches;
913 EverMadeChange = MadeChange = true;
914 }
915
916 MFp->RenumberBlocks();
917 }
918
919 return EverMadeChange;
920}
921
922bool MipsBranchExpansion::runOnMachineFunction(MachineFunction &MF) {
923 const TargetMachine &TM = MF.getTarget();
925 ABI = static_cast<const MipsTargetMachine &>(TM).getABI();
928
929 if (IsPIC && ABI.IsO32() &&
930 MF.getInfo()->globalBaseRegSet())
932
933 MFp = &MF;
934
936
937 bool longBranchChanged = handlePossibleLongBranch();
938 bool forbiddenSlotChanged = handleForbiddenSlot();
939 bool fpuDelaySlotChanged = handleFPUDelaySlot();
940 bool loadDelaySlotChanged = handleLoadDelaySlot();
941 bool MfloChanged = handleMFLO();
942
943 bool Changed = longBranchChanged || forbiddenSlotChanged ||
944 fpuDelaySlotChanged || loadDelaySlotChanged || MfloChanged;
945
946
947 while (forbiddenSlotChanged) {
948 longBranchChanged = handlePossibleLongBranch();
949 fpuDelaySlotChanged = handleFPUDelaySlot();
950 loadDelaySlotChanged = handleLoadDelaySlot();
951 MfloChanged = handleMFLO();
952 if (!longBranchChanged && !fpuDelaySlotChanged && !loadDelaySlotChanged &&
953 !MfloChanged)
954 break;
955 forbiddenSlotChanged = handleForbiddenSlot();
956 }
957
959}
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
MachineBasicBlock MachineBasicBlock::iterator DebugLoc DL
static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")
static GCRegistry::Add< OcamlGC > B("ocaml", "ocaml 3.10-compatible GC")
Analysis containing CSE Info
const HexagonInstrInfo * TII
static std::pair< Iter, bool > getNextMachineInstr(Iter Position, MachineBasicBlock *Parent)
Definition MipsBranchExpansion.cpp:206
static cl::opt< bool > ForceLongBranch("force-mips-long-branch", cl::init(false), cl::desc("MIPS: Expand all branches to long format."), cl::Hidden)
static cl::opt< bool > SkipLongBranch("skip-mips-long-branch", cl::init(false), cl::desc("MIPS: Skip branch expansion pass."), cl::Hidden)
static MachineBasicBlock * getTargetMBB(const MachineInstr &Br)
Iterate over list of Br's operands and search for a MachineBasicBlock operand.
Definition MipsBranchExpansion.cpp:229
static void emitGPDisp(MachineFunction &F, const MipsInstrInfo *TII)
Definition MipsBranchExpansion.cpp:723
static ReverseIter getNonDebugInstr(ReverseIter B, const ReverseIter &E)
Definition MipsBranchExpansion.cpp:242
static Iter getNextMachineInstrInBB(Iter Position)
Definition MipsBranchExpansion.cpp:196
#define IsMFLOMFHI(instr)
uint64_t IntrinsicInst * II
static bool splitMBB(BlockSplitInfo &BSI)
Splits a MachineBasicBlock to branch before SplitBefore.
#define INITIALIZE_PASS(passName, arg, name, cfg, analysis)
This file defines the SmallVector class.
This file defines the 'Statistic' class, which is designed to be an easy way to expose various metric...
#define STATISTIC(VARNAME, DESC)
FunctionPass class - This class is used to implement most global optimizations.
unsigned getNumOperands() const
Return the number of declared MachineOperands for this MachineInstruction.
LLVM_ABI void replaceSuccessor(MachineBasicBlock *Old, MachineBasicBlock *New)
Replace successor OLD with NEW and update probability info.
LLVM_ABI void transferSuccessors(MachineBasicBlock *FromMBB)
Transfers all the successors from MBB to this machine basic block (i.e., copies all the successors Fr...
LLVM_ABI instr_iterator insert(instr_iterator I, MachineInstr *M)
Insert MI into the instruction list before I, possibly inside a bundle.
int getNumber() const
MachineBasicBlocks are uniquely numbered at the function level, unless they're not in a MachineFuncti...
const BasicBlock * getBasicBlock() const
Return the LLVM basic block that this instance corresponded to originally.
LLVM_ABI void addSuccessor(MachineBasicBlock *Succ, BranchProbability Prob=BranchProbability::getUnknown())
Add Succ as a successor of this MachineBasicBlock.
LLVM_ABI void removeSuccessor(MachineBasicBlock *Succ, bool NormalizeSuccProbs=false)
Remove successor from the successors list of this MachineBasicBlock.
Instructions::iterator instr_iterator
MachineInstrBundleIterator< MachineInstr, true > reverse_iterator
const MachineFunction * getParent() const
Return the MachineFunction containing this basic block.
reverse_iterator rbegin()
LLVM_ABI bool isSuccessor(const MachineBasicBlock *MBB) const
Return true if the specified MBB is a successor of this block.
void splice(iterator Where, MachineBasicBlock *Other, iterator From)
Take an instruction from MBB 'Other' at the position From, and insert it into this MBB right before '...
MachineInstrBundleIterator< MachineInstr > iterator
MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
BasicBlockListType::iterator iterator
Ty * getInfo()
getInfo - Keep track of various per-function pieces of information for backends that would like to do...
MachineBasicBlock * CreateMachineBasicBlock(const BasicBlock *BB=nullptr, std::optional< UniqueBBID > BBID=std::nullopt)
CreateMachineInstr - Allocate a new MachineInstr.
void insert(iterator MBBI, MachineBasicBlock *MBB)
const TargetMachine & getTarget() const
getTarget - Return the target machine this machine code is compiled with
const MachineInstrBuilder & addExternalSymbol(const char *FnName, unsigned TargetFlags=0) const
const MachineInstrBuilder & addImm(int64_t Val) const
Add a new immediate operand.
const MachineInstrBuilder & addReg(Register RegNo, unsigned flags=0, unsigned SubReg=0) const
Add a new virtual register operand.
const MachineInstrBuilder & addMBB(MachineBasicBlock *MBB, unsigned TargetFlags=0) const
Representation of each machine instruction.
const MachineBasicBlock * getParent() const
const MCInstrDesc & getDesc() const
Returns the target instruction descriptor of this MachineInstr.
const MachineOperand & getOperand(unsigned i) const
MachineOperand class - Representation of each machine instruction operand.
MachineBasicBlock * getMBB() const
MachineOperandType getType() const
getType - Returns the MachineOperandType for this operand.
Register getReg() const
getReg - Returns the register number.
@ MO_Immediate
Immediate operand.
@ MO_MachineBasicBlock
MachineBasicBlock reference.
@ MO_Register
Register operand.
static MachineOperand CreateMBB(MachineBasicBlock *MBB, unsigned TargetFlags=0)
bool isMBB() const
isMBB - Tests if this is a MO_MachineBasicBlock operand.
bool inMicroMipsMode() const
const MipsInstrInfo * getInstrInfo() const override
bool useIndirectJumpsHazard() const
bool inMips16Mode() const
bool enableLongBranchPass() const
typename SuperClass::iterator iterator
bool isPositionIndependent() const
NodeTy * getNextNode()
Get the next node, or nullptr for the list tail.
#define llvm_unreachable(msg)
Marks that the current location is not supposed to be reachable.
@ BasicBlock
Various leaf nodes.
Predicate
Predicate - These are "(BI << 5) | BO" for various predicates.
initializer< Ty > init(const Ty &Val)
NodeAddr< InstrNode * > Instr
This is an optimization pass for GlobalISel generic memory operations.
MachineInstrBuilder BuildMI(MachineFunction &MF, const MIMetadata &MIMD, const MCInstrDesc &MCID)
Builder interface. Specify how to create the initial instruction itself.
class LLVM_GSL_OWNER SmallVector
Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...
FunctionPass * createMipsBranchExpansion()