Subversion Repositories QNX 8.QNX8 LLVM/Clang compiler suite

Rev

Blame | Last modification | View Log | Download | RSS feed

  1. //===- CompilationDatabase.h ------------------------------------*- C++ -*-===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. //
  9. //  This file provides an interface and multiple implementations for
  10. //  CompilationDatabases.
  11. //
  12. //  While C++ refactoring and analysis tools are not compilers, and thus
  13. //  don't run as part of the build system, they need the exact information
  14. //  of a build in order to be able to correctly understand the C++ code of
  15. //  the project. This information is provided via the CompilationDatabase
  16. //  interface.
  17. //
  18. //  To create a CompilationDatabase from a build directory one can call
  19. //  CompilationDatabase::loadFromDirectory(), which deduces the correct
  20. //  compilation database from the root of the build tree.
  21. //
  22. //  See the concrete subclasses of CompilationDatabase for currently supported
  23. //  formats.
  24. //
  25. //===----------------------------------------------------------------------===//
  26.  
  27. #ifndef LLVM_CLANG_TOOLING_COMPILATIONDATABASE_H
  28. #define LLVM_CLANG_TOOLING_COMPILATIONDATABASE_H
  29.  
  30. #include "clang/Basic/LLVM.h"
  31. #include "llvm/ADT/ArrayRef.h"
  32. #include "llvm/ADT/StringRef.h"
  33. #include "llvm/ADT/Twine.h"
  34. #include "llvm/Support/VirtualFileSystem.h"
  35. #include <memory>
  36. #include <string>
  37. #include <utility>
  38. #include <vector>
  39.  
  40. namespace clang {
  41. namespace tooling {
  42.  
  43. /// Specifies the working directory and command of a compilation.
  44. struct CompileCommand {
  45.   CompileCommand() = default;
  46.   CompileCommand(const Twine &Directory, const Twine &Filename,
  47.                  std::vector<std::string> CommandLine, const Twine &Output)
  48.       : Directory(Directory.str()), Filename(Filename.str()),
  49.         CommandLine(std::move(CommandLine)), Output(Output.str()) {}
  50.  
  51.   /// The working directory the command was executed from.
  52.   std::string Directory;
  53.  
  54.   /// The source file associated with the command.
  55.   std::string Filename;
  56.  
  57.   /// The command line that was executed.
  58.   std::vector<std::string> CommandLine;
  59.  
  60.   /// The output file associated with the command.
  61.   std::string Output;
  62.  
  63.   /// If this compile command was guessed rather than read from an authoritative
  64.   /// source, a short human-readable explanation.
  65.   /// e.g. "inferred from foo/bar.h".
  66.   std::string Heuristic;
  67.  
  68.   friend bool operator==(const CompileCommand &LHS, const CompileCommand &RHS) {
  69.     return LHS.Directory == RHS.Directory && LHS.Filename == RHS.Filename &&
  70.            LHS.CommandLine == RHS.CommandLine && LHS.Output == RHS.Output &&
  71.            LHS.Heuristic == RHS.Heuristic;
  72.   }
  73.  
  74.   friend bool operator!=(const CompileCommand &LHS, const CompileCommand &RHS) {
  75.     return !(LHS == RHS);
  76.   }
  77. };
  78.  
  79. /// Interface for compilation databases.
  80. ///
  81. /// A compilation database allows the user to retrieve compile command lines
  82. /// for the files in a project.
  83. ///
  84. /// Many implementations are enumerable, allowing all command lines to be
  85. /// retrieved. These can be used to run clang tools over a subset of the files
  86. /// in a project.
  87. class CompilationDatabase {
  88. public:
  89.   virtual ~CompilationDatabase();
  90.  
  91.   /// Loads a compilation database from a build directory.
  92.   ///
  93.   /// Looks at the specified 'BuildDirectory' and creates a compilation database
  94.   /// that allows to query compile commands for source files in the
  95.   /// corresponding source tree.
  96.   ///
  97.   /// Returns NULL and sets ErrorMessage if we were not able to build up a
  98.   /// compilation database for the build directory.
  99.   ///
  100.   /// FIXME: Currently only supports JSON compilation databases, which
  101.   /// are named 'compile_commands.json' in the given directory. Extend this
  102.   /// for other build types (like ninja build files).
  103.   static std::unique_ptr<CompilationDatabase>
  104.   loadFromDirectory(StringRef BuildDirectory, std::string &ErrorMessage);
  105.  
  106.   /// Tries to detect a compilation database location and load it.
  107.   ///
  108.   /// Looks for a compilation database in all parent paths of file 'SourceFile'
  109.   /// by calling loadFromDirectory.
  110.   static std::unique_ptr<CompilationDatabase>
  111.   autoDetectFromSource(StringRef SourceFile, std::string &ErrorMessage);
  112.  
  113.   /// Tries to detect a compilation database location and load it.
  114.   ///
  115.   /// Looks for a compilation database in directory 'SourceDir' and all
  116.   /// its parent paths by calling loadFromDirectory.
  117.   static std::unique_ptr<CompilationDatabase>
  118.   autoDetectFromDirectory(StringRef SourceDir, std::string &ErrorMessage);
  119.  
  120.   /// Returns all compile commands in which the specified file was
  121.   /// compiled.
  122.   ///
  123.   /// This includes compile commands that span multiple source files.
  124.   /// For example, consider a project with the following compilations:
  125.   /// $ clang++ -o test a.cc b.cc t.cc
  126.   /// $ clang++ -o production a.cc b.cc -DPRODUCTION
  127.   /// A compilation database representing the project would return both command
  128.   /// lines for a.cc and b.cc and only the first command line for t.cc.
  129.   virtual std::vector<CompileCommand> getCompileCommands(
  130.       StringRef FilePath) const = 0;
  131.  
  132.   /// Returns the list of all files available in the compilation database.
  133.   ///
  134.   /// By default, returns nothing. Implementations should override this if they
  135.   /// can enumerate their source files.
  136.   virtual std::vector<std::string> getAllFiles() const { return {}; }
  137.  
  138.   /// Returns all compile commands for all the files in the compilation
  139.   /// database.
  140.   ///
  141.   /// FIXME: Add a layer in Tooling that provides an interface to run a tool
  142.   /// over all files in a compilation database. Not all build systems have the
  143.   /// ability to provide a feasible implementation for \c getAllCompileCommands.
  144.   ///
  145.   /// By default, this is implemented in terms of getAllFiles() and
  146.   /// getCompileCommands(). Subclasses may override this for efficiency.
  147.   virtual std::vector<CompileCommand> getAllCompileCommands() const;
  148. };
  149.  
  150. /// A compilation database that returns a single compile command line.
  151. ///
  152. /// Useful when we want a tool to behave more like a compiler invocation.
  153. /// This compilation database is not enumerable: getAllFiles() returns {}.
  154. class FixedCompilationDatabase : public CompilationDatabase {
  155. public:
  156.   /// Creates a FixedCompilationDatabase from the arguments after "--".
  157.   ///
  158.   /// Parses the given command line for "--". If "--" is found, the rest of
  159.   /// the arguments will make up the command line in the returned
  160.   /// FixedCompilationDatabase.
  161.   /// The arguments after "--" must not include positional parameters or the
  162.   /// argv[0] of the tool. Those will be added by the FixedCompilationDatabase
  163.   /// when a CompileCommand is requested. The argv[0] of the returned command
  164.   /// line will be "clang-tool".
  165.   ///
  166.   /// Returns NULL in case "--" is not found.
  167.   ///
  168.   /// The argument list is meant to be compatible with normal llvm command line
  169.   /// parsing in main methods.
  170.   /// int main(int argc, char **argv) {
  171.   ///   std::unique_ptr<FixedCompilationDatabase> Compilations(
  172.   ///     FixedCompilationDatabase::loadFromCommandLine(argc, argv));
  173.   ///   cl::ParseCommandLineOptions(argc, argv);
  174.   ///   ...
  175.   /// }
  176.   ///
  177.   /// \param Argc The number of command line arguments - will be changed to
  178.   /// the number of arguments before "--", if "--" was found in the argument
  179.   /// list.
  180.   /// \param Argv Points to the command line arguments.
  181.   /// \param ErrorMsg Contains error text if the function returns null pointer.
  182.   /// \param Directory The base directory used in the FixedCompilationDatabase.
  183.   static std::unique_ptr<FixedCompilationDatabase>
  184.   loadFromCommandLine(int &Argc, const char *const *Argv, std::string &ErrorMsg,
  185.                       const Twine &Directory = ".");
  186.  
  187.   /// Reads flags from the given file, one-per-line.
  188.   /// Returns nullptr and sets ErrorMessage if we can't read the file.
  189.   static std::unique_ptr<FixedCompilationDatabase>
  190.   loadFromFile(StringRef Path, std::string &ErrorMsg);
  191.  
  192.   /// Reads flags from the given buffer, one-per-line.
  193.   /// Directory is the command CWD, typically the parent of compile_flags.txt.
  194.   static std::unique_ptr<FixedCompilationDatabase>
  195.   loadFromBuffer(StringRef Directory, StringRef Data, std::string &ErrorMsg);
  196.  
  197.   /// Constructs a compilation data base from a specified directory
  198.   /// and command line.
  199.   FixedCompilationDatabase(const Twine &Directory,
  200.                            ArrayRef<std::string> CommandLine);
  201.  
  202.   /// Returns the given compile command.
  203.   ///
  204.   /// Will always return a vector with one entry that contains the directory
  205.   /// and command line specified at construction with "clang-tool" as argv[0]
  206.   /// and 'FilePath' as positional argument.
  207.   std::vector<CompileCommand>
  208.   getCompileCommands(StringRef FilePath) const override;
  209.  
  210. private:
  211.   /// This is built up to contain a single entry vector to be returned from
  212.   /// getCompileCommands after adding the positional argument.
  213.   std::vector<CompileCommand> CompileCommands;
  214. };
  215.  
  216. /// Transforms a compile command so that it applies the same configuration to
  217. /// a different file. Most args are left intact, but tweaks may be needed
  218. /// to certain flags (-x, -std etc).
  219. ///
  220. /// The output command will always end in {"--", Filename}.
  221. tooling::CompileCommand transferCompileCommand(tooling::CompileCommand,
  222.                                                StringRef Filename);
  223.  
  224. /// Returns a wrapped CompilationDatabase that defers to the provided one,
  225. /// but getCompileCommands() will infer commands for unknown files.
  226. /// The return value of getAllFiles() or getAllCompileCommands() is unchanged.
  227. /// See InterpolatingCompilationDatabase.cpp for details on heuristics.
  228. std::unique_ptr<CompilationDatabase>
  229.     inferMissingCompileCommands(std::unique_ptr<CompilationDatabase>);
  230.  
  231. /// Returns a wrapped CompilationDatabase that will add -target and -mode flags
  232. /// to commandline when they can be deduced from argv[0] of commandline returned
  233. /// by underlying database.
  234. std::unique_ptr<CompilationDatabase>
  235. inferTargetAndDriverMode(std::unique_ptr<CompilationDatabase> Base);
  236.  
  237. /// Returns a wrapped CompilationDatabase that will expand all rsp(response)
  238. /// files on commandline returned by underlying database.
  239. std::unique_ptr<CompilationDatabase>
  240. expandResponseFiles(std::unique_ptr<CompilationDatabase> Base,
  241.                     llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS);
  242.  
  243. } // namespace tooling
  244. } // namespace clang
  245.  
  246. #endif // LLVM_CLANG_TOOLING_COMPILATIONDATABASE_H
  247.