Lift implementation-only import checking into a request

This diagnostic logic is currently called from
`finishTypeChecking`, however it doesn't need to
be delayed until after all the source files have
been type-checked, only after they have all had
their imports resolved.

It can therefore be lifted into a request that
operates on a ModuleDecl, and be called from
TypeCheckSourceFileRequest. Being a request will
ensure that the pass is only run once across the
module.

Eventually we'll probably want to re-do import
resolution so that it operates on an entire
module. At that point, we'll want to look at
integrating this diagnostic logic into it.
This commit is contained in:
Hamish Knight
2020-05-18 16:17:37 -07:00
parent 5121349674
commit 851f64095f
6 changed files with 47 additions and 20 deletions

View File

@@ -674,18 +674,20 @@ void UnboundImport::diagnoseInvalidAttr(DeclAttrKind attrKind,
attr->setInvalid();
}
void swift::checkInconsistentImplementationOnlyImports(ModuleDecl *MainModule) {
evaluator::SideEffect
CheckInconsistentImplementationOnlyImportsRequest::evaluate(
Evaluator &evaluator, ModuleDecl *mod) const {
bool hasAnyImplementationOnlyImports =
llvm::any_of(MainModule->getFiles(), [](const FileUnit *F) -> bool {
auto *SF = dyn_cast<SourceFile>(F);
return SF && SF->hasImplementationOnlyImports();
});
llvm::any_of(mod->getFiles(), [](const FileUnit *F) -> bool {
auto *SF = dyn_cast<SourceFile>(F);
return SF && SF->hasImplementationOnlyImports();
});
if (!hasAnyImplementationOnlyImports)
return;
return {};
auto diagnose = [MainModule](const ImportDecl *normalImport,
const ImportDecl *implementationOnlyImport) {
auto &diags = MainModule->getDiags();
auto diagnose = [mod](const ImportDecl *normalImport,
const ImportDecl *implementationOnlyImport) {
auto &diags = mod->getDiags();
{
InFlightDiagnostic warning =
diags.diagnose(normalImport, diag::warn_implementation_only_conflict,
@@ -706,7 +708,7 @@ void swift::checkInconsistentImplementationOnlyImports(ModuleDecl *MainModule) {
llvm::DenseMap<ModuleDecl *, std::vector<const ImportDecl *>> normalImports;
llvm::DenseMap<ModuleDecl *, const ImportDecl *> implementationOnlyImports;
for (const FileUnit *file : MainModule->getFiles()) {
for (const FileUnit *file : mod->getFiles()) {
auto *SF = dyn_cast<SourceFile>(file);
if (!SF)
continue;
@@ -750,6 +752,7 @@ void swift::checkInconsistentImplementationOnlyImports(ModuleDecl *MainModule) {
normalImports[module].push_back(nextImport);
}
}
return {};
}
//===----------------------------------------------------------------------===//