From 5c98737715f60ce180a3b607fd1b96c709f6807d Mon Sep 17 00:00:00 2001 From: Eric Holk Date: Fri, 13 May 2022 16:25:22 -0700 Subject: [PATCH 1/2] Drop tracking: handle invalid assignments better Previously this test case was crashing with an index out of bounds error deep in the call to `needs_drop`. We avoid this by detecting clearly invalid assignees in the `mutate` callback and ignoring these. --- .../drop_ranges/record_consumed_borrow.rs | 9 +++++++++ .../issue-73741-type-err-drop-tracking.rs | 14 ++++++++++++++ .../issue-73741-type-err-drop-tracking.stderr | 11 +++++++++++ 3 files changed, 34 insertions(+) create mode 100644 src/test/ui/async-await/issue-73741-type-err-drop-tracking.rs create mode 100644 src/test/ui/async-await/issue-73741-type-err-drop-tracking.stderr diff --git a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs index 928daba0a7b39..b3012cc677661 100644 --- a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs +++ b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs @@ -180,6 +180,15 @@ impl<'tcx> expr_use_visitor::Delegate<'tcx> for ExprUseDelegate<'tcx> { diag_expr_id: HirId, ) { debug!("mutate {assignee_place:?}; diag_expr_id={diag_expr_id:?}"); + + if assignee_place.place.base == PlaceBase::Rvalue + && assignee_place.place.projections.len() == 0 + { + // Assigning to an Rvalue is illegal unless done through a dereference. We would have + // already gotten a type error, so we will just return here. + return; + } + // If the type being assigned needs dropped, then the mutation counts as a borrow // since it is essentially doing `Drop::drop(&mut x); x = new_value;`. if assignee_place.place.base_ty.needs_drop(self.tcx, self.param_env) { diff --git a/src/test/ui/async-await/issue-73741-type-err-drop-tracking.rs b/src/test/ui/async-await/issue-73741-type-err-drop-tracking.rs new file mode 100644 index 0000000000000..c3423ad629f16 --- /dev/null +++ b/src/test/ui/async-await/issue-73741-type-err-drop-tracking.rs @@ -0,0 +1,14 @@ +// edition:2018 +// compile-flags: -Zdrop-tracking +// Regression test for issue #73741 +// Ensures that we don't emit spurious errors when +// a type error ocurrs in an `async fn` + +async fn weird() { + 1 = 2; //~ ERROR invalid left-hand side + + let mut loop_count = 0; + async {}.await +} + +fn main() {} diff --git a/src/test/ui/async-await/issue-73741-type-err-drop-tracking.stderr b/src/test/ui/async-await/issue-73741-type-err-drop-tracking.stderr new file mode 100644 index 0000000000000..d4e3b6c3bf40d --- /dev/null +++ b/src/test/ui/async-await/issue-73741-type-err-drop-tracking.stderr @@ -0,0 +1,11 @@ +error[E0070]: invalid left-hand side of assignment + --> $DIR/issue-73741-type-err-drop-tracking.rs:8:7 + | +LL | 1 = 2; + | - ^ + | | + | cannot assign to this expression + +error: aborting due to previous error + +For more information about this error, try `rustc --explain E0070`. From 6665a4328b4076285e4c233995b5a08aeff4b603 Mon Sep 17 00:00:00 2001 From: Eric Holk Date: Fri, 13 May 2022 19:32:53 -0700 Subject: [PATCH 2/2] Fix nit --- .../generator_interior/drop_ranges/record_consumed_borrow.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs index b3012cc677661..e89a896199615 100644 --- a/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs +++ b/compiler/rustc_typeck/src/check/generator_interior/drop_ranges/record_consumed_borrow.rs @@ -182,7 +182,7 @@ impl<'tcx> expr_use_visitor::Delegate<'tcx> for ExprUseDelegate<'tcx> { debug!("mutate {assignee_place:?}; diag_expr_id={diag_expr_id:?}"); if assignee_place.place.base == PlaceBase::Rvalue - && assignee_place.place.projections.len() == 0 + && assignee_place.place.projections.is_empty() { // Assigning to an Rvalue is illegal unless done through a dereference. We would have // already gotten a type error, so we will just return here.