]> git.lizzy.rs Git - rust.git/commitdiff
Elaborate unmet obligations in E0599 for more context
authorEsteban Küber <esteban@kuber.com.ar>
Thu, 12 Jan 2023 19:53:01 +0000 (19:53 +0000)
committerEsteban Küber <esteban@kuber.com.ar>
Fri, 13 Jan 2023 18:20:23 +0000 (18:20 +0000)
compiler/rustc_hir_typeck/src/method/probe.rs
tests/ui/derives/issue-91550.stderr
tests/ui/missing-trait-bounds/issue-35677.fixed
tests/ui/missing-trait-bounds/issue-35677.stderr

index dd827777df94e68c03c031b98af1594b06e72793..15f6e11717768cfd11ec078f0d620cc451c20897 100644 (file)
@@ -1587,11 +1587,29 @@ fn consider_probe(
                         let o = self.resolve_vars_if_possible(o);
                         if !self.predicate_may_hold(&o) {
                             result = ProbeResult::NoMatch;
-                            possibly_unsatisfied_predicates.push((
-                                o.predicate,
-                                None,
-                                Some(o.cause),
-                            ));
+                            let parent_o = o.clone();
+                            let implied_obligations =
+                                traits::elaborate_obligations(self.tcx, vec![o]);
+                            for o in implied_obligations {
+                                let parent = if o == parent_o {
+                                    None
+                                } else {
+                                    if o.predicate.to_opt_poly_trait_pred().map(|p| p.def_id())
+                                        == self.tcx.lang_items().sized_trait()
+                                    {
+                                        // We don't care to talk about implicit `Sized` bounds.
+                                        continue;
+                                    }
+                                    Some(parent_o.predicate)
+                                };
+                                if !self.predicate_may_hold(&o) {
+                                    possibly_unsatisfied_predicates.push((
+                                        o.predicate,
+                                        parent,
+                                        Some(o.cause),
+                                    ));
+                                }
+                            }
                         }
                     }
                 }
index bf0bb3fbdf8f7f26a6a920f8f5be9cfe30b59a06..381d860a9c36dfcb560c0b15655c127536538727 100644 (file)
@@ -6,12 +6,15 @@ LL | struct Value(u32);
    | |
    | doesn't satisfy `Value: Eq`
    | doesn't satisfy `Value: Hash`
+   | doesn't satisfy `Value: PartialEq`
 ...
 LL |     hs.insert(Value(0));
    |        ^^^^^^
    |
    = note: the following trait bounds were not satisfied:
            `Value: Eq`
+           `Value: PartialEq`
+           which is required by `Value: Eq`
            `Value: Hash`
 help: consider annotating `Value` with `#[derive(Eq, Hash, PartialEq)]`
    |
@@ -22,7 +25,10 @@ error[E0599]: the method `use_eq` exists for struct `Object<NoDerives>`, but its
   --> $DIR/issue-91550.rs:26:9
    |
 LL | pub struct NoDerives;
-   | -------------------- doesn't satisfy `NoDerives: Eq`
+   | --------------------
+   | |
+   | doesn't satisfy `NoDerives: Eq`
+   | doesn't satisfy `NoDerives: PartialEq`
 LL |
 LL | struct Object<T>(T);
    | ---------------- method `use_eq` not found for this struct
@@ -30,7 +36,9 @@ LL | struct Object<T>(T);
 LL |     foo.use_eq();
    |         ^^^^^^ method cannot be called on `Object<NoDerives>` due to unsatisfied trait bounds
    |
-note: trait bound `NoDerives: Eq` was not satisfied
+note: the following trait bounds were not satisfied:
+      `NoDerives: Eq`
+      `NoDerives: PartialEq`
   --> $DIR/issue-91550.rs:15:9
    |
 LL | impl<T: Eq> Object<T> {
@@ -46,7 +54,12 @@ error[E0599]: the method `use_ord` exists for struct `Object<NoDerives>`, but it
   --> $DIR/issue-91550.rs:27:9
    |
 LL | pub struct NoDerives;
-   | -------------------- doesn't satisfy `NoDerives: Ord`
+   | --------------------
+   | |
+   | doesn't satisfy `NoDerives: Eq`
+   | doesn't satisfy `NoDerives: Ord`
+   | doesn't satisfy `NoDerives: PartialEq`
+   | doesn't satisfy `NoDerives: PartialOrd`
 LL |
 LL | struct Object<T>(T);
    | ---------------- method `use_ord` not found for this struct
@@ -54,7 +67,11 @@ LL | struct Object<T>(T);
 LL |     foo.use_ord();
    |         ^^^^^^^ method cannot be called on `Object<NoDerives>` due to unsatisfied trait bounds
    |
-note: trait bound `NoDerives: Ord` was not satisfied
+note: the following trait bounds were not satisfied:
+      `NoDerives: Eq`
+      `NoDerives: Ord`
+      `NoDerives: PartialEq`
+      `NoDerives: PartialOrd`
   --> $DIR/issue-91550.rs:18:9
    |
 LL | impl<T: Ord> Object<T> {
@@ -72,7 +89,9 @@ error[E0599]: the method `use_ord_and_partial_ord` exists for struct `Object<NoD
 LL | pub struct NoDerives;
    | --------------------
    | |
+   | doesn't satisfy `NoDerives: Eq`
    | doesn't satisfy `NoDerives: Ord`
+   | doesn't satisfy `NoDerives: PartialEq`
    | doesn't satisfy `NoDerives: PartialOrd`
 LL |
 LL | struct Object<T>(T);
@@ -82,7 +101,9 @@ LL |     foo.use_ord_and_partial_ord();
    |         ^^^^^^^^^^^^^^^^^^^^^^^ method cannot be called on `Object<NoDerives>` due to unsatisfied trait bounds
    |
 note: the following trait bounds were not satisfied:
+      `NoDerives: Eq`
       `NoDerives: Ord`
+      `NoDerives: PartialEq`
       `NoDerives: PartialOrd`
   --> $DIR/issue-91550.rs:21:9
    |
index 08174d8d8d53ad476ed5212c055012b1a15136ea..c76b6bc9c1851c770abe03b3c1f77e9875dc1555 100644 (file)
@@ -3,7 +3,7 @@
 use std::collections::HashSet;
 use std::hash::Hash;
 
-fn is_subset<T>(this: &HashSet<T>, other: &HashSet<T>) -> bool where T: Eq, T: Hash {
+fn is_subset<T>(this: &HashSet<T>, other: &HashSet<T>) -> bool where T: Eq, T: Hash, T: PartialEq {
     this.is_subset(other)
     //~^ ERROR the method
 }
index a2201b946a6f0d5352c8db71b2e1e8f9972f7b62..067b10b873abfb7aaca25504846c1d9fe07911f2 100644 (file)
@@ -6,11 +6,13 @@ LL |     this.is_subset(other)
    |
    = note: the following trait bounds were not satisfied:
            `T: Eq`
+           `T: PartialEq`
+           which is required by `T: Eq`
            `T: Hash`
 help: consider restricting the type parameters to satisfy the trait bounds
    |
-LL | fn is_subset<T>(this: &HashSet<T>, other: &HashSet<T>) -> bool where T: Eq, T: Hash {
-   |                                                                ++++++++++++++++++++
+LL | fn is_subset<T>(this: &HashSet<T>, other: &HashSet<T>) -> bool where T: Eq, T: Hash, T: PartialEq {
+   |                                                                ++++++++++++++++++++++++++++++++++
 
 error: aborting due to previous error