[llvm] 76a5c84 - [MCRegInfo] Add forward sub and super register iterators. (NFC)
Florian Hahn via llvm-commits
llvm-commits at lists.llvm.org
Thu Dec 5 01:33:20 PST 2019
Author: Florian Hahn
Date: 2019-12-05T09:29:26Z
New Revision: 76a5c8421e04b246892157fe18f1c082c908c5e9
URL: https://github.com/llvm/llvm-project/commit/76a5c8421e04b246892157fe18f1c082c908c5e9
DIFF: https://github.com/llvm/llvm-project/commit/76a5c8421e04b246892157fe18f1c082c908c5e9.diff
LOG: [MCRegInfo] Add forward sub and super register iterators. (NFC)
This patch adds forward iterators mc_difflist_iterator,
mc_subreg_iterator and mc_superreg_iterator, based on the existing
DiffListIterator. Those are used to provide iterator ranges over
sub- and super-register from TRI, which are slightly more convenient
than the existing MCSubRegIterator/MCSuperRegIterator. Unfortunately,
it duplicates a bit of functionality, but the new iterators are a bit
more convenient (and can be used with various existing iterator
utilities) and should probably replace the old iterators in the future.
This patch updates some existing users.
Reviewers: evandro, qcolombet, paquette, MatzeB, arsenm
Reviewed By: qcolombet
Differential Revision: https://reviews.llvm.org/D70565
Added:
Modified:
llvm/include/llvm/MC/MCRegisterInfo.h
llvm/lib/CodeGen/MachineVerifier.cpp
llvm/lib/CodeGen/RegisterScavenging.cpp
llvm/lib/Target/Mips/MCTargetDesc/MipsOptionRecord.cpp
llvm/lib/Target/X86/X86RegisterInfo.cpp
Removed:
################################################################################
diff --git a/llvm/include/llvm/MC/MCRegisterInfo.h b/llvm/include/llvm/MC/MCRegisterInfo.h
index c7dc56ea588e..9280dc75e50b 100644
--- a/llvm/include/llvm/MC/MCRegisterInfo.h
+++ b/llvm/include/llvm/MC/MCRegisterInfo.h
@@ -16,11 +16,13 @@
#define LLVM_MC_MCREGISTERINFO_H
#include "llvm/ADT/DenseMap.h"
+#include "llvm/ADT/iterator.h"
#include "llvm/ADT/iterator_range.h"
#include "llvm/MC/LaneBitmask.h"
#include "llvm/MC/MCRegister.h"
#include <cassert>
#include <cstdint>
+#include <iterator>
#include <utility>
namespace llvm {
@@ -177,6 +179,9 @@ class MCRegisterInfo {
DenseMap<MCRegister, int> L2CVRegs; // LLVM to CV regs mapping
public:
+ // Forward declaration to become a friend class of DiffListIterator.
+ template <class SubT> class mc_
diff list_iterator;
+
/// DiffListIterator - Base iterator class that can traverse the
///
diff erentially encoded register and regunit lists in DiffLists.
/// Don't use this class directly, use one of the specialized sub-classes
@@ -220,8 +225,105 @@ class MCRegisterInfo {
if (!advance())
List = nullptr;
}
+
+ template <class SubT> friend class MCRegisterInfo::mc_
diff list_iterator;
};
+ /// Forward iterator using DiffListIterator.
+ template <class SubT>
+ class mc_
diff list_iterator
+ : public iterator_facade_base<mc_
diff list_iterator<SubT>,
+ std::forward_iterator_tag, MCPhysReg> {
+ MCRegisterInfo::DiffListIterator Iter;
+ /// Current value as MCPhysReg, so we can return a reference to it.
+ MCPhysReg Val;
+
+ protected:
+ mc_
diff list_iterator(MCRegisterInfo::DiffListIterator Iter) : Iter(Iter) {}
+
+ // Allow conversion between instantiations where valid.
+ mc_
diff list_iterator(MCRegister Reg, const MCPhysReg *DiffList) {
+ Iter.init(Reg, DiffList);
+ Val = *Iter;
+ }
+
+ public:
+ // Allow default construction to build variables, but this doesn't build
+ // a useful iterator.
+ mc_
diff list_iterator() = default;
+
+ /// Return an iterator past the last element.
+ static SubT end() {
+ SubT End;
+ End.Iter.List = nullptr;
+ return End;
+ }
+
+ bool operator==(const mc_
diff list_iterator &Arg) const {
+ return Iter.List == Arg.Iter.List;
+ }
+
+ const MCPhysReg &operator*() const { return Val; }
+
+ using mc_
diff list_iterator::iterator_facade_base::operator++;
+ void operator++() {
+ assert(Iter.List && "Cannot increment the end iterator!");
+ ++Iter;
+ Val = *Iter;
+ }
+ };
+
+ /// Forward iterator over all sub-registers.
+ /// TODO: Replace remaining uses of MCSubRegIterator.
+ class mc_subreg_iterator : public mc_
diff list_iterator<mc_subreg_iterator> {
+ public:
+ mc_subreg_iterator(MCRegisterInfo::DiffListIterator Iter)
+ : mc_
diff list_iterator(Iter) {}
+ mc_subreg_iterator() = default;
+ mc_subreg_iterator(MCRegister Reg, const MCRegisterInfo *MCRI)
+ : mc_
diff list_iterator(Reg, MCRI->DiffLists + MCRI->get(Reg).SubRegs) {}
+ };
+
+ /// Forward iterator over all super-registers.
+ /// TODO: Replace remaining uses of MCSuperRegIterator.
+ class mc_superreg_iterator
+ : public mc_
diff list_iterator<mc_superreg_iterator> {
+ public:
+ mc_superreg_iterator(MCRegisterInfo::DiffListIterator Iter)
+ : mc_
diff list_iterator(Iter) {}
+ mc_superreg_iterator() = default;
+ mc_superreg_iterator(MCRegister Reg, const MCRegisterInfo *MCRI)
+ : mc_
diff list_iterator(Reg,
+ MCRI->DiffLists + MCRI->get(Reg).SuperRegs) {}
+ };
+
+ /// Return an iterator range over all sub-registers of \p Reg, excluding \p
+ /// Reg.
+ iterator_range<mc_subreg_iterator> subregs(MCRegister Reg) const {
+ return make_range(std::next(mc_subreg_iterator(Reg, this)),
+ mc_subreg_iterator::end());
+ }
+
+ /// Return an iterator range over all sub-registers of \p Reg, including \p
+ /// Reg.
+ iterator_range<mc_subreg_iterator> subregs_inclusive(MCRegister Reg) const {
+ return make_range({Reg, this}, mc_subreg_iterator::end());
+ }
+
+ /// Return an iterator range over all super-registers of \p Reg, excluding \p
+ /// Reg.
+ iterator_range<mc_superreg_iterator> superregs(MCRegister Reg) const {
+ return make_range(std::next(mc_superreg_iterator(Reg, this)),
+ mc_superreg_iterator::end());
+ }
+
+ /// Return an iterator range over all super-registers of \p Reg, including \p
+ /// Reg.
+ iterator_range<mc_superreg_iterator>
+ superregs_inclusive(MCRegister Reg) const {
+ return make_range({Reg, this}, mc_superreg_iterator::end());
+ }
+
// These iterators are allowed to sub-class DiffListIterator and access
// internal list pointers.
friend class MCSubRegIterator;
diff --git a/llvm/lib/CodeGen/MachineVerifier.cpp b/llvm/lib/CodeGen/MachineVerifier.cpp
index 517f2a941ba2..ca57e51268e8 100644
--- a/llvm/lib/CodeGen/MachineVerifier.cpp
+++ b/llvm/lib/CodeGen/MachineVerifier.cpp
@@ -124,8 +124,8 @@ namespace {
void addRegWithSubRegs(RegVector &RV, unsigned Reg) {
RV.push_back(Reg);
if (Register::isPhysicalRegister(Reg))
- for (MCSubRegIterator SubRegs(Reg, TRI); SubRegs.isValid(); ++SubRegs)
- RV.push_back(*SubRegs);
+ for (const MCPhysReg &SubReg : TRI->subregs(Reg))
+ RV.push_back(SubReg);
}
struct BBInfo {
@@ -802,18 +802,16 @@ MachineVerifier::visitMachineBasicBlockBefore(const MachineBasicBlock *MBB) {
report("MBB live-in list contains non-physical register", MBB);
continue;
}
- for (MCSubRegIterator SubRegs(LI.PhysReg, TRI, /*IncludeSelf=*/true);
- SubRegs.isValid(); ++SubRegs)
- regsLive.insert(*SubRegs);
+ for (const MCPhysReg &SubReg : TRI->subregs_inclusive(LI.PhysReg))
+ regsLive.insert(SubReg);
}
}
const MachineFrameInfo &MFI = MF->getFrameInfo();
BitVector PR = MFI.getPristineRegs(*MF);
for (unsigned I : PR.set_bits()) {
- for (MCSubRegIterator SubRegs(I, TRI, /*IncludeSelf=*/true);
- SubRegs.isValid(); ++SubRegs)
- regsLive.insert(*SubRegs);
+ for (const MCPhysReg &SubReg : TRI->subregs_inclusive(I))
+ regsLive.insert(SubReg);
}
regsKilled.clear();
@@ -2016,9 +2014,9 @@ void MachineVerifier::checkLiveness(const MachineOperand *MO, unsigned MONum) {
bool Bad = !isReserved(Reg);
// We are fine if just any subregister has a defined value.
if (Bad) {
- for (MCSubRegIterator SubRegs(Reg, TRI); SubRegs.isValid();
- ++SubRegs) {
- if (regsLive.count(*SubRegs)) {
+
+ for (const MCPhysReg &SubReg : TRI->subregs(Reg)) {
+ if (regsLive.count(SubReg)) {
Bad = false;
break;
}
@@ -2036,9 +2034,8 @@ void MachineVerifier::checkLiveness(const MachineOperand *MO, unsigned MONum) {
if (!Register::isPhysicalRegister(MOP.getReg()))
continue;
- for (MCSubRegIterator SubRegs(MOP.getReg(), TRI); SubRegs.isValid();
- ++SubRegs) {
- if (*SubRegs == Reg) {
+ for (const MCPhysReg &SubReg : TRI->subregs(MOP.getReg())) {
+ if (SubReg == Reg) {
Bad = false;
break;
}
diff --git a/llvm/lib/CodeGen/RegisterScavenging.cpp b/llvm/lib/CodeGen/RegisterScavenging.cpp
index 270209293f6a..a5bea1463468 100644
--- a/llvm/lib/CodeGen/RegisterScavenging.cpp
+++ b/llvm/lib/CodeGen/RegisterScavenging.cpp
@@ -221,8 +221,8 @@ void RegScavenger::forward() {
// Ideally we would like a way to model this, but leaving the
// insert_subreg around causes both correctness and performance issues.
bool SubUsed = false;
- for (MCSubRegIterator SubRegs(Reg, TRI); SubRegs.isValid(); ++SubRegs)
- if (isRegUsed(*SubRegs)) {
+ for (const MCPhysReg &SubReg : TRI->subregs(Reg))
+ if (isRegUsed(SubReg)) {
SubUsed = true;
break;
}
diff --git a/llvm/lib/Target/Mips/MCTargetDesc/MipsOptionRecord.cpp b/llvm/lib/Target/Mips/MCTargetDesc/MipsOptionRecord.cpp
index 3ff9c722484b..bdfb70aa9813 100644
--- a/llvm/lib/Target/Mips/MCTargetDesc/MipsOptionRecord.cpp
+++ b/llvm/lib/Target/Mips/MCTargetDesc/MipsOptionRecord.cpp
@@ -74,27 +74,23 @@ void MipsRegInfoRecord::SetPhysRegUsed(unsigned Reg,
const MCRegisterInfo *MCRegInfo) {
unsigned Value = 0;
- for (MCSubRegIterator SubRegIt(Reg, MCRegInfo, true); SubRegIt.isValid();
- ++SubRegIt) {
- unsigned CurrentSubReg = *SubRegIt;
-
- unsigned EncVal = MCRegInfo->getEncodingValue(CurrentSubReg);
+ for (const MCPhysReg &SubReg : MCRegInfo->subregs_inclusive(Reg)) {
+ unsigned EncVal = MCRegInfo->getEncodingValue(SubReg);
Value |= 1 << EncVal;
- if (GPR32RegClass->contains(CurrentSubReg) ||
- GPR64RegClass->contains(CurrentSubReg))
+ if (GPR32RegClass->contains(SubReg) || GPR64RegClass->contains(SubReg))
ri_gprmask |= Value;
- else if (COP0RegClass->contains(CurrentSubReg))
+ else if (COP0RegClass->contains(SubReg))
ri_cprmask[0] |= Value;
// MIPS COP1 is the FPU.
- else if (FGR32RegClass->contains(CurrentSubReg) ||
- FGR64RegClass->contains(CurrentSubReg) ||
- AFGR64RegClass->contains(CurrentSubReg) ||
- MSA128BRegClass->contains(CurrentSubReg))
+ else if (FGR32RegClass->contains(SubReg) ||
+ FGR64RegClass->contains(SubReg) ||
+ AFGR64RegClass->contains(SubReg) ||
+ MSA128BRegClass->contains(SubReg))
ri_cprmask[1] |= Value;
- else if (COP2RegClass->contains(CurrentSubReg))
+ else if (COP2RegClass->contains(SubReg))
ri_cprmask[2] |= Value;
- else if (COP3RegClass->contains(CurrentSubReg))
+ else if (COP3RegClass->contains(SubReg))
ri_cprmask[3] |= Value;
}
}
diff --git a/llvm/lib/Target/X86/X86RegisterInfo.cpp b/llvm/lib/Target/X86/X86RegisterInfo.cpp
index 3809a14178fd..f69626b2622e 100644
--- a/llvm/lib/Target/X86/X86RegisterInfo.cpp
+++ b/llvm/lib/Target/X86/X86RegisterInfo.cpp
@@ -530,23 +530,20 @@ BitVector X86RegisterInfo::getReservedRegs(const MachineFunction &MF) const {
Reserved.set(X86::MXCSR);
// Set the stack-pointer register and its aliases as reserved.
- for (MCSubRegIterator I(X86::RSP, this, /*IncludeSelf=*/true); I.isValid();
- ++I)
- Reserved.set(*I);
+ for (const MCPhysReg &SubReg : subregs_inclusive(X86::RSP))
+ Reserved.set(SubReg);
// Set the Shadow Stack Pointer as reserved.
Reserved.set(X86::SSP);
// Set the instruction pointer register and its aliases as reserved.
- for (MCSubRegIterator I(X86::RIP, this, /*IncludeSelf=*/true); I.isValid();
- ++I)
- Reserved.set(*I);
+ for (const MCPhysReg &SubReg : subregs_inclusive(X86::RIP))
+ Reserved.set(SubReg);
// Set the frame-pointer register and its aliases as reserved if needed.
if (TFI->hasFP(MF)) {
- for (MCSubRegIterator I(X86::RBP, this, /*IncludeSelf=*/true); I.isValid();
- ++I)
- Reserved.set(*I);
+ for (const MCPhysReg &SubReg : subregs_inclusive(X86::RBP))
+ Reserved.set(SubReg);
}
// Set the base-pointer register and its aliases as reserved if needed.
@@ -559,9 +556,8 @@ BitVector X86RegisterInfo::getReservedRegs(const MachineFunction &MF) const {
"this calling convention.");
Register BasePtr = getX86SubSuperRegister(getBaseRegister(), 64);
- for (MCSubRegIterator I(BasePtr, this, /*IncludeSelf=*/true);
- I.isValid(); ++I)
- Reserved.set(*I);
+ for (const MCPhysReg &SubReg : subregs_inclusive(BasePtr))
+ Reserved.set(SubReg);
}
// Mark the segment registers as reserved.
More information about the llvm-commits
mailing list