Skip to content

Inaccurate warning message for the last redundant wildcard case in pattern match #21724

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
noti0na1 opened this issue Oct 7, 2024 · 2 comments · Fixed by #21850
Closed

Inaccurate warning message for the last redundant wildcard case in pattern match #21724

noti0na1 opened this issue Oct 7, 2024 · 2 comments · Fixed by #21850

Comments

@noti0na1
Copy link
Member

noti0na1 commented Oct 7, 2024

Compiler version

3.6.0-RC1-bin-SNAPSHOT-nonbootstrapped-git-6ceaab5

Minimized code

trait A
trait B

def test(x: A | B) = x match
  case _: A => println("A")
  case null => println("null")
  case _: B => println("B")
  case _ => println("default") // unreachable

Output

The last case is reported as unreachable except for null, and suggested to be rewritten to case null =>.

-- [E121] Pattern Match Warning: Stest.scala:1240:7 ----------------------------
1240 |  case _ => println("default")
     |       ^
     |Unreachable case except for null (if this is intentional, consider writing case null => instead).
1 warning found

If we replace the wildcard to literal null in the last case, it will be reported as unreachable directly.

-- [E030] Match case Unreachable Warning: Stest.scala:1240:7 -------------------
1240 |  case null => println("default")
     |       ^^^^
     |       Unreachable case
1 warning found

Expectation

The last redundant wildcard case should be reported as unreachable.

Issue

In checkReachability:

if pat != EmptyTree // rethrow case of catch uses EmptyTree
    && !pat.symbol.isAllOf(SyntheticCase, butNot=Method) // ExpandSAMs default cases use SyntheticCase
    && isSubspace(covered, prev)
then {
  val nullOnly = isNullable && i == len - 1 && isWildcardArg(pat)
  val msg = if nullOnly then MatchCaseOnlyNullWarning() else MatchCaseUnreachable()
  report.warning(msg, pat.srcPos)
}
@noti0na1 noti0na1 added itype:bug area:pattern-matching area:nullability stat:needs triage Every issue needs to have an "area" and "itype" label labels Oct 7, 2024
@noti0na1
Copy link
Member Author

noti0na1 commented Oct 7, 2024

Although this issue is produced without explicit nulls, I still add the nullability label because we need to be careful with the behaviour in explicit nulls as well.

@Gedochao Gedochao removed the stat:needs triage Every issue needs to have an "area" and "itype" label label Oct 16, 2024
@noti0na1
Copy link
Member Author

noti0na1 commented Oct 28, 2024

Maybe related:

def test(s: String | Null) = s match // s: String also has the same issue
  case ss => println(1)
  case _ => println(2) // get warning for unreachable except for null
  // but it is unreachable even for null

// both print 1
test("")
test(null)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants