diff --git a/compiler/rustc_typeck/src/check/generator_interior.rs b/compiler/rustc_typeck/src/check/generator_interior.rs index b897d137f74a..bfe0200101c9 100644 --- a/compiler/rustc_typeck/src/check/generator_interior.rs +++ b/compiler/rustc_typeck/src/check/generator_interior.rs @@ -457,7 +457,7 @@ impl<'a, 'tcx> Visitor<'tcx> for InteriorVisitor<'a, 'tcx> { } #[derive(Default)] -pub struct SuspendCheckData<'a, 'tcx> { +struct SuspendCheckData<'a, 'tcx> { expr: Option<&'tcx Expr<'tcx>>, source_span: Span, yield_span: Span, @@ -472,7 +472,7 @@ pub struct SuspendCheckData<'a, 'tcx> { // // Note that this technique was chosen over things like a `Suspend` marker trait // as it is simpler and has precedent in the compiler -pub fn check_must_not_suspend_ty<'tcx>( +fn check_must_not_suspend_ty<'tcx>( fcx: &FnCtxt<'_, 'tcx>, ty: Ty<'tcx>, hir_id: HirId, @@ -582,7 +582,9 @@ pub fn check_must_not_suspend_ty<'tcx>( }, ) } - ty::Ref(_region, ty, _mutability) => { + // If drop tracking is enabled, we want to look through references, since the referrent + // may not be considered live across the await point. + ty::Ref(_region, ty, _mutability) if fcx.sess().opts.debugging_opts.drop_tracking => { let descr_pre = &format!("{}reference{} to ", data.descr_pre, plural_suffix); check_must_not_suspend_ty(fcx, ty, hir_id, SuspendCheckData { descr_pre, ..data }) } diff --git a/src/test/ui/lint/must_not_suspend/ref-drop-tracking.stderr b/src/test/ui/lint/must_not_suspend/ref-drop-tracking.stderr new file mode 100644 index 000000000000..33c7ff2cb337 --- /dev/null +++ b/src/test/ui/lint/must_not_suspend/ref-drop-tracking.stderr @@ -0,0 +1,27 @@ +error: reference to `Umm` held across a suspend point, but should not be + --> $DIR/ref-drop-tracking.rs:19:13 + | +LL | let guard = &mut self.u; + | ^^^^^ +LL | +LL | other().await; + | ------ the value is held across this suspend point + | +note: the lint level is defined here + --> $DIR/ref-drop-tracking.rs:4:9 + | +LL | #![deny(must_not_suspend)] + | ^^^^^^^^^^^^^^^^ +note: You gotta use Umm's, ya know? + --> $DIR/ref-drop-tracking.rs:19:13 + | +LL | let guard = &mut self.u; + | ^^^^^ +help: consider using a block (`{ ... }`) to shrink the value's scope, ending before the suspend point + --> $DIR/ref-drop-tracking.rs:19:13 + | +LL | let guard = &mut self.u; + | ^^^^^ + +error: aborting due to previous error + diff --git a/src/test/ui/lint/must_not_suspend/ref.stderr b/src/test/ui/lint/must_not_suspend/ref.stderr index 8fbf3e71649e..5f000014c7db 100644 --- a/src/test/ui/lint/must_not_suspend/ref.stderr +++ b/src/test/ui/lint/must_not_suspend/ref.stderr @@ -1,5 +1,5 @@ -error: reference to `Umm` held across a suspend point, but should not be - --> $DIR/ref.rs:18:13 +error: `Umm` held across a suspend point, but should not be + --> $DIR/ref.rs:18:26 | LL | let guard = &mut self.u; | ^^^^^^ @@ -13,15 +13,15 @@ note: the lint level is defined here LL | #![deny(must_not_suspend)] | ^^^^^^^^^^^^^^^^ note: You gotta use Umm's, ya know? - --> $DIR/ref.rs:18:13 + --> $DIR/ref.rs:18:26 | LL | let guard = &mut self.u; - | ^^^^^ + | ^^^^^^ help: consider using a block (`{ ... }`) to shrink the value's scope, ending before the suspend point - --> $DIR/ref.rs:18:13 + --> $DIR/ref.rs:18:26 | LL | let guard = &mut self.u; - | ^^^^^ + | ^^^^^^ error: aborting due to previous error