about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--tests/ui/pattern/never_patterns.stderr17
-rw-r--r--tests/ui/rfcs/rfc-0000-never_patterns/typeck.rs (renamed from tests/ui/pattern/never_patterns.rs)64
2 files changed, 51 insertions, 30 deletions
diff --git a/tests/ui/pattern/never_patterns.stderr b/tests/ui/pattern/never_patterns.stderr
deleted file mode 100644
index 20eeb01cf71..00000000000
--- a/tests/ui/pattern/never_patterns.stderr
+++ /dev/null
@@ -1,17 +0,0 @@
-error[E0005]: refutable pattern in local binding
-  --> $DIR/never_patterns.rs:10:9
-   |
-LL |     let Ok(_x) = res;
-   |         ^^^^^^ pattern `Err(_)` not covered
-   |
-   = note: `let` bindings require an "irrefutable pattern", like a `struct` or an `enum` with only one variant
-   = note: for more information, visit https://doc.rust-lang.org/book/ch18-02-refutability.html
-   = note: the matched value is of type `Result<T, Void>`
-help: you might want to use `let else` to handle the variant that isn't matched
-   |
-LL |     let Ok(_x) = res else { todo!() };
-   |                      ++++++++++++++++
-
-error: aborting due to 1 previous error
-
-For more information about this error, try `rustc --explain E0005`.
diff --git a/tests/ui/pattern/never_patterns.rs b/tests/ui/rfcs/rfc-0000-never_patterns/typeck.rs
index 8f44f8a6559..90ff34e2f02 100644
--- a/tests/ui/pattern/never_patterns.rs
+++ b/tests/ui/rfcs/rfc-0000-never_patterns/typeck.rs
@@ -1,63 +1,84 @@
+// check-pass
 #![feature(never_patterns)]
+#![feature(exhaustive_patterns)]
 #![allow(incomplete_features)]
 
+#[derive(Copy, Clone)]
 enum Void {}
 
 fn main() {}
 
 // The classic use for empty types.
-fn safe_unwrap_result<T>(res: Result<T, Void>) {
-    let Ok(_x) = res; //~ ERROR refutable pattern in local binding
+fn safe_unwrap_result<T: Copy>(res: Result<T, Void>) {
+    let Ok(_x) = res;
     let (Ok(_x) | Err(!)) = &res;
-    let (Ok(_x) | Err(&!)) = res.as_ref();
+    let (Ok(_x) | Err(!)) = res.as_ref();
 }
 
 // Check we only accept `!` where we want to.
-fn never_pattern_location(void: Void) {
+fn never_pattern_typeck(void: Void) {
     // FIXME(never_patterns): Don't accept on a non-empty type.
+    match () {
+        !,
+    }
+    match (0, false) {
+        !,
+    }
+    match (0, false) {
+        (_, !),
+    }
     match Some(0) {
         None => {}
         Some(!),
     }
+
     // FIXME(never_patterns): Don't accept on an arbitrary type, even if there are no more branches.
     match () {
         () => {}
         !,
     }
+
     // FIXME(never_patterns): Don't accept even on an empty branch.
     match None::<Void> {
         None => {}
         !,
     }
+    match (&[] as &[Void]) {
+        [] => {}
+        !,
+    }
     // FIXME(never_patterns): Let alone if the emptiness is behind a reference.
     match None::<&Void> {
         None => {}
         !,
     }
+
     // Participate in match ergonomics.
     match &void {
-        !
+        !,
     }
     match &&void {
-        !
+        !,
     }
     match &&void {
-        &!
+        &!,
     }
     match &None::<Void> {
         None => {}
-        Some(!)
+        Some(!),
     }
     match None::<&Void> {
         None => {}
         Some(!),
     }
-    // Accept on a composite empty type.
-    match None::<&(u32, Void)> {
-        None => {}
-        Some(&!),
+
+    // Accept on a directly empty type.
+    match void {
+        !,
+    }
+    match &void {
+        &!,
     }
-    // Accept on an simple empty type.
     match None::<Void> {
         None => {}
         Some(!),
@@ -70,4 +91,21 @@ fn never_pattern_location(void: Void) {
         None => {}
         Some(&(_, !)),
     }
+    match (&[] as &[Void]) {
+        [] => {}
+        [!],
+    }
+    // Accept on a composite empty type.
+    match None::<&(u32, Void)> {
+        None => {}
+        Some(&!),
+    }
+    match None::<&(u32, Void)> {
+        None => {}
+        Some(!),
+    }
+    match None::<&Result<Void, Void>> {
+        None => {}
+        Some(!),
+    }
 }