aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/StaticAnalyzer/Core/CFRefCount.cpp7
-rw-r--r--test/Analysis/retain-release.mm22
2 files changed, 29 insertions, 0 deletions
diff --git a/lib/StaticAnalyzer/Core/CFRefCount.cpp b/lib/StaticAnalyzer/Core/CFRefCount.cpp
index 9fd7fc7d4c..366f6b0665 100644
--- a/lib/StaticAnalyzer/Core/CFRefCount.cpp
+++ b/lib/StaticAnalyzer/Core/CFRefCount.cpp
@@ -930,6 +930,13 @@ RetainSummary* RetainSummaryManager::getSummary(const FunctionDecl* FD) {
S = getPersistentStopSummary();
break;
}
+ // For C++ methods, generate an implicit "stop" summary as well. We
+ // can relax this once we have a clear policy for C++ methods and
+ // ownership attributes.
+ if (isa<CXXMethodDecl>(FD)) {
+ S = getPersistentStopSummary();
+ break;
+ }
// [PR 3337] Use 'getAs<FunctionType>' to strip away any typedefs on the
// function's type.
diff --git a/test/Analysis/retain-release.mm b/test/Analysis/retain-release.mm
index 47d615f188..0faeb1a2a3 100644
--- a/test/Analysis/retain-release.mm
+++ b/test/Analysis/retain-release.mm
@@ -275,10 +275,32 @@ class SmartPointer {
public:
SmartPointer(id x) : x(x) {}
~SmartPointer() { [x release]; }
+
+ void adopt(id x);
+ void noAdopt(id x);
};
+void test_positive() {
+ id x = [[NSObject alloc] init]; // expected-warning {{leak}}
+}
+
void test_smartpointer_1() {
id x = [[NSObject alloc] init]; // no-warning
SmartPointer foo(x);
}
+void test_smartpointer_2() {
+ id x = [[NSObject alloc] init]; // no-warning
+ SmartPointer foo(0);
+ foo.adopt(x);
+}
+
+// FIXME: Eventually we want annotations to say whether or not
+// a C++ method claims ownership of an Objective-C object.
+void test_smartpointer_3() {
+ id x = [[NSObject alloc] init]; // no-warning
+ SmartPointer foo(0);
+ foo.noAdopt(x);
+}
+
+