diff options
Diffstat (limited to 'clang/lib/StaticAnalyzer/Checkers')
-rw-r--r-- | clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp | 14 |
1 files changed, 11 insertions, 3 deletions
diff --git a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp index 4b8d7bd262a..e86d63804b8 100644 --- a/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/RetainCountChecker/RetainCountChecker.cpp @@ -849,7 +849,6 @@ void RetainCountChecker::processNonLeakError(ProgramStateRef St, //===----------------------------------------------------------------------===// bool RetainCountChecker::evalCall(const CallExpr *CE, CheckerContext &C) const { - // Get the callee. We're only interested in simple C functions. ProgramStateRef state = C.getState(); const FunctionDecl *FD = C.getCalleeDecl(CE); if (!FD) @@ -874,18 +873,27 @@ bool RetainCountChecker::evalCall(const CallExpr *CE, CheckerContext &C) const { // Bind the return value. if (BSmr == BehaviorSummary::Identity || - BSmr == BehaviorSummary::IdentityOrZero) { - SVal RetVal = state->getSVal(CE->getArg(0), LCtx); + BSmr == BehaviorSummary::IdentityOrZero || + BSmr == BehaviorSummary::IdentityThis) { + + const Expr *BindReturnTo = + (BSmr == BehaviorSummary::IdentityThis) + ? cast<CXXMemberCallExpr>(CE)->getImplicitObjectArgument() + : CE->getArg(0); + SVal RetVal = state->getSVal(BindReturnTo, LCtx); // If the receiver is unknown or the function has // 'rc_ownership_trusted_implementation' annotate attribute, conjure a // return value. + // FIXME: this branch is very strange. if (RetVal.isUnknown() || (hasTrustedImplementationAnnotation && !ResultTy.isNull())) { SValBuilder &SVB = C.getSValBuilder(); RetVal = SVB.conjureSymbolVal(nullptr, CE, LCtx, ResultTy, C.blockCount()); } + + // Bind the value. state = state->BindExpr(CE, LCtx, RetVal, /*Invalidate=*/false); if (BSmr == BehaviorSummary::IdentityOrZero) { |