Unquadratize SetVector removal loops in DSE.

Erasing from the beginning or middle of the vector is expensive, remove_if can
do it in linear time even though it's a bit ugly without lambdas.

No functionality change.

llvm-svn: 165903
This commit is contained in:
Benjamin Kramer 2012-10-14 10:21:31 +00:00
parent 5ae76a379c
commit 650b1dbd56
1 changed files with 36 additions and 27 deletions

View File

@ -701,6 +701,22 @@ bool DSE::HandleFree(CallInst *F) {
return MadeChange;
}
namespace {
struct CouldRef {
typedef Value *argument_type;
const CallSite CS;
AliasAnalysis *AA;
bool operator()(Value *I) {
// See if the call site touches the value.
AliasAnalysis::ModRefResult A =
AA->getModRefInfo(CS, I, getPointerSize(I, *AA));
return A == AliasAnalysis::ModRef || A == AliasAnalysis::Ref;
}
};
}
/// handleEndBlock - Remove dead stores to stack-allocated locations in the
/// function end block. Ex:
/// %A = alloca i32
@ -802,26 +818,14 @@ bool DSE::handleEndBlock(BasicBlock &BB) {
// If the call might load from any of our allocas, then any store above
// the call is live.
SmallVector<Value*, 8> LiveAllocas;
for (SmallSetVector<Value*, 16>::iterator I = DeadStackObjects.begin(),
E = DeadStackObjects.end(); I != E; ++I) {
// See if the call site touches it.
AliasAnalysis::ModRefResult A =
AA->getModRefInfo(CS, *I, getPointerSize(*I, *AA));
if (A == AliasAnalysis::ModRef || A == AliasAnalysis::Ref)
LiveAllocas.push_back(*I);
}
CouldRef Pred = { CS, AA };
DeadStackObjects.remove_if(Pred);
// If all of the allocas were clobbered by the call then we're not going
// to find anything else to process.
if (DeadStackObjects.size() == LiveAllocas.size())
if (DeadStackObjects.empty())
break;
for (SmallVector<Value*, 8>::iterator I = LiveAllocas.begin(),
E = LiveAllocas.end(); I != E; ++I)
DeadStackObjects.remove(*I);
continue;
}
@ -858,6 +862,20 @@ bool DSE::handleEndBlock(BasicBlock &BB) {
return MadeChange;
}
namespace {
struct CouldAlias {
typedef Value *argument_type;
const AliasAnalysis::Location &LoadedLoc;
AliasAnalysis *AA;
bool operator()(Value *I) {
// See if the loaded location could alias the stack location.
AliasAnalysis::Location StackLoc(I, getPointerSize(I, *AA));
return !AA->isNoAlias(StackLoc, LoadedLoc);
}
};
}
/// RemoveAccessedObjects - Check to see if the specified location may alias any
/// of the stack objects in the DeadStackObjects set. If so, they become live
/// because the location is being loaded.
@ -876,16 +894,7 @@ void DSE::RemoveAccessedObjects(const AliasAnalysis::Location &LoadedLoc,
return;
}
SmallVector<Value*, 16> NowLive;
for (SmallSetVector<Value*, 16>::iterator I = DeadStackObjects.begin(),
E = DeadStackObjects.end(); I != E; ++I) {
// See if the loaded location could alias the stack location.
AliasAnalysis::Location StackLoc(*I, getPointerSize(*I, *AA));
if (!AA->isNoAlias(StackLoc, LoadedLoc))
NowLive.push_back(*I);
}
for (SmallVector<Value*, 16>::iterator I = NowLive.begin(), E = NowLive.end();
I != E; ++I)
DeadStackObjects.remove(*I);
// Remove objects that could alias LoadedLoc.
CouldAlias Pred = { LoadedLoc, AA };
DeadStackObjects.remove_if(Pred);
}