Skip to content

Commit 8951373

Browse files
committed
[IDE] Inspect all equivalent type variables to replace a type variable by an archetype
Sometimes the type variable itself doesn't have have an originator that can be replaced by an archetype but one of its equivalent type variable does. Search thorough all equivalent type variables, looking for one that can be replaced by a generic parameter.
1 parent 3022812 commit 8951373

File tree

2 files changed

+25
-2
lines changed

2 files changed

+25
-2
lines changed

lib/Sema/ConstraintSystem.cpp

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3814,7 +3814,7 @@ Type Solution::simplifyTypeForCodeCompletion(Type Ty) const {
38143814

38153815
// Replace all type variables (which must come from placeholders) by their
38163816
// generic parameters. Because we call into simplifyTypeImpl
3817-
Ty = CS.simplifyTypeImpl(Ty, [&CS](TypeVariableType *typeVar) -> Type {
3817+
Ty = CS.simplifyTypeImpl(Ty, [&CS, this](TypeVariableType *typeVar) -> Type {
38183818
// Code completion depends on generic parameter type being represented in
38193819
// terms of `ArchetypeType` since it's easy to extract protocol requirements
38203820
// from it.
@@ -3831,6 +3831,29 @@ Type Solution::simplifyTypeForCodeCompletion(Type Ty) const {
38313831
return archetype;
38323832
}
38333833

3834+
// Sometimes the type variable itself doesn't have have an originator that
3835+
// can be replaced by an archetype but one of its equivalent type variable
3836+
// does.
3837+
// Search thorough all equivalent type variables, looking for one that can
3838+
// be replaced by a generic parameter.
3839+
std::vector<std::pair<TypeVariableType *, Type>> bindings(
3840+
typeBindings.begin(), typeBindings.end());
3841+
// Make sure we iterate the bindings in a deterministic order.
3842+
llvm::sort(bindings, [](const std::pair<TypeVariableType *, Type> &lhs,
3843+
const std::pair<TypeVariableType *, Type> &rhs) {
3844+
return lhs.first->getID() < rhs.first->getID();
3845+
});
3846+
for (auto binding : bindings) {
3847+
if (auto placeholder = binding.second->getAs<PlaceholderType>()) {
3848+
if (placeholder->getOriginator().dyn_cast<TypeVariableType *>() ==
3849+
typeVar) {
3850+
if (auto archetype = getTypeVarAsArchetype(binding.first)) {
3851+
return archetype;
3852+
}
3853+
}
3854+
}
3855+
}
3856+
38343857
// When applying the logic below to get contextual types inside result
38353858
// builders, the code completion type variable is connected by a one-way
38363859
// constraint to a type variable in the buildBlock call, but that is not the

test/IDE/complete_subscript.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ func test1() {
3939

4040
let _ = MyStruct[#^METATYPE_UNRESOLVED_BRACKET^#
4141
// METATYPE_UNRESOLVED_BRACKET: Begin completions
42-
// METATYPE_UNRESOLVED_BRACKET-DAG: Decl[Subscript]/CurrNominal/Flair[ArgLabels]: ['[']{#(x): Int#}, {#static: _#}[']'][#MyStruct<_>#];
42+
// METATYPE_UNRESOLVED_BRACKET-DAG: Decl[Subscript]/CurrNominal/Flair[ArgLabels]: ['[']{#(x): Int#}, {#static: T#}[']'][#MyStruct<T>#];
4343
// METATYPE_UNRESOLVED_BRACKET: End completions
4444

4545
let _ = MyStruct<Int> #^METATYPE_INT^#

0 commit comments

Comments
 (0)