[cfe-commits] r166671 - in /cfe/trunk: include/clang/Tooling/Tooling.h unittests/Tooling/ToolingTest.cpp

Manuel Klimek klimek at google.com
Thu Oct 25 01:49:11 PDT 2012


Author: klimek
Date: Thu Oct 25 03:49:11 2012
New Revision: 166671

URL: http://llvm.org/viewvc/llvm-project?rev=166671&view=rev
Log:
Adds the possibility to inject a callback that's called after each translation unit is processed.

This is important when one wants to deduplicate results during one run over a translation unit by pointer identity of AST nodes.

Modified:
    cfe/trunk/include/clang/Tooling/Tooling.h
    cfe/trunk/unittests/Tooling/ToolingTest.cpp

Modified: cfe/trunk/include/clang/Tooling/Tooling.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Tooling/Tooling.h?rev=166671&r1=166670&r2=166671&view=diff
==============================================================================
--- cfe/trunk/include/clang/Tooling/Tooling.h (original)
+++ cfe/trunk/include/clang/Tooling/Tooling.h Thu Oct 25 03:49:11 2012
@@ -74,6 +74,14 @@
 template <typename T>
 FrontendActionFactory *newFrontendActionFactory();
 
+/// \brief Called at the end of each source file when used with
+/// \c newFrontendActionFactory.
+class EndOfSourceFileCallback {
+public:
+  virtual ~EndOfSourceFileCallback() {}
+  virtual void run() = 0;
+};
+
 /// \brief Returns a new FrontendActionFactory for any type that provides an
 /// implementation of newASTConsumer().
 ///
@@ -87,7 +95,7 @@
 ///   newFrontendActionFactory(&Factory);
 template <typename FactoryT>
 inline FrontendActionFactory *newFrontendActionFactory(
-    FactoryT *ConsumerFactory);
+    FactoryT *ConsumerFactory, EndOfSourceFileCallback *EndCallback = NULL);
 
 /// \brief Runs (and deletes) the tool on 'Code' with the -fsyntax-only flag.
 ///
@@ -217,34 +225,45 @@
 
 template <typename FactoryT>
 inline FrontendActionFactory *newFrontendActionFactory(
-    FactoryT *ConsumerFactory) {
+    FactoryT *ConsumerFactory, EndOfSourceFileCallback *EndCallback) {
   class FrontendActionFactoryAdapter : public FrontendActionFactory {
   public:
-    explicit FrontendActionFactoryAdapter(FactoryT *ConsumerFactory)
-      : ConsumerFactory(ConsumerFactory) {}
+    explicit FrontendActionFactoryAdapter(FactoryT *ConsumerFactory,
+                                          EndOfSourceFileCallback *EndCallback)
+      : ConsumerFactory(ConsumerFactory), EndCallback(EndCallback) {}
 
     virtual clang::FrontendAction *create() {
-      return new ConsumerFactoryAdaptor(ConsumerFactory);
+      return new ConsumerFactoryAdaptor(ConsumerFactory, EndCallback);
     }
 
   private:
     class ConsumerFactoryAdaptor : public clang::ASTFrontendAction {
     public:
-      ConsumerFactoryAdaptor(FactoryT *ConsumerFactory)
-        : ConsumerFactory(ConsumerFactory) {}
+      ConsumerFactoryAdaptor(FactoryT *ConsumerFactory,
+                             EndOfSourceFileCallback *EndCallback)
+        : ConsumerFactory(ConsumerFactory), EndCallback(EndCallback) {}
 
       clang::ASTConsumer *CreateASTConsumer(clang::CompilerInstance &,
                                             llvm::StringRef) {
         return ConsumerFactory->newASTConsumer();
       }
 
+    protected:
+      virtual void EndSourceFileAction() {
+        if (EndCallback != NULL)
+          EndCallback->run();
+        clang::ASTFrontendAction::EndSourceFileAction();
+      }
+
     private:
       FactoryT *ConsumerFactory;
+      EndOfSourceFileCallback *EndCallback;
     };
     FactoryT *ConsumerFactory;
+    EndOfSourceFileCallback *EndCallback;
   };
 
-  return new FrontendActionFactoryAdapter(ConsumerFactory);
+  return new FrontendActionFactoryAdapter(ConsumerFactory, EndCallback);
 }
 
 /// \brief Returns the absolute path of \c File, by prepending it with

Modified: cfe/trunk/unittests/Tooling/ToolingTest.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/Tooling/ToolingTest.cpp?rev=166671&r1=166670&r2=166671&view=diff
==============================================================================
--- cfe/trunk/unittests/Tooling/ToolingTest.cpp (original)
+++ cfe/trunk/unittests/Tooling/ToolingTest.cpp Thu Oct 25 03:49:11 2012
@@ -130,5 +130,35 @@
   EXPECT_TRUE(Invocation.run());
 }
 
+struct VerifyEndCallback : public EndOfSourceFileCallback {
+  VerifyEndCallback() : Called(0), Matched(false) {}
+  virtual void run() {
+    ++Called;
+  }
+  ASTConsumer *newASTConsumer() {
+    return new FindTopLevelDeclConsumer(&Matched);
+  }
+  unsigned Called;
+  bool Matched;
+};
+
+TEST(newFrontendActionFactory, InjectsEndOfSourceFileCallback) {
+  VerifyEndCallback EndCallback;
+
+  FixedCompilationDatabase Compilations("/", std::vector<std::string>());
+  std::vector<std::string> Sources;
+  Sources.push_back("/a.cc");
+  Sources.push_back("/b.cc");
+  ClangTool Tool(Compilations, Sources);
+
+  Tool.mapVirtualFile("/a.cc", "void a() {}");
+  Tool.mapVirtualFile("/b.cc", "void b() {}");
+
+  Tool.run(newFrontendActionFactory(&EndCallback, &EndCallback));
+
+  EXPECT_TRUE(EndCallback.Matched);
+  EXPECT_EQ(2u, EndCallback.Called);
+}
+
 } // end namespace tooling
 } // end namespace clang





More information about the cfe-commits mailing list