Skip to content

Commit 13b6772

Browse files
committed
Make borrow_as_ptr flag implicit casts as well
1 parent f85331f commit 13b6772

File tree

6 files changed

+70
-4
lines changed

6 files changed

+70
-4
lines changed

clippy_lints/src/casts/borrow_as_ptr.rs

+23-2
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
1-
use clippy_utils::diagnostics::span_lint_and_sugg;
1+
use clippy_utils::diagnostics::{span_lint_and_sugg, span_lint_and_then};
22
use clippy_utils::msrvs::Msrv;
33
use clippy_utils::source::{snippet_with_applicability, snippet_with_context};
44
use clippy_utils::sugg::has_enclosing_paren;
5-
use clippy_utils::{is_expr_temporary_value, is_lint_allowed, msrvs, std_or_core};
5+
use clippy_utils::{get_parent_expr, is_expr_temporary_value, is_lint_allowed, msrvs, std_or_core};
66
use rustc_errors::Applicability;
77
use rustc_hir::{BorrowKind, Expr, ExprKind, Mutability, Ty, TyKind};
88
use rustc_lint::LateContext;
9+
use rustc_middle::ty::adjustment::{Adjust, AutoBorrow};
910
use rustc_span::BytePos;
1011

1112
use super::BORROW_AS_PTR;
@@ -59,3 +60,23 @@ pub(super) fn check<'tcx>(
5960
}
6061
false
6162
}
63+
64+
pub(super) fn check_implicit_cast(cx: &LateContext<'_>, expr: &Expr<'_>) {
65+
if !expr.span.from_expansion()
66+
&& !matches!(get_parent_expr(cx, expr).map(|e| e.kind), Some(ExprKind::Cast(..)))
67+
&& let [deref, borrow] = cx.typeck_results().expr_adjustments(expr)
68+
&& matches!(deref.kind, Adjust::Deref(..))
69+
&& cx.typeck_results().expr_ty(expr).is_ref()
70+
&& let Adjust::Borrow(AutoBorrow::RawPtr(mutability)) = borrow.kind
71+
&& let ExprKind::AddrOf(BorrowKind::Ref, _, target) = expr.kind
72+
{
73+
span_lint_and_then(cx, BORROW_AS_PTR, expr.span, "implicit borrow as raw pointer", |diag| {
74+
diag.span_suggestion_verbose(
75+
expr.span.until(target.span),
76+
"use a raw pointer instead",
77+
format!("&raw {} ", mutability.ptr_str()),
78+
Applicability::MachineApplicable,
79+
);
80+
});
81+
}
82+
}

clippy_lints/src/casts/mod.rs

+3
Original file line numberDiff line numberDiff line change
@@ -846,6 +846,9 @@ impl<'tcx> LateLintPass<'tcx> for Casts {
846846
}
847847
}
848848

849+
if self.msrv.meets(cx, msrvs::BORROW_AS_PTR) {
850+
borrow_as_ptr::check_implicit_cast(cx, expr);
851+
}
849852
cast_ptr_alignment::check(cx, expr);
850853
char_lit_as_u8::check(cx, expr);
851854
ptr_as_ptr::check(cx, expr, self.msrv);

clippy_lints/src/non_copy_const.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -449,7 +449,7 @@ impl<'tcx> LateLintPass<'tcx> for NonCopyConst<'tcx> {
449449

450450
dereferenced_expr = parent_expr;
451451
},
452-
ExprKind::Index(e, _, _) if ptr::eq(&**e, cur_expr) => {
452+
ExprKind::Index(e, _, _) if ptr::eq(&raw const **e, cur_expr) => {
453453
// `e[i]` => desugared to `*Index::index(&e, i)`,
454454
// meaning `e` must be referenced.
455455
// no need to go further up since a method call is involved now.

tests/ui/borrow_as_ptr.fixed

+10
Original file line numberDiff line numberDiff line change
@@ -29,3 +29,13 @@ fn issue_13882() {
2929
let _raw = (&raw mut x[1]).wrapping_offset(-1);
3030
//~^ borrow_as_ptr
3131
}
32+
33+
fn implicit_cast() {
34+
let val = 1;
35+
let p: *const i32 = &raw const val;
36+
//~^ borrow_as_ptr
37+
38+
let mut val = 1;
39+
let p: *mut i32 = &raw mut val;
40+
//~^ borrow_as_ptr
41+
}

tests/ui/borrow_as_ptr.rs

+10
Original file line numberDiff line numberDiff line change
@@ -29,3 +29,13 @@ fn issue_13882() {
2929
let _raw = (&mut x[1] as *mut i32).wrapping_offset(-1);
3030
//~^ borrow_as_ptr
3131
}
32+
33+
fn implicit_cast() {
34+
let val = 1;
35+
let p: *const i32 = &val;
36+
//~^ borrow_as_ptr
37+
38+
let mut val = 1;
39+
let p: *mut i32 = &mut val;
40+
//~^ borrow_as_ptr
41+
}

tests/ui/borrow_as_ptr.stderr

+23-1
Original file line numberDiff line numberDiff line change
@@ -25,5 +25,27 @@ error: borrow as raw pointer
2525
LL | let _raw = (&mut x[1] as *mut i32).wrapping_offset(-1);
2626
| ^^^^^^^^^^^^^^^^^^^^^ help: try: `&raw mut x[1]`
2727

28-
error: aborting due to 4 previous errors
28+
error: implicit borrow as raw pointer
29+
--> tests/ui/borrow_as_ptr.rs:35:25
30+
|
31+
LL | let p: *const i32 = &val;
32+
| ^^^^
33+
|
34+
help: use a raw pointer instead
35+
|
36+
LL | let p: *const i32 = &raw const val;
37+
| +++++++++
38+
39+
error: implicit borrow as raw pointer
40+
--> tests/ui/borrow_as_ptr.rs:39:23
41+
|
42+
LL | let p: *mut i32 = &mut val;
43+
| ^^^^^^^^
44+
|
45+
help: use a raw pointer instead
46+
|
47+
LL | let p: *mut i32 = &raw mut val;
48+
| +++
49+
50+
error: aborting due to 6 previous errors
2951

0 commit comments

Comments
 (0)