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

#[derive(Clone)] fails for HRTB function type taking an associated type #122622

Closed
theemathas opened this issue Mar 17, 2024 · 1 comment · Fixed by #125987
Closed

#[derive(Clone)] fails for HRTB function type taking an associated type #122622

theemathas opened this issue Mar 17, 2024 · 1 comment · Fixed by #125987
Labels
A-attributes Area: Attributes (`#[…]`, `#![…]`) A-lifetimes Area: Lifetimes / regions C-bug Category: This is a bug. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Comments

@theemathas
Copy link
Contributor

The following code does not compile, even though it probably should:

trait SomeTrait {
    type SomeType<'a>;
}

#[derive(Clone)]
struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}

(playground link)

The error message on rust 1.76.0 stable is:

   Compiling playground v0.0.1 (/playground)
error[E0261]: use of undeclared lifetime name `'a`
 --> src/lib.rs:7:31
  |
7 |     x: for<'a> fn(T::SomeType<'a>)
  |                               ^^ undeclared lifetime
  |
  = note: for more information on higher-ranked polymorphism, visit https://doc.rust-lang.org/nomicon/hrtb.html
help: consider making the bound lifetime-generic with a new `'a` lifetime
  |
5 | #[derive(for<'a> Clone)]
  |          +++++++
help: consider introducing lifetime `'a` here
  |
6 | struct Foo<'a, T: SomeTrait> {
  |            +++

For more information about this error, try `rustc --explain E0261`.
error: could not compile `playground` (lib) due to 1 previous error

(The note being incorrect is a separate bug, already filed as #107694.)

The error message on rust 1.78.0-nightly (2024-03-16 766bdce744d531267d53) is:

   Compiling playground v0.0.1 (/playground)
error[E0261]: use of undeclared lifetime name `'a`
 --> src/lib.rs:7:31
  |
6 | struct Foo<T: SomeTrait> {
  |            - help: consider introducing lifetime `'a` here: `'a,`
7 |     x: for<'a> fn(T::SomeType<'a>)
  |                               ^^ undeclared lifetime
  |
  = note: for more information on higher-ranked polymorphism, visit https://doc.rust-lang.org/nomicon/hrtb.html

For more information about this error, try `rustc --explain E0261`.
error: could not compile `playground` (lib) due to 1 previous error

Note that manually implementing a Clone compiles fine without any errors:

trait SomeTrait {
    type SomeType<'a>;
}

struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}

impl<T: SomeTrait> Clone for Foo<T> {
    fn clone(&self) -> Self {
        Self {
            x: self.x
        }
    }
}

(playground link)

@theemathas theemathas added the C-bug Category: This is a bug. label Mar 17, 2024
@rustbot rustbot added the needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. label Mar 17, 2024
@theemathas
Copy link
Contributor Author

For reference, the non-compiling code expands to the following, which has an incorrect where clause

#![feature(prelude_import)]
#[prelude_import]
use std::prelude::rust_2021::*;
#[macro_use]
extern crate std;
trait SomeTrait {
    type SomeType<'a>;
}

struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>),
}
#[automatically_derived]
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}

@fmease fmease added A-attributes Area: Attributes (`#[…]`, `#![…]`) T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. A-lifetimes Area: Lifetimes / regions and removed needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. labels Mar 17, 2024
estebank added a commit to estebank/rust that referenced this issue Jun 4, 2024
When given

```rust
trait SomeTrait {
    type SomeType<'a>;
}

#[derive(Clone)]
struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}
```

expand to

```rust
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where for<'a> T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

instead of the previous invalid

```
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

Fix rust-lang#122622.
matthiaskrgr added a commit to matthiaskrgr/rust that referenced this issue Jun 5, 2024
When `derive`ing, account for HRTB on `BareFn` fields

When given

```rust
trait SomeTrait {
    type SomeType<'a>;
}

#[derive(Clone)]
struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}
```

expand to

```rust
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where for<'a> T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

instead of the previous invalid

```
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

Fix rust-lang#122622.

<!--
If this PR is related to an unstable feature or an otherwise tracked effort,
please link to the relevant tracking issue here. If you don't know of a related
tracking issue or there are none, feel free to ignore this.

This PR will get automatically assigned to a reviewer. In case you would like
a specific user to review your work, you can assign it to them by using

    r​? <reviewer name>
-->
matthiaskrgr added a commit to matthiaskrgr/rust that referenced this issue Jun 6, 2024
When `derive`ing, account for HRTB on `BareFn` fields

When given

```rust
trait SomeTrait {
    type SomeType<'a>;
}

#[derive(Clone)]
struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}
```

expand to

```rust
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where for<'a> T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

instead of the previous invalid

```
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

Fix rust-lang#122622.

<!--
If this PR is related to an unstable feature or an otherwise tracked effort,
please link to the relevant tracking issue here. If you don't know of a related
tracking issue or there are none, feel free to ignore this.

This PR will get automatically assigned to a reviewer. In case you would like
a specific user to review your work, you can assign it to them by using

    r​? <reviewer name>
-->
@bors bors closed this as completed in e7ad2da Jun 6, 2024
rust-timer added a commit to rust-lang-ci/rust that referenced this issue Jun 6, 2024
Rollup merge of rust-lang#125987 - estebank:issue-122622, r=Nadrieril

When `derive`ing, account for HRTB on `BareFn` fields

When given

```rust
trait SomeTrait {
    type SomeType<'a>;
}

#[derive(Clone)]
struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}
```

expand to

```rust
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where for<'a> T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

instead of the previous invalid

```
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

Fix rust-lang#122622.

<!--
If this PR is related to an unstable feature or an otherwise tracked effort,
please link to the relevant tracking issue here. If you don't know of a related
tracking issue or there are none, feel free to ignore this.

This PR will get automatically assigned to a reviewer. In case you would like
a specific user to review your work, you can assign it to them by using

    r​? <reviewer name>
-->
lcnr pushed a commit to lcnr/rust that referenced this issue Jun 12, 2024
When given

```rust
trait SomeTrait {
    type SomeType<'a>;
}

struct Foo<T: SomeTrait> {
    x: for<'a> fn(T::SomeType<'a>)
}
```

expand to

```rust
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where for<'a> T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

instead of the previous invalid

```
impl<T: ::core::clone::Clone + SomeTrait> ::core::clone::Clone for Foo<T>
    where T::SomeType<'a>: ::core::clone::Clone {
    #[inline]
    fn clone(&self) -> Foo<T> {
        Foo { x: ::core::clone::Clone::clone(&self.x) }
    }
}
```

Fix rust-lang#122622.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-attributes Area: Attributes (`#[…]`, `#![…]`) A-lifetimes Area: Lifetimes / regions C-bug Category: This is a bug. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

3 participants