[cfe-commits] r152998 - /cfe/trunk/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp
Jordy Rose
jediknil at belkadan.com
Sat Mar 17 12:53:04 PDT 2012
Author: jrose
Date: Sat Mar 17 14:53:04 2012
New Revision: 152998
URL: http://llvm.org/viewvc/llvm-project?rev=152998&view=rev
Log:
[analyzer] Remove duplicate work on deriving method behavior. No functionality change.
The cocoa::deriveNamingConventions helper is just using method families anyway now, and the way RetainSummaryTemplate works means we're allocating an extra summary for every method with a relevant family.
Also, fix RetainSummaryTemplate to do the right thing w/r/t annotating an /existing/ summary. This was probably the real cause of <rdar://problem/10824732> and the fix in r152448.
Modified:
cfe/trunk/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp
Modified: cfe/trunk/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp?rev=152998&r1=152997&r2=152998&view=diff
==============================================================================
--- cfe/trunk/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp (original)
+++ cfe/trunk/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp Sat Mar 17 14:53:04 2012
@@ -642,8 +642,6 @@
return StopSummary;
}
- const RetainSummary *getInitMethodSummary(QualType RetTy);
-
void InitializeClassMethodSummaries();
void InitializeMethodSummaries();
private:
@@ -810,23 +808,17 @@
class RetainSummaryTemplate {
RetainSummaryManager &Manager;
const RetainSummary *&RealSummary;
- const RetainSummary *BaseSummary;
RetainSummary ScratchSummary;
bool Accessed;
public:
- RetainSummaryTemplate(const RetainSummary *&real, const RetainSummary &base,
- RetainSummaryManager &manager)
- : Manager(manager),
- RealSummary(real),
- BaseSummary(&base),
- ScratchSummary(base),
+ RetainSummaryTemplate(const RetainSummary *&real, const RetainSummary &base,
+ RetainSummaryManager &mgr)
+ : Manager(mgr), RealSummary(real), ScratchSummary(real ? *real : base),
Accessed(false) {}
~RetainSummaryTemplate() {
if (Accessed)
RealSummary = Manager.copySummary(&ScratchSummary);
- else if (!RealSummary)
- RealSummary = BaseSummary;
}
RetainSummary &operator*() {
@@ -1125,18 +1117,6 @@
// Summary creation for Selectors.
//===----------------------------------------------------------------------===//
-const RetainSummary *
-RetainSummaryManager::getInitMethodSummary(QualType RetTy) {
- assert(ScratchArgs.isEmpty());
- // 'init' methods conceptually return a newly allocated object and claim
- // the receiver.
- if (cocoa::isCocoaObjectRef(RetTy) ||
- coreFoundation::isCFObjectRef(RetTy))
- return getPersistentSummary(ObjCInitRetE, DecRefMsg);
-
- return getDefaultSummary();
-}
-
void
RetainSummaryManager::updateSummaryFromAnnotations(const RetainSummary *&Summ,
const FunctionDecl *FD) {
@@ -1192,37 +1172,6 @@
return;
RetainSummaryTemplate Template(Summ, DefaultSummary, *this);
-
- // Check the method family, and apply any default annotations.
- switch (MD->getMethodFamily()) {
- case OMF_None:
- break;
- case OMF_init:
- Template->setRetEffect(ObjCInitRetE);
- Template->setReceiverEffect(DecRefMsg);
- break;
- case OMF_alloc:
- case OMF_new:
- case OMF_copy:
- case OMF_mutableCopy:
- Template->setRetEffect(ObjCAllocRetE);
- break;
- case OMF_autorelease:
- Template->setReceiverEffect(Autorelease);
- case OMF_retain:
- Template->setReceiverEffect(IncRefMsg);
- break;
- case OMF_release:
- Template->setReceiverEffect(DecRefMsg);
- break;
- case OMF_self:
- case OMF_performSelector:
- case OMF_retainCount:
- case OMF_dealloc:
- case OMF_finalize:
- break;
- }
-
bool isTrackedLoc = false;
// Effects on the receiver.
@@ -1289,8 +1238,74 @@
}
}
- // Any special effect for the receiver?
+ // Any special effects?
ArgEffect ReceiverEff = DoNothing;
+ RetEffect ResultEff = RetEffect::MakeNoRet();
+
+ // Check the method family, and apply any default annotations.
+ switch (MD ? MD->getMethodFamily() : S.getMethodFamily()) {
+ case OMF_None:
+ case OMF_performSelector:
+ // Assume all Objective-C methods follow Cocoa Memory Management rules.
+ // FIXME: Does the non-threaded performSelector family really belong here?
+ // The selector could be, say, @selector(copy).
+ if (cocoa::isCocoaObjectRef(RetTy))
+ ResultEff = RetEffect::MakeNotOwned(RetEffect::ObjC);
+ else if (coreFoundation::isCFObjectRef(RetTy)) {
+ // ObjCMethodDecl currently doesn't consider CF objects as valid return
+ // values for alloc, new, copy, or mutableCopy, so we have to
+ // double-check with the selector. This is ugly, but there aren't that
+ // many Objective-C methods that return CF objects, right?
+ if (MD) {
+ switch (S.getMethodFamily()) {
+ case OMF_alloc:
+ case OMF_new:
+ case OMF_copy:
+ case OMF_mutableCopy:
+ ResultEff = RetEffect::MakeOwned(RetEffect::CF, true);
+ break;
+ default:
+ ResultEff = RetEffect::MakeNotOwned(RetEffect::CF);
+ break;
+ }
+ } else {
+ ResultEff = RetEffect::MakeNotOwned(RetEffect::CF);
+ }
+ }
+ break;
+ case OMF_init:
+ ResultEff = ObjCInitRetE;
+ ReceiverEff = DecRefMsg;
+ break;
+ case OMF_alloc:
+ case OMF_new:
+ case OMF_copy:
+ case OMF_mutableCopy:
+ if (cocoa::isCocoaObjectRef(RetTy))
+ ResultEff = ObjCAllocRetE;
+ else if (coreFoundation::isCFObjectRef(RetTy))
+ ResultEff = RetEffect::MakeOwned(RetEffect::CF, true);
+ break;
+ case OMF_autorelease:
+ ReceiverEff = Autorelease;
+ break;
+ case OMF_retain:
+ ReceiverEff = IncRefMsg;
+ break;
+ case OMF_release:
+ ReceiverEff = DecRefMsg;
+ break;
+ case OMF_dealloc:
+ ReceiverEff = Dealloc;
+ break;
+ case OMF_self:
+ // -self is handled specially by the ExprEngine to propagate the receiver.
+ break;
+ case OMF_retainCount:
+ case OMF_finalize:
+ // These methods don't return objects.
+ break;
+ }
// If one of the arguments in the selector has the keyword 'delegate' we
// should stop tracking the reference count for the receiver. This is
@@ -1303,29 +1318,11 @@
ReceiverEff = StopTracking;
}
- // Look for methods that return an owned object.
- if (cocoa::isCocoaObjectRef(RetTy)) {
- // EXPERIMENTAL: assume the Cocoa conventions for all objects returned
- // by instance methods.
- RetEffect E = cocoa::followsFundamentalRule(S, MD)
- ? ObjCAllocRetE : RetEffect::MakeNotOwned(RetEffect::ObjC);
-
- return getPersistentSummary(E, ReceiverEff, MayEscape);
- }
-
- // Look for methods that return an owned core foundation object.
- if (coreFoundation::isCFObjectRef(RetTy)) {
- RetEffect E = cocoa::followsFundamentalRule(S, MD)
- ? RetEffect::MakeOwned(RetEffect::CF, true)
- : RetEffect::MakeNotOwned(RetEffect::CF);
-
- return getPersistentSummary(E, ReceiverEff, MayEscape);
- }
-
- if (ScratchArgs.isEmpty() && ReceiverEff == DoNothing)
+ if (ScratchArgs.isEmpty() && ReceiverEff == DoNothing &&
+ ResultEff.getKind() == RetEffect::NoRet)
return getDefaultSummary();
- return getPersistentSummary(RetEffect::MakeNoRet(), ReceiverEff, MayEscape);
+ return getPersistentSummary(ResultEff, ReceiverEff, MayEscape);
}
const RetainSummary *
@@ -1382,13 +1379,7 @@
const RetainSummary *Summ = ObjCMethodSummaries.find(ID, ClsName, S);
if (!Summ) {
- assert(ScratchArgs.isEmpty());
-
- // "initXXX": pass-through for receiver.
- if (cocoa::deriveNamingConvention(S, MD) == cocoa::InitRule)
- Summ = getInitMethodSummary(RetTy);
- else
- Summ = getCommonMethodSummary(MD, S, RetTy);
+ Summ = getCommonMethodSummary(MD, S, RetTy);
// Annotations override defaults.
updateSummaryFromAnnotations(Summ, MD);
More information about the cfe-commits
mailing list