aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/MIRCanonicalizerPass.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/CodeGen/MIRCanonicalizerPass.cpp')
-rw-r--r--lib/CodeGen/MIRCanonicalizerPass.cpp65
1 files changed, 39 insertions, 26 deletions
diff --git a/lib/CodeGen/MIRCanonicalizerPass.cpp b/lib/CodeGen/MIRCanonicalizerPass.cpp
index f17c23619ed5..f49bc854e23f 100644
--- a/lib/CodeGen/MIRCanonicalizerPass.cpp
+++ b/lib/CodeGen/MIRCanonicalizerPass.cpp
@@ -1,9 +1,8 @@
//===-------------- MIRCanonicalizer.cpp - MIR Canonicalizer --------------===//
//
-// The LLVM Compiler Infrastructure
-//
-// This file is distributed under the University of Illinois Open Source
-// License. See LICENSE.TXT for details.
+// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
+// See https://llvm.org/LICENSE.txt for license information.
+// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
//
@@ -105,6 +104,8 @@ INITIALIZE_PASS_END(MIRCanonicalizer, "mir-canonicalizer",
"Rename Register Operands Canonically", false, false)
static std::vector<MachineBasicBlock *> GetRPOList(MachineFunction &MF) {
+ if (MF.empty())
+ return {};
ReversePostOrderTraversal<MachineBasicBlock *> RPOT(&*MF.begin());
std::vector<MachineBasicBlock *> RPOList;
for (auto MBB : RPOT) {
@@ -179,6 +180,8 @@ static bool rescheduleCanonically(unsigned &PseudoIdempotentInstCount,
}
std::map<MachineInstr *, std::vector<MachineInstr *>> MultiUsers;
+ std::map<unsigned, MachineInstr *> MultiUserLookup;
+ unsigned UseToBringDefCloserToCount = 0;
std::vector<MachineInstr *> PseudoIdempotentInstructions;
std::vector<unsigned> PhysRegDefs;
for (auto *II : Instructions) {
@@ -254,6 +257,7 @@ static bool rescheduleCanonically(unsigned &PseudoIdempotentInstCount,
if (Delta < Distance) {
Distance = Delta;
UseToBringDefCloserTo = UseInst;
+ MultiUserLookup[UseToBringDefCloserToCount++] = UseToBringDefCloserTo;
}
}
@@ -293,11 +297,11 @@ static bool rescheduleCanonically(unsigned &PseudoIdempotentInstCount,
}
// Sort the defs for users of multiple defs lexographically.
- for (const auto &E : MultiUsers) {
+ for (const auto &E : MultiUserLookup) {
auto UseI =
std::find_if(MBB->instr_begin(), MBB->instr_end(),
- [&](MachineInstr &MI) -> bool { return &MI == E.first; });
+ [&](MachineInstr &MI) -> bool { return &MI == E.second; });
if (UseI == MBB->instr_end())
continue;
@@ -305,7 +309,8 @@ static bool rescheduleCanonically(unsigned &PseudoIdempotentInstCount,
LLVM_DEBUG(
dbgs() << "Rescheduling Multi-Use Instructions Lexographically.";);
Changed |= rescheduleLexographically(
- E.second, MBB, [&]() -> MachineBasicBlock::iterator { return UseI; });
+ MultiUsers[E.second], MBB,
+ [&]() -> MachineBasicBlock::iterator { return UseI; });
}
PseudoIdempotentInstCount = PseudoIdempotentInstructions.size();
@@ -342,15 +347,23 @@ static bool propagateLocalCopies(MachineBasicBlock *MBB) {
continue;
if (!TargetRegisterInfo::isVirtualRegister(Src))
continue;
+ // Not folding COPY instructions if regbankselect has not set the RCs.
+ // Why are we only considering Register Classes? Because the verifier
+ // sometimes gets upset if the register classes don't match even if the
+ // types do. A future patch might add COPY folding for matching types in
+ // pre-registerbankselect code.
+ if (!MRI.getRegClassOrNull(Dst))
+ continue;
if (MRI.getRegClass(Dst) != MRI.getRegClass(Src))
continue;
- for (auto UI = MRI.use_begin(Dst); UI != MRI.use_end(); ++UI) {
- MachineOperand *MO = &*UI;
+ std::vector<MachineOperand *> Uses;
+ for (auto UI = MRI.use_begin(Dst); UI != MRI.use_end(); ++UI)
+ Uses.push_back(&*UI);
+ for (auto *MO : Uses)
MO->setReg(Src);
- Changed = true;
- }
+ Changed = true;
MI->eraseFromParent();
}
@@ -474,18 +487,14 @@ class NamedVRegCursor {
unsigned virtualVRegNumber;
public:
- NamedVRegCursor(MachineRegisterInfo &MRI) : MRI(MRI) {
- unsigned VRegGapIndex = 0;
- const unsigned VR_GAP = (++VRegGapIndex * 1000);
-
- unsigned I = MRI.createIncompleteVirtualRegister();
- const unsigned E = (((I + VR_GAP) / VR_GAP) + 1) * VR_GAP;
-
- virtualVRegNumber = E;
- }
+ NamedVRegCursor(MachineRegisterInfo &MRI) : MRI(MRI), virtualVRegNumber(0) {}
void SkipVRegs() {
unsigned VRegGapIndex = 1;
+ if (!virtualVRegNumber) {
+ VRegGapIndex = 0;
+ virtualVRegNumber = MRI.createIncompleteVirtualRegister();
+ }
const unsigned VR_GAP = (++VRegGapIndex * 1000);
unsigned I = virtualVRegNumber;
@@ -501,14 +510,17 @@ public:
return virtualVRegNumber;
}
- unsigned createVirtualRegister(const TargetRegisterClass *RC) {
+ unsigned createVirtualRegister(unsigned VReg) {
+ if (!virtualVRegNumber)
+ SkipVRegs();
std::string S;
raw_string_ostream OS(S);
OS << "namedVReg" << (virtualVRegNumber & ~0x80000000);
OS.flush();
virtualVRegNumber++;
-
- return MRI.createVirtualRegister(RC, OS.str());
+ if (auto RC = MRI.getRegClassOrNull(VReg))
+ return MRI.createVirtualRegister(RC, OS.str());
+ return MRI.createGenericVirtualRegister(MRI.getType(VReg), OS.str());
}
};
} // namespace
@@ -558,7 +570,7 @@ GetVRegRenameMap(const std::vector<TypedVReg> &VRegs,
continue;
}
- auto Rename = NVC.createVirtualRegister(MRI.getRegClass(Reg));
+ auto Rename = NVC.createVirtualRegister(Reg);
if (VRegRenameMap.find(Reg) == VRegRenameMap.end()) {
LLVM_DEBUG(dbgs() << "Mapping vreg ";);
@@ -735,14 +747,15 @@ static bool runOnBasicBlock(MachineBasicBlock *MBB,
// of the MachineBasicBlock so that they are named in the order that we sorted
// them alphabetically. Eventually we wont need SkipVRegs because we will use
// named vregs instead.
- NVC.SkipVRegs();
+ if (IdempotentInstCount)
+ NVC.SkipVRegs();
auto MII = MBB->begin();
for (unsigned i = 0; i < IdempotentInstCount && MII != MBB->end(); ++i) {
MachineInstr &MI = *MII++;
Changed = true;
unsigned vRegToRename = MI.getOperand(0).getReg();
- auto Rename = NVC.createVirtualRegister(MRI.getRegClass(vRegToRename));
+ auto Rename = NVC.createVirtualRegister(vRegToRename);
std::vector<MachineOperand *> RenameMOs;
for (auto &MO : MRI.reg_operands(vRegToRename)) {