Path: blob/main/contrib/llvm-project/clang/lib/ASTMatchers/ASTMatchersInternal.cpp
35262 views
//===- ASTMatchersInternal.cpp - Structural query framework ---------------===//1//2// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.3// See https://llvm.org/LICENSE.txt for license information.4// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception5//6//===----------------------------------------------------------------------===//7//8// Implements the base layer of the matcher framework.9//10//===----------------------------------------------------------------------===//1112#include "clang/ASTMatchers/ASTMatchersInternal.h"13#include "clang/AST/ASTContext.h"14#include "clang/AST/ASTTypeTraits.h"15#include "clang/AST/Decl.h"16#include "clang/AST/DeclTemplate.h"17#include "clang/AST/ParentMapContext.h"18#include "clang/AST/PrettyPrinter.h"19#include "clang/ASTMatchers/ASTMatchers.h"20#include "clang/Basic/LLVM.h"21#include "clang/Lex/Lexer.h"22#include "llvm/ADT/ArrayRef.h"23#include "llvm/ADT/IntrusiveRefCntPtr.h"24#include "llvm/ADT/SmallString.h"25#include "llvm/ADT/SmallVector.h"26#include "llvm/ADT/StringRef.h"27#include "llvm/Support/Casting.h"28#include "llvm/Support/ErrorHandling.h"29#include "llvm/Support/ManagedStatic.h"30#include "llvm/Support/Regex.h"31#include "llvm/Support/WithColor.h"32#include "llvm/Support/raw_ostream.h"33#include <algorithm>34#include <cassert>35#include <cstddef>36#include <optional>37#include <string>38#include <utility>39#include <vector>4041namespace clang {42namespace ast_matchers {4344AST_MATCHER_P(ObjCMessageExpr, hasAnySelectorMatcher, std::vector<std::string>,45Matches) {46return llvm::is_contained(Matches, Node.getSelector().getAsString());47}4849namespace internal {5051static bool notUnaryOperator(const DynTypedNode &DynNode,52ASTMatchFinder *Finder,53BoundNodesTreeBuilder *Builder,54ArrayRef<DynTypedMatcher> InnerMatchers);5556static bool allOfVariadicOperator(const DynTypedNode &DynNode,57ASTMatchFinder *Finder,58BoundNodesTreeBuilder *Builder,59ArrayRef<DynTypedMatcher> InnerMatchers);6061static bool eachOfVariadicOperator(const DynTypedNode &DynNode,62ASTMatchFinder *Finder,63BoundNodesTreeBuilder *Builder,64ArrayRef<DynTypedMatcher> InnerMatchers);6566static bool anyOfVariadicOperator(const DynTypedNode &DynNode,67ASTMatchFinder *Finder,68BoundNodesTreeBuilder *Builder,69ArrayRef<DynTypedMatcher> InnerMatchers);7071static bool optionallyVariadicOperator(const DynTypedNode &DynNode,72ASTMatchFinder *Finder,73BoundNodesTreeBuilder *Builder,74ArrayRef<DynTypedMatcher> InnerMatchers);7576bool matchesAnyBase(const CXXRecordDecl &Node,77const Matcher<CXXBaseSpecifier> &BaseSpecMatcher,78ASTMatchFinder *Finder, BoundNodesTreeBuilder *Builder) {79if (!Node.hasDefinition())80return false;8182CXXBasePaths Paths;83Paths.setOrigin(&Node);8485const auto basePredicate =86[Finder, Builder, &BaseSpecMatcher](const CXXBaseSpecifier *BaseSpec,87CXXBasePath &IgnoredParam) {88BoundNodesTreeBuilder Result(*Builder);89if (BaseSpecMatcher.matches(*BaseSpec, Finder, &Result)) {90*Builder = std::move(Result);91return true;92}93return false;94};9596return Node.lookupInBases(basePredicate, Paths,97/*LookupInDependent =*/true);98}99100void BoundNodesTreeBuilder::visitMatches(Visitor *ResultVisitor) {101if (Bindings.empty())102Bindings.push_back(BoundNodesMap());103for (BoundNodesMap &Binding : Bindings) {104ResultVisitor->visitMatch(BoundNodes(Binding));105}106}107108namespace {109110using VariadicOperatorFunction = bool (*)(111const DynTypedNode &DynNode, ASTMatchFinder *Finder,112BoundNodesTreeBuilder *Builder, ArrayRef<DynTypedMatcher> InnerMatchers);113114template <VariadicOperatorFunction Func>115class VariadicMatcher : public DynMatcherInterface {116public:117VariadicMatcher(std::vector<DynTypedMatcher> InnerMatchers)118: InnerMatchers(std::move(InnerMatchers)) {}119120bool dynMatches(const DynTypedNode &DynNode, ASTMatchFinder *Finder,121BoundNodesTreeBuilder *Builder) const override {122return Func(DynNode, Finder, Builder, InnerMatchers);123}124125private:126std::vector<DynTypedMatcher> InnerMatchers;127};128129class IdDynMatcher : public DynMatcherInterface {130public:131IdDynMatcher(StringRef ID,132IntrusiveRefCntPtr<DynMatcherInterface> InnerMatcher)133: ID(ID), InnerMatcher(std::move(InnerMatcher)) {}134135bool dynMatches(const DynTypedNode &DynNode, ASTMatchFinder *Finder,136BoundNodesTreeBuilder *Builder) const override {137bool Result = InnerMatcher->dynMatches(DynNode, Finder, Builder);138if (Result) Builder->setBinding(ID, DynNode);139return Result;140}141142std::optional<clang::TraversalKind> TraversalKind() const override {143return InnerMatcher->TraversalKind();144}145146private:147const std::string ID;148const IntrusiveRefCntPtr<DynMatcherInterface> InnerMatcher;149};150151/// A matcher that always returns true.152class TrueMatcherImpl : public DynMatcherInterface {153public:154TrueMatcherImpl() = default;155156bool dynMatches(const DynTypedNode &, ASTMatchFinder *,157BoundNodesTreeBuilder *) const override {158return true;159}160};161162/// A matcher that specifies a particular \c TraversalKind.163///164/// The kind provided to the constructor overrides any kind that may be165/// specified by the `InnerMatcher`.166class DynTraversalMatcherImpl : public DynMatcherInterface {167public:168explicit DynTraversalMatcherImpl(169clang::TraversalKind TK,170IntrusiveRefCntPtr<DynMatcherInterface> InnerMatcher)171: TK(TK), InnerMatcher(std::move(InnerMatcher)) {}172173bool dynMatches(const DynTypedNode &DynNode, ASTMatchFinder *Finder,174BoundNodesTreeBuilder *Builder) const override {175return this->InnerMatcher->dynMatches(DynNode, Finder, Builder);176}177178std::optional<clang::TraversalKind> TraversalKind() const override {179return TK;180}181182private:183clang::TraversalKind TK;184IntrusiveRefCntPtr<DynMatcherInterface> InnerMatcher;185};186187} // namespace188189bool ASTMatchFinder::isTraversalIgnoringImplicitNodes() const {190return getASTContext().getParentMapContext().getTraversalKind() ==191TK_IgnoreUnlessSpelledInSource;192}193194DynTypedMatcher195DynTypedMatcher::constructVariadic(DynTypedMatcher::VariadicOperator Op,196ASTNodeKind SupportedKind,197std::vector<DynTypedMatcher> InnerMatchers) {198assert(!InnerMatchers.empty() && "Array must not be empty.");199assert(llvm::all_of(InnerMatchers,200[SupportedKind](const DynTypedMatcher &M) {201return M.canConvertTo(SupportedKind);202}) &&203"InnerMatchers must be convertible to SupportedKind!");204205// We must relax the restrict kind here.206// The different operators might deal differently with a mismatch.207// Make it the same as SupportedKind, since that is the broadest type we are208// allowed to accept.209auto RestrictKind = SupportedKind;210211switch (Op) {212case VO_AllOf:213// In the case of allOf() we must pass all the checks, so making214// RestrictKind the most restrictive can save us time. This way we reject215// invalid types earlier and we can elide the kind checks inside the216// matcher.217for (auto &IM : InnerMatchers) {218RestrictKind =219ASTNodeKind::getMostDerivedType(RestrictKind, IM.RestrictKind);220}221return DynTypedMatcher(222SupportedKind, RestrictKind,223new VariadicMatcher<allOfVariadicOperator>(std::move(InnerMatchers)));224225case VO_AnyOf:226return DynTypedMatcher(227SupportedKind, RestrictKind,228new VariadicMatcher<anyOfVariadicOperator>(std::move(InnerMatchers)));229230case VO_EachOf:231return DynTypedMatcher(232SupportedKind, RestrictKind,233new VariadicMatcher<eachOfVariadicOperator>(std::move(InnerMatchers)));234235case VO_Optionally:236return DynTypedMatcher(SupportedKind, RestrictKind,237new VariadicMatcher<optionallyVariadicOperator>(238std::move(InnerMatchers)));239240case VO_UnaryNot:241// FIXME: Implement the Not operator to take a single matcher instead of a242// vector.243return DynTypedMatcher(244SupportedKind, RestrictKind,245new VariadicMatcher<notUnaryOperator>(std::move(InnerMatchers)));246}247llvm_unreachable("Invalid Op value.");248}249250DynTypedMatcher251DynTypedMatcher::constructRestrictedWrapper(const DynTypedMatcher &InnerMatcher,252ASTNodeKind RestrictKind) {253DynTypedMatcher Copy = InnerMatcher;254Copy.RestrictKind = RestrictKind;255return Copy;256}257258DynTypedMatcher DynTypedMatcher::withTraversalKind(TraversalKind TK) {259auto Copy = *this;260Copy.Implementation =261new DynTraversalMatcherImpl(TK, std::move(Copy.Implementation));262return Copy;263}264265DynTypedMatcher DynTypedMatcher::trueMatcher(ASTNodeKind NodeKind) {266// We only ever need one instance of TrueMatcherImpl, so we create a static267// instance and reuse it to reduce the overhead of the matcher and increase268// the chance of cache hits.269static const llvm::IntrusiveRefCntPtr<TrueMatcherImpl> Instance =270new TrueMatcherImpl();271return DynTypedMatcher(NodeKind, NodeKind, Instance);272}273274bool DynTypedMatcher::canMatchNodesOfKind(ASTNodeKind Kind) const {275return RestrictKind.isBaseOf(Kind);276}277278DynTypedMatcher DynTypedMatcher::dynCastTo(const ASTNodeKind Kind) const {279auto Copy = *this;280Copy.SupportedKind = Kind;281Copy.RestrictKind = ASTNodeKind::getMostDerivedType(Kind, RestrictKind);282return Copy;283}284285bool DynTypedMatcher::matches(const DynTypedNode &DynNode,286ASTMatchFinder *Finder,287BoundNodesTreeBuilder *Builder) const {288TraversalKindScope RAII(Finder->getASTContext(),289Implementation->TraversalKind());290291if (Finder->isTraversalIgnoringImplicitNodes() &&292Finder->IsMatchingInASTNodeNotSpelledInSource())293return false;294295if (!Finder->isTraversalIgnoringImplicitNodes() &&296Finder->IsMatchingInASTNodeNotAsIs())297return false;298299auto N =300Finder->getASTContext().getParentMapContext().traverseIgnored(DynNode);301302if (RestrictKind.isBaseOf(N.getNodeKind()) &&303Implementation->dynMatches(N, Finder, Builder)) {304return true;305}306// Delete all bindings when a matcher does not match.307// This prevents unexpected exposure of bound nodes in unmatches308// branches of the match tree.309Builder->removeBindings([](const BoundNodesMap &) { return true; });310return false;311}312313bool DynTypedMatcher::matchesNoKindCheck(const DynTypedNode &DynNode,314ASTMatchFinder *Finder,315BoundNodesTreeBuilder *Builder) const {316TraversalKindScope raii(Finder->getASTContext(),317Implementation->TraversalKind());318319if (Finder->isTraversalIgnoringImplicitNodes() &&320Finder->IsMatchingInASTNodeNotSpelledInSource())321return false;322323if (!Finder->isTraversalIgnoringImplicitNodes() &&324Finder->IsMatchingInASTNodeNotAsIs())325return false;326327auto N =328Finder->getASTContext().getParentMapContext().traverseIgnored(DynNode);329330assert(RestrictKind.isBaseOf(N.getNodeKind()));331if (Implementation->dynMatches(N, Finder, Builder)) {332return true;333}334// Delete all bindings when a matcher does not match.335// This prevents unexpected exposure of bound nodes in unmatches336// branches of the match tree.337Builder->removeBindings([](const BoundNodesMap &) { return true; });338return false;339}340341std::optional<DynTypedMatcher> DynTypedMatcher::tryBind(StringRef ID) const {342if (!AllowBind)343return std::nullopt;344auto Result = *this;345Result.Implementation =346new IdDynMatcher(ID, std::move(Result.Implementation));347return std::move(Result);348}349350bool DynTypedMatcher::canConvertTo(ASTNodeKind To) const {351const auto From = getSupportedKind();352auto QualKind = ASTNodeKind::getFromNodeKind<QualType>();353auto TypeKind = ASTNodeKind::getFromNodeKind<Type>();354/// Mimic the implicit conversions of Matcher<>.355/// - From Matcher<Type> to Matcher<QualType>356if (From.isSame(TypeKind) && To.isSame(QualKind)) return true;357/// - From Matcher<Base> to Matcher<Derived>358return From.isBaseOf(To);359}360361void BoundNodesTreeBuilder::addMatch(const BoundNodesTreeBuilder &Other) {362Bindings.append(Other.Bindings.begin(), Other.Bindings.end());363}364365static bool notUnaryOperator(const DynTypedNode &DynNode,366ASTMatchFinder *Finder,367BoundNodesTreeBuilder *Builder,368ArrayRef<DynTypedMatcher> InnerMatchers) {369if (InnerMatchers.size() != 1)370return false;371372// The 'unless' matcher will always discard the result:373// If the inner matcher doesn't match, unless returns true,374// but the inner matcher cannot have bound anything.375// If the inner matcher matches, the result is false, and376// any possible binding will be discarded.377// We still need to hand in all the bound nodes up to this378// point so the inner matcher can depend on bound nodes,379// and we need to actively discard the bound nodes, otherwise380// the inner matcher will reset the bound nodes if it doesn't381// match, but this would be inversed by 'unless'.382BoundNodesTreeBuilder Discard(*Builder);383return !InnerMatchers[0].matches(DynNode, Finder, &Discard);384}385386static bool allOfVariadicOperator(const DynTypedNode &DynNode,387ASTMatchFinder *Finder,388BoundNodesTreeBuilder *Builder,389ArrayRef<DynTypedMatcher> InnerMatchers) {390// allOf leads to one matcher for each alternative in the first391// matcher combined with each alternative in the second matcher.392// Thus, we can reuse the same Builder.393return llvm::all_of(InnerMatchers, [&](const DynTypedMatcher &InnerMatcher) {394return InnerMatcher.matchesNoKindCheck(DynNode, Finder, Builder);395});396}397398static bool eachOfVariadicOperator(const DynTypedNode &DynNode,399ASTMatchFinder *Finder,400BoundNodesTreeBuilder *Builder,401ArrayRef<DynTypedMatcher> InnerMatchers) {402BoundNodesTreeBuilder Result;403bool Matched = false;404for (const DynTypedMatcher &InnerMatcher : InnerMatchers) {405BoundNodesTreeBuilder BuilderInner(*Builder);406if (InnerMatcher.matches(DynNode, Finder, &BuilderInner)) {407Matched = true;408Result.addMatch(BuilderInner);409}410}411*Builder = std::move(Result);412return Matched;413}414415static bool anyOfVariadicOperator(const DynTypedNode &DynNode,416ASTMatchFinder *Finder,417BoundNodesTreeBuilder *Builder,418ArrayRef<DynTypedMatcher> InnerMatchers) {419for (const DynTypedMatcher &InnerMatcher : InnerMatchers) {420BoundNodesTreeBuilder Result = *Builder;421if (InnerMatcher.matches(DynNode, Finder, &Result)) {422*Builder = std::move(Result);423return true;424}425}426return false;427}428429static bool430optionallyVariadicOperator(const DynTypedNode &DynNode, ASTMatchFinder *Finder,431BoundNodesTreeBuilder *Builder,432ArrayRef<DynTypedMatcher> InnerMatchers) {433if (InnerMatchers.size() != 1)434return false;435436BoundNodesTreeBuilder Result(*Builder);437if (InnerMatchers[0].matches(DynNode, Finder, &Result))438*Builder = std::move(Result);439return true;440}441442inline static443std::vector<std::string> vectorFromRefs(ArrayRef<const StringRef *> NameRefs) {444std::vector<std::string> Names;445Names.reserve(NameRefs.size());446for (auto *Name : NameRefs)447Names.emplace_back(*Name);448return Names;449}450451Matcher<NamedDecl> hasAnyNameFunc(ArrayRef<const StringRef *> NameRefs) {452return internal::Matcher<NamedDecl>(453new internal::HasNameMatcher(vectorFromRefs(NameRefs)));454}455456Matcher<ObjCMessageExpr> hasAnySelectorFunc(457ArrayRef<const StringRef *> NameRefs) {458return hasAnySelectorMatcher(vectorFromRefs(NameRefs));459}460461HasOpNameMatcher hasAnyOperatorNameFunc(ArrayRef<const StringRef *> NameRefs) {462return HasOpNameMatcher(vectorFromRefs(NameRefs));463}464465HasOverloadOpNameMatcher466hasAnyOverloadedOperatorNameFunc(ArrayRef<const StringRef *> NameRefs) {467return HasOverloadOpNameMatcher(vectorFromRefs(NameRefs));468}469470HasNameMatcher::HasNameMatcher(std::vector<std::string> N)471: UseUnqualifiedMatch(472llvm::all_of(N, [](StringRef Name) { return !Name.contains("::"); })),473Names(std::move(N)) {474#ifndef NDEBUG475for (StringRef Name : Names)476assert(!Name.empty());477#endif478}479480static bool consumeNameSuffix(StringRef &FullName, StringRef Suffix) {481StringRef Name = FullName;482if (!Name.ends_with(Suffix))483return false;484Name = Name.drop_back(Suffix.size());485if (!Name.empty()) {486if (!Name.ends_with("::"))487return false;488Name = Name.drop_back(2);489}490FullName = Name;491return true;492}493494static StringRef getNodeName(const NamedDecl &Node,495llvm::SmallString<128> &Scratch) {496// Simple name.497if (Node.getIdentifier())498return Node.getName();499500if (Node.getDeclName()) {501// Name needs to be constructed.502Scratch.clear();503llvm::raw_svector_ostream OS(Scratch);504Node.printName(OS);505return OS.str();506}507508return "(anonymous)";509}510511static StringRef getNodeName(const RecordDecl &Node,512llvm::SmallString<128> &Scratch) {513if (Node.getIdentifier()) {514return Node.getName();515}516Scratch.clear();517return ("(anonymous " + Node.getKindName() + ")").toStringRef(Scratch);518}519520static StringRef getNodeName(const NamespaceDecl &Node,521llvm::SmallString<128> &Scratch) {522return Node.isAnonymousNamespace() ? "(anonymous namespace)" : Node.getName();523}524525namespace {526527class PatternSet {528public:529PatternSet(ArrayRef<std::string> Names) {530Patterns.reserve(Names.size());531for (StringRef Name : Names)532Patterns.push_back({Name, Name.starts_with("::")});533}534535/// Consumes the name suffix from each pattern in the set and removes the ones536/// that didn't match.537/// Return true if there are still any patterns left.538bool consumeNameSuffix(StringRef NodeName, bool CanSkip) {539for (size_t I = 0; I < Patterns.size();) {540if (::clang::ast_matchers::internal::consumeNameSuffix(Patterns[I].P,541NodeName) ||542CanSkip) {543++I;544} else {545Patterns.erase(Patterns.begin() + I);546}547}548return !Patterns.empty();549}550551/// Check if any of the patterns are a match.552/// A match will be a pattern that was fully consumed, that also matches the553/// 'fully qualified' requirement.554bool foundMatch(bool AllowFullyQualified) const {555return llvm::any_of(Patterns, [&](const Pattern &Pattern) {556return Pattern.P.empty() &&557(AllowFullyQualified || !Pattern.IsFullyQualified);558});559}560561private:562struct Pattern {563StringRef P;564bool IsFullyQualified;565};566567llvm::SmallVector<Pattern, 8> Patterns;568};569570} // namespace571572bool HasNameMatcher::matchesNodeUnqualified(const NamedDecl &Node) const {573assert(UseUnqualifiedMatch);574llvm::SmallString<128> Scratch;575StringRef NodeName = getNodeName(Node, Scratch);576return llvm::any_of(Names, [&](StringRef Name) {577return consumeNameSuffix(Name, NodeName) && Name.empty();578});579}580581bool HasNameMatcher::matchesNodeFullFast(const NamedDecl &Node) const {582PatternSet Patterns(Names);583llvm::SmallString<128> Scratch;584585// This function is copied and adapted from NamedDecl::printQualifiedName()586// By matching each part individually we optimize in a couple of ways:587// - We can exit early on the first failure.588// - We can skip inline/anonymous namespaces without another pass.589// - We print one name at a time, reducing the chance of overflowing the590// inlined space of the SmallString.591592// First, match the name.593if (!Patterns.consumeNameSuffix(getNodeName(Node, Scratch),594/*CanSkip=*/false))595return false;596597// Try to match each declaration context.598// We are allowed to skip anonymous and inline namespaces if they don't match.599const DeclContext *Ctx = Node.getDeclContext();600601if (Ctx->isFunctionOrMethod())602return Patterns.foundMatch(/*AllowFullyQualified=*/false);603604for (; Ctx; Ctx = Ctx->getParent()) {605// Linkage Spec can just be ignored606// FIXME: Any other DeclContext kinds that can be safely disregarded607if (isa<LinkageSpecDecl>(Ctx))608continue;609if (!isa<NamedDecl>(Ctx))610break;611if (Patterns.foundMatch(/*AllowFullyQualified=*/false))612return true;613614if (const auto *ND = dyn_cast<NamespaceDecl>(Ctx)) {615// If it matches (or we can skip it), continue.616if (Patterns.consumeNameSuffix(getNodeName(*ND, Scratch),617/*CanSkip=*/ND->isAnonymousNamespace() ||618ND->isInline()))619continue;620return false;621}622if (const auto *RD = dyn_cast<RecordDecl>(Ctx)) {623if (!isa<ClassTemplateSpecializationDecl>(Ctx)) {624if (Patterns.consumeNameSuffix(getNodeName(*RD, Scratch),625/*CanSkip=*/false))626continue;627628return false;629}630}631632// We don't know how to deal with this DeclContext.633// Fallback to the slow version of the code.634return matchesNodeFullSlow(Node);635}636637return Patterns.foundMatch(/*AllowFullyQualified=*/true);638}639640bool HasNameMatcher::matchesNodeFullSlow(const NamedDecl &Node) const {641const bool SkipUnwrittenCases[] = {false, true};642for (bool SkipUnwritten : SkipUnwrittenCases) {643llvm::SmallString<128> NodeName = StringRef("::");644llvm::raw_svector_ostream OS(NodeName);645646PrintingPolicy Policy = Node.getASTContext().getPrintingPolicy();647Policy.SuppressUnwrittenScope = SkipUnwritten;648Policy.SuppressInlineNamespace = SkipUnwritten;649Node.printQualifiedName(OS, Policy);650651const StringRef FullName = OS.str();652653for (const StringRef Pattern : Names) {654if (Pattern.starts_with("::")) {655if (FullName == Pattern)656return true;657} else if (FullName.ends_with(Pattern) &&658FullName.drop_back(Pattern.size()).ends_with("::")) {659return true;660}661}662}663664return false;665}666667bool HasNameMatcher::matchesNode(const NamedDecl &Node) const {668assert(matchesNodeFullFast(Node) == matchesNodeFullSlow(Node));669if (UseUnqualifiedMatch) {670assert(matchesNodeUnqualified(Node) == matchesNodeFullFast(Node));671return matchesNodeUnqualified(Node);672}673return matchesNodeFullFast(Node);674}675676// Checks whether \p Loc points to a token with source text of \p TokenText.677static bool isTokenAtLoc(const SourceManager &SM, const LangOptions &LangOpts,678StringRef Text, SourceLocation Loc) {679llvm::SmallString<16> Buffer;680bool Invalid = false;681// Since `Loc` may point into an expansion buffer, which has no corresponding682// source, we need to look at the spelling location to read the actual source.683StringRef TokenText = Lexer::getSpelling(SM.getSpellingLoc(Loc), Buffer, SM,684LangOpts, &Invalid);685return !Invalid && Text == TokenText;686}687688std::optional<SourceLocation>689getExpansionLocOfMacro(StringRef MacroName, SourceLocation Loc,690const ASTContext &Context) {691auto &SM = Context.getSourceManager();692const LangOptions &LangOpts = Context.getLangOpts();693while (Loc.isMacroID()) {694SrcMgr::ExpansionInfo Expansion =695SM.getSLocEntry(SM.getFileID(Loc)).getExpansion();696if (Expansion.isMacroArgExpansion())697// Check macro argument for an expansion of the given macro. For example,698// `F(G(3))`, where `MacroName` is `G`.699if (std::optional<SourceLocation> ArgLoc = getExpansionLocOfMacro(700MacroName, Expansion.getSpellingLoc(), Context))701return ArgLoc;702Loc = Expansion.getExpansionLocStart();703if (isTokenAtLoc(SM, LangOpts, MacroName, Loc))704return Loc;705}706return std::nullopt;707}708709std::shared_ptr<llvm::Regex> createAndVerifyRegex(StringRef Regex,710llvm::Regex::RegexFlags Flags,711StringRef MatcherID) {712assert(!Regex.empty() && "Empty regex string");713auto SharedRegex = std::make_shared<llvm::Regex>(Regex, Flags);714std::string Error;715if (!SharedRegex->isValid(Error)) {716llvm::WithColor::error()717<< "building matcher '" << MatcherID << "': " << Error << "\n";718llvm::WithColor::note() << " input was '" << Regex << "'\n";719}720return SharedRegex;721}722} // end namespace internal723724const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCAutoreleasePoolStmt>725autoreleasePoolStmt;726const internal::VariadicDynCastAllOfMatcher<Decl, TranslationUnitDecl>727translationUnitDecl;728const internal::VariadicDynCastAllOfMatcher<Decl, TypedefDecl> typedefDecl;729const internal::VariadicDynCastAllOfMatcher<Decl, TypedefNameDecl>730typedefNameDecl;731const internal::VariadicDynCastAllOfMatcher<Decl, TypeAliasDecl> typeAliasDecl;732const internal::VariadicDynCastAllOfMatcher<Decl, TypeAliasTemplateDecl>733typeAliasTemplateDecl;734const internal::VariadicAllOfMatcher<Decl> decl;735const internal::VariadicDynCastAllOfMatcher<Decl, DecompositionDecl> decompositionDecl;736const internal::VariadicDynCastAllOfMatcher<Decl, BindingDecl> bindingDecl;737const internal::VariadicDynCastAllOfMatcher<Decl, LinkageSpecDecl>738linkageSpecDecl;739const internal::VariadicDynCastAllOfMatcher<Decl, NamedDecl> namedDecl;740const internal::VariadicDynCastAllOfMatcher<Decl, LabelDecl> labelDecl;741const internal::VariadicDynCastAllOfMatcher<Decl, NamespaceDecl> namespaceDecl;742const internal::VariadicDynCastAllOfMatcher<Decl, NamespaceAliasDecl>743namespaceAliasDecl;744const internal::VariadicDynCastAllOfMatcher<Decl, RecordDecl> recordDecl;745const internal::VariadicDynCastAllOfMatcher<Decl, CXXRecordDecl> cxxRecordDecl;746const internal::VariadicDynCastAllOfMatcher<Decl, ClassTemplateDecl>747classTemplateDecl;748const internal::VariadicDynCastAllOfMatcher<Decl,749ClassTemplateSpecializationDecl>750classTemplateSpecializationDecl;751const internal::VariadicDynCastAllOfMatcher<752Decl, ClassTemplatePartialSpecializationDecl>753classTemplatePartialSpecializationDecl;754const internal::VariadicDynCastAllOfMatcher<Decl, DeclaratorDecl>755declaratorDecl;756const internal::VariadicDynCastAllOfMatcher<Decl, ParmVarDecl> parmVarDecl;757const internal::VariadicDynCastAllOfMatcher<Decl, AccessSpecDecl>758accessSpecDecl;759const internal::VariadicAllOfMatcher<CXXBaseSpecifier> cxxBaseSpecifier;760const internal::VariadicAllOfMatcher<CXXCtorInitializer> cxxCtorInitializer;761const internal::VariadicAllOfMatcher<TemplateArgument> templateArgument;762const internal::VariadicAllOfMatcher<TemplateArgumentLoc> templateArgumentLoc;763const internal::VariadicAllOfMatcher<TemplateName> templateName;764const internal::VariadicDynCastAllOfMatcher<Decl, NonTypeTemplateParmDecl>765nonTypeTemplateParmDecl;766const internal::VariadicDynCastAllOfMatcher<Decl, TemplateTypeParmDecl>767templateTypeParmDecl;768const internal::VariadicDynCastAllOfMatcher<Decl, TemplateTemplateParmDecl>769templateTemplateParmDecl;770771const internal::VariadicAllOfMatcher<LambdaCapture> lambdaCapture;772const internal::VariadicAllOfMatcher<QualType> qualType;773const internal::VariadicAllOfMatcher<Type> type;774const internal::VariadicAllOfMatcher<TypeLoc> typeLoc;775776const internal::VariadicDynCastAllOfMatcher<TypeLoc, QualifiedTypeLoc>777qualifiedTypeLoc;778const internal::VariadicDynCastAllOfMatcher<TypeLoc, PointerTypeLoc>779pointerTypeLoc;780const internal::VariadicDynCastAllOfMatcher<TypeLoc, ReferenceTypeLoc>781referenceTypeLoc;782const internal::VariadicDynCastAllOfMatcher<TypeLoc,783TemplateSpecializationTypeLoc>784templateSpecializationTypeLoc;785const internal::VariadicDynCastAllOfMatcher<TypeLoc, ElaboratedTypeLoc>786elaboratedTypeLoc;787788const internal::VariadicDynCastAllOfMatcher<Stmt, UnaryExprOrTypeTraitExpr>789unaryExprOrTypeTraitExpr;790const internal::VariadicDynCastAllOfMatcher<Decl, ValueDecl> valueDecl;791const internal::VariadicDynCastAllOfMatcher<Decl, CXXConstructorDecl>792cxxConstructorDecl;793const internal::VariadicDynCastAllOfMatcher<Decl, CXXDestructorDecl>794cxxDestructorDecl;795const internal::VariadicDynCastAllOfMatcher<Decl, EnumDecl> enumDecl;796const internal::VariadicDynCastAllOfMatcher<Decl, EnumConstantDecl>797enumConstantDecl;798const internal::VariadicDynCastAllOfMatcher<Decl, TagDecl> tagDecl;799const internal::VariadicDynCastAllOfMatcher<Decl, CXXMethodDecl> cxxMethodDecl;800const internal::VariadicDynCastAllOfMatcher<Decl, CXXConversionDecl>801cxxConversionDecl;802const internal::VariadicDynCastAllOfMatcher<Decl, ConceptDecl> conceptDecl;803const internal::VariadicDynCastAllOfMatcher<Decl, VarDecl> varDecl;804const internal::VariadicDynCastAllOfMatcher<Decl, FieldDecl> fieldDecl;805const internal::VariadicDynCastAllOfMatcher<Decl, IndirectFieldDecl>806indirectFieldDecl;807const internal::VariadicDynCastAllOfMatcher<Decl, FunctionDecl> functionDecl;808const internal::VariadicDynCastAllOfMatcher<Decl, FunctionTemplateDecl>809functionTemplateDecl;810const internal::VariadicDynCastAllOfMatcher<Decl, FriendDecl> friendDecl;811const internal::VariadicAllOfMatcher<Stmt> stmt;812const internal::VariadicDynCastAllOfMatcher<Stmt, DeclStmt> declStmt;813const internal::VariadicDynCastAllOfMatcher<Stmt, MemberExpr> memberExpr;814const internal::VariadicDynCastAllOfMatcher<Stmt, UnresolvedMemberExpr>815unresolvedMemberExpr;816const internal::VariadicDynCastAllOfMatcher<Stmt, CXXDependentScopeMemberExpr>817cxxDependentScopeMemberExpr;818const internal::VariadicDynCastAllOfMatcher<Stmt, CallExpr> callExpr;819const internal::VariadicDynCastAllOfMatcher<Stmt, LambdaExpr> lambdaExpr;820const internal::VariadicDynCastAllOfMatcher<Stmt, CXXMemberCallExpr>821cxxMemberCallExpr;822const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCMessageExpr>823objcMessageExpr;824const internal::VariadicDynCastAllOfMatcher<Decl, ObjCInterfaceDecl>825objcInterfaceDecl;826const internal::VariadicDynCastAllOfMatcher<Decl, ObjCImplementationDecl>827objcImplementationDecl;828const internal::VariadicDynCastAllOfMatcher<Decl, ObjCProtocolDecl>829objcProtocolDecl;830const internal::VariadicDynCastAllOfMatcher<Decl, ObjCCategoryDecl>831objcCategoryDecl;832const internal::VariadicDynCastAllOfMatcher<Decl, ObjCCategoryImplDecl>833objcCategoryImplDecl;834const internal::VariadicDynCastAllOfMatcher<Decl, ObjCMethodDecl>835objcMethodDecl;836const internal::VariadicDynCastAllOfMatcher<Decl, BlockDecl>837blockDecl;838const internal::VariadicDynCastAllOfMatcher<Decl, ObjCIvarDecl> objcIvarDecl;839const internal::VariadicDynCastAllOfMatcher<Decl, ObjCPropertyDecl>840objcPropertyDecl;841const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCAtThrowStmt>842objcThrowStmt;843const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCAtTryStmt> objcTryStmt;844const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCAtCatchStmt>845objcCatchStmt;846const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCAtFinallyStmt>847objcFinallyStmt;848const internal::VariadicDynCastAllOfMatcher<Stmt, ExprWithCleanups>849exprWithCleanups;850const internal::VariadicDynCastAllOfMatcher<Stmt, InitListExpr> initListExpr;851const internal::VariadicDynCastAllOfMatcher<Stmt, CXXStdInitializerListExpr>852cxxStdInitializerListExpr;853const internal::VariadicDynCastAllOfMatcher<Stmt, ImplicitValueInitExpr>854implicitValueInitExpr;855const internal::VariadicDynCastAllOfMatcher<Stmt, ParenListExpr> parenListExpr;856const internal::VariadicDynCastAllOfMatcher<Stmt, SubstNonTypeTemplateParmExpr>857substNonTypeTemplateParmExpr;858const internal::VariadicDynCastAllOfMatcher<Decl, UsingDecl> usingDecl;859const internal::VariadicDynCastAllOfMatcher<Decl, UsingEnumDecl> usingEnumDecl;860const internal::VariadicDynCastAllOfMatcher<Decl, UsingDirectiveDecl>861usingDirectiveDecl;862const internal::VariadicDynCastAllOfMatcher<Stmt, UnresolvedLookupExpr>863unresolvedLookupExpr;864const internal::VariadicDynCastAllOfMatcher<Decl, UnresolvedUsingValueDecl>865unresolvedUsingValueDecl;866const internal::VariadicDynCastAllOfMatcher<Decl, UnresolvedUsingTypenameDecl>867unresolvedUsingTypenameDecl;868const internal::VariadicDynCastAllOfMatcher<Stmt, ConstantExpr> constantExpr;869const internal::VariadicDynCastAllOfMatcher<Stmt, ParenExpr> parenExpr;870const internal::VariadicDynCastAllOfMatcher<Stmt, CXXConstructExpr>871cxxConstructExpr;872const internal::VariadicDynCastAllOfMatcher<Stmt, CXXUnresolvedConstructExpr>873cxxUnresolvedConstructExpr;874const internal::VariadicDynCastAllOfMatcher<Stmt, CXXThisExpr> cxxThisExpr;875const internal::VariadicDynCastAllOfMatcher<Stmt, CXXBindTemporaryExpr>876cxxBindTemporaryExpr;877const internal::VariadicDynCastAllOfMatcher<Stmt, MaterializeTemporaryExpr>878materializeTemporaryExpr;879const internal::VariadicDynCastAllOfMatcher<Stmt, CXXNewExpr> cxxNewExpr;880const internal::VariadicDynCastAllOfMatcher<Stmt, CXXDeleteExpr> cxxDeleteExpr;881const internal::VariadicDynCastAllOfMatcher<Stmt, CXXNoexceptExpr>882cxxNoexceptExpr;883const internal::VariadicDynCastAllOfMatcher<Stmt, ArraySubscriptExpr>884arraySubscriptExpr;885const internal::VariadicDynCastAllOfMatcher<Stmt, ArrayInitIndexExpr>886arrayInitIndexExpr;887const internal::VariadicDynCastAllOfMatcher<Stmt, ArrayInitLoopExpr>888arrayInitLoopExpr;889const internal::VariadicDynCastAllOfMatcher<Stmt, CXXDefaultArgExpr>890cxxDefaultArgExpr;891const internal::VariadicDynCastAllOfMatcher<Stmt, CXXOperatorCallExpr>892cxxOperatorCallExpr;893const internal::VariadicDynCastAllOfMatcher<Stmt, CXXRewrittenBinaryOperator>894cxxRewrittenBinaryOperator;895const internal::VariadicDynCastAllOfMatcher<Stmt, CXXFoldExpr> cxxFoldExpr;896const internal::VariadicDynCastAllOfMatcher<Stmt, Expr> expr;897const internal::VariadicDynCastAllOfMatcher<Stmt, DeclRefExpr> declRefExpr;898const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCIvarRefExpr> objcIvarRefExpr;899const internal::VariadicDynCastAllOfMatcher<Stmt, BlockExpr> blockExpr;900const internal::VariadicDynCastAllOfMatcher<Stmt, IfStmt> ifStmt;901const internal::VariadicDynCastAllOfMatcher<Stmt, ForStmt> forStmt;902const internal::VariadicDynCastAllOfMatcher<Stmt, CXXForRangeStmt>903cxxForRangeStmt;904const internal::VariadicDynCastAllOfMatcher<Stmt, WhileStmt> whileStmt;905const internal::VariadicDynCastAllOfMatcher<Stmt, DoStmt> doStmt;906const internal::VariadicDynCastAllOfMatcher<Stmt, BreakStmt> breakStmt;907const internal::VariadicDynCastAllOfMatcher<Stmt, ContinueStmt> continueStmt;908const internal::VariadicDynCastAllOfMatcher<Stmt, CoreturnStmt> coreturnStmt;909const internal::VariadicDynCastAllOfMatcher<Stmt, ReturnStmt> returnStmt;910const internal::VariadicDynCastAllOfMatcher<Stmt, GotoStmt> gotoStmt;911const internal::VariadicDynCastAllOfMatcher<Stmt, LabelStmt> labelStmt;912const internal::VariadicDynCastAllOfMatcher<Stmt, AddrLabelExpr> addrLabelExpr;913const internal::VariadicDynCastAllOfMatcher<Stmt, SwitchStmt> switchStmt;914const internal::VariadicDynCastAllOfMatcher<Stmt, SwitchCase> switchCase;915const internal::VariadicDynCastAllOfMatcher<Stmt, CaseStmt> caseStmt;916const internal::VariadicDynCastAllOfMatcher<Stmt, DefaultStmt> defaultStmt;917const internal::VariadicDynCastAllOfMatcher<Stmt, CompoundStmt> compoundStmt;918const internal::VariadicDynCastAllOfMatcher<Stmt, CoroutineBodyStmt>919coroutineBodyStmt;920const internal::VariadicDynCastAllOfMatcher<Stmt, CXXCatchStmt> cxxCatchStmt;921const internal::VariadicDynCastAllOfMatcher<Stmt, CXXTryStmt> cxxTryStmt;922const internal::VariadicDynCastAllOfMatcher<Stmt, CXXThrowExpr> cxxThrowExpr;923const internal::VariadicDynCastAllOfMatcher<Stmt, NullStmt> nullStmt;924const internal::VariadicDynCastAllOfMatcher<Stmt, AsmStmt> asmStmt;925const internal::VariadicDynCastAllOfMatcher<Stmt, CXXBoolLiteralExpr>926cxxBoolLiteral;927const internal::VariadicDynCastAllOfMatcher<Stmt, StringLiteral> stringLiteral;928const internal::VariadicDynCastAllOfMatcher<Stmt, ObjCStringLiteral> objcStringLiteral;929const internal::VariadicDynCastAllOfMatcher<Stmt, CharacterLiteral>930characterLiteral;931const internal::VariadicDynCastAllOfMatcher<Stmt, IntegerLiteral>932integerLiteral;933const internal::VariadicDynCastAllOfMatcher<Stmt, FloatingLiteral> floatLiteral;934const internal::VariadicDynCastAllOfMatcher<Stmt, ImaginaryLiteral> imaginaryLiteral;935const internal::VariadicDynCastAllOfMatcher<Stmt, FixedPointLiteral>936fixedPointLiteral;937const internal::VariadicDynCastAllOfMatcher<Stmt, UserDefinedLiteral>938userDefinedLiteral;939const internal::VariadicDynCastAllOfMatcher<Stmt, CompoundLiteralExpr>940compoundLiteralExpr;941const internal::VariadicDynCastAllOfMatcher<Stmt, CXXNullPtrLiteralExpr>942cxxNullPtrLiteralExpr;943const internal::VariadicDynCastAllOfMatcher<Stmt, ChooseExpr> chooseExpr;944const internal::VariadicDynCastAllOfMatcher<Stmt, ConvertVectorExpr>945convertVectorExpr;946const internal::VariadicDynCastAllOfMatcher<Stmt, CoawaitExpr>947coawaitExpr;948const internal::VariadicDynCastAllOfMatcher<Stmt, DependentCoawaitExpr>949dependentCoawaitExpr;950const internal::VariadicDynCastAllOfMatcher<Stmt, CoyieldExpr>951coyieldExpr;952const internal::VariadicDynCastAllOfMatcher<Stmt, GNUNullExpr> gnuNullExpr;953const internal::VariadicDynCastAllOfMatcher<Stmt, GenericSelectionExpr>954genericSelectionExpr;955const internal::VariadicDynCastAllOfMatcher<Stmt, AtomicExpr> atomicExpr;956const internal::VariadicDynCastAllOfMatcher<Stmt, StmtExpr> stmtExpr;957const internal::VariadicDynCastAllOfMatcher<Stmt, BinaryOperator>958binaryOperator;959const internal::MapAnyOfMatcher<BinaryOperator, CXXOperatorCallExpr,960CXXRewrittenBinaryOperator>961binaryOperation;962const internal::MapAnyOfMatcher<CallExpr, CXXConstructExpr> invocation;963const internal::VariadicDynCastAllOfMatcher<Stmt, UnaryOperator> unaryOperator;964const internal::VariadicDynCastAllOfMatcher<Stmt, ConditionalOperator>965conditionalOperator;966const internal::VariadicDynCastAllOfMatcher<Stmt, BinaryConditionalOperator>967binaryConditionalOperator;968const internal::VariadicDynCastAllOfMatcher<Stmt, OpaqueValueExpr>969opaqueValueExpr;970const internal::VariadicDynCastAllOfMatcher<Decl, StaticAssertDecl>971staticAssertDecl;972const internal::VariadicDynCastAllOfMatcher<Stmt, CXXReinterpretCastExpr>973cxxReinterpretCastExpr;974const internal::VariadicDynCastAllOfMatcher<Stmt, CXXStaticCastExpr>975cxxStaticCastExpr;976const internal::VariadicDynCastAllOfMatcher<Stmt, CXXDynamicCastExpr>977cxxDynamicCastExpr;978const internal::VariadicDynCastAllOfMatcher<Stmt, CXXConstCastExpr>979cxxConstCastExpr;980const internal::VariadicDynCastAllOfMatcher<Stmt, CStyleCastExpr>981cStyleCastExpr;982const internal::VariadicDynCastAllOfMatcher<Stmt, ExplicitCastExpr>983explicitCastExpr;984const internal::VariadicDynCastAllOfMatcher<Stmt, ImplicitCastExpr>985implicitCastExpr;986const internal::VariadicDynCastAllOfMatcher<Stmt, CastExpr> castExpr;987const internal::VariadicDynCastAllOfMatcher<Stmt, CXXFunctionalCastExpr>988cxxFunctionalCastExpr;989const internal::VariadicDynCastAllOfMatcher<Stmt, CXXTemporaryObjectExpr>990cxxTemporaryObjectExpr;991const internal::VariadicDynCastAllOfMatcher<Stmt, PredefinedExpr>992predefinedExpr;993const internal::VariadicDynCastAllOfMatcher<Stmt, DesignatedInitExpr>994designatedInitExpr;995const internal::VariadicOperatorMatcherFunc<9962, std::numeric_limits<unsigned>::max()>997eachOf = {internal::DynTypedMatcher::VO_EachOf};998const internal::VariadicOperatorMatcherFunc<9992, std::numeric_limits<unsigned>::max()>1000anyOf = {internal::DynTypedMatcher::VO_AnyOf};1001const internal::VariadicOperatorMatcherFunc<10022, std::numeric_limits<unsigned>::max()>1003allOf = {internal::DynTypedMatcher::VO_AllOf};1004const internal::VariadicOperatorMatcherFunc<1, 1> optionally = {1005internal::DynTypedMatcher::VO_Optionally};1006const internal::VariadicFunction<internal::Matcher<NamedDecl>, StringRef,1007internal::hasAnyNameFunc>1008hasAnyName = {};10091010const internal::VariadicFunction<internal::HasOpNameMatcher, StringRef,1011internal::hasAnyOperatorNameFunc>1012hasAnyOperatorName = {};1013const internal::VariadicFunction<internal::HasOverloadOpNameMatcher, StringRef,1014internal::hasAnyOverloadedOperatorNameFunc>1015hasAnyOverloadedOperatorName = {};1016const internal::VariadicFunction<internal::Matcher<ObjCMessageExpr>, StringRef,1017internal::hasAnySelectorFunc>1018hasAnySelector = {};1019const internal::ArgumentAdaptingMatcherFunc<internal::HasMatcher> has = {};1020const internal::ArgumentAdaptingMatcherFunc<internal::HasDescendantMatcher>1021hasDescendant = {};1022const internal::ArgumentAdaptingMatcherFunc<internal::ForEachMatcher> forEach =1023{};1024const internal::ArgumentAdaptingMatcherFunc<internal::ForEachDescendantMatcher>1025forEachDescendant = {};1026const internal::ArgumentAdaptingMatcherFunc<1027internal::HasParentMatcher,1028internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc, Attr>,1029internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc, Attr>>1030hasParent = {};1031const internal::ArgumentAdaptingMatcherFunc<1032internal::HasAncestorMatcher,1033internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc, Attr>,1034internal::TypeList<Decl, NestedNameSpecifierLoc, Stmt, TypeLoc, Attr>>1035hasAncestor = {};1036const internal::VariadicOperatorMatcherFunc<1, 1> unless = {1037internal::DynTypedMatcher::VO_UnaryNot};1038const internal::VariadicAllOfMatcher<NestedNameSpecifier> nestedNameSpecifier;1039const internal::VariadicAllOfMatcher<NestedNameSpecifierLoc>1040nestedNameSpecifierLoc;1041const internal::VariadicAllOfMatcher<Attr> attr;1042const internal::VariadicDynCastAllOfMatcher<Stmt, CUDAKernelCallExpr>1043cudaKernelCallExpr;1044const AstTypeMatcher<BuiltinType> builtinType;1045const AstTypeMatcher<ArrayType> arrayType;1046const AstTypeMatcher<ComplexType> complexType;1047const AstTypeMatcher<ConstantArrayType> constantArrayType;1048const AstTypeMatcher<DeducedTemplateSpecializationType>1049deducedTemplateSpecializationType;1050const AstTypeMatcher<DependentSizedArrayType> dependentSizedArrayType;1051const AstTypeMatcher<DependentSizedExtVectorType> dependentSizedExtVectorType;1052const AstTypeMatcher<IncompleteArrayType> incompleteArrayType;1053const AstTypeMatcher<VariableArrayType> variableArrayType;1054const AstTypeMatcher<AtomicType> atomicType;1055const AstTypeMatcher<AutoType> autoType;1056const AstTypeMatcher<DecltypeType> decltypeType;1057const AstTypeMatcher<FunctionType> functionType;1058const AstTypeMatcher<FunctionProtoType> functionProtoType;1059const AstTypeMatcher<ParenType> parenType;1060const AstTypeMatcher<BlockPointerType> blockPointerType;1061const AstTypeMatcher<MacroQualifiedType> macroQualifiedType;1062const AstTypeMatcher<MemberPointerType> memberPointerType;1063const AstTypeMatcher<PointerType> pointerType;1064const AstTypeMatcher<ObjCObjectPointerType> objcObjectPointerType;1065const AstTypeMatcher<ReferenceType> referenceType;1066const AstTypeMatcher<LValueReferenceType> lValueReferenceType;1067const AstTypeMatcher<RValueReferenceType> rValueReferenceType;1068const AstTypeMatcher<TypedefType> typedefType;1069const AstTypeMatcher<EnumType> enumType;1070const AstTypeMatcher<TemplateSpecializationType> templateSpecializationType;1071const AstTypeMatcher<UnaryTransformType> unaryTransformType;1072const AstTypeMatcher<RecordType> recordType;1073const AstTypeMatcher<TagType> tagType;1074const AstTypeMatcher<ElaboratedType> elaboratedType;1075const AstTypeMatcher<UsingType> usingType;1076const AstTypeMatcher<SubstTemplateTypeParmType> substTemplateTypeParmType;1077const AstTypeMatcher<TemplateTypeParmType> templateTypeParmType;1078const AstTypeMatcher<InjectedClassNameType> injectedClassNameType;1079const AstTypeMatcher<DecayedType> decayedType;1080AST_TYPELOC_TRAVERSE_MATCHER_DEF(hasElementType,1081AST_POLYMORPHIC_SUPPORTED_TYPES(ArrayType,1082ComplexType));1083AST_TYPELOC_TRAVERSE_MATCHER_DEF(hasValueType,1084AST_POLYMORPHIC_SUPPORTED_TYPES(AtomicType));1085AST_TYPELOC_TRAVERSE_MATCHER_DEF(1086pointee,1087AST_POLYMORPHIC_SUPPORTED_TYPES(BlockPointerType, MemberPointerType,1088PointerType, ReferenceType));10891090const internal::VariadicDynCastAllOfMatcher<Stmt, OMPExecutableDirective>1091ompExecutableDirective;1092const internal::VariadicDynCastAllOfMatcher<OMPClause, OMPDefaultClause>1093ompDefaultClause;1094const internal::VariadicDynCastAllOfMatcher<Decl, CXXDeductionGuideDecl>1095cxxDeductionGuideDecl;10961097} // end namespace ast_matchers1098} // end namespace clang109911001101