Skip to content

Commit 5e4d8b4

Browse files
committed
Improve doc for can_move_expr_to_closure_no_visit
1 parent 9500974 commit 5e4d8b4

File tree

1 file changed

+29
-4
lines changed

1 file changed

+29
-4
lines changed

clippy_utils/src/lib.rs

Lines changed: 29 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -631,20 +631,45 @@ pub fn can_mut_borrow_both(cx: &LateContext<'_>, e1: &Expr<'_>, e2: &Expr<'_>) -
631631

632632
/// Checks if the top level expression can be moved into a closure as is.
633633
/// Currently checks for:
634-
/// * Break/Continue outside the given jump targets
634+
/// * Break/Continue outside the given loop HIR ids.
635635
/// * Yield/Return statments.
636-
/// * Inline assembly
636+
/// * Inline assembly.
637637
/// * Usages of a field of a local where the type of the local can be partially moved.
638+
///
639+
/// For example, given the following function:
640+
///
641+
/// ```
642+
/// fn f<'a>(iter: &mut impl Iterator<Item = (usize, &'a mut String)>) {
643+
/// for item in iter {
644+
/// let s = item.1;
645+
/// if item.0 > 10 {
646+
/// continue;
647+
/// } else {
648+
/// s.clear();
649+
/// }
650+
/// }
651+
/// }
652+
/// ```
653+
///
654+
/// When called on the expression `item.0` this will return false unless the local `item` is in the
655+
/// `ignore_locals` set. The type `(usize, &mut String)` can have the second element moved, so it
656+
/// isn't always safe to move into a closure when only a single field is needed.
657+
///
658+
/// When called on the `continue` expression this will return false unless the outer loop expression
659+
/// is in the `loop_ids` set.
660+
///
661+
/// Note that this check is not recursive, so passing the `if` expression will always return true
662+
/// even though sub-expressions might return false.
638663
pub fn can_move_expr_to_closure_no_visit(
639664
cx: &LateContext<'tcx>,
640665
expr: &'tcx Expr<'_>,
641-
jump_targets: &[HirId],
666+
loop_ids: &[HirId],
642667
ignore_locals: &HirIdSet,
643668
) -> bool {
644669
match expr.kind {
645670
ExprKind::Break(Destination { target_id: Ok(id), .. }, _)
646671
| ExprKind::Continue(Destination { target_id: Ok(id), .. })
647-
if jump_targets.contains(&id) =>
672+
if loop_ids.contains(&id) =>
648673
{
649674
true
650675
},

0 commit comments

Comments
 (0)