Skip to content

Commit 604ad21

Browse files
committed
SILGen: Skip function bodies with errors in lazy typechecking mode.
The SILGen pipeline expects function bodies to have been succesfully type checked and will usually crash if it attempts to emit SIL for a function that has errors. To avoid crashing, cause function body typechecking to happen earlier in lazy typechecking mode and then skip functions whenever any errors have been encountered. Resolves rdar://130777647.
1 parent 69ec03c commit 604ad21

File tree

2 files changed

+27
-1
lines changed

2 files changed

+27
-1
lines changed

lib/SILGen/SILGen.cpp

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -646,7 +646,28 @@ static SILFunction *getFunctionToInsertAfter(SILGenModule &SGM,
646646
}
647647

648648
static bool shouldEmitFunctionBody(const AbstractFunctionDecl *AFD) {
649-
return AFD->hasBody() && !AFD->isBodySkipped();
649+
if (!AFD->hasBody())
650+
return false;
651+
652+
if (AFD->isBodySkipped())
653+
return false;
654+
655+
auto &ctx = AFD->getASTContext();
656+
if (ctx.TypeCheckerOpts.EnableLazyTypecheck) {
657+
// Force the function body to be type-checked and then skip it if there
658+
// have been any errors.
659+
(void)AFD->getTypecheckedBody();
660+
661+
// FIXME: Only skip bodies that contain type checking errors.
662+
// It would be ideal to only skip the function body if it is specifically
663+
// the source of an error. However, that information isn't available today
664+
// so instead we avoid emitting all function bodies as soon as any error is
665+
// encountered.
666+
if (ctx.hadError())
667+
return false;
668+
}
669+
670+
return true;
650671
}
651672

652673
static bool isEmittedOnDemand(SILModule &M, SILDeclRef constant) {

test/SILGen/lazy_typecheck_errors.swift

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,3 +53,8 @@ public class DerivedFromNonExistent: NonExistent {
5353

5454
public func method() {}
5555
}
56+
57+
@inlinable public func hasErrorInBody() {
58+
nonExistent()
59+
// expected-error@-1 {{cannot find 'nonExistent' in scope}}
60+
}

0 commit comments

Comments
 (0)