Skip to content

Commit

Permalink
apply return_and_then lint to src
Browse files Browse the repository at this point in the history
  • Loading branch information
aaron-ang committed Jan 23, 2025
1 parent 718e6eb commit a2bcb11
Show file tree
Hide file tree
Showing 21 changed files with 186 additions and 192 deletions.
51 changes: 24 additions & 27 deletions clippy_lints/src/booleans.rs
Original file line number Diff line number Diff line change
Expand Up @@ -403,29 +403,28 @@ fn simplify_not(cx: &LateContext<'_>, curr_msrv: &Msrv, expr: &Expr<'_>) -> Opti
return None;
}

match binop.node {
let op = match binop.node {
BinOpKind::Eq => Some(" != "),
BinOpKind::Ne => Some(" == "),
BinOpKind::Lt => Some(" >= "),
BinOpKind::Gt => Some(" <= "),
BinOpKind::Le => Some(" > "),
BinOpKind::Ge => Some(" < "),
_ => None,
}
.and_then(|op| {
let lhs_snippet = lhs.span.get_source_text(cx)?;
let rhs_snippet = rhs.span.get_source_text(cx)?;

if !(lhs_snippet.starts_with('(') && lhs_snippet.ends_with(')')) {
if let (ExprKind::Cast(..), BinOpKind::Ge) = (&lhs.kind, binop.node) {
// e.g. `(a as u64) < b`. Without the parens the `<` is
// interpreted as a start of generic arguments for `u64`
return Some(format!("({lhs_snippet}){op}{rhs_snippet}"));
}
}?;

let lhs_snippet = lhs.span.get_source_text(cx)?;
let rhs_snippet = rhs.span.get_source_text(cx)?;

if !(lhs_snippet.starts_with('(') && lhs_snippet.ends_with(')')) {
if let (ExprKind::Cast(..), BinOpKind::Ge) = (&lhs.kind, binop.node) {
// e.g. `(a as u64) < b`. Without the parens the `<` is
// interpreted as a start of generic arguments for `u64`
return Some(format!("({lhs_snippet}){op}{rhs_snippet}"));
}
}

Some(format!("{lhs_snippet}{op}{rhs_snippet}"))
})
Some(format!("{lhs_snippet}{op}{rhs_snippet}"))
},
ExprKind::MethodCall(path, receiver, args, _) => {
let type_of_receiver = cx.typeck_results().expr_ty(receiver);
Expand All @@ -434,22 +433,20 @@ fn simplify_not(cx: &LateContext<'_>, curr_msrv: &Msrv, expr: &Expr<'_>) -> Opti
{
return None;
}
METHODS_WITH_NEGATION
let (_, _, neg_method) = METHODS_WITH_NEGATION
.iter()
.copied()
.flat_map(|(msrv, a, b)| vec![(msrv, a, b), (msrv, b, a)])
.find(|&(msrv, a, _)| msrv.is_none_or(|msrv| curr_msrv.meets(msrv)) && a == path.ident.name.as_str())
.and_then(|(_, _, neg_method)| {
let negated_args = args
.iter()
.map(|arg| simplify_not(cx, curr_msrv, arg))
.collect::<Option<Vec<_>>>()?
.join(", ");
Some(format!(
"{}.{neg_method}({negated_args})",
receiver.span.get_source_text(cx)?
))
})
.find(|&(msrv, a, _)| msrv.is_none_or(|msrv| curr_msrv.meets(msrv)) && a == path.ident.name.as_str())?;
let negated_args = args
.iter()
.map(|arg| simplify_not(cx, curr_msrv, arg))
.collect::<Option<Vec<_>>>()?
.join(", ");
Some(format!(
"{}.{neg_method}({negated_args})",
receiver.span.get_source_text(cx)?
))
},
ExprKind::Closure(closure) => {
let body = cx.tcx.hir().body(closure.body);
Expand Down
5 changes: 2 additions & 3 deletions clippy_lints/src/checked_conversions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -72,9 +72,8 @@ impl LateLintPass<'_> for CheckedConversions {
None => check_upper_bound(lt1, gt1).filter(|cv| cv.cvt == ConversionType::FromUnsigned),
Some((lt2, gt2)) => {
let upper_lower = |lt1, gt1, lt2, gt2| {
check_upper_bound(lt1, gt1)
.zip(check_lower_bound(lt2, gt2))
.and_then(|(l, r)| l.combine(r, cx))
let (l, r) = check_upper_bound(lt1, gt1).zip(check_lower_bound(lt2, gt2))?;
l.combine(r, cx)
};
upper_lower(lt1, gt1, lt2, gt2).or_else(|| upper_lower(lt2, gt2, lt1, gt1))
},
Expand Down
71 changes: 35 additions & 36 deletions clippy_lints/src/loops/manual_memcpy.rs
Original file line number Diff line number Diff line change
Expand Up @@ -55,10 +55,10 @@ pub(super) fn check<'tcx>(
let big_sugg = assignments
// The only statements in the for loops can be indexed assignments from
// indexed retrievals (except increments of loop counters).
.map(|o| {
o.and_then(|(lhs, rhs)| {
let rhs = fetch_cloned_expr(rhs);
if let ExprKind::Index(base_left, idx_left, _) = lhs.kind
.map(|assignment| {
let (lhs, rhs) = assignment?;
let rhs = fetch_cloned_expr(rhs);
if let ExprKind::Index(base_left, idx_left, _) = lhs.kind
&& let ExprKind::Index(base_right, idx_right, _) = rhs.kind
&& let Some(ty) = get_slice_like_element_ty(cx, cx.typeck_results().expr_ty(base_left))
&& get_slice_like_element_ty(cx, cx.typeck_results().expr_ty(base_right)).is_some()
Expand All @@ -68,24 +68,23 @@ pub(super) fn check<'tcx>(
&& !local_used_in(cx, canonical_id, base_right)
// Source and destination must be different
&& path_to_local(base_left) != path_to_local(base_right)
{
Some((
ty,
IndexExpr {
base: base_left,
idx: start_left,
idx_offset: offset_left,
},
IndexExpr {
base: base_right,
idx: start_right,
idx_offset: offset_right,
},
))
} else {
None
}
})
{
Some((
ty,
IndexExpr {
base: base_left,
idx: start_left,
idx_offset: offset_left,
},
IndexExpr {
base: base_right,
idx: start_right,
idx_offset: offset_right,
},
))
} else {
None
}
})
.map(|o| o.map(|(ty, dst, src)| build_manual_memcpy_suggestion(cx, start, end, limits, ty, &dst, &src)))
.collect::<Option<Vec<_>>>()
Expand Down Expand Up @@ -380,7 +379,8 @@ fn get_details_from_idx<'tcx>(
offset_opt.map(|(s, o)| (s, Offset::positive(o)))
},
BinOpKind::Sub => {
get_start(lhs, starts).and_then(|s| get_offset(cx, rhs, starts).map(|o| (s, Offset::negative(o))))
let start = get_start(lhs, starts)?;
get_offset(cx, rhs, starts).map(|o| (start, Offset::negative(o)))
},
_ => None,
},
Expand Down Expand Up @@ -442,20 +442,19 @@ fn get_loop_counters<'a, 'tcx>(

// For each candidate, check the parent block to see if
// it's initialized to zero at the start of the loop.
get_enclosing_block(cx, expr.hir_id).and_then(|block| {
increment_visitor
.into_results()
.filter_map(move |var_id| {
let mut initialize_visitor = InitializeVisitor::new(cx, expr, var_id);
walk_block(&mut initialize_visitor, block);

initialize_visitor.get_result().map(|(_, _, initializer)| Start {
id: var_id,
kind: StartKind::Counter { initializer },
})
let block = get_enclosing_block(cx, expr.hir_id)?;
increment_visitor
.into_results()
.filter_map(move |var_id| {
let mut initialize_visitor = InitializeVisitor::new(cx, expr, var_id);
walk_block(&mut initialize_visitor, block);

initialize_visitor.get_result().map(|(_, _, initializer)| Start {
id: var_id,
kind: StartKind::Counter { initializer },
})
.into()
})
})
.into()
}

fn is_array_length_equal_to_range(cx: &LateContext<'_>, start: &Expr<'_>, end: &Expr<'_>, arr: &Expr<'_>) -> bool {
Expand Down
14 changes: 6 additions & 8 deletions clippy_lints/src/minmax.rs
Original file line number Diff line number Diff line change
Expand Up @@ -65,14 +65,12 @@ fn min_max<'a, 'tcx>(cx: &LateContext<'tcx>, expr: &'a Expr<'a>) -> Option<(MinM
match expr.kind {
ExprKind::Call(path, args) => {
if let ExprKind::Path(ref qpath) = path.kind {
cx.typeck_results()
.qpath_res(qpath, path.hir_id)
.opt_def_id()
.and_then(|def_id| match cx.tcx.get_diagnostic_name(def_id) {
Some(sym::cmp_min) => fetch_const(cx, None, args, MinMax::Min),
Some(sym::cmp_max) => fetch_const(cx, None, args, MinMax::Max),
_ => None,
})
let def_id = cx.typeck_results().qpath_res(qpath, path.hir_id).opt_def_id()?;
match cx.tcx.get_diagnostic_name(def_id) {
Some(sym::cmp_min) => fetch_const(cx, None, args, MinMax::Min),
Some(sym::cmp_max) => fetch_const(cx, None, args, MinMax::Max),
_ => None,
}
} else {
None
}
Expand Down
31 changes: 16 additions & 15 deletions clippy_lints/src/needless_late_init.rs
Original file line number Diff line number Diff line change
Expand Up @@ -214,26 +214,27 @@ fn first_usage<'tcx>(
) -> Option<Usage<'tcx>> {
let significant_drop = needs_ordered_drop(cx, cx.typeck_results().node_type(binding_id));

block
let stmt = block
.stmts
.iter()
.skip_while(|stmt| stmt.hir_id != local_stmt_id)
.skip(1)
.take_while(|stmt| !significant_drop || !stmt_needs_ordered_drop(cx, stmt))
.find(|&stmt| is_local_used(cx, stmt, binding_id))
.and_then(|stmt| match stmt.kind {
StmtKind::Expr(expr) => Some(Usage {
stmt,
expr,
needs_semi: true,
}),
StmtKind::Semi(expr) => Some(Usage {
stmt,
expr,
needs_semi: false,
}),
_ => None,
})
.find(|&stmt| is_local_used(cx, stmt, binding_id))?;

match stmt.kind {
StmtKind::Expr(expr) => Some(Usage {
stmt,
expr,
needs_semi: true,
}),
StmtKind::Semi(expr) => Some(Usage {
stmt,
expr,
needs_semi: false,
}),
_ => None,
}
}

fn local_snippet_without_semicolon(cx: &LateContext<'_>, local: &LetStmt<'_>) -> Option<SourceText> {
Expand Down
15 changes: 7 additions & 8 deletions clippy_lints/src/no_effect.rs
Original file line number Diff line number Diff line change
Expand Up @@ -373,14 +373,13 @@ fn reduce_expression<'a>(cx: &LateContext<'_>, expr: &'a Expr<'a>) -> Option<Vec
},
ExprKind::Block(block, _) => {
if block.stmts.is_empty() && !block.targeted_by_break {
block.expr.as_ref().and_then(|e| {
match block.rules {
BlockCheckMode::UnsafeBlock(UnsafeSource::UserProvided) => None,
BlockCheckMode::DefaultBlock => Some(vec![&**e]),
// in case of compiler-inserted signaling blocks
BlockCheckMode::UnsafeBlock(_) => reduce_expression(cx, e),
}
})
let expr = block.expr.as_ref()?;
match block.rules {
BlockCheckMode::UnsafeBlock(UnsafeSource::UserProvided) => None,
BlockCheckMode::DefaultBlock => Some(vec![&**expr]),
// in case of compiler-inserted signaling blocks
BlockCheckMode::UnsafeBlock(_) => reduce_expression(cx, expr),
}
} else {
None
}
Expand Down
5 changes: 2 additions & 3 deletions clippy_lints/src/option_if_let_else.rs
Original file line number Diff line number Diff line change
Expand Up @@ -171,9 +171,8 @@ fn try_get_option_occurrence<'tcx>(
)) = e.kind
{
match some_captures.get(local_id).or_else(|| {
(method_sugg == "map_or_else")
.then_some(())
.and_then(|()| none_captures.get(local_id))
(method_sugg == "map_or_else").then_some(())?;
none_captures.get(local_id)
}) {
Some(CaptureKind::Value | CaptureKind::Ref(Mutability::Mut)) => return None,
Some(CaptureKind::Ref(Mutability::Not)) if as_mut => return None,
Expand Down
6 changes: 4 additions & 2 deletions clippy_lints/src/ptr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -414,6 +414,7 @@ impl<'tcx> DerefTy<'tcx> {
}
}

#[expect(clippy::too_many_lines)]
fn check_fn_args<'cx, 'tcx: 'cx>(
cx: &'cx LateContext<'tcx>,
fn_sig: ty::FnSig<'tcx>,
Expand Down Expand Up @@ -467,7 +468,8 @@ fn check_fn_args<'cx, 'tcx: 'cx>(
.output()
.walk()
.filter_map(|arg| {
arg.as_region().and_then(|lifetime| match lifetime.kind() {
let lifetime = arg.as_region()?;
match lifetime.kind() {
ty::ReEarlyParam(r) => Some(
cx.tcx
.generics_of(cx.tcx.parent(param_def_id.to_def_id()))
Expand All @@ -481,7 +483,7 @@ fn check_fn_args<'cx, 'tcx: 'cx>(
| ty::RePlaceholder(_)
| ty::ReErased
| ty::ReError(_) => None,
})
}
})
.any(|def_id| def_id.as_local().is_some_and(|def_id| def_id == param_def_id))
{
Expand Down
5 changes: 3 additions & 2 deletions clippy_lints/src/regex.rs
Original file line number Diff line number Diff line change
Expand Up @@ -222,10 +222,11 @@ fn lint_syntax_error(cx: &LateContext<'_>, error: &regex_syntax::Error, unescape
}

fn const_str<'tcx>(cx: &LateContext<'tcx>, e: &'tcx Expr<'_>) -> Option<String> {
ConstEvalCtxt::new(cx).eval(e).and_then(|c| match c {
let constant = ConstEvalCtxt::new(cx).eval(e)?;
match constant {
Constant::Str(s) => Some(s),
_ => None,
})
}
}

fn is_trivial_regex(s: &regex_syntax::hir::Hir) -> Option<&'static str> {
Expand Down
21 changes: 10 additions & 11 deletions clippy_lints/src/suspicious_operation_groupings.rs
Original file line number Diff line number Diff line change
Expand Up @@ -635,18 +635,17 @@ fn suggestion_with_swapped_ident(
new_ident: Ident,
applicability: &mut Applicability,
) -> Option<String> {
get_ident(expr, location).and_then(|current_ident| {
if eq_id(current_ident, new_ident) {
// We never want to suggest a non-change
return None;
}
let current_ident = get_ident(expr, location)?;
if eq_id(current_ident, new_ident) {
// We never want to suggest a non-change
return None;
}

Some(format!(
"{}{new_ident}{}",
snippet_with_applicability(cx, expr.span.with_hi(current_ident.span.lo()), "..", applicability),
snippet_with_applicability(cx, expr.span.with_lo(current_ident.span.hi()), "..", applicability),
))
})
Some(format!(
"{}{new_ident}{}",
snippet_with_applicability(cx, expr.span.with_hi(current_ident.span.lo()), "..", applicability),
snippet_with_applicability(cx, expr.span.with_lo(current_ident.span.hi()), "..", applicability),
))
}

fn skip_index<A, Iter>(iter: Iter, index: usize) -> impl Iterator<Item = A>
Expand Down
3 changes: 2 additions & 1 deletion clippy_utils/src/consts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -720,7 +720,8 @@ impl<'tcx> ConstEvalCtxt<'tcx> {
if b {
self.expr(then)
} else {
otherwise.as_ref().and_then(|expr| self.expr(expr))
let expr = otherwise.as_ref()?;
self.expr(expr)
}
} else {
None
Expand Down
Loading

0 comments on commit a2bcb11

Please sign in to comment.