mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
add support to getTopLevelDecls for clang submodules (#76401)
rdar://126031510
This commit is contained in:
@@ -17,6 +17,7 @@
|
||||
#include "swift/AST/Module.h"
|
||||
#include "swift/AST/NameLookup.h"
|
||||
#include "swift/Sema/IDETypeChecking.h"
|
||||
#include "clang/Basic/Module.h"
|
||||
#include "llvm/ADT/STLExtras.h"
|
||||
#include "llvm/Support/JSON.h"
|
||||
#include "llvm/Support/Path.h"
|
||||
@@ -30,14 +31,16 @@ namespace {
|
||||
int serializeSymbolGraph(SymbolGraph &SG,
|
||||
const SymbolGraphOptions &Options) {
|
||||
SmallString<256> FileName;
|
||||
FileName.append(SG.M.getNameStr());
|
||||
FileName.append(getFullModuleName(&SG.M));
|
||||
if (SG.ExtendedModule.has_value()) {
|
||||
FileName.push_back('@');
|
||||
FileName.append(SG.ExtendedModule.value()->getNameStr());
|
||||
// FileName.append(SG.ExtendedModule.value()->getNameStr());
|
||||
FileName.append(getFullModuleName(SG.ExtendedModule.value()));
|
||||
} else if (SG.DeclaringModule.has_value()) {
|
||||
// Treat cross-import overlay modules as "extensions" of their declaring module
|
||||
FileName.push_back('@');
|
||||
FileName.append(SG.DeclaringModule.value()->getNameStr());
|
||||
// FileName.append(SG.DeclaringModule.value()->getNameStr());
|
||||
FileName.append(getFullModuleName(SG.DeclaringModule.value()));
|
||||
}
|
||||
FileName.append(".symbols.json");
|
||||
|
||||
@@ -62,18 +65,60 @@ int symbolgraphgen::emitSymbolGraphForModule(
|
||||
ModuleDecl *M, const SymbolGraphOptions &Options) {
|
||||
ModuleDecl::ImportCollector importCollector(Options.MinimumAccessLevel);
|
||||
|
||||
auto importFilter = [&Options](const ModuleDecl *module) {
|
||||
if (!module)
|
||||
return false;
|
||||
SmallPtrSet<const clang::Module *, 2> ExportedClangModules = {};
|
||||
SmallPtrSet<const clang::Module *, 2> WildcardExportClangModules = {};
|
||||
if (const auto *ClangModule = M->findUnderlyingClangModule()) {
|
||||
// Scan through the Clang module's exports and collect them for later
|
||||
// handling
|
||||
for (auto ClangExport : ClangModule->Exports) {
|
||||
if (ClangExport.getInt()) {
|
||||
// Blanket exports are represented as a true boolean tag
|
||||
if (const auto *ExportParent = ClangExport.getPointer()) {
|
||||
// If a pointer is present, this is a scoped blanket export, like
|
||||
// `export Submodule.*`
|
||||
WildcardExportClangModules.insert(ExportParent);
|
||||
} else {
|
||||
// Otherwise it represents a full blanket `export *`
|
||||
WildcardExportClangModules.insert(ClangModule);
|
||||
}
|
||||
} else if (!ClangExport.getInt() && ClangExport.getPointer()) {
|
||||
// This is an explicit `export Submodule`
|
||||
ExportedClangModules.insert(ClangExport.getPointer());
|
||||
}
|
||||
}
|
||||
|
||||
if (ExportedClangModules.empty() && WildcardExportClangModules.empty()) {
|
||||
// HACK: In the absence of an explicit export declaration, export all of the submodules.
|
||||
WildcardExportClangModules.insert(ClangModule);
|
||||
}
|
||||
}
|
||||
|
||||
auto importFilter = [&Options, &WildcardExportClangModules,
|
||||
&ExportedClangModules](const ModuleDecl *module) {
|
||||
if (!module)
|
||||
return false;
|
||||
|
||||
if (const auto *ClangModule = module->findUnderlyingClangModule()) {
|
||||
if (ExportedClangModules.contains(ClangModule)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
for (const auto *ClangParent : WildcardExportClangModules) {
|
||||
if (ClangModule->isSubModuleOf(ClangParent))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (Options.AllowedReexportedModules.has_value())
|
||||
for (const auto &allowedModuleName : *Options.AllowedReexportedModules)
|
||||
if (allowedModuleName == module->getNameStr())
|
||||
return true;
|
||||
|
||||
return false;
|
||||
};
|
||||
return false;
|
||||
};
|
||||
|
||||
if (Options.AllowedReexportedModules.has_value())
|
||||
if (Options.AllowedReexportedModules.has_value() ||
|
||||
!WildcardExportClangModules.empty() || !ExportedClangModules.empty())
|
||||
importCollector.importFilter = std::move(importFilter);
|
||||
|
||||
SmallVector<Decl *, 64> ModuleDecls;
|
||||
|
||||
Reference in New Issue
Block a user