diff options
author | Anna Zaks <ganna@apple.com> | 2012-05-02 00:15:40 +0000 |
---|---|---|
committer | Anna Zaks <ganna@apple.com> | 2012-05-02 00:15:40 +0000 |
commit | e7958da55ec0ec66e56b6beed6c6ce24dbdc4075 (patch) | |
tree | 3738738d1881bff9ddef0a54ab7ec7a5656ecc58 | |
parent | 12f3297fbef1673b32c8987da9933687996c65b3 (diff) |
[analyzer] RetainRelease: Self assignment should not suppress a leak
warning.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@155966 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp | 6 | ||||
-rw-r--r-- | test/Analysis/retain-release.m | 5 |
2 files changed, 10 insertions, 1 deletions
diff --git a/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp b/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp index 2a97e1c24a..3bd7ae4322 100644 --- a/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp +++ b/lib/StaticAnalyzer/Checkers/RetainCountChecker.cpp @@ -3347,7 +3347,11 @@ void RetainCountChecker::checkBind(SVal loc, SVal val, const Stmt *S, // To test (3), generate a new state with the binding added. If it is // the same state, then it escapes (since the store cannot represent // the binding). - escapes = (state == (state->bindLoc(*regionLoc, val))); + // Do this only if we know that the store is not supposed to generate the + // same state. + SVal StoredVal = state->getSVal(regionLoc->getRegion()); + if (StoredVal != val) + escapes = (state == (state->bindLoc(*regionLoc, val))); } if (!escapes) { // Case 4: We do not currently model what happens when a symbol is diff --git a/test/Analysis/retain-release.m b/test/Analysis/retain-release.m index 3aa2656c62..54af13d2a3 100644 --- a/test/Analysis/retain-release.m +++ b/test/Analysis/retain-release.m @@ -1305,6 +1305,11 @@ void testattr2_b() { TestOwnershipAttr *x = [[TestOwnershipAttr alloc] pseudoInit]; // expected-warning{{leak}} } +void testattr2_b_11358224_self_assign_looses_the_leak() { + TestOwnershipAttr *x = [[TestOwnershipAttr alloc] pseudoInit];// expected-warning{{leak}} + x = x; +} + void testattr2_c() { TestOwnershipAttr *x = [[TestOwnershipAttr alloc] pseudoInit]; // no-warning [x release]; |