about summary refs log tree commit diff
diff options
context:
space:
mode:
authorOli Scherer <git-spam-no-reply9815368754983@oli-obk.de>2024-04-09 10:08:20 +0000
committerOli Scherer <git-spam-no-reply9815368754983@oli-obk.de>2024-04-16 11:52:12 +0000
commit0a88339a57557152bb32c4969f2f76955793133e (patch)
tree549f3ad6a2f308927cf548391be8d39a00558f79
parent4f75d67b6fd0bd677c17d5060facd31c70dd4afe (diff)
downloadrust-0a88339a57557152bb32c4969f2f76955793133e.tar.gz
rust-0a88339a57557152bb32c4969f2f76955793133e.zip
Don't ICE for kind mismatches during error rendering
-rw-r--r--compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs3
-rw-r--r--tests/ui/const-generics/kind_mismatch.rs24
-rw-r--r--tests/ui/const-generics/kind_mismatch.stderr39
3 files changed, 66 insertions, 0 deletions
diff --git a/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs b/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs
index 3dc54b33801..4aa5f9752ab 100644
--- a/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs
+++ b/compiler/rustc_trait_selection/src/traits/error_reporting/type_err_ctxt_ext.rs
@@ -1974,6 +1974,9 @@ impl<'tcx> TypeErrCtxt<'_, 'tcx> {
                     for (obligation_arg, impl_arg) in
                         std::iter::zip(obligation_trait_ref.args, impl_trait_ref.args)
                     {
+                        if (obligation_arg, impl_arg).references_error() {
+                            return false;
+                        }
                         if let Err(terr) =
                             ocx.eq(&ObligationCause::dummy(), param_env, impl_arg, obligation_arg)
                         {
diff --git a/tests/ui/const-generics/kind_mismatch.rs b/tests/ui/const-generics/kind_mismatch.rs
new file mode 100644
index 00000000000..bab58d5952a
--- /dev/null
+++ b/tests/ui/const-generics/kind_mismatch.rs
@@ -0,0 +1,24 @@
+//! This test used to ICE in typeck because of the type/const mismatch,
+//! even though wfcheck already errored.
+//! issue: rust-lang/rust#123457
+
+pub struct KeyHolder<const K: u8> {}
+
+pub trait ContainsKey<const K: u8> {}
+
+pub trait SubsetExcept<P> {}
+
+impl<K> ContainsKey<K> for KeyHolder<K> {}
+//~^ ERROR: type provided when a constant was expected
+//~| ERROR: type provided when a constant was expected
+
+impl<P, T: ContainsKey<0>> SubsetExcept<P> for T {}
+
+pub fn remove_key<K, S: SubsetExcept<K>>() -> S {
+    loop {}
+}
+
+fn main() {
+    let map: KeyHolder<0> = remove_key::<_, _>();
+    //~^ ERROR: the trait bound `KeyHolder<0>: SubsetExcept<_>` is not satisfied
+}
diff --git a/tests/ui/const-generics/kind_mismatch.stderr b/tests/ui/const-generics/kind_mismatch.stderr
new file mode 100644
index 00000000000..80968ebea68
--- /dev/null
+++ b/tests/ui/const-generics/kind_mismatch.stderr
@@ -0,0 +1,39 @@
+error[E0747]: type provided when a constant was expected
+  --> $DIR/kind_mismatch.rs:11:38
+   |
+LL | impl<K> ContainsKey<K> for KeyHolder<K> {}
+   |      -                               ^
+   |      |
+   |      help: consider changing this type parameter to a const parameter: `const K: u8`
+
+error[E0747]: type provided when a constant was expected
+  --> $DIR/kind_mismatch.rs:11:21
+   |
+LL | impl<K> ContainsKey<K> for KeyHolder<K> {}
+   |      -              ^
+   |      |
+   |      help: consider changing this type parameter to a const parameter: `const K: u8`
+
+error[E0277]: the trait bound `KeyHolder<0>: SubsetExcept<_>` is not satisfied
+  --> $DIR/kind_mismatch.rs:22:45
+   |
+LL |     let map: KeyHolder<0> = remove_key::<_, _>();
+   |                                             ^ the trait `ContainsKey<0>` is not implemented for `KeyHolder<0>`, which is required by `KeyHolder<0>: SubsetExcept<_>`
+   |
+note: required for `KeyHolder<0>` to implement `SubsetExcept<_>`
+  --> $DIR/kind_mismatch.rs:15:28
+   |
+LL | impl<P, T: ContainsKey<0>> SubsetExcept<P> for T {}
+   |            --------------  ^^^^^^^^^^^^^^^     ^
+   |            |
+   |            unsatisfied trait bound introduced here
+note: required by a bound in `remove_key`
+  --> $DIR/kind_mismatch.rs:17:25
+   |
+LL | pub fn remove_key<K, S: SubsetExcept<K>>() -> S {
+   |                         ^^^^^^^^^^^^^^^ required by this bound in `remove_key`
+
+error: aborting due to 3 previous errors
+
+Some errors have detailed explanations: E0277, E0747.
+For more information about an error, try `rustc --explain E0277`.