Change:
<!-- [31mICE[0m: Rustc '' 'thread 'rustc' panicked at 'expect 0 RPITITs in call to '', 'thread 'rustc' panicked at 'expect 0 RPITITs in call to '' File: --auto-reduced (treereduce-rust): original: Version information `
Command: <!-- Include a backtrace in the code block by setting in your environment. E.g. . --<details<summary<strongProgram output</strong</summary<p</p</details<!-- query stack: [collectreturnpositionimpltraitintraittys] comparing an impl and trait method signature, inferring any hidden types in the process [typeof] computing type of [checkwellformed] checking that is well-formed [checkmodtype_wf] checking that types are well-formed in top-level module [analysis] running analysis passes on this crate --
Okay, lol, here the types obviously do unify and therefore isn't effective in this situation.
More fundamentally, the thing that goes “wrong” in these kinds of situations is the fact that we call if we have which is the case because generated one because the HIR (!) type visitor inside found an opaque type in the HIR type (here ) while the lowered type (here ) no longer contains any opaque types ultimately leading to the assert triggering. In short: visit the HIR ty , see an opaque type and take note of that synthesize an assoc ty for the RPITIT (I think) because of (1) lower the ty to due to the argument kind mismatch try to collect RPITITs on the lowered type & fail to find the opaque type I don't know if this is actually useful in general :thinking: What kinds of bugs is it supposed to catch?
cc
So either we delay the detection of RPITITs and the synthesis of RPITIT assoc tys until after HIR ty lowering / AstConv (but I don't know if that's an option) or we modify the assert (either remove it outright or check the corresp. HIR ty, I don't know if that makes sense; furthermore oli is/was on a roll to remove HIR operations from this part of the code base iirc).
Yeah, this assertion was simply there to make sure we weren't incorrectly calling for methods that had no RPITITs themselves (b/c it's expensive, and it actually is a bit stronger in what it enforces in the method signatures since it uses rather than in the signature relation for lifetime reasons), but now that this code isn't being changed much, I doubt that will ever happen. Feel free to remove it, or else I can do.
We could also delay a bug on mismatch

Discussion:
} } <del> if !unnormalized_trait_sig.output().references_error() { debug_assert!( !collector.types.is_empty(), "expect >0 RPITITs in call to `collect_return_position_impl_trait_in_trait_tys`" </del> <ins> if !unnormalized_trait_sig.output().references_error() && collector.types.is_empty() { tcx.dcx().delayed_bug( "expect >0 RPITITs in call to `collect_return_position_impl_trait_in_trait_tys`", </ins> ); }

<del> struct Wrapper<'rom>(T); //~^ ERROR cannot find type `T` in this scope </del> <ins> struct Wrapper<'rom>(&'rom ()); </ins> trait Foo { fn bar() -> Wrapper<impl Sized>;

} } <ins> trait Bar { fn foo() -> Wrapper<impl Sized>; //~^ ERROR missing lifetime specifier //~| ERROR struct takes 0 generic arguments but 1 generic argument was supplied } impl Bar for () { fn foo() -> Wrapper<impl Sized> { //~^ ERROR missing lifetime specifier //~| ERROR struct takes 0 generic arguments but 1 generic argument was supplied Wrapper(&()) } } </ins> fn main() {}

error[E0106]: missing lifetime specifier <del> --> $DIR/opaque-and-lifetime-mismatch.rs:5:24 </del> <ins> --> $DIR/opaque-and-lifetime-mismatch.rs:4:24 </ins> | LL |     fn bar() -> Wrapper<impl Sized>; |                        ^ expected named lifetime parameter

LL |     fn bar() -> Wrapper<'static, impl Sized>; |                         ++++++++ <del> error[E0412]: cannot find type `T` in this scope --> $DIR/opaque-and-lifetime-mismatch.rs:1:22 </del> <ins> error[E0106]: missing lifetime specifier --> $DIR/opaque-and-lifetime-mismatch.rs:18:24 | LL |     fn foo() -> Wrapper<impl Sized>; |                        ^ expected named lifetime parameter | = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from help: consider using the `'static` lifetime, but this is uncommon unless you're returning a borrowed value from a `const` or a `static`, or if you will only have owned values | LL |     fn foo() -> Wrapper<'static, impl Sized>; |                         ++++++++ error[E0106]: missing lifetime specifier --> $DIR/opaque-and-lifetime-mismatch.rs:24:24 </ins> | <del> LL | struct Wrapper<'rom>(T); |                      ^ not found in this scope </del> <ins> LL |     fn foo() -> Wrapper<impl Sized> { |                        ^ expected named lifetime parameter </ins> | <del> help: you might be missing a type parameter </del> <ins> = help: this function's return type contains a borrowed value, but there is no value for it to be borrowed from help: consider using the `'static` lifetime, but this is uncommon unless you're returning a borrowed value from a `const` or a `static`, or if you will only have owned values </ins> | <del> LL | struct Wrapper<'rom, T>(T); |                    +++ </del> <ins> LL |     fn foo() -> Wrapper<'static, impl Sized> { |                         ++++++++ </ins> error[E0107]: struct takes 0 generic arguments but 1 generic argument was supplied <del> --> $DIR/opaque-and-lifetime-mismatch.rs:5:17 </del> <ins> --> $DIR/opaque-and-lifetime-mismatch.rs:4:17 </ins> | LL |     fn bar() -> Wrapper<impl Sized>; |                 ^^^^^^^ ---------- help: remove this generic argument

note: struct defined here, with 0 generic parameters --> $DIR/opaque-and-lifetime-mismatch.rs:1:8 | <del> LL | struct Wrapper<'rom>(T); </del> <ins> LL | struct Wrapper<'rom>(&'rom ()); |        ^^^^^^^ error[E0107]: struct takes 0 generic arguments but 1 generic argument was supplied --> $DIR/opaque-and-lifetime-mismatch.rs:18:17 | LL |     fn foo() -> Wrapper<impl Sized>; |                 ^^^^^^^ ---------- help: remove this generic argument |                 | |                 expected 0 generic arguments | note: struct defined here, with 0 generic parameters --> $DIR/opaque-and-lifetime-mismatch.rs:1:8 | LL | struct Wrapper<'rom>(&'rom ()); </ins> |        ^^^^^^^ error[E0053]: method `bar` has an incompatible return type for trait <del> --> $DIR/opaque-and-lifetime-mismatch.rs:11:17 </del> <ins> --> $DIR/opaque-and-lifetime-mismatch.rs:10:17 </ins> | LL |     fn bar() -> i32 { |                 ^^^

|                 return type in trait error[E0053]: method `bar` has an incompatible type for trait <del> --> $DIR/opaque-and-lifetime-mismatch.rs:11:17 </del> <ins> --> $DIR/opaque-and-lifetime-mismatch.rs:10:17 </ins> | LL |     fn bar() -> i32 { |                 ^^^

|                 help: change the output type to match the trait: `Wrapper<'static>` | note: type in trait <del> --> $DIR/opaque-and-lifetime-mismatch.rs:5:17 </del> <ins> --> $DIR/opaque-and-lifetime-mismatch.rs:4:17 </ins> | LL |     fn bar() -> Wrapper<impl Sized>; |                 ^^^^^^^^^^^^^^^^^^^ = note: expected signature `fn() -> Wrapper<'static>` found signature `fn() -> i32` <del> error: aborting due to 5 previous errors </del> <ins> error[E0107]: struct takes 0 generic arguments but 1 generic argument was supplied --> $DIR/opaque-and-lifetime-mismatch.rs:24:17 | LL |     fn foo() -> Wrapper<impl Sized> { |                 ^^^^^^^ ---------- help: remove this generic argument |                 | |                 expected 0 generic arguments | note: struct defined here, with 0 generic parameters --> $DIR/opaque-and-lifetime-mismatch.rs:1:8 | LL | struct Wrapper<'rom>(&'rom ()); |        ^^^^^^^ error: aborting due to 8 previous errors </ins> <del> Some errors have detailed explanations: E0053, E0106, E0107, E0412. </del> <ins> Some errors have detailed explanations: E0053, E0106, E0107. </ins> For more information about an error, try `rustc --explain E0053`.