clang 24.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"
15#include "clang/Basic/Module.h"
29#include "llvm/Config/llvm-config.h" // for LLVM_HOST_TRIPLE
30#include "llvm/Support/ErrorHandling.h"
31#include "llvm/Support/FileSystem.h"
32#include "llvm/Support/MemoryBuffer.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
41//===----------------------------------------------------------------------===//
42// Custom Actions
43//===----------------------------------------------------------------------===//
44
45std::unique_ptr<ASTConsumer>
46InitOnlyAction::CreateASTConsumer(CompilerInstance &CI, StringRef InFile) {
47 return std::make_unique<ASTConsumer>();
48}
49
51}
52
53// Basically PreprocessOnlyAction::ExecuteAction.
55 Preprocessor &PP = getCompilerInstance().getPreprocessor();
56
57 // Ignore unknown pragmas.
58 PP.IgnorePragmas();
59
60 Token Tok;
61 // Start parsing the specified input file.
63 do {
64 PP.Lex(Tok);
65 } while (Tok.isNot(tok::eof));
66}
67
68std::unique_ptr<ASTConsumer>
69ReadPCHAndPreprocessAction::CreateASTConsumer(CompilerInstance &CI,
70 StringRef InFile) {
71 return std::make_unique<ASTConsumer>();
72}
73
74//===----------------------------------------------------------------------===//
75// AST Consumer Actions
76//===----------------------------------------------------------------------===//
77
78std::unique_ptr<ASTConsumer>
80 if (std::unique_ptr<raw_ostream> OS =
81 CI.createDefaultOutputFile(false, InFile))
82 return CreateASTPrinter(std::move(OS), CI.getFrontendOpts().ASTDumpFilter);
83 return nullptr;
84}
85
86std::unique_ptr<ASTConsumer>
88 const FrontendOptions &Opts = CI.getFrontendOpts();
89 return CreateASTDumper(nullptr /*Dump to stdout.*/, Opts.ASTDumpFilter,
90 Opts.ASTDumpDecls, Opts.ASTDumpAll,
92 Opts.ASTDumpFormat);
93}
94
95std::unique_ptr<ASTConsumer>
99
100std::unique_ptr<ASTConsumer>
102 return CreateASTViewer();
103}
104
105std::unique_ptr<ASTConsumer>
107 std::string Sysroot;
108 if (!ComputeASTConsumerArguments(CI, /*ref*/ Sysroot))
109 return nullptr;
110
111 std::string OutputFile;
112 std::unique_ptr<raw_pwrite_stream> OS =
113 CreateOutputFile(CI, InFile, /*ref*/ OutputFile, SetOnlyIfDifferent);
114 if (!OS)
115 return nullptr;
116
118 Sysroot.clear();
119
120 const auto &FrontendOpts = CI.getFrontendOpts();
121 auto Buffer = std::make_shared<PCHBuffer>();
122 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
123 Consumers.push_back(std::make_unique<PCHGenerator>(
124 CI.getPreprocessor(), CI.getModuleCache(), OutputFile, Sysroot, Buffer,
125 CI.getCodeGenOpts(), FrontendOpts.ModuleFileExtensions,
127 FrontendOpts.IncludeTimestamps, FrontendOpts.BuildingImplicitModule));
128 Consumers.push_back(CI.getPCHContainerWriter().CreatePCHContainerGenerator(
129 CI, std::string(InFile), OutputFile, std::move(OS), Buffer));
130
131 return std::make_unique<MultiplexConsumer>(std::move(Consumers));
132}
133
135 std::string &Sysroot) {
136 Sysroot = CI.getHeaderSearchOpts().Sysroot;
137 if (CI.getFrontendOpts().RelocatablePCH && Sysroot.empty()) {
138 CI.getDiagnostics().Report(diag::err_relocatable_without_isysroot);
139 return false;
140 }
141
142 return true;
143}
144
145std::unique_ptr<llvm::raw_pwrite_stream>
147 std::string &OutputFile,
148 bool SetOnlyIfDifferent) {
149 // Because this is exposed via libclang we must disable RemoveFileOnSignal.
150 std::unique_ptr<raw_pwrite_stream> OS = CI.createDefaultOutputFile(
151 /*Binary=*/true, InFile, /*Extension=*/"", /*RemoveFileOnSignal=*/false,
152 /*CreateMissingDirectories=*/false, /*ForceUseTemporary=*/false,
154 if (!OS)
155 return nullptr;
156
157 OutputFile = CI.getFrontendOpts().OutputFile;
158 return OS;
159}
160
162 if (getCompilerInstance().getPreprocessorOpts().AllowPCHWithCompilerErrors)
163 return false;
165}
166
171
172std::vector<std::unique_ptr<ASTConsumer>>
174 StringRef InFile) {
175 if (!OS)
176 OS = CreateOutputFile(CI, InFile);
177 if (!OS)
178 return {};
179
180 std::string OutputFile = CI.getFrontendOpts().OutputFile;
181 std::string Sysroot;
182
183 auto Buffer = std::make_shared<PCHBuffer>();
184 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
185
186 Consumers.push_back(std::make_unique<PCHGenerator>(
187 CI.getPreprocessor(), CI.getModuleCache(), OutputFile, Sysroot, Buffer,
189 /*AllowASTWithErrors=*/
191 /*IncludeTimestamps=*/
194 /*BuildingImplicitModule=*/+CI.getFrontendOpts().BuildingImplicitModule));
195 Consumers.push_back(CI.getPCHContainerWriter().CreatePCHContainerGenerator(
196 CI, std::string(InFile), OutputFile, std::move(OS), Buffer));
197 return Consumers;
198}
199
200std::unique_ptr<ASTConsumer>
202 StringRef InFile) {
203 std::vector<std::unique_ptr<ASTConsumer>> Consumers =
204 CreateMultiplexConsumer(CI, InFile);
205 if (Consumers.empty())
206 return nullptr;
207
208 return std::make_unique<MultiplexConsumer>(std::move(Consumers));
209}
210
215
216bool GenerateModuleFromModuleMapAction::BeginSourceFileAction(
217 CompilerInstance &CI) {
218 if (!CI.getLangOpts().Modules) {
219 CI.getDiagnostics().Report(diag::err_module_build_requires_fmodules);
220 return false;
221 }
222
224}
225
226std::unique_ptr<raw_pwrite_stream>
227GenerateModuleFromModuleMapAction::CreateOutputFile(CompilerInstance &CI,
228 StringRef InFile) {
229 // If no output file was provided, figure out where this module would go
230 // in the module cache.
231 if (CI.getFrontendOpts().OutputFile.empty()) {
232 StringRef ModuleMapFile = CI.getFrontendOpts().OriginalModuleMap;
233 if (ModuleMapFile.empty())
234 ModuleMapFile = InFile;
235
237 ModuleFileName FileName = HS.getCachedModuleFileName(
238 CI.getLangOpts().CurrentModule, ModuleMapFile);
240 }
241
242 // Because this is exposed via libclang we must disable RemoveFileOnSignal.
243 return CI.createDefaultOutputFile(/*Binary=*/true, InFile, /*Extension=*/"",
244 /*RemoveFileOnSignal=*/false,
245 /*CreateMissingDirectories=*/true,
246 /*ForceUseTemporary=*/true,
247 /*SetOnlyIfDifferent=*/SetOnlyIfDifferent);
248}
249
251 CompilerInstance &CI) {
252 for (const auto &FIF : CI.getFrontendOpts().Inputs) {
253 if (const auto InputFormat = FIF.getKind().getFormat();
254 InputFormat != InputKind::Format::Source) {
256 diag::err_frontend_action_unsupported_input_format)
257 << "module interface compilation" << FIF.getFile() << InputFormat;
258 return false;
259 }
260 }
262}
263
270
271std::unique_ptr<ASTConsumer>
273 StringRef InFile) {
274 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
275
277 !CI.getFrontendOpts().ModuleOutputPath.empty()) {
278 Consumers.push_back(std::make_unique<ReducedBMIGenerator>(
282 }
283
284 Consumers.push_back(std::make_unique<CXX20ModulesGenerator>(
288
289 return std::make_unique<MultiplexConsumer>(std::move(Consumers));
290}
291
292std::unique_ptr<raw_pwrite_stream>
294 StringRef InFile) {
295 return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
296}
297
298std::unique_ptr<ASTConsumer>
299GenerateReducedModuleInterfaceAction::CreateASTConsumer(CompilerInstance &CI,
300 StringRef InFile) {
301 return std::make_unique<ReducedBMIGenerator>(
304}
305
306bool GenerateHeaderUnitAction::BeginSourceFileAction(CompilerInstance &CI) {
307 if (!CI.getLangOpts().CPlusPlusModules) {
308 CI.getDiagnostics().Report(diag::err_module_interface_requires_cpp_modules);
309 return false;
310 }
311 CI.getLangOpts().setCompilingModule(LangOptions::CMK_HeaderUnit);
313}
314
315std::unique_ptr<raw_pwrite_stream>
316GenerateHeaderUnitAction::CreateOutputFile(CompilerInstance &CI,
317 StringRef InFile) {
318 return CI.createDefaultOutputFile(/*Binary=*/true, InFile, "pcm");
319}
320
323
324std::unique_ptr<ASTConsumer>
326 return std::make_unique<ASTConsumer>();
327}
328
329std::unique_ptr<ASTConsumer>
331 StringRef InFile) {
332 return std::make_unique<ASTConsumer>();
333}
334
335std::unique_ptr<ASTConsumer>
337 return std::make_unique<ASTConsumer>();
338}
339
343 const std::string &Sysroot = CI.getHeaderSearchOpts().Sysroot;
344 std::unique_ptr<ASTReader> Reader(new ASTReader(
348 Sysroot.empty() ? "" : Sysroot.c_str(),
350 /*AllowASTWithCompilerErrors*/ false,
351 /*AllowConfigurationMismatch*/ true,
352 /*ValidateSystemInputs*/ true, /*ForceValidateUserInputs*/ true));
353
357}
358
359namespace {
360 /// AST reader listener that dumps module information for a module
361 /// file.
362 class DumpModuleInfoListener : public ASTReaderListener {
363 llvm::raw_ostream &Out;
365
366 public:
367 DumpModuleInfoListener(llvm::raw_ostream &Out, FileManager &FileMgr)
368 : Out(Out), FileMgr(FileMgr) {}
369
370#define DUMP_BOOLEAN(Value, Text) \
371 Out.indent(4) << Text << ": " << (Value? "Yes" : "No") << "\n"
372
373 bool ReadFullVersionInformation(StringRef FullVersion) override {
374 Out.indent(2)
375 << "Generated by "
376 << (FullVersion == getClangFullRepositoryVersion()? "this"
377 : "a different")
378 << " Clang: " << FullVersion << "\n";
380 }
381
382 void ReadModuleName(StringRef ModuleName) override {
383 Out.indent(2) << "Module name: " << ModuleName << "\n";
384 }
385 void ReadModuleMapFile(StringRef ModuleMapPath) override {
386 Out.indent(2) << "Module map file: " << ModuleMapPath << "\n";
387 }
388
389 bool ReadLanguageOptions(const LangOptions &LangOpts,
390 StringRef ModuleFilename, bool Complain,
391 bool AllowCompatibleDifferences) override {
392 // FIXME: Replace with C++20 `using enum LangOptions::CompatibilityKind`.
393 using CK = LangOptions::CompatibilityKind;
394
395 Out.indent(2) << "Language options:\n";
396#define LANGOPT(Name, Bits, Default, Compatibility, Description) \
397 if constexpr (CK::Compatibility != CK::Benign) \
398 DUMP_BOOLEAN(LangOpts.Name, Description);
399#define ENUM_LANGOPT(Name, Type, Bits, Default, Compatibility, Description) \
400 if constexpr (CK::Compatibility != CK::Benign) \
401 Out.indent(4) << Description << ": " \
402 << static_cast<unsigned>(LangOpts.get##Name()) << "\n";
403#define VALUE_LANGOPT(Name, Bits, Default, Compatibility, Description) \
404 if constexpr (CK::Compatibility != CK::Benign) \
405 Out.indent(4) << Description << ": " << LangOpts.Name << "\n";
406#include "clang/Basic/LangOptions.def"
407
408 if (!LangOpts.ModuleFeatures.empty()) {
409 Out.indent(4) << "Module features:\n";
410 for (StringRef Feature : LangOpts.ModuleFeatures)
411 Out.indent(6) << Feature << "\n";
412 }
413
414 return false;
415 }
416
417 bool ReadTargetOptions(const TargetOptions &TargetOpts,
418 StringRef ModuleFilename, bool Complain,
419 bool AllowCompatibleDifferences) override {
420 Out.indent(2) << "Target options:\n";
421 Out.indent(4) << " Triple: " << TargetOpts.Triple << "\n";
422 Out.indent(4) << " CPU: " << TargetOpts.CPU << "\n";
423 Out.indent(4) << " TuneCPU: " << TargetOpts.TuneCPU << "\n";
424 Out.indent(4) << " ABI: " << TargetOpts.ABI << "\n";
425
426 if (!TargetOpts.FeaturesAsWritten.empty()) {
427 Out.indent(4) << "Target features:\n";
428 for (unsigned I = 0, N = TargetOpts.FeaturesAsWritten.size();
429 I != N; ++I) {
430 Out.indent(6) << TargetOpts.FeaturesAsWritten[I] << "\n";
431 }
432 }
433
434 return false;
435 }
436
437 bool ReadDiagnosticOptions(DiagnosticOptions &DiagOpts,
438 StringRef ModuleFilename,
439 bool Complain) override {
440 Out.indent(2) << "Diagnostic options:\n";
441#define DIAGOPT(Name, Bits, Default) DUMP_BOOLEAN(DiagOpts.Name, #Name);
442#define ENUM_DIAGOPT(Name, Type, Bits, Default) \
443 Out.indent(4) << #Name << ": " \
444 << static_cast<unsigned>(DiagOpts.get##Name()) << "\n";
445#define VALUE_DIAGOPT(Name, Bits, Default) \
446 Out.indent(4) << #Name << ": " << DiagOpts.Name << "\n";
447#include "clang/Basic/DiagnosticOptions.def"
448
449 Out.indent(4) << "Diagnostic flags:\n";
450 for (const std::string &Warning : DiagOpts.Warnings)
451 Out.indent(6) << "-W" << Warning << "\n";
452 for (const std::string &Remark : DiagOpts.Remarks)
453 Out.indent(6) << "-R" << Remark << "\n";
454
455 return false;
456 }
457
458 bool ReadHeaderSearchOptions(const HeaderSearchOptions &HSOpts,
459 StringRef ModuleFilename,
460 StringRef ContextHash,
461 bool Complain) override {
462 std::string SpecificModuleCachePath = createSpecificModuleCachePath(
463 FileMgr, HSOpts.ModuleCachePath, HSOpts.DisableModuleHash,
464 std::string(ContextHash));
465
466 Out.indent(2) << "Header search options:\n";
467 Out.indent(4) << "System root [-isysroot=]: '" << HSOpts.Sysroot << "'\n";
468 Out.indent(4) << "Resource dir [ -resource-dir=]: '" << HSOpts.ResourceDir << "'\n";
469 Out.indent(4) << "Module Cache: '" << SpecificModuleCachePath << "'\n";
471 "Use builtin include directories [-nobuiltininc]");
473 "Use standard system include directories [-nostdinc]");
475 "Use standard C++ include directories [-nostdinc++]");
476 DUMP_BOOLEAN(HSOpts.UseLibcxx,
477 "Use libc++ (rather than libstdc++) [-stdlib=]");
478 return false;
479 }
480
481 bool ReadHeaderSearchPaths(const HeaderSearchOptions &HSOpts,
482 bool Complain) override {
483 Out.indent(2) << "Header search paths:\n";
484 Out.indent(4) << "User entries:\n";
485 for (const auto &Entry : HSOpts.UserEntries)
486 Out.indent(6) << Entry.Path << "\n";
487 Out.indent(4) << "System header prefixes:\n";
488 for (const auto &Prefix : HSOpts.SystemHeaderPrefixes)
489 Out.indent(6) << Prefix.Prefix << "\n";
490 Out.indent(4) << "VFS overlay files:\n";
491 for (const auto &Overlay : HSOpts.VFSOverlayFiles)
492 Out.indent(6) << Overlay << "\n";
493 return false;
494 }
495
496 bool ReadPreprocessorOptions(const PreprocessorOptions &PPOpts,
497 StringRef ModuleFilename, bool ReadMacros,
498 bool Complain,
499 std::string &SuggestedPredefines) override {
500 Out.indent(2) << "Preprocessor options:\n";
502 "Uses compiler/target-specific predefines [-undef]");
504 "Uses detailed preprocessing record (for indexing)");
505
506 if (ReadMacros) {
507 Out.indent(4) << "Predefined macros:\n";
508 }
509
510 for (std::vector<std::pair<std::string, bool/*isUndef*/> >::const_iterator
511 I = PPOpts.Macros.begin(), IEnd = PPOpts.Macros.end();
512 I != IEnd; ++I) {
513 Out.indent(6);
514 if (I->second)
515 Out << "-U";
516 else
517 Out << "-D";
518 Out << I->first << "\n";
519 }
520 return false;
521 }
522
523 /// Indicates that a particular module file extension has been read.
524 void readModuleFileExtension(
525 const ModuleFileExtensionMetadata &Metadata) override {
526 Out.indent(2) << "Module file extension '"
527 << Metadata.BlockName << "' " << Metadata.MajorVersion
528 << "." << Metadata.MinorVersion;
529 if (!Metadata.UserInfo.empty()) {
530 Out << ": ";
531 Out.write_escaped(Metadata.UserInfo);
532 }
533
534 Out << "\n";
535 }
536
537 /// Tells the \c ASTReaderListener that we want to receive the
538 /// input files of the AST file via \c visitInputFile.
539 bool needsInputFileVisitation() override { return true; }
540
541 /// Tells the \c ASTReaderListener that we want to receive the
542 /// input files of the AST file via \c visitInputFile.
543 bool needsSystemInputFileVisitation() override { return true; }
544
545 /// Indicates that the AST file contains particular input file.
546 ///
547 /// \returns true to continue receiving the next input file, false to stop.
548 bool visitInputFileAsRequested(StringRef FilenameAsRequested,
549 StringRef Filename, bool isSystem,
550 bool isOverridden, time_t StoredTime,
551 bool isExplicitModule) override {
552
553 Out.indent(2) << "Input file: " << FilenameAsRequested;
554
555 if (isSystem || isOverridden || isExplicitModule) {
556 Out << " [";
557 if (isSystem) {
558 Out << "System";
559 if (isOverridden || isExplicitModule)
560 Out << ", ";
561 }
562 if (isOverridden) {
563 Out << "Overridden";
564 if (isExplicitModule)
565 Out << ", ";
566 }
567 if (isExplicitModule)
568 Out << "ExplicitModule";
569
570 Out << "]";
571 }
572
573 Out << "\n";
574
575 if (StoredTime > 0)
576 Out.indent(4) << "MTime: " << llvm::itostr(StoredTime) << "\n";
577
578 return true;
579 }
580
581 /// Returns true if this \c ASTReaderListener wants to receive the
582 /// imports of the AST file via \c visitImport, false otherwise.
583 bool needsImportVisitation() const override { return true; }
584
585 /// If needsImportVisitation returns \c true, this is called for each
586 /// AST file imported by this AST file.
587 void visitImport(StringRef ModuleName, StringRef Filename) override {
588 Out.indent(2) << "Imports module '" << ModuleName
589 << "': " << Filename.str() << "\n";
590 }
591#undef DUMP_BOOLEAN
592 };
593}
594
596 // The Object file reader also supports raw ast files and there is no point in
597 // being strict about the module file format in -module-file-info mode.
599 return true;
600}
601
602static StringRef ModuleKindName(Module::ModuleKind MK) {
603 switch (MK) {
605 return "Module Map Module";
607 return "Interface Unit";
609 return "Implementation Unit";
611 return "Partition Interface";
613 return "Partition Implementation";
615 return "Header Unit";
617 return "Global Module Fragment";
619 return "Implicit Module Fragment";
621 return "Private Module Fragment";
622 }
623 llvm_unreachable("unknown module kind!");
624}
625
628
629 // Don't process files of type other than module to avoid crash
630 if (!isCurrentFileAST()) {
631 CI.getDiagnostics().Report(diag::err_file_is_not_module)
632 << getCurrentFile();
633 return;
634 }
635
636 // Set up the output file.
637 StringRef OutputFileName = CI.getFrontendOpts().OutputFile;
638 if (!OutputFileName.empty() && OutputFileName != "-") {
639 std::error_code EC;
640 OutputStream.reset(new llvm::raw_fd_ostream(
641 OutputFileName.str(), EC, llvm::sys::fs::OF_TextWithCRLF));
642 }
643 llvm::raw_ostream &Out = OutputStream ? *OutputStream : llvm::outs();
644
645 Out << "Information for module file '" << getCurrentFile() << "':\n";
646 auto &FileMgr = CI.getFileManager();
647 auto Buffer = FileMgr.getBufferForFile(getCurrentFile());
648 StringRef Magic = (*Buffer)->getMemBufferRef().getBuffer();
649 bool IsRaw = Magic.starts_with("CPCH");
650 Out << " Module format: " << (IsRaw ? "raw" : "obj") << "\n";
651
652 Preprocessor &PP = CI.getPreprocessor();
653 DumpModuleInfoListener Listener(Out, CI.getFileManager());
654 const HeaderSearchOptions &HSOpts =
655 PP.getHeaderSearchInfo().getHeaderSearchOpts();
656
657 // The FrontendAction::BeginSourceFile () method loads the AST so that much
658 // of the information is already available and modules should have been
659 // loaded.
660
662 if (LO.CPlusPlusModules && !LO.CurrentModule.empty()) {
664 unsigned SubModuleCount = R->getTotalNumSubmodules();
665 serialization::ModuleFile &MF = R->getModuleManager().getPrimaryModule();
666 Out << " ====== C++20 Module structure ======\n";
667
668 if (MF.ModuleName != LO.CurrentModule)
669 Out << " Mismatched module names : " << MF.ModuleName << " and "
670 << LO.CurrentModule << "\n";
671
672 struct SubModInfo {
673 unsigned Idx;
674 Module *Mod;
676 std::string &Name;
677 bool Seen;
678 };
679 std::map<std::string, SubModInfo> SubModMap;
680 auto PrintSubMapEntry = [&](std::string Name, Module::ModuleKind Kind) {
681 Out << " " << ModuleKindName(Kind) << " '" << Name << "'";
682 auto I = SubModMap.find(Name);
683 if (I == SubModMap.end())
684 Out << " was not found in the sub modules!\n";
685 else {
686 I->second.Seen = true;
687 Out << " is at index #" << I->second.Idx << "\n";
688 }
689 };
690 Module *Primary = nullptr;
691 for (unsigned Idx = 0; Idx <= SubModuleCount; ++Idx) {
692 Module *M = R->getModule(Idx);
693 if (!M)
694 continue;
695 if (M->Name == LO.CurrentModule) {
696 Primary = M;
697 Out << " " << ModuleKindName(M->Kind) << " '" << LO.CurrentModule
698 << "' is the Primary Module at index #" << Idx << "\n";
699 SubModMap.insert({M->Name, {Idx, M, M->Kind, M->Name, true}});
700 } else
701 SubModMap.insert({M->Name, {Idx, M, M->Kind, M->Name, false}});
702 }
703 if (Primary) {
704 if (!Primary->submodules().empty())
705 Out << " Sub Modules:\n";
706 for (Module *MI : Primary->submodules()) {
707 PrintSubMapEntry(MI->Name, MI->Kind);
708 }
709 if (!Primary->Imports.empty())
710 Out << " Imports:\n";
711 for (Module *IMP : Primary->Imports) {
712 PrintSubMapEntry(IMP->Name, IMP->Kind);
713 }
714 if (!Primary->Exports.empty())
715 Out << " Exports:\n";
716 for (unsigned MN = 0, N = Primary->Exports.size(); MN != N; ++MN) {
717 if (Module *M = Primary->Exports[MN].first) {
718 PrintSubMapEntry(M->Name, M->Kind);
719 }
720 }
721 }
722
723 // Emit the macro definitions in the module file so that we can know how
724 // much definitions in the module file quickly.
725 // TODO: Emit the macro definition bodies completely.
726 {
727 std::vector<StringRef> MacroNames;
728 for (const auto &M : R->getPreprocessor().macros()) {
729 if (M.first->isFromAST())
730 MacroNames.push_back(M.first->getName());
731 }
732 llvm::sort(MacroNames);
733 if (!MacroNames.empty())
734 Out << " Macro Definitions:\n";
735 for (StringRef Name : MacroNames)
736 Out << " " << Name << "\n";
737 }
738
739 // Now let's print out any modules we did not see as part of the Primary.
740 for (const auto &SM : SubModMap) {
741 if (!SM.second.Seen && SM.second.Mod) {
742 Out << " " << ModuleKindName(SM.second.Kind) << " '" << SM.first
743 << "' at index #" << SM.second.Idx
744 << " has no direct reference in the Primary\n";
745 }
746 }
747 Out << " ====== ======\n";
748 }
749
750 // The reminder of the output is produced from the listener as the AST
751 // FileCcontrolBlock is (re-)parsed.
755 /*FindModuleFileExtensions=*/true, Listener,
757}
758
759//===----------------------------------------------------------------------===//
760// Preprocessor Actions
761//===----------------------------------------------------------------------===//
762
766
767 // Start lexing the specified input file.
768 llvm::MemoryBufferRef FromFile = SM.getBufferOrFake(SM.getMainFileID());
769 Lexer RawLex(SM.getMainFileID(), FromFile, SM, PP.getLangOpts());
770 RawLex.SetKeepWhitespaceMode(true);
771
772 Token RawTok;
773 RawLex.LexFromRawLexer(RawTok);
774 while (RawTok.isNot(tok::eof)) {
775 PP.DumpToken(RawTok, true);
776 llvm::errs() << "\n";
777 RawLex.LexFromRawLexer(RawTok);
778 }
779}
780
783 // Start preprocessing the specified input file.
784 Token Tok;
786 do {
787 PP.Lex(Tok);
788 PP.DumpToken(Tok, true);
789 llvm::errs() << "\n";
790 } while (Tok.isNot(tok::eof));
791}
792
795
796 // Ignore unknown pragmas.
797 PP.IgnorePragmas();
798
799 Token Tok;
800 // Start parsing the specified input file.
802 do {
803 PP.Lex(Tok);
804 } while (Tok.isNot(tok::eof));
805}
806
809 // Output file may need to be set to 'Binary', to avoid converting Unix style
810 // line feeds (<LF>) to Microsoft style line feeds (<CR><LF>) on Windows.
811 //
812 // Look to see what type of line endings the file uses. If there's a
813 // CRLF, then we won't open the file up in binary mode. If there is
814 // just an LF or CR, then we will open the file up in binary mode.
815 // In this fashion, the output format should match the input format, unless
816 // the input format has inconsistent line endings.
817 //
818 // This should be a relatively fast operation since most files won't have
819 // all of their source code on a single line. However, that is still a
820 // concern, so if we scan for too long, we'll just assume the file should
821 // be opened in binary mode.
822
823 bool BinaryMode = false;
824 if (llvm::Triple(LLVM_HOST_TRIPLE).isOSWindows()) {
825 BinaryMode = true;
826 const SourceManager &SM = CI.getSourceManager();
827 if (std::optional<llvm::MemoryBufferRef> Buffer =
828 SM.getBufferOrNone(SM.getMainFileID())) {
829 const char *cur = Buffer->getBufferStart();
830 const char *end = Buffer->getBufferEnd();
831 const char *next = (cur != end) ? cur + 1 : end;
832
833 // Limit ourselves to only scanning 256 characters into the source
834 // file. This is mostly a check in case the file has no
835 // newlines whatsoever.
836 if (end - cur > 256)
837 end = cur + 256;
838
839 while (next < end) {
840 if (*cur == 0x0D) { // CR
841 if (*next == 0x0A) // CRLF
842 BinaryMode = false;
843
844 break;
845 } else if (*cur == 0x0A) // LF
846 break;
847
848 ++cur;
849 ++next;
850 }
851 }
852 }
853
854 std::unique_ptr<raw_ostream> OS =
856 if (!OS) return;
857
858 // If we're preprocessing a module map, start by dumping the contents of the
859 // module itself before switching to the input buffer.
860 auto &Input = getCurrentInput();
861 if (Input.getKind().getFormat() == InputKind::ModuleMap) {
862 if (Input.isFile()) {
863 (*OS) << "# 1 \"";
864 OS->write_escaped(Input.getFile());
865 (*OS) << "\"\n";
866 }
867 getCurrentModule()->print(*OS);
868 (*OS) << "#pragma clang module contents\n";
869 }
870
873}
874
876 switch (getCurrentFileKind().getLanguage()) {
877 case Language::C:
878 case Language::CXX:
879 case Language::ObjC:
880 case Language::ObjCXX:
881 case Language::OpenCL:
883 case Language::CUDA:
884 case Language::HIP:
885 case Language::HLSL:
886 case Language::CIR:
887 break;
888
890 case Language::Asm:
892 // We can't do anything with these.
893 return;
894 }
895
896 // We don't expect to find any #include directives in a preprocessed input.
897 if (getCurrentFileKind().isPreprocessed())
898 return;
899
901 auto Buffer = CI.getFileManager().getBufferForFile(getCurrentFile());
902 if (Buffer) {
903 unsigned Preamble =
904 Lexer::ComputePreamble((*Buffer)->getBuffer(), CI.getLangOpts()).Size;
905 llvm::outs().write((*Buffer)->getBufferStart(), Preamble);
906 }
907}
908
909static void writeCompilerOptionValues(raw_ostream &OS,
910 StringRef CompilerOptionNames,
911 ArrayRef<bool> CompilerOptionValues) {
912 bool FirstValue = true;
913 for (bool CompilerOptionValue : CompilerOptionValues) {
914 auto [CompilerOptionName, RemainingCompilerOptionNames] =
915 CompilerOptionNames.split('\0');
916 CompilerOptionNames = RemainingCompilerOptionNames;
917 if (!FirstValue)
918 OS << ",\n";
919 FirstValue = false;
920 OS << "\t{\"" << CompilerOptionName
921 << "\" : " << (CompilerOptionValue ? "true" : "false") << "}";
922 }
923 assert(CompilerOptionNames.empty() && "compiler option name count mismatch");
924}
925
927 CompilerInstance &CI = getCompilerInstance();
928 std::unique_ptr<raw_ostream> OSP =
930 if (!OSP)
931 return;
932
933 raw_ostream &OS = *OSP;
934 const Preprocessor &PP = CI.getPreprocessor();
935 const LangOptions &LangOpts = PP.getLangOpts();
936
937 // FIXME: Rather than manually format the JSON (which is awkward due to
938 // needing to remove trailing commas), this should make use of a JSON library.
939 // FIXME: Instead of printing enums as an integral value and specifying the
940 // type as a separate field, use introspection to print the enumerator.
941
942 OS << "{\n";
943 OS << "\n\"features\" : [\n";
944 {
945 static constexpr char FeatureNames[] = {
946#define FEATURE(Name, Predicate) #Name "\0"
947#include "clang/Basic/Features.def"
948 };
949 const bool FeatureValues[] = {
950#define FEATURE(Name, Predicate) static_cast<bool>(Predicate),
951#include "clang/Basic/Features.def"
952 };
954 OS, StringRef(FeatureNames, sizeof(FeatureNames) - 1), FeatureValues);
955 }
956 OS << "\n],\n";
957
958 OS << "\n\"extensions\" : [\n";
959 {
960 static constexpr char ExtensionNames[] = {
961#define EXTENSION(Name, Predicate) #Name "\0"
962#include "clang/Basic/Features.def"
963 };
964 const bool ExtensionValues[] = {
965#define EXTENSION(Name, Predicate) static_cast<bool>(Predicate),
966#include "clang/Basic/Features.def"
967 };
969 OS, StringRef(ExtensionNames, sizeof(ExtensionNames) - 1),
970 ExtensionValues);
971 }
972 OS << "\n]\n";
973
974 OS << "}";
975}
976
980 llvm::MemoryBufferRef FromFile = SM.getBufferOrFake(SM.getMainFileID());
981
985 FromFile.getBuffer(), Tokens, Directives, &CI.getDiagnostics(),
986 SM.getLocForStartOfFile(SM.getMainFileID()))) {
987 assert(CI.getDiagnostics().hasErrorOccurred() &&
988 "no errors reported for failure");
989
990 // Preprocess the source when verifying the diagnostics to capture the
991 // 'expected' comments.
992 if (CI.getDiagnosticOpts().VerifyDiagnostics) {
993 // Make sure we don't emit new diagnostics!
997 Token Tok;
998 do {
999 PP.Lex(Tok);
1000 } while (Tok.isNot(tok::eof));
1001 }
1002 return;
1003 }
1004 printDependencyDirectivesAsSource(FromFile.getBuffer(), Directives,
1005 llvm::outs());
1006}
1007
1008//===----------------------------------------------------------------------===//
1009// HLSL Specific Actions
1010//===----------------------------------------------------------------------===//
1011
1013private:
1014 Sema &Actions;
1015 StringRef RootSigName;
1016 llvm::dxbc::RootSignatureVersion Version;
1017
1018 std::optional<StringLiteral *> processStringLiteral(ArrayRef<Token> Tokens) {
1019 for (Token Tok : Tokens)
1020 if (!tok::isStringLiteral(Tok.getKind()))
1021 return std::nullopt;
1022
1023 ExprResult StringResult = Actions.ActOnUnevaluatedStringLiteral(Tokens);
1024 if (StringResult.isInvalid())
1025 return std::nullopt;
1026
1027 if (auto Signature = dyn_cast<StringLiteral>(StringResult.get()))
1028 return Signature;
1029
1030 return std::nullopt;
1031 }
1032
1033public:
1034 void MacroDefined(const Token &MacroNameTok,
1035 const MacroDirective *MD) override {
1036 if (RootSigName != MacroNameTok.getIdentifierInfo()->getName())
1037 return;
1038
1039 const MacroInfo *MI = MD->getMacroInfo();
1040 auto Signature = processStringLiteral(MI->tokens());
1041 if (!Signature.has_value()) {
1042 Actions.getDiagnostics().Report(MI->getDefinitionLoc(),
1043 diag::err_expected_string_literal)
1044 << /*in attributes...*/ 4 << "RootSignature";
1045 return;
1046 }
1047
1048 IdentifierInfo *DeclIdent =
1049 hlsl::ParseHLSLRootSignature(Actions, Version, *Signature);
1050 Actions.HLSL().SetRootSignatureOverride(DeclIdent);
1051 }
1052
1053 InjectRootSignatureCallback(Sema &Actions, StringRef RootSigName,
1054 llvm::dxbc::RootSignatureVersion Version)
1055 : PPCallbacks(), Actions(Actions), RootSigName(RootSigName),
1056 Version(Version) {}
1057};
1058
1060 // Pre-requisites to invoke
1062 if (!CI.hasASTContext() || !CI.hasPreprocessor())
1064
1065 // InjectRootSignatureCallback requires access to invoke Sema to lookup/
1066 // register a root signature declaration. The wrapped action is required to
1067 // account for this by only creating a Sema if one doesn't already exist
1068 // (like we have done, and, ASTFrontendAction::ExecuteAction)
1069 if (!CI.hasSema())
1071 /*CodeCompleteConsumer=*/nullptr);
1072 Sema &S = CI.getSema();
1073
1074 auto &TargetInfo = CI.getASTContext().getTargetInfo();
1075 bool IsRootSignatureTarget =
1076 TargetInfo.getTriple().getEnvironment() == llvm::Triple::RootSignature;
1077 StringRef HLSLEntry = TargetInfo.getTargetOpts().HLSLEntry;
1078
1079 // Register HLSL specific callbacks
1080 auto LangOpts = CI.getLangOpts();
1081 StringRef RootSigName =
1082 IsRootSignatureTarget ? HLSLEntry : LangOpts.HLSLRootSigOverride;
1083
1084 auto MacroCallback = std::make_unique<InjectRootSignatureCallback>(
1085 S, RootSigName, LangOpts.HLSLRootSigVer);
1086
1087 Preprocessor &PP = CI.getPreprocessor();
1088 PP.addPPCallbacks(std::move(MacroCallback));
1089
1090 // If we are targeting a root signature, invoke custom handling
1091 if (IsRootSignatureTarget)
1092 return hlsl::HandleRootSignatureTarget(S, HLSLEntry);
1093 else // otherwise, invoke as normal
1095}
1096
1098 std::unique_ptr<FrontendAction> WrappedAction)
This is the interface for scanning header and source files to get the minimum necessary preprocessor ...
Defines the clang::FileManager interface and associated types.
Token Tok
The Token.
static void writeCompilerOptionValues(raw_ostream &OS, StringRef CompilerOptionNames, ArrayRef< bool > CompilerOptionValues)
#define DUMP_BOOLEAN(Value, Text)
static StringRef ModuleKindName(Module::ModuleKind MK)
Defines the clang::Module class, which describes a module in the source code.
#define SM(sm)
Defines the clang::Preprocessor interface.
void MacroDefined(const Token &MacroNameTok, const MacroDirective *MD) override
Hook called whenever a macro definition is seen.
InjectRootSignatureCallback(Sema &Actions, StringRef RootSigName, llvm::dxbc::RootSignatureVersion Version)
const TargetInfo & getTargetInfo() const
Definition ASTContext.h:927
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.
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:117
virtual bool ReadFullVersionInformation(StringRef FullVersion)
Receives the full Clang version information.
Definition ASTReader.h:125
Reads an AST files chain containing the contents of a translation unit.
Definition ASTReader.h:427
@ ARR_ConfigurationMismatch
The client can handle an AST file that cannot load because it's compiled configuration doesn't match ...
Definition ASTReader.h:1838
static bool readASTFileControlBlock(StringRef Filename, FileManager &FileMgr, const ModuleCache &ModCache, const PCHContainerReader &PCHContainerRdr, bool FindModuleFileExtensions, ASTReaderListener &Listener, bool ValidateDiagnosticOptions, unsigned ClientLoadCapabilities=ARR_ConfigurationMismatch|ARR_OutOfDate)
Read the control block for the named AST file.
const LangOptions & getLangOpts() const
Definition ASTUnit.h:476
IntrusiveRefCntPtr< ASTReader > getASTReader() const
Definition ASTUnit.cpp:647
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
PtrTy get() const
Definition Ownership.h:171
bool isInvalid() const
Definition Ownership.h:167
CompilerInstance - Helper class for managing a single instance of the Clang compiler.
std::unique_ptr< raw_pwrite_stream > createDefaultOutputFile(bool Binary=true, StringRef BaseInput="", StringRef Extension="", bool RemoveFileOnSignal=true, bool CreateMissingDirectories=false, bool ForceUseTemporary=false, bool SetOnlyIfDifferent=false)
Create the default output file (from the invocation's options) and add it to the list of tracked outp...
const PCHContainerReader & getPCHContainerReader() const
Return the appropriate PCHContainerReader depending on the current CodeGenOptions.
DiagnosticsEngine & getDiagnostics() const
Get the current diagnostics engine.
FileManager & getFileManager() const
Return the current file manager to the caller.
PreprocessorOutputOptions & getPreprocessorOutputOpts()
ModuleCache & getModuleCache() const
Preprocessor & getPreprocessor() const
Return the current preprocessor.
ASTContext & getASTContext() const
FrontendOptions & getFrontendOpts()
HeaderSearchOptions & getHeaderSearchOpts()
const PCHContainerWriter & getPCHContainerWriter() const
Return the appropriate PCHContainerWriter depending on the current CodeGenOptions.
PreprocessorOptions & getPreprocessorOpts()
DiagnosticOptions & getDiagnosticOpts()
CodeGenOptions & getCodeGenOpts()
SourceManager & getSourceManager() const
Return the current source manager.
void createSema(TranslationUnitKind TUKind, CodeCompleteConsumer *CompletionConsumer)
Create the Sema object to be used for parsing.
std::vector< std::string > Remarks
The list of -R... options used to alter the diagnostic mappings, with the prefixes removed.
std::vector< std::string > Warnings
The list of -W... options used to alter the diagnostic mappings, with the prefixes removed.
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
bool hasErrorOccurred() const
Definition Diagnostic.h:882
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:737
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.
Implements support for file system lookup, file system caching, and directory search management.
Definition FileManager.h:52
llvm::ErrorOr< std::unique_ptr< llvm::MemoryBuffer > > getBufferForFile(FileEntryRef Entry, bool isVolatile=false, bool RequiresNullTerminator=true, std::optional< int64_t > MaybeLimit=std::nullopt, bool IsText=true)
Open the specified file as a MemoryBuffer, returning a new MemoryBuffer if successful,...
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
virtual bool PrepareToExecuteAction(CompilerInstance &CI)
Prepare to execute the action on the given CompilerInstance.
Module * getCurrentModule() const
StringRef getCurrentFile() const
virtual bool BeginSourceFileAction(CompilerInstance &CI)
Callback at the start of processing a single input.
virtual void ExecuteAction()=0
Callback to run the program action, using the initialized compiler instance.
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.
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.
SmallVector< FrontendInputFile, 0 > Inputs
The input files and their types.
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.
bool PrepareToExecuteAction(CompilerInstance &CI) override
Prepare to execute the action on the given CompilerInstance.
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.
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.
static std::unique_ptr< llvm::raw_pwrite_stream > CreateOutputFile(CompilerInstance &CI, StringRef InFile, std::string &OutputFile, bool SetOnlyIfDifferent=false)
Creates file to write the PCH into and returns a stream to write it into.
bool shouldEraseOutputFiles() override
Callback at the end of processing a single input, to determine if the output files should be erased o...
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
HLSLFrontendAction(std::unique_ptr< FrontendAction > WrappedAction)
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::string ModuleCachePath
The directory used for the module cache.
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.
unsigned DisableModuleHash
Whether we should disable the use of the hash string within the module cache.
ModuleFileName 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.
StringRef getName() const
Return the actual identifier string.
@ CMK_HeaderUnit
Compiling a module header unit.
@ CMK_ModuleInterface
Compiling a C++ modules interface unit.
Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...
std::string HLSLRootSigOverride
The HLSL root signature that will be used to overide the root signature used for the shader entry poi...
llvm::dxbc::RootSignatureVersion HLSLRootSigVer
The HLSL root signature version for dxil.
std::string CurrentModule
The name of the current module, of which the main source file is a part.
std::vector< std::string > ModuleFeatures
The names of any features to enable in module 'requires' decls in addition to the hard-coded list in ...
Lexer - This provides a simple interface that turns a text buffer into a stream of tokens.
Definition Lexer.h:79
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:669
Encapsulates changes to the "macros namespace" (the location where the macro name became active,...
Definition MacroInfo.h:314
const MacroInfo * getMacroInfo() const
Definition MacroInfo.h:417
Encapsulates the data about a macro definition (e.g.
Definition MacroInfo.h:40
SourceLocation getDefinitionLoc() const
Return the location that the macro was defined at.
Definition MacroInfo.h:126
ArrayRef< Token > tokens() const
Definition MacroInfo.h:250
static ModuleFileName makeExplicit(std::string Name)
Creates a file name for an explicit module.
Definition Module.h:142
Describes a module or submodule.
Definition Module.h:340
SmallVector< ExportDecl, 2 > Exports
The set of export declarations.
Definition Module.h:671
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:456
ModuleKind Kind
The kind of this module.
Definition Module.h:385
std::string Name
The name of this module.
Definition Module.h:343
llvm::iterator_range< submodule_iterator > submodules()
Definition Module.h:1067
@ ModuleImplementationUnit
This is a C++20 module implementation unit.
Definition Module.h:363
@ ModuleMapModule
This is a module that was defined by a module map and built out of header files.
Definition Module.h:354
@ ImplicitGlobalModuleFragment
This is an implicit fragment of the global module which contains only language linkage declarations (...
Definition Module.h:381
@ ModulePartitionInterface
This is a C++20 module partition interface.
Definition Module.h:366
@ ModuleInterfaceUnit
This is a C++20 module interface unit.
Definition Module.h:360
@ ModuleHeaderUnit
This is a C++20 header unit.
Definition Module.h:357
@ ModulePartitionImplementation
This is a C++20 module partition implementation.
Definition Module.h:369
@ PrivateModuleFragment
This is the private module fragment within some C++ module.
Definition Module.h:376
@ ExplicitGlobalModuleFragment
This is the explicit Global Module Fragment of a modular TU.
Definition Module.h:373
llvm::SmallVector< ModuleRef, 2 > Imports
The set of modules imported by this module, and on which this module depends.
Definition Module.h:658
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:37
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
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.
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:2219
void Lex(Token &Result)
Lex the next token for this preprocessor.
void addPPCallbacks(std::unique_ptr< PPCallbacks > C)
void EnterMainSourceFile()
Enter the specified FileID as the main source file, which implicitly adds the builtin defines etc.
SourceManager & getSourceManager() const
HeaderSearch & getHeaderSearchInfo() const
const LangOptions & getLangOpts() const
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:868
Encodes a location in the source.
This class handles loading and caching of source files into memory.
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
Exposes information about the current target.
Definition TargetInfo.h:227
TargetOptions & getTargetOpts() const
Retrieve the target options.
Definition TargetInfo.h:330
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
std::string Triple
The name of the target triple to compile for.
std::string ABI
If given, the name of the target ABI to use.
std::string TuneCPU
If given, the name of the target CPU to tune code for.
std::string CPU
If given, the name of the target CPU to generate code for.
std::vector< std::string > FeaturesAsWritten
The list of target specific features to enable or disable, as written on the command line.
std::string HLSLEntry
The entry point name for HLSL shader being compiled as specified by -E.
Token - This structure provides full information about a lexed token.
Definition Token.h:36
IdentifierInfo * getIdentifierInfo() const
Definition Token.h:197
bool isNot(tok::TokenKind K) const
Definition Token.h:111
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.
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
WrapperFrontendAction(std::unique_ptr< FrontendAction > WrappedAction)
Construct a WrapperFrontendAction from an existing action, taking ownership of it.
TranslationUnitKind getTranslationUnitKind() override
For AST-based actions, the kind of translation unit we're handling.
std::unique_ptr< FrontendAction > WrappedAction
Information about a module that has been loaded by the ASTReader.
Definition ModuleFile.h:158
std::string ModuleName
The name of the module.
Definition ModuleFile.h:183
Defines the clang::TargetInfo interface.
@ HeaderSearch
Remove unused header search paths including header maps.
@ OS
Indicates that the tracking object is a descendant of a referenced-counted OSObject,...
void HandleRootSignatureTarget(Sema &S, StringRef EntryRootSig)
IdentifierInfo * ParseHLSLRootSignature(Sema &Actions, llvm::dxbc::RootSignatureVersion Version, StringLiteral *Signature)
@ MK_PCH
File is a PCH file treated as such.
Definition ModuleFile.h:52
@ MK_Preamble
File is a PCH file treated as the preamble.
Definition ModuleFile.h:55
bool isStringLiteral(TokenKind K)
Return true if this is a C or C++ string-literal (or C++11 user-defined-string-literal) token.
Definition TokenKinds.h:101
The JSON file list parser is used to communicate input to InstallAPI.
void printDependencyDirectivesAsSource(StringRef Source, ArrayRef< dependency_directives_scan::Directive > Directives, llvm::raw_ostream &OS)
Print the previously scanned dependency directives as minimized source text.
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.
std::string createSpecificModuleCachePath(FileManager &FileMgr, StringRef ModuleCachePath, bool DisableModuleHash, std::string ContextHash)
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
ActionResult< Expr * > ExprResult
Definition Ownership.h:249
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:63