1
0
mirror of https://github.com/RPCS3/llvm-mirror.git synced 2024-10-20 03:23:01 +02:00

Make spiller push stores right after the definition of a register so

that they are as far away from the loads as possible.

llvm-svn: 11895
This commit is contained in:
Alkis Evlogimenos 2004-02-27 04:51:35 +00:00
parent 3093de5bfb
commit 63fda9c474

View File

@ -23,6 +23,7 @@
#include "llvm/Target/TargetInstrInfo.h"
#include "Support/Statistic.h"
#include "Support/Debug.h"
#include "Support/DenseMap.h"
#include "Support/STLExtras.h"
#include <iostream>
@ -73,6 +74,7 @@ namespace {
class Spiller {
typedef std::vector<unsigned> Phys2VirtMap;
typedef std::vector<bool> PhysFlag;
typedef DenseMap<MachineInstr*, VirtReg2IndexFunctor> Virt2MI;
MachineFunction& mf_;
const TargetMachine& tm_;
@ -81,6 +83,7 @@ namespace {
const VirtRegMap& vrm_;
Phys2VirtMap p2vMap_;
PhysFlag dirty_;
Virt2MI lastDef_;
public:
Spiller(MachineFunction& mf, const VirtRegMap& vrm)
@ -90,7 +93,8 @@ namespace {
mri_(*tm_.getRegisterInfo()),
vrm_(vrm),
p2vMap_(mri_.getNumRegs(), 0),
dirty_(mri_.getNumRegs(), false) {
dirty_(mri_.getNumRegs(), false),
lastDef_() {
DEBUG(std::cerr << "********** REWRITE MACHINE CODE **********\n");
DEBUG(std::cerr << "********** Function: "
<< mf_.getFunction()->getName() << '\n');
@ -99,11 +103,13 @@ namespace {
void eliminateVirtRegs() {
for (MachineFunction::iterator mbbi = mf_.begin(),
mbbe = mf_.end(); mbbi != mbbe; ++mbbi) {
lastDef_.grow(mf_.getSSARegMap()->getLastVirtReg());
DEBUG(std::cerr << mbbi->getBasicBlock()->getName() << ":\n");
eliminateVirtRegsInMbb(*mbbi);
// clear map and dirty flag
// clear map, dirty flag and last ref
p2vMap_.assign(p2vMap_.size(), 0);
dirty_.assign(dirty_.size(), false);
lastDef_.clear();
}
}
@ -113,11 +119,21 @@ namespace {
unsigned physReg) {
unsigned virtReg = p2vMap_[physReg];
if (dirty_[physReg] && vrm_.hasStackSlot(virtReg)) {
mri_.storeRegToStackSlot(mbb, mii, physReg,
assert(lastDef_[virtReg] && "virtual register is mapped "
"to a register and but was not defined!");
MachineBasicBlock::iterator lastDef = lastDef_[virtReg];
MachineBasicBlock::iterator nextLastRef = next(lastDef);
mri_.storeRegToStackSlot(*lastDef->getParent(),
nextLastRef,
physReg,
vrm_.getStackSlot(virtReg),
mri_.getRegClass(physReg));
++numStores;
DEBUG(std::cerr << "*\t"; prior(mii)->print(std::cerr, tm_));
DEBUG(std::cerr << "\t\tadded: ";
prior(nextLastRef)->print(std::cerr, tm_);
std::cerr << "\t\tafter: ";
lastDef->print(std::cerr, tm_));
lastDef_[virtReg] = 0;
}
p2vMap_[physReg] = 0;
dirty_[physReg] = false;
@ -145,7 +161,11 @@ namespace {
vrm_.getStackSlot(virtReg),
mri_.getRegClass(physReg));
++numLoads;
DEBUG(std::cerr << "*\t"; prior(mii)->print(std::cerr,tm_));
DEBUG(std::cerr << "\t\tadded: ";
prior(mii)->print(std::cerr,tm_);
std::cerr << "\t\tbefore: ";
mii->print(std::cerr, tm_));
lastDef_[virtReg] = mii;
}
}
}
@ -160,6 +180,7 @@ namespace {
p2vMap_[physReg] = virtReg;
dirty_[physReg] = true;
lastDef_[virtReg] = mii;
}
void eliminateVirtRegsInMbb(MachineBasicBlock& mbb) {
@ -170,11 +191,15 @@ namespace {
MachineOperand& op = mii->getOperand(i);
if (op.isRegister() && op.getReg() && op.isUse() &&
MRegisterInfo::isVirtualRegister(op.getReg())) {
unsigned physReg = vrm_.getPhys(op.getReg());
handleUse(mbb, mii, op.getReg(), physReg);
unsigned virtReg = op.getReg();
unsigned physReg = vrm_.getPhys(virtReg);
handleUse(mbb, mii, virtReg, physReg);
mii->SetMachineOperandReg(i, physReg);
// mark as dirty if this is def&use
if (op.isDef()) dirty_[physReg] = true;
if (op.isDef()) {
dirty_[physReg] = true;
lastDef_[virtReg] = mii;
}
}
}