Skip to content

Commit eb8bde5

Browse files
committed
replace temporary_cstring_as_ptr with dangling_pointers_from_temporaries
1 parent 241c8c4 commit eb8bde5

15 files changed

+26
-57
lines changed

compiler/rustc_lint/src/dangling.rs

+2-52
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,11 @@
11
use rustc_hir::{Expr, ExprKind, LangItem};
2-
use rustc_middle::ty::{self, Ty, TyCtxt};
2+
use rustc_middle::ty::{Ty, TyCtxt};
33
use rustc_session::{declare_lint, declare_lint_pass};
44
use rustc_span::symbol::sym;
55

66
use crate::lints::InstantlyDangling;
77
use crate::{LateContext, LateLintPass, LintContext};
88

9-
declare_lint! {
10-
/// The `temporary_cstring_as_ptr` lint detects getting the inner pointer of
11-
/// a temporary `CString`.
12-
///
13-
/// ### Example
14-
///
15-
/// ```rust
16-
/// # #![allow(unused)]
17-
/// # use std::ffi::CString;
18-
/// let c_str = CString::new("foo").unwrap().as_ptr();
19-
/// ```
20-
///
21-
/// {{produces}}
22-
///
23-
/// ### Explanation
24-
///
25-
/// The inner pointer of a `CString` lives only as long as the `CString` it
26-
/// points to. Getting the inner pointer of a *temporary* `CString` allows the `CString`
27-
/// to be dropped at the end of the statement, as it is not being referenced as far as the
28-
/// typesystem is concerned. This means outside of the statement the pointer will point to
29-
/// freed memory, which causes undefined behavior if the pointer is later dereferenced.
30-
pub TEMPORARY_CSTRING_AS_PTR,
31-
Warn,
32-
"detects getting the inner pointer of a temporary `CString`"
33-
}
34-
359
// FIXME: does not catch UnsafeCell::get
3610
// FIXME: does not catch getting a ref to a temporary and then converting it to a ptr
3711
declare_lint! {
@@ -68,34 +42,10 @@ declare_lint! {
6842
"detects getting a pointer from a temporary"
6943
}
7044

71-
declare_lint_pass!(DanglingPointers => [TEMPORARY_CSTRING_AS_PTR, DANGLING_POINTERS_FROM_TEMPORARIES]);
45+
declare_lint_pass!(DanglingPointers => [DANGLING_POINTERS_FROM_TEMPORARIES]);
7246

7347
impl<'tcx> LateLintPass<'tcx> for DanglingPointers {
7448
fn check_expr(&mut self, cx: &LateContext<'tcx>, expr: &'tcx Expr<'_>) {
75-
if let ExprKind::MethodCall(as_ptr_path, as_ptr_receiver, ..) = expr.kind
76-
&& as_ptr_path.ident.name == sym::as_ptr
77-
&& let ExprKind::MethodCall(unwrap_path, unwrap_receiver, ..) = as_ptr_receiver.kind
78-
&& (unwrap_path.ident.name == sym::unwrap || unwrap_path.ident.name == sym::expect)
79-
&& let source_type = cx.typeck_results().expr_ty(unwrap_receiver)
80-
&& let ty::Adt(def, args) = source_type.kind()
81-
&& cx.tcx.is_diagnostic_item(sym::Result, def.did())
82-
&& let ty = args.type_at(0)
83-
&& let ty::Adt(adt, _) = ty.kind()
84-
&& cx.tcx.is_diagnostic_item(sym::cstring_type, adt.did())
85-
{
86-
cx.emit_span_lint(
87-
TEMPORARY_CSTRING_AS_PTR,
88-
as_ptr_path.ident.span,
89-
InstantlyDangling {
90-
callee: as_ptr_path.ident.name,
91-
ty,
92-
ptr_span: as_ptr_path.ident.span,
93-
temporary_span: as_ptr_receiver.span,
94-
},
95-
);
96-
return; // One lint is enough
97-
}
98-
9949
if let ExprKind::MethodCall(method, receiver, _args, _span) = expr.kind
10050
&& matches!(method.ident.name, sym::as_ptr | sym::as_mut_ptr)
10151
&& is_temporary_rvalue(receiver)

compiler/rustc_lint/src/lib.rs

+1
Original file line numberDiff line numberDiff line change
@@ -346,6 +346,7 @@ fn register_builtins(store: &mut LintStore) {
346346
store.register_renamed("non_fmt_panic", "non_fmt_panics");
347347
store.register_renamed("unused_tuple_struct_fields", "dead_code");
348348
store.register_renamed("static_mut_ref", "static_mut_refs");
349+
store.register_renamed("temporary_cstring_as_ptr", "dangling_pointers_from_temporaries");
349350

350351
// These were moved to tool lints, but rustc still sees them when compiling normally, before
351352
// tool lints are registered, so `check_tool_name_for_backwards_compat` doesn't work. Use

tests/ui/lint/dangling-ptr/cstring-as-param.rs renamed to tests/ui/lint/dangling-pointers-from-temporaries/cstring-as-param.rs

+1
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
#![deny(temporary_cstring_as_ptr)]
2+
//~^ [renamed_and_removed_lints]
23

34
use std::ffi::CString;
45
use std::os::raw::c_char;

tests/ui/lint/dangling-ptr/cstring-as-param.stderr renamed to tests/ui/lint/dangling-pointers-from-temporaries/cstring-as-param.stderr

+10-2
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,13 @@
1+
warning: lint `temporary_cstring_as_ptr` has been renamed to `dangling_pointers_from_temporaries`
2+
--> $DIR/cstring-as-param.rs:1:9
3+
|
4+
LL | #![deny(temporary_cstring_as_ptr)]
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `dangling_pointers_from_temporaries`
6+
|
7+
= note: `#[warn(renamed_and_removed_lints)]` on by default
8+
19
error: getting a pointer from a temporary `CString` will result in a dangling pointer
2-
--> $DIR/cstring-as-param.rs:9:45
10+
--> $DIR/cstring-as-param.rs:10:45
311
|
412
LL | some_function(CString::new("").unwrap().as_ptr());
513
| ------------------------- ^^^^^^ this pointer will immediately be invalid
@@ -14,5 +22,5 @@ note: the lint level is defined here
1422
LL | #![deny(temporary_cstring_as_ptr)]
1523
| ^^^^^^^^^^^^^^^^^^^^^^^^
1624

17-
error: aborting due to 1 previous error
25+
error: aborting due to 1 previous error; 1 warning emitted
1826

tests/ui/lint/dangling-ptr/cstring-as-ptr.rs renamed to tests/ui/lint/dangling-pointers-from-temporaries/cstring-as-ptr.rs

+1
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
// this program is not technically incorrect, but is an obscure enough style to be worth linting
22
#![deny(temporary_cstring_as_ptr)]
3+
//~^ [renamed_and_removed_lints]
34

45
use std::ffi::CString;
56

tests/ui/lint/dangling-ptr/cstring-as-ptr.stderr renamed to tests/ui/lint/dangling-pointers-from-temporaries/cstring-as-ptr.stderr

+11-3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,13 @@
1+
warning: lint `temporary_cstring_as_ptr` has been renamed to `dangling_pointers_from_temporaries`
2+
--> $DIR/cstring-as-ptr.rs:2:9
3+
|
4+
LL | #![deny(temporary_cstring_as_ptr)]
5+
| ^^^^^^^^^^^^^^^^^^^^^^^^ help: use the new name: `dangling_pointers_from_temporaries`
6+
|
7+
= note: `#[warn(renamed_and_removed_lints)]` on by default
8+
19
error: getting a pointer from a temporary `CString` will result in a dangling pointer
2-
--> $DIR/cstring-as-ptr.rs:14:48
10+
--> $DIR/cstring-as-ptr.rs:15:48
311
|
412
LL | let s = CString::new("some text").unwrap().as_ptr();
513
| ---------------------------------- ^^^^^^ this pointer will immediately be invalid
@@ -15,7 +23,7 @@ LL | #![deny(temporary_cstring_as_ptr)]
1523
| ^^^^^^^^^^^^^^^^^^^^^^^^
1624

1725
error: getting a pointer from a temporary `CString` will result in a dangling pointer
18-
--> $DIR/cstring-as-ptr.rs:8:52
26+
--> $DIR/cstring-as-ptr.rs:9:52
1927
|
2028
LL | let s = CString::new("some text").unwrap().as_ptr();
2129
| ---------------------------------- ^^^^^^ this pointer will immediately be invalid
@@ -29,5 +37,5 @@ LL | mymacro!();
2937
= help: for more information, see https://doc.rust-lang.org/reference/destructors.html
3038
= note: this error originates in the macro `mymacro` (in Nightly builds, run with -Z macro-backtrace for more info)
3139

32-
error: aborting due to 2 previous errors
40+
error: aborting due to 2 previous errors; 1 warning emitted
3341

0 commit comments

Comments
 (0)