Author: Nathan Ridge Date: 2023-08-25T16:54:29-04:00 New Revision: f0f53cb4bfb2b6c5ec6661b565a764c704484fa2
URL: https://github.com/llvm/llvm-project/commit/f0f53cb4bfb2b6c5ec6661b565a764c704484fa2 DIFF: https://github.com/llvm/llvm-project/commit/f0f53cb4bfb2b6c5ec6661b565a764c704484fa2.diff LOG: [clangd] Do not ignore qualifier in heuristic resolution of dependent MemberExpr Fixes https://github.com/llvm/llvm-project/issues/64841 Differential Revision: https://reviews.llvm.org/D158873 Added: Modified: clang-tools-extra/clangd/HeuristicResolver.cpp clang-tools-extra/clangd/unittests/XRefsTests.cpp Removed: ################################################################################ diff --git a/clang-tools-extra/clangd/HeuristicResolver.cpp b/clang-tools-extra/clangd/HeuristicResolver.cpp index 719094dbf2b7e5..3c147b6b582bf0 100644 --- a/clang-tools-extra/clangd/HeuristicResolver.cpp +++ b/clang-tools-extra/clangd/HeuristicResolver.cpp @@ -119,8 +119,8 @@ const Type *HeuristicResolver::getPointeeType(const Type *T) const { std::vector<const NamedDecl *> HeuristicResolver::resolveMemberExpr( const CXXDependentScopeMemberExpr *ME) const { - // If the expression has a qualifier, first try resolving the member - // inside the qualifier's type. + // If the expression has a qualifier, try resolving the member inside the + // qualifier's type. // Note that we cannot use a NonStaticFilter in either case, for a couple // of reasons: // 1. It's valid to access a static member using instance member syntax, @@ -137,10 +137,15 @@ std::vector<const NamedDecl *> HeuristicResolver::resolveMemberExpr( if (!Decls.empty()) return Decls; } + + // Do not proceed to try resolving the member in the expression's base type + // without regard to the qualifier, as that could produce incorrect results. + // For example, `void foo() { this->Base::foo(); }` shouldn't resolve to + // foo() itself! + return {}; } - // If that didn't yield any results, try resolving the member inside - // the expression's base type. + // Try resolving the member inside the expression's base type. const Type *BaseType = ME->getBaseType().getTypePtrOrNull(); if (ME->isArrow()) { BaseType = getPointeeType(BaseType); diff --git a/clang-tools-extra/clangd/unittests/XRefsTests.cpp b/clang-tools-extra/clangd/unittests/XRefsTests.cpp index 6d7fd62016991a..f53cbf01b7992c 100644 --- a/clang-tools-extra/clangd/unittests/XRefsTests.cpp +++ b/clang-tools-extra/clangd/unittests/XRefsTests.cpp @@ -1009,7 +1009,17 @@ TEST(LocateSymbol, All) { void play(Dog *dog) { [dog ho^wl]; } - )objc"}; + )objc", + R"cpp( + struct PointerIntPairInfo { + static void *getPointer(void *Value); + }; + + template <typename Info = PointerIntPairInfo> struct PointerIntPair { + void *Value; + void *getPointer() const { return Info::get^Pointer(Value); } + }; + )cpp"}; for (const char *Test : Tests) { Annotations T(Test); std::optional<Range> WantDecl; _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits