clang 19.0.0git
FrontendActions.cpp
Go to the documentation of this file.
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
11#include "clang/AST/Decl.h"
14#include "clang/Basic/Module.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 <optional>
37#include <system_error>
38
39using namespace clang;
40
41namespace {
42CodeCompleteConsumer *GetCodeCompletionConsumer(CompilerInstance &CI) {
44 : nullptr;
45}
46
47void EnsureSemaIsCreated(CompilerInstance &CI, FrontendAction &Action) {
48 if (Action.hasCodeCompletionSupport() &&
51
52 if (!CI.hasSema())
54 GetCodeCompletionConsumer(CI));
55}
56} // namespace
57
58//===----------------------------------------------------------------------===//
59// Custom Actions
60//===----------------------------------------------------------------------===//
61
62std::unique_ptr<ASTConsumer>
63InitOnlyAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
64 return std::make_unique<ASTConsumer>();
65}
66
67void InitOnlyAction::ExecuteAction() {
68}
69
70// Basically PreprocessOnlyAction::ExecuteAction.
71void ReadPCHAndPreprocessAction::ExecuteAction() {
73
74 // Ignore unknown pragmas.
75 PP.IgnorePragmas();
76
77 Token Tok;
78 // Start parsing the specified input file.
80 do {
81 PP.Lex(Tok);
82 } while (Tok.isNot(tok::eof));
83}
84
85std::unique_ptr<ASTConsumer>
86ReadPCHAndPreprocessAction::CreateASTConsumer(CompilerInstance &CI,
87 StringRef InFile) {
88 return std::make_unique<ASTConsumer>();
89}
90
91//===----------------------------------------------------------------------===//
92// AST Consumer Actions
93//===----------------------------------------------------------------------===//
94
95std::unique_ptr<ASTConsumer>
97 if (std::unique_ptr<raw_ostream> OS =
98 CI.createDefaultOutputFile(false, InFile))
99 return CreateASTPrinter(std::move(OS), CI.getFrontendOpts().ASTDumpFilter);
100 return nullptr;
101}
102
103std::unique_ptr<ASTConsumer>
105 const FrontendOptions &Opts = CI.getFrontendOpts();
106 return CreateASTDumper(nullptr /*Dump to stdout.*/, Opts.ASTDumpFilter,
107 Opts.ASTDumpDecls, Opts.ASTDumpAll,
109 Opts.ASTDumpFormat);
110}
111
112std::unique_ptr<ASTConsumer>
115}
116
117std::unique_ptr<ASTConsumer>
119 return CreateASTViewer();
120}
121
122std::unique_ptr<ASTConsumer>
124 std::string Sysroot;
125 if (!ComputeASTConsumerArguments(CI, /*ref*/ Sysroot))
126 return nullptr;
127
128 std::string OutputFile;
129 std::unique_ptr<raw_pwrite_stream> OS =
130 CreateOutputFile(CI, InFile, /*ref*/ OutputFile);
131 if (!OS)
132 return nullptr;
133
135 Sysroot.clear();
136
137 const auto &FrontendOpts = CI.getFrontendOpts();
138 auto Buffer = std::make_shared<PCHBuffer>();
139 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
140 Consumers.push_back(std::make_unique<PCHGenerator>(
141 CI.getPreprocessor(), CI.getModuleCache(), OutputFile, Sysroot, Buffer,
142 FrontendOpts.ModuleFileExtensions,
144 FrontendOpts.IncludeTimestamps, FrontendOpts.BuildingImplicitModule,
145 +CI.getLangOpts().CacheGeneratedPCH));
146 Consumers.push_back(CI.getPCHContainerWriter().CreatePCHContainerGenerator(
147 CI, std::string(InFile), OutputFile, std::move(OS), Buffer));
148
149 return std::make_unique<MultiplexConsumer>(std::move(Consumers));
150}
151
153 std::string &Sysroot) {
154 Sysroot = CI.getHeaderSearchOpts().Sysroot;
155 if (CI.getFrontendOpts().RelocatablePCH && Sysroot.empty()) {
156 CI.getDiagnostics().Report(diag::err_relocatable_without_isysroot);
157 return false;
158 }
159
160 return true;
161}
162
163std::unique_ptr<llvm::raw_pwrite_stream>
165 std::string &OutputFile) {
166 // Because this is exposed via libclang we must disable RemoveFileOnSignal.
167 std::unique_ptr<raw_pwrite_stream> OS = CI.createDefaultOutputFile(
168 /*Binary=*/true, InFile, /*Extension=*/"", /*RemoveFileOnSignal=*/false);
169 if (!OS)
170 return nullptr;
171
172 OutputFile = CI.getFrontendOpts().OutputFile;
173 return OS;
174}
175
177 if (getCompilerInstance().getPreprocessorOpts().AllowPCHWithCompilerErrors)
178 return false;
180}
181
183 CI.getLangOpts().CompilingPCH = true;
184 return true;
185}
186
187std::vector<std::unique_ptr<ASTConsumer>>
189 StringRef InFile) {
190 std::unique_ptr<raw_pwrite_stream> OS = CreateOutputFile(CI, InFile);
191 if (!OS)
192 return {};
193
194 std::string OutputFile = CI.getFrontendOpts().OutputFile;
195 std::string Sysroot;
196
197 auto Buffer = std::make_shared<PCHBuffer>();
198 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
199
200 Consumers.push_back(std::make_unique<PCHGenerator>(
201 CI.getPreprocessor(), CI.getModuleCache(), OutputFile, Sysroot, Buffer,
203 /*AllowASTWithErrors=*/
205 /*IncludeTimestamps=*/
208 /*BuildingImplicitModule=*/+CI.getFrontendOpts().BuildingImplicitModule,
209 /*ShouldCacheASTInMemory=*/
211 Consumers.push_back(CI.getPCHContainerWriter().CreatePCHContainerGenerator(
212 CI, std::string(InFile), OutputFile, std::move(OS), Buffer));
213 return Consumers;
214}
215
216std::unique_ptr<ASTConsumer>
218 StringRef InFile) {
219 std::vector<std::unique_ptr<ASTConsumer>> Consumers =
220 CreateMultiplexConsumer(CI, InFile);
221 if (Consumers.empty())
222 return nullptr;
223
224 return std::make_unique<MultiplexConsumer>(std::move(Consumers));
225}
226
230}
231
232bool GenerateModuleFromModuleMapAction::BeginSourceFileAction(
233 CompilerInstance &CI) {
234 if (!CI.getLangOpts().Modules) {
235 CI.getDiagnostics().Report(diag::err_module_build_requires_fmodules);
236 return false;
237 }
238
240}
241
242std::unique_ptr<raw_pwrite_stream>
243GenerateModuleFromModuleMapAction::CreateOutputFile(CompilerInstance &CI,
244 StringRef InFile) {
245 // If no output file was provided, figure out where this module would go
246 // in the module cache.
247 if (CI.getFrontendOpts().OutputFile.empty()) {
248 StringRef ModuleMapFile = CI.getFrontendOpts().OriginalModuleMap;
249 if (ModuleMapFile.empty())
250 ModuleMapFile = InFile;
251
255 ModuleMapFile);
256 }
257
258 // Because this is exposed via libclang we must disable RemoveFileOnSignal.
259 return CI.createDefaultOutputFile(/*Binary=*/true, InFile, /*Extension=*/"",
260 /*RemoveFileOnSignal=*/false,
261 /*CreateMissingDirectories=*/true,
262 /*ForceUseTemporary=*/true);
263}
264
266 CompilerInstance &CI) {
267 CI.getLangOpts().setCompilingModule(LangOptions::CMK_ModuleInterface);
268
270}
271
272std::unique_ptr<ASTConsumer>
274 StringRef InFile) {
275 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
276 Consumers.push_back(std::make_unique<CXX20ModulesGenerator>(
279
281 !CI.getFrontendOpts().ModuleOutputPath.empty()) {
282 Consumers.push_back(std::make_unique<ReducedBMIGenerator>(
285 }
286
287 return std::make_unique<MultiplexConsumer>(std::move(Consumers));
288}
289
290std::unique_ptr<raw_pwrite_stream>
292 StringRef InFile) {
293 return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
294}
295
296std::unique_ptr<ASTConsumer>
297GenerateReducedModuleInterfaceAction::CreateASTConsumer(CompilerInstance &CI,
298 StringRef InFile) {
299 return std::make_unique<ReducedBMIGenerator>(CI.getPreprocessor(),
300 CI.getModuleCache(),
302}
303
304bool GenerateHeaderUnitAction::BeginSourceFileAction(CompilerInstance &CI) {
305 if (!CI.getLangOpts().CPlusPlusModules) {
306 CI.getDiagnostics().Report(diag::err_module_interface_requires_cpp_modules);
307 return false;
308 }
309 CI.getLangOpts().setCompilingModule(LangOptions::CMK_HeaderUnit);
311}
312
313std::unique_ptr<raw_pwrite_stream>
314GenerateHeaderUnitAction::CreateOutputFile(CompilerInstance &CI,
315 StringRef InFile) {
316 return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
317}
318
320}
321
322std::unique_ptr<ASTConsumer>
324 return std::make_unique<ASTConsumer>();
325}
326
327std::unique_ptr<ASTConsumer>
329 StringRef InFile) {
330 return std::make_unique<ASTConsumer>();
331}
332
333std::unique_ptr<ASTConsumer>
335 return std::make_unique<ASTConsumer>();
336}
337
341 const std::string &Sysroot = CI.getHeaderSearchOpts().Sysroot;
342 std::unique_ptr<ASTReader> Reader(new ASTReader(
345 Sysroot.empty() ? "" : Sysroot.c_str(),
347 /*AllowASTWithCompilerErrors*/ false,
348 /*AllowConfigurationMismatch*/ true,
349 /*ValidateSystemInputs*/ true));
350
351 Reader->ReadAST(getCurrentFile(),
356}
357
358namespace {
359struct TemplightEntry {
360 std::string Name;
361 std::string Kind;
362 std::string Event;
363 std::string DefinitionLocation;
364 std::string PointOfInstantiation;
365};
366} // namespace
367
368namespace llvm {
369namespace yaml {
370template <> struct MappingTraits<TemplightEntry> {
371 static void mapping(IO &io, TemplightEntry &fields) {
372 io.mapRequired("name", fields.Name);
373 io.mapRequired("kind", fields.Kind);
374 io.mapRequired("event", fields.Event);
375 io.mapRequired("orig", fields.DefinitionLocation);
376 io.mapRequired("poi", fields.PointOfInstantiation);
377 }
378};
379} // namespace yaml
380} // namespace llvm
381
382namespace {
383class DefaultTemplateInstCallback : public TemplateInstantiationCallback {
384 using CodeSynthesisContext = Sema::CodeSynthesisContext;
385
386public:
387 void initialize(const Sema &) override {}
388
389 void finalize(const Sema &) override {}
390
391 void atTemplateBegin(const Sema &TheSema,
392 const CodeSynthesisContext &Inst) override {
393 displayTemplightEntry<true>(llvm::outs(), TheSema, Inst);
394 }
395
396 void atTemplateEnd(const Sema &TheSema,
397 const CodeSynthesisContext &Inst) override {
398 displayTemplightEntry<false>(llvm::outs(), TheSema, Inst);
399 }
400
401private:
402 static std::string toString(CodeSynthesisContext::SynthesisKind Kind) {
403 switch (Kind) {
404 case CodeSynthesisContext::TemplateInstantiation:
405 return "TemplateInstantiation";
406 case CodeSynthesisContext::DefaultTemplateArgumentInstantiation:
407 return "DefaultTemplateArgumentInstantiation";
408 case CodeSynthesisContext::DefaultFunctionArgumentInstantiation:
409 return "DefaultFunctionArgumentInstantiation";
410 case CodeSynthesisContext::ExplicitTemplateArgumentSubstitution:
411 return "ExplicitTemplateArgumentSubstitution";
412 case CodeSynthesisContext::DeducedTemplateArgumentSubstitution:
413 return "DeducedTemplateArgumentSubstitution";
414 case CodeSynthesisContext::LambdaExpressionSubstitution:
415 return "LambdaExpressionSubstitution";
416 case CodeSynthesisContext::PriorTemplateArgumentSubstitution:
417 return "PriorTemplateArgumentSubstitution";
418 case CodeSynthesisContext::DefaultTemplateArgumentChecking:
419 return "DefaultTemplateArgumentChecking";
420 case CodeSynthesisContext::ExceptionSpecEvaluation:
421 return "ExceptionSpecEvaluation";
422 case CodeSynthesisContext::ExceptionSpecInstantiation:
423 return "ExceptionSpecInstantiation";
424 case CodeSynthesisContext::DeclaringSpecialMember:
425 return "DeclaringSpecialMember";
426 case CodeSynthesisContext::DeclaringImplicitEqualityComparison:
427 return "DeclaringImplicitEqualityComparison";
428 case CodeSynthesisContext::DefiningSynthesizedFunction:
429 return "DefiningSynthesizedFunction";
430 case CodeSynthesisContext::RewritingOperatorAsSpaceship:
431 return "RewritingOperatorAsSpaceship";
432 case CodeSynthesisContext::Memoization:
433 return "Memoization";
434 case CodeSynthesisContext::ConstraintsCheck:
435 return "ConstraintsCheck";
436 case CodeSynthesisContext::ConstraintSubstitution:
437 return "ConstraintSubstitution";
438 case CodeSynthesisContext::ConstraintNormalization:
439 return "ConstraintNormalization";
440 case CodeSynthesisContext::RequirementParameterInstantiation:
441 return "RequirementParameterInstantiation";
442 case CodeSynthesisContext::ParameterMappingSubstitution:
443 return "ParameterMappingSubstitution";
444 case CodeSynthesisContext::RequirementInstantiation:
445 return "RequirementInstantiation";
446 case CodeSynthesisContext::NestedRequirementConstraintsCheck:
447 return "NestedRequirementConstraintsCheck";
448 case CodeSynthesisContext::InitializingStructuredBinding:
449 return "InitializingStructuredBinding";
450 case CodeSynthesisContext::MarkingClassDllexported:
451 return "MarkingClassDllexported";
452 case CodeSynthesisContext::BuildingBuiltinDumpStructCall:
453 return "BuildingBuiltinDumpStructCall";
454 case CodeSynthesisContext::BuildingDeductionGuides:
455 return "BuildingDeductionGuides";
456 case CodeSynthesisContext::TypeAliasTemplateInstantiation:
457 return "TypeAliasTemplateInstantiation";
458 }
459 return "";
460 }
461
462 template <bool BeginInstantiation>
463 static void displayTemplightEntry(llvm::raw_ostream &Out, const Sema &TheSema,
464 const CodeSynthesisContext &Inst) {
465 std::string YAML;
466 {
467 llvm::raw_string_ostream OS(YAML);
468 llvm::yaml::Output YO(OS);
469 TemplightEntry Entry =
470 getTemplightEntry<BeginInstantiation>(TheSema, Inst);
471 llvm::yaml::EmptyContext Context;
472 llvm::yaml::yamlize(YO, Entry, true, Context);
473 }
474 Out << "---" << YAML << "\n";
475 }
476
477 static void printEntryName(const Sema &TheSema, const Decl *Entity,
478 llvm::raw_string_ostream &OS) {
479 auto *NamedTemplate = cast<NamedDecl>(Entity);
480
481 PrintingPolicy Policy = TheSema.Context.getPrintingPolicy();
482 // FIXME: Also ask for FullyQualifiedNames?
483 Policy.SuppressDefaultTemplateArgs = false;
484 NamedTemplate->getNameForDiagnostic(OS, Policy, true);
485
486 if (!OS.str().empty())
487 return;
488
489 Decl *Ctx = Decl::castFromDeclContext(NamedTemplate->getDeclContext());
490 NamedDecl *NamedCtx = dyn_cast_or_null<NamedDecl>(Ctx);
491
492 if (const auto *Decl = dyn_cast<TagDecl>(NamedTemplate)) {
493 if (const auto *R = dyn_cast<RecordDecl>(Decl)) {
494 if (R->isLambda()) {
495 OS << "lambda at ";
496 Decl->getLocation().print(OS, TheSema.getSourceManager());
497 return;
498 }
499 }
500 OS << "unnamed " << Decl->getKindName();
501 return;
502 }
503
504 assert(NamedCtx && "NamedCtx cannot be null");
505
506 if (const auto *Decl = dyn_cast<ParmVarDecl>(NamedTemplate)) {
507 OS << "unnamed function parameter " << Decl->getFunctionScopeIndex()
508 << " ";
509 if (Decl->getFunctionScopeDepth() > 0)
510 OS << "(at depth " << Decl->getFunctionScopeDepth() << ") ";
511 OS << "of ";
512 NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
513 return;
514 }
515
516 if (const auto *Decl = dyn_cast<TemplateTypeParmDecl>(NamedTemplate)) {
517 if (const Type *Ty = Decl->getTypeForDecl()) {
518 if (const auto *TTPT = dyn_cast_or_null<TemplateTypeParmType>(Ty)) {
519 OS << "unnamed template type parameter " << TTPT->getIndex() << " ";
520 if (TTPT->getDepth() > 0)
521 OS << "(at depth " << TTPT->getDepth() << ") ";
522 OS << "of ";
523 NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
524 return;
525 }
526 }
527 }
528
529 if (const auto *Decl = dyn_cast<NonTypeTemplateParmDecl>(NamedTemplate)) {
530 OS << "unnamed template non-type parameter " << Decl->getIndex() << " ";
531 if (Decl->getDepth() > 0)
532 OS << "(at depth " << Decl->getDepth() << ") ";
533 OS << "of ";
534 NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
535 return;
536 }
537
538 if (const auto *Decl = dyn_cast<TemplateTemplateParmDecl>(NamedTemplate)) {
539 OS << "unnamed template template parameter " << Decl->getIndex() << " ";
540 if (Decl->getDepth() > 0)
541 OS << "(at depth " << Decl->getDepth() << ") ";
542 OS << "of ";
543 NamedCtx->getNameForDiagnostic(OS, TheSema.getLangOpts(), true);
544 return;
545 }
546
547 llvm_unreachable("Failed to retrieve a name for this entry!");
548 OS << "unnamed identifier";
549 }
550
551 template <bool BeginInstantiation>
552 static TemplightEntry getTemplightEntry(const Sema &TheSema,
553 const CodeSynthesisContext &Inst) {
554 TemplightEntry Entry;
555 Entry.Kind = toString(Inst.Kind);
556 Entry.Event = BeginInstantiation ? "Begin" : "End";
557 llvm::raw_string_ostream OS(Entry.Name);
558 printEntryName(TheSema, Inst.Entity, OS);
559 const PresumedLoc DefLoc =
560 TheSema.getSourceManager().getPresumedLoc(Inst.Entity->getLocation());
561 if (!DefLoc.isInvalid())
562 Entry.DefinitionLocation = std::string(DefLoc.getFilename()) + ":" +
563 std::to_string(DefLoc.getLine()) + ":" +
564 std::to_string(DefLoc.getColumn());
565 const PresumedLoc PoiLoc =
566 TheSema.getSourceManager().getPresumedLoc(Inst.PointOfInstantiation);
567 if (!PoiLoc.isInvalid()) {
568 Entry.PointOfInstantiation = std::string(PoiLoc.getFilename()) + ":" +
569 std::to_string(PoiLoc.getLine()) + ":" +
570 std::to_string(PoiLoc.getColumn());
571 }
572 return Entry;
573 }
574};
575} // namespace
576
577std::unique_ptr<ASTConsumer>
579 return std::make_unique<ASTConsumer>();
580}
581
584
585 // This part is normally done by ASTFrontEndAction, but needs to happen
586 // before Templight observers can be created
587 // FIXME: Move the truncation aspect of this into Sema, we delayed this till
588 // here so the source manager would be initialized.
589 EnsureSemaIsCreated(CI, *this);
590
591 CI.getSema().TemplateInstCallbacks.push_back(
592 std::make_unique<DefaultTemplateInstCallback>());
594}
595
596namespace {
597 /// AST reader listener that dumps module information for a module
598 /// file.
599 class DumpModuleInfoListener : public ASTReaderListener {
600 llvm::raw_ostream &Out;
601
602 public:
603 DumpModuleInfoListener(llvm::raw_ostream &Out) : Out(Out) { }
604
605#define DUMP_BOOLEAN(Value, Text) \
606 Out.indent(4) << Text << ": " << (Value? "Yes" : "No") << "\n"
607
608 bool ReadFullVersionInformation(StringRef FullVersion) override {
609 Out.indent(2)
610 << "Generated by "
611 << (FullVersion == getClangFullRepositoryVersion()? "this"
612 : "a different")
613 << " Clang: " << FullVersion << "\n";
615 }
616
617 void ReadModuleName(StringRef ModuleName) override {
618 Out.indent(2) << "Module name: " << ModuleName << "\n";
619 }
620 void ReadModuleMapFile(StringRef ModuleMapPath) override {
621 Out.indent(2) << "Module map file: " << ModuleMapPath << "\n";
622 }
623
624 bool ReadLanguageOptions(const LangOptions &LangOpts, bool Complain,
625 bool AllowCompatibleDifferences) override {
626 Out.indent(2) << "Language options:\n";
627#define LANGOPT(Name, Bits, Default, Description) \
628 DUMP_BOOLEAN(LangOpts.Name, Description);
629#define ENUM_LANGOPT(Name, Type, Bits, Default, Description) \
630 Out.indent(4) << Description << ": " \
631 << static_cast<unsigned>(LangOpts.get##Name()) << "\n";
632#define VALUE_LANGOPT(Name, Bits, Default, Description) \
633 Out.indent(4) << Description << ": " << LangOpts.Name << "\n";
634#define BENIGN_LANGOPT(Name, Bits, Default, Description)
635#define BENIGN_ENUM_LANGOPT(Name, Type, Bits, Default, Description)
636#include "clang/Basic/LangOptions.def"
637
638 if (!LangOpts.ModuleFeatures.empty()) {
639 Out.indent(4) << "Module features:\n";
640 for (StringRef Feature : LangOpts.ModuleFeatures)
641 Out.indent(6) << Feature << "\n";
642 }
643
644 return false;
645 }
646
647 bool ReadTargetOptions(const TargetOptions &TargetOpts, bool Complain,
648 bool AllowCompatibleDifferences) override {
649 Out.indent(2) << "Target options:\n";
650 Out.indent(4) << " Triple: " << TargetOpts.Triple << "\n";
651 Out.indent(4) << " CPU: " << TargetOpts.CPU << "\n";
652 Out.indent(4) << " TuneCPU: " << TargetOpts.TuneCPU << "\n";
653 Out.indent(4) << " ABI: " << TargetOpts.ABI << "\n";
654
655 if (!TargetOpts.FeaturesAsWritten.empty()) {
656 Out.indent(4) << "Target features:\n";
657 for (unsigned I = 0, N = TargetOpts.FeaturesAsWritten.size();
658 I != N; ++I) {
659 Out.indent(6) << TargetOpts.FeaturesAsWritten[I] << "\n";
660 }
661 }
662
663 return false;
664 }
665
666 bool ReadDiagnosticOptions(IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts,
667 bool Complain) override {
668 Out.indent(2) << "Diagnostic options:\n";
669#define DIAGOPT(Name, Bits, Default) DUMP_BOOLEAN(DiagOpts->Name, #Name);
670#define ENUM_DIAGOPT(Name, Type, Bits, Default) \
671 Out.indent(4) << #Name << ": " << DiagOpts->get##Name() << "\n";
672#define VALUE_DIAGOPT(Name, Bits, Default) \
673 Out.indent(4) << #Name << ": " << DiagOpts->Name << "\n";
674#include "clang/Basic/DiagnosticOptions.def"
675
676 Out.indent(4) << "Diagnostic flags:\n";
677 for (const std::string &Warning : DiagOpts->Warnings)
678 Out.indent(6) << "-W" << Warning << "\n";
679 for (const std::string &Remark : DiagOpts->Remarks)
680 Out.indent(6) << "-R" << Remark << "\n";
681
682 return false;
683 }
684
685 bool ReadHeaderSearchOptions(const HeaderSearchOptions &HSOpts,
686 StringRef SpecificModuleCachePath,
687 bool Complain) override {
688 Out.indent(2) << "Header search options:\n";
689 Out.indent(4) << "System root [-isysroot=]: '" << HSOpts.Sysroot << "'\n";
690 Out.indent(4) << "Resource dir [ -resource-dir=]: '" << HSOpts.ResourceDir << "'\n";
691 Out.indent(4) << "Module Cache: '" << SpecificModuleCachePath << "'\n";
693 "Use builtin include directories [-nobuiltininc]");
695 "Use standard system include directories [-nostdinc]");
697 "Use standard C++ include directories [-nostdinc++]");
698 DUMP_BOOLEAN(HSOpts.UseLibcxx,
699 "Use libc++ (rather than libstdc++) [-stdlib=]");
700 return false;
701 }
702
703 bool ReadHeaderSearchPaths(const HeaderSearchOptions &HSOpts,
704 bool Complain) override {
705 Out.indent(2) << "Header search paths:\n";
706 Out.indent(4) << "User entries:\n";
707 for (const auto &Entry : HSOpts.UserEntries)
708 Out.indent(6) << Entry.Path << "\n";
709 Out.indent(4) << "System header prefixes:\n";
710 for (const auto &Prefix : HSOpts.SystemHeaderPrefixes)
711 Out.indent(6) << Prefix.Prefix << "\n";
712 Out.indent(4) << "VFS overlay files:\n";
713 for (const auto &Overlay : HSOpts.VFSOverlayFiles)
714 Out.indent(6) << Overlay << "\n";
715 return false;
716 }
717
718 bool ReadPreprocessorOptions(const PreprocessorOptions &PPOpts,
719 bool ReadMacros, bool Complain,
720 std::string &SuggestedPredefines) override {
721 Out.indent(2) << "Preprocessor options:\n";
723 "Uses compiler/target-specific predefines [-undef]");
725 "Uses detailed preprocessing record (for indexing)");
726
727 if (ReadMacros) {
728 Out.indent(4) << "Predefined macros:\n";
729 }
730
731 for (std::vector<std::pair<std::string, bool/*isUndef*/> >::const_iterator
732 I = PPOpts.Macros.begin(), IEnd = PPOpts.Macros.end();
733 I != IEnd; ++I) {
734 Out.indent(6);
735 if (I->second)
736 Out << "-U";
737 else
738 Out << "-D";
739 Out << I->first << "\n";
740 }
741 return false;
742 }
743
744 /// Indicates that a particular module file extension has been read.
745 void readModuleFileExtension(
746 const ModuleFileExtensionMetadata &Metadata) override {
747 Out.indent(2) << "Module file extension '"
748 << Metadata.BlockName << "' " << Metadata.MajorVersion
749 << "." << Metadata.MinorVersion;
750 if (!Metadata.UserInfo.empty()) {
751 Out << ": ";
752 Out.write_escaped(Metadata.UserInfo);
753 }
754
755 Out << "\n";
756 }
757
758 /// Tells the \c ASTReaderListener that we want to receive the
759 /// input files of the AST file via \c visitInputFile.
760 bool needsInputFileVisitation() override { return true; }
761
762 /// Tells the \c ASTReaderListener that we want to receive the
763 /// input files of the AST file via \c visitInputFile.
764 bool needsSystemInputFileVisitation() override { return true; }
765
766 /// Indicates that the AST file contains particular input file.
767 ///
768 /// \returns true to continue receiving the next input file, false to stop.
769 bool visitInputFile(StringRef Filename, bool isSystem,
770 bool isOverridden, bool isExplicitModule) override {
771
772 Out.indent(2) << "Input file: " << Filename;
773
774 if (isSystem || isOverridden || isExplicitModule) {
775 Out << " [";
776 if (isSystem) {
777 Out << "System";
778 if (isOverridden || isExplicitModule)
779 Out << ", ";
780 }
781 if (isOverridden) {
782 Out << "Overridden";
783 if (isExplicitModule)
784 Out << ", ";
785 }
786 if (isExplicitModule)
787 Out << "ExplicitModule";
788
789 Out << "]";
790 }
791
792 Out << "\n";
793
794 return true;
795 }
796
797 /// Returns true if this \c ASTReaderListener wants to receive the
798 /// imports of the AST file via \c visitImport, false otherwise.
799 bool needsImportVisitation() const override { return true; }
800
801 /// If needsImportVisitation returns \c true, this is called for each
802 /// AST file imported by this AST file.
803 void visitImport(StringRef ModuleName, StringRef Filename) override {
804 Out.indent(2) << "Imports module '" << ModuleName
805 << "': " << Filename.str() << "\n";
806 }
807#undef DUMP_BOOLEAN
808 };
809}
810
812 // The Object file reader also supports raw ast files and there is no point in
813 // being strict about the module file format in -module-file-info mode.
815 return true;
816}
817
818static StringRef ModuleKindName(Module::ModuleKind MK) {
819 switch (MK) {
821 return "Module Map Module";
823 return "Interface Unit";
825 return "Implementation Unit";
827 return "Partition Interface";
829 return "Partition Implementation";
831 return "Header Unit";
833 return "Global Module Fragment";
835 return "Implicit Module Fragment";
837 return "Private Module Fragment";
838 }
839 llvm_unreachable("unknown module kind!");
840}
841
843 assert(isCurrentFileAST() && "dumping non-AST?");
844 // Set up the output file.
846 StringRef OutputFileName = CI.getFrontendOpts().OutputFile;
847 if (!OutputFileName.empty() && OutputFileName != "-") {
848 std::error_code EC;
849 OutputStream.reset(new llvm::raw_fd_ostream(
850 OutputFileName.str(), EC, llvm::sys::fs::OF_TextWithCRLF));
851 }
852 llvm::raw_ostream &Out = OutputStream ? *OutputStream : llvm::outs();
853
854 Out << "Information for module file '" << getCurrentFile() << "':\n";
855 auto &FileMgr = CI.getFileManager();
856 auto Buffer = FileMgr.getBufferForFile(getCurrentFile());
857 StringRef Magic = (*Buffer)->getMemBufferRef().getBuffer();
858 bool IsRaw = Magic.starts_with("CPCH");
859 Out << " Module format: " << (IsRaw ? "raw" : "obj") << "\n";
860
861 Preprocessor &PP = CI.getPreprocessor();
862 DumpModuleInfoListener Listener(Out);
863 HeaderSearchOptions &HSOpts = PP.getHeaderSearchInfo().getHeaderSearchOpts();
864
865 // The FrontendAction::BeginSourceFile () method loads the AST so that much
866 // of the information is already available and modules should have been
867 // loaded.
868
870 if (LO.CPlusPlusModules && !LO.CurrentModule.empty()) {
872 unsigned SubModuleCount = R->getTotalNumSubmodules();
874 Out << " ====== C++20 Module structure ======\n";
875
876 if (MF.ModuleName != LO.CurrentModule)
877 Out << " Mismatched module names : " << MF.ModuleName << " and "
878 << LO.CurrentModule << "\n";
879
880 struct SubModInfo {
881 unsigned Idx;
882 Module *Mod;
884 std::string &Name;
885 bool Seen;
886 };
887 std::map<std::string, SubModInfo> SubModMap;
888 auto PrintSubMapEntry = [&](std::string Name, Module::ModuleKind Kind) {
889 Out << " " << ModuleKindName(Kind) << " '" << Name << "'";
890 auto I = SubModMap.find(Name);
891 if (I == SubModMap.end())
892 Out << " was not found in the sub modules!\n";
893 else {
894 I->second.Seen = true;
895 Out << " is at index #" << I->second.Idx << "\n";
896 }
897 };
898 Module *Primary = nullptr;
899 for (unsigned Idx = 0; Idx <= SubModuleCount; ++Idx) {
900 Module *M = R->getModule(Idx);
901 if (!M)
902 continue;
903 if (M->Name == LO.CurrentModule) {
904 Primary = M;
905 Out << " " << ModuleKindName(M->Kind) << " '" << LO.CurrentModule
906 << "' is the Primary Module at index #" << Idx << "\n";
907 SubModMap.insert({M->Name, {Idx, M, M->Kind, M->Name, true}});
908 } else
909 SubModMap.insert({M->Name, {Idx, M, M->Kind, M->Name, false}});
910 }
911 if (Primary) {
912 if (!Primary->submodules().empty())
913 Out << " Sub Modules:\n";
914 for (auto *MI : Primary->submodules()) {
915 PrintSubMapEntry(MI->Name, MI->Kind);
916 }
917 if (!Primary->Imports.empty())
918 Out << " Imports:\n";
919 for (auto *IMP : Primary->Imports) {
920 PrintSubMapEntry(IMP->Name, IMP->Kind);
921 }
922 if (!Primary->Exports.empty())
923 Out << " Exports:\n";
924 for (unsigned MN = 0, N = Primary->Exports.size(); MN != N; ++MN) {
925 if (Module *M = Primary->Exports[MN].getPointer()) {
926 PrintSubMapEntry(M->Name, M->Kind);
927 }
928 }
929 }
930
931 // Emit the macro definitions in the module file so that we can know how
932 // much definitions in the module file quickly.
933 // TODO: Emit the macro definition bodies completely.
934 if (auto FilteredMacros = llvm::make_filter_range(
935 R->getPreprocessor().macros(),
936 [](const auto &Macro) { return Macro.first->isFromAST(); });
937 !FilteredMacros.empty()) {
938 Out << " Macro Definitions:\n";
939 for (/*<IdentifierInfo *, MacroState> pair*/ const auto &Macro :
940 FilteredMacros)
941 Out << " " << Macro.first->getName() << "\n";
942 }
943
944 // Now let's print out any modules we did not see as part of the Primary.
945 for (const auto &SM : SubModMap) {
946 if (!SM.second.Seen && SM.second.Mod) {
947 Out << " " << ModuleKindName(SM.second.Kind) << " '" << SM.first
948 << "' at index #" << SM.second.Idx
949 << " has no direct reference in the Primary\n";
950 }
951 }
952 Out << " ====== ======\n";
953 }
954
955 // The reminder of the output is produced from the listener as the AST
956 // FileCcontrolBlock is (re-)parsed.
958 getCurrentFile(), FileMgr, CI.getModuleCache(),
960 /*FindModuleFileExtensions=*/true, Listener,
962}
963
964//===----------------------------------------------------------------------===//
965// Preprocessor Actions
966//===----------------------------------------------------------------------===//
967
971
972 // Start lexing the specified input file.
973 llvm::MemoryBufferRef FromFile = SM.getBufferOrFake(SM.getMainFileID());
974 Lexer RawLex(SM.getMainFileID(), FromFile, SM, PP.getLangOpts());
975 RawLex.SetKeepWhitespaceMode(true);
976
977 Token RawTok;
978 RawLex.LexFromRawLexer(RawTok);
979 while (RawTok.isNot(tok::eof)) {
980 PP.DumpToken(RawTok, true);
981 llvm::errs() << "\n";
982 RawLex.LexFromRawLexer(RawTok);
983 }
984}
985
988 // Start preprocessing the specified input file.
989 Token Tok;
991 do {
992 PP.Lex(Tok);
993 PP.DumpToken(Tok, true);
994 llvm::errs() << "\n";
995 } while (Tok.isNot(tok::eof));
996}
997
1000
1001 // Ignore unknown pragmas.
1002 PP.IgnorePragmas();
1003
1004 Token Tok;
1005 // Start parsing the specified input file.
1007 do {
1008 PP.Lex(Tok);
1009 } while (Tok.isNot(tok::eof));
1010}
1011
1014 // Output file may need to be set to 'Binary', to avoid converting Unix style
1015 // line feeds (<LF>) to Microsoft style line feeds (<CR><LF>) on Windows.
1016 //
1017 // Look to see what type of line endings the file uses. If there's a
1018 // CRLF, then we won't open the file up in binary mode. If there is
1019 // just an LF or CR, then we will open the file up in binary mode.
1020 // In this fashion, the output format should match the input format, unless
1021 // the input format has inconsistent line endings.
1022 //
1023 // This should be a relatively fast operation since most files won't have
1024 // all of their source code on a single line. However, that is still a
1025 // concern, so if we scan for too long, we'll just assume the file should
1026 // be opened in binary mode.
1027
1028 bool BinaryMode = false;
1029 if (llvm::Triple(LLVM_HOST_TRIPLE).isOSWindows()) {
1030 BinaryMode = true;
1031 const SourceManager &SM = CI.getSourceManager();
1032 if (std::optional<llvm::MemoryBufferRef> Buffer =
1033 SM.getBufferOrNone(SM.getMainFileID())) {
1034 const char *cur = Buffer->getBufferStart();
1035 const char *end = Buffer->getBufferEnd();
1036 const char *next = (cur != end) ? cur + 1 : end;
1037
1038 // Limit ourselves to only scanning 256 characters into the source
1039 // file. This is mostly a check in case the file has no
1040 // newlines whatsoever.
1041 if (end - cur > 256)
1042 end = cur + 256;
1043
1044 while (next < end) {
1045 if (*cur == 0x0D) { // CR
1046 if (*next == 0x0A) // CRLF
1047 BinaryMode = false;
1048
1049 break;
1050 } else if (*cur == 0x0A) // LF
1051 break;
1052
1053 ++cur;
1054 ++next;
1055 }
1056 }
1057 }
1058
1059 std::unique_ptr<raw_ostream> OS =
1061 if (!OS) return;
1062
1063 // If we're preprocessing a module map, start by dumping the contents of the
1064 // module itself before switching to the input buffer.
1065 auto &Input = getCurrentInput();
1066 if (Input.getKind().getFormat() == InputKind::ModuleMap) {
1067 if (Input.isFile()) {
1068 (*OS) << "# 1 \"";
1069 OS->write_escaped(Input.getFile());
1070 (*OS) << "\"\n";
1071 }
1072 getCurrentModule()->print(*OS);
1073 (*OS) << "#pragma clang module contents\n";
1074 }
1075
1078}
1079
1081 switch (getCurrentFileKind().getLanguage()) {
1082 case Language::C:
1083 case Language::CXX:
1084 case Language::ObjC:
1085 case Language::ObjCXX:
1086 case Language::OpenCL:
1088 case Language::CUDA:
1089 case Language::HIP:
1090 case Language::HLSL:
1091 case Language::CIR:
1092 break;
1093
1094 case Language::Unknown:
1095 case Language::Asm:
1096 case Language::LLVM_IR:
1098 // We can't do anything with these.
1099 return;
1100 }
1101
1102 // We don't expect to find any #include directives in a preprocessed input.
1103 if (getCurrentFileKind().isPreprocessed())
1104 return;
1105
1107 auto Buffer = CI.getFileManager().getBufferForFile(getCurrentFile());
1108 if (Buffer) {
1109 unsigned Preamble =
1110 Lexer::ComputePreamble((*Buffer)->getBuffer(), CI.getLangOpts()).Size;
1111 llvm::outs().write((*Buffer)->getBufferStart(), Preamble);
1112 }
1113}
1114
1115void DumpCompilerOptionsAction::ExecuteAction() {
1117 std::unique_ptr<raw_ostream> OSP =
1119 if (!OSP)
1120 return;
1121
1122 raw_ostream &OS = *OSP;
1123 const Preprocessor &PP = CI.getPreprocessor();
1124 const LangOptions &LangOpts = PP.getLangOpts();
1125
1126 // FIXME: Rather than manually format the JSON (which is awkward due to
1127 // needing to remove trailing commas), this should make use of a JSON library.
1128 // FIXME: Instead of printing enums as an integral value and specifying the
1129 // type as a separate field, use introspection to print the enumerator.
1130
1131 OS << "{\n";
1132 OS << "\n\"features\" : [\n";
1133 {
1135#define FEATURE(Name, Predicate) \
1136 ("\t{\"" #Name "\" : " + llvm::Twine(Predicate ? "true" : "false") + "},\n") \
1137 .toVector(Str);
1138#include "clang/Basic/Features.def"
1139#undef FEATURE
1140 // Remove the newline and comma from the last entry to ensure this remains
1141 // valid JSON.
1142 OS << Str.substr(0, Str.size() - 2);
1143 }
1144 OS << "\n],\n";
1145
1146 OS << "\n\"extensions\" : [\n";
1147 {
1149#define EXTENSION(Name, Predicate) \
1150 ("\t{\"" #Name "\" : " + llvm::Twine(Predicate ? "true" : "false") + "},\n") \
1151 .toVector(Str);
1152#include "clang/Basic/Features.def"
1153#undef EXTENSION
1154 // Remove the newline and comma from the last entry to ensure this remains
1155 // valid JSON.
1156 OS << Str.substr(0, Str.size() - 2);
1157 }
1158 OS << "\n]\n";
1159
1160 OS << "}";
1161}
1162
1166 llvm::MemoryBufferRef FromFile = SM.getBufferOrFake(SM.getMainFileID());
1167
1171 FromFile.getBuffer(), Tokens, Directives, &CI.getDiagnostics(),
1172 SM.getLocForStartOfFile(SM.getMainFileID()))) {
1173 assert(CI.getDiagnostics().hasErrorOccurred() &&
1174 "no errors reported for failure");
1175
1176 // Preprocess the source when verifying the diagnostics to capture the
1177 // 'expected' comments.
1178 if (CI.getDiagnosticOpts().VerifyDiagnostics) {
1179 // Make sure we don't emit new diagnostics!
1183 Token Tok;
1184 do {
1185 PP.Lex(Tok);
1186 } while (Tok.isNot(tok::eof));
1187 }
1188 return;
1189 }
1190 printDependencyDirectivesAsSource(FromFile.getBuffer(), Directives,
1191 llvm::outs());
1192}
1193
1194void GetDependenciesByModuleNameAction::ExecuteAction() {
1196 Preprocessor &PP = CI.getPreprocessor();
1198 FileID MainFileID = SM.getMainFileID();
1199 SourceLocation FileStart = SM.getLocForStartOfFile(MainFileID);
1201 IdentifierInfo *ModuleID = PP.getIdentifierInfo(ModuleName);
1202 Path.push_back(std::make_pair(ModuleID, FileStart));
1203 auto ModResult = CI.loadModule(FileStart, Path, Module::Hidden, false);
1204 PPCallbacks *CB = PP.getPPCallbacks();
1205 CB->moduleImport(SourceLocation(), Path, ModResult);
1206}
#define SM(sm)
Definition: Cuda.cpp:83
This is the interface for scanning header and source files to get the minimum necessary preprocessor ...
Defines the clang::FileManager interface and associated types.
StringRef Filename
Definition: Format.cpp:2975
#define DUMP_BOOLEAN(Value, Text)
static StringRef ModuleKindName(Module::ModuleKind MK)
Defines the clang::Module class, which describes a module in the source code.
Defines the clang::Preprocessor interface.
static std::string toString(const clang::SanitizerSet &Sanitizers)
Produce a string containing comma-separated names of sanitizers in Sanitizers set.
const clang::PrintingPolicy & getPrintingPolicy() const
Definition: ASTContext.h:697
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
void ExecuteAction() override
Implement the ExecuteAction interface by running Sema on the already-initialized AST consumer.
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
Abstract interface for callback invocations by the ASTReader.
Definition: ASTReader.h:114
virtual bool ReadFullVersionInformation(StringRef FullVersion)
Receives the full Clang version information.
Definition: ASTReader.h:122
Reads an AST files chain containing the contents of a translation unit.
Definition: ASTReader.h:366
ModuleManager & getModuleManager()
Retrieve the module manager.
Definition: ASTReader.h:1773
@ ARR_ConfigurationMismatch
The client can handle an AST file that cannot load because it's compiled configuration doesn't match ...
Definition: ASTReader.h:1628
unsigned getTotalNumSubmodules() const
Returns the number of submodules known.
Definition: ASTReader.h:1869
Module * getModule(unsigned ID) override
Retrieve the module that corresponds to the given module ID.
Definition: ASTReader.cpp:8987
static bool readASTFileControlBlock(StringRef Filename, FileManager &FileMgr, const InMemoryModuleCache &ModuleCache, const PCHContainerReader &PCHContainerRdr, bool FindModuleFileExtensions, ASTReaderListener &Listener, bool ValidateDiagnosticOptions, unsigned ClientLoadCapabilities=ARR_ConfigurationMismatch|ARR_OutOfDate)
Read the control block for the named AST file.
Definition: ASTReader.cpp:5397
Preprocessor & getPreprocessor() const
Retrieve the preprocessor.
Definition: ASTReader.h:1777
const LangOptions & getLangOpts() const
Definition: ASTUnit.h:464
IntrusiveRefCntPtr< ASTReader > getASTReader() const
Definition: ASTUnit.cpp:762
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
Abstract interface for a consumer of code-completion information.
CompilerInstance - Helper class for managing a single instance of the Clang compiler.
const PCHContainerReader & getPCHContainerReader() const
Return the appropriate PCHContainerReader depending on the current CodeGenOptions.
DiagnosticsEngine & getDiagnostics() const
Get the current diagnostics engine.
std::unique_ptr< raw_pwrite_stream > createDefaultOutputFile(bool Binary=true, StringRef BaseInput="", StringRef Extension="", bool RemoveFileOnSignal=true, bool CreateMissingDirectories=false, bool ForceUseTemporary=false)
Create the default output file (from the invocation's options) and add it to the list of tracked outp...
ModuleLoadResult loadModule(SourceLocation ImportLoc, ModuleIdPath Path, Module::NameVisibilityKind Visibility, bool IsInclusionDirective) override
Attempt to load the given module.
FileManager & getFileManager() const
Return the current file manager to the caller.
PreprocessorOutputOptions & getPreprocessorOutputOpts()
InMemoryModuleCache & getModuleCache() const
Preprocessor & getPreprocessor() const
Return the current preprocessor.
ASTContext & getASTContext() const
FrontendOptions & getFrontendOpts()
HeaderSearchOptions & getHeaderSearchOpts()
bool hasCodeCompletionConsumer() const
const PCHContainerWriter & getPCHContainerWriter() const
Return the appropriate PCHContainerWriter depending on the current CodeGenOptions.
PreprocessorOptions & getPreprocessorOpts()
void createCodeCompletionConsumer()
Create a code completion consumer using the invocation; note that this will cause the source manager ...
DiagnosticOptions & getDiagnosticOpts()
LangOptions & getLangOpts()
SourceManager & getSourceManager() const
Return the current source manager.
CodeCompleteConsumer & getCodeCompletionConsumer() const
void createSema(TranslationUnitKind TUKind, CodeCompleteConsumer *CompletionConsumer)
Create the Sema object to be used for parsing.
Decl - This represents one declaration (or definition), e.g.
Definition: DeclBase.h:86
static Decl * castFromDeclContext(const DeclContext *)
Definition: DeclBase.cpp:1019
SourceLocation getLocation() const
Definition: DeclBase.h:445
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
Definition: Diagnostic.h:1547
bool hasErrorOccurred() const
Definition: Diagnostic.h:843
void setSuppressAllDiagnostics(bool Val)
Suppress all diagnostics, to silence the front end when we know that we don't want any more diagnosti...
Definition: Diagnostic.h:697
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
void ExecuteAction() override
Implement the ExecuteAction interface by running Sema on the already-initialized AST consumer.
bool BeginInvocation(CompilerInstance &CI) override
Callback before starting processing a single input, giving the opportunity to modify the CompilerInvo...
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
An opaque identifier used by SourceManager which refers to a source file (MemoryBuffer) along with it...
llvm::ErrorOr< std::unique_ptr< llvm::MemoryBuffer > > getBufferForFile(FileEntryRef Entry, bool isVolatile=false, bool RequiresNullTerminator=true)
Open the specified file as a MemoryBuffer, returning a new MemoryBuffer if successful,...
Abstract base class for actions which can be performed by the frontend.
const FrontendInputFile & getCurrentInput() const
InputKind getCurrentFileKind() const
virtual bool shouldEraseOutputFiles()
Callback at the end of processing a single input, to determine if the output files should be erased o...
ASTUnit & getCurrentASTUnit() const
CompilerInstance & getCompilerInstance() const
Module * getCurrentModule() const
StringRef getCurrentFile() const
virtual bool BeginSourceFileAction(CompilerInstance &CI)
Callback at the start of processing a single input.
virtual TranslationUnitKind getTranslationUnitKind()
For AST-based actions, the kind of translation unit we're handling.
virtual bool hasCodeCompletionSupport() const
Does this action support use with code completion?
StringRef getCurrentFileOrBufferName() const
bool isCurrentFileAST() const
FrontendOptions - Options for controlling the behavior of the frontend.
unsigned BuildingImplicitModule
Whether we are performing an implicit module build.
unsigned AllowPCMWithCompilerErrors
Output (and read) PCM files regardless of compiler errors.
unsigned IncludeTimestamps
Whether timestamps should be written to the produced PCH file.
std::string ASTDumpFilter
If given, filter dumped AST Decl nodes by this substring.
unsigned ASTDumpLookups
Whether we include lookup table dumps in AST dumps.
ASTDumpOutputFormat ASTDumpFormat
Specifies the output format of the AST.
std::string OutputFile
The output file, if any.
unsigned GenReducedBMI
Whether to generate reduced BMI for C++20 named modules.
std::vector< std::shared_ptr< ModuleFileExtension > > ModuleFileExtensions
The list of module file extensions.
ParsedSourceLocation CodeCompletionAt
If given, enable code completion at the provided location.
std::string OriginalModuleMap
When the input is a module map, the original module map file from which that map was inferred,...
std::string ModuleOutputPath
Output Path for module output file.
unsigned ASTDumpDeclTypes
Whether we include declaration type dumps in AST dumps.
unsigned ASTDumpAll
Whether we deserialize all decls when forming AST dumps.
unsigned RelocatablePCH
When generating PCH files, instruct the AST writer to create relocatable PCH files.
unsigned ASTDumpDecls
Whether we include declaration dumps in AST dumps.
bool shouldEraseOutputFiles() override
Callback at the end of processing a single input, to determine if the output files should be erased o...
std::vector< std::unique_ptr< ASTConsumer > > CreateMultiplexConsumer(CompilerInstance &CI, StringRef InFile)
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
bool BeginSourceFileAction(CompilerInstance &CI) override
Callback at the start of processing a single input.
std::unique_ptr< raw_pwrite_stream > CreateOutputFile(CompilerInstance &CI, StringRef InFile) override
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
static std::unique_ptr< llvm::raw_pwrite_stream > CreateOutputFile(CompilerInstance &CI, StringRef InFile, std::string &OutputFile)
Creates file to write the PCH into and returns a stream to write it into.
bool BeginSourceFileAction(CompilerInstance &CI) override
Callback at the start of processing a single input.
static bool ComputeASTConsumerArguments(CompilerInstance &CI, std::string &Sysroot)
Compute the AST consumer arguments that will be used to create the PCHGenerator instance returned by ...
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
bool shouldEraseOutputFiles() override
Callback at the end of processing a single input, to determine if the output files should be erased o...
HeaderSearchOptions - Helper class for storing options related to the initialization of the HeaderSea...
std::vector< SystemHeaderPrefix > SystemHeaderPrefixes
User-specified system header prefixes.
std::string ModuleFormat
The module/pch container format.
std::string Sysroot
If non-empty, the directory to use as a "virtual system root" for include paths.
std::vector< std::string > VFSOverlayFiles
The set of user-provided virtual filesystem overlay files.
unsigned UseLibcxx
Use libc++ instead of the default libstdc++.
unsigned UseBuiltinIncludes
Include the compiler builtin includes.
unsigned UseStandardCXXIncludes
Include the system standard C++ library include search directories.
std::vector< Entry > UserEntries
User specified include entries.
std::string ResourceDir
The directory which holds the compiler resource files (builtin includes, etc.).
unsigned UseStandardSystemIncludes
Include the system standard include search directories.
Encapsulates the information needed to find the file referenced by a #include or #include_next,...
Definition: HeaderSearch.h:253
std::string getCachedModuleFileName(Module *Module)
Retrieve the name of the cached module file that should be used to load the given module.
One of these records is kept for each identifier that is lexed.
@ CMK_HeaderUnit
Compiling a module header unit.
Definition: LangOptions.h:105
@ CMK_ModuleInterface
Compiling a C++ modules interface unit.
Definition: LangOptions.h:108
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
Definition: LangOptions.h:461
std::string CurrentModule
The name of the current module, of which the main source file is a part.
Definition: LangOptions.h:516
std::vector< std::string > ModuleFeatures
The names of any features to enable in module 'requires' decls in addition to the hard-coded list in ...
Definition: LangOptions.h:522
Lexer - This provides a simple interface that turns a text buffer into a stream of tokens.
Definition: Lexer.h:78
void SetKeepWhitespaceMode(bool Val)
SetKeepWhitespaceMode - This method lets clients enable or disable whitespace retention mode.
Definition: Lexer.h:254
bool LexFromRawLexer(Token &Result)
LexFromRawLexer - Lex a token from a designated raw lexer (one with no associated preprocessor object...
Definition: Lexer.h:236
static PreambleBounds ComputePreamble(StringRef Buffer, const LangOptions &LangOpts, unsigned MaxLines=0)
Compute the preamble of the given file.
Definition: Lexer.cpp:637
Describes a module or submodule.
Definition: Module.h:105
SmallVector< ExportDecl, 2 > Exports
The set of export declarations.
Definition: Module.h:415
@ Hidden
All of the names in this module are hidden.
Definition: Module.h:389
void print(raw_ostream &OS, unsigned Indent=0, bool Dump=false) const
Print the module map for this module to the given stream.
Definition: Module.cpp:482
ModuleKind Kind
The kind of this module.
Definition: Module.h:150
llvm::SmallSetVector< Module *, 2 > Imports
The set of modules imported by this module, and on which this module depends.
Definition: Module.h:402
std::string Name
The name of this module.
Definition: Module.h:108
llvm::iterator_range< submodule_iterator > submodules()
Definition: Module.h:783
@ ModuleImplementationUnit
This is a C++20 module implementation unit.
Definition: Module.h:128
@ ModuleMapModule
This is a module that was defined by a module map and built out of header files.
Definition: Module.h:119
@ ImplicitGlobalModuleFragment
This is an implicit fragment of the global module which contains only language linkage declarations (...
Definition: Module.h:146
@ ModulePartitionInterface
This is a C++20 module partition interface.
Definition: Module.h:131
@ ModuleInterfaceUnit
This is a C++20 module interface unit.
Definition: Module.h:125
@ ModuleHeaderUnit
This is a C++20 header unit.
Definition: Module.h:122
@ ModulePartitionImplementation
This is a C++20 module partition implementation.
Definition: Module.h:134
@ PrivateModuleFragment
This is the private module fragment within some C++ module.
Definition: Module.h:141
@ ExplicitGlobalModuleFragment
This is the explicit Global Module Fragment of a modular TU.
Definition: Module.h:138
This represents a decl that may have a name.
Definition: Decl.h:249
virtual void getNameForDiagnostic(raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const
Appends a human-readable name for this declaration into the given stream.
Definition: Decl.cpp:1826
virtual std::unique_ptr< ASTConsumer > CreatePCHContainerGenerator(CompilerInstance &CI, const std::string &MainFileName, const std::string &OutputFileName, std::unique_ptr< llvm::raw_pwrite_stream > OS, std::shared_ptr< PCHBuffer > Buffer) const =0
Return an ASTConsumer that can be chained with a PCHGenerator that produces a wrapper file format con...
This interface provides a way to observe the actions of the preprocessor as it does its thing.
Definition: PPCallbacks.h:35
virtual void moduleImport(SourceLocation ImportLoc, ModuleIdPath Path, const Module *Imported)
Callback invoked whenever there was an explicit module-import syntax.
Definition: PPCallbacks.h:180
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
PreprocessorOptions - This class is used for passing the various options used in preprocessor initial...
std::pair< unsigned, bool > PrecompiledPreambleBytes
If non-zero, the implicit PCH include is actually a precompiled preamble that covers this number of b...
bool DetailedRecord
Whether we should maintain a detailed record of all macro definitions and expansions.
bool UsePredefines
Initialize the preprocessor with the compiler and target specific predefines.
std::vector< std::pair< std::string, bool > > Macros
bool AllowPCHWithCompilerErrors
When true, a PCH with compiler errors will not be rejected.
Engages in a tight little dance with the lexer to efficiently preprocess tokens.
Definition: Preprocessor.h:128
void DumpToken(const Token &Tok, bool DumpFlags=false) const
Print the token to stderr, used for debugging.
void IgnorePragmas()
Install empty handlers for all pragmas (making them ignored).
Definition: Pragma.cpp:2196
PPCallbacks * getPPCallbacks() const
void Lex(Token &Result)
Lex the next token for this preprocessor.
void EnterMainSourceFile()
Enter the specified FileID as the main source file, which implicitly adds the builtin defines etc.
IdentifierInfo * getIdentifierInfo(StringRef Name) const
Return information about the specified preprocessor identifier token.
SourceManager & getSourceManager() const
llvm::iterator_range< macro_iterator > macros(bool IncludeExternalMacros=true) const
HeaderSearch & getHeaderSearchInfo() const
const LangOptions & getLangOpts() const
Represents an unpacked "presumed" location which can be presented to the user.
unsigned getColumn() const
Return the presumed column number of this location.
const char * getFilename() const
Return the presumed filename of this location.
unsigned getLine() const
Return the presumed line number of this location.
bool isInvalid() const
Return true if this object is invalid or uninitialized.
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
Sema - This implements semantic analysis and AST building for C.
Definition: Sema.h:451
ASTContext & Context
Definition: Sema.h:848
const LangOptions & getLangOpts() const
Definition: Sema.h:510
std::vector< std::unique_ptr< TemplateInstantiationCallback > > TemplateInstCallbacks
The template instantiation callbacks to trace or track instantiations (objects can be chained).
Definition: Sema.h:10209
SourceManager & getSourceManager() const
Definition: Sema.h:515
Encodes a location in the source.
void print(raw_ostream &OS, const SourceManager &SM) const
This class handles loading and caching of source files into memory.
PresumedLoc getPresumedLoc(SourceLocation Loc, bool UseLineDirectives=true) const
Returns the "presumed" location of a SourceLocation specifies.
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
Options for controlling the target.
Definition: TargetOptions.h:26
std::string Triple
The name of the target triple to compile for.
Definition: TargetOptions.h:29
std::string ABI
If given, the name of the target ABI to use.
Definition: TargetOptions.h:45
std::string TuneCPU
If given, the name of the target CPU to tune code for.
Definition: TargetOptions.h:39
std::string CPU
If given, the name of the target CPU to generate code for.
Definition: TargetOptions.h:36
std::vector< std::string > FeaturesAsWritten
The list of target specific features to enable or disable, as written on the command line.
Definition: TargetOptions.h:54
This is a base class for callbacks that will be notified at every template instantiation.
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
void ExecuteAction() override
Implement the ExecuteAction interface by running Sema on the already-initialized AST consumer.
Token - This structure provides full information about a lexed token.
Definition: Token.h:36
bool isNot(tok::TokenKind K) const
Definition: Token.h:100
The base class of the type hierarchy.
Definition: Type.h:1813
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
void ExecuteAction() override
Implement the ExecuteAction interface by running Sema on the already-initialized AST consumer.
Information about a module that has been loaded by the ASTReader.
Definition: ModuleFile.h:124
std::string ModuleName
The name of the module.
Definition: ModuleFile.h:142
ModuleFile & getPrimaryModule()
Returns the primary module associated with the manager, that is, the first module loaded.
Defines the clang::TargetInfo interface.
@ MK_PCH
File is a PCH file treated as such.
Definition: ModuleFile.h:50
@ MK_Preamble
File is a PCH file treated as the preamble.
Definition: ModuleFile.h:53
The JSON file list parser is used to communicate input to InstallAPI.
void atTemplateEnd(TemplateInstantiationCallbackPtrs &Callbacks, const Sema &TheSema, const Sema::CodeSynthesisContext &Inst)
void atTemplateBegin(TemplateInstantiationCallbackPtrs &Callbacks, const Sema &TheSema, const Sema::CodeSynthesisContext &Inst)
void printDependencyDirectivesAsSource(StringRef Source, ArrayRef< dependency_directives_scan::Directive > Directives, llvm::raw_ostream &OS)
Print the previously scanned dependency directives as minimized source text.
void initialize(TemplateInstantiationCallbackPtrs &Callbacks, const Sema &TheSema)
bool scanSourceForDependencyDirectives(StringRef Input, SmallVectorImpl< dependency_directives_scan::Token > &Tokens, SmallVectorImpl< dependency_directives_scan::Directive > &Directives, DiagnosticsEngine *Diags=nullptr, SourceLocation InputSourceLoc=SourceLocation())
Scan the input for the preprocessor directives that might have an effect on the dependencies for a co...
std::unique_ptr< ASTConsumer > CreateASTDeclNodeLister()
@ C
Languages that the frontend can parse and compile.
@ CIR
LLVM IR & CIR: we accept these so that we can run the optimizer on them, and compile them to assembly...
@ Asm
Assembly: we accept this only so that we can preprocess it.
void DoPrintPreprocessedInput(Preprocessor &PP, raw_ostream *OS, const PreprocessorOutputOptions &Opts)
DoPrintPreprocessedInput - Implement -E mode.
std::unique_ptr< ASTConsumer > CreateASTDumper(std::unique_ptr< raw_ostream > OS, StringRef FilterString, bool DumpDecls, bool Deserialize, bool DumpLookups, bool DumpDeclTypes, ASTDumpOutputFormat Format)
std::unique_ptr< ASTConsumer > CreateASTPrinter(std::unique_ptr< raw_ostream > OS, StringRef FilterString)
std::unique_ptr< ASTConsumer > CreateASTViewer()
@ None
Perform validation, don't disable it.
std::string getClangFullRepositoryVersion()
Retrieves the full repository version that is an amalgamation of the information in getClangRepositor...
Definition: Version.cpp:68
void finalize(TemplateInstantiationCallbackPtrs &Callbacks, const Sema &TheSema)
Diagnostic wrappers for TextAPI types for error reporting.
Definition: Dominators.h:30
Metadata for a module file extension.
unsigned MajorVersion
The major version of the extension data.
std::string UserInfo
A string containing additional user information that will be stored with the metadata.
std::string BlockName
The name used to identify this particular extension block within the resulting module file.
unsigned MinorVersion
The minor version of the extension data.
unsigned Size
Size of the preamble in bytes.
Definition: Lexer.h:62
Describes how types, statements, expressions, and declarations should be printed.
Definition: PrettyPrinter.h:57
unsigned SuppressDefaultTemplateArgs
When true, attempt to suppress template arguments that match the default argument for the parameter.
A context in which code is being synthesized (where a source location alone is not sufficient to iden...
Definition: Sema.h:9720
static void mapping(IO &io, TemplightEntry &fields)