From 911d205b1fab7cb0b84e1768c1744d89bd2c5c27 Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sat, 1 Jun 2019 18:42:59 -0500 Subject: [PATCH 1/7] On TerminatorKind::DropAndReplace still handle unused_mut correctly --- src/librustc_mir/borrow_check/used_muts.rs | 44 +++++++++++----------- 1 file changed, 23 insertions(+), 21 deletions(-) diff --git a/src/librustc_mir/borrow_check/used_muts.rs b/src/librustc_mir/borrow_check/used_muts.rs index abfc2f9466c8e..2334bd33694c0 100644 --- a/src/librustc_mir/borrow_check/used_muts.rs +++ b/src/librustc_mir/borrow_check/used_muts.rs @@ -52,6 +52,24 @@ struct GatherUsedMutsVisitor<'visit, 'cx: 'visit, 'gcx: 'tcx, 'tcx: 'cx> { mbcx: &'visit mut MirBorrowckCtxt<'cx, 'gcx, 'tcx>, } +impl<'visit, 'cx, 'gcx, 'tcx> GatherUsedMutsVisitor<'visit, 'cx, 'gcx, 'tcx> { + fn remove_never_initialized_mut_locals(into: &Place) { + // Remove any locals that we found were initialized from the + // `never_initialized_mut_locals` set. At the end, the only remaining locals will + // be those that were never initialized - we will consider those as being used as + // they will either have been removed by unreachable code optimizations; or linted + // as unused variables. + if let Some(local) = into.base_local() { + debug!( + "visit_statement: statement={:?} local={:?} \ + never_initialized_mut_locals={:?}", + statement, local, self.never_initialized_mut_locals + ); + let _ = self.never_initialized_mut_locals.remove(&local); + } + } +} + impl<'visit, 'cx, 'gcx, 'tcx> Visitor<'tcx> for GatherUsedMutsVisitor<'visit, 'cx, 'gcx, 'tcx> { fn visit_terminator_kind( &mut self, @@ -61,14 +79,10 @@ impl<'visit, 'cx, 'gcx, 'tcx> Visitor<'tcx> for GatherUsedMutsVisitor<'visit, 'c debug!("visit_terminator_kind: kind={:?}", kind); match &kind { TerminatorKind::Call { destination: Some((into, _)), .. } => { - if let Some(local) = into.base_local() { - debug!( - "visit_terminator_kind: kind={:?} local={:?} \ - never_initialized_mut_locals={:?}", - kind, local, self.never_initialized_mut_locals - ); - let _ = self.never_initialized_mut_locals.remove(&local); - } + self.remove_never_initialized_mut_locals(&into); + }, + TerminatorKind::DropAndReplace { location, .. } => { + self.remove_never_initialized_mut_locals(&location); }, _ => {}, } @@ -81,19 +95,7 @@ impl<'visit, 'cx, 'gcx, 'tcx> Visitor<'tcx> for GatherUsedMutsVisitor<'visit, 'c ) { match &statement.kind { StatementKind::Assign(into, _) => { - // Remove any locals that we found were initialized from the - // `never_initialized_mut_locals` set. At the end, the only remaining locals will - // be those that were never initialized - we will consider those as being used as - // they will either have been removed by unreachable code optimizations; or linted - // as unused variables. - if let Some(local) = into.base_local() { - debug!( - "visit_statement: statement={:?} local={:?} \ - never_initialized_mut_locals={:?}", - statement, local, self.never_initialized_mut_locals - ); - let _ = self.never_initialized_mut_locals.remove(&local); - } + self.remove_never_initialized_mut_locals(into); }, _ => {}, } From c25b3df3e548ec42de1bb8a3aaad1e10d9de4aab Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sat, 1 Jun 2019 16:50:15 -0700 Subject: [PATCH 2/7] Elide lifetimes not used Co-Authored-By: Mazdak Farrokhzad --- src/librustc_mir/borrow_check/used_muts.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librustc_mir/borrow_check/used_muts.rs b/src/librustc_mir/borrow_check/used_muts.rs index 2334bd33694c0..db5c3c7a34046 100644 --- a/src/librustc_mir/borrow_check/used_muts.rs +++ b/src/librustc_mir/borrow_check/used_muts.rs @@ -52,7 +52,7 @@ struct GatherUsedMutsVisitor<'visit, 'cx: 'visit, 'gcx: 'tcx, 'tcx: 'cx> { mbcx: &'visit mut MirBorrowckCtxt<'cx, 'gcx, 'tcx>, } -impl<'visit, 'cx, 'gcx, 'tcx> GatherUsedMutsVisitor<'visit, 'cx, 'gcx, 'tcx> { +impl GatherUsedMutsVisitor<'_, '_, '_, '_> { fn remove_never_initialized_mut_locals(into: &Place) { // Remove any locals that we found were initialized from the // `never_initialized_mut_locals` set. At the end, the only remaining locals will From a39fffea220b5bd72b1ae3d34c25e97d77fac1dc Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sat, 1 Jun 2019 19:05:08 -0500 Subject: [PATCH 3/7] Add self parameter --- src/librustc_mir/borrow_check/used_muts.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librustc_mir/borrow_check/used_muts.rs b/src/librustc_mir/borrow_check/used_muts.rs index db5c3c7a34046..828429a1808c3 100644 --- a/src/librustc_mir/borrow_check/used_muts.rs +++ b/src/librustc_mir/borrow_check/used_muts.rs @@ -53,7 +53,7 @@ struct GatherUsedMutsVisitor<'visit, 'cx: 'visit, 'gcx: 'tcx, 'tcx: 'cx> { } impl GatherUsedMutsVisitor<'_, '_, '_, '_> { - fn remove_never_initialized_mut_locals(into: &Place) { + fn remove_never_initialized_mut_locals(&mut self, into: &Place) { // Remove any locals that we found were initialized from the // `never_initialized_mut_locals` set. At the end, the only remaining locals will // be those that were never initialized - we will consider those as being used as From 0a6a5c81ac8c853a8f026ab109965338ced4c3bb Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sat, 1 Jun 2019 19:05:18 -0500 Subject: [PATCH 4/7] Move debug statement into statement visitor --- src/librustc_mir/borrow_check/used_muts.rs | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/src/librustc_mir/borrow_check/used_muts.rs b/src/librustc_mir/borrow_check/used_muts.rs index 828429a1808c3..b9accd40c3998 100644 --- a/src/librustc_mir/borrow_check/used_muts.rs +++ b/src/librustc_mir/borrow_check/used_muts.rs @@ -60,11 +60,6 @@ impl GatherUsedMutsVisitor<'_, '_, '_, '_> { // they will either have been removed by unreachable code optimizations; or linted // as unused variables. if let Some(local) = into.base_local() { - debug!( - "visit_statement: statement={:?} local={:?} \ - never_initialized_mut_locals={:?}", - statement, local, self.never_initialized_mut_locals - ); let _ = self.never_initialized_mut_locals.remove(&local); } } @@ -95,6 +90,13 @@ impl<'visit, 'cx, 'gcx, 'tcx> Visitor<'tcx> for GatherUsedMutsVisitor<'visit, 'c ) { match &statement.kind { StatementKind::Assign(into, _) => { + if let Some(local) = into.base_local() { + debug!( + "visit_statement: statement={:?} local={:?} \ + never_initialized_mut_locals={:?}", + statement, local, self.never_initialized_mut_locals + ); + } self.remove_never_initialized_mut_locals(into); }, _ => {}, From 2a3b29ef97449038bf15f982d74e0d9379a4b953 Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sat, 1 Jun 2019 19:06:22 -0500 Subject: [PATCH 5/7] Add anonymous lifetime to Place parameter --- src/librustc_mir/borrow_check/used_muts.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/librustc_mir/borrow_check/used_muts.rs b/src/librustc_mir/borrow_check/used_muts.rs index b9accd40c3998..4a4787337ab58 100644 --- a/src/librustc_mir/borrow_check/used_muts.rs +++ b/src/librustc_mir/borrow_check/used_muts.rs @@ -53,7 +53,7 @@ struct GatherUsedMutsVisitor<'visit, 'cx: 'visit, 'gcx: 'tcx, 'tcx: 'cx> { } impl GatherUsedMutsVisitor<'_, '_, '_, '_> { - fn remove_never_initialized_mut_locals(&mut self, into: &Place) { + fn remove_never_initialized_mut_locals(&mut self, into: &Place<'_>) { // Remove any locals that we found were initialized from the // `never_initialized_mut_locals` set. At the end, the only remaining locals will // be those that were never initialized - we will consider those as being used as From 7feeaf0d2748f9ff81076a96c16ef360c9033071 Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sat, 1 Jun 2019 19:14:09 -0500 Subject: [PATCH 6/7] Add test --- src/test/ui/nll/issue-61424.rs | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 src/test/ui/nll/issue-61424.rs diff --git a/src/test/ui/nll/issue-61424.rs b/src/test/ui/nll/issue-61424.rs new file mode 100644 index 0000000000000..fcb5ff675986e --- /dev/null +++ b/src/test/ui/nll/issue-61424.rs @@ -0,0 +1,7 @@ +#![deny(unused_mut)] + +fn main() { + let mut x; //~ ERROR: variable does not need to be mutable + x = 0; + dbg!(0); +} From fea2cdb0a48e0cc6119d036a2ff4954e71bb8670 Mon Sep 17 00:00:00 2001 From: Chris Gregory Date: Sun, 2 Jun 2019 19:11:15 -0700 Subject: [PATCH 7/7] Use a type implementing Drop --- src/test/ui/nll/issue-61424.rs | 4 ++-- src/test/ui/nll/issue-61424.stderr | 16 ++++++++++++++++ 2 files changed, 18 insertions(+), 2 deletions(-) create mode 100644 src/test/ui/nll/issue-61424.stderr diff --git a/src/test/ui/nll/issue-61424.rs b/src/test/ui/nll/issue-61424.rs index fcb5ff675986e..44c8e9f7256f5 100644 --- a/src/test/ui/nll/issue-61424.rs +++ b/src/test/ui/nll/issue-61424.rs @@ -2,6 +2,6 @@ fn main() { let mut x; //~ ERROR: variable does not need to be mutable - x = 0; - dbg!(0); + x = String::new(); + dbg!(x); } diff --git a/src/test/ui/nll/issue-61424.stderr b/src/test/ui/nll/issue-61424.stderr new file mode 100644 index 0000000000000..ae336b2fe1c03 --- /dev/null +++ b/src/test/ui/nll/issue-61424.stderr @@ -0,0 +1,16 @@ +error: variable does not need to be mutable + --> $DIR/issue-61424.rs:4:9 + | +LL | let mut x; + | ----^ + | | + | help: remove this `mut` + | +note: lint level defined here + --> $DIR/issue-61424.rs:1:9 + | +LL | #![deny(unused_mut)] + | ^^^^^^^^^^ + +error: aborting due to previous error +