Skip to content

Commit c7c180f

Browse files
committed
Fix <rdar://problem/23700031> QoI: Terrible diagnostic in tuple assignment
When inferring a contextual type for the input expression to an assignment, use getRValueType() to strip lvalues from tuple types in recursive positions, this allows us to produce a sensible diagnostic of: error: binary operator '%' cannot be applied to two 'T' operands instead of: error: cannot assign value of type 'T' to type '@lvalue _' because we don't have a weird lvalue type in the way.
1 parent c73a04d commit c7c180f

File tree

2 files changed

+12
-1
lines changed

2 files changed

+12
-1
lines changed

lib/Sema/CSDiag.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -3855,7 +3855,7 @@ bool FailureDiagnosis::visitAssignExpr(AssignExpr *assignExpr) {
38553855

38563856
// If the source type is already an error type, we've already posted an error.
38573857
auto srcExpr = typeCheckChildIndependently(assignExpr->getSrc(),
3858-
destType->getLValueOrInOutObjectType(),
3858+
destType->getRValueType(),
38593859
CTP_AssignSource);
38603860
if (!srcExpr) return true;
38613861
return false;

test/Constraints/tuple.swift

+11
Original file line numberDiff line numberDiff line change
@@ -141,3 +141,14 @@ variadicWithTrailingClosure(y: 0, fn: +)
141141
variadicWithTrailingClosure(1, 2, 3, fn: +)
142142
variadicWithTrailingClosure(1, fn: +)
143143
variadicWithTrailingClosure(fn: +)
144+
145+
146+
// <rdar://problem/23700031> QoI: Terrible diagnostic in tuple assignment
147+
func gcd_23700031<T>(a: T, b: T) {
148+
var a = a
149+
var b = b
150+
(a, b) = (b, a % b) // expected-error {{binary operator '%' cannot be applied to two 'T' operands}}
151+
// expected-note @-1 {{overloads for '%' exist with these partially matching parameter lists: (UInt8, UInt8), (Int8, Int8), (UInt16, UInt16), (Int16, Int16), (UInt32, UInt32), (Int32, Int32), (UInt64, UInt64), (Int64, Int64), (UInt, UInt), (Int, Int), (Float, Float)}}
152+
}
153+
154+

0 commit comments

Comments
 (0)