Author: Ryosuke Niwa Date: 2026-08-31T13:30:46+09:00 New Revision: e98637eed96e6bced860a7149494287375414d19
URL: https://github.com/llvm/llvm-project/commit/e98637eed96e6bced860a7149494287375414d19 DIFF: https://github.com/llvm/llvm-project/commit/e98637eed96e6bced860a7149494287375414d19.diff LOG: [alpha.webkit.UncountedLocalVarsChecker] Support obtaining guardian's value via operator* (#219647) This PR fixes a bug in alpha.webkit.UncountedLocalVarsChecker that it wasn't allowing a guardian variable's getter to be called when initializing a raw pointer/reference. Also fix a bug that operator* wasn't recognized as a valid getter on a smart pointer. --------- Co-authored-by: Balázs Benics <[email protected]> Added: Modified: clang/lib/StaticAnalyzer/Checkers/WebKit/PtrTypesSemantics.cpp clang/lib/StaticAnalyzer/Checkers/WebKit/RawPtrRefLocalVarsChecker.cpp clang/test/Analysis/Checkers/WebKit/mock-types.h clang/test/Analysis/Checkers/WebKit/objc-mock-types.h clang/test/Analysis/Checkers/WebKit/uncounted-local-vars.cpp clang/test/Analysis/Checkers/WebKit/unretained-call-args.mm clang/test/Analysis/Checkers/WebKit/unretained-local-vars.mm Removed: ################################################################################ diff --git a/clang/lib/StaticAnalyzer/Checkers/WebKit/PtrTypesSemantics.cpp b/clang/lib/StaticAnalyzer/Checkers/WebKit/PtrTypesSemantics.cpp index b4e6751224595..d5fb88a15b6de 100644 --- a/clang/lib/StaticAnalyzer/Checkers/WebKit/PtrTypesSemantics.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/WebKit/PtrTypesSemantics.cpp @@ -357,10 +357,13 @@ std::optional<bool> isGetterOfSafePtr(const CXXMethodDecl *M) { std::string className = safeGetName(calleeMethodsClass); std::string method = safeGetName(M); - if (isCheckedPtr(className) && (method == "get" || method == "ptr")) + auto OpType = M->getOverloadedOperator(); + if (isCheckedPtr(className) && + (method == "get" || method == "ptr" || OpType == OO_Star)) return true; - if ((isRefType(className) && (method == "get" || method == "ptr")) || + if ((isRefType(className) && + (method == "get" || method == "ptr" || OpType == OO_Star)) || ((className == "String" || className == "AtomString" || className == "AtomStringImpl" || className == "UniqueString" || className == "UniqueStringImpl" || className == "Identifier") && diff --git a/clang/lib/StaticAnalyzer/Checkers/WebKit/RawPtrRefLocalVarsChecker.cpp b/clang/lib/StaticAnalyzer/Checkers/WebKit/RawPtrRefLocalVarsChecker.cpp index b420ce73ae82e..7f5c82a3437bd 100644 --- a/clang/lib/StaticAnalyzer/Checkers/WebKit/RawPtrRefLocalVarsChecker.cpp +++ b/clang/lib/StaticAnalyzer/Checkers/WebKit/RawPtrRefLocalVarsChecker.cpp @@ -89,6 +89,10 @@ struct GuardianVisitor : DynamicRecursiveASTVisitor { return false; if (isPtrConversion(Callee)) return true; + if (auto *Method = dyn_cast<CXXMethodDecl>(Callee)) { + if (isGetterOfSafePtr(Method).value_or(false)) + return true; + } unsigned ArgIndex = 0; unsigned ArgOffset = isa<CXXOperatorCallExpr>(CE); for (auto *Arg : CE->arguments()) { diff --git a/clang/test/Analysis/Checkers/WebKit/mock-types.h b/clang/test/Analysis/Checkers/WebKit/mock-types.h index 87b495f526f27..dea16f534ba2b 100644 --- a/clang/test/Analysis/Checkers/WebKit/mock-types.h +++ b/clang/test/Analysis/Checkers/WebKit/mock-types.h @@ -435,7 +435,8 @@ struct RefCountable { unsigned m_refCount { 0 }; }; -template <typename T> T *downcast(T *t) { return t; } +template <typename U, typename T> U [[clang::annotate_type("webkit.pointerconversion")]] *downcast(T *t) { return static_cast<U*>(t); } +template <typename U, typename T> U [[clang::annotate_type("webkit.pointerconversion")]] &downcast(T &t) { return static_cast<U&>(t); } template <typename T> struct CheckedRef { private: diff --git a/clang/test/Analysis/Checkers/WebKit/objc-mock-types.h b/clang/test/Analysis/Checkers/WebKit/objc-mock-types.h index ee9ac937eb0bf..aad2a6185d0b0 100644 --- a/clang/test/Analysis/Checkers/WebKit/objc-mock-types.h +++ b/clang/test/Analysis/Checkers/WebKit/objc-mock-types.h @@ -273,8 +273,6 @@ template<typename T> RetainPtr<T> adoptNSNullable(T*); template<typename T> RetainPtr<T> adoptCF(T); template<typename T> RetainPtr<T> adoptCFNullable(T); -template <typename T, typename S> T *downcast(S *t) { return static_cast<T*>(t); } - template <typename T> struct RemovePointer { typedef T Type; }; @@ -713,7 +711,6 @@ using WTF::adoptCFNullable; using WTF::retainPtr; using WTF::OSObjectPtr; using WTF::adoptOSObject; -using WTF::downcast; using WTF::bridge_cast; using WTF::bridge_id_cast; using WTF::is_objc; diff --git a/clang/test/Analysis/Checkers/WebKit/uncounted-local-vars.cpp b/clang/test/Analysis/Checkers/WebKit/uncounted-local-vars.cpp index d36e78f12453f..31990217525c1 100644 --- a/clang/test/Analysis/Checkers/WebKit/uncounted-local-vars.cpp +++ b/clang/test/Analysis/Checkers/WebKit/uncounted-local-vars.cpp @@ -214,6 +214,23 @@ void foo9(RefCountable& o) { } } +RefCountable* provide(); + +struct Derived : public RefCountable { +}; + +void foo10() { + RefPtr<RefCountable> obj = provide(); + if (obj) { + auto* ptr = downcast<Derived>(obj.get()); + ptr->method(); + } + if (obj) { + auto& ref = downcast<Derived>(*obj); + ref.method(); + } +} + } // namespace guardian_scopes namespace auto_keyword { @@ -705,4 +722,4 @@ namespace binding_raw_ptr { a->method(); } -} \ No newline at end of file +} diff --git a/clang/test/Analysis/Checkers/WebKit/unretained-call-args.mm b/clang/test/Analysis/Checkers/WebKit/unretained-call-args.mm index 037bc1571bbef..e0e867d783bb1 100644 --- a/clang/test/Analysis/Checkers/WebKit/unretained-call-args.mm +++ b/clang/test/Analysis/Checkers/WebKit/unretained-call-args.mm @@ -2,6 +2,7 @@ // RUN: %clang_analyze_cc1 -analyzer-checker=alpha.webkit.UnretainedCallArgsChecker -verify %s #include "objc-mock-types.h" +#include "mock-types.h" SomeObj *provide(); void consume_obj(SomeObj*); diff --git a/clang/test/Analysis/Checkers/WebKit/unretained-local-vars.mm b/clang/test/Analysis/Checkers/WebKit/unretained-local-vars.mm index a33cf9eec8476..4e1ac86bd823d 100644 --- a/clang/test/Analysis/Checkers/WebKit/unretained-local-vars.mm +++ b/clang/test/Analysis/Checkers/WebKit/unretained-local-vars.mm @@ -1,6 +1,7 @@ // RUN: %clang_analyze_cc1 -analyzer-checker=alpha.webkit.UnretainedLocalVarsChecker -verify %s #import "objc-mock-types.h" +#import "mock-types.h" #import "mock-system-header.h" void someFunction(); _______________________________________________ cfe-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits
