RetainCountChecker: don't adjust the retain count when analyzing a ReturnStmt unless we are in the top-level call frame. We can do more later, but this makes the checker self-consistent (and fixes a crash).

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@151426 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Ted Kremenek 2012-02-25 02:09:09 +00:00
Родитель 63787f0343
Коммит e571578002
2 изменённых файлов: 29 добавлений и 0 удалений

Просмотреть файл

@ -3069,8 +3069,23 @@ bool RetainCountChecker::evalCall(const CallExpr *CE, CheckerContext &C) const {
// Handle return statements.
//===----------------------------------------------------------------------===//
// Return true if the current LocationContext has no caller context.
static bool inTopFrame(CheckerContext &C) {
const LocationContext *LC = C.getLocationContext();
return LC->getParent() == 0;
}
void RetainCountChecker::checkPreStmt(const ReturnStmt *S,
CheckerContext &C) const {
// Only adjust the reference count if this is the top-level call frame,
// and not the result of inlining. In the future, we should do
// better checking even for inlined calls, and see if they match
// with their expected semantics (e.g., the method should return a retained
// object, etc.).
if (!inTopFrame(C))
return;
const Expr *RetE = S->getRetValue();
if (!RetE)
return;

Просмотреть файл

@ -281,3 +281,17 @@ void test_neg() {
bar(s);
}
//===----------------------------------------------------------------------===//
// Test returning retained and not-retained values.
//===----------------------------------------------------------------------===//
id test_return_retained() {
return [[NSString alloc] init]; // expected-warning {{leak}}
}
void test_test_return_retained() {
id x = test_return_retained();
[x retain];
[x release];
}