mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
Revert "Disallow conversions from IUOs to extistentials."
Revert 7c665c105b because it results in a
much worse source compatibility regression than the one it was intended
to fix.
The problem is that it results in force-unwrapping IUOs, which can lead
to cases where we prefer type-checking solutions that choose methods
over properties where we used to choose properties. So for example a
collection literal like [x] will result in a collection with a method
named 'x' in it rather than a property named 'x'.
I'll be looking at other solutions which fix both the original
compatibility regression as well as retain the behavior in the new test
added here.
Fixes SR-3715 and rdar://problem/30176166.
This commit is contained in:
@@ -2032,22 +2032,9 @@ ConstraintSystem::matchTypes(Type type1, Type type2, ConstraintKind kind,
|
||||
// Instance type check for the above. We are going to check conformance once
|
||||
// we hit commit_to_conversions below, but we have to add a token restriction
|
||||
// to ensure we wrap the metatype value in a metatype erasure.
|
||||
|
||||
// Disallow direct IUO-to-Any conversions. This will allow us to
|
||||
// force-unwrap the IUO before attempting to convert, which makes it
|
||||
// possible to disambiguate certain cases where we would otherwise
|
||||
// consider an IUO or plain optional to be equally desirable choices
|
||||
// where we really want the IUO to decay to a plain optional.
|
||||
{
|
||||
bool disallowExistentialConversion = false;
|
||||
if (type2->isAny() &&
|
||||
type1->getRValueType()->getImplicitlyUnwrappedOptionalObjectType())
|
||||
disallowExistentialConversion = true;
|
||||
|
||||
if (concrete && !disallowExistentialConversion &&
|
||||
type2->isExistentialType() && kind >= ConstraintKind::Subtype) {
|
||||
conversionsOrFixes.push_back(ConversionRestrictionKind::Existential);
|
||||
}
|
||||
if (concrete && type2->isExistentialType() &&
|
||||
kind >= ConstraintKind::Subtype) {
|
||||
conversionsOrFixes.push_back(ConversionRestrictionKind::Existential);
|
||||
}
|
||||
|
||||
// A value of type T! can be converted to type U if T is convertible
|
||||
|
||||
Reference in New Issue
Block a user