27 #include "llvm/Support/ErrorHandling.h"
28 #include "llvm/Support/FileSystem.h"
29 #include "llvm/Support/MemoryBuffer.h"
30 #include "llvm/Support/Timer.h"
31 #include "llvm/Support/raw_ostream.h"
32 #include <system_error>
33 using namespace clang;
35 template class llvm::Registry<clang::PluginASTAction>;
44 explicit DelegatingDeserializationListener(
46 : Previous(Previous), DeletePrevious(DeletePrevious) {}
47 ~DelegatingDeserializationListener()
override {
52 void ReaderInitialized(
ASTReader *Reader)
override {
81 class DeserializedDeclsDumper :
public DelegatingDeserializationListener {
85 : DelegatingDeserializationListener(Previous, DeletePrevious) {}
88 llvm::outs() <<
"PCH DECL: " << D->getDeclKindName();
89 if (
const NamedDecl *ND = dyn_cast<NamedDecl>(D))
90 llvm::outs() <<
" - " << *ND;
93 DelegatingDeserializationListener::DeclRead(ID, D);
99 class DeserializedDeclsChecker :
public DelegatingDeserializationListener {
101 std::set<std::string> NamesToCheck;
105 const std::set<std::string> &NamesToCheck,
108 : DelegatingDeserializationListener(Previous, DeletePrevious), Ctx(Ctx),
109 NamesToCheck(NamesToCheck) {}
112 if (
const NamedDecl *ND = dyn_cast<NamedDecl>(D))
113 if (NamesToCheck.find(ND->getNameAsString()) != NamesToCheck.end()) {
116 "%0 was deserialized");
118 << ND->getNameAsString();
121 DelegatingDeserializationListener::DeclRead(ID, D);
132 std::unique_ptr<ASTUnit> AST) {
133 this->CurrentInput = CurrentInput;
134 CurrentASTUnit = std::move(AST);
137 std::unique_ptr<ASTConsumer>
150 std::vector<std::unique_ptr<ASTConsumer>> Consumers;
151 std::vector<std::unique_ptr<ASTConsumer>> AfterConsumers;
155 std::unique_ptr<PluginASTAction>
P = it->instantiate();
171 std::unique_ptr<ASTConsumer> PluginConsumer = P->CreateASTConsumer(CI, InFile);
173 Consumers.push_back(std::move(PluginConsumer));
175 AfterConsumers.push_back(std::move(PluginConsumer));
181 Consumers.push_back(std::move(Consumer));
182 for (
auto &C : AfterConsumers) {
183 Consumers.push_back(std::move(C));
186 return llvm::make_unique<MultiplexConsumer>(std::move(Consumers));
191 assert(!Instance &&
"Already processing a source file!");
192 assert(!Input.
isEmpty() &&
"Unexpected empty filename!");
196 StringRef InputFile = Input.
getFile();
197 bool HasBegunSourceFile =
false;
205 "Attempt to pass AST file to preprocessor only action!");
207 "This action does not have AST file support!");
220 HasBegunSourceFile =
true;
261 "This action does not have IR file support!");
265 HasBegunSourceFile =
true;
288 llvm::sys::path::native(PCHDir->getName(), DirNative);
290 for (llvm::sys::fs::directory_iterator Dir(DirNative, EC), DirEnd;
291 Dir != DirEnd && !EC; Dir.increment(EC)) {
296 SpecificModuleCachePath)) {
318 HasBegunSourceFile =
true;
336 std::unique_ptr<ASTConsumer> Consumer =
337 CreateWrappedASTConsumer(CI, InputFile);
355 assert(
hasPCHSupport() &&
"This action does not have PCH support!");
357 Consumer->GetASTDeserializationListener();
358 bool DeleteDeserialListener =
false;
360 DeserialListener =
new DeserializedDeclsDumper(DeserialListener,
361 DeleteDeserialListener);
362 DeleteDeserialListener =
true;
365 DeserialListener =
new DeserializedDeclsChecker(
368 DeserialListener, DeleteDeserialListener);
369 DeleteDeserialListener =
true;
375 DeleteDeserialListener);
402 "modules enabled but created an external source that "
403 "doesn't support modules");
442 if (HasBegunSourceFile)
501 llvm::errs() <<
"\nSTATISTICS FOR '" <<
getCurrentFile() <<
"':\n";
506 llvm::errs() <<
"\n";
560 void PluginASTAction::anchor() { }
562 std::unique_ptr<ASTConsumer>
565 llvm_unreachable(
"Invalid CreateASTConsumer on preprocessor action!");
568 std::unique_ptr<ASTConsumer>
571 return WrappedAction->CreateASTConsumer(CI, InFile);
574 return WrappedAction->BeginInvocation(CI);
579 WrappedAction->setCompilerInstance(&CI);
580 auto Ret = WrappedAction->BeginSourceFileAction(CI, Filename);
586 WrappedAction->ExecuteAction();
589 WrappedAction->EndSourceFileAction();
593 return WrappedAction->usesPreprocessorOnly();
596 return WrappedAction->getTranslationUnitKind();
599 return WrappedAction->hasPCHSupport();
602 return WrappedAction->hasASTFileSupport();
605 return WrappedAction->hasIRSupport();
608 return WrappedAction->hasCodeCompletionSupport();
612 std::unique_ptr<FrontendAction> WrappedAction)
613 : WrappedAction(std::move(WrappedAction)) {}
void setExternalSource(IntrusiveRefCntPtr< ExternalASTSource > Source)
Attach an external AST source to the AST context.
Defines the clang::ASTContext interface.
virtual bool isModelParsingAction() const
Is this action invoked on a model file?
LangOptions & getLangOpts()
void resetAndLeakFileManager()
bool hasFileManager() const
ASTContext & getASTContext() const
CompilerInvocation & getInvocation()
PreprocessorOptions & getPreprocessorOpts()
void createCodeCompletionConsumer()
Create a code completion consumer using the invocation; note that this will cause the source manager ...
Smart pointer class that efficiently represents Objective-C method names.
A (possibly-)qualified type.
bool hasASTConsumer() const
Implements support for file system lookup, file system caching, and directory search management...
IntrusiveRefCntPtr< ExternalSemaSource > createChainedIncludesSource(CompilerInstance &CI, IntrusiveRefCntPtr< ExternalSemaSource > &Reader)
The ChainedIncludesSource class converts headers to chained PCHs in memory, mainly for testing...
void EndSourceFile()
Perform any per-file post processing, deallocate per-file objects, and run statistics and output file...
void ExecuteAction() override
Implement the ExecuteAction interface by running Sema on the already-initialized AST consumer...
uint32_t IdentID
An ID number that refers to an identifier in an AST file.
void createSema(TranslationUnitKind TUKind, CodeCompleteConsumer *CompletionConsumer)
Create the Sema object to be used for parsing.
virtual bool hasCodeCompletionSupport() const
Does this action support use with code completion?
CompilerInstance & getCompilerInstance() const
void EndSourceFile()
Inform the preprocessor callbacks that processing is complete.
bool hasCodeCompletionConsumer() const
virtual bool usesPreprocessorOnly() const =0
Does this action only use the preprocessor?
bool hasErrorOccurred() const
TypePropertyCache< Private > Cache
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Provide a default implementation which returns aborts; this method should never be called by Frontend...
FullSourceLoc getFullLoc(SourceLocation Loc) const
uint32_t DeclID
An ID number that refers to a declaration in an AST file.
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
bool BeginSourceFileAction(CompilerInstance &CI, StringRef Filename) override
Callback at the start of processing a single input.
bool InitializeSourceManager(const FrontendInputFile &Input)
InitializeSourceManager - Initialize the source manager to set InputFile as the main file...
virtual void IdentifierRead(serialization::IdentID ID, IdentifierInfo *II)
An identifier was deserialized from the AST file.
PreprocessorOptions - This class is used for passing the various options used in preprocessor initial...
void setModuleManager(IntrusiveRefCntPtr< ASTReader > Reader)
void setSourceManager(SourceManager *Value)
setSourceManager - Replace the current source manager.
virtual void EndSourceFile()
Callback to inform the diagnostic client that processing of a source file has ended.
SourceManager & getSourceManager() const
Return the current source manager.
Builtin::Context & getBuiltinInfo()
One of these records is kept for each identifier that is lexed.
const FrontendInputFile & getCurrentInput() const
virtual void ReaderInitialized(ASTReader *Reader)
The ASTReader was initialized.
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Record the location of a macro definition.
bool usesPreprocessorOnly() const override
Does this action only use the preprocessor?
bool BeginSourceFile(CompilerInstance &CI, const FrontendInputFile &Input)
Prepare the action for processing the input file Input.
void createFileManager()
Create the file manager and replace any existing one with it.
void createSourceManager(FileManager &FileMgr)
Create the source manager and replace any existing one with it.
virtual bool hasASTFileSupport() const
Does this action support use with AST files?
std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile) override
Create the AST consumer object for this action, if supported.
const LangOptions & getLangOpts() const
void setASTContext(ASTContext *Value)
setASTContext - Replace the current AST context.
CodeGenOptions & getCodeGenOpts()
Execute the action before the main action.
bool hasPCHSupport() const override
Does this action support use with PCH?
Action is determined by the cc1 command-line.
unsigned ShowStats
Show frontend performance metrics and statistics.
FrontendOptions & getFrontendOpts()
DiagnosticConsumer & getDiagnosticClient() const
HeaderSearch & getHeaderSearchInfo() const
virtual ~FrontendAction()
void setASTConsumer(std::unique_ptr< ASTConsumer > Value)
setASTConsumer - Replace the current AST consumer; the compiler instance takes ownership of Value...
unsigned SkipFunctionBodies
Emit ARC errors even if the migrator can fix them.
IntrusiveRefCntPtr< ASTReader > getModuleManager() const
virtual bool BeginInvocation(CompilerInstance &CI)
Callback before starting processing a single input, giving the opportunity to modify the CompilerInvo...
void setFileManager(FileManager *Value)
Replace the current file manager and virtual file system.
bool BeginInvocation(CompilerInstance &CI) override
Callback before starting processing a single input, giving the opportunity to modify the CompilerInvo...
virtual bool BeginSourceFileAction(CompilerInstance &CI, StringRef Filename)
Callback at the start of processing a single input.
bool DisablePCHValidation
When true, disables most of the normal validation performed on precompiled headers.
Preprocessor & getPreprocessor() const
Return the current preprocessor.
DiagnosticsEngine & getDiagnostics() const
virtual void SelectorRead(serialization::SelectorID iD, Selector Sel)
A selector was read from the AST file.
void createPCHExternalASTSource(StringRef Path, bool DisablePCHValidation, bool AllowPCHWithCompilerErrors, void *DeserializationListener, bool OwnDeserializationListener)
Create an external AST source to read a PCH file and attach it to the AST context.
bool hasVirtualFileSystem() const
static ErrorCode writeIndex(FileManager &FileMgr, const PCHContainerReader &PCHContainerRdr, StringRef Path)
Write a global index into the given.
const FileEntry * getFile(StringRef Filename, bool OpenFile=false, bool CacheFailure=true)
Lookup, cache, and verify the specified file (real or virtual).
virtual void DeclRead(serialization::DeclID ID, const Decl *D)
A decl was deserialized from the AST file.
void setPreprocessor(Preprocessor *Value)
Replace the current preprocessor.
bool hasCodeCompletionSupport() const override
Does this action support use with code completion?
const DirectoryEntry * getDirectory(StringRef DirName, bool CacheFailure=true)
Lookup, cache, and verify the specified directory (real or virtual).
void setVirtualFileSystem(IntrusiveRefCntPtr< vfs::FileSystem > FS)
Replace the current virtual file system.
virtual bool shouldEraseOutputFiles()
Callback at the end of processing a single input, to determine if the output files should be erased o...
std::vector< std::string > ChainedIncludes
Headers that will be converted to chained PCHs in memory.
void resetAndLeakPreprocessor()
void setCurrentInput(const FrontendInputFile &CurrentInput, std::unique_ptr< ASTUnit > AST=nullptr)
static bool isAcceptableASTFile(StringRef Filename, FileManager &FileMgr, const PCHContainerReader &PCHContainerRdr, const LangOptions &LangOpts, const TargetOptions &TargetOpts, const PreprocessorOptions &PPOpts, std::string ExistingModuleCachePath)
Determine whether the given AST file is acceptable to load into a translation unit with the given lan...
bool hasIRSupport() const override
Does this action support use with IR files?
std::string getSpecificModuleCachePath()
WrapperFrontendAction(std::unique_ptr< FrontendAction > WrappedAction)
Construct a WrapperFrontendAction from an existing action, taking ownership of it.
std::set< std::string > DeserializedPCHDeclsToErrorOn
This is a set of names for decls that we do not want to be deserialized, and we emit an error if they...
Defines the clang::Preprocessor interface.
IntrusiveRefCntPtr< vfs::FileSystem > createVFSFromCompilerInvocation(const CompilerInvocation &CI, DiagnosticsEngine &Diags)
void createASTContext()
Create the AST context.
virtual void EndSourceFileAction()
Callback at the end of processing a single input.
TranslationUnitKind getTranslationUnitKind() override
For AST-based actions, the kind of translation unit we're handling.
void setSema(Sema *S)
Replace the current Sema; the compiler instance takes ownership of S.
virtual bool hasIRSupport() const
Does this action support use with IR files?
virtual std::unique_ptr< ASTConsumer > CreateASTConsumer(CompilerInstance &CI, StringRef InFile)=0
Create the AST consumer object for this action, if supported.
DiagnosticsEngine & getDiagnostics() const
Get the current diagnostics engine.
virtual void ExecuteAction()=0
Callback to run the program action, using the initialized compiler instance.
void EndSourceFileAction() override
Callback at the end of processing a single input.
bool AllowPCHWithCompilerErrors
When true, a PCH with compiler errors will not be rejected.
bool hasSourceManager() const
FileSystemOptions & getFileSystemOpts()
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.
void resetAndLeakSourceManager()
ExternalASTSource * getExternalSource() const
Retrieve a pointer to the external AST source associated with this AST context, if any...
bool Execute()
Set the source manager's main input file, and run the action.
const TemplateArgument * iterator
std::vector< std::string > ModuleFiles
The list of additional prebuilt module files to load before processing the input. ...
ParsedSourceLocation CodeCompletionAt
If given, enable code completion at the provided location.
virtual TranslationUnitKind getTranslationUnitKind()
For AST-based actions, the kind of translation unit we're handling.
std::string ImplicitPCHInclude
The implicit PCH included at the start of the translation unit, or empty.
virtual void MacroDefinitionRead(serialization::PreprocessedEntityID, MacroDefinitionRecord *MD)
A macro definition was read from the AST file.
void ExecuteAction() override
Callback to run the program action, using the initialized compiler instance.
const StringRef getCurrentFile() const
IdentifierTable & getIdentifierTable()
void ParseAST(Preprocessor &pp, ASTConsumer *C, ASTContext &Ctx, bool PrintStats=false, TranslationUnitKind TUKind=TU_Complete, CodeCompleteConsumer *CompletionConsumer=nullptr, bool SkipFunctionBodies=false)
Parse the entire file specified, notifying the ASTConsumer as the file is parsed. ...
void initializeBuiltins(IdentifierTable &Table, const LangOptions &LangOpts)
Mark the identifiers for all the builtins with their appropriate builtin ID # and mark any non-portab...
std::unordered_map< std::string, std::vector< std::string > > PluginArgs
Args to pass to the plugins.
Execute the action after the main action.
unsigned getCustomDiagID(Level L, const char(&FormatString)[N])
Return an ID for a diagnostic with the specified format string and level.
void createPreprocessor(TranslationUnitKind TUKind)
Create the preprocessor, using the invocation, file, and source managers, and replace any existing on...
virtual void TypeRead(serialization::TypeIdx Idx, QualType T)
A type was deserialized from the AST file.
std::string OverrideRecordLayoutsFile
File name of the file that will provide record layouts (in the format produced by -fdump-record-layou...
Abstract interface for a consumer of code-completion information.
bool hasFrontendTimer() const
Reads an AST files chain containing the contents of a translation unit.
FileManager & getFileManager() const
Return the current file manager to the caller.
bool loadModuleFile(StringRef FileName)
void setASTMutationListener(ASTMutationListener *Listener)
Attach an AST mutation listener to the AST context.
bool isCurrentFileAST() const
virtual bool hasPCHSupport() const
Does this action support use with PCH?
void clearOutputFiles(bool EraseFiles)
clearOutputFiles - Clear the output file list.
void BuryPointer(const void *Ptr)
bool hasASTFileSupport() const override
Does this action support use with AST files?
void setCompilerInstance(CompilerInstance *Value)
void PrintStats() const
Print some statistics to stderr that indicate how well the hashing is doing.
CodeCompleteConsumer & getCodeCompletionConsumer() const
bool hasASTContext() const
std::vector< std::string > AddPluginActions
The list of plugin actions to run in addition to the normal action.
Cached information about one directory (either on disk or in the virtual file system).
unsigned DisableFree
Disable memory freeing on exit.
An external AST source that overrides the layout of a specified set of record types.
uint32_t PreprocessedEntityID
An ID number that refers to an entity in the detailed preprocessing record.
bool shouldBuildGlobalModuleIndex() const
Indicates whether we should (re)build the global module index.
void resetAndLeakASTContext()
uint32_t SelectorID
An ID number that refers to an ObjC selector in an AST file.
llvm::Timer & getFrontendTimer() const
TranslationUnitKind
Describes the kind of translation unit being processed.
void PrintStats() const
Print statistics to stderr.
bool hasPreprocessor() const
Defines the clang::FrontendAction interface and various convenience abstract classes (clang::ASTFront...
std::unique_ptr< ASTConsumer > takeASTConsumer()
takeASTConsumer - Remove the current AST consumer and give ownership to the caller.
void createModuleManager()
}
NamedDecl - This represents a decl with a name.
bool DumpDeserializedPCHDecls
Dump declarations that are deserialized from PCH, for testing.
virtual void BeginSourceFile(const LangOptions &LangOpts, const Preprocessor *PP=nullptr)
Callback to inform the diagnostic client that processing of a source file is beginning.
static std::unique_ptr< ASTUnit > LoadFromASTFile(const std::string &Filename, const PCHContainerReader &PCHContainerRdr, IntrusiveRefCntPtr< DiagnosticsEngine > Diags, const FileSystemOptions &FileSystemOpts, bool UseDebugInfo=false, bool OnlyLocalDecls=false, ArrayRef< RemappedFile > RemappedFiles=None, bool CaptureDiagnostics=false, bool AllowPCHWithCompilerErrors=false, bool UserFilesAreVolatile=false)
Create a ASTUnit from an AST file.
TargetOptions & getTargetOpts()
A type index; the type ID with the qualifier bits removed.
Engages in a tight little dance with the lexer to efficiently preprocess tokens.
std::vector< std::string > ModuleMapFiles
The list of module map files to load before processing the input.