Skip to content

Commit 8bf1758

Browse files
committed
Auto merge of #68269 - csmoe:temp, r=estebank
Suggest to shorten temporary borrow from raw pointer Closes #65436 r? @estebank cc @tmandry
2 parents 8647aa1 + cd7b5ed commit 8bf1758

File tree

4 files changed

+75
-6
lines changed

4 files changed

+75
-6
lines changed

Diff for: src/librustc/traits/error_reporting/suggestions.rs

+32-5
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ use rustc_errors::{
1212
error_code, pluralize, struct_span_err, Applicability, DiagnosticBuilder, Style,
1313
};
1414
use rustc_hir as hir;
15+
use rustc_hir::def::DefKind;
1516
use rustc_hir::def_id::DefId;
1617
use rustc_hir::intravisit::Visitor;
1718
use rustc_hir::Node;
@@ -1366,14 +1367,40 @@ impl<'a, 'tcx> InferCtxt<'a, 'tcx> {
13661367

13671368
if let Some(expr_id) = expr {
13681369
let expr = hir.expect_expr(expr_id);
1369-
let is_ref = tables.expr_adjustments(expr).iter().any(|adj| adj.is_region_borrow());
1370+
debug!("target_ty evaluated from {:?}", expr);
1371+
13701372
let parent = hir.get_parent_node(expr_id);
13711373
if let Some(hir::Node::Expr(e)) = hir.find(parent) {
1372-
let method_span = hir.span(parent);
1373-
if tables.is_method_call(e) && is_ref {
1374+
let parent_span = hir.span(parent);
1375+
let parent_did = parent.owner_def_id();
1376+
// ```rust
1377+
// impl T {
1378+
// fn foo(&self) -> i32 {}
1379+
// }
1380+
// T.foo();
1381+
// ^^^^^^^ a temporary `&T` created inside this method call due to `&self`
1382+
// ```
1383+
//
1384+
let is_region_borrow =
1385+
tables.expr_adjustments(expr).iter().any(|adj| adj.is_region_borrow());
1386+
1387+
// ```rust
1388+
// struct Foo(*const u8);
1389+
// bar(Foo(std::ptr::null())).await;
1390+
// ^^^^^^^^^^^^^^^^^^^^^ raw-ptr `*T` created inside this struct ctor.
1391+
// ```
1392+
debug!("parent_def_kind: {:?}", self.tcx.def_kind(parent_did));
1393+
let is_raw_borrow_inside_fn_like_call = match self.tcx.def_kind(parent_did) {
1394+
Some(DefKind::Fn) | Some(DefKind::Ctor(..)) => target_ty.is_unsafe_ptr(),
1395+
_ => false,
1396+
};
1397+
1398+
if (tables.is_method_call(e) && is_region_borrow)
1399+
|| is_raw_borrow_inside_fn_like_call
1400+
{
13741401
err.span_help(
1375-
method_span,
1376-
"consider moving this method call into a `let` \
1402+
parent_span,
1403+
"consider moving this into a `let` \
13771404
binding to create a shorter lived borrow",
13781405
);
13791406
}

Diff for: src/test/ui/async-await/issue-64130-4-async-move.stderr

+1-1
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ LL | let _x = get().await;
2525
...
2626
LL | }
2727
| - `client` is later dropped here
28-
help: consider moving this method call into a `let` binding to create a shorter lived borrow
28+
help: consider moving this into a `let` binding to create a shorter lived borrow
2929
--> $DIR/issue-64130-4-async-move.rs:19:15
3030
|
3131
LL | match client.status() {
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
// edition:2018
2+
3+
struct Foo(*const u8);
4+
5+
unsafe impl Send for Foo {}
6+
7+
async fn bar(_: Foo) {}
8+
9+
fn assert_send<T: Send>(_: T) {}
10+
11+
fn main() {
12+
assert_send(async {
13+
//~^ ERROR future cannot be sent between threads safely
14+
bar(Foo(std::ptr::null())).await;
15+
})
16+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
error: future cannot be sent between threads safely
2+
--> $DIR/issue-65436-raw-ptr-not-send.rs:12:5
3+
|
4+
LL | fn assert_send<T: Send>(_: T) {}
5+
| ----------- ---- required by this bound in `assert_send`
6+
...
7+
LL | assert_send(async {
8+
| ^^^^^^^^^^^ future returned by `main` is not `Send`
9+
|
10+
= help: within `impl std::future::Future`, the trait `std::marker::Send` is not implemented for `*const u8`
11+
note: future is not `Send` as this value is used across an await
12+
--> $DIR/issue-65436-raw-ptr-not-send.rs:14:9
13+
|
14+
LL | bar(Foo(std::ptr::null())).await;
15+
| ^^^^^^^^----------------^^^^^^^^- `std::ptr::null()` is later dropped here
16+
| | |
17+
| | has type `*const u8`
18+
| await occurs here, with `std::ptr::null()` maybe used later
19+
help: consider moving this into a `let` binding to create a shorter lived borrow
20+
--> $DIR/issue-65436-raw-ptr-not-send.rs:14:13
21+
|
22+
LL | bar(Foo(std::ptr::null())).await;
23+
| ^^^^^^^^^^^^^^^^^^^^^
24+
25+
error: aborting due to previous error
26+

0 commit comments

Comments
 (0)