SILGen: Don't skip functions nested in closures in inlinable functions.

The logic for walking up the tree of DeclContexts did not handle closures
correctly.

Resolves rdar://119350220
This commit is contained in:
Allan Shortlidge
2023-12-07 15:17:37 -08:00
parent b6d0afba1f
commit 13a1861a1f
2 changed files with 31 additions and 12 deletions

View File

@@ -804,24 +804,23 @@ bool SILGenModule::shouldSkipDecl(Decl *D) {
if (!getASTContext().SILOpts.SkipNonExportableDecls)
return false;
if (auto *afd = dyn_cast<AbstractFunctionDecl>(D)) {
do {
if (afd->isExposedToClients())
return false;
if (D->isExposedToClients())
return false;
// If this function is nested within another function that is exposed to
// clients then it should be emitted.
auto dc = afd->getDeclContext()->getAsDecl();
afd = dc ? dyn_cast<AbstractFunctionDecl>(dc) : nullptr;
} while (afd);
if (isa<AbstractFunctionDecl>(D)) {
// If this function is nested within another function that is exposed to
// clients then it should be emitted.
auto dc = D->getDeclContext();
do {
if (auto afd = dyn_cast<AbstractFunctionDecl>(dc))
if (afd->isExposedToClients())
return false;
} while ((dc = dc->getParent()));
// We didn't find a parent function that is exposed.
return true;
}
if (D->isExposedToClients())
return false;
return true;
}