Skip to content

Misleading message for [E0392] with associated types of trait bound #67361

Open
@sharnoff

Description

@sharnoff

E0392 notifies the user that a type parameter is not being used, but it sometimes falsely identifies parameters as being unused only when there is already another that is actually unused. I don't entirely understand expected behavior here, see the bottom for clarification.

For example, the following code (on 1.39.0 stable, 1.40.0-beta6, and 1.41.0-nightly) correctly fails to compile

trait MyTrait<A> {
    type Foo;
}

struct MyStructFails<A, B, M>
where
    M: MyTrait<A, Foo = B>,
{
    my_trait: M,
}

but it has the following error message

error[E0392]: parameter `A` is never used
 --> src/lib.rs:7:22
  |
7 | struct MyStructFails<A, B, M>
  |                      ^ unused parameter
  |
  = help: consider removing `A` or using a marker such as `std::marker::PhantomData`

error[E0392]: parameter `B` is never used
 --> src/lib.rs:7:25
  |
7 | struct MyStructFails<A, B, M>
  |                         ^ unused parameter
  |
  = help: consider removing `B` or using a marker such as `std::marker::PhantomData`

which notably includes B as an unused parameter. Clearly this isn't the case, because changing MyStruct to only add PhantomData<A> allows it to compile:

struct MyStructWorks<A, B, M>
where
    M: MyTrait<A, Foo = B>,
{
    my_trait: M,
    _marker: std::marker::PhantomData<A>,
}

and only adding PhantomData<B> does not get rid of the error. Tuple structs produce the same error.

Also notable is that this false identification only occurs for the associated type of the trait bound that A is being used in; this example produces the correct error:

playground

trait Bar {
    type Foo;
}

trait MyTrait<T> {}

struct MyStruct<F, B, T, M>
where
    B: Bar<Foo = F>,
    M: MyTrait<T>,
{
    bar: B,
    my_trait: M,
}

Clarification

I'm not very familiar with what the expected behavior should be. If the following code should indeed give an error, it's just a diagnostics bug.

trait MyTrait<T> {}

struct MyStructFails<T, M: MyTrait<T>> {
    inner: M,
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-diagnosticsArea: Messages for errors, warnings, and lintsA-varianceArea: Variance (https://doc.rust-lang.org/nomicon/subtyping.html)C-bugCategory: This is a bug.T-compilerRelevant to the compiler team, which will review and decide on the PR/issue.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions