Skip to content

Commit 58a8a2a

Browse files
authored
Merge pull request #67591 from hamishknight/quieter
[CS] Avoid emitting invalid binding diagnostic in more cases
2 parents 9e35a83 + 2210ea6 commit 58a8a2a

File tree

2 files changed

+31
-7
lines changed

2 files changed

+31
-7
lines changed

lib/Sema/CSDiagnostics.cpp

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -8365,12 +8365,13 @@ bool InvalidEmptyKeyPathFailure::diagnoseAsError() {
83658365
}
83668366

83678367
bool InvalidPatternInExprFailure::diagnoseAsError() {
8368-
// Check to see if we have something like 'case <fn>(let foo)', where <fn>
8369-
// has a fix associated with it. In such a case, it's more likely than not
8370-
// that the user is trying to write an EnumElementPattern, but has made some
8371-
// kind of mistake in the function expr that causes it to be treated as an
8372-
// ExprPattern. Emitting an additional error for the out of place 'let foo' is
8373-
// just noise in that case, so let's avoid diagnosing.
8368+
// Check to see if we have something like 'case <fn>(let foo)', where either
8369+
// <fn> or the call itself has a fix associated with it. In such a case, it's
8370+
// more likely than not that the user is trying to write an
8371+
// EnumElementPattern, but has made some kind of mistake in the function expr
8372+
// that causes it to be treated as an ExprPattern. Emitting an additional
8373+
// error for the out of place 'let foo' is just noise in that case, so let's
8374+
// avoid diagnosing.
83748375
llvm::SmallPtrSet<Expr *, 4> fixAnchors;
83758376
for (auto *fix : getSolution().Fixes) {
83768377
if (auto *anchor = getAsExpr(fix->getAnchor()))
@@ -8380,7 +8381,7 @@ bool InvalidPatternInExprFailure::diagnoseAsError() {
83808381
auto *E = castToExpr(getLocator()->getAnchor());
83818382
while (auto *parent = findParentExpr(E)) {
83828383
if (auto *CE = dyn_cast<CallExpr>(parent)) {
8383-
if (fixAnchors.contains(CE->getFn()))
8384+
if (fixAnchors.contains(CE) || fixAnchors.contains(CE->getFn()))
83848385
return false;
83858386
}
83868387
E = parent;

test/Constraints/rdar113025351.swift

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// RUN: %target-typecheck-verify-swift
2+
3+
struct S {
4+
enum E: Error {
5+
case e(Int)
6+
case f
7+
}
8+
}
9+
10+
func foo() throws {}
11+
12+
// rdar://113025351: Avoid emitting a separate diagnostic complaining that a
13+
// 'let' cannot be nested in an expression, as it just adds noise.
14+
func bar() throws {
15+
do {
16+
try foo()
17+
} catch S.E(let x) {} // expected-error {{'S.E' cannot be constructed because it has no accessible initializers}}
18+
}
19+
20+
func baz(_ x: S.E) {
21+
if case S.E(let y) = x {} // expected-error {{'S.E' cannot be constructed because it has no accessible initializers}}
22+
if case S.E(S.E.e(let y)) = x {} // expected-error {{'S.E' cannot be constructed because it has no accessible initializers}}
23+
}

0 commit comments

Comments
 (0)