Skip to content

Commit f494bfc

Browse files
committed
Revert "[Sema] Check completion key path component to determine if completion node was type checked in multi expression closure"
This reverts commit ffd0072.
1 parent 996ced8 commit f494bfc

File tree

4 files changed

+20
-92
lines changed

4 files changed

+20
-92
lines changed

include/swift/Sema/ConstraintSystem.h

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1293,10 +1293,6 @@ class Solution {
12931293

12941294
bool hasType(ASTNode node) const;
12951295

1296-
/// Returns \c true if the \p ComponentIndex-th component in \p KP has a type
1297-
/// associated with it.
1298-
bool hasType(const KeyPathExpr *KP, unsigned ComponentIndex) const;
1299-
13001296
/// Retrieve the type of the given node, as recorded in this solution.
13011297
Type getType(ASTNode node) const;
13021298

lib/Sema/CSApply.cpp

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8920,11 +8920,6 @@ bool Solution::hasType(ASTNode node) const {
89208920
return cs.hasType(node);
89218921
}
89228922

8923-
bool Solution::hasType(const KeyPathExpr *KP, unsigned ComponentIndex) const {
8924-
auto &cs = getConstraintSystem();
8925-
return cs.hasType(KP, ComponentIndex);
8926-
}
8927-
89288923
Type Solution::getType(ASTNode node) const {
89298924
auto result = nodeTypes.find(node);
89308925
if (result != nodeTypes.end())

lib/Sema/TypeCheckCodeCompletion.cpp

Lines changed: 20 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -622,10 +622,10 @@ class CompletionContextFinder : public ASTWalker {
622622
/// If we are completing inside an expression, the \c CodeCompletionExpr that
623623
/// represents the code completion token.
624624

625-
/// The AST node that represents the code completion token, either as a
626-
/// \c CodeCompletionExpr or a \c KeyPathExpr which contains a code completion
627-
/// component.
628-
llvm::PointerUnion<CodeCompletionExpr *, const KeyPathExpr *> CompletionNode;
625+
/// The AST node that represents the code completion token, either as an
626+
/// expression or a KeyPath component.
627+
llvm::PointerUnion<CodeCompletionExpr *, const KeyPathExpr::Component *>
628+
CompletionNode;
629629

630630
Expr *InitialExpr = nullptr;
631631
DeclContext *InitialDC;
@@ -679,13 +679,10 @@ class CompletionContextFinder : public ASTWalker {
679679
for (auto &component : KeyPath->getComponents()) {
680680
if (component.getKind() ==
681681
KeyPathExpr::Component::Kind::CodeCompletion) {
682-
CompletionNode = KeyPath;
682+
CompletionNode = &component;
683683
return std::make_pair(false, nullptr);
684684
}
685685
}
686-
// Code completion in key paths is modelled by a code completion component
687-
// Don't walk the key path's parsed expressions.
688-
return std::make_pair(false, E);
689686
}
690687

691688
return std::make_pair(true, E);
@@ -720,33 +717,12 @@ class CompletionContextFinder : public ASTWalker {
720717
}
721718

722719
bool hasCompletionKeyPathComponent() const {
723-
return CompletionNode.dyn_cast<const KeyPathExpr *>() != nullptr;
720+
return CompletionNode.dyn_cast<const KeyPathExpr::Component *>() != nullptr;
724721
}
725722

726-
/// If we are completing in a key path, returns the \c KeyPath that contains
727-
/// the code completion component.
728-
const KeyPathExpr *getKeyPathContainingCompletionComponent() const {
723+
const KeyPathExpr::Component *getCompletionKeyPathComponent() const {
729724
assert(hasCompletionKeyPathComponent());
730-
return CompletionNode.get<const KeyPathExpr *>();
731-
}
732-
733-
/// If we are completing in a key path, returns the index at which the key
734-
/// path has the code completion component.
735-
size_t getKeyPathCompletionComponentIndex() const {
736-
assert(hasCompletionKeyPathComponent());
737-
size_t ComponentIndex = 0;
738-
auto Components =
739-
getKeyPathContainingCompletionComponent()->getComponents();
740-
for (auto &Component : Components) {
741-
if (Component.getKind() == KeyPathExpr::Component::Kind::CodeCompletion) {
742-
break;
743-
} else {
744-
ComponentIndex++;
745-
}
746-
}
747-
assert(ComponentIndex < Components.size() &&
748-
"No completion component in the key path?");
749-
return ComponentIndex;
725+
return CompletionNode.get<const KeyPathExpr::Component *>();
750726
}
751727

752728
struct Fallback {
@@ -977,27 +953,20 @@ bool TypeChecker::typeCheckForCodeCompletion(
977953
if (contextAnalyzer.locatedInMultiStmtClosure()) {
978954
auto &solution = solutions.front();
979955

980-
bool HasTypeForCompletionNode = false;
981-
if (completionExpr) {
982-
HasTypeForCompletionNode = solution.hasType(completionExpr);
983-
} else {
984-
assert(contextAnalyzer.hasCompletionKeyPathComponent());
985-
HasTypeForCompletionNode = solution.hasType(
986-
contextAnalyzer.getKeyPathContainingCompletionComponent(),
987-
contextAnalyzer.getKeyPathCompletionComponentIndex());
956+
if (solution.hasType(contextAnalyzer.getCompletionExpr())) {
957+
llvm::for_each(solutions, callback);
958+
return CompletionResult::Ok;
988959
}
989960

990-
if (!HasTypeForCompletionNode) {
991-
// At this point we know the code completion node wasn't checked with
992-
// the closure's surrounding context, so can defer to regular
993-
// type-checking for the current call to typeCheckExpression. If that
994-
// succeeds we will get a second call to typeCheckExpression for the
995-
// body of the closure later and can gather completions then. If it
996-
// doesn't we rely on the fallback typechecking in the subclasses of
997-
// TypeCheckCompletionCallback that considers in isolation a
998-
// sub-expression of the closure that contains the completion location.
999-
return CompletionResult::NotApplicable;
1000-
}
961+
// At this point we know the code completion expression wasn't checked
962+
// with the closure's surrounding context, so can defer to regular type-
963+
// checking for the current call to typeCheckExpression. If that succeeds
964+
// we will get a second call to typeCheckExpression for the body of the
965+
// closure later and can gather completions then. If it doesn't we rely
966+
// on the fallback typechecking in the subclasses of
967+
// TypeCheckCompletionCallback that considers in isolation a
968+
// sub-expression of the closure that contains the completion location.
969+
return CompletionResult::NotApplicable;
1001970
}
1002971

1003972
llvm::for_each(solutions, callback);

test/IDE/complete_swift_key_path.swift

Lines changed: 0 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -36,9 +36,6 @@
3636
// RUN: %target-swift-ide-test -code-completion -source-filename %s -code-completion-token=GENERIC_KEY_PATH_RESULT | %FileCheck %s -check-prefix=PERSONTYPE-DOT
3737

3838
// RUN: %target-swift-ide-test -code-completion -source-filename %s -code-completion-token=COMPLETE_AFTER_SELF | %FileCheck %s -check-prefix=OBJ-NODOT
39-
// RUN: %target-swift-ide-test -code-completion -source-filename %s -code-completion-token=IN_RESULT_BUILDER | %FileCheck %s -check-prefix=PERSONTYPE-DOT
40-
// RUN: %target-swift-ide-test -code-completion -source-filename %s -code-completion-token=IN_MULTI_STMT_CLOSURE | %FileCheck %s -check-prefix=PERSONTYPE-DOT
41-
4239
class Person {
4340
var name: String
4441
var friends: [Person] = []
@@ -199,32 +196,3 @@ func genericKeyPathResult<KeyPathResult>(id: KeyPath<Person, KeyPathResult>) {
199196
func completeAfterSelf(people: [Person]) {
200197
people.map(\.self#^COMPLETE_AFTER_SELF^#)
201198
}
202-
203-
func inResultBuilder() {
204-
protocol View2 {}
205-
206-
@resultBuilder public struct ViewBuilder2 {
207-
public static func buildBlock<Content>(_ content: Content) -> Content where Content : View2 { fatalError() }
208-
public static func buildIf<Content>(_ content: Content?) -> Content? where Content : View2 { fatalError() }
209-
}
210-
211-
struct VStack2<Content>: View2 {
212-
init(@ViewBuilder2 view: () -> Content) {}
213-
}
214-
215-
@ViewBuilder2 var body: some View2 {
216-
VStack2 {
217-
if true {
218-
var people: [Person] = []
219-
people.map(\.#^IN_RESULT_BUILDER^#)
220-
}
221-
}
222-
}
223-
}
224-
225-
func inMultiStmtClosure(closure: () -> Void) {
226-
inMultiStmtClosure {
227-
var people: [Person] = []
228-
people.map(\.#^IN_MULTI_STMT_CLOSURE^#)
229-
}
230-
}

0 commit comments

Comments
 (0)