From 84f8caca9c975bca4b46172b0bad5e5fef81bb61 Mon Sep 17 00:00:00 2001 From: Jason Newcomb Date: Thu, 15 Apr 2021 12:20:43 -0400 Subject: [PATCH] Don't lint `multiple_inherent_impl` with generic arguments --- clippy_lints/src/inherent_impl.rs | 27 +++++++++++++++++++++------ tests/ui/impl.rs | 17 +++++++++++++++++ 2 files changed, 38 insertions(+), 6 deletions(-) diff --git a/clippy_lints/src/inherent_impl.rs b/clippy_lints/src/inherent_impl.rs index c31013e49be5..f3095849b0d5 100644 --- a/clippy_lints/src/inherent_impl.rs +++ b/clippy_lints/src/inherent_impl.rs @@ -3,7 +3,7 @@ use clippy_utils::diagnostics::span_lint_and_then; use clippy_utils::in_macro; use rustc_hir::def_id::DefIdMap; -use rustc_hir::{def_id, Crate, Impl, Item, ItemKind}; +use rustc_hir::{def_id, Crate, Impl, Item, ItemKind, QPath, TyKind}; use rustc_lint::{LateContext, LateLintPass}; use rustc_session::{declare_tool_lint, impl_lint_pass}; use rustc_span::Span; @@ -53,15 +53,30 @@ impl<'tcx> LateLintPass<'tcx> for MultipleInherentImpl { if let ItemKind::Impl(Impl { ref generics, of_trait: None, + self_ty, .. }) = item.kind { - // Remember for each inherent implementation encountered its span and generics - // but filter out implementations that have generic params (type or lifetime) - // or are derived from a macro - if !in_macro(item.span) && generics.params.is_empty() { - self.impls.insert(item.def_id.to_def_id(), item.span); + // Don't count impls from macros, or with generic parameters. + if in_macro(item.span) || !generics.params.is_empty() { + return; } + match self_ty.kind { + TyKind::OpaqueDef(_, []) => (), + TyKind::Path(QPath::Resolved(None, path)) if path.segments.iter().all(|s| s.args.is_none()) => (), + TyKind::TraitObject(traits, ..) + if traits.iter().all(|t| { + t.bound_generic_params.is_empty() && t.trait_ref.path.segments.iter().all(|s| s.args.is_none()) + }) => + { + () + }, + // Don't count impls with generic arguments. + _ => return, + } + + // Remember the span of each inherent implementation encountered + self.impls.insert(item.def_id.to_def_id(), item.span); } } diff --git a/tests/ui/impl.rs b/tests/ui/impl.rs index 1c46e3a53378..d721031ee640 100644 --- a/tests/ui/impl.rs +++ b/tests/ui/impl.rs @@ -33,4 +33,21 @@ impl fmt::Debug for MyStruct { } } +// issue #5772 +struct WithArgs(T); +impl WithArgs { + fn f1() {} +} +impl WithArgs { + fn f2() {} +} + +trait TraitWithArgs {} +impl dyn TraitWithArgs { + fn f1(&self) {} +} +impl dyn TraitWithArgs { + fn f2(&self) {} +} + fn main() {}