CompilerInstance.h revision 221345
1//===-- CompilerInstance.h - Clang Compiler Instance ------------*- 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#ifndef LLVM_CLANG_FRONTEND_COMPILERINSTANCE_H_
11#define LLVM_CLANG_FRONTEND_COMPILERINSTANCE_H_
12
13#include "clang/Frontend/CompilerInvocation.h"
14#include "llvm/ADT/IntrusiveRefCntPtr.h"
15#include "llvm/ADT/StringRef.h"
16#include "llvm/ADT/OwningPtr.h"
17#include <cassert>
18#include <list>
19#include <string>
20
21namespace llvm {
22class raw_ostream;
23class raw_fd_ostream;
24class Timer;
25}
26
27namespace clang {
28class ASTContext;
29class ASTConsumer;
30class CodeCompleteConsumer;
31class Diagnostic;
32class DiagnosticClient;
33class ExternalASTSource;
34class FileManager;
35class FrontendAction;
36class ASTReader;
37class Preprocessor;
38class Sema;
39class SourceManager;
40class TargetInfo;
41
42/// CompilerInstance - Helper class for managing a single instance of the Clang
43/// compiler.
44///
45/// The CompilerInstance serves two purposes:
46///  (1) It manages the various objects which are necessary to run the compiler,
47///      for example the preprocessor, the target information, and the AST
48///      context.
49///  (2) It provides utility routines for constructing and manipulating the
50///      common Clang objects.
51///
52/// The compiler instance generally owns the instance of all the objects that it
53/// manages. However, clients can still share objects by manually setting the
54/// object and retaking ownership prior to destroying the CompilerInstance.
55///
56/// The compiler instance is intended to simplify clients, but not to lock them
57/// in to the compiler instance for everything. When possible, utility functions
58/// come in two forms; a short form that reuses the CompilerInstance objects,
59/// and a long form that takes explicit instances of any required objects.
60class CompilerInstance {
61  /// The options used in this compiler instance.
62  llvm::IntrusiveRefCntPtr<CompilerInvocation> Invocation;
63
64  /// The diagnostics engine instance.
65  llvm::IntrusiveRefCntPtr<Diagnostic> Diagnostics;
66
67  /// The target being compiled for.
68  llvm::IntrusiveRefCntPtr<TargetInfo> Target;
69
70  /// The file manager.
71  llvm::IntrusiveRefCntPtr<FileManager> FileMgr;
72
73  /// The source manager.
74  llvm::IntrusiveRefCntPtr<SourceManager> SourceMgr;
75
76  /// The preprocessor.
77  llvm::IntrusiveRefCntPtr<Preprocessor> PP;
78
79  /// The AST context.
80  llvm::IntrusiveRefCntPtr<ASTContext> Context;
81
82  /// The AST consumer.
83  llvm::OwningPtr<ASTConsumer> Consumer;
84
85  /// The code completion consumer.
86  llvm::OwningPtr<CodeCompleteConsumer> CompletionConsumer;
87
88  /// \brief The semantic analysis object.
89  llvm::OwningPtr<Sema> TheSema;
90
91  /// The frontend timer
92  llvm::OwningPtr<llvm::Timer> FrontendTimer;
93
94  /// \brief Holds information about the output file.
95  ///
96  /// If TempFilename is not empty we must rename it to Filename at the end.
97  /// TempFilename may be empty and Filename non empty if creating the temporary
98  /// failed.
99  struct OutputFile {
100    std::string Filename;
101    std::string TempFilename;
102    llvm::raw_ostream *OS;
103
104    OutputFile(const std::string &filename, const std::string &tempFilename,
105               llvm::raw_ostream *os)
106      : Filename(filename), TempFilename(tempFilename), OS(os) { }
107  };
108
109  /// The list of active output files.
110  std::list<OutputFile> OutputFiles;
111
112  void operator=(const CompilerInstance &);  // DO NOT IMPLEMENT
113  CompilerInstance(const CompilerInstance&); // DO NOT IMPLEMENT
114public:
115  CompilerInstance();
116  ~CompilerInstance();
117
118  /// @name High-Level Operations
119  /// {
120
121  /// ExecuteAction - Execute the provided action against the compiler's
122  /// CompilerInvocation object.
123  ///
124  /// This function makes the following assumptions:
125  ///
126  ///  - The invocation options should be initialized. This function does not
127  ///    handle the '-help' or '-version' options, clients should handle those
128  ///    directly.
129  ///
130  ///  - The diagnostics engine should have already been created by the client.
131  ///
132  ///  - No other CompilerInstance state should have been initialized (this is
133  ///    an unchecked error).
134  ///
135  ///  - Clients should have initialized any LLVM target features that may be
136  ///    required.
137  ///
138  ///  - Clients should eventually call llvm_shutdown() upon the completion of
139  ///    this routine to ensure that any managed objects are properly destroyed.
140  ///
141  /// Note that this routine may write output to 'stderr'.
142  ///
143  /// \param Act - The action to execute.
144  /// \return - True on success.
145  //
146  // FIXME: This function should take the stream to write any debugging /
147  // verbose output to as an argument.
148  //
149  // FIXME: Eliminate the llvm_shutdown requirement, that should either be part
150  // of the context or else not CompilerInstance specific.
151  bool ExecuteAction(FrontendAction &Act);
152
153  /// }
154  /// @name Compiler Invocation and Options
155  /// {
156
157  bool hasInvocation() const { return Invocation != 0; }
158
159  CompilerInvocation &getInvocation() {
160    assert(Invocation && "Compiler instance has no invocation!");
161    return *Invocation;
162  }
163
164  /// setInvocation - Replace the current invocation.
165  void setInvocation(CompilerInvocation *Value);
166
167  /// }
168  /// @name Forwarding Methods
169  /// {
170
171  AnalyzerOptions &getAnalyzerOpts() {
172    return Invocation->getAnalyzerOpts();
173  }
174  const AnalyzerOptions &getAnalyzerOpts() const {
175    return Invocation->getAnalyzerOpts();
176  }
177
178  CodeGenOptions &getCodeGenOpts() {
179    return Invocation->getCodeGenOpts();
180  }
181  const CodeGenOptions &getCodeGenOpts() const {
182    return Invocation->getCodeGenOpts();
183  }
184
185  DependencyOutputOptions &getDependencyOutputOpts() {
186    return Invocation->getDependencyOutputOpts();
187  }
188  const DependencyOutputOptions &getDependencyOutputOpts() const {
189    return Invocation->getDependencyOutputOpts();
190  }
191
192  DiagnosticOptions &getDiagnosticOpts() {
193    return Invocation->getDiagnosticOpts();
194  }
195  const DiagnosticOptions &getDiagnosticOpts() const {
196    return Invocation->getDiagnosticOpts();
197  }
198
199  const FileSystemOptions &getFileSystemOpts() const {
200    return Invocation->getFileSystemOpts();
201  }
202
203  FrontendOptions &getFrontendOpts() {
204    return Invocation->getFrontendOpts();
205  }
206  const FrontendOptions &getFrontendOpts() const {
207    return Invocation->getFrontendOpts();
208  }
209
210  HeaderSearchOptions &getHeaderSearchOpts() {
211    return Invocation->getHeaderSearchOpts();
212  }
213  const HeaderSearchOptions &getHeaderSearchOpts() const {
214    return Invocation->getHeaderSearchOpts();
215  }
216
217  LangOptions &getLangOpts() {
218    return Invocation->getLangOpts();
219  }
220  const LangOptions &getLangOpts() const {
221    return Invocation->getLangOpts();
222  }
223
224  PreprocessorOptions &getPreprocessorOpts() {
225    return Invocation->getPreprocessorOpts();
226  }
227  const PreprocessorOptions &getPreprocessorOpts() const {
228    return Invocation->getPreprocessorOpts();
229  }
230
231  PreprocessorOutputOptions &getPreprocessorOutputOpts() {
232    return Invocation->getPreprocessorOutputOpts();
233  }
234  const PreprocessorOutputOptions &getPreprocessorOutputOpts() const {
235    return Invocation->getPreprocessorOutputOpts();
236  }
237
238  TargetOptions &getTargetOpts() {
239    return Invocation->getTargetOpts();
240  }
241  const TargetOptions &getTargetOpts() const {
242    return Invocation->getTargetOpts();
243  }
244
245  /// }
246  /// @name Diagnostics Engine
247  /// {
248
249  bool hasDiagnostics() const { return Diagnostics != 0; }
250
251  /// Get the current diagnostics engine.
252  Diagnostic &getDiagnostics() const {
253    assert(Diagnostics && "Compiler instance has no diagnostics!");
254    return *Diagnostics;
255  }
256
257  /// setDiagnostics - Replace the current diagnostics engine.
258  void setDiagnostics(Diagnostic *Value);
259
260  DiagnosticClient &getDiagnosticClient() const {
261    assert(Diagnostics && Diagnostics->getClient() &&
262           "Compiler instance has no diagnostic client!");
263    return *Diagnostics->getClient();
264  }
265
266  /// }
267  /// @name Target Info
268  /// {
269
270  bool hasTarget() const { return Target != 0; }
271
272  TargetInfo &getTarget() const {
273    assert(Target && "Compiler instance has no target!");
274    return *Target;
275  }
276
277  /// Replace the current diagnostics engine.
278  void setTarget(TargetInfo *Value);
279
280  /// }
281  /// @name File Manager
282  /// {
283
284  bool hasFileManager() const { return FileMgr != 0; }
285
286  /// Return the current file manager to the caller.
287  FileManager &getFileManager() const {
288    assert(FileMgr && "Compiler instance has no file manager!");
289    return *FileMgr;
290  }
291
292  void resetAndLeakFileManager() {
293    FileMgr.resetWithoutRelease();
294  }
295
296  /// setFileManager - Replace the current file manager.
297  void setFileManager(FileManager *Value);
298
299  /// }
300  /// @name Source Manager
301  /// {
302
303  bool hasSourceManager() const { return SourceMgr != 0; }
304
305  /// Return the current source manager.
306  SourceManager &getSourceManager() const {
307    assert(SourceMgr && "Compiler instance has no source manager!");
308    return *SourceMgr;
309  }
310
311  void resetAndLeakSourceManager() {
312    SourceMgr.resetWithoutRelease();
313  }
314
315  /// setSourceManager - Replace the current source manager.
316  void setSourceManager(SourceManager *Value);
317
318  /// }
319  /// @name Preprocessor
320  /// {
321
322  bool hasPreprocessor() const { return PP != 0; }
323
324  /// Return the current preprocessor.
325  Preprocessor &getPreprocessor() const {
326    assert(PP && "Compiler instance has no preprocessor!");
327    return *PP;
328  }
329
330  void resetAndLeakPreprocessor() {
331    PP.resetWithoutRelease();
332  }
333
334  /// Replace the current preprocessor.
335  void setPreprocessor(Preprocessor *Value);
336
337  /// }
338  /// @name ASTContext
339  /// {
340
341  bool hasASTContext() const { return Context != 0; }
342
343  ASTContext &getASTContext() const {
344    assert(Context && "Compiler instance has no AST context!");
345    return *Context;
346  }
347
348  void resetAndLeakASTContext() {
349    Context.resetWithoutRelease();
350  }
351
352  /// setASTContext - Replace the current AST context.
353  void setASTContext(ASTContext *Value);
354
355  /// \brief Replace the current Sema; the compiler instance takes ownership
356  /// of S.
357  void setSema(Sema *S);
358
359  /// }
360  /// @name ASTConsumer
361  /// {
362
363  bool hasASTConsumer() const { return Consumer != 0; }
364
365  ASTConsumer &getASTConsumer() const {
366    assert(Consumer && "Compiler instance has no AST consumer!");
367    return *Consumer;
368  }
369
370  /// takeASTConsumer - Remove the current AST consumer and give ownership to
371  /// the caller.
372  ASTConsumer *takeASTConsumer() { return Consumer.take(); }
373
374  /// setASTConsumer - Replace the current AST consumer; the compiler instance
375  /// takes ownership of \arg Value.
376  void setASTConsumer(ASTConsumer *Value);
377
378  /// }
379  /// @name Semantic analysis
380  /// {
381  bool hasSema() const { return TheSema != 0; }
382
383  Sema &getSema() const {
384    assert(TheSema && "Compiler instance has no Sema object!");
385    return *TheSema;
386  }
387
388  Sema *takeSema() { return TheSema.take(); }
389
390  /// }
391  /// @name Code Completion
392  /// {
393
394  bool hasCodeCompletionConsumer() const { return CompletionConsumer != 0; }
395
396  CodeCompleteConsumer &getCodeCompletionConsumer() const {
397    assert(CompletionConsumer &&
398           "Compiler instance has no code completion consumer!");
399    return *CompletionConsumer;
400  }
401
402  /// takeCodeCompletionConsumer - Remove the current code completion consumer
403  /// and give ownership to the caller.
404  CodeCompleteConsumer *takeCodeCompletionConsumer() {
405    return CompletionConsumer.take();
406  }
407
408  /// setCodeCompletionConsumer - Replace the current code completion consumer;
409  /// the compiler instance takes ownership of \arg Value.
410  void setCodeCompletionConsumer(CodeCompleteConsumer *Value);
411
412  /// }
413  /// @name Frontend timer
414  /// {
415
416  bool hasFrontendTimer() const { return FrontendTimer != 0; }
417
418  llvm::Timer &getFrontendTimer() const {
419    assert(FrontendTimer && "Compiler instance has no frontend timer!");
420    return *FrontendTimer;
421  }
422
423  /// }
424  /// @name Output Files
425  /// {
426
427  /// addOutputFile - Add an output file onto the list of tracked output files.
428  ///
429  /// \param OutFile - The output file info.
430  void addOutputFile(const OutputFile &OutFile);
431
432  /// clearOutputFiles - Clear the output file list, destroying the contained
433  /// output streams.
434  ///
435  /// \param EraseFiles - If true, attempt to erase the files from disk.
436  void clearOutputFiles(bool EraseFiles);
437
438  /// }
439  /// @name Construction Utility Methods
440  /// {
441
442  /// Create the diagnostics engine using the invocation's diagnostic options
443  /// and replace any existing one with it.
444  ///
445  /// Note that this routine also replaces the diagnostic client,
446  /// allocating one if one is not provided.
447  ///
448  /// \param Client If non-NULL, a diagnostic client that will be
449  /// attached to (and, then, owned by) the Diagnostic inside this AST
450  /// unit.
451  void createDiagnostics(int Argc, const char* const *Argv,
452                         DiagnosticClient *Client = 0);
453
454  /// Create a Diagnostic object with a the TextDiagnosticPrinter.
455  ///
456  /// The \arg Argc and \arg Argv arguments are used only for logging purposes,
457  /// when the diagnostic options indicate that the compiler should output
458  /// logging information.
459  ///
460  /// If no diagnostic client is provided, this creates a
461  /// DiagnosticClient that is owned by the returned diagnostic
462  /// object, if using directly the caller is responsible for
463  /// releasing the returned Diagnostic's client eventually.
464  ///
465  /// \param Opts - The diagnostic options; note that the created text
466  /// diagnostic object contains a reference to these options and its lifetime
467  /// must extend past that of the diagnostic engine.
468  ///
469  /// \param Client If non-NULL, a diagnostic client that will be
470  /// attached to (and, then, owned by) the returned Diagnostic
471  /// object.
472  ///
473  /// \param CodeGenOpts If non-NULL, the code gen options in use, which may be
474  /// used by some diagnostics printers (for logging purposes only).
475  ///
476  /// \return The new object on success, or null on failure.
477  static llvm::IntrusiveRefCntPtr<Diagnostic>
478  createDiagnostics(const DiagnosticOptions &Opts, int Argc,
479                    const char* const *Argv,
480                    DiagnosticClient *Client = 0,
481                    const CodeGenOptions *CodeGenOpts = 0);
482
483  /// Create the file manager and replace any existing one with it.
484  void createFileManager();
485
486  /// Create the source manager and replace any existing one with it.
487  void createSourceManager(FileManager &FileMgr);
488
489  /// Create the preprocessor, using the invocation, file, and source managers,
490  /// and replace any existing one with it.
491  void createPreprocessor();
492
493  /// Create a Preprocessor object.
494  ///
495  /// Note that this also creates a new HeaderSearch object which will be owned
496  /// by the resulting Preprocessor.
497  ///
498  /// \return The new object on success, or null on failure.
499  static Preprocessor *createPreprocessor(Diagnostic &, const LangOptions &,
500                                          const PreprocessorOptions &,
501                                          const HeaderSearchOptions &,
502                                          const DependencyOutputOptions &,
503                                          const TargetInfo &,
504                                          const FrontendOptions &,
505                                          SourceManager &, FileManager &);
506
507  /// Create the AST context.
508  void createASTContext();
509
510  /// Create an external AST source to read a PCH file and attach it to the AST
511  /// context.
512  void createPCHExternalASTSource(llvm::StringRef Path,
513                                  bool DisablePCHValidation,
514                                  bool DisableStatCache,
515                                  void *DeserializationListener);
516
517  /// Create an external AST source to read a PCH file.
518  ///
519  /// \return - The new object on success, or null on failure.
520  static ExternalASTSource *
521  createPCHExternalASTSource(llvm::StringRef Path, const std::string &Sysroot,
522                             bool DisablePCHValidation,
523                             bool DisableStatCache,
524                             Preprocessor &PP, ASTContext &Context,
525                             void *DeserializationListener, bool Preamble);
526
527  /// Create a code completion consumer using the invocation; note that this
528  /// will cause the source manager to truncate the input source file at the
529  /// completion point.
530  void createCodeCompletionConsumer();
531
532  /// Create a code completion consumer to print code completion results, at
533  /// \arg Filename, \arg Line, and \arg Column, to the given output stream \arg
534  /// OS.
535  static CodeCompleteConsumer *
536  createCodeCompletionConsumer(Preprocessor &PP, const std::string &Filename,
537                               unsigned Line, unsigned Column,
538                               bool ShowMacros,
539                               bool ShowCodePatterns, bool ShowGlobals,
540                               llvm::raw_ostream &OS);
541
542  /// \brief Create the Sema object to be used for parsing.
543  void createSema(bool CompleteTranslationUnit,
544                  CodeCompleteConsumer *CompletionConsumer);
545
546  /// Create the frontend timer and replace any existing one with it.
547  void createFrontendTimer();
548
549  /// Create the default output file (from the invocation's options) and add it
550  /// to the list of tracked output files.
551  ///
552  /// \return - Null on error.
553  llvm::raw_fd_ostream *
554  createDefaultOutputFile(bool Binary = true, llvm::StringRef BaseInput = "",
555                          llvm::StringRef Extension = "");
556
557  /// Create a new output file and add it to the list of tracked output files,
558  /// optionally deriving the output path name.
559  ///
560  /// \return - Null on error.
561  llvm::raw_fd_ostream *
562  createOutputFile(llvm::StringRef OutputPath,
563                   bool Binary = true, bool RemoveFileOnSignal = true,
564                   llvm::StringRef BaseInput = "",
565                   llvm::StringRef Extension = "");
566
567  /// Create a new output file, optionally deriving the output path name.
568  ///
569  /// If \arg OutputPath is empty, then createOutputFile will derive an output
570  /// path location as \arg BaseInput, with any suffix removed, and \arg
571  /// Extension appended. If OutputPath is not stdout createOutputFile will
572  /// create a new temporary file that must be renamed to OutputPath in the end.
573  ///
574  /// \param OutputPath - If given, the path to the output file.
575  /// \param Error [out] - On failure, the error message.
576  /// \param BaseInput - If \arg OutputPath is empty, the input path name to use
577  /// for deriving the output path.
578  /// \param Extension - The extension to use for derived output names.
579  /// \param Binary - The mode to open the file in.
580  /// \param RemoveFileOnSignal - Whether the file should be registered with
581  /// llvm::sys::RemoveFileOnSignal. Note that this is not safe for
582  /// multithreaded use, as the underlying signal mechanism is not reentrant
583  /// \param ResultPathName [out] - If given, the result path name will be
584  /// stored here on success.
585  /// \param TempPathName [out] - If given, the temporary file path name
586  /// will be stored here on success.
587  static llvm::raw_fd_ostream *
588  createOutputFile(llvm::StringRef OutputPath, std::string &Error,
589                   bool Binary = true, bool RemoveFileOnSignal = true,
590                   llvm::StringRef BaseInput = "",
591                   llvm::StringRef Extension = "",
592                   std::string *ResultPathName = 0,
593                   std::string *TempPathName = 0);
594
595  /// }
596  /// @name Initialization Utility Methods
597  /// {
598
599  /// InitializeSourceManager - Initialize the source manager to set InputFile
600  /// as the main file.
601  ///
602  /// \return True on success.
603  bool InitializeSourceManager(llvm::StringRef InputFile);
604
605  /// InitializeSourceManager - Initialize the source manager to set InputFile
606  /// as the main file.
607  ///
608  /// \return True on success.
609  static bool InitializeSourceManager(llvm::StringRef InputFile,
610                                      Diagnostic &Diags,
611                                      FileManager &FileMgr,
612                                      SourceManager &SourceMgr,
613                                      const FrontendOptions &Opts);
614
615  /// }
616};
617
618} // end namespace clang
619
620#endif
621