Add a argument to storeRegToStackSlot and storeRegToAddr to specify whether

the stored register is killed.


git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@44600 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Evan Cheng 2007-12-05 03:14:33 +00:00
parent f89a22a3d1
commit d64b5c82b9
24 changed files with 159 additions and 101 deletions

View File

@ -278,6 +278,9 @@ namespace llvm {
SmallVector<unsigned, 2> &Ops, SmallVector<unsigned, 2> &Ops,
bool isSS, int Slot, unsigned Reg); bool isSS, int Slot, unsigned Reg);
bool canFoldMemoryOperand(MachineInstr *MI,
SmallVector<unsigned, 2> &Ops) const;
/// anyKillInMBBAfterIdx - Returns true if there is a kill of the specified /// anyKillInMBBAfterIdx - Returns true if there is a kill of the specified
/// VNInfo that's after the specified index but is within the basic block. /// VNInfo that's after the specified index but is within the basic block.
bool anyKillInMBBAfterIdx(const LiveInterval &li, const VNInfo *VNI, bool anyKillInMBBAfterIdx(const LiveInterval &li, const VNInfo *VNI,
@ -304,7 +307,7 @@ namespace llvm {
/// rewriteInstructionForSpills, rewriteInstructionsForSpills - Helper functions /// rewriteInstructionForSpills, rewriteInstructionsForSpills - Helper functions
/// for addIntervalsForSpills to rewrite uses / defs for the given live range. /// for addIntervalsForSpills to rewrite uses / defs for the given live range.
void rewriteInstructionForSpills(const LiveInterval &li, bool TrySplit, bool rewriteInstructionForSpills(const LiveInterval &li, bool TrySplit,
unsigned id, unsigned index, unsigned end, MachineInstr *MI, unsigned id, unsigned index, unsigned end, MachineInstr *MI,
MachineInstr *OrigDefMI, MachineInstr *DefMI, unsigned Slot, int LdSlot, MachineInstr *OrigDefMI, MachineInstr *DefMI, unsigned Slot, int LdSlot,
bool isLoad, bool isLoadSS, bool DefIsReMat, bool CanDelete, bool isLoad, bool isLoadSS, bool DefIsReMat, bool CanDelete,

View File

@ -493,10 +493,10 @@ public:
virtual void storeRegToStackSlot(MachineBasicBlock &MBB, virtual void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const = 0; const TargetRegisterClass *RC) const = 0;
virtual void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, virtual void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const = 0; SmallVectorImpl<MachineInstr*> &NewMIs) const = 0;
@ -553,12 +553,12 @@ public:
return 0; return 0;
} }
/// getOpcodeAfterMemoryFold - Returns the opcode of the would be new /// canFoldMemoryOperand - Returns true if the specified load / store is
/// instruction after load / store is folded into an instruction of the /// folding is possible.
/// specified opcode. It returns zero if the specified unfolding is not virtual
/// possible. bool canFoldMemoryOperand(MachineInstr *MI,
virtual unsigned getOpcodeAfterMemoryFold(unsigned Opc, unsigned OpNum) const{ SmallVectorImpl<unsigned> &Ops) const{
return 0; return false;
} }
/// unfoldMemoryOperand - Separate a single instruction which folded a load or /// unfoldMemoryOperand - Separate a single instruction which folded a load or

View File

@ -253,7 +253,7 @@ void PEI::saveCalleeSavedRegisters(MachineFunction &Fn) {
MBB->addLiveIn(CSI[i].getReg()); MBB->addLiveIn(CSI[i].getReg());
// Insert the spill to the stack frame. // Insert the spill to the stack frame.
RegInfo->storeRegToStackSlot(*MBB, I, CSI[i].getReg(), RegInfo->storeRegToStackSlot(*MBB, I, CSI[i].getReg(), true,
CSI[i].getFrameIdx(), CSI[i].getRegClass()); CSI[i].getFrameIdx(), CSI[i].getRegClass());
} }
} }

View File

@ -329,7 +329,7 @@ void RABigBlock::spillVirtReg(MachineBasicBlock &MBB,
const TargetRegisterClass *RC = MF->getSSARegMap()->getRegClass(VirtReg); const TargetRegisterClass *RC = MF->getSSARegMap()->getRegClass(VirtReg);
int FrameIndex = getStackSpaceFor(VirtReg, RC); int FrameIndex = getStackSpaceFor(VirtReg, RC);
DOUT << " to stack slot #" << FrameIndex; DOUT << " to stack slot #" << FrameIndex;
RegInfo->storeRegToStackSlot(MBB, I, PhysReg, FrameIndex, RC); RegInfo->storeRegToStackSlot(MBB, I, PhysReg, true, FrameIndex, RC);
++NumStores; // Update statistics ++NumStores; // Update statistics
} }

View File

@ -286,7 +286,7 @@ void RALocal::spillVirtReg(MachineBasicBlock &MBB,
const TargetRegisterClass *RC = MF->getSSARegMap()->getRegClass(VirtReg); const TargetRegisterClass *RC = MF->getSSARegMap()->getRegClass(VirtReg);
int FrameIndex = getStackSpaceFor(VirtReg, RC); int FrameIndex = getStackSpaceFor(VirtReg, RC);
DOUT << " to stack slot #" << FrameIndex; DOUT << " to stack slot #" << FrameIndex;
RegInfo->storeRegToStackSlot(MBB, I, PhysReg, FrameIndex, RC); RegInfo->storeRegToStackSlot(MBB, I, PhysReg, true, FrameIndex, RC);
++NumStores; // Update statistics ++NumStores; // Update statistics
} }

View File

@ -156,7 +156,7 @@ void RegAllocSimple::spillVirtReg(MachineBasicBlock &MBB,
// Add move instruction(s) // Add move instruction(s)
++NumStores; ++NumStores;
RegInfo->storeRegToStackSlot(MBB, I, PhysReg, FrameIdx, RC); RegInfo->storeRegToStackSlot(MBB, I, PhysReg, true, FrameIdx, RC);
} }

View File

@ -282,7 +282,7 @@ unsigned RegScavenger::scavengeRegister(const TargetRegisterClass *RC,
RegInfo->eliminateFrameIndex(II, SPAdj, this); RegInfo->eliminateFrameIndex(II, SPAdj, this);
} }
RegInfo->storeRegToStackSlot(*MBB, I, SReg, ScavengingFrameIndex, RC); RegInfo->storeRegToStackSlot(*MBB, I, SReg, true, ScavengingFrameIndex, RC);
MachineBasicBlock::iterator II = prior(I); MachineBasicBlock::iterator II = prior(I);
RegInfo->eliminateFrameIndex(II, SPAdj, this); RegInfo->eliminateFrameIndex(II, SPAdj, this);
ScavengedReg = SReg; ScavengedReg = SReg;

View File

@ -208,7 +208,8 @@ bool SimpleSpiller::runOnMachineFunction(MachineFunction &MF, VirtRegMap &VRM) {
} }
if (MO.isDef()) { if (MO.isDef()) {
MRI.storeRegToStackSlot(MBB, next(MII), PhysReg, StackSlot, RC); MRI.storeRegToStackSlot(MBB, next(MII), PhysReg, true,
StackSlot, RC);
++NumStores; ++NumStores;
} }
} }
@ -861,7 +862,7 @@ void LocalSpiller::SpillRegToStackSlot(MachineBasicBlock &MBB,
BitVector &RegKills, BitVector &RegKills,
std::vector<MachineOperand*> &KillOps, std::vector<MachineOperand*> &KillOps,
VirtRegMap &VRM) { VirtRegMap &VRM) {
MRI->storeRegToStackSlot(MBB, next(MII), PhysReg, StackSlot, RC); MRI->storeRegToStackSlot(MBB, next(MII), PhysReg, true, StackSlot, RC);
DOUT << "Store:\t" << *next(MII); DOUT << "Store:\t" << *next(MII);
// If there is a dead store to this stack slot, nuke it now. // If there is a dead store to this stack slot, nuke it now.
@ -984,9 +985,10 @@ void LocalSpiller::RewriteMBB(MachineBasicBlock &MBB, VirtRegMap &VRM) {
const TargetRegisterClass *RC = RegMap->getRegClass(VirtReg); const TargetRegisterClass *RC = RegMap->getRegClass(VirtReg);
unsigned Phys = VRM.getPhys(VirtReg); unsigned Phys = VRM.getPhys(VirtReg);
int StackSlot = VRM.getStackSlot(VirtReg); int StackSlot = VRM.getStackSlot(VirtReg);
MRI->storeRegToStackSlot(MBB, next(MII), Phys, StackSlot, RC); MRI->storeRegToStackSlot(MBB, next(MII), Phys, false, StackSlot, RC);
DOUT << "Store:\t" << *next(MII); MachineInstr *StoreMI = next(MII);
VRM.virtFolded(VirtReg, next(MII), VirtRegMap::isMod); DOUT << "Store:\t" << StoreMI;
VRM.virtFolded(VirtReg, StoreMI, VirtRegMap::isMod);
} }
NextMII = next(MII); NextMII = next(MII);
} }
@ -1011,12 +1013,6 @@ void LocalSpiller::RewriteMBB(MachineBasicBlock &MBB, VirtRegMap &VRM) {
assert(MRegisterInfo::isVirtualRegister(VirtReg) && assert(MRegisterInfo::isVirtualRegister(VirtReg) &&
"Not a virtual or a physical register?"); "Not a virtual or a physical register?");
// Assumes this is the last use of a split interval. IsKill will be unset
// if reg is use later unless it's a two-address operand.
if (MO.isUse() && VRM.getPreSplitReg(VirtReg) &&
TID->getOperandConstraint(i, TOI::TIED_TO) == -1)
MI.getOperand(i).setIsKill();
unsigned SubIdx = MO.getSubReg(); unsigned SubIdx = MO.getSubReg();
if (VRM.isAssignedReg(VirtReg)) { if (VRM.isAssignedReg(VirtReg)) {
// This virtual register was assigned a physreg! // This virtual register was assigned a physreg!

View File

@ -158,31 +158,32 @@ static const MachineInstrBuilder &ARMInstrAddOperand(MachineInstrBuilder &MIB,
void ARMRegisterInfo:: void ARMRegisterInfo::
storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
unsigned SrcReg, int FI, unsigned SrcReg, bool isKill, int FI,
const TargetRegisterClass *RC) const { const TargetRegisterClass *RC) const {
if (RC == ARM::GPRRegisterClass) { if (RC == ARM::GPRRegisterClass) {
MachineFunction &MF = *MBB.getParent(); MachineFunction &MF = *MBB.getParent();
ARMFunctionInfo *AFI = MF.getInfo<ARMFunctionInfo>(); ARMFunctionInfo *AFI = MF.getInfo<ARMFunctionInfo>();
if (AFI->isThumbFunction()) if (AFI->isThumbFunction())
BuildMI(MBB, I, TII.get(ARM::tSpill)).addReg(SrcReg, false, false, true) BuildMI(MBB, I, TII.get(ARM::tSpill)).addReg(SrcReg, false, false, isKill)
.addFrameIndex(FI).addImm(0); .addFrameIndex(FI).addImm(0);
else else
AddDefaultPred(BuildMI(MBB, I, TII.get(ARM::STR)) AddDefaultPred(BuildMI(MBB, I, TII.get(ARM::STR))
.addReg(SrcReg, false, false, true) .addReg(SrcReg, false, false, isKill)
.addFrameIndex(FI).addReg(0).addImm(0)); .addFrameIndex(FI).addReg(0).addImm(0));
} else if (RC == ARM::DPRRegisterClass) { } else if (RC == ARM::DPRRegisterClass) {
AddDefaultPred(BuildMI(MBB, I, TII.get(ARM::FSTD)) AddDefaultPred(BuildMI(MBB, I, TII.get(ARM::FSTD))
.addReg(SrcReg, false, false, true) .addReg(SrcReg, false, false, isKill)
.addFrameIndex(FI).addImm(0)); .addFrameIndex(FI).addImm(0));
} else { } else {
assert(RC == ARM::SPRRegisterClass && "Unknown regclass!"); assert(RC == ARM::SPRRegisterClass && "Unknown regclass!");
AddDefaultPred(BuildMI(MBB, I, TII.get(ARM::FSTS)) AddDefaultPred(BuildMI(MBB, I, TII.get(ARM::FSTS))
.addReg(SrcReg, false, false, true) .addReg(SrcReg, false, false, isKill)
.addFrameIndex(FI).addImm(0)); .addFrameIndex(FI).addImm(0));
} }
} }
void ARMRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void ARMRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
@ -192,7 +193,7 @@ void ARMRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
if (AFI->isThumbFunction()) { if (AFI->isThumbFunction()) {
Opc = Addr[0].isFrameIndex() ? ARM::tSpill : ARM::tSTR; Opc = Addr[0].isFrameIndex() ? ARM::tSpill : ARM::tSTR;
MachineInstrBuilder MIB = MachineInstrBuilder MIB =
BuildMI(TII.get(Opc)).addReg(SrcReg, false, false, true); BuildMI(TII.get(Opc)).addReg(SrcReg, false, false, isKill);
for (unsigned i = 0, e = Addr.size(); i != e; ++i) for (unsigned i = 0, e = Addr.size(); i != e; ++i)
MIB = ARMInstrAddOperand(MIB, Addr[i]); MIB = ARMInstrAddOperand(MIB, Addr[i]);
NewMIs.push_back(MIB); NewMIs.push_back(MIB);
@ -207,7 +208,7 @@ void ARMRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
} }
MachineInstrBuilder MIB = MachineInstrBuilder MIB =
BuildMI(TII.get(Opc)).addReg(SrcReg, false, false, true); BuildMI(TII.get(Opc)).addReg(SrcReg, false, false, isKill);
for (unsigned i = 0, e = Addr.size(); i != e; ++i) for (unsigned i = 0, e = Addr.size(); i != e; ++i)
MIB = ARMInstrAddOperand(MIB, Addr[i]); MIB = ARMInstrAddOperand(MIB, Addr[i]);
AddDefaultPred(MIB); AddDefaultPred(MIB);
@ -426,6 +427,39 @@ MachineInstr *ARMRegisterInfo::foldMemoryOperand(MachineInstr *MI,
return NewMI; return NewMI;
} }
bool ARMRegisterInfo::canFoldMemoryOperand(MachineInstr *MI,
SmallVectorImpl<unsigned> &Ops) const {
if (Ops.size() != 1) return NULL;
unsigned OpNum = Ops[0];
unsigned Opc = MI->getOpcode();
switch (Opc) {
default: break;
case ARM::MOVr:
// If it is updating CPSR, then it cannot be foled.
return MI->getOperand(4).getReg() != ARM::CPSR;
case ARM::tMOVr: {
if (OpNum == 0) { // move -> store
unsigned SrcReg = MI->getOperand(1).getReg();
if (isPhysicalRegister(SrcReg) && !isLowRegister(SrcReg))
// tSpill cannot take a high register operand.
return false;
} else { // move -> load
unsigned DstReg = MI->getOperand(0).getReg();
if (isPhysicalRegister(DstReg) && !isLowRegister(DstReg))
// tRestore cannot target a high register operand.
return false;
}
return true;
}
case ARM::FCPYS:
case ARM::FCPYD:
return true;
}
return false;
}
const unsigned* const unsigned*
ARMRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const { ARMRegisterInfo::getCalleeSavedRegs(const MachineFunction *MF) const {
static const unsigned CalleeSavedRegs[] = { static const unsigned CalleeSavedRegs[] = {

View File

@ -48,10 +48,10 @@ public:
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, MachineBasicBlock::iterator MBBI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;
@ -84,6 +84,9 @@ public:
return 0; return 0;
} }
bool canFoldMemoryOperand(MachineInstr *MI,
SmallVectorImpl<unsigned> &Ops) const;
const unsigned *getCalleeSavedRegs(const MachineFunction *MF = 0) const; const unsigned *getCalleeSavedRegs(const MachineFunction *MF = 0) const;
const TargetRegisterClass* const* const TargetRegisterClass* const*

View File

@ -61,28 +61,29 @@ AlphaRegisterInfo::AlphaRegisterInfo(const TargetInstrInfo &tii)
void void
AlphaRegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB, AlphaRegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIdx, unsigned SrcReg, bool isKill, int FrameIdx,
const TargetRegisterClass *RC) const { const TargetRegisterClass *RC) const {
//cerr << "Trying to store " << getPrettyName(SrcReg) << " to " //cerr << "Trying to store " << getPrettyName(SrcReg) << " to "
// << FrameIdx << "\n"; // << FrameIdx << "\n";
//BuildMI(MBB, MI, Alpha::WTF, 0).addReg(SrcReg); //BuildMI(MBB, MI, Alpha::WTF, 0).addReg(SrcReg);
if (RC == Alpha::F4RCRegisterClass) if (RC == Alpha::F4RCRegisterClass)
BuildMI(MBB, MI, TII.get(Alpha::STS)) BuildMI(MBB, MI, TII.get(Alpha::STS))
.addReg(SrcReg, false, false, true) .addReg(SrcReg, false, false, isKill)
.addFrameIndex(FrameIdx).addReg(Alpha::F31); .addFrameIndex(FrameIdx).addReg(Alpha::F31);
else if (RC == Alpha::F8RCRegisterClass) else if (RC == Alpha::F8RCRegisterClass)
BuildMI(MBB, MI, TII.get(Alpha::STT)) BuildMI(MBB, MI, TII.get(Alpha::STT))
.addReg(SrcReg, false, false, true) .addReg(SrcReg, false, false, isKill)
.addFrameIndex(FrameIdx).addReg(Alpha::F31); .addFrameIndex(FrameIdx).addReg(Alpha::F31);
else if (RC == Alpha::GPRCRegisterClass) else if (RC == Alpha::GPRCRegisterClass)
BuildMI(MBB, MI, TII.get(Alpha::STQ)) BuildMI(MBB, MI, TII.get(Alpha::STQ))
.addReg(SrcReg, false, false, true) .addReg(SrcReg, false, false, isKill)
.addFrameIndex(FrameIdx).addReg(Alpha::F31); .addFrameIndex(FrameIdx).addReg(Alpha::F31);
else else
abort(); abort();
} }
void AlphaRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void AlphaRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
@ -96,7 +97,7 @@ void AlphaRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
else else
abort(); abort();
MachineInstrBuilder MIB = MachineInstrBuilder MIB =
BuildMI(TII.get(Opc)).addReg(SrcReg, false, false, true); BuildMI(TII.get(Opc)).addReg(SrcReg, false, false, isKill);
for (unsigned i = 0, e = Addr.size(); i != e; ++i) { for (unsigned i = 0, e = Addr.size(); i != e; ++i) {
MachineOperand &MO = Addr[i]; MachineOperand &MO = Addr[i];
if (MO.isRegister()) if (MO.isRegister())

View File

@ -30,10 +30,10 @@ struct AlphaRegisterInfo : public AlphaGenRegisterInfo {
/// Code Generation virtual methods... /// Code Generation virtual methods...
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, MachineBasicBlock::iterator MBBI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;

View File

@ -194,7 +194,7 @@ SPURegisterInfo::SPURegisterInfo(const SPUSubtarget &subtarget,
void void
SPURegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB, SPURegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIdx, unsigned SrcReg, bool isKill, int FrameIdx,
const TargetRegisterClass *RC) const const TargetRegisterClass *RC) const
{ {
MachineOpCode opc; MachineOpCode opc;
@ -227,10 +227,12 @@ SPURegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
abort(); abort();
} }
addFrameReference(BuildMI(MBB, MI, TII.get(opc)).addReg(SrcReg), FrameIdx); addFrameReference(BuildMI(MBB, MI, TII.get(opc))
.addReg(SrcReg, false, false, isKill), FrameIdx);
} }
void SPURegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void SPURegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
@ -258,7 +260,7 @@ void SPURegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
abort(); abort();
} }
MachineInstrBuilder MIB = BuildMI(TII.get(Opc)) MachineInstrBuilder MIB = BuildMI(TII.get(Opc))
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
for (unsigned i = 0, e = Addr.size(); i != e; ++i) { for (unsigned i = 0, e = Addr.size(); i != e; ++i) {
MachineOperand &MO = Addr[i]; MachineOperand &MO = Addr[i];
if (MO.isRegister()) if (MO.isRegister())

View File

@ -44,11 +44,11 @@ namespace llvm {
//! Store a register to a stack slot, based on its register class. //! Store a register to a stack slot, based on its register class.
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, MachineBasicBlock::iterator MBBI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
//! Store a register to an address, based on its register class //! Store a register to an address, based on its register class
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;

View File

@ -38,22 +38,23 @@ IA64RegisterInfo::IA64RegisterInfo(const TargetInstrInfo &tii)
void IA64RegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB, void IA64RegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIdx, unsigned SrcReg, bool isKill,
int FrameIdx,
const TargetRegisterClass *RC) const{ const TargetRegisterClass *RC) const{
if (RC == IA64::FPRegisterClass) { if (RC == IA64::FPRegisterClass) {
BuildMI(MBB, MI, TII.get(IA64::STF_SPILL)).addFrameIndex(FrameIdx) BuildMI(MBB, MI, TII.get(IA64::STF_SPILL)).addFrameIndex(FrameIdx)
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
} else if (RC == IA64::GRRegisterClass) { } else if (RC == IA64::GRRegisterClass) {
BuildMI(MBB, MI, TII.get(IA64::ST8)).addFrameIndex(FrameIdx) BuildMI(MBB, MI, TII.get(IA64::ST8)).addFrameIndex(FrameIdx)
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
} else if (RC == IA64::PRRegisterClass) { } else if (RC == IA64::PRRegisterClass) {
/* we use IA64::r2 as a temporary register for doing this hackery. */ /* we use IA64::r2 as a temporary register for doing this hackery. */
// first we load 0: // first we load 0:
BuildMI(MBB, MI, TII.get(IA64::MOV), IA64::r2).addReg(IA64::r0); BuildMI(MBB, MI, TII.get(IA64::MOV), IA64::r2).addReg(IA64::r0);
// then conditionally add 1: // then conditionally add 1:
BuildMI(MBB, MI, TII.get(IA64::CADDIMM22), IA64::r2).addReg(IA64::r2) BuildMI(MBB, MI, TII.get(IA64::CADDIMM22), IA64::r2).addReg(IA64::r2)
.addImm(1).addReg(SrcReg, false, false, true); .addImm(1).addReg(SrcReg, false, false, isKill);
// and then store it to the stack // and then store it to the stack
BuildMI(MBB, MI, TII.get(IA64::ST8)).addFrameIndex(FrameIdx).addReg(IA64::r2); BuildMI(MBB, MI, TII.get(IA64::ST8)).addFrameIndex(FrameIdx).addReg(IA64::r2);
} else assert(0 && } else assert(0 &&
@ -61,6 +62,7 @@ void IA64RegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
} }
void IA64RegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void IA64RegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
@ -86,7 +88,7 @@ void IA64RegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
else else
MIB.addFrameIndex(MO.getFrameIndex()); MIB.addFrameIndex(MO.getFrameIndex());
} }
MIB.addReg(SrcReg, false, false, true); MIB.addReg(SrcReg, false, false, isKill);
NewMIs.push_back(MIB); NewMIs.push_back(MIB);
return; return;

View File

@ -31,10 +31,10 @@ struct IA64RegisterInfo : public IA64GenRegisterInfo {
/// Code Generation virtual methods... /// Code Generation virtual methods...
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;

View File

@ -85,24 +85,25 @@ getRegisterNumbering(unsigned RegEnum)
void MipsRegisterInfo:: void MipsRegisterInfo::
storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
unsigned SrcReg, int FI, unsigned SrcReg, bool isKill, int FI,
const TargetRegisterClass *RC) const const TargetRegisterClass *RC) const
{ {
if (RC == Mips::CPURegsRegisterClass) if (RC == Mips::CPURegsRegisterClass)
BuildMI(MBB, I, TII.get(Mips::SW)).addReg(SrcReg, false, false, true) BuildMI(MBB, I, TII.get(Mips::SW)).addReg(SrcReg, false, false, isKill)
.addImm(0).addFrameIndex(FI); .addImm(0).addFrameIndex(FI);
else else
assert(0 && "Can't store this register to stack slot"); assert(0 && "Can't store this register to stack slot");
} }
void MipsRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void MipsRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
if (RC != Mips::CPURegsRegisterClass) if (RC != Mips::CPURegsRegisterClass)
assert(0 && "Can't store this register"); assert(0 && "Can't store this register");
MachineInstrBuilder MIB = BuildMI(TII.get(Mips::SW)) MachineInstrBuilder MIB = BuildMI(TII.get(Mips::SW))
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
for (unsigned i = 0, e = Addr.size(); i != e; ++i) { for (unsigned i = 0, e = Addr.size(); i != e; ++i) {
MachineOperand &MO = Addr[i]; MachineOperand &MO = Addr[i];
if (MO.isRegister()) if (MO.isRegister())

View File

@ -34,10 +34,10 @@ struct MipsRegisterInfo : public MipsGenRegisterInfo {
/// Code Generation virtual methods... /// Code Generation virtual methods...
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, MachineBasicBlock::iterator MBBI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;

View File

@ -104,39 +104,39 @@ PPCRegisterInfo::PPCRegisterInfo(const PPCSubtarget &ST,
} }
static void StoreRegToStackSlot(const TargetInstrInfo &TII, static void StoreRegToStackSlot(const TargetInstrInfo &TII,
unsigned SrcReg, int FrameIdx, unsigned SrcReg, bool isKill, int FrameIdx,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) { SmallVectorImpl<MachineInstr*> &NewMIs) {
if (RC == PPC::GPRCRegisterClass) { if (RC == PPC::GPRCRegisterClass) {
if (SrcReg != PPC::LR) { if (SrcReg != PPC::LR) {
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STW)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STW))
.addReg(SrcReg, false, false, true), FrameIdx)); .addReg(SrcReg, false, false, isKill), FrameIdx));
} else { } else {
// FIXME: this spills LR immediately to memory in one step. To do this, // FIXME: this spills LR immediately to memory in one step. To do this,
// we use R11, which we know cannot be used in the prolog/epilog. This is // we use R11, which we know cannot be used in the prolog/epilog. This is
// a hack. // a hack.
NewMIs.push_back(BuildMI(TII.get(PPC::MFLR), PPC::R11)); NewMIs.push_back(BuildMI(TII.get(PPC::MFLR), PPC::R11));
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STW)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STW))
.addReg(PPC::R11, false, false, true), FrameIdx)); .addReg(PPC::R11, false, false, isKill), FrameIdx));
} }
} else if (RC == PPC::G8RCRegisterClass) { } else if (RC == PPC::G8RCRegisterClass) {
if (SrcReg != PPC::LR8) { if (SrcReg != PPC::LR8) {
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STD)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STD))
.addReg(SrcReg, false, false, true), FrameIdx)); .addReg(SrcReg, false, false, isKill), FrameIdx));
} else { } else {
// FIXME: this spills LR immediately to memory in one step. To do this, // FIXME: this spills LR immediately to memory in one step. To do this,
// we use R11, which we know cannot be used in the prolog/epilog. This is // we use R11, which we know cannot be used in the prolog/epilog. This is
// a hack. // a hack.
NewMIs.push_back(BuildMI(TII.get(PPC::MFLR8), PPC::X11)); NewMIs.push_back(BuildMI(TII.get(PPC::MFLR8), PPC::X11));
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STD)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STD))
.addReg(PPC::X11, false, false, true), FrameIdx)); .addReg(PPC::X11, false, false, isKill), FrameIdx));
} }
} else if (RC == PPC::F8RCRegisterClass) { } else if (RC == PPC::F8RCRegisterClass) {
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STFD)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STFD))
.addReg(SrcReg, false, false, true), FrameIdx)); .addReg(SrcReg, false, false, isKill), FrameIdx));
} else if (RC == PPC::F4RCRegisterClass) { } else if (RC == PPC::F4RCRegisterClass) {
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STFS)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STFS))
.addReg(SrcReg, false, false, true), FrameIdx)); .addReg(SrcReg, false, false, isKill), FrameIdx));
} else if (RC == PPC::CRRCRegisterClass) { } else if (RC == PPC::CRRCRegisterClass) {
// FIXME: We use R0 here, because it isn't available for RA. // FIXME: We use R0 here, because it isn't available for RA.
// We need to store the CR in the low 4-bits of the saved value. First, // We need to store the CR in the low 4-bits of the saved value. First,
@ -153,7 +153,7 @@ static void StoreRegToStackSlot(const TargetInstrInfo &TII,
} }
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STW)) NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::STW))
.addReg(PPC::R0, false, false, true), FrameIdx)); .addReg(PPC::R0, false, false, isKill), FrameIdx));
} else if (RC == PPC::VRRCRegisterClass) { } else if (RC == PPC::VRRCRegisterClass) {
// We don't have indexed addressing for vector loads. Emit: // We don't have indexed addressing for vector loads. Emit:
// R0 = ADDI FI# // R0 = ADDI FI#
@ -163,7 +163,7 @@ static void StoreRegToStackSlot(const TargetInstrInfo &TII,
NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::ADDI), PPC::R0), NewMIs.push_back(addFrameReference(BuildMI(TII.get(PPC::ADDI), PPC::R0),
FrameIdx, 0, 0)); FrameIdx, 0, 0));
NewMIs.push_back(BuildMI(TII.get(PPC::STVX)) NewMIs.push_back(BuildMI(TII.get(PPC::STVX))
.addReg(SrcReg, false, false, true).addReg(PPC::R0).addReg(PPC::R0)); .addReg(SrcReg, false, false, isKill).addReg(PPC::R0).addReg(PPC::R0));
} else { } else {
assert(0 && "Unknown regclass!"); assert(0 && "Unknown regclass!");
abort(); abort();
@ -173,20 +173,22 @@ static void StoreRegToStackSlot(const TargetInstrInfo &TII,
void void
PPCRegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB, PPCRegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIdx, unsigned SrcReg, bool isKill, int FrameIdx,
const TargetRegisterClass *RC) const { const TargetRegisterClass *RC) const {
SmallVector<MachineInstr*, 4> NewMIs; SmallVector<MachineInstr*, 4> NewMIs;
StoreRegToStackSlot(TII, SrcReg, FrameIdx, RC, NewMIs); StoreRegToStackSlot(TII, SrcReg, isKill, FrameIdx, RC, NewMIs);
for (unsigned i = 0, e = NewMIs.size(); i != e; ++i) for (unsigned i = 0, e = NewMIs.size(); i != e; ++i)
MBB.insert(MI, NewMIs[i]); MBB.insert(MI, NewMIs[i]);
} }
void PPCRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void PPCRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
if (Addr[0].isFrameIndex()) { if (Addr[0].isFrameIndex()) {
StoreRegToStackSlot(TII, SrcReg, Addr[0].getFrameIndex(), RC, NewMIs); StoreRegToStackSlot(TII, SrcReg, isKill, Addr[0].getFrameIndex(), RC,
NewMIs);
return; return;
} }
@ -206,7 +208,7 @@ void PPCRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
abort(); abort();
} }
MachineInstrBuilder MIB = BuildMI(TII.get(Opc)) MachineInstrBuilder MIB = BuildMI(TII.get(Opc))
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
for (unsigned i = 0, e = Addr.size(); i != e; ++i) { for (unsigned i = 0, e = Addr.size(); i != e; ++i) {
MachineOperand &MO = Addr[i]; MachineOperand &MO = Addr[i];
if (MO.isRegister()) if (MO.isRegister())

View File

@ -37,10 +37,10 @@ public:
/// Code Generation virtual methods... /// Code Generation virtual methods...
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, MachineBasicBlock::iterator MBBI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;

View File

@ -32,23 +32,24 @@ SparcRegisterInfo::SparcRegisterInfo(SparcSubtarget &st,
void SparcRegisterInfo:: void SparcRegisterInfo::
storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I, storeRegToStackSlot(MachineBasicBlock &MBB, MachineBasicBlock::iterator I,
unsigned SrcReg, int FI, unsigned SrcReg, bool isKill, int FI,
const TargetRegisterClass *RC) const { const TargetRegisterClass *RC) const {
// On the order of operands here: think "[FrameIdx + 0] = SrcReg". // On the order of operands here: think "[FrameIdx + 0] = SrcReg".
if (RC == SP::IntRegsRegisterClass) if (RC == SP::IntRegsRegisterClass)
BuildMI(MBB, I, TII.get(SP::STri)).addFrameIndex(FI).addImm(0) BuildMI(MBB, I, TII.get(SP::STri)).addFrameIndex(FI).addImm(0)
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
else if (RC == SP::FPRegsRegisterClass) else if (RC == SP::FPRegsRegisterClass)
BuildMI(MBB, I, TII.get(SP::STFri)).addFrameIndex(FI).addImm(0) BuildMI(MBB, I, TII.get(SP::STFri)).addFrameIndex(FI).addImm(0)
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
else if (RC == SP::DFPRegsRegisterClass) else if (RC == SP::DFPRegsRegisterClass)
BuildMI(MBB, I, TII.get(SP::STDFri)).addFrameIndex(FI).addImm(0) BuildMI(MBB, I, TII.get(SP::STDFri)).addFrameIndex(FI).addImm(0)
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
else else
assert(0 && "Can't store this register to stack slot"); assert(0 && "Can't store this register to stack slot");
} }
void SparcRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void SparcRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
@ -71,7 +72,7 @@ void SparcRegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
else else
MIB.addFrameIndex(MO.getFrameIndex()); MIB.addFrameIndex(MO.getFrameIndex());
} }
MIB.addReg(SrcReg, false, false, true); MIB.addReg(SrcReg, false, false, isKill);
NewMIs.push_back(MIB); NewMIs.push_back(MIB);
return; return;
} }

View File

@ -32,10 +32,10 @@ struct SparcRegisterInfo : public SparcGenRegisterInfo {
/// Code Generation virtual methods... /// Code Generation virtual methods...
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MBBI, MachineBasicBlock::iterator MBBI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;

View File

@ -834,14 +834,15 @@ static unsigned getStoreRegOpcode(const TargetRegisterClass *RC,
void X86RegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB, void X86RegisterInfo::storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIdx, unsigned SrcReg, bool isKill, int FrameIdx,
const TargetRegisterClass *RC) const { const TargetRegisterClass *RC) const {
unsigned Opc = getStoreRegOpcode(RC, StackAlign); unsigned Opc = getStoreRegOpcode(RC, StackAlign);
addFrameReference(BuildMI(MBB, MI, TII.get(Opc)), FrameIdx) addFrameReference(BuildMI(MBB, MI, TII.get(Opc)), FrameIdx)
.addReg(SrcReg, false, false, true); .addReg(SrcReg, false, false, isKill);
} }
void X86RegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void X86RegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const { SmallVectorImpl<MachineInstr*> &NewMIs) const {
@ -849,7 +850,7 @@ void X86RegisterInfo::storeRegToAddr(MachineFunction &MF, unsigned SrcReg,
MachineInstrBuilder MIB = BuildMI(TII.get(Opc)); MachineInstrBuilder MIB = BuildMI(TII.get(Opc));
for (unsigned i = 0, e = Addr.size(); i != e; ++i) for (unsigned i = 0, e = Addr.size(); i != e; ++i)
MIB = X86InstrAddOperand(MIB, Addr[i]); MIB = X86InstrAddOperand(MIB, Addr[i]);
MIB.addReg(SrcReg, false, false, true); MIB.addReg(SrcReg, false, false, isKill);
NewMIs.push_back(MIB); NewMIs.push_back(MIB);
} }
@ -1195,11 +1196,27 @@ MachineInstr* X86RegisterInfo::foldMemoryOperand(MachineInstr *MI,
} }
unsigned X86RegisterInfo::getOpcodeAfterMemoryFold(unsigned Opc, bool X86RegisterInfo::canFoldMemoryOperand(MachineInstr *MI,
unsigned OpNum) const { SmallVectorImpl<unsigned> &Ops) const {
// Check switch flag // Check switch flag
if (NoFusing) return 0; if (NoFusing) return 0;
const DenseMap<unsigned*, unsigned> *OpcodeTablePtr = NULL;
if (Ops.size() == 2 && Ops[0] == 0 && Ops[1] == 1) {
switch (MI->getOpcode()) {
default: return false;
case X86::TEST8rr:
case X86::TEST16rr:
case X86::TEST32rr:
case X86::TEST64rr:
return true;
}
}
if (Ops.size() != 1)
return false;
unsigned OpNum = Ops[0];
unsigned Opc = MI->getOpcode();
unsigned NumOps = TII.getNumOperands(Opc); unsigned NumOps = TII.getNumOperands(Opc);
bool isTwoAddr = NumOps > 1 && bool isTwoAddr = NumOps > 1 &&
TII.getOperandConstraint(Opc, 1, TOI::TIED_TO) != -1; TII.getOperandConstraint(Opc, 1, TOI::TIED_TO) != -1;
@ -1207,18 +1224,16 @@ unsigned X86RegisterInfo::getOpcodeAfterMemoryFold(unsigned Opc,
// Folding a memory location into the two-address part of a two-address // Folding a memory location into the two-address part of a two-address
// instruction is different than folding it other places. It requires // instruction is different than folding it other places. It requires
// replacing the *two* registers with the memory location. // replacing the *two* registers with the memory location.
const DenseMap<unsigned*, unsigned> *OpcodeTablePtr = NULL;
if (isTwoAddr && NumOps >= 2 && OpNum < 2) { if (isTwoAddr && NumOps >= 2 && OpNum < 2) {
OpcodeTablePtr = &RegOp2MemOpTable2Addr; OpcodeTablePtr = &RegOp2MemOpTable2Addr;
} else if (OpNum == 0) { // If operand 0 } else if (OpNum == 0) { // If operand 0
switch (Opc) { switch (Opc) {
case X86::MOV16r0: case X86::MOV16r0:
return X86::MOV16mi;
case X86::MOV32r0: case X86::MOV32r0:
return X86::MOV32mi;
case X86::MOV64r0: case X86::MOV64r0:
return X86::MOV64mi32;
case X86::MOV8r0: case X86::MOV8r0:
return X86::MOV8mi; return true;
default: break; default: break;
} }
OpcodeTablePtr = &RegOp2MemOpTable0; OpcodeTablePtr = &RegOp2MemOpTable0;
@ -1233,9 +1248,9 @@ unsigned X86RegisterInfo::getOpcodeAfterMemoryFold(unsigned Opc,
DenseMap<unsigned*, unsigned>::iterator I = DenseMap<unsigned*, unsigned>::iterator I =
OpcodeTablePtr->find((unsigned*)Opc); OpcodeTablePtr->find((unsigned*)Opc);
if (I != OpcodeTablePtr->end()) if (I != OpcodeTablePtr->end())
return I->second; return true;
} }
return 0; return false;
} }
bool X86RegisterInfo::unfoldMemoryOperand(MachineFunction &MF, MachineInstr *MI, bool X86RegisterInfo::unfoldMemoryOperand(MachineFunction &MF, MachineInstr *MI,
@ -1335,7 +1350,7 @@ bool X86RegisterInfo::unfoldMemoryOperand(MachineFunction &MF, MachineInstr *MI,
const TargetOperandInfo &DstTOI = TID.OpInfo[0]; const TargetOperandInfo &DstTOI = TID.OpInfo[0];
const TargetRegisterClass *DstRC = (DstTOI.Flags & M_LOOK_UP_PTR_REG_CLASS) const TargetRegisterClass *DstRC = (DstTOI.Flags & M_LOOK_UP_PTR_REG_CLASS)
? TII.getPointerRegClass() : getRegClass(DstTOI.RegClass); ? TII.getPointerRegClass() : getRegClass(DstTOI.RegClass);
storeRegToAddr(MF, Reg, AddrOps, DstRC, NewMIs); storeRegToAddr(MF, Reg, true, AddrOps, DstRC, NewMIs);
} }
return true; return true;

View File

@ -101,10 +101,10 @@ public:
void storeRegToStackSlot(MachineBasicBlock &MBB, void storeRegToStackSlot(MachineBasicBlock &MBB,
MachineBasicBlock::iterator MI, MachineBasicBlock::iterator MI,
unsigned SrcReg, int FrameIndex, unsigned SrcReg, bool isKill, int FrameIndex,
const TargetRegisterClass *RC) const; const TargetRegisterClass *RC) const;
void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, void storeRegToAddr(MachineFunction &MF, unsigned SrcReg, bool isKill,
SmallVectorImpl<MachineOperand> &Addr, SmallVectorImpl<MachineOperand> &Addr,
const TargetRegisterClass *RC, const TargetRegisterClass *RC,
SmallVectorImpl<MachineInstr*> &NewMIs) const; SmallVectorImpl<MachineInstr*> &NewMIs) const;
@ -148,11 +148,9 @@ public:
SmallVectorImpl<unsigned> &Ops, SmallVectorImpl<unsigned> &Ops,
MachineInstr* LoadMI) const; MachineInstr* LoadMI) const;
/// getOpcodeAfterMemoryFold - Returns the opcode of the would be new /// canFoldMemoryOperand - Returns true if the specified load / store is
/// instruction after load / store is folded into an instruction of the /// folding is possible.
/// specified opcode. It returns zero if the specified unfolding is not bool canFoldMemoryOperand(MachineInstr*, SmallVectorImpl<unsigned> &) const;
/// possible.
unsigned getOpcodeAfterMemoryFold(unsigned Opc, unsigned OpNum) const;
/// unfoldMemoryOperand - Separate a single instruction which folded a load or /// unfoldMemoryOperand - Separate a single instruction which folded a load or
/// a store or a load and a store into two or more instruction. If this is /// a store or a load and a store into two or more instruction. If this is