ASTMatchersMacros.h revision 7bb7fb634d20d9f3f5c6b5058a514a4b41b6f33d
14da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//===--- ASTMatchersMacros.h - Structural query framework -------*- C++ -*-===//
24da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
34da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//                     The LLVM Compiler Infrastructure
44da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
54da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek// This file is distributed under the University of Illinois Open Source
64da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek// License. See LICENSE.TXT for details.
74da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
84da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//===----------------------------------------------------------------------===//
94da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
104da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  Defines macros that enable us to define new matchers in a single place.
114da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  Since a matcher is a function which returns a Matcher<T> object, where
124da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  T is the type of the actual implementation of the matcher, the macros allow
134da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  us to write matchers like functions and take care of the definition of the
144da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  class boilerplate.
154da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
164da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  Note that when you define a matcher with an AST_MATCHER* macro, only the
174da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  function which creates the matcher goes into the current namespace - the
184da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  class that implements the actual matcher, which gets returned by the
194da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  generator function, is put into the 'internal' namespace. This allows us
204da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  to only have the functions (which is all the user cares about) in the
214da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  'ast_matchers' namespace and hide the boilerplate.
224da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
234da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  To define a matcher in user code, always put it into the clang::ast_matchers
244da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  namespace and refer to the internal types via the 'internal::':
254da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
264da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  namespace clang {
274da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  namespace ast_matchers {
284da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  AST_MATCHER_P(MemberExpr, Member,
294da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//                internal::Matcher<ValueDecl>, InnerMatcher) {
304da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//    return InnerMatcher.matches(*Node.getMemberDecl(), Finder, Builder);
314da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  }
324da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  } // end namespace ast_matchers
334da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//  } // end namespace clang
344da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//
354da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek//===----------------------------------------------------------------------===//
364da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
374da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#ifndef LLVM_CLANG_AST_MATCHERS_AST_MATCHERS_MACROS_H
384da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#define LLVM_CLANG_AST_MATCHERS_AST_MATCHERS_MACROS_H
394da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
404da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_MATCHER(Type, DefineMatcher) { ... }
414da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a zero parameter function named DefineMatcher() that returns a
424da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<Type> object.
434da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
444da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code between the curly braces has access to the following variables:
454da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
464da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Node:                  the AST node being matched; its type is Type.
474da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Finder:                an ASTMatchFinder*.
484da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Builder:               a BoundNodesTreeBuilder*.
494da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
504da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code should return true if 'Node' matches.
514da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#define AST_MATCHER(Type, DefineMatcher)                                       \
524da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  namespace internal {                                                         \
537bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class matcher_##DefineMatcher##Matcher : public MatcherInterface<Type> {     \
547bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
557bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    explicit matcher_##DefineMatcher##Matcher() {                              \
567bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
577bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    virtual bool matches(const Type &Node, ASTMatchFinder *Finder,             \
587bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                         BoundNodesTreeBuilder *Builder) const;                \
594da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  };                                                                           \
604da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
614da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline internal::Matcher<Type> DefineMatcher() {                             \
624da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    return internal::makeMatcher(                                              \
637bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        new internal::matcher_##DefineMatcher##Matcher());                     \
644da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
654da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline bool internal::matcher_##DefineMatcher##Matcher::matches(             \
664da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      const Type &Node, ASTMatchFinder *Finder,                                \
674da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      BoundNodesTreeBuilder *Builder) const
684da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
694da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_MATCHER_P(Type, DefineMatcher, ParamType, Param) { ... }
704da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a single-parameter function named DefineMatcher() that returns a
714da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<Type> object.
724da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
734da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code between the curly braces has access to the following variables:
744da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
754da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Node:                  the AST node being matched; its type is Type.
764da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Param:                 the parameter passed to the function; its type
774da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///                          is ParamType.
784da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Finder:                an ASTMatchFinder*.
794da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Builder:               a BoundNodesTreeBuilder*.
804da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
814da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code should return true if 'Node' matches.
824da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#define AST_MATCHER_P(Type, DefineMatcher, ParamType, Param)                   \
834da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  namespace internal {                                                         \
847bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class matcher_##DefineMatcher##Matcher : public MatcherInterface<Type> {     \
857bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
867bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    explicit matcher_##DefineMatcher##Matcher(const ParamType &A##Param)       \
877bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        : Param(A##Param) {                                                    \
887bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
897bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    virtual bool matches(const Type &Node, ASTMatchFinder *Finder,             \
907bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                         BoundNodesTreeBuilder *Builder) const;                \
917bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  private:                                                                     \
924da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    const ParamType Param;                                                     \
934da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  };                                                                           \
944da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
954da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline internal::Matcher<Type> DefineMatcher(const ParamType &Param) {       \
964da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    return internal::makeMatcher(                                              \
977bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        new internal::matcher_##DefineMatcher##Matcher(Param));                \
984da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
994da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline bool internal::matcher_##DefineMatcher##Matcher::matches(             \
1004da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      const Type &Node, ASTMatchFinder *Finder,                                \
1014da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      BoundNodesTreeBuilder *Builder) const
1024da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
1034da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_MATCHER_P2(
1044da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///     Type, DefineMatcher, ParamType1, Param1, ParamType2, Param2) { ... }
1054da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a two-parameter function named DefineMatcher() that returns a
1064da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<Type> object.
1074da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
1084da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code between the curly braces has access to the following variables:
1094da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
1104da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Node:                  the AST node being matched; its type is Type.
1114da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Param1, Param2:        the parameters passed to the function; their types
1124da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///                          are ParamType1 and ParamType2.
1134da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Finder:                an ASTMatchFinder*.
1144da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///   Builder:               a BoundNodesTreeBuilder*.
1154da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
1164da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code should return true if 'Node' matches.
1177bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek#define AST_MATCHER_P2(Type, DefineMatcher, ParamType1, Param1, ParamType2,    \
1187bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                       Param2)                                                 \
1194da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  namespace internal {                                                         \
1207bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class matcher_##DefineMatcher##Matcher : public MatcherInterface<Type> {     \
1217bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
1227bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    matcher_##DefineMatcher##Matcher(const ParamType1 &A##Param1,              \
1237bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                     const ParamType2 &A##Param2)              \
1247bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        : Param1(A##Param1), Param2(A##Param2) {                               \
1257bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
1267bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    virtual bool matches(const Type &Node, ASTMatchFinder *Finder,             \
1277bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                         BoundNodesTreeBuilder *Builder) const;                \
1287bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  private:                                                                     \
1294da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    const ParamType1 Param1;                                                   \
1304da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    const ParamType2 Param2;                                                   \
1314da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  };                                                                           \
1324da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
1337bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  inline internal::Matcher<Type> DefineMatcher(const ParamType1 &Param1,       \
1347bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                               const ParamType2 &Param2) {     \
1354da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    return internal::makeMatcher(                                              \
1367bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        new internal::matcher_##DefineMatcher##Matcher(Param1, Param2));       \
1374da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
1384da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline bool internal::matcher_##DefineMatcher##Matcher::matches(             \
1394da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      const Type &Node, ASTMatchFinder *Finder,                                \
1404da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      BoundNodesTreeBuilder *Builder) const
1414da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
1424da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_POLYMORPHIC_MATCHER_P(DefineMatcher, ParamType, Param) { ... }
1434da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a single-parameter function named DefineMatcher() that is
1444da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// polymorphic in the return type.
1454da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
1464da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The variables are the same as for
1474da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// AST_MATCHER_P, with the addition of NodeType, which specifies the node type
1484da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// of the matcher Matcher<NodeType> returned by the function matcher().
1494da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
1504da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// FIXME: Pull out common code with above macro?
1514da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#define AST_POLYMORPHIC_MATCHER_P(DefineMatcher, ParamType, Param)             \
1524da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  namespace internal {                                                         \
1534da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  template <typename NodeType, typename ParamT>                                \
1547bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class matcher_##DefineMatcher##Matcher : public MatcherInterface<NodeType> { \
1557bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
1567bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    explicit matcher_##DefineMatcher##Matcher(const ParamType &A##Param)       \
1577bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        : Param(A##Param) {                                                    \
1587bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
1597bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    virtual bool matches(const NodeType &Node, ASTMatchFinder *Finder,         \
1607bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                         BoundNodesTreeBuilder *Builder) const;                \
1617bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  private:                                                                     \
1624da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    const ParamType Param;                                                     \
1634da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  };                                                                           \
1644da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
1654da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline internal::PolymorphicMatcherWithParam1<                               \
1664da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek      internal::matcher_##DefineMatcher##Matcher,                              \
1677bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      ParamType> DefineMatcher(const ParamType &Param) {                       \
1684da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    return internal::PolymorphicMatcherWithParam1<                             \
1697bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        internal::matcher_##DefineMatcher##Matcher, ParamType>(Param);         \
1704da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
1714da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  template <typename NodeType, typename ParamT>                                \
1724da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  bool internal::matcher_##DefineMatcher##Matcher<NodeType, ParamT>::matches(  \
1737bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          const NodeType &Node, ASTMatchFinder *Finder,                        \
1747bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          BoundNodesTreeBuilder *Builder) const
1754da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
1764da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_POLYMORPHIC_MATCHER_P2(
1774da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///     DefineMatcher, ParamType1, Param1, ParamType2, Param2) { ... }
1784da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a two-parameter function named matcher() that is polymorphic in
1794da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// the return type.
1804da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek///
1814da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The variables are the same as for AST_MATCHER_P2, with the
1824da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// addition of NodeType, which specifies the node type of the matcher
1834da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<NodeType> returned by the function DefineMatcher().
1847bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek#define AST_POLYMORPHIC_MATCHER_P2(DefineMatcher, ParamType1, Param1,          \
1857bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                   ParamType2, Param2)                         \
1864da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  namespace internal {                                                         \
1874da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  template <typename NodeType, typename ParamT1, typename ParamT2>             \
1887bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class matcher_##DefineMatcher##Matcher : public MatcherInterface<NodeType> { \
1897bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
1907bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    matcher_##DefineMatcher##Matcher(const ParamType1 &A##Param1,              \
1917bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                     const ParamType2 &A##Param2)              \
1927bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        : Param1(A##Param1), Param2(A##Param2) {                               \
1937bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
1947bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    virtual bool matches(const NodeType &Node, ASTMatchFinder *Finder,         \
1957bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                         BoundNodesTreeBuilder *Builder) const;                \
1967bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  private:                                                                     \
1974da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    const ParamType1 Param1;                                                   \
1984da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    const ParamType2 Param2;                                                   \
1994da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  };                                                                           \
2004da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
2014da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  inline internal::PolymorphicMatcherWithParam2<                               \
2027bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      internal::matcher_##DefineMatcher##Matcher, ParamType1,                  \
2037bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      ParamType2> DefineMatcher(const ParamType1 &Param1,                      \
2047bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                const ParamType2 &Param2) {                    \
2054da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek    return internal::PolymorphicMatcherWithParam2<                             \
2067bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        internal::matcher_##DefineMatcher##Matcher, ParamType1,                \
2077bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        ParamType2>(Param1, Param2);                                           \
2084da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  }                                                                            \
2094da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  template <typename NodeType, typename ParamT1, typename ParamT2>             \
2104da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek  bool internal::matcher_##DefineMatcher##Matcher<                             \
2117bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          NodeType, ParamT1,                                                   \
2127bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          ParamT2>::matches(const NodeType &Node, ASTMatchFinder *Finder,      \
2137bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                            BoundNodesTreeBuilder *Builder) const
2144da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek
215ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \brief Creates a variadic matcher for both a specific \c Type as well as
216ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// the corresponding \c TypeLoc.
217ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper#define AST_TYPE_MATCHER(NodeType, MatcherName)                                \
218ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper  const internal::VariadicDynCastAllOfMatcher<Type, NodeType> MatcherName;     \
219ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper  const internal::VariadicDynCastAllOfMatcher<TypeLoc,                         \
220ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper                                              NodeType##Loc> MatcherName##Loc
221ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper
222ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \brief AST_TYPE_TRAVERSE_MATCHER(MatcherName, FunctionName) defines
223ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// the matcher \c MatcherName that can be used to traverse from one \c Type
224ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// to another.
225a7564433191601cb8851196b8dde39392c9c05eeDaniel Jasper///
226ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// For a specific \c SpecificType, the traversal is done using
227ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \c SpecificType::FunctionName. The existance of such a function determines
228ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// whether a corresponding matcher can be used on \c SpecificType.
229ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper#define AST_TYPE_TRAVERSE_MATCHER(MatcherName, FunctionName)                   \
2307bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class Polymorphic##MatcherName##TypeMatcher {                                \
2317bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
2327bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    Polymorphic##MatcherName##TypeMatcher(                                     \
2337bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        const internal::Matcher<QualType> &InnerMatcher)                       \
2347bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        : InnerMatcher(InnerMatcher) {                                         \
2357bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
2367bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    template <typename T> operator internal:: Matcher< T>() {                  \
2377bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      return internal::Matcher<T>(new internal::TypeTraverseMatcher<T>(        \
2387bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                          InnerMatcher, &T::FunctionName));    \
2397bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
2407bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  private:                                                                     \
2417bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    const internal::Matcher<QualType> InnerMatcher;                            \
242a7564433191601cb8851196b8dde39392c9c05eeDaniel Jasper  }                                                                            \
2437bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  ;                                                                            \
2447bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class Variadic##MatcherName##TypeTraverseMatcher                             \
2457bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      : public llvm::VariadicFunction<                                         \
2467bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          Polymorphic##MatcherName##TypeMatcher, internal::Matcher<QualType>,  \
2477bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          internal::makeTypeAllOfComposite<                                    \
2487bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek              Polymorphic##MatcherName##TypeMatcher, QualType> > {             \
2497bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
2507bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    Variadic##MatcherName##TypeTraverseMatcher() {                             \
2517bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
2527bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  }                                                                            \
2537bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  ;                                                                            \
2547bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  const Variadic##MatcherName##TypeTraverseMatcher MatcherName
255ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper
256ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \brief AST_TYPELOC_TRAVERSE_MATCHER(MatcherName, FunctionName) works
257ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// identical to \c AST_TYPE_TRAVERSE_MATCHER but operates on \c TypeLocs.
258ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper#define AST_TYPELOC_TRAVERSE_MATCHER(MatcherName, FunctionName)                \
2597bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class Polymorphic##MatcherName##TypeLocMatcher {                             \
2607bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
2617bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    Polymorphic##MatcherName##TypeLocMatcher(                                  \
2627bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        const internal::Matcher<TypeLoc> &InnerMatcher)                        \
2637bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek        : InnerMatcher(InnerMatcher) {                                         \
2647bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
2657bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    template <typename T> operator internal:: Matcher< T>() {                  \
2667bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      return internal::Matcher<T>(                                             \
2677bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          new internal::TypeLocTraverseMatcher<T>(InnerMatcher,                \
2687bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek                                                  &T::FunctionName##Loc));     \
2697bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
2707bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  private:                                                                     \
2717bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    const internal::Matcher<TypeLoc> InnerMatcher;                             \
2727bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  }                                                                            \
2737bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  ;                                                                            \
2747bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  class Variadic##MatcherName##TypeLocTraverseMatcher                          \
2757bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek      : public llvm::VariadicFunction<                                         \
2767bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          Polymorphic##MatcherName##TypeLocMatcher, internal::Matcher<TypeLoc>,\
2777bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek          internal::makeTypeAllOfComposite<                                    \
2787bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek              Polymorphic##MatcherName##TypeLocMatcher, TypeLoc> > {           \
2797bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  public:                                                                      \
2807bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    Variadic##MatcherName##TypeLocTraverseMatcher() {                          \
2817bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek    }                                                                          \
282ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper  }                                                                            \
2837bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  ;                                                                            \
2847bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  const Variadic##MatcherName##TypeLocTraverseMatcher MatcherName##Loc;        \
2857bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek  AST_TYPE_TRAVERSE_MATCHER(MatcherName, FunctionName##Type)
286a7564433191601cb8851196b8dde39392c9c05eeDaniel Jasper
2874da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#endif // LLVM_CLANG_AST_MATCHERS_AST_MATCHERS_MACROS_H
288