Skip to content

Commit 84205e3

Browse files
committed
[CodeCompletion] Fix a crash in collectPossibleReturnTypesFromContext
Avoid re-typechecking for nested closures. For example: Something { Other { #^COMPLETE^# } } If 'Something' is successfully type checked but 'Other' is failed, the outer closure has type, but the inner closure doesn't. In such state, when the type of 'Other' is requested, the outer closure used to be re-typechecked. That may cause crash because it may contain expressions CSGen doesn't expect. rdar://problem/69246891
1 parent 7f2185d commit 84205e3

File tree

2 files changed

+18
-4
lines changed

2 files changed

+18
-4
lines changed

lib/Sema/TypeCheckStmt.cpp

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1933,11 +1933,13 @@ bool TypeCheckASTNodeAtLocRequest::evaluate(Evaluator &evaluator,
19331933
// The enclosing closure might be a single expression closure or a function
19341934
// builder closure. In such cases, the body elements are type checked with
19351935
// the closure itself. So we need to try type checking the enclosing closure
1936-
// signature first.
1936+
// signature first unless it has already been type checked.
19371937
if (auto CE = dyn_cast<ClosureExpr>(DC)) {
1938-
swift::typeCheckASTNodeAtLoc(CE->getParent(), CE->getLoc());
1939-
if (CE->getBodyState() != ClosureExpr::BodyState::ReadyForTypeChecking)
1940-
return false;
1938+
if (CE->getBodyState() == ClosureExpr::BodyState::Parsed) {
1939+
swift::typeCheckASTNodeAtLoc(CE->getParent(), CE->getLoc());
1940+
if (CE->getBodyState() != ClosureExpr::BodyState::ReadyForTypeChecking)
1941+
return false;
1942+
}
19411943
}
19421944

19431945
TypeChecker::typeCheckASTNode(finder.getRef(), DC,
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
// RUN: %target-swift-ide-test -code-completion -code-completion-token=COMPLETE -source-filename=%s
2+
3+
class MyCls {
4+
public init(body: (Int) throws -> Void) {}
5+
}
6+
7+
func foo() {
8+
MyCls { arg in
9+
MyCls { #^COMPLETE^#
10+
}
11+
}
12+
}

0 commit comments

Comments
 (0)