1 | ====================== |
2 | Matching the Clang AST |
3 | ====================== |
4 | |
5 | This document explains how to use Clang's LibASTMatchers to match interesting |
6 | nodes of the AST and execute code that uses the matched nodes. Combined with |
7 | :doc:`LibTooling`, LibASTMatchers helps to write code-to-code transformation |
8 | tools or query tools. |
9 | |
10 | We assume basic knowledge about the Clang AST. See the :doc:`Introduction |
11 | to the Clang AST <IntroductionToTheClangAST>` if you want to learn more |
12 | about how the AST is structured. |
13 | |
14 | .. FIXME: create tutorial and link to the tutorial |
15 | |
16 | Introduction |
17 | ------------ |
18 | |
19 | LibASTMatchers provides a domain specific language to create predicates on |
20 | Clang's AST. This DSL is written in and can be used from C++, allowing users |
21 | to write a single program to both match AST nodes and access the node's C++ |
22 | interface to extract attributes, source locations, or any other information |
23 | provided on the AST level. |
24 | |
25 | AST matchers are predicates on nodes in the AST. Matchers are created by |
26 | calling creator functions that allow building up a tree of matchers, where |
27 | inner matchers are used to make the match more specific. |
28 | |
29 | For example, to create a matcher that matches all class or union declarations |
30 | in the AST of a translation unit, you can call `recordDecl() |
31 | <LibASTMatchersReference.html#recordDecl0Anchor>`_. To narrow the match down, |
32 | for example to find all class or union declarations with the name "``Foo``", |
33 | insert a `hasName <LibASTMatchersReference.html#hasName0Anchor>`_ matcher: the |
34 | call ``recordDecl(hasName("Foo"))`` returns a matcher that matches classes or |
35 | unions that are named "``Foo``", in any namespace. By default, matchers that |
36 | accept multiple inner matchers use an implicit `allOf() |
37 | <LibASTMatchersReference.html#allOf0Anchor>`_. This allows further narrowing |
38 | down the match, for example to match all classes that are derived from |
39 | "``Bar``": ``recordDecl(hasName("Foo"), isDerivedFrom("Bar"))``. |
40 | |
41 | How to create a matcher |
42 | ----------------------- |
43 | |
44 | With more than a thousand classes in the Clang AST, one can quickly get lost |
45 | when trying to figure out how to create a matcher for a specific pattern. This |
46 | section will teach you how to use a rigorous step-by-step pattern to build the |
47 | matcher you are interested in. Note that there will always be matchers missing |
48 | for some part of the AST. See the section about :ref:`how to write your own |
49 | AST matchers <astmatchers-writing>` later in this document. |
50 | |
51 | .. FIXME: why is it linking back to the same section?! |
52 | |
53 | The precondition to using the matchers is to understand how the AST for what you |
54 | want to match looks like. The |
55 | :doc:`Introduction to the Clang AST <IntroductionToTheClangAST>` teaches you |
56 | how to dump a translation unit's AST into a human readable format. |
57 | |
58 | .. FIXME: Introduce link to ASTMatchersTutorial.html |
59 | .. FIXME: Introduce link to ASTMatchersCookbook.html |
60 | |
61 | In general, the strategy to create the right matchers is: |
62 | |
63 | #. Find the outermost class in Clang's AST you want to match. |
64 | #. Look at the `AST Matcher Reference <LibASTMatchersReference.html>`_ for |
65 | matchers that either match the node you're interested in or narrow down |
66 | attributes on the node. |
67 | #. Create your outer match expression. Verify that it works as expected. |
68 | #. Examine the matchers for what the next inner node you want to match is. |
69 | #. Repeat until the matcher is finished. |
70 | |
71 | .. _astmatchers-bind: |
72 | |
73 | Binding nodes in match expressions |
74 | ---------------------------------- |
75 | |
76 | Matcher expressions allow you to specify which parts of the AST are interesting |
77 | for a certain task. Often you will want to then do something with the nodes |
78 | that were matched, like building source code transformations. |
79 | |
80 | To that end, matchers that match specific AST nodes (so called node matchers) |
81 | are bindable; for example, ``recordDecl(hasName("MyClass")).bind("id")`` will |
82 | bind the matched ``recordDecl`` node to the string "``id``", to be later |
83 | retrieved in the `match callback |
84 | <https://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder_1_1MatchCallback.html>`_. |
85 | |
86 | .. FIXME: Introduce link to ASTMatchersTutorial.html |
87 | .. FIXME: Introduce link to ASTMatchersCookbook.html |
88 | |
89 | Writing your own matchers |
90 | ------------------------- |
91 | |
92 | There are multiple different ways to define a matcher, depending on its type |
93 | and flexibility. |
94 | |
95 | ``VariadicDynCastAllOfMatcher<Base, Derived>`` |
96 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
97 | |
98 | Those match all nodes of type *Base* if they can be dynamically casted to |
99 | *Derived*. The names of those matchers are nouns, which closely resemble |
100 | *Derived*. ``VariadicDynCastAllOfMatchers`` are the backbone of the matcher |
101 | hierarchy. Most often, your match expression will start with one of them, and |
102 | you can :ref:`bind <astmatchers-bind>` the node they represent to ids for later |
103 | processing. |
104 | |
105 | ``VariadicDynCastAllOfMatchers`` are callable classes that model variadic |
106 | template functions in C++03. They take an arbitrary number of |
107 | ``Matcher<Derived>`` and return a ``Matcher<Base>``. |
108 | |
109 | ``AST_MATCHER_P(Type, Name, ParamType, Param)`` |
110 | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ |
111 | |
112 | Most matcher definitions use the matcher creation macros. Those define both |
113 | the matcher of type ``Matcher<Type>`` itself, and a matcher-creation function |
114 | named *Name* that takes a parameter of type *ParamType* and returns the |
115 | corresponding matcher. |
116 | |
117 | There are multiple matcher definition macros that deal with polymorphic return |
118 | values and different parameter counts. See `ASTMatchersMacros.h |
119 | <https://clang.llvm.org/doxygen/ASTMatchersMacros_8h.html>`_. |
120 | |
121 | .. _astmatchers-writing: |
122 | |
123 | Matcher creation functions |
124 | ^^^^^^^^^^^^^^^^^^^^^^^^^^ |
125 | |
126 | Matchers are generated by nesting calls to matcher creation functions. Most of |
127 | the time those functions are either created by using |
128 | ``VariadicDynCastAllOfMatcher`` or the matcher creation macros (see below). |
129 | The free-standing functions are an indication that this matcher is just a |
130 | combination of other matchers, as is for example the case with `callee |
131 | <LibASTMatchersReference.html#callee1Anchor>`_. |
132 | |
133 | .. FIXME: "... macros (see below)" --- there isn't anything below |
134 | |
135 | |