Skip to content

Commit fc4216e

Browse files
committed
[Sema] Don't suggest fixits that try to force unwrap implicit $match
Check if a variable is actually spelled out in code before suggesting a fixit that adds a force unwrap to it This fixes SR-1827
1 parent f96083c commit fc4216e

File tree

4 files changed

+32
-2
lines changed

4 files changed

+32
-2
lines changed

lib/Sema/CSDiag.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5943,7 +5943,7 @@ bool ConstraintSystem::salvage(SmallVectorImpl<Solution> &viable, Expr *expr) {
59435943

59445944
if (getExpressionTooComplex()) {
59455945
TC.diagnose(expr->getLoc(), diag::expression_too_complex).
5946-
highlight(expr->getSourceRange());
5946+
highlight(expr->getSourceRange());
59475947
return true;
59485948
}
59495949

lib/Sema/CSSimplify.cpp

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2009,7 +2009,20 @@ ConstraintSystem::matchTypes(Type type1, Type type2, TypeMatchKind kind,
20092009
// If we have an optional type, try to force-unwrap it.
20102010
// FIXME: Should we also try '?'?
20112011
if (objectType1->getOptionalObjectType()) {
2012-
conversionsOrFixes.push_back(FixKind::ForceOptional);
2012+
bool forceUnwrapPossible = true;
2013+
if (auto declRefExpr =
2014+
dyn_cast_or_null<DeclRefExpr>(locator.trySimplifyToExpr())) {
2015+
if (declRefExpr->getDecl()->isImplicit()) {
2016+
// The expression that provides the first type is implicit and never
2017+
// spelled out in source code, e.g. $match in an expression pattern.
2018+
// Thus we cannot force unwrap the first type
2019+
forceUnwrapPossible = false;
2020+
}
2021+
}
2022+
2023+
if (forceUnwrapPossible) {
2024+
conversionsOrFixes.push_back(FixKind::ForceOptional);
2025+
}
20132026
}
20142027

20152028
// If we have a value of type AnyObject that we're trying to convert to

lib/Sema/TypeCheckConstraints.cpp

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2150,6 +2150,8 @@ bool TypeChecker::typeCheckExprPattern(ExprPattern *EP, DeclContext *DC,
21502150
Context.getIdentifier("$match"),
21512151
rhsType,
21522152
DC);
2153+
2154+
matchVar->setImplicit();
21532155
EP->setMatchVar(matchVar);
21542156
matchVar->setHasNonPatternBindingInit();
21552157

test/expr/unary/selector/selector.swift

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -120,3 +120,18 @@ switch optionalSel {
120120
case #selector(C1.method1)?:
121121
break
122122
}
123+
124+
@objc class SR1827 {
125+
func bar() {}
126+
}
127+
128+
switch optionalSel {
129+
case #selector(SR1827.bar): // expected-error{{expression pattern of type 'Selector' cannot match values of type 'Selector?'}}
130+
break
131+
case #selector(SR1827.bar)!: // expected-error{{cannot force unwrap value of non-optional type 'Selector'}}
132+
break
133+
case #selector(SR1827.bar)?:
134+
break
135+
default:
136+
break
137+
}

0 commit comments

Comments
 (0)