1//===--- Utils.h - Misc utilities for the front-end -------------*- 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 header contains miscellaneous utilities for various front-end actions.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_CLANG_FRONTEND_UTILS_H
15#define LLVM_CLANG_FRONTEND_UTILS_H
16
17#include "clang/Basic/Diagnostic.h"
18#include "clang/Basic/VirtualFileSystem.h"
19#include "llvm/ADT/IntrusiveRefCntPtr.h"
20#include "llvm/ADT/StringRef.h"
21#include "llvm/ADT/StringSet.h"
22#include "llvm/Option/OptSpecifier.h"
23
24namespace llvm {
25class raw_fd_ostream;
26class Triple;
27
28namespace opt {
29class ArgList;
30}
31}
32
33namespace clang {
34class ASTConsumer;
35class ASTReader;
36class CompilerInstance;
37class CompilerInvocation;
38class Decl;
39class DependencyOutputOptions;
40class DiagnosticsEngine;
41class DiagnosticOptions;
42class ExternalSemaSource;
43class FileManager;
44class HeaderSearch;
45class HeaderSearchOptions;
46class IdentifierTable;
47class LangOptions;
48class Preprocessor;
49class PreprocessorOptions;
50class PreprocessorOutputOptions;
51class SourceManager;
52class Stmt;
53class TargetInfo;
54class FrontendOptions;
55
56/// Apply the header search options to get given HeaderSearch object.
57void ApplyHeaderSearchOptions(HeaderSearch &HS,
58                              const HeaderSearchOptions &HSOpts,
59                              const LangOptions &Lang,
60                              const llvm::Triple &triple);
61
62/// InitializePreprocessor - Initialize the preprocessor getting it and the
63/// environment ready to process a single file.
64void InitializePreprocessor(Preprocessor &PP,
65                            const PreprocessorOptions &PPOpts,
66                            const FrontendOptions &FEOpts);
67
68/// DoPrintPreprocessedInput - Implement -E mode.
69void DoPrintPreprocessedInput(Preprocessor &PP, raw_ostream* OS,
70                              const PreprocessorOutputOptions &Opts);
71
72/// An interface for collecting the dependencies of a compilation. Users should
73/// use \c attachToPreprocessor and \c attachToASTReader to get all of the
74/// dependencies.
75// FIXME: Migrate DependencyFileGen, DependencyGraphGen, ModuleDepCollectory to
76// use this interface.
77class DependencyCollector {
78public:
79  void attachToPreprocessor(Preprocessor &PP);
80  void attachToASTReader(ASTReader &R);
81  llvm::ArrayRef<std::string> getDependencies() const { return Dependencies; }
82
83  /// Called when a new file is seen. Return true if \p Filename should be added
84  /// to the list of dependencies.
85  ///
86  /// The default implementation ignores <built-in> and system files.
87  virtual bool sawDependency(StringRef Filename, bool FromModule,
88                             bool IsSystem, bool IsModuleFile, bool IsMissing);
89  /// Called when the end of the main file is reached.
90  virtual void finishedMainFile() { }
91  /// Return true if system files should be passed to sawDependency().
92  virtual bool needSystemDependencies() { return false; }
93  virtual ~DependencyCollector();
94
95public: // implementation detail
96  /// Add a dependency \p Filename if it has not been seen before and
97  /// sawDependency() returns true.
98  void maybeAddDependency(StringRef Filename, bool FromModule, bool IsSystem,
99                          bool IsModuleFile, bool IsMissing);
100private:
101  llvm::StringSet<> Seen;
102  std::vector<std::string> Dependencies;
103};
104
105/// Builds a depdenency file when attached to a Preprocessor (for includes) and
106/// ASTReader (for module imports), and writes it out at the end of processing
107/// a source file.  Users should attach to the ast reader whenever a module is
108/// loaded.
109class DependencyFileGenerator {
110  void *Impl; // Opaque implementation
111  DependencyFileGenerator(void *Impl);
112public:
113  static DependencyFileGenerator *CreateAndAttachToPreprocessor(
114    Preprocessor &PP, const DependencyOutputOptions &Opts);
115  void AttachToASTReader(ASTReader &R);
116};
117
118/// Collects the dependencies for imported modules into a directory.  Users
119/// should attach to the AST reader whenever a module is loaded.
120class ModuleDependencyCollector {
121  std::string DestDir;
122  bool HasErrors;
123  llvm::StringSet<> Seen;
124  vfs::YAMLVFSWriter VFSWriter;
125
126public:
127  StringRef getDest() { return DestDir; }
128  bool insertSeen(StringRef Filename) { return Seen.insert(Filename); }
129  void setHasErrors() { HasErrors = true; }
130  void addFileMapping(StringRef VPath, StringRef RPath) {
131    VFSWriter.addFileMapping(VPath, RPath);
132  }
133
134  void attachToASTReader(ASTReader &R);
135  void writeFileMap();
136  bool hasErrors() { return HasErrors; }
137  ModuleDependencyCollector(std::string DestDir)
138      : DestDir(DestDir), HasErrors(false) {}
139  ~ModuleDependencyCollector() { writeFileMap(); }
140};
141
142/// AttachDependencyGraphGen - Create a dependency graph generator, and attach
143/// it to the given preprocessor.
144  void AttachDependencyGraphGen(Preprocessor &PP, StringRef OutputFile,
145                                StringRef SysRoot);
146
147/// AttachHeaderIncludeGen - Create a header include list generator, and attach
148/// it to the given preprocessor.
149///
150/// \param ShowAllHeaders - If true, show all header information instead of just
151/// headers following the predefines buffer. This is useful for making sure
152/// includes mentioned on the command line are also reported, but differs from
153/// the default behavior used by -H.
154/// \param OutputPath - If non-empty, a path to write the header include
155/// information to, instead of writing to stderr.
156/// \param ShowDepth - Whether to indent to show the nesting of the includes.
157/// \param MSStyle - Whether to print in cl.exe /showIncludes style.
158void AttachHeaderIncludeGen(Preprocessor &PP, bool ShowAllHeaders = false,
159                            StringRef OutputPath = "",
160                            bool ShowDepth = true, bool MSStyle = false);
161
162/// CacheTokens - Cache tokens for use with PCH. Note that this requires
163/// a seekable stream.
164void CacheTokens(Preprocessor &PP, llvm::raw_fd_ostream* OS);
165
166/// The ChainedIncludesSource class converts headers to chained PCHs in
167/// memory, mainly for testing.
168IntrusiveRefCntPtr<ExternalSemaSource>
169createChainedIncludesSource(CompilerInstance &CI,
170                            IntrusiveRefCntPtr<ExternalSemaSource> &Reader);
171
172/// createInvocationFromCommandLine - Construct a compiler invocation object for
173/// a command line argument vector.
174///
175/// \return A CompilerInvocation, or 0 if none was built for the given
176/// argument vector.
177CompilerInvocation *
178createInvocationFromCommandLine(ArrayRef<const char *> Args,
179                            IntrusiveRefCntPtr<DiagnosticsEngine> Diags =
180                                IntrusiveRefCntPtr<DiagnosticsEngine>());
181
182/// Return the value of the last argument as an integer, or a default. If Diags
183/// is non-null, emits an error if the argument is given, but non-integral.
184int getLastArgIntValue(const llvm::opt::ArgList &Args,
185                       llvm::opt::OptSpecifier Id, int Default,
186                       DiagnosticsEngine *Diags = nullptr);
187
188inline int getLastArgIntValue(const llvm::opt::ArgList &Args,
189                              llvm::opt::OptSpecifier Id, int Default,
190                              DiagnosticsEngine &Diags) {
191  return getLastArgIntValue(Args, Id, Default, &Diags);
192}
193
194uint64_t getLastArgUInt64Value(const llvm::opt::ArgList &Args,
195                               llvm::opt::OptSpecifier Id, uint64_t Default,
196                               DiagnosticsEngine *Diags = nullptr);
197
198inline uint64_t getLastArgUInt64Value(const llvm::opt::ArgList &Args,
199                                      llvm::opt::OptSpecifier Id,
200                                      uint64_t Default,
201                                      DiagnosticsEngine &Diags) {
202  return getLastArgUInt64Value(Args, Id, Default, &Diags);
203}
204
205// When Clang->getFrontendOpts().DisableFree is set we don't delete some of the
206// global objects, but we don't want LeakDetectors to complain, so we bury them
207// in a globally visible array.
208void BuryPointer(const void *Ptr);
209
210} // end namespace clang
211
212#endif
213