From daa117eab715f38d08facfb826b04116bc9fe0b7 Mon Sep 17 00:00:00 2001 From: Nadrieril Date: Sun, 17 Nov 2019 17:48:45 +0000 Subject: [PATCH] Small improvement to exhaustiveness diagnostics --- src/librustc_mir/hair/pattern/_match.rs | 16 ++++++++++++++-- .../usefulness/slice-patterns-exhaustiveness.rs | 4 ++-- .../slice-patterns-exhaustiveness.stderr | 8 ++++---- 3 files changed, 20 insertions(+), 8 deletions(-) diff --git a/src/librustc_mir/hair/pattern/_match.rs b/src/librustc_mir/hair/pattern/_match.rs index 51ee1f29bf8..d379f606da4 100644 --- a/src/librustc_mir/hair/pattern/_match.rs +++ b/src/librustc_mir/hair/pattern/_match.rs @@ -957,8 +957,20 @@ fn apply<'a>( PatKind::Slice { prefix: subpatterns.collect(), slice: None, suffix: vec![] } } VarLen(prefix, _) => { - let prefix = subpatterns.by_ref().take(prefix as usize).collect(); - let suffix = subpatterns.collect(); + let mut prefix: Vec<_> = subpatterns.by_ref().take(prefix as usize).collect(); + let mut suffix: Vec<_> = subpatterns.collect(); + if slice.array_len.is_some() { + // Improves diagnostics a bit: if the type is a known-size array, instead + // of reporting `[x, _, .., _, y]`, we prefer to report `[x, .., y]`. + // This is incorrect if the size is not known, since `[_, ..]` captures + // arrays of lengths `>= 1` whereas `[..]` captures any length. + while !suffix.is_empty() && suffix.first().unwrap().is_wildcard() { + suffix.remove(0); + } + while !prefix.is_empty() && prefix.last().unwrap().is_wildcard() { + prefix.pop(); + } + } let wild = Pat::wildcard_from_ty(ty); PatKind::Slice { prefix, slice: Some(wild), suffix } } diff --git a/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.rs b/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.rs index 5881c35d356..eb3dfac950f 100644 --- a/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.rs +++ b/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.rs @@ -12,11 +12,11 @@ fn main() { [true, .., true] => {} } match s3 { - //~^ ERROR `&[false, .., _]` not covered + //~^ ERROR `&[false, ..]` not covered [true, .., true] => {} } match s10 { - //~^ ERROR `&[false, .., _]` not covered + //~^ ERROR `&[false, ..]` not covered [true, .., true] => {} } diff --git a/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.stderr b/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.stderr index 9a711f2a441..ebadedccfea 100644 --- a/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.stderr +++ b/src/test/ui/pattern/usefulness/slice-patterns-exhaustiveness.stderr @@ -6,19 +6,19 @@ LL | match s2 { | = help: ensure that all possible cases are being handled, possibly by adding wildcards or more match arms -error[E0004]: non-exhaustive patterns: `&[false, .., _]` not covered +error[E0004]: non-exhaustive patterns: `&[false, ..]` not covered --> $DIR/slice-patterns-exhaustiveness.rs:14:11 | LL | match s3 { - | ^^ pattern `&[false, .., _]` not covered + | ^^ pattern `&[false, ..]` not covered | = help: ensure that all possible cases are being handled, possibly by adding wildcards or more match arms -error[E0004]: non-exhaustive patterns: `&[false, .., _]` not covered +error[E0004]: non-exhaustive patterns: `&[false, ..]` not covered --> $DIR/slice-patterns-exhaustiveness.rs:18:11 | LL | match s10 { - | ^^^ pattern `&[false, .., _]` not covered + | ^^^ pattern `&[false, ..]` not covered | = help: ensure that all possible cases are being handled, possibly by adding wildcards or more match arms