[llvm-commits] [llvm] r98511 - /llvm/trunk/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
Chris Lattner
sabre at nondot.org
Sun Mar 14 12:43:04 PDT 2010
Author: lattner
Date: Sun Mar 14 14:43:04 2010
New Revision: 98511
URL: http://llvm.org/viewvc/llvm-project?rev=98511&view=rev
Log:
rewrite ShrinkDemandedOps to be faster and indent less,
no functionality change.
Modified:
llvm/trunk/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
Modified: llvm/trunk/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp?rev=98511&r1=98510&r2=98511&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp (original)
+++ llvm/trunk/lib/CodeGen/SelectionDAG/SelectionDAGISel.cpp Sun Mar 14 14:43:04 2010
@@ -446,12 +446,25 @@
/// nodes from the worklist.
class SDOPsWorkListRemover : public SelectionDAG::DAGUpdateListener {
SmallVector<SDNode*, 128> &Worklist;
+ SmallPtrSet<SDNode*, 128> &InWorklist;
public:
- SDOPsWorkListRemover(SmallVector<SDNode*, 128> &wl) : Worklist(wl) {}
+ SDOPsWorkListRemover(SmallVector<SDNode*, 128> &wl,
+ SmallPtrSet<SDNode*, 128> &inwl)
+ : Worklist(wl), InWorklist(inwl) {}
+ void RemoveFromWorklist(SDNode *N) {
+ if (!InWorklist.erase(N)) return;
+
+ SmallVector<SDNode*, 128>::iterator I =
+ std::find(Worklist.begin(), Worklist.end(), N);
+ assert(I != Worklist.end() && "Not in worklist");
+
+ *I = Worklist.back();
+ Worklist.pop_back();
+ }
+
virtual void NodeDeleted(SDNode *N, SDNode *E) {
- Worklist.erase(std::remove(Worklist.begin(), Worklist.end(), N),
- Worklist.end());
+ RemoveFromWorklist(N);
}
virtual void NodeUpdated(SDNode *N) {
@@ -480,20 +493,20 @@
/// x+y to (VT)((SmallVT)x+(SmallVT)y) if the casts are free.
void SelectionDAGISel::ShrinkDemandedOps() {
SmallVector<SDNode*, 128> Worklist;
+ SmallPtrSet<SDNode*, 128> InWorklist;
// Add all the dag nodes to the worklist.
Worklist.reserve(CurDAG->allnodes_size());
for (SelectionDAG::allnodes_iterator I = CurDAG->allnodes_begin(),
- E = CurDAG->allnodes_end(); I != E; ++I)
+ E = CurDAG->allnodes_end(); I != E; ++I) {
Worklist.push_back(I);
-
- APInt Mask;
- APInt KnownZero;
- APInt KnownOne;
+ InWorklist.insert(I);
+ }
TargetLowering::TargetLoweringOpt TLO(*CurDAG, true);
while (!Worklist.empty()) {
SDNode *N = Worklist.pop_back_val();
+ InWorklist.erase(N);
if (N->use_empty() && N != CurDAG->getRoot().getNode()) {
CurDAG->DeleteNode(N);
@@ -501,49 +514,52 @@
}
// Run ShrinkDemandedOp on scalar binary operations.
- if (N->getNumValues() == 1 &&
- N->getValueType(0).isSimple() && N->getValueType(0).isInteger()) {
- unsigned BitWidth = N->getValueType(0).getScalarType().getSizeInBits();
- APInt Demanded = APInt::getAllOnesValue(BitWidth);
- APInt KnownZero, KnownOne;
- if (TLI.SimplifyDemandedBits(SDValue(N, 0), Demanded,
- KnownZero, KnownOne, TLO) ||
- (N->getOpcode() == ISD::TRUNCATE &&
- TrivialTruncElim(SDValue(N, 0), TLO))) {
- // Revisit the node.
- Worklist.erase(std::remove(Worklist.begin(), Worklist.end(), N),
- Worklist.end());
- Worklist.push_back(N);
-
- // Replace the old value with the new one.
- DEBUG(errs() << "\nReplacing ";
- TLO.Old.getNode()->dump(CurDAG);
- errs() << "\nWith: ";
- TLO.New.getNode()->dump(CurDAG);
- errs() << '\n');
-
- Worklist.push_back(TLO.New.getNode());
-
- SDOPsWorkListRemover DeadNodes(Worklist);
- CurDAG->ReplaceAllUsesOfValueWith(TLO.Old, TLO.New, &DeadNodes);
-
- if (TLO.Old.getNode()->use_empty()) {
- for (unsigned i = 0, e = TLO.Old.getNode()->getNumOperands();
- i != e; ++i) {
- SDNode *OpNode = TLO.Old.getNode()->getOperand(i).getNode();
- if (OpNode->hasOneUse()) {
- Worklist.erase(std::remove(Worklist.begin(), Worklist.end(),
- OpNode), Worklist.end());
- Worklist.push_back(OpNode);
- }
- }
-
- Worklist.erase(std::remove(Worklist.begin(), Worklist.end(),
- TLO.Old.getNode()), Worklist.end());
- CurDAG->DeleteNode(TLO.Old.getNode());
- }
+ if (N->getNumValues() != 1 ||
+ !N->getValueType(0).isSimple() || !N->getValueType(0).isInteger())
+ continue;
+
+ unsigned BitWidth = N->getValueType(0).getScalarType().getSizeInBits();
+ APInt Demanded = APInt::getAllOnesValue(BitWidth);
+ APInt KnownZero, KnownOne;
+ if (!TLI.SimplifyDemandedBits(SDValue(N, 0), Demanded,
+ KnownZero, KnownOne, TLO) &&
+ (N->getOpcode() != ISD::TRUNCATE ||
+ !TrivialTruncElim(SDValue(N, 0), TLO)))
+ continue;
+
+ // Revisit the node.
+ assert(!InWorklist.count(N) && "Already in worklist");
+ Worklist.push_back(N);
+ InWorklist.insert(N);
+
+ // Replace the old value with the new one.
+ DEBUG(errs() << "\nShrinkDemandedOps replacing ";
+ TLO.Old.getNode()->dump(CurDAG);
+ errs() << "\nWith: ";
+ TLO.New.getNode()->dump(CurDAG);
+ errs() << '\n');
+
+ if (InWorklist.insert(TLO.New.getNode()))
+ Worklist.push_back(TLO.New.getNode());
+
+ SDOPsWorkListRemover DeadNodes(Worklist, InWorklist);
+ CurDAG->ReplaceAllUsesOfValueWith(TLO.Old, TLO.New, &DeadNodes);
+
+ if (!TLO.Old.getNode()->use_empty()) continue;
+
+ for (unsigned i = 0, e = TLO.Old.getNode()->getNumOperands();
+ i != e; ++i) {
+ SDNode *OpNode = TLO.Old.getNode()->getOperand(i).getNode();
+ if (OpNode->hasOneUse()) {
+ // Add OpNode to the end of the list to revisit.
+ DeadNodes.RemoveFromWorklist(OpNode);
+ Worklist.push_back(OpNode);
+ InWorklist.insert(OpNode);
}
}
+
+ DeadNodes.RemoveFromWorklist(TLO.Old.getNode());
+ CurDAG->DeleteNode(TLO.Old.getNode());
}
}
More information about the llvm-commits
mailing list