rust-lang/rust-clippy

False-positive extra_unused_type_parameters

vitvakatu opened this issue · 4 comments

Summary

It seems to be a joint issue with bytemuck::Zeroable.

My rust-toolchain.toml:

[toolchain]
channel = "nightly-2023-06-01"
components = ["clippy", "rustfmt"]
profile = "default"

Cargo.toml:

[package]
name = "reproduce_clippy_issue"
version = "0.1.0"
edition = "2021"

[dependencies]
bytemuck = { version = "1.13.1", features = ["derive"] }

Lint Name

extra_unused_type_parameters

Reproducer

I tried this code:

use bytemuck::Zeroable;

#[derive(Debug, Default, Zeroable)]
pub struct Slot<Item> {
    pub value: Item,
    pub version: (),
}

I saw this happen:

❯ cargo clippy -- -D warnings
    Checking reproduce_clippy_issue v0.1.0 (/Users/ilyabogdanov/projects/reproduce_clippy_issue)
error: type parameter `Item` goes unused in function definition
 --> src/lib.rs:6:17
  |
6 | pub struct Slot<Item> {
  |                 ^^^^
  |
  = help: consider removing the parameter
  = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#extra_unused_type_parameters
  = note: `-D clippy::extra-unused-type-parameters` implied by `-D warnings`

error: could not compile `reproduce_clippy_issue` (lib) due to previous error

I expected to see this happen:

No warnings should be produced here. The Item is used by the struct definition. A more complex example of this bug can be seen here: enso-org/enso#7109 (comment)

Version

rustc 1.72.0-nightly (871b59520 2023-05-31)
binary: rustc
commit-hash: 871b5952023139738f72eba235063575062bc2e9
commit-date: 2023-05-31
host: aarch64-apple-darwin
release: 1.72.0-nightly
LLVM version: 16.0.4

Additional Labels

No response

Also, I couldn't disable the lint by using #[allow(clippy::extra_unused_type_parameters)] on a struct. Only the outer lint on the module helps.

Lokathor/bytemuck#180 seems to be related.

Part of the code generated from #[derive(Zeroable)] looks like

#[allow(clippy :: missing_const_for_fn)]
fn check<Item>() where Item: ::bytemuck::Zeroable {
    fn assert_impl<T: ::bytemuck::Zeroable>() {}
    assert_impl::<()>();
}

Item is entirely unused by the function (note that it says "function declaration", not struct!). This could probably be easily prevented by checking if it's from a procedural macro.

I can take this :)
@rustbot claim