Skip to content
Open
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions clang/include/clang/Frontend/CompilerInstance.h
Original file line number Diff line number Diff line change
Expand Up @@ -946,6 +946,12 @@ class CompilerInstance : public ModuleLoader {
DependencyCollectors.push_back(std::move(Listener));
}

void clearDependencyCollectors() { DependencyCollectors.clear(); }

std::vector<std::shared_ptr<DependencyCollector>> &getDependencyCollectors() {
return DependencyCollectors;
}

void setExternalSemaSource(IntrusiveRefCntPtr<ExternalSemaSource> ESS);

ModuleCache &getModuleCache() const { return *ModCache; }
Expand Down
9 changes: 0 additions & 9 deletions clang/include/clang/Frontend/FrontendActions.h
Original file line number Diff line number Diff line change
Expand Up @@ -320,15 +320,6 @@ class PrintPreprocessedAction : public PreprocessorFrontendAction {
bool hasPCHSupport() const override { return true; }
};

class GetDependenciesByModuleNameAction : public PreprocessOnlyAction {
StringRef ModuleName;
void ExecuteAction() override;

public:
GetDependenciesByModuleNameAction(StringRef ModuleName)
: ModuleName(ModuleName) {}
};

//===----------------------------------------------------------------------===//
// HLSL Specific Actions
//===----------------------------------------------------------------------===//
Expand Down
4 changes: 4 additions & 0 deletions clang/include/clang/Frontend/Utils.h
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ class DiagnosticsEngine;
class ExternalSemaSource;
class FrontendOptions;
class PCHContainerReader;
class PPCallbacks;
class Preprocessor;
class PreprocessorOptions;
class PreprocessorOutputOptions;
Expand Down Expand Up @@ -87,6 +88,9 @@ class DependencyCollector {
bool IsSystem, bool IsModuleFile,
bool IsMissing);

/// @return the PPCallback this collector added to the Preprocessor.
virtual PPCallbacks *getPPCallbacks() { return nullptr; };

protected:
/// Return true if the filename was added to the list of dependencies, false
/// otherwise.
Expand Down
1 change: 1 addition & 0 deletions clang/include/clang/Lex/Preprocessor.h
Original file line number Diff line number Diff line change
Expand Up @@ -1327,6 +1327,7 @@ class Preprocessor {
std::move(Callbacks));
Callbacks = std::move(C);
}
void removePPCallbacks() { Callbacks.reset(); }
/// \}

/// Get the number of tokens processed so far.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -151,14 +151,44 @@ class DependencyScanningTool {
LookupModuleOutputCallback LookupModuleOutput,
std::optional<llvm::MemoryBufferRef> TUBuffer = std::nullopt);

/// Given a compilation context specified via the Clang driver command-line,
/// gather modular dependencies of module with the given name, and return the
/// information needed for explicit build.
llvm::Expected<TranslationUnitDeps> getModuleDependencies(
StringRef ModuleName, const std::vector<std::string> &CommandLine,
StringRef CWD, const llvm::DenseSet<ModuleID> &AlreadySeen,
/// The following three methods provide a new interface to perform
/// by name dependency scan. The new interface's intention is to improve
/// dependency scanning performance when a sequence of name is looked up
/// with the same current working directory and the command line.

/// @brief Initializing the context and the compiler instance.
/// This method must be called before calling
/// computeDependenciesByNameWithContext.
/// @param CWD The current working directory used during the scan.
/// @param CommandLine The commandline used for the scan.
/// @return Error if the initializaiton fails.
llvm::Error initializeCompilerInstanceWithContext(
StringRef CWD, const std::vector<std::string> &CommandLine);

/// @brief Computes the dependeny for the module named ModuleName.
/// @param ModuleName The name of the module for which this method computes
///. dependencies.
/// @param AlreadySeen This stores modules which have previously been
/// reported. Use the same instance for all calls to this
/// function for a single \c DependencyScanningTool in a
/// single build. Note that this parameter is not part of
/// the context because it can be shared across different
/// worker threads and each worker thread may update it.
/// @param LookupModuleOutput This function is called to fill in
/// "-fmodule-file=", "-o" and other output
/// arguments for dependencies.
/// @return An instance of \c TranslationUnitDeps if the scan is successful.
/// Otherwise it returns an error.
llvm::Expected<TranslationUnitDeps> computeDependenciesByNameWithContext(
StringRef ModuleName, const llvm::DenseSet<ModuleID> &AlreadySeen,
LookupModuleOutputCallback LookupModuleOutput);

/// @brief This method finializes the compiler instance. It finalizes the
/// diagnostics and deletes the compiler instance. Call this method
/// once all names for a same commandline are scanned.
/// @return Error if an error occured during finalization.
llvm::Error finalizeCompilerInstanceWithContext();

llvm::vfs::FileSystem &getWorkerVFS() const { return Worker.getVFS(); }

private:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ namespace tooling {
namespace dependencies {

class DependencyScanningWorkerFilesystem;
class CompilerInstanceWithContext;

/// A command-line tool invocation that is part of building a TU.
///
Expand Down Expand Up @@ -89,6 +90,8 @@ class DependencyScanningWorker {
DependencyScanningWorker(DependencyScanningService &Service,
llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS);

~DependencyScanningWorker();

/// Run the dependency scanning tool for a given clang driver command-line,
/// and report the discovered dependencies to the provided consumer. If
/// TUBuffer is not nullopt, it is used as TU input for the dependency
Expand All @@ -103,18 +106,6 @@ class DependencyScanningWorker {
DiagnosticConsumer &DiagConsumer,
std::optional<llvm::MemoryBufferRef> TUBuffer = std::nullopt);

/// Run the dependency scanning tool for a given clang driver command-line
/// for a specific module.
///
/// \returns false if clang errors occurred (with diagnostics reported to
/// \c DiagConsumer), true otherwise.
bool computeDependencies(StringRef WorkingDirectory,
const std::vector<std::string> &CommandLine,
DependencyConsumer &DepConsumer,
DependencyActionController &Controller,
DiagnosticConsumer &DiagConsumer,
StringRef ModuleName);

/// Run the dependency scanning tool for a given clang driver command-line
/// for a specific translation unit via file system or memory buffer.
///
Expand All @@ -125,16 +116,33 @@ class DependencyScanningWorker {
DependencyConsumer &Consumer, DependencyActionController &Controller,
std::optional<llvm::MemoryBufferRef> TUBuffer = std::nullopt);

/// Run the dependency scanning tool for a given clang driver command-line
/// for a specific module.
///
/// \returns A \c StringError with the diagnostic output if clang errors
/// occurred, success otherwise.
llvm::Error computeDependencies(StringRef WorkingDirectory,
const std::vector<std::string> &CommandLine,
DependencyConsumer &Consumer,
DependencyActionController &Controller,
StringRef ModuleName);
/// The three method below implements a new interface for by name
/// dependency scanning. They together enable the dependency scanning worker
/// to more effectively perform scanning for a sequence of modules
/// by name when the CWD and CommandLine do not change across the queries.

/// @brief Initializing the context and the compiler instance.
/// @param CWD The current working directory used during the scan.
/// @param CommandLine The commandline used for the scan.
/// @return Error if the initializaiton fails.
llvm::Error initializeCompierInstanceWithContext(
StringRef CWD, const std::vector<std::string> &CommandLine);

/// @brief Performaces dependency scanning for the module whose name is
/// specified.
/// @param ModuleName The name of the module whose dependency will be
/// scanned.
/// @param Consumer The dependency consumer that stores the results.
/// @param Controller The controller for the dependency scanning action.
/// @return Error if the scanner incurs errors.
llvm::Error
computeDependenciesByNameWithContext(StringRef ModuleName,
DependencyConsumer &Consumer,
DependencyActionController &Controller);

/// @brief Finalizes the diagnostics engine and deletes the compiler instance.
/// @return Error if errors occur during finalization.
llvm::Error finalizeCompilerInstanceWithContext();

llvm::vfs::FileSystem &getVFS() const { return *BaseFS; }

Expand All @@ -151,14 +159,16 @@ class DependencyScanningWorker {
/// (passed in the constructor).
llvm::IntrusiveRefCntPtr<DependencyScanningWorkerFilesystem> DepFS;

friend class CompilerInstanceWithContext;
std::unique_ptr<CompilerInstanceWithContext> CIWithContext;

/// Private helper functions.
bool scanDependencies(StringRef WorkingDirectory,
const std::vector<std::string> &CommandLine,
DependencyConsumer &Consumer,
DependencyActionController &Controller,
DiagnosticConsumer &DC,
llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS,
std::optional<StringRef> ModuleName);
llvm::IntrusiveRefCntPtr<llvm::vfs::FileSystem> FS);
};

} // end namespace dependencies
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,8 @@ class ModuleDepCollector final : public DependencyCollector {
void attachToPreprocessor(Preprocessor &PP) override;
void attachToASTReader(ASTReader &R) override;

PPCallbacks *getPPCallbacks() override { return CollectorPPPtr; }

/// Apply any changes implied by the discovered dependencies to the given
/// invocation, (e.g. disable implicit modules, add explicit module paths).
void applyDiscoveredDependencies(CompilerInvocation &CI);
Expand Down Expand Up @@ -339,6 +341,10 @@ class ModuleDepCollector final : public DependencyCollector {
std::optional<P1689ModuleInfo> ProvidedStdCXXModule;
std::vector<P1689ModuleInfo> RequiredStdCXXModules;

/// A pointer to the preprocessor callback so we can invoke it directly
/// if needed.
ModuleDepCollectorPP *CollectorPPPtr = nullptr;

/// Checks whether the module is known as being prebuilt.
bool isPrebuiltModule(const Module *M);

Expand Down
14 changes: 0 additions & 14 deletions clang/lib/Frontend/FrontendActions.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1233,20 +1233,6 @@ void PrintDependencyDirectivesSourceMinimizerAction::ExecuteAction() {
llvm::outs());
}

void GetDependenciesByModuleNameAction::ExecuteAction() {
CompilerInstance &CI = getCompilerInstance();
Preprocessor &PP = CI.getPreprocessor();
SourceManager &SM = PP.getSourceManager();
FileID MainFileID = SM.getMainFileID();
SourceLocation FileStart = SM.getLocForStartOfFile(MainFileID);
SmallVector<IdentifierLoc, 2> Path;
IdentifierInfo *ModuleID = PP.getIdentifierInfo(ModuleName);
Path.emplace_back(FileStart, ModuleID);
auto ModResult = CI.loadModule(FileStart, Path, Module::Hidden, false);
PPCallbacks *CB = PP.getPPCallbacks();
CB->moduleImport(SourceLocation(), Path, ModResult);
}

//===----------------------------------------------------------------------===//
// HLSL Specific Actions
//===----------------------------------------------------------------------===//
Expand Down
Loading
Loading