summaryrefslogtreecommitdiffstats
path: root/llvm/lib/Analysis/IPA
diff options
context:
space:
mode:
authorDuncan Sands <baldrick@free.fr>2008-09-12 07:29:58 +0000
committerDuncan Sands <baldrick@free.fr>2008-09-12 07:29:58 +0000
commit06dbb126e6733f9b9963ce435a33b559e14c35d4 (patch)
tree57146de6350fb7dfbcb38cc10fb64eb172a0651d /llvm/lib/Analysis/IPA
parentd3f0d9b07ca0eaee3f3a46f5f963b913cad85bce (diff)
downloadbcm5719-llvm-06dbb126e6733f9b9963ce435a33b559e14c35d4.tar.gz
bcm5719-llvm-06dbb126e6733f9b9963ce435a33b559e14c35d4.zip
Rather than marking all internal globals "Ref"
when a readonly declaration is called, set a flag. This is faster and uses less memory. In theory it is less accurate, because before only those internal globals that were read by someone were being marked "Ref", but now all are. But in practice, thanks to other passes, all internal globals of the kind considered here will be both read and stored to: those only read will have been turned into constants, and those only stored to will have been deleted. llvm-svn: 56143
Diffstat (limited to 'llvm/lib/Analysis/IPA')
-rw-r--r--llvm/lib/Analysis/IPA/GlobalsModRef.cpp28
1 files changed, 11 insertions, 17 deletions
diff --git a/llvm/lib/Analysis/IPA/GlobalsModRef.cpp b/llvm/lib/Analysis/IPA/GlobalsModRef.cpp
index 6736e6f3ce4..390a6028eb4 100644
--- a/llvm/lib/Analysis/IPA/GlobalsModRef.cpp
+++ b/llvm/lib/Analysis/IPA/GlobalsModRef.cpp
@@ -49,18 +49,22 @@ namespace {
/// function.
std::map<GlobalValue*, unsigned> GlobalInfo;
+ /// MayReadAnyGlobal - May read global variables, but it is not known which.
+ bool MayReadAnyGlobal;
+
unsigned getInfoForGlobal(GlobalValue *GV) const {
+ unsigned Effect = MayReadAnyGlobal ? AliasAnalysis::Ref : 0;
std::map<GlobalValue*, unsigned>::const_iterator I = GlobalInfo.find(GV);
if (I != GlobalInfo.end())
- return I->second;
- return 0;
+ Effect |= I->second;
+ return Effect;
}
/// FunctionEffect - Capture whether or not this function reads or writes to
/// ANY memory. If not, we can do a lot of aggressive analysis on it.
unsigned FunctionEffect;
- FunctionRecord() : FunctionEffect(0) {}
+ FunctionRecord() : MayReadAnyGlobal (false), FunctionEffect(0) {}
};
/// GlobalsModRef - The actual analysis pass.
@@ -70,10 +74,6 @@ namespace {
/// taken.
std::set<GlobalValue*> NonAddressTakenGlobals;
- /// ReadGlobals - The globals without addresses taken that are read by
- /// some function.
- std::set<GlobalValue*> ReadGlobals;
-
/// IndirectGlobals - The memory pointed to by this global is known to be
/// 'owned' by the global.
std::set<GlobalValue*> IndirectGlobals;
@@ -203,10 +203,6 @@ void GlobalsModRef::AnalyzeGlobals(Module &M) {
// Remember that we are tracking this global, and the mod/ref fns
NonAddressTakenGlobals.insert(I);
- if (!Readers.empty())
- // Some function read this global - remember that.
- ReadGlobals.insert(I);
-
for (unsigned i = 0, e = Readers.size(); i != e; ++i)
FunctionInfo[Readers[i]].GlobalInfo[I] |= Ref;
@@ -384,13 +380,10 @@ void GlobalsModRef::AnalyzeCallGraph(CallGraph &CG, Module &M) {
// Can't do better than that!
} else if (F->onlyReadsMemory()) {
FunctionEffect |= Ref;
- if (!F->isIntrinsic()) {
+ if (!F->isIntrinsic())
// This function might call back into the module and read a global -
- // mark all globals read somewhere as being read by this function.
- for (std::set<GlobalValue*>::iterator GI = ReadGlobals.begin(),
- E = ReadGlobals.end(); GI != E; ++GI)
- FR.GlobalInfo[*GI] |= Ref;
- }
+ // consider every global as possibly being read by this function.
+ FR.MayReadAnyGlobal = true;
} else {
FunctionEffect |= ModRef;
// Can't say anything useful unless it's an intrinsic - they don't
@@ -412,6 +405,7 @@ void GlobalsModRef::AnalyzeCallGraph(CallGraph &CG, Module &M) {
CalleeFR->GlobalInfo.begin(), E = CalleeFR->GlobalInfo.end();
GI != E; ++GI)
FR.GlobalInfo[GI->first] |= GI->second;
+ FR.MayReadAnyGlobal |= CalleeFR->MayReadAnyGlobal;
} else {
// Can't say anything about it. However, if it is inside our SCC,
// then nothing needs to be done.
OpenPOWER on IntegriCloud