aboutsummaryrefslogtreecommitdiff
path: root/lib/StaticAnalyzer/Core/CFRefCount.cpp
diff options
context:
space:
mode:
authorJordy Rose <jediknil@belkadan.com>2011-08-24 09:02:37 +0000
committerJordy Rose <jediknil@belkadan.com>2011-08-24 09:02:37 +0000
commit0fe62f8a8c6d9f75842cd8f8349ca7b80952f785 (patch)
treef995ffffe830b1e83b27e0913956eb722a4a9ee5 /lib/StaticAnalyzer/Core/CFRefCount.cpp
parent35c869593677e89fb531c069f7b66eb53e0e5084 (diff)
[analyzer] Fix potential crasher with RAII. No functionality change. (No test because this particular circumstance requires an impossible series of events, but this is future-proofing.)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@138430 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/StaticAnalyzer/Core/CFRefCount.cpp')
-rw-r--r--lib/StaticAnalyzer/Core/CFRefCount.cpp88
1 files changed, 50 insertions, 38 deletions
diff --git a/lib/StaticAnalyzer/Core/CFRefCount.cpp b/lib/StaticAnalyzer/Core/CFRefCount.cpp
index 11d240c31e..8a7d3acbbd 100644
--- a/lib/StaticAnalyzer/Core/CFRefCount.cpp
+++ b/lib/StaticAnalyzer/Core/CFRefCount.cpp
@@ -854,6 +854,37 @@ public:
}
};
+// Used to avoid allocating long-term (BPAlloc'd) memory for default retain
+// summaries. If a function or method looks like it has a default summary, but
+// it has annotations, the annotations are added to the stack-based template
+// and then copied into managed memory.
+class RetainSummaryTemplate {
+ RetainSummaryManager &Manager;
+ RetainSummary *&RealSummary;
+ RetainSummary ScratchSummary;
+ bool Accessed;
+public:
+ RetainSummaryTemplate(RetainSummary *&real, const RetainSummary &base,
+ RetainSummaryManager &manager)
+ : Manager(manager), RealSummary(real), ScratchSummary(base), Accessed(false)
+ {}
+
+ ~RetainSummaryTemplate() {
+ if (!RealSummary && Accessed)
+ RealSummary = Manager.copySummary(&ScratchSummary);
+ }
+
+ RetainSummary &operator*() {
+ Accessed = true;
+ return RealSummary ? *RealSummary : ScratchSummary;
+ }
+
+ RetainSummary *operator->() {
+ Accessed = true;
+ return RealSummary ? RealSummary : &ScratchSummary;
+ }
+};
+
} // end anonymous namespace
//===----------------------------------------------------------------------===//
@@ -1166,9 +1197,7 @@ RetainSummaryManager::updateSummaryFromAnnotations(RetainSummary *&Summ,
if (!FD)
return;
- RetainSummary BasedOnDefault(DefaultSummary);
- if (!Summ)
- Summ = &BasedOnDefault;
+ RetainSummaryTemplate Template(Summ, DefaultSummary, *this);
// Effects on the parameters.
unsigned parm_idx = 0;
@@ -1177,10 +1206,10 @@ RetainSummaryManager::updateSummaryFromAnnotations(RetainSummary *&Summ,
const ParmVarDecl *pd = *pi;
if (pd->getAttr<NSConsumedAttr>()) {
if (!GCEnabled) {
- Summ->addArg(AF, parm_idx, DecRef);
+ Template->addArg(AF, parm_idx, DecRef);
}
} else if (pd->getAttr<CFConsumedAttr>()) {
- Summ->addArg(AF, parm_idx, DecRef);
+ Template->addArg(AF, parm_idx, DecRef);
}
}
@@ -1189,32 +1218,25 @@ RetainSummaryManager::updateSummaryFromAnnotations(RetainSummary *&Summ,
// Determine if there is a special return effect for this method.
if (cocoa::isCocoaObjectRef(RetTy)) {
if (FD->getAttr<NSReturnsRetainedAttr>()) {
- Summ->setRetEffect(ObjCAllocRetE);
+ Template->setRetEffect(ObjCAllocRetE);
}
else if (FD->getAttr<CFReturnsRetainedAttr>()) {
- Summ->setRetEffect(RetEffect::MakeOwned(RetEffect::CF, true));
+ Template->setRetEffect(RetEffect::MakeOwned(RetEffect::CF, true));
}
else if (FD->getAttr<NSReturnsNotRetainedAttr>()) {
- Summ->setRetEffect(RetEffect::MakeNotOwned(RetEffect::ObjC));
+ Template->setRetEffect(RetEffect::MakeNotOwned(RetEffect::ObjC));
}
else if (FD->getAttr<CFReturnsNotRetainedAttr>()) {
- Summ->setRetEffect(RetEffect::MakeNotOwned(RetEffect::CF));
+ Template->setRetEffect(RetEffect::MakeNotOwned(RetEffect::CF));
}
} else if (RetTy->getAs<PointerType>()) {
if (FD->getAttr<CFReturnsRetainedAttr>()) {
- Summ->setRetEffect(RetEffect::MakeOwned(RetEffect::CF, true));
+ Template->setRetEffect(RetEffect::MakeOwned(RetEffect::CF, true));
}
else if (FD->getAttr<CFReturnsNotRetainedAttr>()) {
- Summ->setRetEffect(RetEffect::MakeNotOwned(RetEffect::CF));
+ Template->setRetEffect(RetEffect::MakeNotOwned(RetEffect::CF));
}
}
-
- if (Summ == &BasedOnDefault) {
- if (!(*Summ == DefaultSummary))
- Summ = copySummary(Summ);
- else
- Summ = 0;
- }
}
void
@@ -1223,16 +1245,14 @@ RetainSummaryManager::updateSummaryFromAnnotations(RetainSummary *&Summ,
if (!MD)
return;
- RetainSummary BasedOnDefault = DefaultSummary;
- if (!Summ)
- Summ = &BasedOnDefault;
+ RetainSummaryTemplate Template(Summ, DefaultSummary, *this);
bool isTrackedLoc = false;
// Effects on the receiver.
if (MD->getAttr<NSConsumesSelfAttr>()) {
if (!GCEnabled)
- Summ->setReceiverEffect(DecRefMsg);
+ Template->setReceiverEffect(DecRefMsg);
}
// Effects on the parameters.
@@ -1242,42 +1262,34 @@ RetainSummaryManager::updateSummaryFromAnnotations(RetainSummary *&Summ,
const ParmVarDecl *pd = *pi;
if (pd->getAttr<NSConsumedAttr>()) {
if (!GCEnabled)
- Summ->addArg(AF, parm_idx, DecRef);
+ Template->addArg(AF, parm_idx, DecRef);
}
else if(pd->getAttr<CFConsumedAttr>()) {
- Summ->addArg(AF, parm_idx, DecRef);
+ Template->addArg(AF, parm_idx, DecRef);
}
}
// Determine if there is a special return effect for this method.
if (cocoa::isCocoaObjectRef(MD->getResultType())) {
if (MD->getAttr<NSReturnsRetainedAttr>()) {
- Summ->setRetEffect(ObjCAllocRetE);
+ Template->setRetEffect(ObjCAllocRetE);
return;
}
if (MD->getAttr<NSReturnsNotRetainedAttr>()) {
- Summ->setRetEffect(RetEffect::MakeNotOwned(RetEffect::ObjC));
+ Template->setRetEffect(RetEffect::MakeNotOwned(RetEffect::ObjC));
return;
}
isTrackedLoc = true;
- }
-
- if (!isTrackedLoc)
+ } else {
isTrackedLoc = MD->getResultType()->getAs<PointerType>() != NULL;
+ }
if (isTrackedLoc) {
if (MD->getAttr<CFReturnsRetainedAttr>())
- Summ->setRetEffect(RetEffect::MakeOwned(RetEffect::CF, true));
+ Template->setRetEffect(RetEffect::MakeOwned(RetEffect::CF, true));
else if (MD->getAttr<CFReturnsNotRetainedAttr>())
- Summ->setRetEffect(RetEffect::MakeNotOwned(RetEffect::CF));
- }
-
- if (Summ == &BasedOnDefault) {
- if (!(*Summ == DefaultSummary))
- Summ = copySummary(Summ);
- else
- Summ = 0;
+ Template->setRetEffect(RetEffect::MakeNotOwned(RetEffect::CF));
}
}