Warning: That file was not part of the compilation database. It may have many parsing errors.

1//===- Tooling.h - Framework for standalone Clang tools ---------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file implements functions to run clang tools standalone instead
11// of running them as a plugin.
12//
13// A ClangTool is initialized with a CompilationDatabase and a set of files
14// to run over. The tool will then run a user-specified FrontendAction over
15// all TUs in which the given files are compiled.
16//
17// It is also possible to run a FrontendAction over a snippet of code by
18// calling runToolOnCode, which is useful for unit testing.
19//
20// Applications that need more fine grained control over how to run
21// multiple FrontendActions over code can use ToolInvocation.
22//
23// Example tools:
24// - running clang -fsyntax-only over source code from an editor to get
25// fast syntax checks
26// - running match/replace tools over C++ code
27//
28//===----------------------------------------------------------------------===//
29
30#ifndef LLVM_CLANG_TOOLING_TOOLING_H
31#define LLVM_CLANG_TOOLING_TOOLING_H
32
33#include "clang/AST/ASTConsumer.h"
34#include "clang/Basic/FileManager.h"
35#include "clang/Basic/LLVM.h"
36#include "clang/Basic/VirtualFileSystem.h"
37#include "clang/Frontend/FrontendAction.h"
38#include "clang/Frontend/PCHContainerOperations.h"
39#include "clang/Tooling/ArgumentsAdjusters.h"
40#include "llvm/ADT/ArrayRef.h"
41#include "llvm/ADT/IntrusiveRefCntPtr.h"
42#include "llvm/ADT/StringMap.h"
43#include "llvm/ADT/StringRef.h"
44#include "llvm/ADT/StringSet.h"
45#include "llvm/ADT/Twine.h"
46#include "llvm/Option/Option.h"
47#include <memory>
48#include <string>
49#include <utility>
50#include <vector>
51
52namespace clang {
53
54class CompilerInstance;
55class CompilerInvocation;
56class DiagnosticConsumer;
57class DiagnosticsEngine;
58class SourceManager;
59
60namespace driver {
61
62class Compilation;
63
64} // namespace driver
65
66namespace tooling {
67
68class CompilationDatabase;
69
70/// Interface to process a clang::CompilerInvocation.
71///
72/// If your tool is based on FrontendAction, you should be deriving from
73/// FrontendActionFactory instead.
74class ToolAction {
75public:
76 virtual ~ToolAction();
77
78 /// Perform an action for an invocation.
79 virtual bool
80 runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
81 FileManager *Files,
82 std::shared_ptr<PCHContainerOperations> PCHContainerOps,
83 DiagnosticConsumer *DiagConsumer) = 0;
84};
85
86/// Interface to generate clang::FrontendActions.
87///
88/// Having a factory interface allows, for example, a new FrontendAction to be
89/// created for each translation unit processed by ClangTool. This class is
90/// also a ToolAction which uses the FrontendActions created by create() to
91/// process each translation unit.
92class FrontendActionFactory : public ToolAction {
93public:
94 ~FrontendActionFactory() override;
95
96 /// Invokes the compiler with a FrontendAction created by create().
97 bool runInvocation(std::shared_ptr<CompilerInvocation> Invocation,
98 FileManager *Files,
99 std::shared_ptr<PCHContainerOperations> PCHContainerOps,
100 DiagnosticConsumer *DiagConsumer) override;
101
102 /// Returns a new clang::FrontendAction.
103 ///
104 /// The caller takes ownership of the returned action.
105 virtual FrontendAction *create() = 0;
106};
107
108/// Returns a new FrontendActionFactory for a given type.
109///
110/// T must derive from clang::FrontendAction.
111///
112/// Example:
113/// FrontendActionFactory *Factory =
114/// newFrontendActionFactory<clang::SyntaxOnlyAction>();
115template <typename T>
116std::unique_ptr<FrontendActionFactory> newFrontendActionFactory();
117
118/// Callbacks called before and after each source file processed by a
119/// FrontendAction created by the FrontedActionFactory returned by \c
120/// newFrontendActionFactory.
121class SourceFileCallbacks {
122public:
123 virtual ~SourceFileCallbacks() = default;
124
125 /// Called before a source file is processed by a FrontEndAction.
126 /// \see clang::FrontendAction::BeginSourceFileAction
127 virtual bool handleBeginSource(CompilerInstance &CI) {
128 return true;
129 }
130
131 /// Called after a source file is processed by a FrontendAction.
132 /// \see clang::FrontendAction::EndSourceFileAction
133 virtual void handleEndSource() {}
134};
135
136/// Returns a new FrontendActionFactory for any type that provides an
137/// implementation of newASTConsumer().
138///
139/// FactoryT must implement: ASTConsumer *newASTConsumer().
140///
141/// Example:
142/// struct ProvidesASTConsumers {
143/// clang::ASTConsumer *newASTConsumer();
144/// } Factory;
145/// std::unique_ptr<FrontendActionFactory> FactoryAdapter(
146/// newFrontendActionFactory(&Factory));
147template <typename FactoryT>
148inline std::unique_ptr<FrontendActionFactory> newFrontendActionFactory(
149 FactoryT *ConsumerFactory, SourceFileCallbacks *Callbacks = nullptr);
150
151/// Runs (and deletes) the tool on 'Code' with the -fsyntax-only flag.
152///
153/// \param ToolAction The action to run over the code.
154/// \param Code C++ code.
155/// \param FileName The file name which 'Code' will be mapped as.
156/// \param PCHContainerOps The PCHContainerOperations for loading and creating
157/// clang modules.
158///
159/// \return - True if 'ToolAction' was successfully executed.
160bool runToolOnCode(FrontendAction *ToolAction, const Twine &Code,
161 const Twine &FileName = "input.cc",
162 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
163 std::make_shared<PCHContainerOperations>());
164
165/// The first part of the pair is the filename, the second part the
166/// file-content.
167using FileContentMappings = std::vector<std::pair<std::string, std::string>>;
168
169/// Runs (and deletes) the tool on 'Code' with the -fsyntax-only flag and
170/// with additional other flags.
171///
172/// \param ToolAction The action to run over the code.
173/// \param Code C++ code.
174/// \param Args Additional flags to pass on.
175/// \param FileName The file name which 'Code' will be mapped as.
176/// \param ToolName The name of the binary running the tool. Standard library
177/// header paths will be resolved relative to this.
178/// \param PCHContainerOps The PCHContainerOperations for loading and creating
179/// clang modules.
180///
181/// \return - True if 'ToolAction' was successfully executed.
182bool runToolOnCodeWithArgs(
183 FrontendAction *ToolAction, const Twine &Code,
184 const std::vector<std::string> &Args, const Twine &FileName = "input.cc",
185 const Twine &ToolName = "clang-tool",
186 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
187 std::make_shared<PCHContainerOperations>(),
188 const FileContentMappings &VirtualMappedFiles = FileContentMappings());
189
190// Similar to the overload except this takes a VFS.
191bool runToolOnCodeWithArgs(
192 FrontendAction *ToolAction, const Twine &Code,
193 llvm::IntrusiveRefCntPtr<vfs::FileSystem> VFS,
194 const std::vector<std::string> &Args, const Twine &FileName = "input.cc",
195 const Twine &ToolName = "clang-tool",
196 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
197 std::make_shared<PCHContainerOperations>());
198
199/// Builds an AST for 'Code'.
200///
201/// \param Code C++ code.
202/// \param FileName The file name which 'Code' will be mapped as.
203/// \param PCHContainerOps The PCHContainerOperations for loading and creating
204/// clang modules.
205///
206/// \return The resulting AST or null if an error occurred.
207std::unique_ptr<ASTUnit>
208buildASTFromCode(const Twine &Code, const Twine &FileName = "input.cc",
209 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
210 std::make_shared<PCHContainerOperations>());
211
212/// Builds an AST for 'Code' with additional flags.
213///
214/// \param Code C++ code.
215/// \param Args Additional flags to pass on.
216/// \param FileName The file name which 'Code' will be mapped as.
217/// \param ToolName The name of the binary running the tool. Standard library
218/// header paths will be resolved relative to this.
219/// \param PCHContainerOps The PCHContainerOperations for loading and creating
220/// clang modules.
221///
222/// \param Adjuster A function to filter the command line arguments as specified.
223///
224/// \return The resulting AST or null if an error occurred.
225std::unique_ptr<ASTUnit> buildASTFromCodeWithArgs(
226 const Twine &Code, const std::vector<std::string> &Args,
227 const Twine &FileName = "input.cc", const Twine &ToolName = "clang-tool",
228 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
229 std::make_shared<PCHContainerOperations>(),
230 ArgumentsAdjuster Adjuster = getClangStripDependencyFileAdjuster());
231
232/// Utility to run a FrontendAction in a single clang invocation.
233class ToolInvocation {
234public:
235 /// Create a tool invocation.
236 ///
237 /// \param CommandLine The command line arguments to clang. Note that clang
238 /// uses its binary name (CommandLine[0]) to locate its builtin headers.
239 /// Callers have to ensure that they are installed in a compatible location
240 /// (see clang driver implementation) or mapped in via mapVirtualFile.
241 /// \param FAction The action to be executed. Class takes ownership.
242 /// \param Files The FileManager used for the execution. Class does not take
243 /// ownership.
244 /// \param PCHContainerOps The PCHContainerOperations for loading and creating
245 /// clang modules.
246 ToolInvocation(std::vector<std::string> CommandLine, FrontendAction *FAction,
247 FileManager *Files,
248 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
249 std::make_shared<PCHContainerOperations>());
250
251 /// Create a tool invocation.
252 ///
253 /// \param CommandLine The command line arguments to clang.
254 /// \param Action The action to be executed.
255 /// \param Files The FileManager used for the execution.
256 /// \param PCHContainerOps The PCHContainerOperations for loading and creating
257 /// clang modules.
258 ToolInvocation(std::vector<std::string> CommandLine, ToolAction *Action,
259 FileManager *Files,
260 std::shared_ptr<PCHContainerOperations> PCHContainerOps);
261
262 ~ToolInvocation();
263
264 /// Set a \c DiagnosticConsumer to use during parsing.
265 void setDiagnosticConsumer(DiagnosticConsumer *DiagConsumer) {
266 this->DiagConsumer = DiagConsumer;
267 }
268
269 /// Map a virtual file to be used while running the tool.
270 ///
271 /// \param FilePath The path at which the content will be mapped.
272 /// \param Content A null terminated buffer of the file's content.
273 // FIXME: remove this when all users have migrated!
274 void mapVirtualFile(StringRef FilePath, StringRef Content);
275
276 /// Run the clang invocation.
277 ///
278 /// \returns True if there were no errors during execution.
279 bool run();
280
281 private:
282 void addFileMappingsTo(SourceManager &SourceManager);
283
284 bool runInvocation(const char *BinaryName,
285 driver::Compilation *Compilation,
286 std::shared_ptr<CompilerInvocation> Invocation,
287 std::shared_ptr<PCHContainerOperations> PCHContainerOps);
288
289 std::vector<std::string> CommandLine;
290 ToolAction *Action;
291 bool OwnsAction;
292 FileManager *Files;
293 std::shared_ptr<PCHContainerOperations> PCHContainerOps;
294 // Maps <file name> -> <file content>.
295 llvm::StringMap<StringRef> MappedFileContents;
296 DiagnosticConsumer *DiagConsumer = nullptr;
297};
298
299/// Utility to run a FrontendAction over a set of files.
300///
301/// This class is written to be usable for command line utilities.
302/// By default the class uses ClangSyntaxOnlyAdjuster to modify
303/// command line arguments before the arguments are used to run
304/// a frontend action. One could install an additional command line
305/// arguments adjuster by calling the appendArgumentsAdjuster() method.
306class ClangTool {
307public:
308 /// Constructs a clang tool to run over a list of files.
309 ///
310 /// \param Compilations The CompilationDatabase which contains the compile
311 /// command lines for the given source paths.
312 /// \param SourcePaths The source files to run over. If a source files is
313 /// not found in Compilations, it is skipped.
314 /// \param PCHContainerOps The PCHContainerOperations for loading and creating
315 /// clang modules.
316 /// \param BaseFS VFS used for all underlying file accesses when running the
317 /// tool.
318 ClangTool(const CompilationDatabase &Compilations,
319 ArrayRef<std::string> SourcePaths,
320 std::shared_ptr<PCHContainerOperations> PCHContainerOps =
321 std::make_shared<PCHContainerOperations>(),
322 IntrusiveRefCntPtr<vfs::FileSystem> BaseFS =
323 vfs::getRealFileSystem());
324
325 ~ClangTool();
326
327 /// Set a \c DiagnosticConsumer to use during parsing.
328 void setDiagnosticConsumer(DiagnosticConsumer *DiagConsumer) {
329 this->DiagConsumer = DiagConsumer;
330 }
331
332 /// Map a virtual file to be used while running the tool.
333 ///
334 /// \param FilePath The path at which the content will be mapped.
335 /// \param Content A null terminated buffer of the file's content.
336 void mapVirtualFile(StringRef FilePath, StringRef Content);
337
338 /// Append a command line arguments adjuster to the adjuster chain.
339 ///
340 /// \param Adjuster An argument adjuster, which will be run on the output of
341 /// previous argument adjusters.
342 void appendArgumentsAdjuster(ArgumentsAdjuster Adjuster);
343
344 /// Clear the command line arguments adjuster chain.
345 void clearArgumentsAdjusters();
346
347 /// Runs an action over all files specified in the command line.
348 ///
349 /// \param Action Tool action.
350 ///
351 /// \returns 0 on success; 1 if any error occurred; 2 if there is no error but
352 /// some files are skipped due to missing compile commands.
353 int run(ToolAction *Action);
354
355 /// Create an AST for each file specified in the command line and
356 /// append them to ASTs.
357 int buildASTs(std::vector<std::unique_ptr<ASTUnit>> &ASTs);
358
359 /// Returns the file manager used in the tool.
360 ///
361 /// The file manager is shared between all translation units.
362 FileManager &getFiles() { return *Files; }
363
364 llvm::ArrayRef<std::string> getSourcePaths() const { return SourcePaths; }
365
366private:
367 const CompilationDatabase &Compilations;
368 std::vector<std::string> SourcePaths;
369 std::shared_ptr<PCHContainerOperations> PCHContainerOps;
370
371 llvm::IntrusiveRefCntPtr<vfs::OverlayFileSystem> OverlayFileSystem;
372 llvm::IntrusiveRefCntPtr<vfs::InMemoryFileSystem> InMemoryFileSystem;
373 llvm::IntrusiveRefCntPtr<FileManager> Files;
374
375 // Contains a list of pairs (<file name>, <file content>).
376 std::vector<std::pair<StringRef, StringRef>> MappedFileContents;
377
378 llvm::StringSet<> SeenWorkingDirectories;
379
380 ArgumentsAdjuster ArgsAdjuster;
381
382 DiagnosticConsumer *DiagConsumer = nullptr;
383};
384
385template <typename T>
386std::unique_ptr<FrontendActionFactory> newFrontendActionFactory() {
387 class SimpleFrontendActionFactory : public FrontendActionFactory {
388 public:
389 FrontendAction *create() override { return new T; }
390 };
391
392 return std::unique_ptr<FrontendActionFactory>(
393 new SimpleFrontendActionFactory);
394}
395
396template <typename FactoryT>
397inline std::unique_ptr<FrontendActionFactory> newFrontendActionFactory(
398 FactoryT *ConsumerFactory, SourceFileCallbacks *Callbacks) {
399 class FrontendActionFactoryAdapter : public FrontendActionFactory {
400 public:
401 explicit FrontendActionFactoryAdapter(FactoryT *ConsumerFactory,
402 SourceFileCallbacks *Callbacks)
403 : ConsumerFactory(ConsumerFactory), Callbacks(Callbacks) {}
404
405 FrontendAction *create() override {
406 return new ConsumerFactoryAdaptor(ConsumerFactory, Callbacks);
407 }
408
409 private:
410 class ConsumerFactoryAdaptor : public ASTFrontendAction {
411 public:
412 ConsumerFactoryAdaptor(FactoryT *ConsumerFactory,
413 SourceFileCallbacks *Callbacks)
414 : ConsumerFactory(ConsumerFactory), Callbacks(Callbacks) {}
415
416 std::unique_ptr<ASTConsumer>
417 CreateASTConsumer(CompilerInstance &, StringRef) override {
418 return ConsumerFactory->newASTConsumer();
419 }
420
421 protected:
422 bool BeginSourceFileAction(CompilerInstance &CI) override {
423 if (!ASTFrontendAction::BeginSourceFileAction(CI))
424 return false;
425 if (Callbacks)
426 return Callbacks->handleBeginSource(CI);
427 return true;
428 }
429
430 void EndSourceFileAction() override {
431 if (Callbacks)
432 Callbacks->handleEndSource();
433 ASTFrontendAction::EndSourceFileAction();
434 }
435
436 private:
437 FactoryT *ConsumerFactory;
438 SourceFileCallbacks *Callbacks;
439 };
440 FactoryT *ConsumerFactory;
441 SourceFileCallbacks *Callbacks;
442 };
443
444 return std::unique_ptr<FrontendActionFactory>(
445 new FrontendActionFactoryAdapter(ConsumerFactory, Callbacks));
446}
447
448/// Returns the absolute path of \c File, by prepending it with
449/// the current directory if \c File is not absolute.
450///
451/// Otherwise returns \c File.
452/// If 'File' starts with "./", the returned path will not contain the "./".
453/// Otherwise, the returned path will contain the literal path-concatenation of
454/// the current directory and \c File.
455///
456/// The difference to llvm::sys::fs::make_absolute is the canonicalization this
457/// does by removing "./" and computing native paths.
458///
459/// \param File Either an absolute or relative path.
460std::string getAbsolutePath(StringRef File);
461
462/// Changes CommandLine to contain implicit flags that would have been
463/// defined had the compiler driver been invoked through the path InvokedAs.
464///
465/// For example, when called with \c InvokedAs set to `i686-linux-android-g++`,
466/// the arguments '-target', 'i686-linux-android`, `--driver-mode=g++` will
467/// be inserted after the first argument in \c CommandLine.
468///
469/// This function will not add new `-target` or `--driver-mode` flags if they
470/// are already present in `CommandLine` (even if they have different settings
471/// than would have been inserted).
472///
473/// \pre `llvm::InitializeAllTargets()` has been called.
474///
475/// \param CommandLine the command line used to invoke the compiler driver or
476/// Clang tool, including the path to the executable as \c CommandLine[0].
477/// \param InvokedAs the path to the driver used to infer implicit flags.
478///
479/// \note This will not set \c CommandLine[0] to \c InvokedAs. The tooling
480/// infrastructure expects that CommandLine[0] is a tool path relative to which
481/// the builtin headers can be found.
482void addTargetAndModeForProgramName(std::vector<std::string> &CommandLine,
483 StringRef InvokedAs);
484
485/// Creates a \c CompilerInvocation.
486CompilerInvocation *newInvocation(DiagnosticsEngine *Diagnostics,
487 const llvm::opt::ArgStringList &CC1Args);
488
489} // namespace tooling
490
491} // namespace clang
492
493#endif // LLVM_CLANG_TOOLING_TOOLING_H
494

Warning: That file was not part of the compilation database. It may have many parsing errors.