ExpandModularHeadersPPCallbacks.h 5.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. //===- ExpandModularHeadersPPCallbacks.h - clang-tidy -----------*- C++ -*-===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. #ifndef LLVM_CLANG_TOOLING_EXPANDMODULARHEADERSPPCALLBACKS_H_
  9. #define LLVM_CLANG_TOOLING_EXPANDMODULARHEADERSPPCALLBACKS_H_
  10. #include "clang/Lex/PPCallbacks.h"
  11. #include "clang/Lex/Preprocessor.h"
  12. #include "llvm/ADT/DenseSet.h"
  13. namespace llvm::vfs {
  14. class OverlayFileSystem;
  15. class InMemoryFileSystem;
  16. } // namespace llvm::vfs
  17. namespace clang {
  18. class CompilerInstance;
  19. namespace serialization {
  20. class ModuleFile;
  21. } // namespace serialization
  22. namespace tooling {
  23. /// Handles PPCallbacks and re-runs preprocessing of the whole
  24. /// translation unit with modules disabled.
  25. ///
  26. /// This way it's possible to get PPCallbacks for the whole translation unit
  27. /// including the contents of the modular headers and all their transitive
  28. /// includes.
  29. ///
  30. /// This allows existing tools based on PPCallbacks to retain their functionality
  31. /// when running with C++ modules enabled. This only works in the backwards
  32. /// compatible modules mode, i.e. when code can still be parsed in non-modular
  33. /// way.
  34. class ExpandModularHeadersPPCallbacks : public PPCallbacks {
  35. public:
  36. ExpandModularHeadersPPCallbacks(
  37. CompilerInstance *Compiler,
  38. IntrusiveRefCntPtr<llvm::vfs::OverlayFileSystem> OverlayFS);
  39. ~ExpandModularHeadersPPCallbacks();
  40. /// Returns the preprocessor that provides callbacks for the whole
  41. /// translation unit, including the main file, textual headers, and modular
  42. /// headers.
  43. ///
  44. /// This preprocessor is separate from the one used by the rest of the
  45. /// compiler.
  46. Preprocessor *getPreprocessor() const;
  47. private:
  48. class FileRecorder;
  49. void handleModuleFile(serialization::ModuleFile *MF);
  50. void parseToLocation(SourceLocation Loc);
  51. // Handle PPCallbacks.
  52. void FileChanged(SourceLocation Loc, FileChangeReason Reason,
  53. SrcMgr::CharacteristicKind FileType,
  54. FileID PrevFID) override;
  55. void InclusionDirective(SourceLocation DirectiveLoc,
  56. const Token &IncludeToken, StringRef IncludedFilename,
  57. bool IsAngled, CharSourceRange FilenameRange,
  58. OptionalFileEntryRef IncludedFile,
  59. StringRef SearchPath, StringRef RelativePath,
  60. const Module *Imported,
  61. SrcMgr::CharacteristicKind FileType) override;
  62. void EndOfMainFile() override;
  63. // Handle all other callbacks.
  64. // Just parse to the corresponding location to generate PPCallbacks for the
  65. // corresponding range
  66. void Ident(SourceLocation Loc, StringRef) override;
  67. void PragmaDirective(SourceLocation Loc, PragmaIntroducerKind) override;
  68. void PragmaComment(SourceLocation Loc, const IdentifierInfo *,
  69. StringRef) override;
  70. void PragmaDetectMismatch(SourceLocation Loc, StringRef, StringRef) override;
  71. void PragmaDebug(SourceLocation Loc, StringRef) override;
  72. void PragmaMessage(SourceLocation Loc, StringRef, PragmaMessageKind,
  73. StringRef) override;
  74. void PragmaDiagnosticPush(SourceLocation Loc, StringRef) override;
  75. void PragmaDiagnosticPop(SourceLocation Loc, StringRef) override;
  76. void PragmaDiagnostic(SourceLocation Loc, StringRef, diag::Severity,
  77. StringRef) override;
  78. void HasInclude(SourceLocation Loc, StringRef, bool, OptionalFileEntryRef,
  79. SrcMgr::CharacteristicKind) override;
  80. void PragmaOpenCLExtension(SourceLocation NameLoc, const IdentifierInfo *,
  81. SourceLocation StateLoc, unsigned) override;
  82. void PragmaWarning(SourceLocation Loc, PragmaWarningSpecifier,
  83. ArrayRef<int>) override;
  84. void PragmaWarningPush(SourceLocation Loc, int) override;
  85. void PragmaWarningPop(SourceLocation Loc) override;
  86. void PragmaAssumeNonNullBegin(SourceLocation Loc) override;
  87. void PragmaAssumeNonNullEnd(SourceLocation Loc) override;
  88. void MacroExpands(const Token &MacroNameTok, const MacroDefinition &,
  89. SourceRange Range, const MacroArgs *) override;
  90. void MacroDefined(const Token &MacroNameTok,
  91. const MacroDirective *MD) override;
  92. void MacroUndefined(const Token &, const MacroDefinition &,
  93. const MacroDirective *Undef) override;
  94. void Defined(const Token &MacroNameTok, const MacroDefinition &,
  95. SourceRange Range) override;
  96. void SourceRangeSkipped(SourceRange Range, SourceLocation EndifLoc) override;
  97. void If(SourceLocation Loc, SourceRange, ConditionValueKind) override;
  98. void Elif(SourceLocation Loc, SourceRange, ConditionValueKind,
  99. SourceLocation) override;
  100. void Ifdef(SourceLocation Loc, const Token &,
  101. const MacroDefinition &) override;
  102. void Ifndef(SourceLocation Loc, const Token &,
  103. const MacroDefinition &) override;
  104. void Else(SourceLocation Loc, SourceLocation) override;
  105. void Endif(SourceLocation Loc, SourceLocation) override;
  106. std::unique_ptr<FileRecorder> Recorder;
  107. // Set of all the modules visited. Avoids processing a module more than once.
  108. llvm::DenseSet<serialization::ModuleFile *> VisitedModules;
  109. CompilerInstance &Compiler;
  110. // Additional filesystem for replay. Provides all input files from modules.
  111. llvm::IntrusiveRefCntPtr<llvm::vfs::InMemoryFileSystem> InMemoryFs;
  112. SourceManager &Sources;
  113. DiagnosticsEngine Diags;
  114. LangOptions LangOpts;
  115. TrivialModuleLoader ModuleLoader;
  116. std::unique_ptr<HeaderSearch> HeaderInfo;
  117. std::unique_ptr<Preprocessor> PP;
  118. bool EnteredMainFile = false;
  119. bool StartedLexing = false;
  120. Token CurrentToken;
  121. };
  122. } // namespace tooling
  123. } // namespace clang
  124. #endif // LLVM_CLANG_TOOLING_EXPANDMODULARHEADERSPPCALLBACKS_H_