Auto merge of #7657 - dswij:needless-borrow-mut, r=llogiq

`needless_borrow` checks for mutable borrow

closes #7635

changelog: [`needless_borrow`] now checks for needless mutable borrow
This commit is contained in:
bors 2021-09-17 22:25:07 +00:00
commit 59cd77710d
4 changed files with 51 additions and 23 deletions

View file

@ -104,7 +104,7 @@ impl<'tcx> LateLintPass<'tcx> for NeedlessBorrow {
if e.span.from_expansion() { if e.span.from_expansion() {
return; return;
} }
if let ExprKind::AddrOf(BorrowKind::Ref, Mutability::Not, inner) = e.kind { if let ExprKind::AddrOf(BorrowKind::Ref, mutability, inner) = e.kind {
if let ty::Ref(_, ty, _) = cx.typeck_results().expr_ty(inner).kind() { if let ty::Ref(_, ty, _) = cx.typeck_results().expr_ty(inner).kind() {
for adj3 in cx.typeck_results().expr_adjustments(e).windows(3) { for adj3 in cx.typeck_results().expr_adjustments(e).windows(3) {
if let [Adjustment { if let [Adjustment {
@ -116,14 +116,20 @@ impl<'tcx> LateLintPass<'tcx> for NeedlessBorrow {
.. ..
}] = *adj3 }] = *adj3
{ {
let help_msg_ty = if matches!(mutability, Mutability::Not) {
format!("&{}", ty)
} else {
format!("&mut {}", ty)
};
span_lint_and_then( span_lint_and_then(
cx, cx,
NEEDLESS_BORROW, NEEDLESS_BORROW,
e.span, e.span,
&format!( &format!(
"this expression borrows a reference (`&{}`) that is immediately dereferenced \ "this expression borrows a reference (`{}`) that is immediately dereferenced \
by the compiler", by the compiler",
ty help_msg_ty
), ),
|diag| { |diag| {
if let Some(snippet) = snippet_opt(cx, inner.span) { if let Some(snippet) = snippet_opt(cx, inner.span) {

View file

@ -1,17 +1,16 @@
// run-rustfix // run-rustfix
#![allow(clippy::needless_borrowed_reference)]
fn x(y: &i32) -> i32 {
*y
}
#[warn(clippy::all, clippy::needless_borrow)] #[warn(clippy::all, clippy::needless_borrow)]
#[allow(unused_variables)] #[allow(unused_variables)]
fn main() { fn main() {
let a = 5; let a = 5;
let b = x(&a); let _ = x(&a); // no warning
let c = x(&a); let _ = x(&a); // warn
let mut b = 5;
mut_ref(&mut b); // no warning
mut_ref(&mut b); // warn
let s = &String::from("hi"); let s = &String::from("hi");
let s_ident = f(&s); // should not error, because `&String` implements Copy, but `String` does not let s_ident = f(&s); // should not error, because `&String` implements Copy, but `String` does not
let g_val = g(&Vec::new()); // should not error, because `&Vec<T>` derefs to `&[T]` let g_val = g(&Vec::new()); // should not error, because `&Vec<T>` derefs to `&[T]`
@ -29,6 +28,15 @@ fn main() {
}; };
} }
#[allow(clippy::needless_borrowed_reference)]
fn x(y: &i32) -> i32 {
*y
}
fn mut_ref(y: &mut i32) {
*y = 5;
}
fn f<T: Copy>(y: &T) -> T { fn f<T: Copy>(y: &T) -> T {
*y *y
} }

View file

@ -1,17 +1,16 @@
// run-rustfix // run-rustfix
#![allow(clippy::needless_borrowed_reference)]
fn x(y: &i32) -> i32 {
*y
}
#[warn(clippy::all, clippy::needless_borrow)] #[warn(clippy::all, clippy::needless_borrow)]
#[allow(unused_variables)] #[allow(unused_variables)]
fn main() { fn main() {
let a = 5; let a = 5;
let b = x(&a); let _ = x(&a); // no warning
let c = x(&&a); let _ = x(&&a); // warn
let mut b = 5;
mut_ref(&mut b); // no warning
mut_ref(&mut &mut b); // warn
let s = &String::from("hi"); let s = &String::from("hi");
let s_ident = f(&s); // should not error, because `&String` implements Copy, but `String` does not let s_ident = f(&s); // should not error, because `&String` implements Copy, but `String` does not
let g_val = g(&Vec::new()); // should not error, because `&Vec<T>` derefs to `&[T]` let g_val = g(&Vec::new()); // should not error, because `&Vec<T>` derefs to `&[T]`
@ -29,6 +28,15 @@ fn main() {
}; };
} }
#[allow(clippy::needless_borrowed_reference)]
fn x(y: &i32) -> i32 {
*y
}
fn mut_ref(y: &mut i32) {
*y = 5;
}
fn f<T: Copy>(y: &T) -> T { fn f<T: Copy>(y: &T) -> T {
*y *y
} }

View file

@ -1,16 +1,22 @@
error: this expression borrows a reference (`&i32`) that is immediately dereferenced by the compiler error: this expression borrows a reference (`&i32`) that is immediately dereferenced by the compiler
--> $DIR/needless_borrow.rs:14:15 --> $DIR/needless_borrow.rs:8:15
| |
LL | let c = x(&&a); LL | let _ = x(&&a); // warn
| ^^^ help: change this to: `&a` | ^^^ help: change this to: `&a`
| |
= note: `-D clippy::needless-borrow` implied by `-D warnings` = note: `-D clippy::needless-borrow` implied by `-D warnings`
error: this expression borrows a reference (`&mut i32`) that is immediately dereferenced by the compiler
--> $DIR/needless_borrow.rs:12:13
|
LL | mut_ref(&mut &mut b); // warn
| ^^^^^^^^^^^ help: change this to: `&mut b`
error: this expression borrows a reference (`&i32`) that is immediately dereferenced by the compiler error: this expression borrows a reference (`&i32`) that is immediately dereferenced by the compiler
--> $DIR/needless_borrow.rs:27:15 --> $DIR/needless_borrow.rs:26:15
| |
LL | 46 => &&a, LL | 46 => &&a,
| ^^^ help: change this to: `&a` | ^^^ help: change this to: `&a`
error: aborting due to 2 previous errors error: aborting due to 3 previous errors