<html>
<head></head>
<body>
<p>Hi,</p>
<p>Ok, Manuel. Thanks for your answers. I'm going to experment with all this.</p>
<blockquote class="replyBlock" style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p><span style="font-size: 12.727272033691406px;">Traversing the AST is super cheap compared to parsing the C++ code.</span></p>
</blockquote><p>Hehehe, ok. It was only curiosity!</p>
<blockquote class="replyBlock" style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><br/>
<div style="font-size: 12.727272033691406px;">Sorry if I'm sounding harsh - I'm more than happy to help with any reasonable questions, but we've already taught you everything you need. In fact, you should have been able to learn all this without us - I myself have learned this mostly through experimentation, reading the documentation and the Clang source code. This is the way you can learn effectively.</div></blockquote><p>Don't worry for this Gabor, you're right. Actually, most of the times I have already thought in some of the answers you give me, but what I want to know if there is a better way to accomplish that. Everybody here have helped me a lot and I'm very thankful for this.</p>
<p>Best regards</p>
<br/>
<div><em>El dia 16 may 2013 12:37, Manuel Klimek <klimek@google.com> escribió:</em></div><blockquote class="replyBlock" style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div dir="ltr">On Thu, May 16, 2013 at 12:30 PM, Pedro Delgado Perez <span dir="ltr"><<a href="mailto:pedro.delgado@uca.es" target="_blank">pedro.delgado@uca.es</a>></span> wrote:<br /><div class="gmail_extra"><div class="gmail_quote"><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><div>Hi,</div><div class="im"><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div>You'll have one process(Decl*) method that does all the common stuff, and overloads for more specific types as needed, e.g. process(FunctionDecl*), which then call the Decl* overload by explicit casting. Have overload resolution work for you.</div></blockquote></div><p>Ok, I think the best in my case is to have a process method per matcher, so don't take care of this anymore.</p>
<p>Now, I have other two or three questions spinning in my mind.</p>
<p>1. Imagine that I have two files to process in the same execution and both include the same header file. Will that header file's code be processed twice? In this case, how could I avoid this?</p>
</div></blockquote><div>Yes. You don't want to avoid this, you want to fix it afterwards by deduplicating your results.</div><div> </div><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><p>2. A matcher finds a CXXConstructorDecl node in a header file (we can call it X.h):<br />-first: I need to inform the cpp files that include X.h that the header has changed. How can I find that files? Up to now, I was only proccesing one file and searched for the file through Context->getSourceManager().getMainFileID() (That I suppose is the file which have the main method implemented, but I'm not absolutely sure). But now, I need to find another way to find these cpp files.</p>
</div></blockquote><div>You'll want to write a matcher that matches all calls to the CXXConstructorDecl. </div><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><br/>
<br/>
<p>3. Is there a way to stop the traversal of the AST in a certain moment when, for instance, I find what I was looking for?</p>
</div></blockquote><div>No. Why would you want to do that? Traversing the AST is super cheap compared to parsing the C++ code.</div><div> </div><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><p>Thanks in advance,</p>
<p>Pedro.</p>
<br/>
<div><em>El dia 14 may 2013 21:13, Gábor Kozár <<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> escribió:</em></div><div><div class="h5"><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div dir="ltr"><div>I don't see the problem.</div><div>You'll have one process(Decl*) method that does all the common stuff, and overloads for more specific types as needed, e.g. process(FunctionDecl*), which then call the Decl* overload by explicit casting. Have overload resolution work for you.</div><div>Gabor</div></div><div class="gmail_extra"><br /><br /><div class="gmail_quote">2013/5/14 Pedro Delgado Perez <span dir="ltr"><<a href="mailto:pedro.delgado@uca.es" target="_blank">pedro.delgado@uca.es</a>></span><br /><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><p>Ok, what I'm trying to do is not to repeat the same code again and again in different methods (process_matcher1(), process_matcher2()...) For example, matcher1 and matcher2 are treated in the same way except in a little part.  At first, I thought of having a Decl* variable and casting the node result, but I'm not sure if this is a good option. Later, for instance, I need to use the getPreviousDecl() method that you told me and then I'll have to know the class type (or maybe I can cast to Decl* again).</p>
<p>Pedro.</p>
<div><em>El dia 14 may 2013 20:15, Gábor Kozár <<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> escribió:</em></div><div><div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div dir="ltr"><div>Hi,</div><div>> <em>if (Result.Nodes.getNodeAs<clang::CXXConstructorDecl>("matcher1")) {</em></div><div><em><br /></em></div><div>I usually do this:<em><br /></em></div><div>if(const CXXConstructorDecl* ctor = Result.Nodes.getNodeAs<CXXConstructorDecl>("matcher1")) { ... }</div><div>> <em>template<typename T><br />void process(const T* Node) {</em></div><div><em><br /></em></div><div>I would recommend against this. Template metaprogramming gives you no advantages here so far as I can see. Use overloading and polymorphism instead.</div><div>Gabor</div></div><div class="gmail_extra"><br /><br /><div class="gmail_quote">2013/5/14 Pedro Delgado Perez <span dir="ltr"><<a href="mailto:pedro.delgado@uca.es" target="_blank">pedro.delgado@uca.es</a>></span><br /><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><p>Hi,</p>
<div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p>Neither :) Just create an object in main(), and hand a pointer to that object to your callback - then call stuff on it from the match callback.</p>
</blockquote></div><p>Ok, ok, that was the problem.</p>
<div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div>> <em>1. I create a MatchFinder.<br />> 2. Then, I add two different matchers to the same callback.<br />> 3. I call run. <br /> ><br />> My questions are:<br />> 1. How many times is called the run method? Every time the MatchFinder finds a node to match?</em></div><div><em><br /></em></div><div>Yes, each time either matcher accepts a node.<em><br /> </em></div><div>> <em>2. The object callback I add to MatchFinder is created more than once? When it is deleted?</em></div><div><em><br /></em></div><div>You (the user) are the one responsible for creating and destroying the callback object. Usually what we do is allocate it on the stack (and pass it the appropriate arguments, of course), and then pass its address to MatchFinder. MatchFinder doesn't create, copy or delete your callback object, so it is safe to store state in the callback.<em><br /> </em></div><div>> <em>Could you explain better "if the second matcher has no deps on the information collected by matcher1"?</em></div><div><em><br /></em></div><div>deps = dependencies<em><br /></em></div><div><em><br /></em></div><div>Gabor</div></blockquote></div><p>Thanks for your answers Gabor.</p>
<p>I have decided to follow up the advice of Manuel and I have created a MatchFinder object with all the matchers and a single MatchCallback object. So now, I'm in my run() method and I want to know which matcher was bound. So I think the only way to know this is to ask:</p>
<p>if (Result.Nodes.getNodeAs<clang::CXXConstructorDecl>("matcher1")){<br />...<br />}<br />else if(Result.Nodes.getNodeAs<clang::CXXRecordDecl>("matcher2")){<br />... <br />}</p>
<p>Notice that I'm retrieving different classes of nodes (clang::CXXConstructorDecl, clang::CXXRecordDecl...) In spite of this fact, I want to process all the nodes in the same way except from a subtle difference and I was asking myself if there is a better way I can do something like this:</p>
<p>if (Result.Nodes.getNodeAs<clang::CXXConstructorDecl>("matcher1")){<br />  ...<br /> process(Result.Nodes.getNodeAs<clang::CXXConstructorDecl>("matcher1"))</p>
<p>}<br />else if(Result.Nodes.getNodeAs<clang::CXXRecordDecl>("matcher2")){<br /> ...<br /> process(Result.Nodes.getNodeAs<clang::CXXRecordDecl>("matcher2"))<br />}<br />...</p>
<br/>
<p>template<typename T><br />void process(const T* Node){<br />...<br />}</p>
<p>Regards,</p>
<p>Pedro.</p>
<br/>
<div><em>El dia 10 may 2013 09:21, Gábor Kozár <<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> escribió:</em></div><div><div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div dir="ltr"><div>Hi,</div><div>> <em>1. I create a MatchFinder.<br />> 2. Then, I add two different matchers to the same callback.<br />> 3. I call run. <br />><br />> My questions are:<br />> 1. How many times is called the run method? Every time the MatchFinder finds a node to match?</em></div><div><em><br /></em></div><div>Yes, each time either matcher accepts a node.<em><br /></em></div><div>> <em>2. The object callback I add to MatchFinder is created more than once? When it is deleted?</em></div><div><em><br /> </em></div><div>You (the user) are the one responsible for creating and destroying the callback object. Usually what we do is allocate it on the stack (and pass it the appropriate arguments, of course), and then pass its address to MatchFinder. MatchFinder doesn't create, copy or delete your callback object, so it is safe to store state in the callback.<em><br /> </em></div><div>> <em>Could you explain better "if the second matcher has no deps on the information collected by matcher1"?</em></div><div><em><br /></em></div><div>deps = dependencies<em><br /></em></div><div><em><br /></em></div><div>Gabor</div></div><div class="gmail_extra"><br /><br /><div class="gmail_quote">2013/5/8 Pedro Delgado Perez <span dir="ltr"><<a href="mailto:pedro.delgadoperez@mail.uca.es" target="_blank">pedro.delgadoperez@mail.uca.es</a>></span><br /><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><p>Hi,</p>
<p>Thanks for all your support. I'm going to respond all your contributions little by little:</p>
<div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p><span style="font-size: 12.727272033691406px;">You can execute Matcher1 first, and when it returns, you start executing Matcher2. I'm not sure what your problem is exactly. (Of course, this will also mean that you will traverse the whole AST twice, which can potentially be very expensive.)</span></p>
</blockquote></div><p>Ok. What I don't understand quite well is the order in the execution.</p>
<p>1. I create a MatchFinder.<br />2. Then, I add two different matchers to the same callback.<br />3. I call run. </p>
<p>My questions are:<br />1. How many times is called the run method? Every time the MatchFinder finds a node to match?<br />2. The object callback I add to MatchFinder is created more than once? When it is deleted? The problem is that I create the object callback with an argument (a constructor method with an argument, not the default constructor) and store it in a variable member. However, when the run method executes, the value of the variable member is lost and I can't understand the problem.</p>
<div><br /><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p><span style="font-size: 12.727272033691406px;">Sorry, missed the comment in one of your more recent emails. So you basically want all matches by matcher1 to be found before all matchers by matcher2. I think the easiest way to do this is just have two MatchFinder classes. Add matcher1 and its callback to the first MatchFinder and call run(). Add matcher2 and its callback to the second MatchFinder and call run() after the first run() returns. You won't have to reparse the file but you will have to traverse the AST twice. There's not much you can do about this given the order you want. However, if the second matcher has no deps on the information collected by matcher1 you could just get away with a single MatchFinder and two callbacks that just store their finds in two vectors which you process after run returns</span></p>
</blockquote><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p><span style="font-size: 12.727272033691406px;">I'm not sure what order you're interested in but you can create two match callbacks one to use for each matcher. The callbacks will be called in the order the nodes are found in the tree by doing a depth-first pre-order traversal as is usual for RecursiveASTVisitor. If both matchers match a given node, the callbacks are called in the order they are registered. </span><br style="font-size: 12.727272033691406px;" /> <br style="font-size: 12.727272033691406px;" /><span style="font-size: 12.727272033691406px;">What sort of order are you looking for? </span></p>
</blockquote></div><p>I understand what you have explained until you say "two callbacks". Why could I want to have two different callbacks? Could you explain better "<span style="font-size: 12.727272033691406px;">if the second matcher </span><span style="font-size: 12.727272033691406px;">has no deps on the information collected by matcher1"?</span></p>
<div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><br /><div style="font-size: 12.727272033691406px;">What is often faster is to produce a superset of the information needed during the traversal / match phase, and then combine / filter the results after everything's done...</div></blockquote></div><div>That is a good solution, I suppose. I will have to study my case more in detail to determine whether this fit my problem or not. But, do you store all that information in global variables or in the callback object?</div><div><br /><br /><p>.</p>
<blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p><span style="font-size: 12.727272033691406px;">You can just count how many times your match callback is called and then print that number after run() returns. </span></p>
</blockquote></div><p>Again, my problem is that I don't $when the match callback is called. </p>
<p>I hope I can end up getting the usage of all this with your help.</p>
<p>Pedro.</p>
<br/>
<div><em>El dia 08 may 2013 12:10, Gábor Kozár <<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> escribió:</em></div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div dir="ltr"><div>Hi,</div><div><div><div>> <em>Ok, this also helps, but the problem is that I need to print something when all the nodes have been matched. So, is there a way I can check within onStartOfTranslationUnit() method if we have reached the end? I have just found this:</em></div><div><em><br /></em></div><div>onStartOfTranslationUnit() is - obviously - called at the start of each TU. I.e. this will be called after the previous TU has been completed, i.e. all nodes in it have been matched.<em><br /></em></div><div>> <em>clang::ast_matchers::MatchFinder::ParsingDoneTestCallback</em></div><div><em><br /></em></div><div>This is for testing purposes only, it's not recommended to use it.<em><br /></em></div><div>> <em>So, what you are saying is that I can't control the order the nodes are matched?</em></div><div><em><br /></em></div><div>No, you can't. You'll have to implement a RecursiveASTVisitor manually if you need this fine control.<em><br /> </em></div><div>> <em>What I'm trying to explain is that I need all the nodes bound with Matcher1 are treated before the execution of nodes bound with Matcher2 starts.</em></div><div><em><br /></em></div><div>You can execute Matcher1 first, and when it returns, you start executing Matcher2. I'm not sure what your problem is exactly. (Of course, this will also mean that you will traverse the whole AST twice, which can potentially be very expensive.)</div><div><em><br /></em></div><div>Gabor<em><br /></em></div></div></div></div><div class="gmail_extra"><br /><br /><div class="gmail_quote"><div><div>2013/5/8 Pedro Delgado Perez <span dir="ltr"><<a href="mailto:pedro.delgadoperez@mail.uca.es" target="_blank">pedro.delgadoperez@mail.uca.es</a>></span></div></div><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><div><div><p>Hi,</p>
<div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div>You collect information about the matches into e.g. a vector, and you can use the MatchCallback's onStartOfTranslationUnit to process the previous TU's matches.<em><br /> </em></div></blockquote></div><p>Ok, this also helps, but the problem is that I need to print something when <strong>all the nodes</strong> have been matched. So, is there a way I can check within onStartOfTranslationUnit() method if we have reached the end? I have just found this:</p>
<p>clang::ast_matchers::MatchFinder::ParsingDoneTestCallback</p>
<p>This is the implementation of the class:</p>
<p><span>class </span><a title="Called when parsing is finished. Intended for testing only." href="http://fossies.org/dox/clang-3.2.src/classclang_1_1ast__matchers_1_1MatchFinder_1_1ParsingDoneTestCallback.html" target="_blank">ParsingDoneTestCallback</a> {</p>
<div><a name="13eace47045872d7_13ea45e68095c0e9_13ea2d9a810f1f53_13e855393759f756_13e835036b2d5d74_l00100"></a>  <span>public</span>:</div><div><a name="13eace47045872d7_13ea45e68095c0e9_13ea2d9a810f1f53_13e855393759f756_13e835036b2d5d74_l00101"></a><span> </span> <span>virtual</span> <a href="http://fossies.org/dox/clang-3.2.src/classclang_1_1ast__matchers_1_1MatchFinder_1_1ParsingDoneTestCallback.html#ab6018406e1835b0dcc7fa982e0836a55" target="_blank">~ParsingDoneTestCallback</a>();</div><div><a name="13eace47045872d7_13ea45e68095c0e9_13ea2d9a810f1f53_13e855393759f756_13e835036b2d5d74_l00102"></a><span> </span> <span>virtual</span> <span>void</span> <a href="http://fossies.org/dox/clang-3.2.src/classclang_1_1ast__matchers_1_1MatchFinder_1_1ParsingDoneTestCallback.html#a818b643aaad117bb86bcda80bba32ceb" target="_blank">run</a>() = 0;</div><div><a name="13eace47045872d7_13ea45e68095c0e9_13ea2d9a810f1f53_13e855393759f756_13e835036b2d5d74_l00103"></a>};</div><br/>
<p>Maybe I could redefine the run method. Do you think this may be my solution?</p>
<div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div>So the matchers run regardless of whether you ever access the bound nodes. What this means is that your run() method will be called for every match, with the appropriate nodes bound to the names you defined. So a MatchResult only contains information about one single match (i.e. a subtree of the AST, if you will). Hope this clears things up.</div></blockquote></div><p>Um... I'm a bit mixed up at this moment. So, what you are saying is that I can't control the order the nodes are matched? For me that would be a problem because I need to keep an order in the execution. What I'm trying to explain is that I need all the nodes bound with Matcher1 are treated before the execution of nodes bound with Matcher2 starts.</p>
<p>Thanks,</p>
<p>Pedro.</p>
<div><em>El dia 07 may 2013 22:10, Gábor Kozár <<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> escribió:</em></div></div></div><div><div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div dir="ltr"><div>Hi,</div><div><div>><em>1. Imagine that I need to print something after all the nodes have been matched. For example, the number of nodes matched. How can I do that? </em></div><div><em><br /> </em></div></div><div><div>You collect information about the matches into e.g. a vector, and you can use the MatchCallback's onStartOfTranslationUnit to process the previous TU's matches.<em><br /></em></div></div><div><div>> <em>How does the 'run' method behave in this case? I mean that I don't know if it retrieves, one by one, all the nodes in applyMatch1 and ,after that, all the nodes in applyMatch2 or it matches one in applyMatch1 and then other in applyMatch2 in each iteration.</em></div><div><em><br /></em></div></div><div><div>So the matchers run regardless of whether you ever access the bound nodes. What this means is that your run() method will be called for every match, with the appropriate nodes bound to the names you defined. So a MatchResult only contains information about one single match (i.e. a subtree of the AST, if you will). Hope this clears things up.</div><div>Gabor</div></div></div><div class="gmail_extra"><br /><br /><div class="gmail_quote"><div>2013/5/7 Pedro Delgado Perez <span dir="ltr"><<a href="mailto:pedro.delgadoperez@mail.uca.es" target="_blank">pedro.delgadoperez@mail.uca.es</a>></span></div><blockquote class="gmail_quote" style="margin: 0 0 0 .8ex; border-left: 1px #ccc solid; padding-left: 1ex;"><div><div><p>Hi again,</p>
<p>Sorry to make so much questions, but I hope a good structure of my tool will save me a lot of time in future.</p>
<p>I'm using something like this in <a href="http://clang.llvm.org/docs/LibASTMatchersTutorial.html" target="_blank">http://clang.llvm.org/docs/LibASTMatchersTutorial.html</a>:</p>
<br/>
<pre style="overflow-x: auto; overflow-y: hidden; border: thin dotted #0c3762; margin: 0px 0px 12px; padding: 0.8em; background-color: #f0f0f0; color: #333333;"><span style="color: #007020; font-weight: bold;">class</span> <span style="color: #0e84b5; font-weight: bold;">LoopPrinter</span> <span style="color: #666666;">:</span> <span style="color: #007020; font-weight: bold;">public</span> <span>MatchFinder</span><span style="color: #666666;">::</span><span>MatchCallback</span> <span>{</span><span style="color: #007020; font-weight: bold;">public</span> <span style="color: #666666;">:</span>  <span style="color: #007020; font-weight: bold;">virtual</span> <span style="color: #902000;">void</span> <span>run</span><span>(</span><span style="color: #007020; font-weight: bold;">const</span> <span>MatchFinder</span><span style="color: #666666;">::</span><span>MatchResult</span> <span style="color: #666666;">&</span><span>Result</span><span>)</span> <span>{</span>    <span style="color: #007020; font-weight: bold;">if</span> <span>(</span><span style="color: #007020; font-weight: bold;">const</span> <span>ForStmt</span> <span style="color: #666666;">*</span><span>FS</span> <span style="color: #666666;">=</span> <span>Result</span><span>.</span><span>Nodes</span><span>.</span><span>getNodeAs</span><span style="color: #666666;"><</span><span>clang</span><span style="color: #666666;">::</span><span>ForStmt</span><span style="color: #666666;">></span><span>(</span><span style="color: #4070a0;">"forLoop"</span><span>))</span>      <span>FS</span><span style="color: #666666;">-></span><span>dump</span><span>();</span>  <span>}</span><span>};</span></pre><br/>
<p>So, now I have two questions:</p>
<p>1. Imagine that I need to print something after <strong>all</strong> the nodes have been matched. For example, the number of nodes matched. How can I do that? </p>
</div><p>2. Imagine that I have two methods within the run method to separate two kind of nodes I want to bind. Something like this:</p>
<div><br /><br /><pre style="color: #333333; font-size: 11.818181991577148px; margin: 0px 0px 12px; overflow-x: auto; overflow-y: hidden; border: thin dotted #0c3762; padding: 0.8em; background-color: #f0f0f0;"><span style="color: #007020; font-weight: bold;"><br /> class</span> <span style="color: #0e84b5; font-weight: bold;">LoopPrinter</span> <span style="color: #666666;">:</span> <span style="color: #007020; font-weight: bold;">public</span> <span>MatchFinder</span><span style="color: #666666;">::</span><span>MatchCallback</span> <span>{</span><span style="color: #007020; font-weight: bold;">public</span> <span style="color: #666666;">:</span>  <span style="color: #007020; font-weight: bold;">virtual</span> <span style="color: #902000;">void</span> <span>run</span><span>(</span><span style="color: #007020; font-weight: bold;">const</span> <span>MatchFinder</span><span style="color: #666666;">::</span><span>MatchResult</span> <span style="color: #666666;">&</span><span>Result</span><span>)</span> <span>{</span>    <span>applyMatch1();<br /> </span>    applyMatch2();  <span>}<br /><br /></span>void <span style="color: #000000;">applyMatch1(){<br /> <span style="color: #007020; font-weight: bold;">if</span> <span>(</span><span style="color: #007020; font-weight: bold;">const</span> <span>ForStmt</span> <span style="color: #666666;">*</span><span>FS</span> <span style="color: #666666;">=</span> <span>Result</span><span>.</span><span>Nodes</span><span>.</span><span>getNodeAs</span><span style="color: #666666;"><</span><span>clang</span><span style="color: #666666;">::</span><span>ForStmt</span><span style="color: #666666;">></span><span>(</span><span style="color: #4070a0;">"forLoop__1"</span><span>))</span><span style="white-space: pre-wrap;"><br /> </span></span>}<br /><br />void apply2(){</pre><pre style="color: #333333; font-size: 11.818181991577148px; margin: 0px 0px 12px; overflow-x: auto; overflow-y: hidden; border: thin dotted #0c3762; padding: 0.8em;"><span style="color: #000000;"><span style="color: #007020; font-weight: bold;">if</span> <span>(</span><span style="color: #007020; font-weight: bold;">const</span> <span>ForStmt</span> <span style="color: #666666;">*</span><span>FS</span> <span style="color: #666666;">=</span> <span>Result</span><span>.</span><span>Nodes</span><span>.</span><span>getNodeAs</span><span style="color: #666666;"><</span><span>clang</span><span style="color: #666666;">::</span><span>ForStmt</span><span style="color: #666666;">></span><span>(</span><span style="color: #4070a0;">"forLoop_2"</span><span>))</span></span></pre><pre style="color: #333333; font-size: 11.818181991577148px; margin: 0px 0px 12px; overflow-x: auto; overflow-y: hidden; border: thin dotted #0c3762; padding: 0.8em; background-color: #f0f0f0;">}<br /><span>};</span></pre><br/>
<br/>
</div><div><p>How does the 'run' method behave in this case? I mean that I don't know if it retrieves, one by one, all the nodes in applyMatch1 and ,after that, all the nodes in applyMatch2 or it matches one in applyMatch1 and then other in applyMatch2 in each iteration. I hope you can understand me because this is very important in my case.</p>
<p>Thanks in advance.</p>
<p>Pedro</p>
</div><div><div><div><br /><br /><div><em>El dia 06 may 2013 22:32, "Vane, Edwin" <<a href="mailto:edwin.vane@intel.com" target="_blank">edwin.vane@intel.com</a>> escribió:</em></div></div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><div><p>Given your description, I'm not sure matchers are what you want. If you just want to print information on certain types of nodes, you could use a RecursiveASTVisitor for that.</p>
<p>However, if what you're looking for is a little more complex then matchers may be what you want after all.</p>
<p>As for the two classes, you want to use tooling::MatchFinder as shown in the tutorial. The other is just an implementation detail of the match finding code.</p>
<p>newASTConsumer() is a function that's required to be defined for objects passed to newFrontendActionFactory(). You don't need to implement it. It's implemented by MatchFinder. Again, it's an implementation detail you don't need to worry about at this point.</p>
<p>The use of ASTConsumers is not necessary if you're using MatchFinder and ClangTool as described in the tutorial. MatchFinder is an abstraction around RecursiveASTVisitor so all that stuff in RecursiveASTVisitor you'd normally have to use is actually hidden away.</p>
<p>I think you should first decide which route you want to go: MatchFinder or RecursiveASTVisitor. The first question I'd ask is: how hard is it to find the nodes I want to print info on in the AST. If all I want is every for loop that's easy. If I want for loops within member functions of a specific class, that's hard and an excellent use case for ASTMatchers.</p>
</div><div><div><blockquote style="border-left: 2px solid #000083; margin: 0pt 0pt 0pt 0.8ex; padding-left: 1ex;"><p>-----Original Message-----<br />From: <a href="mailto:cfe-dev-bounces@cs.uiuc.edu" target="_blank">cfe-dev-bounces@cs.uiuc.edu</a> [<a href="mailto:cfe-dev-bounces@cs.uiuc.edu" target="_blank">mailto:cfe-dev-bounces@cs.uiuc.edu</a>] On<br /> Behalf Of Pedro Delgado Perez<br />Sent: Monday, May 06, 2013 12:58 PM<br />To: <a href="mailto:klimek@google.com" target="_blank">klimek@google.com</a>; <a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a><br /> Cc: <a href="mailto:cfe-dev@cs.uiuc.edu" target="_blank">cfe-dev@cs.uiuc.edu</a><br />Subject: Re: [cfe-dev] ASTMatchers: isVirtual and isOverride</p>
<p>Hi,</p>
<p>I need your help again. Look, in my tool I was trying to use the syntax that's<br />shown here:</p>
<p><a href="http://clang.llvm.org/docs/LibASTMatchersTutorial.html" target="_blank">http://clang.llvm.org/docs/LibASTMatchersTutorial.html</a></p>
<p>Namely I'm referring to this part:</p>
<p>int main(int argc, const char **argv) {<br />CommonOptionsParser OptionsParser(argc, argv);<br />ClangTool Tool(OptionsParser.getCompilations(),<br />OptionsParser.getSourcePathList());</p>
<p>LoopPrinter Printer;<br />MatchFinder Finder;<br />Finder.addMatcher(LoopMatcher, &Printer);</p>
<p>return Tool.run(newFrontendActionFactory(&Finder));<br />}</p>
<p>However, now I want to create a object "Printer" with different features<br />depending on the arguments provided in command line. So I was thinking on<br />implement a factory method pattern to create a different LoopPrinter object:<br /> class OptionsFactory {<br />public:<br />LoopPrinter getOption() {<br />if(...)<br />return LoopPrinter(attribute1, attribute2);<br />else<br />return LoopPrinter(attribute1);<br />}<br />};</p>
<p>I was searching for a better solution and there are some things that I can't<br />completely understand.</p>
<p>- Why are there two classes MatchFinder:<br /><a href="http://clang.llvm.org/doxygen/classclang_1_1tooling_1_1MatchFinder.html" target="_blank">http://clang.llvm.org/doxygen/classclang_1_1tooling_1_1MatchFinder.html</a><br /> <a href="http://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder" target="_blank">http://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder</a>.<br />html</p>
<p>- What the method in ast_matchers:MatchFinder</p>
<p>clang::ASTConsumer<br /><<a href="http://clang.llvm.org/doxygen/classclang_1_1ASTConsumer.html%3E" target="_blank">http://clang.llvm.org/doxygen/classclang_1_1ASTConsumer.html></a> *</p>
<p>newASTConsumer<br /><<a href="http://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder" target="_blank">http://clang.llvm.org/doxygen/classclang_1_1ast__matchers_1_1MatchFinder</a><br />.html#a4807049e6e39572d19ff127406df3d81> ()</p>
<p>is used for? I see we can 'associate' an ASTConsumer to the Frontend as in:<br /><a href="http://clang.llvm.org/docs/RAVFrontendAction.html" target="_blank">http://clang.llvm.org/docs/RAVFrontendAction.html</a></p>
<p>but, is this possible using Matchers? Would it have any sense to create an<br />ASTConsumer in my class OptionsFactory?</p>
<p>I have improved a lot since you last helped me, but clang is too big!</p>
<p>By the way, do you know how to use CommandLine? I posted a new thread</p>
<p><a href="http://lists.cs.uiuc.edu/pipermail/cfe-dev/2013-May/029473.html" target="_blank">http://lists.cs.uiuc.edu/pipermail/cfe-dev/2013-May/029473.html</a></p>
<p>If you know how to solve that problem, please, let me know.</p>
<p>Thanks in advance,</p>
<p>Pedro.</p>
<br/>
<p>El dia 27 abr 2013 18:39, Manuel Klimek <<a href="mailto:klimek@google.com" target="_blank">klimek@google.com</a>> escribió:</p>
<p>On Sat, Apr 27, 2013 at 6:36 PM, Gábor Kozár<br /><<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> wrote:</p>
<br/>
<br/>
<p>2013/4/27 Manuel Klimek <<a href="mailto:klimek@google.com" target="_blank">klimek@google.com</a>></p>
<br/>
<p>Just use the empty string for binding and getNodeAs :)</p>
<br/>
<p>That would potentially lead to confusion when there are more<br />nodes bound, but the programmer forgot to supply the proper name. In my<br />suggestion, the parameterless getNodeAs would have an assert to check there is<br /> exactly one node bound (and whose name is the default name).</p>
<p>If you put everything behind constants, I think it'll be easy enough to see<br />what's happening - and that's a generally good strategy anyway, as you get a<br />compile error if you mistype...<br />Thus, I think it'd not add enough value to special case the interface.</p>
<br/>
<br/>
<br/>
<p>2013/4/27 Manuel Klimek <<a href="mailto:klimek@google.com" target="_blank">klimek@google.com</a>></p>
<br/>
<p>On Sat, Apr 27, 2013 at 6:28 PM, Gábor Kozár<br /><<a href="mailto:kozargabor@gmail.com" target="_blank">kozargabor@gmail.com</a>> wrote:</p>
<p>Hi,<br />2013/4/26 Pedro Delgado Perez<br /><<a href="mailto:pedro.delgadoperez@mail.uca.es" target="_blank">pedro.delgadoperez@mail.uca.es</a>></p>
<br/>
<p>Hehehe... I found the problem with<br />this. I was binding wrongly the matcher! I used a id in the matcher thas was<br />different from the id in the function that retrieves the nodes... I think this will be<br />a typical mistake for newbies...</p>
<p>Ah, yes, that happens a lot to me as well. Now<br />that I think about it, it might be worthwhile adding a parameterless .bind() and<br />.getNodeAs<T>() for situations where only one node is bound. Should be fairly<br /> trivial, but also not all that useful...</p>
<p>Just use the empty string for binding and getNodeAs :)</p>
<br/>
<br/>
<p>2013/4/26 Pedro Delgado Perez<br /><<a href="mailto:pedro.delgadoperez@mail.uca.es" target="_blank">pedro.delgadoperez@mail.uca.es</a>></p>
<br/>
<p>Thanks both! Now I can see all this<br />much clearer and I have the enough knowledge to start out with clang.</p>
<br/>
<p>You're welcome. Good luck!</p>
<br/>
<p>2013/4/25 Manuel Klimek <<a href="mailto:klimek@google.com" target="_blank">klimek@google.com</a>></p>
<br/>
<p>And btw thanks a lot for all the great user support you're giving<br />here!</p>
<br/>
<p>Thank you, I'm happy to help. Clang is a great project!</p>
<p>As soon as the university term is over, I'm also planning on trying to<br />contribute code-wise, mainly to the Static Analyzer but I guess also on just about<br />anything that catches my attention. :) I'm quite excited - this is going to be the<br /> first open source project I contribute to.<br />Gabor</p>
</blockquote></div></div></blockquote></div></div></div></blockquote></div><br/>
</div></blockquote></div></div></div></blockquote></div><br/>
</div></blockquote></div></blockquote></div><br/>
</div></blockquote></div></div></div></blockquote></div><br/>
</div></blockquote></div></div></div></blockquote></div><br/>
</div></blockquote></div></div></div></blockquote></div><br/>
</div></div></blockquote>
</body>
</html>