[clang] Add missing support for traversal kind in addMatcher overloads (#170953)
This was noted in #170540, and seems to simply be an oversight. This patch just add the same logic already used in other addMatcher() implementations that honor the traversal kind. Fixes #179386.
This commit is contained in:
parent
13f659c21d
commit
64e1318c55
@ -396,6 +396,7 @@ Fixed Point Support in Clang
|
||||
AST Matchers
|
||||
------------
|
||||
- Add ``functionTypeLoc`` matcher for matching ``FunctionTypeLoc``.
|
||||
- Add missing support for ``TraversalKind`` in some ``addMatcher()`` overloads.
|
||||
|
||||
clang-format
|
||||
------------
|
||||
|
||||
@ -1654,6 +1654,16 @@ private:
|
||||
} // end namespace
|
||||
} // end namespace internal
|
||||
|
||||
template <typename T>
|
||||
static internal::Matcher<T>
|
||||
adjustTraversalKind(const internal::Matcher<T> &NodeMatch,
|
||||
MatchFinder::MatchCallback *Action) {
|
||||
if (Action)
|
||||
if (std::optional<TraversalKind> TK = Action->getCheckTraversalKind())
|
||||
return traverse(*TK, NodeMatch);
|
||||
return NodeMatch;
|
||||
}
|
||||
|
||||
MatchFinder::MatchResult::MatchResult(const BoundNodes &Nodes,
|
||||
ASTContext *Context)
|
||||
: Nodes(Nodes), Context(Context),
|
||||
@ -1669,67 +1679,61 @@ MatchFinder::~MatchFinder() {}
|
||||
|
||||
void MatchFinder::addMatcher(const DeclarationMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
std::optional<TraversalKind> TK;
|
||||
if (Action)
|
||||
TK = Action->getCheckTraversalKind();
|
||||
if (TK)
|
||||
Matchers.DeclOrStmt.emplace_back(traverse(*TK, NodeMatch), Action);
|
||||
else
|
||||
Matchers.DeclOrStmt.emplace_back(NodeMatch, Action);
|
||||
Matchers.DeclOrStmt.emplace_back(adjustTraversalKind(NodeMatch, Action),
|
||||
Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const TypeMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.Type.emplace_back(NodeMatch, Action);
|
||||
Matchers.Type.emplace_back(adjustTraversalKind(NodeMatch, Action), Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const StatementMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
std::optional<TraversalKind> TK;
|
||||
if (Action)
|
||||
TK = Action->getCheckTraversalKind();
|
||||
if (TK)
|
||||
Matchers.DeclOrStmt.emplace_back(traverse(*TK, NodeMatch), Action);
|
||||
else
|
||||
Matchers.DeclOrStmt.emplace_back(NodeMatch, Action);
|
||||
Matchers.DeclOrStmt.emplace_back(adjustTraversalKind(NodeMatch, Action),
|
||||
Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const NestedNameSpecifierMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.NestedNameSpecifier.emplace_back(NodeMatch, Action);
|
||||
Matchers.NestedNameSpecifier.emplace_back(
|
||||
adjustTraversalKind(NodeMatch, Action), Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const NestedNameSpecifierLocMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.NestedNameSpecifierLoc.emplace_back(NodeMatch, Action);
|
||||
Matchers.NestedNameSpecifierLoc.emplace_back(
|
||||
adjustTraversalKind(NodeMatch, Action), Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const TypeLocMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.TypeLoc.emplace_back(NodeMatch, Action);
|
||||
Matchers.TypeLoc.emplace_back(adjustTraversalKind(NodeMatch, Action), Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const CXXCtorInitializerMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.CtorInit.emplace_back(NodeMatch, Action);
|
||||
Matchers.CtorInit.emplace_back(adjustTraversalKind(NodeMatch, Action),
|
||||
Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const TemplateArgumentLocMatcher &NodeMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.TemplateArgumentLoc.emplace_back(NodeMatch, Action);
|
||||
Matchers.TemplateArgumentLoc.emplace_back(
|
||||
adjustTraversalKind(NodeMatch, Action), Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
void MatchFinder::addMatcher(const AttrMatcher &AttrMatch,
|
||||
MatchCallback *Action) {
|
||||
Matchers.Attr.emplace_back(AttrMatch, Action);
|
||||
Matchers.Attr.emplace_back(adjustTraversalKind(AttrMatch, Action), Action);
|
||||
Matchers.AllCallbacks.insert(Action);
|
||||
}
|
||||
|
||||
|
||||
@ -297,6 +297,41 @@ TEST(DynTypedMatcherTest, ConstructWithTraversalKindOverridesNestedTK) {
|
||||
llvm::ValueIs(TK_IgnoreUnlessSpelledInSource));
|
||||
}
|
||||
|
||||
TEST(MatchFinder, AddMatcherOverloadsHonorTraversalKind) {
|
||||
StringRef Code = R"cpp(
|
||||
struct B {};
|
||||
struct C : B {
|
||||
C() {}
|
||||
};
|
||||
)cpp";
|
||||
|
||||
// C() has an implicit initializer for B.
|
||||
auto Matcher = cxxCtorInitializer(isBaseInitializer());
|
||||
|
||||
{
|
||||
bool Matched = false;
|
||||
MatchFinder Finder;
|
||||
struct TestCallback : public MatchFinder::MatchCallback {
|
||||
std::optional<TraversalKind> TK;
|
||||
bool *Matched;
|
||||
TestCallback(std::optional<TraversalKind> TK, bool *Matched)
|
||||
: TK(TK), Matched(Matched) {}
|
||||
void run(const MatchFinder::MatchResult &Result) override {
|
||||
*Matched = true;
|
||||
}
|
||||
std::optional<TraversalKind> getCheckTraversalKind() const override {
|
||||
return TK;
|
||||
}
|
||||
} Callback(TK_IgnoreUnlessSpelledInSource, &Matched);
|
||||
Finder.addMatcher(Matcher, &Callback);
|
||||
std::unique_ptr<FrontendActionFactory> Factory(
|
||||
newFrontendActionFactory(&Finder));
|
||||
ASSERT_TRUE(tooling::runToolOnCode(Factory->create(), Code));
|
||||
EXPECT_FALSE(Matched) << "Matcher not using specified TraversalKind, "
|
||||
"TK_IgnoreUnlessSpelledInSource";
|
||||
}
|
||||
}
|
||||
|
||||
TEST(IsInlineMatcher, IsInline) {
|
||||
EXPECT_TRUE(matches("void g(); inline void f();",
|
||||
functionDecl(isInline(), hasName("f"))));
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user