forked from OSchip/llvm-project
Allow target to place 2-address pass inserted copies in better spots. Thumb2 will use this to try to avoid breaking up IT blocks.
llvm-svn: 105745
This commit is contained in:
parent
aea0620b89
commit
a0746bd50a
|
@ -203,6 +203,14 @@ public:
|
||||||
const MachineInstr *Orig,
|
const MachineInstr *Orig,
|
||||||
const TargetRegisterInfo &TRI) const = 0;
|
const TargetRegisterInfo &TRI) const = 0;
|
||||||
|
|
||||||
|
/// scheduleTwoAddrSource - Schedule the copy / re-mat of the source of the
|
||||||
|
/// two-addrss instruction inserted by two-address pass.
|
||||||
|
virtual void scheduleTwoAddrSource(MachineInstr *SrcMI,
|
||||||
|
MachineInstr *UseMI,
|
||||||
|
const TargetRegisterInfo &TRI) const {
|
||||||
|
// Do nothing.
|
||||||
|
}
|
||||||
|
|
||||||
/// duplicate - Create a duplicate of the Orig instruction in MF. This is like
|
/// duplicate - Create a duplicate of the Orig instruction in MF. This is like
|
||||||
/// MachineFunction::CloneMachineInstr(), but the target may update operands
|
/// MachineFunction::CloneMachineInstr(), but the target may update operands
|
||||||
/// that are required to be unique.
|
/// that are required to be unique.
|
||||||
|
|
|
@ -1104,7 +1104,12 @@ bool TwoAddressInstructionPass::runOnMachineFunction(MachineFunction &MF) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Schedule the source copy / remat inserted to form two-address
|
||||||
|
// instruction. FIXME: Does it matter the distance map may not be
|
||||||
|
// accurate after it's scheduled?
|
||||||
|
TII->scheduleTwoAddrSource(prior(mi), mi, *TRI);
|
||||||
|
|
||||||
MadeChange = true;
|
MadeChange = true;
|
||||||
|
|
||||||
DEBUG(dbgs() << "\t\trewrite to:\t" << *mi);
|
DEBUG(dbgs() << "\t\trewrite to:\t" << *mi);
|
||||||
|
|
|
@ -61,15 +61,7 @@ static ARMCC::CondCodes getPredicate(const MachineInstr *MI, unsigned &PredReg){
|
||||||
unsigned Opc = MI->getOpcode();
|
unsigned Opc = MI->getOpcode();
|
||||||
if (Opc == ARM::tBcc || Opc == ARM::t2Bcc)
|
if (Opc == ARM::tBcc || Opc == ARM::t2Bcc)
|
||||||
return ARMCC::AL;
|
return ARMCC::AL;
|
||||||
|
return llvm::getInstrPredicate(MI, PredReg);
|
||||||
int PIdx = MI->findFirstPredOperandIdx();
|
|
||||||
if (PIdx == -1) {
|
|
||||||
PredReg = 0;
|
|
||||||
return ARMCC::AL;
|
|
||||||
}
|
|
||||||
|
|
||||||
PredReg = MI->getOperand(PIdx+1).getReg();
|
|
||||||
return (ARMCC::CondCodes)MI->getOperand(PIdx).getImm();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
|
@ -242,15 +234,15 @@ bool Thumb2ITBlockPass::InsertITBlock(MachineInstr *First, MachineInstr *Last) {
|
||||||
// Insert a new block for consecutive predicated instructions.
|
// Insert a new block for consecutive predicated instructions.
|
||||||
MachineFunction *MF = MBB->getParent();
|
MachineFunction *MF = MBB->getParent();
|
||||||
MachineBasicBlock *NewMBB = MF->CreateMachineBasicBlock(MBB->getBasicBlock());
|
MachineBasicBlock *NewMBB = MF->CreateMachineBasicBlock(MBB->getBasicBlock());
|
||||||
MachineFunction::iterator Pos = MBB;
|
MachineFunction::iterator InsertPos = MBB;
|
||||||
MF->insert(++Pos, NewMBB);
|
MF->insert(++InsertPos, NewMBB);
|
||||||
|
|
||||||
// Move all the successors of this block to the specified block.
|
// Move all the successors of this block to the specified block.
|
||||||
NewMBB->transferSuccessors(MBB);
|
NewMBB->transferSuccessors(MBB);
|
||||||
|
|
||||||
// Add an edge from CurMBB to NewMBB for the fall-through.
|
// Add an edge from CurMBB to NewMBB for the fall-through.
|
||||||
MBB->addSuccessor(NewMBB);
|
MBB->addSuccessor(NewMBB);
|
||||||
NewMBB->splice(NewMBB->end(), MBB, ++MBBI, MBB->end());
|
NewMBB->splice(NewMBB->end(), MBB, ++MBBI, MBB->end());
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -503,3 +503,46 @@ bool llvm::rewriteT2FrameIndex(MachineInstr &MI, unsigned FrameRegIdx,
|
||||||
Offset = (isSub) ? -Offset : Offset;
|
Offset = (isSub) ? -Offset : Offset;
|
||||||
return Offset == 0;
|
return Offset == 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// scheduleTwoAddrSource - Schedule the copy / re-mat of the source of the
|
||||||
|
/// two-addrss instruction inserted by two-address pass.
|
||||||
|
void
|
||||||
|
Thumb2InstrInfo::scheduleTwoAddrSource(MachineInstr *SrcMI,
|
||||||
|
MachineInstr *UseMI,
|
||||||
|
const TargetRegisterInfo &TRI) const {
|
||||||
|
if (SrcMI->getOpcode() != ARM::tMOVgpr2gpr ||
|
||||||
|
SrcMI->getOperand(1).isKill())
|
||||||
|
return;
|
||||||
|
|
||||||
|
unsigned PredReg = 0;
|
||||||
|
ARMCC::CondCodes CC = llvm::getInstrPredicate(UseMI, PredReg);
|
||||||
|
if (CC == ARMCC::AL || PredReg != ARM::CPSR)
|
||||||
|
return;
|
||||||
|
|
||||||
|
// Schedule the copy so it doesn't come between previous instructions
|
||||||
|
// and UseMI which can form an IT block.
|
||||||
|
unsigned SrcReg = SrcMI->getOperand(1).getReg();
|
||||||
|
ARMCC::CondCodes OCC = ARMCC::getOppositeCondition(CC);
|
||||||
|
MachineBasicBlock *MBB = UseMI->getParent();
|
||||||
|
MachineBasicBlock::iterator MBBI = SrcMI;
|
||||||
|
unsigned NumInsts = 0;
|
||||||
|
while (--MBBI != MBB->begin()) {
|
||||||
|
if (MBBI->isDebugValue())
|
||||||
|
continue;
|
||||||
|
|
||||||
|
MachineInstr *NMI = &*MBBI;
|
||||||
|
ARMCC::CondCodes NCC = llvm::getInstrPredicate(NMI, PredReg);
|
||||||
|
if (!(NCC == CC || NCC == OCC) ||
|
||||||
|
NMI->modifiesRegister(SrcReg, &TRI) ||
|
||||||
|
NMI->definesRegister(ARM::CPSR))
|
||||||
|
break;
|
||||||
|
if (++NumInsts == 4)
|
||||||
|
// Too many in a row!
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (NumInsts) {
|
||||||
|
MBB->remove(SrcMI);
|
||||||
|
MBB->insert(++MBBI, SrcMI);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -50,6 +50,11 @@ public:
|
||||||
const TargetRegisterClass *RC,
|
const TargetRegisterClass *RC,
|
||||||
const TargetRegisterInfo *TRI) const;
|
const TargetRegisterInfo *TRI) const;
|
||||||
|
|
||||||
|
/// scheduleTwoAddrSource - Schedule the copy / re-mat of the source of the
|
||||||
|
/// two-addrss instruction inserted by two-address pass.
|
||||||
|
void scheduleTwoAddrSource(MachineInstr *SrcMI, MachineInstr *UseMI,
|
||||||
|
const TargetRegisterInfo &TRI) const;
|
||||||
|
|
||||||
/// getRegisterInfo - TargetInstrInfo is a superset of MRegister info. As
|
/// getRegisterInfo - TargetInstrInfo is a superset of MRegister info. As
|
||||||
/// such, whenever a client has an instance of instruction info, it should
|
/// such, whenever a client has an instance of instruction info, it should
|
||||||
/// always be able to get register info as well (through this method).
|
/// always be able to get register info as well (through this method).
|
||||||
|
|
Loading…
Reference in New Issue