diff options
author | Dan Gohman <gohman@apple.com> | 2010-06-18 23:28:01 +0000 |
---|---|---|
committer | Dan Gohman <gohman@apple.com> | 2010-06-18 23:28:01 +0000 |
commit | db4971259ce94cea26e555e9ade82672a3581f5c (patch) | |
tree | 312318482d5af5306e9d2881f4bdc15f3b4664b2 /lib/CodeGen/SelectionDAG/InstrEmitter.cpp | |
parent | 8af5ed9e15cfb48817c0f1f46b66b8fe54412036 (diff) |
Teach regular and fast isel to set dead flags on unused implicit defs
on calls and similar instructions.
git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@106353 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/CodeGen/SelectionDAG/InstrEmitter.cpp')
-rw-r--r-- | lib/CodeGen/SelectionDAG/InstrEmitter.cpp | 27 |
1 files changed, 27 insertions, 0 deletions
diff --git a/lib/CodeGen/SelectionDAG/InstrEmitter.cpp b/lib/CodeGen/SelectionDAG/InstrEmitter.cpp index 1c53dbd1b2..61a73412bb 100644 --- a/lib/CodeGen/SelectionDAG/InstrEmitter.cpp +++ b/lib/CodeGen/SelectionDAG/InstrEmitter.cpp @@ -676,6 +676,33 @@ EmitMachineNode(SDNode *Node, bool IsClone, bool IsCloned, // Create the new machine instruction. MachineInstr *MI = BuildMI(*MF, Node->getDebugLoc(), II); + + // The MachineInstr constructor adds implicit-def operands. Scan through + // these to determine which are dead. + if (MI->getNumOperands() != 0 && + Node->getValueType(Node->getNumValues()-1) == MVT::Flag) { + // First, collect all used registers. + SmallVector<unsigned, 8> UsedRegs; + for (SDNode *F = Node->getFlaggedUser(); F; F = F->getFlaggedUser()) + if (F->getOpcode() == ISD::CopyFromReg) + UsedRegs.push_back(cast<RegisterSDNode>(F->getOperand(1))->getReg()); + else { + // Collect declared implicit uses. + const TargetInstrDesc &TID = TII->get(F->getMachineOpcode()); + UsedRegs.append(TID.getImplicitUses(), + TID.getImplicitUses() + TID.getNumImplicitUses()); + // In addition to declared implicit uses, we must also check for + // direct RegisterSDNode operands. + for (unsigned i = 0, e = F->getNumOperands(); i != e; ++i) + if (RegisterSDNode *R = dyn_cast<RegisterSDNode>(F->getOperand(i))) { + unsigned Reg = R->getReg(); + if (Reg != 0 && TargetRegisterInfo::isPhysicalRegister(Reg)) + UsedRegs.push_back(Reg); + } + } + // Then mark unused registers as dead. + MI->setPhysRegsDeadExcept(UsedRegs, *TRI); + } // Add result register values for things that are defined by this // instruction. |