diff --git a/clang/lib/StaticAnalyzer/Checkers/WebKit/UncountedLambdaCapturesChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/WebKit/UncountedLambdaCapturesChecker.cpp index 53ef423bd82e7..a56f48c83c660 100644 --- a/clang/lib/StaticAnalyzer/Checkers/WebKit/UncountedLambdaCapturesChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/WebKit/UncountedLambdaCapturesChecker.cpp @@ -109,9 +109,7 @@ class UncountedLambdaCapturesChecker bool VisitCallExpr(CallExpr *CE) override { checkCalleeLambda(CE); if (auto *Callee = CE->getDirectCallee()) { - unsigned ArgIndex = 0; - if (auto *CXXCallee = dyn_cast(Callee)) - ArgIndex = CXXCallee->isInstance(); + unsigned ArgIndex = isa(CE); bool TreatAllArgsAsNoEscape = shouldTreatAllArgAsNoEscape(Callee); for (auto *Param : Callee->parameters()) { if (ArgIndex >= CE->getNumArgs()) diff --git a/clang/test/Analysis/Checkers/WebKit/uncounted-lambda-captures.cpp b/clang/test/Analysis/Checkers/WebKit/uncounted-lambda-captures.cpp index 2a1a164557cdb..4f4a960282253 100644 --- a/clang/test/Analysis/Checkers/WebKit/uncounted-lambda-captures.cpp +++ b/clang/test/Analysis/Checkers/WebKit/uncounted-lambda-captures.cpp @@ -63,6 +63,19 @@ template Function adopt(Detail::Callab return Function(impl, Function::Adopt); } +template +class HashMap { +public: + HashMap(); + HashMap([[clang::noescape]] const Function&); + void ensure(const KeyType&, [[clang::noescape]] const Function&); + bool operator+([[clang::noescape]] const Function&) const; + static void ifAny(HashMap, [[clang::noescape]] const Function&); + +private: + ValueType* m_table { nullptr }; +}; + } // namespace WTF struct A { @@ -268,6 +281,24 @@ struct RefCountableWithLambdaCapturingThis { nonTrivial(); }); } + + static void callLambda([[clang::noescape]] const WTF::Function()>&); + void method_captures_this_in_template_method() { + RefCountable* obj = make_obj(); + WTF::HashMap> nextMap; + nextMap.ensure(3, [&] { + return obj->next(); + }); + nextMap+[&] { + return obj->next(); + }; + WTF::HashMap>::ifAny(nextMap, [&](auto& item) -> bool { + return item->next() && obj->next(); + }); + callLambda([&]() -> RefPtr { + return obj->next(); + }); + } }; struct NonRefCountableWithLambdaCapturingThis {