ASTMatchersMacros.h revision 3f84bb341bfb1312842b09db71d76bc3898ba247
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) \ 52415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek AST_MATCHER_OVERLOAD(Type, DefineMatcher, 0) 53415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 54415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek#define AST_MATCHER_OVERLOAD(Type, DefineMatcher, OverloadId) \ 554da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek namespace internal { \ 56415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek class matcher_##DefineMatcher##OverloadId##Matcher \ 57415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek : public MatcherInterface<Type> { \ 587bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek public: \ 59415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek explicit matcher_##DefineMatcher##OverloadId##Matcher() {} \ 607bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek virtual bool matches(const Type &Node, ASTMatchFinder *Finder, \ 617bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek BoundNodesTreeBuilder *Builder) const; \ 624da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek }; \ 634da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 644da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek inline internal::Matcher<Type> DefineMatcher() { \ 654da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek return internal::makeMatcher( \ 66415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek new internal::matcher_##DefineMatcher##OverloadId##Matcher()); \ 674da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 68415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek inline bool internal::matcher_##DefineMatcher##OverloadId##Matcher::matches( \ 694da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const Type &Node, ASTMatchFinder *Finder, \ 704da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek BoundNodesTreeBuilder *Builder) const 714da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek 724da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_MATCHER_P(Type, DefineMatcher, ParamType, Param) { ... } 734da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a single-parameter function named DefineMatcher() that returns a 744da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<Type> object. 754da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 764da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code between the curly braces has access to the following variables: 774da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 784da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Node: the AST node being matched; its type is Type. 794da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Param: the parameter passed to the function; its type 804da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// is ParamType. 814da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Finder: an ASTMatchFinder*. 824da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Builder: a BoundNodesTreeBuilder*. 834da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 844da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code should return true if 'Node' matches. 854da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#define AST_MATCHER_P(Type, DefineMatcher, ParamType, Param) \ 86415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek AST_MATCHER_P_OVERLOAD(Type, DefineMatcher, ParamType, Param, 0) 87415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 88415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek#define AST_MATCHER_P_OVERLOAD(Type, DefineMatcher, ParamType, Param, \ 89415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek OverloadId) \ 904da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek namespace internal { \ 91415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek class matcher_##DefineMatcher##OverloadId##Matcher \ 92415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek : public MatcherInterface<Type> { \ 937bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek public: \ 94415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek explicit matcher_##DefineMatcher##OverloadId##Matcher( \ 95415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek const ParamType &A##Param) \ 967bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek : Param(A##Param) { \ 977bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek } \ 987bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek virtual bool matches(const Type &Node, ASTMatchFinder *Finder, \ 997bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek BoundNodesTreeBuilder *Builder) const; \ 1007bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek private: \ 1014da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const ParamType Param; \ 1024da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek }; \ 1034da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 1044da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek inline internal::Matcher<Type> DefineMatcher(const ParamType &Param) { \ 1054da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek return internal::makeMatcher( \ 106415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek new internal::matcher_##DefineMatcher##OverloadId##Matcher(Param)); \ 1074da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 108415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek inline bool internal::matcher_##DefineMatcher##OverloadId##Matcher::matches( \ 1094da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const Type &Node, ASTMatchFinder *Finder, \ 1104da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek BoundNodesTreeBuilder *Builder) const 1114da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek 1124da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_MATCHER_P2( 1134da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Type, DefineMatcher, ParamType1, Param1, ParamType2, Param2) { ... } 1144da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a two-parameter function named DefineMatcher() that returns a 1154da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<Type> object. 1164da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 1174da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code between the curly braces has access to the following variables: 1184da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 1194da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Node: the AST node being matched; its type is Type. 1204da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Param1, Param2: the parameters passed to the function; their types 1214da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// are ParamType1 and ParamType2. 1224da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Finder: an ASTMatchFinder*. 1234da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Builder: a BoundNodesTreeBuilder*. 1244da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 1254da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The code should return true if 'Node' matches. 1267bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek#define AST_MATCHER_P2(Type, DefineMatcher, ParamType1, Param1, ParamType2, \ 1277bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek Param2) \ 128415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek AST_MATCHER_P2_OVERLOAD(Type, DefineMatcher, ParamType1, Param1, ParamType2, \ 129415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek Param2, 0) 130415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 131415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek#define AST_MATCHER_P2_OVERLOAD(Type, DefineMatcher, ParamType1, Param1, \ 132415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek ParamType2, Param2, OverloadId) \ 1334da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek namespace internal { \ 134415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek class matcher_##DefineMatcher##OverloadId##Matcher \ 135415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek : public MatcherInterface<Type> { \ 1367bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek public: \ 137415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek matcher_##DefineMatcher##OverloadId##Matcher(const ParamType1 &A##Param1, \ 138415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek const ParamType2 &A##Param2) \ 1397bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek : Param1(A##Param1), Param2(A##Param2) { \ 1407bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek } \ 1417bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek virtual bool matches(const Type &Node, ASTMatchFinder *Finder, \ 1427bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek BoundNodesTreeBuilder *Builder) const; \ 1437bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek private: \ 1444da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const ParamType1 Param1; \ 1454da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const ParamType2 Param2; \ 1464da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek }; \ 1474da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 148415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek inline internal::Matcher<Type> \ 149415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek DefineMatcher(const ParamType1 &Param1, const ParamType2 &Param2) { \ 1504da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek return internal::makeMatcher( \ 151415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek new internal::matcher_##DefineMatcher##OverloadId##Matcher(Param1, \ 152415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek Param2)); \ 1534da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 154415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek inline bool internal::matcher_##DefineMatcher##OverloadId##Matcher::matches( \ 1554da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const Type &Node, ASTMatchFinder *Finder, \ 1564da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek BoundNodesTreeBuilder *Builder) const 1574da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek 158ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// \brief Construct a type-list to be passed to the AST_POLYMORPHIC_MATCHER* 159ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// macros. 160ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// 161ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// You can't pass something like \c TypeList<Foo, Bar> to a macro, because it 162ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// will look at that as two arguments. However, you can pass 163ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// \c void(TypeList<Foo, Bar>), which works thanks to the parenthesis. 164ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// The \c PolymorphicMatcherWithParam* classes will unpack the function type to 165ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen/// extract the TypeList object. 1663f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen#define AST_POLYMORPHIC_SUPPORTED_TYPES_1(t1) void(internal::TypeList<t1>) 167ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_SUPPORTED_TYPES_2(t1, t2) \ 168ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen void(internal::TypeList<t1, t2>) 169ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_SUPPORTED_TYPES_3(t1, t2, t3) \ 170ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen void(internal::TypeList<t1, t2, t3>) 171ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_SUPPORTED_TYPES_4(t1, t2, t3, t4) \ 172ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen void(internal::TypeList<t1, t2, t3, t4>) 173ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_SUPPORTED_TYPES_5(t1, t2, t3, t4, t5) \ 174ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen void(internal::TypeList<t1, t2, t3, t4, t5>) 175ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen 176415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek/// \brief AST_POLYMORPHIC_MATCHER(DefineMatcher) { ... } 177415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek/// defines a single-parameter function named DefineMatcher() that is 178415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek/// polymorphic in the return type. 179415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek/// 180415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek/// The variables are the same as for AST_MATCHER, but NodeType will be deduced 181415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek/// from the calling context. 182ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_MATCHER(DefineMatcher, ReturnTypesF) \ 183ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen AST_POLYMORPHIC_MATCHER_OVERLOAD(DefineMatcher, ReturnTypesF, 0) 184415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 185ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_MATCHER_OVERLOAD(DefineMatcher, ReturnTypesF, \ 186ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen OverloadId) \ 187415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek namespace internal { \ 188415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek template <typename NodeType> \ 189415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek class matcher_##DefineMatcher##OverloadId##Matcher \ 190415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek : public MatcherInterface<NodeType> { \ 191415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek public: \ 192415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek virtual bool matches(const NodeType &Node, ASTMatchFinder *Finder, \ 193415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek BoundNodesTreeBuilder *Builder) const; \ 194415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek }; \ 195415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek } \ 196415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek inline internal::PolymorphicMatcherWithParam0< \ 197ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen internal::matcher_##DefineMatcher##OverloadId##Matcher, ReturnTypesF> \ 198ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen DefineMatcher() { \ 199415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek return internal::PolymorphicMatcherWithParam0< \ 200ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen internal::matcher_##DefineMatcher##OverloadId##Matcher, \ 201ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ReturnTypesF>(); \ 202415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek } \ 203415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek template <typename NodeType> \ 204415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek bool internal::matcher_##DefineMatcher##OverloadId##Matcher< \ 205415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek NodeType>::matches(const NodeType &Node, ASTMatchFinder *Finder, \ 206415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek BoundNodesTreeBuilder *Builder) const 207415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 2084da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_POLYMORPHIC_MATCHER_P(DefineMatcher, ParamType, Param) { ... } 2094da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a single-parameter function named DefineMatcher() that is 2104da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// polymorphic in the return type. 2114da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 2124da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The variables are the same as for 2134da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// AST_MATCHER_P, with the addition of NodeType, which specifies the node type 2144da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// of the matcher Matcher<NodeType> returned by the function matcher(). 2154da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 2164da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// FIXME: Pull out common code with above macro? 217ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_MATCHER_P(DefineMatcher, ReturnTypesF, ParamType, \ 218ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen Param) \ 219ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen AST_POLYMORPHIC_MATCHER_P_OVERLOAD(DefineMatcher, ReturnTypesF, ParamType, \ 220ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen Param, 0) 221415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 222ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_MATCHER_P_OVERLOAD(DefineMatcher, ReturnTypesF, \ 223ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ParamType, Param, OverloadId) \ 2244da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek namespace internal { \ 2254da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek template <typename NodeType, typename ParamT> \ 226415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek class matcher_##DefineMatcher##OverloadId##Matcher \ 227415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek : public MatcherInterface<NodeType> { \ 2287bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek public: \ 229415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek explicit matcher_##DefineMatcher##OverloadId##Matcher( \ 230415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek const ParamType &A##Param) \ 2317bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek : Param(A##Param) { \ 2327bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek } \ 2337bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek virtual bool matches(const NodeType &Node, ASTMatchFinder *Finder, \ 2347bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek BoundNodesTreeBuilder *Builder) const; \ 2357bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek private: \ 2364da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const ParamType Param; \ 2374da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek }; \ 2384da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 2394da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek inline internal::PolymorphicMatcherWithParam1< \ 240ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen internal::matcher_##DefineMatcher##OverloadId##Matcher, ParamType, \ 241ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ReturnTypesF> DefineMatcher(const ParamType & Param) { \ 2424da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek return internal::PolymorphicMatcherWithParam1< \ 243ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen internal::matcher_##DefineMatcher##OverloadId##Matcher, ParamType, \ 244ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ReturnTypesF>(Param); \ 2454da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 2464da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek template <typename NodeType, typename ParamT> \ 247415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek bool internal::matcher_##DefineMatcher##OverloadId##Matcher< \ 248415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek NodeType, ParamT>::matches(const NodeType &Node, ASTMatchFinder *Finder, \ 249415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek BoundNodesTreeBuilder *Builder) const 2504da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek 2514da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// \brief AST_POLYMORPHIC_MATCHER_P2( 2524da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// DefineMatcher, ParamType1, Param1, ParamType2, Param2) { ... } 2534da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// defines a two-parameter function named matcher() that is polymorphic in 2544da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// the return type. 2554da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// 2564da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// The variables are the same as for AST_MATCHER_P2, with the 2574da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// addition of NodeType, which specifies the node type of the matcher 2584da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek/// Matcher<NodeType> returned by the function DefineMatcher(). 259ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_MATCHER_P2(DefineMatcher, ReturnTypesF, ParamType1, \ 260ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen Param1, ParamType2, Param2) \ 261ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen AST_POLYMORPHIC_MATCHER_P2_OVERLOAD(DefineMatcher, ReturnTypesF, ParamType1, \ 262ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen Param1, ParamType2, Param2, 0) 263415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek 264ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen#define AST_POLYMORPHIC_MATCHER_P2_OVERLOAD(DefineMatcher, ReturnTypesF, \ 265ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ParamType1, Param1, ParamType2, \ 266ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen Param2, OverloadId) \ 2674da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek namespace internal { \ 2684da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek template <typename NodeType, typename ParamT1, typename ParamT2> \ 269415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek class matcher_##DefineMatcher##OverloadId##Matcher \ 270415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek : public MatcherInterface<NodeType> { \ 2717bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek public: \ 272415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek matcher_##DefineMatcher##OverloadId##Matcher(const ParamType1 &A##Param1, \ 273415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek const ParamType2 &A##Param2) \ 2747bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek : Param1(A##Param1), Param2(A##Param2) { \ 2757bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek } \ 2767bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek virtual bool matches(const NodeType &Node, ASTMatchFinder *Finder, \ 2777bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek BoundNodesTreeBuilder *Builder) const; \ 2787bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek private: \ 2794da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const ParamType1 Param1; \ 2804da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek const ParamType2 Param2; \ 2814da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek }; \ 2824da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 2834da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek inline internal::PolymorphicMatcherWithParam2< \ 284415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek internal::matcher_##DefineMatcher##OverloadId##Matcher, ParamType1, \ 285ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ParamType2, ReturnTypesF> DefineMatcher(const ParamType1 & Param1, \ 286ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen const ParamType2 & Param2) { \ 2874da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek return internal::PolymorphicMatcherWithParam2< \ 288415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek internal::matcher_##DefineMatcher##OverloadId##Matcher, ParamType1, \ 289ef7eb024397a6a9d1455b31bc7b10288a817ac3bSamuel Benzaquen ParamType2, ReturnTypesF>(Param1, Param2); \ 2904da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek } \ 2914da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek template <typename NodeType, typename ParamT1, typename ParamT2> \ 292415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek bool internal::matcher_##DefineMatcher##OverloadId##Matcher< \ 293415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek NodeType, ParamT1, ParamT2>::matches( \ 294415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek const NodeType &Node, ASTMatchFinder *Finder, \ 295415514d5fbc2761b7f2938aa9112b079249820d6Manuel Klimek BoundNodesTreeBuilder *Builder) const 2964da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek 297ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \brief Creates a variadic matcher for both a specific \c Type as well as 298ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// the corresponding \c TypeLoc. 299ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper#define AST_TYPE_MATCHER(NodeType, MatcherName) \ 3005be093c0ef46c7749c942d0d9056af6dc3d591a4David Blaikie const internal::VariadicDynCastAllOfMatcher<Type, NodeType> MatcherName 3015be093c0ef46c7749c942d0d9056af6dc3d591a4David Blaikie// FIXME: add a matcher for TypeLoc derived classes using its custom casting 3025be093c0ef46c7749c942d0d9056af6dc3d591a4David Blaikie// API (no longer dyn_cast) if/when we need such matching 303ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper 304ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \brief AST_TYPE_TRAVERSE_MATCHER(MatcherName, FunctionName) defines 305ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// the matcher \c MatcherName that can be used to traverse from one \c Type 306ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// to another. 307a7564433191601cb8851196b8dde39392c9c05eeDaniel Jasper/// 308ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// For a specific \c SpecificType, the traversal is done using 309ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \c SpecificType::FunctionName. The existance of such a function determines 310ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// whether a corresponding matcher can be used on \c SpecificType. 3113f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen#define AST_TYPE_TRAVERSE_MATCHER(MatcherName, FunctionName, ReturnTypesF) \ 3123f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen namespace internal { \ 3133f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen template <typename T> struct TypeMatcher##MatcherName##Getter { \ 3143f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen static QualType (T::*value())() const { return &T::FunctionName; } \ 3153f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen }; \ 3167bb7fb634d20d9f3f5c6b5058a514a4b41b6f33dManuel Klimek } \ 3173f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen const internal::TypeTraversePolymorphicMatcher< \ 3183f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen QualType, internal::TypeMatcher##MatcherName##Getter, \ 3193f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen internal::TypeTraverseMatcher, ReturnTypesF>::Func MatcherName 320ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper 321ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// \brief AST_TYPELOC_TRAVERSE_MATCHER(MatcherName, FunctionName) works 322ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper/// identical to \c AST_TYPE_TRAVERSE_MATCHER but operates on \c TypeLocs. 3233f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen#define AST_TYPELOC_TRAVERSE_MATCHER(MatcherName, FunctionName, ReturnTypesF) \ 3243f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen namespace internal { \ 3253f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen template <typename T> struct TypeLocMatcher##MatcherName##Getter { \ 3263f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen static TypeLoc (T::*value())() const { return &T::FunctionName##Loc; } \ 3273f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen }; \ 328ce62007526cdf718faed10df5e9fc7c3cd160cdeDaniel Jasper } \ 3293f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen const internal::TypeTraversePolymorphicMatcher< \ 3303f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen TypeLoc, internal::TypeLocMatcher##MatcherName##Getter, \ 3313f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen internal::TypeLocTraverseMatcher, ReturnTypesF>::Func MatcherName##Loc; \ 3323f84bb341bfb1312842b09db71d76bc3898ba247Samuel Benzaquen AST_TYPE_TRAVERSE_MATCHER(MatcherName, FunctionName##Type, ReturnTypesF) 333a7564433191601cb8851196b8dde39392c9c05eeDaniel Jasper 3344da216637fa1ad4bdfd31bc265edb57ca35c2c12Manuel Klimek#endif // LLVM_CLANG_AST_MATCHERS_AST_MATCHERS_MACROS_H 335