xref: /freebsd/contrib/llvm-project/clang/lib/Frontend/FrontendActions.cpp (revision 60d0871dbfbebe20a9e24c1b4c659cfe841154c1)
1  //===--- FrontendActions.cpp ----------------------------------------------===//
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  #include "clang/Frontend/FrontendActions.h"
10  #include "clang/AST/ASTConsumer.h"
11  #include "clang/AST/Decl.h"
12  #include "clang/Basic/FileManager.h"
13  #include "clang/Basic/LangStandard.h"
14  #include "clang/Basic/Module.h"
15  #include "clang/Basic/TargetInfo.h"
16  #include "clang/Frontend/ASTConsumers.h"
17  #include "clang/Frontend/CompilerInstance.h"
18  #include "clang/Frontend/FrontendDiagnostic.h"
19  #include "clang/Frontend/MultiplexConsumer.h"
20  #include "clang/Frontend/Utils.h"
21  #include "clang/Lex/DependencyDirectivesScanner.h"
22  #include "clang/Lex/HeaderSearch.h"
23  #include "clang/Lex/Preprocessor.h"
24  #include "clang/Lex/PreprocessorOptions.h"
25  #include "clang/Sema/TemplateInstCallback.h"
26  #include "clang/Serialization/ASTReader.h"
27  #include "clang/Serialization/ASTWriter.h"
28  #include "clang/Serialization/ModuleFile.h"
29  #include "llvm/Support/ErrorHandling.h"
30  #include "llvm/Support/FileSystem.h"
31  #include "llvm/Support/MemoryBuffer.h"
32  #include "llvm/Support/Path.h"
33  #include "llvm/Support/YAMLTraits.h"
34  #include "llvm/Support/raw_ostream.h"
35  #include <memory>
36  #include <system_error>
37  
38  using namespace clang;
39  
40  namespace {
41  CodeCompleteConsumer *GetCodeCompletionConsumer(CompilerInstance &CI) {
42    return CI.hasCodeCompletionConsumer() ? &CI.getCodeCompletionConsumer()
43                                          : nullptr;
44  }
45  
46  void EnsureSemaIsCreated(CompilerInstance &CI, FrontendAction &Action) {
47    if (Action.hasCodeCompletionSupport() &&
48        !CI.getFrontendOpts().CodeCompletionAt.FileName.empty())
49      CI.createCodeCompletionConsumer();
50  
51    if (!CI.hasSema())
52      CI.createSema(Action.getTranslationUnitKind(),
53                    GetCodeCompletionConsumer(CI));
54  }
55  } // namespace
56  
57  //===----------------------------------------------------------------------===//
58  // Custom Actions
59  //===----------------------------------------------------------------------===//
60  
61  std::unique_ptr<ASTConsumer>
62  InitOnlyAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
63    return std::make_unique<ASTConsumer>();
64  }
65  
66  void InitOnlyAction::ExecuteAction() {
67  }
68  
69  // Basically PreprocessOnlyAction::ExecuteAction.
70  void ReadPCHAndPreprocessAction::ExecuteAction() {
71    Preprocessor &PP = getCompilerInstance().getPreprocessor();
72  
73    // Ignore unknown pragmas.
74    PP.IgnorePragmas();
75  
76    Token Tok;
77    // Start parsing the specified input file.
78    PP.EnterMainSourceFile();
79    do {
80      PP.Lex(Tok);
81    } while (Tok.isNot(tok::eof));
82  }
83  
84  std::unique_ptr<ASTConsumer>
85  ReadPCHAndPreprocessAction::CreateASTConsumer(CompilerInstance &CI,
86                                                StringRef InFile) {
87    return std::make_unique<ASTConsumer>();
88  }
89  
90  //===----------------------------------------------------------------------===//
91  // AST Consumer Actions
92  //===----------------------------------------------------------------------===//
93  
94  std::unique_ptr<ASTConsumer>
95  ASTPrintAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
96    if (std::unique_ptr<raw_ostream> OS =
97            CI.createDefaultOutputFile(false, InFile))
98      return CreateASTPrinter(std::move(OS), CI.getFrontendOpts().ASTDumpFilter);
99    return nullptr;
100  }
101  
102  std::unique_ptr<ASTConsumer>
103  ASTDumpAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
104    const FrontendOptions &Opts = CI.getFrontendOpts();
105    return CreateASTDumper(nullptr /*Dump to stdout.*/, Opts.ASTDumpFilter,
106                           Opts.ASTDumpDecls, Opts.ASTDumpAll,
107                           Opts.ASTDumpLookups, Opts.ASTDumpDeclTypes,
108                           Opts.ASTDumpFormat);
109  }
110  
111  std::unique_ptr<ASTConsumer>
112  ASTDeclListAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
113    return CreateASTDeclNodeLister();
114  }
115  
116  std::unique_ptr<ASTConsumer>
117  ASTViewAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
118    return CreateASTViewer();
119  }
120  
121  std::unique_ptr<ASTConsumer>
122  GeneratePCHAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
123    std::string Sysroot;
124    if (!ComputeASTConsumerArguments(CI, /*ref*/ Sysroot))
125      return nullptr;
126  
127    std::string OutputFile;
128    std::unique_ptr<raw_pwrite_stream> OS =
129        CreateOutputFile(CI, InFile, /*ref*/ OutputFile);
130    if (!OS)
131      return nullptr;
132  
133    if (!CI.getFrontendOpts().RelocatablePCH)
134      Sysroot.clear();
135  
136    const auto &FrontendOpts = CI.getFrontendOpts();
137    auto Buffer = std::make_shared<PCHBuffer>();
138    std::vector<std::unique_ptr<ASTConsumer>> Consumers;
139    Consumers.push_back(std::make_unique<PCHGenerator>(
140        CI.getPreprocessor(), CI.getModuleCache(), OutputFile, Sysroot, Buffer,
141        FrontendOpts.ModuleFileExtensions,
142        CI.getPreprocessorOpts().AllowPCHWithCompilerErrors,
143        FrontendOpts.IncludeTimestamps, +CI.getLangOpts().CacheGeneratedPCH));
144    Consumers.push_back(CI.getPCHContainerWriter().CreatePCHContainerGenerator(
145        CI, std::string(InFile), OutputFile, std::move(OS), Buffer));
146  
147    return std::make_unique<MultiplexConsumer>(std::move(Consumers));
148  }
149  
150  bool GeneratePCHAction::ComputeASTConsumerArguments(CompilerInstance &CI,
151                                                      std::string &Sysroot) {
152    Sysroot = CI.getHeaderSearchOpts().Sysroot;
153    if (CI.getFrontendOpts().RelocatablePCH && Sysroot.empty()) {
154      CI.getDiagnostics().Report(diag::err_relocatable_without_isysroot);
155      return false;
156    }
157  
158    return true;
159  }
160  
161  std::unique_ptr<llvm::raw_pwrite_stream>
162  GeneratePCHAction::CreateOutputFile(CompilerInstance &CI, StringRef InFile,
163                                      std::string &OutputFile) {
164    // Because this is exposed via libclang we must disable RemoveFileOnSignal.
165    std::unique_ptr<raw_pwrite_stream> OS = CI.createDefaultOutputFile(
166        /*Binary=*/true, InFile, /*Extension=*/"", /*RemoveFileOnSignal=*/false);
167    if (!OS)
168      return nullptr;
169  
170    OutputFile = CI.getFrontendOpts().OutputFile;
171    return OS;
172  }
173  
174  bool GeneratePCHAction::shouldEraseOutputFiles() {
175    if (getCompilerInstance().getPreprocessorOpts().AllowPCHWithCompilerErrors)
176      return false;
177    return ASTFrontendAction::shouldEraseOutputFiles();
178  }
179  
180  bool GeneratePCHAction::BeginSourceFileAction(CompilerInstance &CI) {
181    CI.getLangOpts().CompilingPCH = true;
182    return true;
183  }
184  
185  std::unique_ptr<ASTConsumer>
186  GenerateModuleAction::CreateASTConsumer(CompilerInstance &CI,
187                                          StringRef InFile) {
188    std::unique_ptr<raw_pwrite_stream> OS = CreateOutputFile(CI, InFile);
189    if (!OS)
190      return nullptr;
191  
192    std::string OutputFile = CI.getFrontendOpts().OutputFile;
193    std::string Sysroot;
194  
195    auto Buffer = std::make_shared<PCHBuffer>();
196    std::vector<std::unique_ptr<ASTConsumer>> Consumers;
197  
198    Consumers.push_back(std::make_unique<PCHGenerator>(
199        CI.getPreprocessor(), CI.getModuleCache(), OutputFile, Sysroot, Buffer,
200        CI.getFrontendOpts().ModuleFileExtensions,
201        /*AllowASTWithErrors=*/
202        +CI.getFrontendOpts().AllowPCMWithCompilerErrors,
203        /*IncludeTimestamps=*/
204        +CI.getFrontendOpts().BuildingImplicitModule,
205        /*ShouldCacheASTInMemory=*/
206        +CI.getFrontendOpts().BuildingImplicitModule));
207    Consumers.push_back(CI.getPCHContainerWriter().CreatePCHContainerGenerator(
208        CI, std::string(InFile), OutputFile, std::move(OS), Buffer));
209    return std::make_unique<MultiplexConsumer>(std::move(Consumers));
210  }
211  
212  bool GenerateModuleAction::shouldEraseOutputFiles() {
213    return !getCompilerInstance().getFrontendOpts().AllowPCMWithCompilerErrors &&
214           ASTFrontendAction::shouldEraseOutputFiles();
215  }
216  
217  bool GenerateModuleFromModuleMapAction::BeginSourceFileAction(
218      CompilerInstance &CI) {
219    if (!CI.getLangOpts().Modules) {
220      CI.getDiagnostics().Report(diag::err_module_build_requires_fmodules);
221      return false;
222    }
223  
224    return GenerateModuleAction::BeginSourceFileAction(CI);
225  }
226  
227  std::unique_ptr<raw_pwrite_stream>
228  GenerateModuleFromModuleMapAction::CreateOutputFile(CompilerInstance &CI,
229                                                      StringRef InFile) {
230    // If no output file was provided, figure out where this module would go
231    // in the module cache.
232    if (CI.getFrontendOpts().OutputFile.empty()) {
233      StringRef ModuleMapFile = CI.getFrontendOpts().OriginalModuleMap;
234      if (ModuleMapFile.empty())
235        ModuleMapFile = InFile;
236  
237      HeaderSearch &HS = CI.getPreprocessor().getHeaderSearchInfo();
238      CI.getFrontendOpts().OutputFile =
239          HS.getCachedModuleFileName(CI.getLangOpts().CurrentModule,
240                                     ModuleMapFile);
241    }
242  
243    // Because this is exposed via libclang we must disable RemoveFileOnSignal.
244    return CI.createDefaultOutputFile(/*Binary=*/true, InFile, /*Extension=*/"",
245                                      /*RemoveFileOnSignal=*/false,
246                                      /*CreateMissingDirectories=*/true,
247                                      /*ForceUseTemporary=*/true);
248  }
249  
250  bool GenerateModuleInterfaceAction::BeginSourceFileAction(
251      CompilerInstance &CI) {
252    if (!CI.getLangOpts().ModulesTS && !CI.getLangOpts().CPlusPlusModules) {
253      CI.getDiagnostics().Report(diag::err_module_interface_requires_cpp_modules);
254      return false;
255    }
256  
257    CI.getLangOpts().setCompilingModule(LangOptions::CMK_ModuleInterface);
258  
259    return GenerateModuleAction::BeginSourceFileAction(CI);
260  }
261  
262  std::unique_ptr<raw_pwrite_stream>
263  GenerateModuleInterfaceAction::CreateOutputFile(CompilerInstance &CI,
264                                                  StringRef InFile) {
265    return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
266  }
267  
268  bool GenerateHeaderModuleAction::PrepareToExecuteAction(
269      CompilerInstance &CI) {
270    if (!CI.getLangOpts().Modules) {
271      CI.getDiagnostics().Report(diag::err_header_module_requires_modules);
272      return false;
273    }
274  
275    auto &Inputs = CI.getFrontendOpts().Inputs;
276    if (Inputs.empty())
277      return GenerateModuleAction::BeginInvocation(CI);
278  
279    auto Kind = Inputs[0].getKind();
280  
281    // Convert the header file inputs into a single module input buffer.
282    SmallString<256> HeaderContents;
283    ModuleHeaders.reserve(Inputs.size());
284    for (const FrontendInputFile &FIF : Inputs) {
285      // FIXME: We should support re-compiling from an AST file.
286      if (FIF.getKind().getFormat() != InputKind::Source || !FIF.isFile()) {
287        CI.getDiagnostics().Report(diag::err_module_header_file_not_found)
288            << (FIF.isFile() ? FIF.getFile()
289                             : FIF.getBuffer().getBufferIdentifier());
290        return true;
291      }
292  
293      HeaderContents += "#include \"";
294      HeaderContents += FIF.getFile();
295      HeaderContents += "\"\n";
296      ModuleHeaders.push_back(std::string(FIF.getFile()));
297    }
298    Buffer = llvm::MemoryBuffer::getMemBufferCopy(
299        HeaderContents, Module::getModuleInputBufferName());
300  
301    // Set that buffer up as our "real" input.
302    Inputs.clear();
303    Inputs.push_back(
304        FrontendInputFile(Buffer->getMemBufferRef(), Kind, /*IsSystem*/ false));
305  
306    return GenerateModuleAction::PrepareToExecuteAction(CI);
307  }
308  
309  bool GenerateHeaderModuleAction::BeginSourceFileAction(
310      CompilerInstance &CI) {
311    CI.getLangOpts().setCompilingModule(LangOptions::CMK_HeaderModule);
312  
313    // Synthesize a Module object for the given headers.
314    auto &HS = CI.getPreprocessor().getHeaderSearchInfo();
315    SmallVector<Module::Header, 16> Headers;
316    for (StringRef Name : ModuleHeaders) {
317      Optional<FileEntryRef> FE = HS.LookupFile(
318          Name, SourceLocation(), /*Angled*/ false, nullptr, nullptr, None,
319          nullptr, nullptr, nullptr, nullptr, nullptr, nullptr);
320      if (!FE) {
321        CI.getDiagnostics().Report(diag::err_module_header_file_not_found)
322          << Name;
323        continue;
324      }
325      Headers.push_back(
326          {std::string(Name), std::string(Name), &FE->getFileEntry()});
327    }
328    HS.getModuleMap().createHeaderModule(CI.getLangOpts().CurrentModule, Headers);
329  
330    return GenerateModuleAction::BeginSourceFileAction(CI);
331  }
332  
333  std::unique_ptr<raw_pwrite_stream>
334  GenerateHeaderModuleAction::CreateOutputFile(CompilerInstance &CI,
335                                               StringRef InFile) {
336    return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
337  }
338  
339  bool GenerateHeaderUnitAction::BeginSourceFileAction(CompilerInstance &CI) {
340    if (!CI.getLangOpts().CPlusPlusModules) {
341      CI.getDiagnostics().Report(diag::err_module_interface_requires_cpp_modules);
342      return false;
343    }
344    CI.getLangOpts().setCompilingModule(LangOptions::CMK_HeaderUnit);
345    return GenerateModuleAction::BeginSourceFileAction(CI);
346  }
347  
348  std::unique_ptr<raw_pwrite_stream>
349  GenerateHeaderUnitAction::CreateOutputFile(CompilerInstance &CI,
350                                             StringRef InFile) {
351    return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
352  }
353  
354  SyntaxOnlyAction::~SyntaxOnlyAction() {
355  }
356  
357  std::unique_ptr<ASTConsumer>
358  SyntaxOnlyAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
359    return std::make_unique<ASTConsumer>();
360  }
361  
362  std::unique_ptr<ASTConsumer>
363  DumpModuleInfoAction::CreateASTConsumer(CompilerInstance &CI,
364                                          StringRef InFile) {
365    return std::make_unique<ASTConsumer>();
366  }
367  
368  std::unique_ptr<ASTConsumer>
369  VerifyPCHAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
370    return std::make_unique<ASTConsumer>();
371  }
372  
373  void VerifyPCHAction::ExecuteAction() {
374    CompilerInstance &CI = getCompilerInstance();
375    bool Preamble = CI.getPreprocessorOpts().PrecompiledPreambleBytes.first != 0;
376    const std::string &Sysroot = CI.getHeaderSearchOpts().Sysroot;
377    std::unique_ptr<ASTReader> Reader(new ASTReader(
378        CI.getPreprocessor(), CI.getModuleCache(), &CI.getASTContext(),
379        CI.getPCHContainerReader(), CI.getFrontendOpts().ModuleFileExtensions,
380        Sysroot.empty() ? "" : Sysroot.c_str(),
381        DisableValidationForModuleKind::None,
382        /*AllowASTWithCompilerErrors*/ false,
383        /*AllowConfigurationMismatch*/ true,
384        /*ValidateSystemInputs*/ true));
385  
386    Reader->ReadAST(getCurrentFile(),
387                    Preamble ? serialization::MK_Preamble
388                             : serialization::MK_PCH,
389                    SourceLocation(),
390                    ASTReader::ARR_ConfigurationMismatch);
391  }
392  
393  namespace {
394  struct TemplightEntry {
395    std::string Name;
396    std::string Kind;
397    std::string Event;
398    std::string DefinitionLocation;
399    std::string PointOfInstantiation;
400  };
401  } // namespace
402  
403  namespace llvm {
404  namespace yaml {
405  template <> struct MappingTraits<TemplightEntry> {
406    static void mapping(IO &io, TemplightEntry &fields) {
407      io.mapRequired("name", fields.Name);
408      io.mapRequired("kind", fields.Kind);
409      io.mapRequired("event", fields.Event);
410      io.mapRequired("orig", fields.DefinitionLocation);
411      io.mapRequired("poi", fields.PointOfInstantiation);
412    }
413  };
414  } // namespace yaml
415  } // namespace llvm
416  
417  namespace {
418  class DefaultTemplateInstCallback : public TemplateInstantiationCallback {
419    using CodeSynthesisContext = Sema::CodeSynthesisContext;
420  
421  public:
422    void initialize(const Sema &) override {}
423  
424    void finalize(const Sema &) override {}
425  
426    void atTemplateBegin(const Sema &TheSema,
427                         const CodeSynthesisContext &Inst) override {
428      displayTemplightEntry<true>(llvm::outs(), TheSema, Inst);
429    }
430  
431    void atTemplateEnd(const Sema &TheSema,
432                       const CodeSynthesisContext &Inst) override {
433      displayTemplightEntry<false>(llvm::outs(), TheSema, Inst);
434    }
435  
436  private:
437    static std::string toString(CodeSynthesisContext::SynthesisKind Kind) {
438      switch (Kind) {
439      case CodeSynthesisContext::TemplateInstantiation:
440        return "TemplateInstantiation";
441      case CodeSynthesisContext::DefaultTemplateArgumentInstantiation:
442        return "DefaultTemplateArgumentInstantiation";
443      case CodeSynthesisContext::DefaultFunctionArgumentInstantiation:
444        return "DefaultFunctionArgumentInstantiation";
445      case CodeSynthesisContext::ExplicitTemplateArgumentSubstitution:
446        return "ExplicitTemplateArgumentSubstitution";
447      case CodeSynthesisContext::DeducedTemplateArgumentSubstitution:
448        return "DeducedTemplateArgumentSubstitution";
449      case CodeSynthesisContext::PriorTemplateArgumentSubstitution:
450        return "PriorTemplateArgumentSubstitution";
451      case CodeSynthesisContext::DefaultTemplateArgumentChecking:
452        return "DefaultTemplateArgumentChecking";
453      case CodeSynthesisContext::ExceptionSpecEvaluation:
454        return "ExceptionSpecEvaluation";
455      case CodeSynthesisContext::ExceptionSpecInstantiation:
456        return "ExceptionSpecInstantiation";
457      case CodeSynthesisContext::DeclaringSpecialMember:
458        return "DeclaringSpecialMember";
459      case CodeSynthesisContext::DeclaringImplicitEqualityComparison:
460        return "DeclaringImplicitEqualityComparison";
461      case CodeSynthesisContext::DefiningSynthesizedFunction:
462        return "DefiningSynthesizedFunction";
463      case CodeSynthesisContext::RewritingOperatorAsSpaceship:
464        return "RewritingOperatorAsSpaceship";
465      case CodeSynthesisContext::Memoization:
466        return "Memoization";
467      case CodeSynthesisContext::ConstraintsCheck:
468        return "ConstraintsCheck";
469      case CodeSynthesisContext::ConstraintSubstitution:
470        return "ConstraintSubstitution";
471      case CodeSynthesisContext::ConstraintNormalization:
472        return "ConstraintNormalization";
473      case CodeSynthesisContext::ParameterMappingSubstitution:
474        return "ParameterMappingSubstitution";
475      case CodeSynthesisContext::RequirementInstantiation:
476        return "RequirementInstantiation";
477      case CodeSynthesisContext::NestedRequirementConstraintsCheck:
478        return "NestedRequirementConstraintsCheck";
479      case CodeSynthesisContext::InitializingStructuredBinding:
480        return "InitializingStructuredBinding";
481      case CodeSynthesisContext::MarkingClassDllexported:
482        return "MarkingClassDllexported";
483      case CodeSynthesisContext::BuildingBuiltinDumpStructCall:
484        return "BuildingBuiltinDumpStructCall";
485      }
486      return "";
487    }
488  
489    template <bool BeginInstantiation>
490    static void displayTemplightEntry(llvm::raw_ostream &Out, const Sema &TheSema,
491                                      const CodeSynthesisContext &Inst) {
492      std::string YAML;
493      {
494        llvm::raw_string_ostream OS(YAML);
495        llvm::yaml::Output YO(OS);
496        TemplightEntry Entry =
497            getTemplightEntry<BeginInstantiation>(TheSema, Inst);
498        llvm::yaml::EmptyContext Context;
499        llvm::yaml::yamlize(YO, Entry, true, Context);
500      }
501      Out << "---" << YAML << "\n";
502    }
503  
504    static void printEntryName(const Sema &TheSema, const Decl *Entity,
505                               llvm::raw_string_ostream &OS) {
506      auto *NamedTemplate = cast<NamedDecl>(Entity);
507  
508      PrintingPolicy Policy = TheSema.Context.getPrintingPolicy();
509      // FIXME: Also ask for FullyQualifiedNames?
510      Policy.SuppressDefaultTemplateArgs = false;
511      NamedTemplate->getNameForDiagnostic(OS, Policy, true);
512  
513      if (!OS.str().empty())
514        return;
515  
516      Decl *Ctx = Decl::castFromDeclContext(NamedTemplate->getDeclContext());
517      NamedDecl *NamedCtx = dyn_cast_or_null<NamedDecl>(Ctx);
518  
519      if (const auto *Decl = dyn_cast<TagDecl>(NamedTemplate)) {
520        if (const auto *R = dyn_cast<RecordDecl>(Decl)) {
521          if (R->isLambda()) {
522            OS << "lambda at ";
523            Decl->getLocation().print(OS, TheSema.getSourceManager());
524            return;
525          }
526        }
527        OS << "unnamed " << Decl->getKindName();
528        return;
529      }
530  
531      if (const auto *Decl = dyn_cast<ParmVarDecl>(NamedTemplate)) {
532        OS << "unnamed function parameter " << Decl->getFunctionScopeIndex()
533           << " ";
534        if (Decl->getFunctionScopeDepth() > 0)
535          OS << "(at depth " << Decl->getFunctionScopeDepth() << ") ";
536        OS << "of ";
537        NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
538        return;
539      }
540  
541      if (const auto *Decl = dyn_cast<TemplateTypeParmDecl>(NamedTemplate)) {
542        if (const Type *Ty = Decl->getTypeForDecl()) {
543          if (const auto *TTPT = dyn_cast_or_null<TemplateTypeParmType>(Ty)) {
544            OS << "unnamed template type parameter " << TTPT->getIndex() << " ";
545            if (TTPT->getDepth() > 0)
546              OS << "(at depth " << TTPT->getDepth() << ") ";
547            OS << "of ";
548            NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
549            return;
550          }
551        }
552      }
553  
554      if (const auto *Decl = dyn_cast<NonTypeTemplateParmDecl>(NamedTemplate)) {
555        OS << "unnamed template non-type parameter " << Decl->getIndex() << " ";
556        if (Decl->getDepth() > 0)
557          OS << "(at depth " << Decl->getDepth() << ") ";
558        OS << "of ";
559        NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
560        return;
561      }
562  
563      if (const auto *Decl = dyn_cast<TemplateTemplateParmDecl>(NamedTemplate)) {
564        OS << "unnamed template template parameter " << Decl->getIndex() << " ";
565        if (Decl->getDepth() > 0)
566          OS << "(at depth " << Decl->getDepth() << ") ";
567        OS << "of ";
568        NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
569        return;
570      }
571  
572      llvm_unreachable("Failed to retrieve a name for this entry!");
573      OS << "unnamed identifier";
574    }
575  
576    template <bool BeginInstantiation>
577    static TemplightEntry getTemplightEntry(const Sema &TheSema,
578                                            const CodeSynthesisContext &Inst) {
579      TemplightEntry Entry;
580      Entry.Kind = toString(Inst.Kind);
581      Entry.Event = BeginInstantiation ? "Begin" : "End";
582      llvm::raw_string_ostream OS(Entry.Name);
583      printEntryName(TheSema, Inst.Entity, OS);
584      const PresumedLoc DefLoc =
585          TheSema.getSourceManager().getPresumedLoc(Inst.Entity->getLocation());
586      if (!DefLoc.isInvalid())
587        Entry.DefinitionLocation = std::string(DefLoc.getFilename()) + ":" +
588                                   std::to_string(DefLoc.getLine()) + ":" +
589                                   std::to_string(DefLoc.getColumn());
590      const PresumedLoc PoiLoc =
591          TheSema.getSourceManager().getPresumedLoc(Inst.PointOfInstantiation);
592      if (!PoiLoc.isInvalid()) {
593        Entry.PointOfInstantiation = std::string(PoiLoc.getFilename()) + ":" +
594                                     std::to_string(PoiLoc.getLine()) + ":" +
595                                     std::to_string(PoiLoc.getColumn());
596      }
597      return Entry;
598    }
599  };
600  } // namespace
601  
602  std::unique_ptr<ASTConsumer>
603  TemplightDumpAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
604    return std::make_unique<ASTConsumer>();
605  }
606  
607  void TemplightDumpAction::ExecuteAction() {
608    CompilerInstance &CI = getCompilerInstance();
609  
610    // This part is normally done by ASTFrontEndAction, but needs to happen
611    // before Templight observers can be created
612    // FIXME: Move the truncation aspect of this into Sema, we delayed this till
613    // here so the source manager would be initialized.
614    EnsureSemaIsCreated(CI, *this);
615  
616    CI.getSema().TemplateInstCallbacks.push_back(
617        std::make_unique<DefaultTemplateInstCallback>());
618    ASTFrontendAction::ExecuteAction();
619  }
620  
621  namespace {
622    /// AST reader listener that dumps module information for a module
623    /// file.
624    class DumpModuleInfoListener : public ASTReaderListener {
625      llvm::raw_ostream &Out;
626  
627    public:
628      DumpModuleInfoListener(llvm::raw_ostream &Out) : Out(Out) { }
629  
630  #define DUMP_BOOLEAN(Value, Text)                       \
631      Out.indent(4) << Text << ": " << (Value? "Yes" : "No") << "\n"
632  
633      bool ReadFullVersionInformation(StringRef FullVersion) override {
634        Out.indent(2)
635          << "Generated by "
636          << (FullVersion == getClangFullRepositoryVersion()? "this"
637                                                            : "a different")
638          << " Clang: " << FullVersion << "\n";
639        return ASTReaderListener::ReadFullVersionInformation(FullVersion);
640      }
641  
642      void ReadModuleName(StringRef ModuleName) override {
643        Out.indent(2) << "Module name: " << ModuleName << "\n";
644      }
645      void ReadModuleMapFile(StringRef ModuleMapPath) override {
646        Out.indent(2) << "Module map file: " << ModuleMapPath << "\n";
647      }
648  
649      bool ReadLanguageOptions(const LangOptions &LangOpts, bool Complain,
650                               bool AllowCompatibleDifferences) override {
651        Out.indent(2) << "Language options:\n";
652  #define LANGOPT(Name, Bits, Default, Description) \
653        DUMP_BOOLEAN(LangOpts.Name, Description);
654  #define ENUM_LANGOPT(Name, Type, Bits, Default, Description) \
655        Out.indent(4) << Description << ": "                   \
656                      << static_cast<unsigned>(LangOpts.get##Name()) << "\n";
657  #define VALUE_LANGOPT(Name, Bits, Default, Description) \
658        Out.indent(4) << Description << ": " << LangOpts.Name << "\n";
659  #define BENIGN_LANGOPT(Name, Bits, Default, Description)
660  #define BENIGN_ENUM_LANGOPT(Name, Type, Bits, Default, Description)
661  #include "clang/Basic/LangOptions.def"
662  
663        if (!LangOpts.ModuleFeatures.empty()) {
664          Out.indent(4) << "Module features:\n";
665          for (StringRef Feature : LangOpts.ModuleFeatures)
666            Out.indent(6) << Feature << "\n";
667        }
668  
669        return false;
670      }
671  
672      bool ReadTargetOptions(const TargetOptions &TargetOpts, bool Complain,
673                             bool AllowCompatibleDifferences) override {
674        Out.indent(2) << "Target options:\n";
675        Out.indent(4) << "  Triple: " << TargetOpts.Triple << "\n";
676        Out.indent(4) << "  CPU: " << TargetOpts.CPU << "\n";
677        Out.indent(4) << "  TuneCPU: " << TargetOpts.TuneCPU << "\n";
678        Out.indent(4) << "  ABI: " << TargetOpts.ABI << "\n";
679  
680        if (!TargetOpts.FeaturesAsWritten.empty()) {
681          Out.indent(4) << "Target features:\n";
682          for (unsigned I = 0, N = TargetOpts.FeaturesAsWritten.size();
683               I != N; ++I) {
684            Out.indent(6) << TargetOpts.FeaturesAsWritten[I] << "\n";
685          }
686        }
687  
688        return false;
689      }
690  
691      bool ReadDiagnosticOptions(IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts,
692                                 bool Complain) override {
693        Out.indent(2) << "Diagnostic options:\n";
694  #define DIAGOPT(Name, Bits, Default) DUMP_BOOLEAN(DiagOpts->Name, #Name);
695  #define ENUM_DIAGOPT(Name, Type, Bits, Default) \
696        Out.indent(4) << #Name << ": " << DiagOpts->get##Name() << "\n";
697  #define VALUE_DIAGOPT(Name, Bits, Default) \
698        Out.indent(4) << #Name << ": " << DiagOpts->Name << "\n";
699  #include "clang/Basic/DiagnosticOptions.def"
700  
701        Out.indent(4) << "Diagnostic flags:\n";
702        for (const std::string &Warning : DiagOpts->Warnings)
703          Out.indent(6) << "-W" << Warning << "\n";
704        for (const std::string &Remark : DiagOpts->Remarks)
705          Out.indent(6) << "-R" << Remark << "\n";
706  
707        return false;
708      }
709  
710      bool ReadHeaderSearchOptions(const HeaderSearchOptions &HSOpts,
711                                   StringRef SpecificModuleCachePath,
712                                   bool Complain) override {
713        Out.indent(2) << "Header search options:\n";
714        Out.indent(4) << "System root [-isysroot=]: '" << HSOpts.Sysroot << "'\n";
715        Out.indent(4) << "Resource dir [ -resource-dir=]: '" << HSOpts.ResourceDir << "'\n";
716        Out.indent(4) << "Module Cache: '" << SpecificModuleCachePath << "'\n";
717        DUMP_BOOLEAN(HSOpts.UseBuiltinIncludes,
718                     "Use builtin include directories [-nobuiltininc]");
719        DUMP_BOOLEAN(HSOpts.UseStandardSystemIncludes,
720                     "Use standard system include directories [-nostdinc]");
721        DUMP_BOOLEAN(HSOpts.UseStandardCXXIncludes,
722                     "Use standard C++ include directories [-nostdinc++]");
723        DUMP_BOOLEAN(HSOpts.UseLibcxx,
724                     "Use libc++ (rather than libstdc++) [-stdlib=]");
725        return false;
726      }
727  
728      bool ReadPreprocessorOptions(const PreprocessorOptions &PPOpts,
729                                   bool Complain,
730                                   std::string &SuggestedPredefines) override {
731        Out.indent(2) << "Preprocessor options:\n";
732        DUMP_BOOLEAN(PPOpts.UsePredefines,
733                     "Uses compiler/target-specific predefines [-undef]");
734        DUMP_BOOLEAN(PPOpts.DetailedRecord,
735                     "Uses detailed preprocessing record (for indexing)");
736  
737        if (!PPOpts.Macros.empty()) {
738          Out.indent(4) << "Predefined macros:\n";
739        }
740  
741        for (std::vector<std::pair<std::string, bool/*isUndef*/> >::const_iterator
742               I = PPOpts.Macros.begin(), IEnd = PPOpts.Macros.end();
743             I != IEnd; ++I) {
744          Out.indent(6);
745          if (I->second)
746            Out << "-U";
747          else
748            Out << "-D";
749          Out << I->first << "\n";
750        }
751        return false;
752      }
753  
754      /// Indicates that a particular module file extension has been read.
755      void readModuleFileExtension(
756             const ModuleFileExtensionMetadata &Metadata) override {
757        Out.indent(2) << "Module file extension '"
758                      << Metadata.BlockName << "' " << Metadata.MajorVersion
759                      << "." << Metadata.MinorVersion;
760        if (!Metadata.UserInfo.empty()) {
761          Out << ": ";
762          Out.write_escaped(Metadata.UserInfo);
763        }
764  
765        Out << "\n";
766      }
767  
768      /// Tells the \c ASTReaderListener that we want to receive the
769      /// input files of the AST file via \c visitInputFile.
770      bool needsInputFileVisitation() override { return true; }
771  
772      /// Tells the \c ASTReaderListener that we want to receive the
773      /// input files of the AST file via \c visitInputFile.
774      bool needsSystemInputFileVisitation() override { return true; }
775  
776      /// Indicates that the AST file contains particular input file.
777      ///
778      /// \returns true to continue receiving the next input file, false to stop.
779      bool visitInputFile(StringRef Filename, bool isSystem,
780                          bool isOverridden, bool isExplicitModule) override {
781  
782        Out.indent(2) << "Input file: " << Filename;
783  
784        if (isSystem || isOverridden || isExplicitModule) {
785          Out << " [";
786          if (isSystem) {
787            Out << "System";
788            if (isOverridden || isExplicitModule)
789              Out << ", ";
790          }
791          if (isOverridden) {
792            Out << "Overridden";
793            if (isExplicitModule)
794              Out << ", ";
795          }
796          if (isExplicitModule)
797            Out << "ExplicitModule";
798  
799          Out << "]";
800        }
801  
802        Out << "\n";
803  
804        return true;
805      }
806  
807      /// Returns true if this \c ASTReaderListener wants to receive the
808      /// imports of the AST file via \c visitImport, false otherwise.
809      bool needsImportVisitation() const override { return true; }
810  
811      /// If needsImportVisitation returns \c true, this is called for each
812      /// AST file imported by this AST file.
813      void visitImport(StringRef ModuleName, StringRef Filename) override {
814        Out.indent(2) << "Imports module '" << ModuleName
815                      << "': " << Filename.str() << "\n";
816      }
817  #undef DUMP_BOOLEAN
818    };
819  }
820  
821  bool DumpModuleInfoAction::BeginInvocation(CompilerInstance &CI) {
822    // The Object file reader also supports raw ast files and there is no point in
823    // being strict about the module file format in -module-file-info mode.
824    CI.getHeaderSearchOpts().ModuleFormat = "obj";
825    return true;
826  }
827  
828  static StringRef ModuleKindName(Module::ModuleKind MK) {
829    switch (MK) {
830    case Module::ModuleMapModule:
831      return "Module Map Module";
832    case Module::ModuleInterfaceUnit:
833      return "Interface Unit";
834    case Module::ModulePartitionInterface:
835      return "Partition Interface";
836    case Module::ModulePartitionImplementation:
837      return "Partition Implementation";
838    case Module::ModuleHeaderUnit:
839      return "Header Unit";
840    case Module::GlobalModuleFragment:
841      return "Global Module Fragment";
842    case Module::PrivateModuleFragment:
843      return "Private Module Fragment";
844    }
845    llvm_unreachable("unknown module kind!");
846  }
847  
848  void DumpModuleInfoAction::ExecuteAction() {
849    assert(isCurrentFileAST() && "dumping non-AST?");
850    // Set up the output file.
851    std::unique_ptr<llvm::raw_fd_ostream> OutFile;
852    StringRef OutputFileName = getCompilerInstance().getFrontendOpts().OutputFile;
853    if (!OutputFileName.empty() && OutputFileName != "-") {
854      std::error_code EC;
855      OutFile.reset(new llvm::raw_fd_ostream(OutputFileName.str(), EC,
856                                             llvm::sys::fs::OF_TextWithCRLF));
857      OutputStream = OutFile.get();
858    }
859    llvm::raw_ostream &Out = OutputStream ? *OutputStream : llvm::outs();
860  
861    Out << "Information for module file '" << getCurrentFile() << "':\n";
862    auto &FileMgr = getCompilerInstance().getFileManager();
863    auto Buffer = FileMgr.getBufferForFile(getCurrentFile());
864    StringRef Magic = (*Buffer)->getMemBufferRef().getBuffer();
865    bool IsRaw = (Magic.size() >= 4 && Magic[0] == 'C' && Magic[1] == 'P' &&
866                  Magic[2] == 'C' && Magic[3] == 'H');
867    Out << "  Module format: " << (IsRaw ? "raw" : "obj") << "\n";
868  
869    Preprocessor &PP = getCompilerInstance().getPreprocessor();
870    DumpModuleInfoListener Listener(Out);
871    HeaderSearchOptions &HSOpts = PP.getHeaderSearchInfo().getHeaderSearchOpts();
872  
873    // The FrontendAction::BeginSourceFile () method loads the AST so that much
874    // of the information is already available and modules should have been
875    // loaded.
876  
877    const LangOptions &LO = getCurrentASTUnit().getLangOpts();
878    if (LO.CPlusPlusModules && !LO.CurrentModule.empty()) {
879  
880      ASTReader *R = getCurrentASTUnit().getASTReader().get();
881      unsigned SubModuleCount = R->getTotalNumSubmodules();
882      serialization::ModuleFile &MF = R->getModuleManager().getPrimaryModule();
883      Out << "  ====== C++20 Module structure ======\n";
884  
885      if (MF.ModuleName != LO.CurrentModule)
886        Out << "  Mismatched module names : " << MF.ModuleName << " and "
887            << LO.CurrentModule << "\n";
888  
889      struct SubModInfo {
890        unsigned Idx;
891        Module *Mod;
892        Module::ModuleKind Kind;
893        std::string &Name;
894        bool Seen;
895      };
896      std::map<std::string, SubModInfo> SubModMap;
897      auto PrintSubMapEntry = [&](std::string Name, Module::ModuleKind Kind) {
898        Out << "    " << ModuleKindName(Kind) << " '" << Name << "'";
899        auto I = SubModMap.find(Name);
900        if (I == SubModMap.end())
901          Out << " was not found in the sub modules!\n";
902        else {
903          I->second.Seen = true;
904          Out << " is at index #" << I->second.Idx << "\n";
905        }
906      };
907      Module *Primary = nullptr;
908      for (unsigned Idx = 0; Idx <= SubModuleCount; ++Idx) {
909        Module *M = R->getModule(Idx);
910        if (!M)
911          continue;
912        if (M->Name == LO.CurrentModule) {
913          Primary = M;
914          Out << "  " << ModuleKindName(M->Kind) << " '" << LO.CurrentModule
915              << "' is the Primary Module at index #" << Idx << "\n";
916          SubModMap.insert({M->Name, {Idx, M, M->Kind, M->Name, true}});
917        } else
918          SubModMap.insert({M->Name, {Idx, M, M->Kind, M->Name, false}});
919      }
920      if (Primary) {
921        if (!Primary->submodules().empty())
922          Out << "   Sub Modules:\n";
923        for (auto MI : Primary->submodules()) {
924          PrintSubMapEntry(MI->Name, MI->Kind);
925        }
926        if (!Primary->Imports.empty())
927          Out << "   Imports:\n";
928        for (auto IMP : Primary->Imports) {
929          PrintSubMapEntry(IMP->Name, IMP->Kind);
930        }
931        if (!Primary->Exports.empty())
932          Out << "   Exports:\n";
933        for (unsigned MN = 0, N = Primary->Exports.size(); MN != N; ++MN) {
934          if (Module *M = Primary->Exports[MN].getPointer()) {
935            PrintSubMapEntry(M->Name, M->Kind);
936          }
937        }
938      }
939      // Now let's print out any modules we did not see as part of the Primary.
940      for (auto SM : SubModMap) {
941        if (!SM.second.Seen && SM.second.Mod) {
942          Out << "  " << ModuleKindName(SM.second.Kind) << " '" << SM.first
943              << "' at index #" << SM.second.Idx
944              << " has no direct reference in the Primary\n";
945        }
946      }
947      Out << "  ====== ======\n";
948    }
949  
950    // The reminder of the output is produced from the listener as the AST
951    // FileCcontrolBlock is (re-)parsed.
952    ASTReader::readASTFileControlBlock(
953        getCurrentFile(), FileMgr, getCompilerInstance().getPCHContainerReader(),
954        /*FindModuleFileExtensions=*/true, Listener,
955        HSOpts.ModulesValidateDiagnosticOptions);
956  }
957  
958  //===----------------------------------------------------------------------===//
959  // Preprocessor Actions
960  //===----------------------------------------------------------------------===//
961  
962  void DumpRawTokensAction::ExecuteAction() {
963    Preprocessor &PP = getCompilerInstance().getPreprocessor();
964    SourceManager &SM = PP.getSourceManager();
965  
966    // Start lexing the specified input file.
967    llvm::MemoryBufferRef FromFile = SM.getBufferOrFake(SM.getMainFileID());
968    Lexer RawLex(SM.getMainFileID(), FromFile, SM, PP.getLangOpts());
969    RawLex.SetKeepWhitespaceMode(true);
970  
971    Token RawTok;
972    RawLex.LexFromRawLexer(RawTok);
973    while (RawTok.isNot(tok::eof)) {
974      PP.DumpToken(RawTok, true);
975      llvm::errs() << "\n";
976      RawLex.LexFromRawLexer(RawTok);
977    }
978  }
979  
980  void DumpTokensAction::ExecuteAction() {
981    Preprocessor &PP = getCompilerInstance().getPreprocessor();
982    // Start preprocessing the specified input file.
983    Token Tok;
984    PP.EnterMainSourceFile();
985    do {
986      PP.Lex(Tok);
987      PP.DumpToken(Tok, true);
988      llvm::errs() << "\n";
989    } while (Tok.isNot(tok::eof));
990  }
991  
992  void PreprocessOnlyAction::ExecuteAction() {
993    Preprocessor &PP = getCompilerInstance().getPreprocessor();
994  
995    // Ignore unknown pragmas.
996    PP.IgnorePragmas();
997  
998    Token Tok;
999    // Start parsing the specified input file.
1000    PP.EnterMainSourceFile();
1001    do {
1002      PP.Lex(Tok);
1003    } while (Tok.isNot(tok::eof));
1004  }
1005  
1006  void PrintPreprocessedAction::ExecuteAction() {
1007    CompilerInstance &CI = getCompilerInstance();
1008    // Output file may need to be set to 'Binary', to avoid converting Unix style
1009    // line feeds (<LF>) to Microsoft style line feeds (<CR><LF>) on Windows.
1010    //
1011    // Look to see what type of line endings the file uses. If there's a
1012    // CRLF, then we won't open the file up in binary mode. If there is
1013    // just an LF or CR, then we will open the file up in binary mode.
1014    // In this fashion, the output format should match the input format, unless
1015    // the input format has inconsistent line endings.
1016    //
1017    // This should be a relatively fast operation since most files won't have
1018    // all of their source code on a single line. However, that is still a
1019    // concern, so if we scan for too long, we'll just assume the file should
1020    // be opened in binary mode.
1021  
1022    bool BinaryMode = false;
1023    if (llvm::Triple(LLVM_HOST_TRIPLE).isOSWindows()) {
1024      BinaryMode = true;
1025      const SourceManager &SM = CI.getSourceManager();
1026      if (llvm::Optional<llvm::MemoryBufferRef> Buffer =
1027              SM.getBufferOrNone(SM.getMainFileID())) {
1028        const char *cur = Buffer->getBufferStart();
1029        const char *end = Buffer->getBufferEnd();
1030        const char *next = (cur != end) ? cur + 1 : end;
1031  
1032        // Limit ourselves to only scanning 256 characters into the source
1033        // file.  This is mostly a check in case the file has no
1034        // newlines whatsoever.
1035        if (end - cur > 256)
1036          end = cur + 256;
1037  
1038        while (next < end) {
1039          if (*cur == 0x0D) {  // CR
1040            if (*next == 0x0A) // CRLF
1041              BinaryMode = false;
1042  
1043            break;
1044          } else if (*cur == 0x0A) // LF
1045            break;
1046  
1047          ++cur;
1048          ++next;
1049        }
1050      }
1051    }
1052  
1053    std::unique_ptr<raw_ostream> OS =
1054        CI.createDefaultOutputFile(BinaryMode, getCurrentFileOrBufferName());
1055    if (!OS) return;
1056  
1057    // If we're preprocessing a module map, start by dumping the contents of the
1058    // module itself before switching to the input buffer.
1059    auto &Input = getCurrentInput();
1060    if (Input.getKind().getFormat() == InputKind::ModuleMap) {
1061      if (Input.isFile()) {
1062        (*OS) << "# 1 \"";
1063        OS->write_escaped(Input.getFile());
1064        (*OS) << "\"\n";
1065      }
1066      getCurrentModule()->print(*OS);
1067      (*OS) << "#pragma clang module contents\n";
1068    }
1069  
1070    DoPrintPreprocessedInput(CI.getPreprocessor(), OS.get(),
1071                             CI.getPreprocessorOutputOpts());
1072  }
1073  
1074  void PrintPreambleAction::ExecuteAction() {
1075    switch (getCurrentFileKind().getLanguage()) {
1076    case Language::C:
1077    case Language::CXX:
1078    case Language::ObjC:
1079    case Language::ObjCXX:
1080    case Language::OpenCL:
1081    case Language::OpenCLCXX:
1082    case Language::CUDA:
1083    case Language::HIP:
1084    case Language::HLSL:
1085      break;
1086  
1087    case Language::Unknown:
1088    case Language::Asm:
1089    case Language::LLVM_IR:
1090    case Language::RenderScript:
1091      // We can't do anything with these.
1092      return;
1093    }
1094  
1095    // We don't expect to find any #include directives in a preprocessed input.
1096    if (getCurrentFileKind().isPreprocessed())
1097      return;
1098  
1099    CompilerInstance &CI = getCompilerInstance();
1100    auto Buffer = CI.getFileManager().getBufferForFile(getCurrentFile());
1101    if (Buffer) {
1102      unsigned Preamble =
1103          Lexer::ComputePreamble((*Buffer)->getBuffer(), CI.getLangOpts()).Size;
1104      llvm::outs().write((*Buffer)->getBufferStart(), Preamble);
1105    }
1106  }
1107  
1108  void DumpCompilerOptionsAction::ExecuteAction() {
1109    CompilerInstance &CI = getCompilerInstance();
1110    std::unique_ptr<raw_ostream> OSP =
1111        CI.createDefaultOutputFile(false, getCurrentFile());
1112    if (!OSP)
1113      return;
1114  
1115    raw_ostream &OS = *OSP;
1116    const Preprocessor &PP = CI.getPreprocessor();
1117    const LangOptions &LangOpts = PP.getLangOpts();
1118  
1119    // FIXME: Rather than manually format the JSON (which is awkward due to
1120    // needing to remove trailing commas), this should make use of a JSON library.
1121    // FIXME: Instead of printing enums as an integral value and specifying the
1122    // type as a separate field, use introspection to print the enumerator.
1123  
1124    OS << "{\n";
1125    OS << "\n\"features\" : [\n";
1126    {
1127      llvm::SmallString<128> Str;
1128  #define FEATURE(Name, Predicate)                                               \
1129    ("\t{\"" #Name "\" : " + llvm::Twine(Predicate ? "true" : "false") + "},\n") \
1130        .toVector(Str);
1131  #include "clang/Basic/Features.def"
1132  #undef FEATURE
1133      // Remove the newline and comma from the last entry to ensure this remains
1134      // valid JSON.
1135      OS << Str.substr(0, Str.size() - 2);
1136    }
1137    OS << "\n],\n";
1138  
1139    OS << "\n\"extensions\" : [\n";
1140    {
1141      llvm::SmallString<128> Str;
1142  #define EXTENSION(Name, Predicate)                                             \
1143    ("\t{\"" #Name "\" : " + llvm::Twine(Predicate ? "true" : "false") + "},\n") \
1144        .toVector(Str);
1145  #include "clang/Basic/Features.def"
1146  #undef EXTENSION
1147      // Remove the newline and comma from the last entry to ensure this remains
1148      // valid JSON.
1149      OS << Str.substr(0, Str.size() - 2);
1150    }
1151    OS << "\n]\n";
1152  
1153    OS << "}";
1154  }
1155  
1156  void PrintDependencyDirectivesSourceMinimizerAction::ExecuteAction() {
1157    CompilerInstance &CI = getCompilerInstance();
1158    SourceManager &SM = CI.getPreprocessor().getSourceManager();
1159    llvm::MemoryBufferRef FromFile = SM.getBufferOrFake(SM.getMainFileID());
1160  
1161    llvm::SmallVector<dependency_directives_scan::Token, 16> Tokens;
1162    llvm::SmallVector<dependency_directives_scan::Directive, 32> Directives;
1163    if (scanSourceForDependencyDirectives(
1164            FromFile.getBuffer(), Tokens, Directives, &CI.getDiagnostics(),
1165            SM.getLocForStartOfFile(SM.getMainFileID()))) {
1166      assert(CI.getDiagnostics().hasErrorOccurred() &&
1167             "no errors reported for failure");
1168  
1169      // Preprocess the source when verifying the diagnostics to capture the
1170      // 'expected' comments.
1171      if (CI.getDiagnosticOpts().VerifyDiagnostics) {
1172        // Make sure we don't emit new diagnostics!
1173        CI.getDiagnostics().setSuppressAllDiagnostics(true);
1174        Preprocessor &PP = getCompilerInstance().getPreprocessor();
1175        PP.EnterMainSourceFile();
1176        Token Tok;
1177        do {
1178          PP.Lex(Tok);
1179        } while (Tok.isNot(tok::eof));
1180      }
1181      return;
1182    }
1183    printDependencyDirectivesAsSource(FromFile.getBuffer(), Directives,
1184                                      llvm::outs());
1185  }
1186  
1187  void GetDependenciesByModuleNameAction::ExecuteAction() {
1188    CompilerInstance &CI = getCompilerInstance();
1189    Preprocessor &PP = CI.getPreprocessor();
1190    SourceManager &SM = PP.getSourceManager();
1191    FileID MainFileID = SM.getMainFileID();
1192    SourceLocation FileStart = SM.getLocForStartOfFile(MainFileID);
1193    SmallVector<std::pair<IdentifierInfo *, SourceLocation>, 2> Path;
1194    IdentifierInfo *ModuleID = PP.getIdentifierInfo(ModuleName);
1195    Path.push_back(std::make_pair(ModuleID, FileStart));
1196    auto ModResult = CI.loadModule(FileStart, Path, Module::Hidden, false);
1197    PPCallbacks *CB = PP.getPPCallbacks();
1198    CB->moduleImport(SourceLocation(), Path, ModResult);
1199  }
1200