// Test case from Chalk. // Make sure that we make sure that we don't allow arbitrary bounds to be // proven when a bound and a where clause of an associated type are the same. #![feature(trivial_bounds)] trait Print { fn print(); } trait Foo { type Item: Sized where ::Item: Sized; } struct Number { } impl Foo for Number { // Well-formedness checks require that the following // goal is true: // ``` // if (str: Sized) { # if the where clauses hold // str: Sized # then the bound on the associated type hold // } // ``` // which it is :) type Item = str where str: Sized; } struct OnlySized where T: Sized { f: T } impl Print for OnlySized { fn print() { println!("{}", std::mem::size_of::()); } } trait Bar { type Assoc: Print; } impl Bar for T where T: Foo { // This is not ok, we need to prove `wf(::Item)`, which requires // knowing that `::Item: Sized` to satisfy the where clause. We // can use the bound on `Foo::Item` for this, but that requires // `wf(::Item)`, which is an invalid cycle. type Assoc = OnlySized<::Item>; //~^ ERROR overflow evaluating the requirement `::Item: Sized` } fn foo() { T::print() // oops, in fact `T = OnlySized` which is ill-formed } fn bar() { // we have `FromEnv(T: Bar)` hence // `::Assoc` is well-formed and // `Implemented(::Assoc: Print)` hold foo::<::Assoc>() } fn main() { bar::() }