xref: /freebsd/contrib/llvm-project/clang/include/clang/Frontend/CompilerInstance.h (revision 700637cbb5e582861067a11aaca4d053546871d2)
1 //===-- CompilerInstance.h - Clang Compiler Instance ------------*- 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 #ifndef LLVM_CLANG_FRONTEND_COMPILERINSTANCE_H_
10 #define LLVM_CLANG_FRONTEND_COMPILERINSTANCE_H_
11 
12 #include "clang/AST/ASTConsumer.h"
13 #include "clang/Basic/Diagnostic.h"
14 #include "clang/Basic/SourceManager.h"
15 #include "clang/Basic/TargetInfo.h"
16 #include "clang/Frontend/CompilerInvocation.h"
17 #include "clang/Frontend/PCHContainerOperations.h"
18 #include "clang/Frontend/Utils.h"
19 #include "clang/Lex/DependencyDirectivesScanner.h"
20 #include "clang/Lex/HeaderSearchOptions.h"
21 #include "clang/Lex/ModuleLoader.h"
22 #include "llvm/ADT/ArrayRef.h"
23 #include "llvm/ADT/DenseMap.h"
24 #include "llvm/ADT/IntrusiveRefCntPtr.h"
25 #include "llvm/ADT/StringRef.h"
26 #include "llvm/Support/BuryPointer.h"
27 #include "llvm/Support/FileSystem.h"
28 #include "llvm/Support/VirtualFileSystem.h"
29 #include <cassert>
30 #include <list>
31 #include <memory>
32 #include <optional>
33 #include <string>
34 #include <utility>
35 
36 namespace llvm {
37 class raw_fd_ostream;
38 class Timer;
39 class TimerGroup;
40 }
41 
42 namespace clang {
43 class ASTContext;
44 class ASTReader;
45 
46 namespace serialization {
47 class ModuleFile;
48 }
49 
50 class CodeCompleteConsumer;
51 class DiagnosticsEngine;
52 class DiagnosticConsumer;
53 class FileManager;
54 class FrontendAction;
55 class Module;
56 class ModuleCache;
57 class Preprocessor;
58 class Sema;
59 class SourceManager;
60 class TargetInfo;
61 enum class DisableValidationForModuleKind;
62 
63 /// CompilerInstance - Helper class for managing a single instance of the Clang
64 /// compiler.
65 ///
66 /// The CompilerInstance serves two purposes:
67 ///  (1) It manages the various objects which are necessary to run the compiler,
68 ///      for example the preprocessor, the target information, and the AST
69 ///      context.
70 ///  (2) It provides utility routines for constructing and manipulating the
71 ///      common Clang objects.
72 ///
73 /// The compiler instance generally owns the instance of all the objects that it
74 /// manages. However, clients can still share objects by manually setting the
75 /// object and retaking ownership prior to destroying the CompilerInstance.
76 ///
77 /// The compiler instance is intended to simplify clients, but not to lock them
78 /// in to the compiler instance for everything. When possible, utility functions
79 /// come in two forms; a short form that reuses the CompilerInstance objects,
80 /// and a long form that takes explicit instances of any required objects.
81 class CompilerInstance : public ModuleLoader {
82   /// The options used in this compiler instance.
83   std::shared_ptr<CompilerInvocation> Invocation;
84 
85   /// The diagnostics engine instance.
86   IntrusiveRefCntPtr<DiagnosticsEngine> Diagnostics;
87 
88   /// The target being compiled for.
89   IntrusiveRefCntPtr<TargetInfo> Target;
90 
91   /// Options for the auxiliary target.
92   std::unique_ptr<TargetOptions> AuxTargetOpts;
93 
94   /// Auxiliary Target info.
95   IntrusiveRefCntPtr<TargetInfo> AuxTarget;
96 
97   /// The file manager.
98   IntrusiveRefCntPtr<FileManager> FileMgr;
99 
100   /// The source manager.
101   IntrusiveRefCntPtr<SourceManager> SourceMgr;
102 
103   /// The cache of PCM files.
104   IntrusiveRefCntPtr<ModuleCache> ModCache;
105 
106   /// Functor for getting the dependency preprocessor directives of a file.
107   std::unique_ptr<DependencyDirectivesGetter> GetDependencyDirectives;
108 
109   /// The preprocessor.
110   std::shared_ptr<Preprocessor> PP;
111 
112   /// The AST context.
113   IntrusiveRefCntPtr<ASTContext> Context;
114 
115   /// An optional sema source that will be attached to sema.
116   IntrusiveRefCntPtr<ExternalSemaSource> ExternalSemaSrc;
117 
118   /// The AST consumer.
119   std::unique_ptr<ASTConsumer> Consumer;
120 
121   /// The code completion consumer.
122   std::unique_ptr<CodeCompleteConsumer> CompletionConsumer;
123 
124   /// The semantic analysis object.
125   std::unique_ptr<Sema> TheSema;
126 
127   /// The frontend timer group.
128   std::unique_ptr<llvm::TimerGroup> timerGroup;
129 
130   /// The frontend timer.
131   std::unique_ptr<llvm::Timer> FrontendTimer;
132 
133   /// The ASTReader, if one exists.
134   IntrusiveRefCntPtr<ASTReader> TheASTReader;
135 
136   /// The module dependency collector for crashdumps
137   std::shared_ptr<ModuleDependencyCollector> ModuleDepCollector;
138 
139   /// The module provider.
140   std::shared_ptr<PCHContainerOperations> ThePCHContainerOperations;
141 
142   std::vector<std::shared_ptr<DependencyCollector>> DependencyCollectors;
143 
144   /// The set of modules that failed to build.
145   ///
146   /// This value will be passed among all of the compiler instances created
147   /// to (re)build modules, so that once a module fails to build anywhere,
148   /// other instances will see that the module has failed and won't try to
149   /// build it again.
150   llvm::StringSet<> FailedModules;
151 
152   /// The set of top-level modules that has already been built on the
153   /// fly as part of this overall compilation action.
154   std::map<std::string, std::string, std::less<>> BuiltModules;
155 
156   /// Should we delete the BuiltModules when we're done?
157   bool DeleteBuiltModules = true;
158 
159   /// The location of the module-import keyword for the last module
160   /// import.
161   SourceLocation LastModuleImportLoc;
162 
163   /// The result of the last module import.
164   ///
165   ModuleLoadResult LastModuleImportResult;
166 
167   /// Whether we should (re)build the global module index once we
168   /// have finished with this translation unit.
169   bool BuildGlobalModuleIndex = false;
170 
171   /// We have a full global module index, with all modules.
172   bool HaveFullGlobalModuleIndex = false;
173 
174   /// One or more modules failed to build.
175   bool DisableGeneratingGlobalModuleIndex = false;
176 
177   /// The stream for verbose output if owned, otherwise nullptr.
178   std::unique_ptr<raw_ostream> OwnedVerboseOutputStream;
179 
180   /// The stream for verbose output.
181   raw_ostream *VerboseOutputStream = &llvm::errs();
182 
183   /// Holds information about the output file.
184   ///
185   /// If TempFilename is not empty we must rename it to Filename at the end.
186   /// TempFilename may be empty and Filename non-empty if creating the temporary
187   /// failed.
188   struct OutputFile {
189     std::string Filename;
190     std::optional<llvm::sys::fs::TempFile> File;
191 
OutputFileOutputFile192     OutputFile(std::string filename,
193                std::optional<llvm::sys::fs::TempFile> file)
194         : Filename(std::move(filename)), File(std::move(file)) {}
195   };
196 
197   /// The list of active output files.
198   std::list<OutputFile> OutputFiles;
199 
200   /// Force an output buffer.
201   std::unique_ptr<llvm::raw_pwrite_stream> OutputStream;
202 
203   CompilerInstance(const CompilerInstance &) = delete;
204   void operator=(const CompilerInstance &) = delete;
205 public:
206   explicit CompilerInstance(
207       std::shared_ptr<CompilerInvocation> Invocation =
208           std::make_shared<CompilerInvocation>(),
209       std::shared_ptr<PCHContainerOperations> PCHContainerOps =
210           std::make_shared<PCHContainerOperations>(),
211       ModuleCache *ModCache = nullptr);
212   ~CompilerInstance() override;
213 
214   /// @name High-Level Operations
215   /// @{
216 
217   /// ExecuteAction - Execute the provided action against the compiler's
218   /// CompilerInvocation object.
219   ///
220   /// This function makes the following assumptions:
221   ///
222   ///  - The invocation options should be initialized. This function does not
223   ///    handle the '-help' or '-version' options, clients should handle those
224   ///    directly.
225   ///
226   ///  - The diagnostics engine should have already been created by the client.
227   ///
228   ///  - No other CompilerInstance state should have been initialized (this is
229   ///    an unchecked error).
230   ///
231   ///  - Clients should have initialized any LLVM target features that may be
232   ///    required.
233   ///
234   ///  - Clients should eventually call llvm_shutdown() upon the completion of
235   ///    this routine to ensure that any managed objects are properly destroyed.
236   ///
237   /// Note that this routine may write output to 'stderr'.
238   ///
239   /// \param Act - The action to execute.
240   /// \return - True on success.
241   //
242   // FIXME: Eliminate the llvm_shutdown requirement, that should either be part
243   // of the context or else not CompilerInstance specific.
244   bool ExecuteAction(FrontendAction &Act);
245 
246   /// At the end of a compilation, print the number of warnings/errors.
247   void printDiagnosticStats();
248 
249   /// Load the list of plugins requested in the \c FrontendOptions.
250   void LoadRequestedPlugins();
251 
252   /// @}
253   /// @name Compiler Invocation and Options
254   /// @{
255 
getInvocation()256   CompilerInvocation &getInvocation() { return *Invocation; }
257 
getInvocationPtr()258   std::shared_ptr<CompilerInvocation> getInvocationPtr() { return Invocation; }
259 
260   /// Indicates whether we should (re)build the global module index.
261   bool shouldBuildGlobalModuleIndex() const;
262 
263   /// Set the flag indicating whether we should (re)build the global
264   /// module index.
setBuildGlobalModuleIndex(bool Build)265   void setBuildGlobalModuleIndex(bool Build) {
266     BuildGlobalModuleIndex = Build;
267   }
268 
269   /// @}
270   /// @name Forwarding Methods
271   /// @{
272 
getAnalyzerOpts()273   AnalyzerOptions &getAnalyzerOpts() { return Invocation->getAnalyzerOpts(); }
274 
getCodeGenOpts()275   CodeGenOptions &getCodeGenOpts() {
276     return Invocation->getCodeGenOpts();
277   }
getCodeGenOpts()278   const CodeGenOptions &getCodeGenOpts() const {
279     return Invocation->getCodeGenOpts();
280   }
281 
getDependencyOutputOpts()282   DependencyOutputOptions &getDependencyOutputOpts() {
283     return Invocation->getDependencyOutputOpts();
284   }
getDependencyOutputOpts()285   const DependencyOutputOptions &getDependencyOutputOpts() const {
286     return Invocation->getDependencyOutputOpts();
287   }
288 
getDiagnosticOpts()289   DiagnosticOptions &getDiagnosticOpts() {
290     return Invocation->getDiagnosticOpts();
291   }
getDiagnosticOpts()292   const DiagnosticOptions &getDiagnosticOpts() const {
293     return Invocation->getDiagnosticOpts();
294   }
295 
getFileSystemOpts()296   FileSystemOptions &getFileSystemOpts() {
297     return Invocation->getFileSystemOpts();
298   }
getFileSystemOpts()299   const FileSystemOptions &getFileSystemOpts() const {
300     return Invocation->getFileSystemOpts();
301   }
302 
getFrontendOpts()303   FrontendOptions &getFrontendOpts() {
304     return Invocation->getFrontendOpts();
305   }
getFrontendOpts()306   const FrontendOptions &getFrontendOpts() const {
307     return Invocation->getFrontendOpts();
308   }
309 
getHeaderSearchOpts()310   HeaderSearchOptions &getHeaderSearchOpts() {
311     return Invocation->getHeaderSearchOpts();
312   }
getHeaderSearchOpts()313   const HeaderSearchOptions &getHeaderSearchOpts() const {
314     return Invocation->getHeaderSearchOpts();
315   }
316 
getAPINotesOpts()317   APINotesOptions &getAPINotesOpts() { return Invocation->getAPINotesOpts(); }
getAPINotesOpts()318   const APINotesOptions &getAPINotesOpts() const {
319     return Invocation->getAPINotesOpts();
320   }
321 
getLangOpts()322   LangOptions &getLangOpts() { return Invocation->getLangOpts(); }
getLangOpts()323   const LangOptions &getLangOpts() const { return Invocation->getLangOpts(); }
324 
getPreprocessorOpts()325   PreprocessorOptions &getPreprocessorOpts() {
326     return Invocation->getPreprocessorOpts();
327   }
getPreprocessorOpts()328   const PreprocessorOptions &getPreprocessorOpts() const {
329     return Invocation->getPreprocessorOpts();
330   }
331 
getPreprocessorOutputOpts()332   PreprocessorOutputOptions &getPreprocessorOutputOpts() {
333     return Invocation->getPreprocessorOutputOpts();
334   }
getPreprocessorOutputOpts()335   const PreprocessorOutputOptions &getPreprocessorOutputOpts() const {
336     return Invocation->getPreprocessorOutputOpts();
337   }
338 
getTargetOpts()339   TargetOptions &getTargetOpts() {
340     return Invocation->getTargetOpts();
341   }
getTargetOpts()342   const TargetOptions &getTargetOpts() const {
343     return Invocation->getTargetOpts();
344   }
345 
346   /// @}
347   /// @name Diagnostics Engine
348   /// @{
349 
hasDiagnostics()350   bool hasDiagnostics() const { return Diagnostics != nullptr; }
351 
352   /// Get the current diagnostics engine.
getDiagnostics()353   DiagnosticsEngine &getDiagnostics() const {
354     assert(Diagnostics && "Compiler instance has no diagnostics!");
355     return *Diagnostics;
356   }
357 
getDiagnosticsPtr()358   IntrusiveRefCntPtr<DiagnosticsEngine> getDiagnosticsPtr() const {
359     assert(Diagnostics && "Compiler instance has no diagnostics!");
360     return Diagnostics;
361   }
362 
363   /// setDiagnostics - Replace the current diagnostics engine.
364   void setDiagnostics(DiagnosticsEngine *Value);
365 
getDiagnosticClient()366   DiagnosticConsumer &getDiagnosticClient() const {
367     assert(Diagnostics && Diagnostics->getClient() &&
368            "Compiler instance has no diagnostic client!");
369     return *Diagnostics->getClient();
370   }
371 
372   /// @}
373   /// @name VerboseOutputStream
374   /// @{
375 
376   /// Replace the current stream for verbose output.
377   void setVerboseOutputStream(raw_ostream &Value);
378 
379   /// Replace the current stream for verbose output.
380   void setVerboseOutputStream(std::unique_ptr<raw_ostream> Value);
381 
382   /// Get the current stream for verbose output.
getVerboseOutputStream()383   raw_ostream &getVerboseOutputStream() {
384     return *VerboseOutputStream;
385   }
386 
387   /// @}
388   /// @name Target Info
389   /// @{
390 
hasTarget()391   bool hasTarget() const { return Target != nullptr; }
392 
getTarget()393   TargetInfo &getTarget() const {
394     assert(Target && "Compiler instance has no target!");
395     return *Target;
396   }
397 
getTargetPtr()398   IntrusiveRefCntPtr<TargetInfo> getTargetPtr() const {
399     assert(Target && "Compiler instance has no target!");
400     return Target;
401   }
402 
403   /// Replace the current Target.
404   void setTarget(TargetInfo *Value);
405 
406   /// @}
407   /// @name AuxTarget Info
408   /// @{
409 
getAuxTarget()410   TargetInfo *getAuxTarget() const { return AuxTarget.get(); }
411 
412   /// Replace the current AuxTarget.
413   void setAuxTarget(TargetInfo *Value);
414 
415   // Create Target and AuxTarget based on current options
416   bool createTarget();
417 
418   /// @}
419   /// @name Virtual File System
420   /// @{
421 
422   llvm::vfs::FileSystem &getVirtualFileSystem() const;
423 
424   /// @}
425   /// @name File Manager
426   /// @{
427 
hasFileManager()428   bool hasFileManager() const { return FileMgr != nullptr; }
429 
430   /// Return the current file manager to the caller.
getFileManager()431   FileManager &getFileManager() const {
432     assert(FileMgr && "Compiler instance has no file manager!");
433     return *FileMgr;
434   }
435 
getFileManagerPtr()436   IntrusiveRefCntPtr<FileManager> getFileManagerPtr() const {
437     assert(FileMgr && "Compiler instance has no file manager!");
438     return FileMgr;
439   }
440 
resetAndLeakFileManager()441   void resetAndLeakFileManager() {
442     llvm::BuryPointer(FileMgr.get());
443     FileMgr.resetWithoutRelease();
444   }
445 
446   /// Replace the current file manager and virtual file system.
447   void setFileManager(FileManager *Value);
448 
449   /// @}
450   /// @name Source Manager
451   /// @{
452 
hasSourceManager()453   bool hasSourceManager() const { return SourceMgr != nullptr; }
454 
455   /// Return the current source manager.
getSourceManager()456   SourceManager &getSourceManager() const {
457     assert(SourceMgr && "Compiler instance has no source manager!");
458     return *SourceMgr;
459   }
460 
getSourceManagerPtr()461   IntrusiveRefCntPtr<SourceManager> getSourceManagerPtr() const {
462     assert(SourceMgr && "Compiler instance has no source manager!");
463     return SourceMgr;
464   }
465 
resetAndLeakSourceManager()466   void resetAndLeakSourceManager() {
467     llvm::BuryPointer(SourceMgr.get());
468     SourceMgr.resetWithoutRelease();
469   }
470 
471   /// setSourceManager - Replace the current source manager.
472   void setSourceManager(SourceManager *Value);
473 
474   /// @}
475   /// @name Preprocessor
476   /// @{
477 
hasPreprocessor()478   bool hasPreprocessor() const { return PP != nullptr; }
479 
480   /// Return the current preprocessor.
getPreprocessor()481   Preprocessor &getPreprocessor() const {
482     assert(PP && "Compiler instance has no preprocessor!");
483     return *PP;
484   }
485 
getPreprocessorPtr()486   std::shared_ptr<Preprocessor> getPreprocessorPtr() { return PP; }
487 
resetAndLeakPreprocessor()488   void resetAndLeakPreprocessor() {
489     llvm::BuryPointer(new std::shared_ptr<Preprocessor>(PP));
490   }
491 
492   /// Replace the current preprocessor.
493   void setPreprocessor(std::shared_ptr<Preprocessor> Value);
494 
495   /// @}
496   /// @name ASTContext
497   /// @{
498 
hasASTContext()499   bool hasASTContext() const { return Context != nullptr; }
500 
getASTContext()501   ASTContext &getASTContext() const {
502     assert(Context && "Compiler instance has no AST context!");
503     return *Context;
504   }
505 
getASTContextPtr()506   IntrusiveRefCntPtr<ASTContext> getASTContextPtr() const {
507     assert(Context && "Compiler instance has no AST context!");
508     return Context;
509   }
510 
resetAndLeakASTContext()511   void resetAndLeakASTContext() {
512     llvm::BuryPointer(Context.get());
513     Context.resetWithoutRelease();
514   }
515 
516   /// setASTContext - Replace the current AST context.
517   void setASTContext(ASTContext *Value);
518 
519   /// Replace the current Sema; the compiler instance takes ownership
520   /// of S.
521   void setSema(Sema *S);
522 
523   /// @}
524   /// @name ASTConsumer
525   /// @{
526 
hasASTConsumer()527   bool hasASTConsumer() const { return (bool)Consumer; }
528 
getASTConsumer()529   ASTConsumer &getASTConsumer() const {
530     assert(Consumer && "Compiler instance has no AST consumer!");
531     return *Consumer;
532   }
533 
534   /// takeASTConsumer - Remove the current AST consumer and give ownership to
535   /// the caller.
takeASTConsumer()536   std::unique_ptr<ASTConsumer> takeASTConsumer() { return std::move(Consumer); }
537 
538   /// setASTConsumer - Replace the current AST consumer; the compiler instance
539   /// takes ownership of \p Value.
540   void setASTConsumer(std::unique_ptr<ASTConsumer> Value);
541 
542   /// @}
543   /// @name Semantic analysis
544   /// @{
hasSema()545   bool hasSema() const { return (bool)TheSema; }
546 
getSema()547   Sema &getSema() const {
548     assert(TheSema && "Compiler instance has no Sema object!");
549     return *TheSema;
550   }
551 
552   std::unique_ptr<Sema> takeSema();
553   void resetAndLeakSema();
554 
555   /// @}
556   /// @name Module Management
557   /// @{
558 
559   IntrusiveRefCntPtr<ASTReader> getASTReader() const;
560   void setASTReader(IntrusiveRefCntPtr<ASTReader> Reader);
561 
562   std::shared_ptr<ModuleDependencyCollector> getModuleDepCollector() const;
563   void setModuleDepCollector(
564       std::shared_ptr<ModuleDependencyCollector> Collector);
565 
getPCHContainerOperations()566   std::shared_ptr<PCHContainerOperations> getPCHContainerOperations() const {
567     return ThePCHContainerOperations;
568   }
569 
570   /// Return the appropriate PCHContainerWriter depending on the
571   /// current CodeGenOptions.
getPCHContainerWriter()572   const PCHContainerWriter &getPCHContainerWriter() const {
573     assert(Invocation && "cannot determine module format without invocation");
574     StringRef Format = getHeaderSearchOpts().ModuleFormat;
575     auto *Writer = ThePCHContainerOperations->getWriterOrNull(Format);
576     if (!Writer) {
577       if (Diagnostics)
578         Diagnostics->Report(diag::err_module_format_unhandled) << Format;
579       llvm::report_fatal_error("unknown module format");
580     }
581     return *Writer;
582   }
583 
584   /// Return the appropriate PCHContainerReader depending on the
585   /// current CodeGenOptions.
getPCHContainerReader()586   const PCHContainerReader &getPCHContainerReader() const {
587     assert(Invocation && "cannot determine module format without invocation");
588     StringRef Format = getHeaderSearchOpts().ModuleFormat;
589     auto *Reader = ThePCHContainerOperations->getReaderOrNull(Format);
590     if (!Reader) {
591       if (Diagnostics)
592         Diagnostics->Report(diag::err_module_format_unhandled) << Format;
593       llvm::report_fatal_error("unknown module format");
594     }
595     return *Reader;
596   }
597 
598   /// @}
599   /// @name Code Completion
600   /// @{
601 
hasCodeCompletionConsumer()602   bool hasCodeCompletionConsumer() const { return (bool)CompletionConsumer; }
603 
getCodeCompletionConsumer()604   CodeCompleteConsumer &getCodeCompletionConsumer() const {
605     assert(CompletionConsumer &&
606            "Compiler instance has no code completion consumer!");
607     return *CompletionConsumer;
608   }
609 
610   /// setCodeCompletionConsumer - Replace the current code completion consumer;
611   /// the compiler instance takes ownership of \p Value.
612   void setCodeCompletionConsumer(CodeCompleteConsumer *Value);
613 
614   /// @}
615   /// @name Frontend timer
616   /// @{
617 
getTimerGroup()618   llvm::TimerGroup &getTimerGroup() const { return *timerGroup; }
619 
getFrontendTimer()620   llvm::Timer &getFrontendTimer() const {
621     assert(FrontendTimer && "Compiler instance has no frontend timer!");
622     return *FrontendTimer;
623   }
624 
625   /// }
626   /// @name Output Files
627   /// @{
628 
629   /// clearOutputFiles - Clear the output file list. The underlying output
630   /// streams must have been closed beforehand.
631   ///
632   /// \param EraseFiles - If true, attempt to erase the files from disk.
633   void clearOutputFiles(bool EraseFiles);
634 
635   /// @}
636   /// @name Construction Utility Methods
637   /// @{
638 
639   /// Create the diagnostics engine using the invocation's diagnostic options
640   /// and replace any existing one with it.
641   ///
642   /// Note that this routine also replaces the diagnostic client,
643   /// allocating one if one is not provided.
644   ///
645   /// \param VFS is used for any IO needed when creating DiagnosticsEngine. It
646   /// doesn't replace VFS in the CompilerInstance (if any).
647   ///
648   /// \param Client If non-NULL, a diagnostic client that will be
649   /// attached to (and, then, owned by) the DiagnosticsEngine inside this AST
650   /// unit.
651   ///
652   /// \param ShouldOwnClient If Client is non-NULL, specifies whether
653   /// the diagnostic object should take ownership of the client.
654   void createDiagnostics(llvm::vfs::FileSystem &VFS,
655                          DiagnosticConsumer *Client = nullptr,
656                          bool ShouldOwnClient = true);
657 
658   /// Create a DiagnosticsEngine object with a the TextDiagnosticPrinter.
659   ///
660   /// If no diagnostic client is provided, this creates a
661   /// DiagnosticConsumer that is owned by the returned diagnostic
662   /// object, if using directly the caller is responsible for
663   /// releasing the returned DiagnosticsEngine's client eventually.
664   ///
665   /// \param Opts - The diagnostic options; note that the created text
666   /// diagnostic object contains a reference to these options.
667   ///
668   /// \param Client If non-NULL, a diagnostic client that will be
669   /// attached to (and, then, owned by) the returned DiagnosticsEngine
670   /// object.
671   ///
672   /// \param CodeGenOpts If non-NULL, the code gen options in use, which may be
673   /// used by some diagnostics printers (for logging purposes only).
674   ///
675   /// \return The new object on success, or null on failure.
676   static IntrusiveRefCntPtr<DiagnosticsEngine>
677   createDiagnostics(llvm::vfs::FileSystem &VFS, DiagnosticOptions &Opts,
678                     DiagnosticConsumer *Client = nullptr,
679                     bool ShouldOwnClient = true,
680                     const CodeGenOptions *CodeGenOpts = nullptr);
681 
682   /// Create the file manager and replace any existing one with it.
683   ///
684   /// \return The new file manager on success, or null on failure.
685   FileManager *
686   createFileManager(IntrusiveRefCntPtr<llvm::vfs::FileSystem> VFS = nullptr);
687 
688   /// Create the source manager and replace any existing one with it.
689   void createSourceManager(FileManager &FileMgr);
690 
691   /// Create the preprocessor, using the invocation, file, and source managers,
692   /// and replace any existing one with it.
693   void createPreprocessor(TranslationUnitKind TUKind);
694 
setDependencyDirectivesGetter(std::unique_ptr<DependencyDirectivesGetter> Getter)695   void setDependencyDirectivesGetter(
696       std::unique_ptr<DependencyDirectivesGetter> Getter) {
697     GetDependencyDirectives = std::move(Getter);
698   }
699 
700   std::string getSpecificModuleCachePath(StringRef ModuleHash);
getSpecificModuleCachePath()701   std::string getSpecificModuleCachePath() {
702     return getSpecificModuleCachePath(getInvocation().getModuleHash());
703   }
704 
705   /// Create the AST context.
706   void createASTContext();
707 
708   /// Create an external AST source to read a PCH file and attach it to the AST
709   /// context.
710   void createPCHExternalASTSource(
711       StringRef Path, DisableValidationForModuleKind DisableValidation,
712       bool AllowPCHWithCompilerErrors, void *DeserializationListener,
713       bool OwnDeserializationListener);
714 
715   /// Create an external AST source to read a PCH file.
716   ///
717   /// \return - The new object on success, or null on failure.
718   static IntrusiveRefCntPtr<ASTReader> createPCHExternalASTSource(
719       StringRef Path, StringRef Sysroot,
720       DisableValidationForModuleKind DisableValidation,
721       bool AllowPCHWithCompilerErrors, Preprocessor &PP, ModuleCache &ModCache,
722       ASTContext &Context, const PCHContainerReader &PCHContainerRdr,
723       ArrayRef<std::shared_ptr<ModuleFileExtension>> Extensions,
724       ArrayRef<std::shared_ptr<DependencyCollector>> DependencyCollectors,
725       void *DeserializationListener, bool OwnDeserializationListener,
726       bool Preamble, bool UseGlobalModuleIndex);
727 
728   /// Create a code completion consumer using the invocation; note that this
729   /// will cause the source manager to truncate the input source file at the
730   /// completion point.
731   void createCodeCompletionConsumer();
732 
733   /// Create a code completion consumer to print code completion results, at
734   /// \p Filename, \p Line, and \p Column, to the given output stream \p OS.
735   static CodeCompleteConsumer *createCodeCompletionConsumer(
736       Preprocessor &PP, StringRef Filename, unsigned Line, unsigned Column,
737       const CodeCompleteOptions &Opts, raw_ostream &OS);
738 
739   /// Create the Sema object to be used for parsing.
740   void createSema(TranslationUnitKind TUKind,
741                   CodeCompleteConsumer *CompletionConsumer);
742 
743   /// Create the frontend timer and replace any existing one with it.
744   void createFrontendTimer();
745 
746   /// Create the default output file (from the invocation's options) and add it
747   /// to the list of tracked output files.
748   ///
749   /// The files created by this are usually removed on signal, and, depending
750   /// on FrontendOptions, may also use a temporary file (that is, the data is
751   /// written to a temporary file which will atomically replace the target
752   /// output on success).
753   ///
754   /// \return - Null on error.
755   std::unique_ptr<raw_pwrite_stream> createDefaultOutputFile(
756       bool Binary = true, StringRef BaseInput = "", StringRef Extension = "",
757       bool RemoveFileOnSignal = true, bool CreateMissingDirectories = false,
758       bool ForceUseTemporary = false);
759 
760   /// Create a new output file, optionally deriving the output path name, and
761   /// add it to the list of tracked output files.
762   ///
763   /// \return - Null on error.
764   std::unique_ptr<raw_pwrite_stream>
765   createOutputFile(StringRef OutputPath, bool Binary, bool RemoveFileOnSignal,
766                    bool UseTemporary, bool CreateMissingDirectories = false);
767 
768 private:
769   /// Create a new output file and add it to the list of tracked output files.
770   ///
771   /// If \p OutputPath is empty, then createOutputFile will derive an output
772   /// path location as \p BaseInput, with any suffix removed, and \p Extension
773   /// appended. If \p OutputPath is not stdout and \p UseTemporary
774   /// is true, createOutputFile will create a new temporary file that must be
775   /// renamed to \p OutputPath in the end.
776   ///
777   /// \param OutputPath - If given, the path to the output file.
778   /// \param Binary - The mode to open the file in.
779   /// \param RemoveFileOnSignal - Whether the file should be registered with
780   /// llvm::sys::RemoveFileOnSignal. Note that this is not safe for
781   /// multithreaded use, as the underlying signal mechanism is not reentrant
782   /// \param UseTemporary - Create a new temporary file that must be renamed to
783   /// OutputPath in the end.
784   /// \param CreateMissingDirectories - When \p UseTemporary is true, create
785   /// missing directories in the output path.
786   Expected<std::unique_ptr<raw_pwrite_stream>>
787   createOutputFileImpl(StringRef OutputPath, bool Binary,
788                        bool RemoveFileOnSignal, bool UseTemporary,
789                        bool CreateMissingDirectories);
790 
791 public:
792   std::unique_ptr<raw_pwrite_stream> createNullOutputFile();
793 
794   /// @}
795   /// @name Initialization Utility Methods
796   /// @{
797 
798   /// InitializeSourceManager - Initialize the source manager to set InputFile
799   /// as the main file.
800   ///
801   /// \return True on success.
802   bool InitializeSourceManager(const FrontendInputFile &Input);
803 
804   /// InitializeSourceManager - Initialize the source manager to set InputFile
805   /// as the main file.
806   ///
807   /// \return True on success.
808   static bool InitializeSourceManager(const FrontendInputFile &Input,
809                                       DiagnosticsEngine &Diags,
810                                       FileManager &FileMgr,
811                                       SourceManager &SourceMgr);
812 
813   /// @}
814 
setOutputStream(std::unique_ptr<llvm::raw_pwrite_stream> OutStream)815   void setOutputStream(std::unique_ptr<llvm::raw_pwrite_stream> OutStream) {
816     OutputStream = std::move(OutStream);
817   }
818 
takeOutputStream()819   std::unique_ptr<llvm::raw_pwrite_stream> takeOutputStream() {
820     return std::move(OutputStream);
821   }
822 
823   void createASTReader();
824 
825   bool loadModuleFile(StringRef FileName,
826                       serialization::ModuleFile *&LoadedModuleFile);
827 
828   /// Configuration object for making the result of \c cloneForModuleCompile()
829   /// thread-safe.
830   class ThreadSafeCloneConfig {
831     IntrusiveRefCntPtr<llvm::vfs::FileSystem> VFS;
832     DiagnosticConsumer &DiagConsumer;
833     std::shared_ptr<ModuleDependencyCollector> ModuleDepCollector;
834 
835   public:
836     ThreadSafeCloneConfig(
837         IntrusiveRefCntPtr<llvm::vfs::FileSystem> VFS,
838         DiagnosticConsumer &DiagConsumer,
839         std::shared_ptr<ModuleDependencyCollector> ModuleDepCollector = nullptr)
VFS(std::move (VFS))840         : VFS(std::move(VFS)), DiagConsumer(DiagConsumer),
841           ModuleDepCollector(std::move(ModuleDepCollector)) {
842       assert(this->VFS && "Clone config requires non-null VFS");
843     }
844 
getVFS()845     IntrusiveRefCntPtr<llvm::vfs::FileSystem> getVFS() const { return VFS; }
getDiagConsumer()846     DiagnosticConsumer &getDiagConsumer() const { return DiagConsumer; }
getModuleDepCollector()847     std::shared_ptr<ModuleDependencyCollector> getModuleDepCollector() const {
848       return ModuleDepCollector;
849     }
850   };
851 
852 private:
853   /// Find a module, potentially compiling it, before reading its AST.  This is
854   /// the guts of loadModule.
855   ///
856   /// For prebuilt modules, the Module is not expected to exist in
857   /// HeaderSearch's ModuleMap.  If a ModuleFile by that name is in the
858   /// ModuleManager, then it will be loaded and looked up.
859   ///
860   /// For implicit modules, the Module is expected to already be in the
861   /// ModuleMap.  First attempt to load it from the given path on disk.  If that
862   /// fails, defer to compileModuleAndReadAST, which will first build and then
863   /// load it.
864   ModuleLoadResult findOrCompileModuleAndReadAST(StringRef ModuleName,
865                                                  SourceLocation ImportLoc,
866                                                  SourceLocation ModuleNameLoc,
867                                                  bool IsInclusionDirective);
868 
869   /// Creates a \c CompilerInstance for compiling a module.
870   ///
871   /// This expects a properly initialized \c FrontendInputFile.
872   std::unique_ptr<CompilerInstance> cloneForModuleCompileImpl(
873       SourceLocation ImportLoc, StringRef ModuleName, FrontendInputFile Input,
874       StringRef OriginalModuleMapFile, StringRef ModuleFileName,
875       std::optional<ThreadSafeCloneConfig> ThreadSafeConfig = std::nullopt);
876 
877 public:
878   /// Creates a new \c CompilerInstance for compiling a module.
879   ///
880   /// This takes care of creating appropriate \c FrontendInputFile for
881   /// public/private frameworks, inferred modules and such.
882   ///
883   /// The \c ThreadSafeConfig takes precedence over the \c DiagnosticConsumer
884   /// and \c FileSystem of this instance (and disables \c FileManager sharing).
885   std::unique_ptr<CompilerInstance> cloneForModuleCompile(
886       SourceLocation ImportLoc, Module *Module, StringRef ModuleFileName,
887       std::optional<ThreadSafeCloneConfig> ThreadSafeConfig = std::nullopt);
888 
889   /// Compile a module file for the given module, using the options
890   /// provided by the importing compiler instance. Returns true if the module
891   /// was built without errors.
892   // FIXME: This should be private, but it's called from static non-member
893   // functions in the implementation file.
894   bool compileModule(SourceLocation ImportLoc, StringRef ModuleName,
895                      StringRef ModuleFileName, CompilerInstance &Instance);
896 
897   ModuleLoadResult loadModule(SourceLocation ImportLoc, ModuleIdPath Path,
898                               Module::NameVisibilityKind Visibility,
899                               bool IsInclusionDirective) override;
900 
901   void createModuleFromSource(SourceLocation ImportLoc, StringRef ModuleName,
902                               StringRef Source) override;
903 
904   void makeModuleVisible(Module *Mod, Module::NameVisibilityKind Visibility,
905                          SourceLocation ImportLoc) override;
906 
hadModuleLoaderFatalFailure()907   bool hadModuleLoaderFatalFailure() const {
908     return ModuleLoader::HadFatalFailure;
909   }
910 
911   GlobalModuleIndex *loadGlobalModuleIndex(SourceLocation TriggerLoc) override;
912 
913   bool lookupMissingImports(StringRef Name, SourceLocation TriggerLoc) override;
914 
addDependencyCollector(std::shared_ptr<DependencyCollector> Listener)915   void addDependencyCollector(std::shared_ptr<DependencyCollector> Listener) {
916     DependencyCollectors.push_back(std::move(Listener));
917   }
918 
919   void setExternalSemaSource(IntrusiveRefCntPtr<ExternalSemaSource> ESS);
920 
getModuleCache()921   ModuleCache &getModuleCache() const { return *ModCache; }
922 };
923 
924 } // end namespace clang
925 
926 #endif
927