rust-lang / rust

Empowering everyone to build reliable and efficient software.
https://www.rust-lang.org
Other
97.72k stars 12.64k forks source link

implied bounds from impl header are not used when comparing trait and impl methods #105495

Open aliemjay opened 1 year ago

aliemjay commented 1 year ago

This doesn't compile:

trait Trait {
    fn get();
}
impl<'a, 'b> Trait for &'a &'b () { // There is an implied bound 'b: 'a
    fn get() where 'b: 'a, {}
    //~^ ERROR impl has stricter requirements than trait
}

Although it should for the same reason it compiles with the following change:

- impl<'a, 'b> Trait for &'a &'b () {
+ impl<'a, 'b> Trait for &'a &'b () where 'b: 'a, {

There should be no difference in behavior between implied and explicit bounds on impl header.

This is because we're not adding sufficient implied bounds in compare_predicate_entailment() here: https://github.com/rust-lang/rust/blob/14ca83a04b00433a8caf3b805d5ea08cb2691e1b/compiler/rustc_hir_analysis/src/check/compare_method.rs#L252

@rustbot label T-types A-implied-bounds A-associated-items C-bug

aliemjay commented 1 year ago

This should be fixed for associated types as well:

trait Trait {
    type Ty;
}
impl<'a, 'b> Trait for &'a &'b () {
    type Ty = () where 'b: 'a;
}
aliemjay commented 1 year ago

another test case:

trait Trait {
    type Assoc;
    fn test(_: ());
}

impl<'a, T> Trait for &'a T {
    type Assoc = ();
    fn test(_: Self::Assoc) {}
}