Implement ARMBaseRegisterInfo::getRegAllocationHints().

This provides the same functionality as getRawAllocationOrder() for the
even/odd hints, but without the many constant register arrays.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@169169 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Jakob Stoklund Olesen 2012-12-03 22:35:35 +00:00
parent bfeecc1306
commit 303da1baf2
2 changed files with 65 additions and 0 deletions

View File

@ -26,6 +26,7 @@
#include "llvm/CodeGen/MachineInstrBuilder.h"
#include "llvm/CodeGen/MachineRegisterInfo.h"
#include "llvm/CodeGen/RegisterScavenging.h"
#include "llvm/CodeGen/VirtRegMap.h"
#include "llvm/Constants.h"
#include "llvm/DerivedTypes.h"
#include "llvm/Function.h"
@ -173,6 +174,64 @@ ARMBaseRegisterInfo::getRegPressureLimit(const TargetRegisterClass *RC,
}
}
// Get the other register in a GPRPair.
static unsigned getPairedGPR(unsigned Reg, bool Odd, const MCRegisterInfo *RI) {
for (MCSuperRegIterator Supers(Reg, RI); Supers.isValid(); ++Supers)
if (ARM::GPRPairRegClass.contains(*Supers))
return RI->getSubReg(*Supers, Odd ? ARM::gsub_1 : ARM::gsub_0);
return 0;
}
// Resolve the RegPairEven / RegPairOdd register allocator hints.
void
ARMBaseRegisterInfo::getRegAllocationHints(unsigned VirtReg,
ArrayRef<MCPhysReg> Order,
SmallVectorImpl<MCPhysReg> &Hints,
const MachineFunction &MF,
const VirtRegMap *VRM) const {
const MachineRegisterInfo &MRI = MF.getRegInfo();
std::pair<unsigned, unsigned> Hint = MRI.getRegAllocationHint(VirtReg);
unsigned Odd;
switch (Hint.first) {
case ARMRI::RegPairEven:
Odd = 0;
break;
case ARMRI::RegPairOdd:
Odd = 1;
break;
default:
TargetRegisterInfo::getRegAllocationHints(VirtReg, Order, Hints, MF, VRM);
return;
}
// This register should preferably be even (Odd == 0) or odd (Odd == 1).
// Check if the other part of the pair has already been assigned, and provide
// the paired register as the first hint.
unsigned PairedPhys = 0;
if (VRM && VRM->hasPhys(Hint.second)) {
PairedPhys = getPairedGPR(VRM->getPhys(Hint.second), Odd, this);
if (PairedPhys && MRI.isReserved(PairedPhys))
PairedPhys = 0;
}
// First prefer the paired physreg.
if (PairedPhys)
Hints.push_back(PairedPhys);
// Then prefer even or odd registers.
for (unsigned I = 0, E = Order.size(); I != E; ++I) {
unsigned Reg = Order[I];
if (Reg == PairedPhys || (getEncodingValue(Reg) & 1) != Odd)
continue;
// Don't provide hints that are paired to a reserved register.
unsigned Paired = getPairedGPR(Reg, !Odd, this);
if (!Paired || MRI.isReserved(Paired))
continue;
Hints.push_back(Reg);
}
}
/// getRawAllocationOrder - Returns the register allocation order for a
/// specified register class with a target-dependent hint.
ArrayRef<uint16_t>

View File

@ -115,6 +115,12 @@ public:
unsigned HintType, unsigned HintReg,
const MachineFunction &MF) const;
void getRegAllocationHints(unsigned VirtReg,
ArrayRef<MCPhysReg> Order,
SmallVectorImpl<MCPhysReg> &Hints,
const MachineFunction &MF,
const VirtRegMap *VRM) const;
unsigned ResolveRegAllocHint(unsigned Type, unsigned Reg,
const MachineFunction &MF) const;