diff options
| author | Samuel Tardieu <sam@rfc1149.net> | 2023-11-26 22:46:13 +0100 |
|---|---|---|
| committer | Samuel Tardieu <sam@rfc1149.net> | 2023-11-26 22:46:13 +0100 |
| commit | 0d09cb0a6b22066ccf1470b35f50886d675108d1 (patch) | |
| tree | e01e52198fc899e5dd14d6c867df2a124238066c | |
| parent | 7af811b6c43a90ed61a97ce239f5020263e39c7e (diff) | |
| download | rust-0d09cb0a6b22066ccf1470b35f50886d675108d1.tar.gz rust-0d09cb0a6b22066ccf1470b35f50886d675108d1.zip | |
`manual_try_fold`: check that `fold` is really `Iterator::fold`
| -rw-r--r-- | clippy_lints/src/methods/manual_try_fold.rs | 5 | ||||
| -rw-r--r-- | tests/ui/manual_try_fold.rs | 30 |
2 files changed, 33 insertions, 2 deletions
diff --git a/clippy_lints/src/methods/manual_try_fold.rs b/clippy_lints/src/methods/manual_try_fold.rs index 51145afda7f..f93edded729 100644 --- a/clippy_lints/src/methods/manual_try_fold.rs +++ b/clippy_lints/src/methods/manual_try_fold.rs @@ -1,14 +1,14 @@ use clippy_config::msrvs::{self, Msrv}; use clippy_utils::diagnostics::span_lint_and_sugg; -use clippy_utils::is_from_proc_macro; use clippy_utils::source::snippet_opt; use clippy_utils::ty::implements_trait; +use clippy_utils::{is_from_proc_macro, is_trait_method}; use rustc_errors::Applicability; use rustc_hir::def::{DefKind, Res}; use rustc_hir::{Expr, ExprKind}; use rustc_lint::{LateContext, LintContext}; use rustc_middle::lint::in_external_macro; -use rustc_span::Span; +use rustc_span::{sym, Span}; use super::MANUAL_TRY_FOLD; @@ -22,6 +22,7 @@ pub(super) fn check<'tcx>( ) { if !in_external_macro(cx.sess(), fold_span) && msrv.meets(msrvs::ITERATOR_TRY_FOLD) + && is_trait_method(cx, expr, sym::Iterator) && let init_ty = cx.typeck_results().expr_ty(init) && let Some(try_trait) = cx.tcx.lang_items().try_trait() && implements_trait(cx, init_ty, try_trait, &[]) diff --git a/tests/ui/manual_try_fold.rs b/tests/ui/manual_try_fold.rs index bddf03ac3f1..7299d7cf986 100644 --- a/tests/ui/manual_try_fold.rs +++ b/tests/ui/manual_try_fold.rs @@ -96,3 +96,33 @@ fn msrv_juust_right() { .fold(Some(0i32), |sum, i| sum?.checked_add(*i)) .unwrap(); } + +mod issue11876 { + struct Foo; + + impl Bar for Foo { + type Output = u32; + } + + trait Bar: Sized { + type Output; + fn fold<A, F>(self, init: A, func: F) -> Fold<Self, A, F> + where + A: Clone, + F: Fn(A, Self::Output) -> A, + { + Fold { this: self, init, func } + } + } + + #[allow(dead_code)] + struct Fold<S, A, F> { + this: S, + init: A, + func: F, + } + + fn main() { + Foo.fold(Some(0), |acc, entry| Some(acc? + entry)); + } +} |
