diff --git a/lib/Sema/CSSimplify.cpp b/lib/Sema/CSSimplify.cpp index 0ff46495538d7..2bf0aa0be444f 100644 --- a/lib/Sema/CSSimplify.cpp +++ b/lib/Sema/CSSimplify.cpp @@ -13394,8 +13394,12 @@ bool ConstraintSystem::simplifyAppliedOverloadsImpl( choiceType = objectType; } + // FIXME: The !getSelfProtocolDecl() check is load-bearing, because + // this optimization interacts poorly with existential opening + // somehow. It should all be removed. if (auto *choiceFnType = choiceType->getAs()) { - if (isa(choice.getDecl())) { + if (isa(choice.getDecl()) && + !choice.getDecl()->getDeclContext()->getSelfProtocolDecl()) { auto choiceResultType = choice.getBaseType() ->getRValueType() ->getMetatypeInstanceType(); diff --git a/test/Constraints/opened_existentials_overload.swift b/test/Constraints/opened_existentials_overload.swift new file mode 100644 index 0000000000000..28eb4c1243a6a --- /dev/null +++ b/test/Constraints/opened_existentials_overload.swift @@ -0,0 +1,30 @@ +// RUN: %target-typecheck-verify-swift + +protocol P {} + +func g(_: some P) {} +// expected-note@-1 {{required by global function 'g' where 'some P' = 'any P'}} + +// rdar://problem/160389221 +func good(_ x: Array) { + Array(x).forEach { y in g(y) } +} + +extension Array { + var ffirst: Element? { fatalError() } + func ffirst(wwhere: (Element) -> Bool) -> Element { fatalError() } +} + +func bad(_ x: Array) { + let y = x.ffirst! + g(y) // ok + + let yy = x.ffirst + g(yy!) // ok + + // FIXME: This is broken + + g(x.ffirst!) + // expected-error@-1 {{type 'any P' cannot conform to 'P'}} + // expected-note@-2 {{only concrete types such as structs, enums and classes can conform to protocols}} +}