Skip to content

Commit 4f1bae0

Browse files
committed
Auto merge of #10116 - tgross35:patch-1, r=llogiq
`not_unsafe_ptr_arg_deref` update documentation changelog: [`not_unsafe_ptr_arg_deref`]: strengthened documentation wording, fixes #7714
2 parents e8703a0 + 12f2dea commit 4f1bae0

File tree

1 file changed

+28
-5
lines changed
  • clippy_lints/src/functions

1 file changed

+28
-5
lines changed

clippy_lints/src/functions/mod.rs

Lines changed: 28 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -63,30 +63,53 @@ declare_clippy_lint! {
6363
/// arguments but are not marked `unsafe`.
6464
///
6565
/// ### Why is this bad?
66-
/// The function should probably be marked `unsafe`, since
67-
/// for an arbitrary raw pointer, there is no way of telling for sure if it is
68-
/// valid.
66+
/// The function should almost definitely be marked `unsafe`, since for an
67+
/// arbitrary raw pointer, there is no way of telling for sure if it is valid.
68+
///
69+
/// In general, this lint should **never be disabled** unless it is definitely a
70+
/// false positive (please submit an issue if so) since it breaks Rust's
71+
/// soundness guarantees, directly exposing API users to potentially dangerous
72+
/// program behavior. This is also true for internal APIs, as it is easy to leak
73+
/// unsoundness.
74+
///
75+
/// ### Context
76+
/// In Rust, an `unsafe {...}` block is used to indicate that the code in that
77+
/// section has been verified in some way that the compiler can not. For a
78+
/// function that accepts a raw pointer then accesses the pointer's data, this is
79+
/// generally impossible as the incoming pointer could point anywhere, valid or
80+
/// not. So, the signature should be marked `unsafe fn`: this indicates that the
81+
/// function's caller must provide some verification that the arguments it sends
82+
/// are valid (and then call the function within an `unsafe` block).
6983
///
7084
/// ### Known problems
7185
/// * It does not check functions recursively so if the pointer is passed to a
7286
/// private non-`unsafe` function which does the dereferencing, the lint won't
73-
/// trigger.
87+
/// trigger (false negative).
7488
/// * It only checks for arguments whose type are raw pointers, not raw pointers
7589
/// got from an argument in some other way (`fn foo(bar: &[*const u8])` or
76-
/// `some_argument.get_raw_ptr()`).
90+
/// `some_argument.get_raw_ptr()`) (false negative).
7791
///
7892
/// ### Example
7993
/// ```rust,ignore
8094
/// pub fn foo(x: *const u8) {
8195
/// println!("{}", unsafe { *x });
8296
/// }
97+
///
98+
/// // this call "looks" safe but will segfault or worse!
99+
/// // foo(invalid_ptr);
83100
/// ```
84101
///
85102
/// Use instead:
86103
/// ```rust,ignore
87104
/// pub unsafe fn foo(x: *const u8) {
88105
/// println!("{}", unsafe { *x });
89106
/// }
107+
///
108+
/// // this would cause a compiler error for calling without `unsafe`
109+
/// // foo(invalid_ptr);
110+
///
111+
/// // sound call if the caller knows the pointer is valid
112+
/// unsafe { foo(valid_ptr); }
90113
/// ```
91114
#[clippy::version = "pre 1.29.0"]
92115
pub NOT_UNSAFE_PTR_ARG_DEREF,

0 commit comments

Comments
 (0)