Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Possible regression with type_alias_impl_trait #97651

Closed
FrozenDroid opened this issue Jun 2, 2022 · 8 comments
Closed

Possible regression with type_alias_impl_trait #97651

FrozenDroid opened this issue Jun 2, 2022 · 8 comments
Labels
C-bug Category: This is a bug. F-type_alias_impl_trait `#[feature(type_alias_impl_trait)]` regression-untriaged Untriaged performance or correctness regression. requires-nightly This issue requires a nightly compiler in some way. T-types Relevant to the types team, which will review and decide on the PR/issue.

Comments

@FrozenDroid
Copy link

Code

I tried this code:

#![feature(type_alias_impl_trait)]

trait Printy: core::fmt::Debug {
    fn test(self: &mut Self) {
        println!("{:?}", self);
    }
}

pub trait Foo {
    type Ty: Printy;
    fn bar(self) -> Self::Ty;
}

#[derive(Debug)]
struct Quix<'a>(&'a u8);

impl Printy for &mut Quix<'_> {}

impl Foo for &mut Quix<'_> {
    type Ty = impl Printy;

    fn bar(self) -> Self::Ty {
        self
    }
}

fn main() {
    let mut q = Quix(&1);
    (&mut q).test();
}

I expected to see this happen: Successful compile

Instead, this happened:

error[E0491]: in type `&mut Quix<'_>`, reference has a longer lifetime than the data it references
  --> src/main.rs:20:15
   |
20 |     type Ty = impl Printy;
   |               ^^^^^^^^^^^
   |
note: the pointer is valid for the lifetime `'_` as defined here
  --> src/main.rs:19:14
   |
19 | impl Foo for &mut Quix<'_> {
   |              ^
note: but the referenced data is only valid for the lifetime `'_` as defined here
  --> src/main.rs:19:14
   |
19 | impl Foo for &mut Quix<'_> {
   |              ^

Version it worked on

It most recently worked on: nightly-2021-10-21
It's very possible there are more recent nightlies where this compiles, but I don't know how to easily find this.

Version with regression

rustc --version --verbose:

rustc 1.62.0-nightly (de1026a67 2022-04-23)
binary: rustc
commit-hash: de1026a67b0a3f5d6b61a1f77093af97d4799376
commit-date: 2022-04-23
host: aarch64-apple-darwin
release: 1.62.0-nightly
LLVM version: 14.0.1

Additional observations

Works with:

#![feature(type_alias_impl_trait)]

trait Printy: core::fmt::Debug {
    fn test(self: &mut Self) {
        println!("{:?}", self);
    }
}

pub trait Foo {
    type Ty: Printy;
    fn bar(self) -> Self::Ty;
}

#[derive(Debug)]
struct Quix<'a>(&'a u8);

impl Printy for &mut Quix<'_> {}

impl<'a> Foo for &'a mut Quix<'a> {
    type Ty = impl Printy;

    fn bar(self) -> Self::Ty {
        self
    }
}

fn main() {
    let mut q = Quix(&1);
    (&mut q).test();
}

but also if the implementations are on an immutable reference to Quix

@FrozenDroid FrozenDroid added C-bug Category: This is a bug. regression-untriaged Untriaged performance or correctness regression. labels Jun 2, 2022
@rustbot rustbot added requires-nightly This issue requires a nightly compiler in some way. I-prioritize Issue: Indicates that prioritization has been requested for this issue. labels Jun 2, 2022
@inquisitivecrystal inquisitivecrystal added the T-types Relevant to the types team, which will review and decide on the PR/issue. label Jun 2, 2022
@FrozenDroid
Copy link
Author

I don't have any experience with rustc development but PR #95474 seems relevant?

@inquisitivecrystal
Copy link
Contributor

inquisitivecrystal commented Jun 2, 2022

Regresses in #95519 (though it's a nightly feature, so not really a regression). CC @oli-obk: I'm guessing this was intentional, but it's worth checking, especially as I can't make sense of that error.

@FrozenDroid
Copy link
Author

@rustbot label: +F-type_alias_impl_trait

@rustbot rustbot added the F-type_alias_impl_trait `#[feature(type_alias_impl_trait)]` label Jun 2, 2022
@inquisitivecrystal
Copy link
Contributor

@rustbot label: +F-type_alias_impl_trait

signs on to apply a label they missed
finds the issue reporter has already applied the label
😄

While I'm thanking you for being helpful, it was nice to have the date of the nightly where this worked. It makes bisecting (running the script that figures out when the change was introduced) a lot faster.

@101arrowz
Copy link

This seems potentially related to #97515 as well.

@inquisitivecrystal
Copy link
Contributor

@101arrowz: I think that's not super likely. #95519, which introduced this, was specifically related to validation for type-alias impl traits. My impression is that it shouldn't have affected GATs.

@aliemjay
Copy link
Member

aliemjay commented Jun 3, 2022

This is #95922.

The problem is that type-alias-impl-trait doesn't make use of implied bounds from the impl header. As a workaround for now, you can specify explicit bounds instead:

impl<'a, 'b> Foo for &'b mut Quix<'a>
where
   'a: 'b, 
{
    type Ty = impl Printy;

    fn bar(self) -> Self::Ty {
        self
    }
}

Unrelated to this issue, but you should expect this impl to break once #96996 is fixed. The correct way would then be:

impl<'a, 'b> Foo for &'b mut Quix<'a> {
    type Ty = impl Printy + Captures<'a> + Captures<'b>;

    fn bar(self) -> Self::Ty {
        self
    }
}

Captures trait is arguably an ugly hack. We should figure out a better way to indicate an opaque type captures a lifetime.

@inquisitivecrystal
Copy link
Contributor

Thanks @aliemjay. Closing as a duplicate.

@inquisitivecrystal inquisitivecrystal removed the I-prioritize Issue: Indicates that prioritization has been requested for this issue. label Jun 4, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
C-bug Category: This is a bug. F-type_alias_impl_trait `#[feature(type_alias_impl_trait)]` regression-untriaged Untriaged performance or correctness regression. requires-nightly This issue requires a nightly compiler in some way. T-types Relevant to the types team, which will review and decide on the PR/issue.
Development

No branches or pull requests

5 participants