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