about summary refs log tree commit diff
diff options
context:
space:
mode:
authorMichael Goulet <michael@errs.io>2022-06-27 15:43:23 -0700
committerMichael Goulet <michael@errs.io>2022-06-28 22:34:13 +0000
commitf4fdcc7e24aefb1b75cbe075a475632b525c7a78 (patch)
tree4b0f3a0cba2653175d78a9608746ae9c8c478d29
parent830880640304ba8699c5f9a0c4665c38a3271963 (diff)
downloadrust-f4fdcc7e24aefb1b75cbe075a475632b525c7a78.tar.gz
rust-f4fdcc7e24aefb1b75cbe075a475632b525c7a78.zip
Remove redundant logic to suggest `as_ref`
-rw-r--r--compiler/rustc_borrowck/src/diagnostics/move_errors.rs53
-rw-r--r--src/test/ui/binop/binop-move-semantics.stderr16
-rw-r--r--src/test/ui/borrowck/suggest-as-ref-on-mut-closure.rs16
-rw-r--r--src/test/ui/borrowck/suggest-as-ref-on-mut-closure.stderr31
-rw-r--r--src/test/ui/suggestions/option-content-move.stderr26
-rw-r--r--src/test/ui/unop-move-semantics.stderr16
6 files changed, 102 insertions, 56 deletions
diff --git a/compiler/rustc_borrowck/src/diagnostics/move_errors.rs b/compiler/rustc_borrowck/src/diagnostics/move_errors.rs
index eb5e61fa064..becb81b2e26 100644
--- a/compiler/rustc_borrowck/src/diagnostics/move_errors.rs
+++ b/compiler/rustc_borrowck/src/diagnostics/move_errors.rs
@@ -4,7 +4,7 @@ use rustc_middle::ty;
 use rustc_mir_dataflow::move_paths::{
     IllegalMoveOrigin, IllegalMoveOriginKind, LookupResult, MoveError, MovePathIndex,
 };
-use rustc_span::{sym, Span};
+use rustc_span::Span;
 
 use crate::diagnostics::UseSpans;
 use crate::prefixes::PrefixSet;
@@ -218,29 +218,13 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
 
     fn report(&mut self, error: GroupedMoveError<'tcx>) {
         let (mut err, err_span) = {
-            let (span, use_spans, original_path, kind, has_complex_bindings): (
-                Span,
-                Option<UseSpans<'tcx>>,
-                Place<'tcx>,
-                &IllegalMoveOriginKind<'_>,
-                bool,
-            ) = match error {
-                GroupedMoveError::MovesFromPlace {
-                    span,
-                    original_path,
-                    ref kind,
-                    ref binds_to,
-                    ..
+            let (span, use_spans, original_path, kind) = match error {
+                GroupedMoveError::MovesFromPlace { span, original_path, ref kind, .. }
+                | GroupedMoveError::MovesFromValue { span, original_path, ref kind, .. } => {
+                    (span, None, original_path, kind)
                 }
-                | GroupedMoveError::MovesFromValue {
-                    span,
-                    original_path,
-                    ref kind,
-                    ref binds_to,
-                    ..
-                } => (span, None, original_path, kind, !binds_to.is_empty()),
                 GroupedMoveError::OtherIllegalMove { use_spans, original_path, ref kind } => {
-                    (use_spans.args_or_use(), Some(use_spans), original_path, kind, false)
+                    (use_spans.args_or_use(), Some(use_spans), original_path, kind)
                 }
             };
             debug!(
@@ -259,7 +243,6 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
                             target_place,
                             span,
                             use_spans,
-                            has_complex_bindings,
                         ),
                     &IllegalMoveOriginKind::InteriorOfTypeWithDestructor { container_ty: ty } => {
                         self.cannot_move_out_of_interior_of_drop(span, ty)
@@ -302,7 +285,6 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
         deref_target_place: Place<'tcx>,
         span: Span,
         use_spans: Option<UseSpans<'tcx>>,
-        has_complex_bindings: bool,
     ) -> DiagnosticBuilder<'a, ErrorGuaranteed> {
         // Inspect the type of the content behind the
         // borrow to provide feedback about why this
@@ -399,28 +381,7 @@ impl<'a, 'tcx> MirBorrowckCtxt<'a, 'tcx> {
                 }
             }
         };
-        let ty = move_place.ty(self.body, self.infcx.tcx).ty;
-        let def_id = match *ty.kind() {
-            ty::Adt(self_def, _) => self_def.did(),
-            ty::Foreign(def_id)
-            | ty::FnDef(def_id, _)
-            | ty::Closure(def_id, _)
-            | ty::Generator(def_id, ..)
-            | ty::Opaque(def_id, _) => def_id,
-            _ => return err,
-        };
-        let diag_name = self.infcx.tcx.get_diagnostic_name(def_id);
-        if matches!(diag_name, Some(sym::Option | sym::Result))
-            && use_spans.map_or(true, |v| !v.for_closure())
-            && !has_complex_bindings
-        {
-            err.span_suggestion_verbose(
-                span.shrink_to_hi(),
-                &format!("consider borrowing the `{}`'s content", diag_name.unwrap()),
-                ".as_ref()",
-                Applicability::MaybeIncorrect,
-            );
-        } else if let Some(use_spans) = use_spans {
+        if let Some(use_spans) = use_spans {
             self.explain_captures(
                 &mut err, span, span, use_spans, move_place, None, "", "", "", false, true,
             );
diff --git a/src/test/ui/binop/binop-move-semantics.stderr b/src/test/ui/binop/binop-move-semantics.stderr
index 2cd6d1abfdc..695b01d5ee3 100644
--- a/src/test/ui/binop/binop-move-semantics.stderr
+++ b/src/test/ui/binop/binop-move-semantics.stderr
@@ -63,8 +63,20 @@ LL |     use_mut(n); use_imm(m);
 error[E0507]: cannot move out of `*m` which is behind a mutable reference
   --> $DIR/binop-move-semantics.rs:30:5
    |
-LL |     *m
-   |     ^^ move occurs because `*m` has type `T`, which does not implement the `Copy` trait
+LL |       *m
+   |       -^
+   |       |
+   |  _____move occurs because `*m` has type `T`, which does not implement the `Copy` trait
+   | |
+LL | |     +
+LL | |     *n;
+   | |______- `*m` moved due to usage in operator
+   |
+note: calling this operator moves the left-hand side
+  --> $SRC_DIR/core/src/ops/arith.rs:LL:COL
+   |
+LL |     fn add(self, rhs: Rhs) -> Self::Output;
+   |            ^^^^
 
 error[E0507]: cannot move out of `*n` which is behind a shared reference
   --> $DIR/binop-move-semantics.rs:32:5
diff --git a/src/test/ui/borrowck/suggest-as-ref-on-mut-closure.rs b/src/test/ui/borrowck/suggest-as-ref-on-mut-closure.rs
new file mode 100644
index 00000000000..d3d75d579e6
--- /dev/null
+++ b/src/test/ui/borrowck/suggest-as-ref-on-mut-closure.rs
@@ -0,0 +1,16 @@
+// This is not exactly right, yet.
+
+// Ideally we should be suggesting `as_mut` for the first case,
+//and suggesting to change `as_ref` to `as_mut` in the second.
+
+fn x(cb: &mut Option<&mut dyn FnMut()>) {
+    cb.map(|cb| cb());
+    //~^ ERROR cannot move out of `*cb` which is behind a mutable reference
+}
+
+fn x2(cb: &mut Option<&mut dyn FnMut()>) {
+    cb.as_ref().map(|cb| cb());
+    //~^ ERROR cannot borrow `*cb` as mutable, as it is behind a `&` reference
+}
+
+fn main() {}
diff --git a/src/test/ui/borrowck/suggest-as-ref-on-mut-closure.stderr b/src/test/ui/borrowck/suggest-as-ref-on-mut-closure.stderr
new file mode 100644
index 00000000000..47e45a25e59
--- /dev/null
+++ b/src/test/ui/borrowck/suggest-as-ref-on-mut-closure.stderr
@@ -0,0 +1,31 @@
+error[E0507]: cannot move out of `*cb` which is behind a mutable reference
+  --> $DIR/suggest-as-ref-on-mut-closure.rs:7:5
+   |
+LL |     cb.map(|cb| cb());
+   |     ^^^--------------
+   |     |  |
+   |     |  `*cb` moved due to this method call
+   |     move occurs because `*cb` has type `Option<&mut dyn FnMut()>`, which does not implement the `Copy` trait
+   |
+note: this function takes ownership of the receiver `self`, which moves `*cb`
+  --> $SRC_DIR/core/src/option.rs:LL:COL
+   |
+LL |     pub const fn map<U, F>(self, f: F) -> Option<U>
+   |                            ^^^^
+help: consider calling `.as_ref()` to borrow the type's contents
+   |
+LL |     cb.as_ref().map(|cb| cb());
+   |        +++++++++
+
+error[E0596]: cannot borrow `*cb` as mutable, as it is behind a `&` reference
+  --> $DIR/suggest-as-ref-on-mut-closure.rs:12:26
+   |
+LL |     cb.as_ref().map(|cb| cb());
+   |                      --  ^^ `cb` is a `&` reference, so the data it refers to cannot be borrowed as mutable
+   |                      |
+   |                      help: consider changing this to be a mutable reference: `&mut &mut dyn FnMut()`
+
+error: aborting due to 2 previous errors
+
+Some errors have detailed explanations: E0507, E0596.
+For more information about an error, try `rustc --explain E0507`.
diff --git a/src/test/ui/suggestions/option-content-move.stderr b/src/test/ui/suggestions/option-content-move.stderr
index a9e540084e5..fccfbe1d744 100644
--- a/src/test/ui/suggestions/option-content-move.stderr
+++ b/src/test/ui/suggestions/option-content-move.stderr
@@ -2,23 +2,37 @@ error[E0507]: cannot move out of `selection.1` which is behind a shared referenc
   --> $DIR/option-content-move.rs:11:20
    |
 LL |                 if selection.1.unwrap().contains(selection.0) {
-   |                    ^^^^^^^^^^^ move occurs because `selection.1` has type `Option<String>`, which does not implement the `Copy` trait
+   |                    ^^^^^^^^^^^ -------- `selection.1` moved due to this method call
+   |                    |
+   |                    move occurs because `selection.1` has type `Option<String>`, which does not implement the `Copy` trait
    |
-help: consider borrowing the `Option`'s content
+note: this function takes ownership of the receiver `self`, which moves `selection.1`
+  --> $SRC_DIR/core/src/option.rs:LL:COL
+   |
+LL |     pub const fn unwrap(self) -> T {
+   |                         ^^^^
+help: consider calling `.as_ref()` to borrow the type's contents
    |
 LL |                 if selection.1.as_ref().unwrap().contains(selection.0) {
-   |                               +++++++++
+   |                                +++++++++
 
 error[E0507]: cannot move out of `selection.1` which is behind a shared reference
   --> $DIR/option-content-move.rs:29:20
    |
 LL |                 if selection.1.unwrap().contains(selection.0) {
-   |                    ^^^^^^^^^^^ move occurs because `selection.1` has type `Result<String, String>`, which does not implement the `Copy` trait
+   |                    ^^^^^^^^^^^ -------- `selection.1` moved due to this method call
+   |                    |
+   |                    move occurs because `selection.1` has type `Result<String, String>`, which does not implement the `Copy` trait
+   |
+note: this function takes ownership of the receiver `self`, which moves `selection.1`
+  --> $SRC_DIR/core/src/result.rs:LL:COL
    |
-help: consider borrowing the `Result`'s content
+LL |     pub fn unwrap(self) -> T
+   |                   ^^^^
+help: consider calling `.as_ref()` to borrow the type's contents
    |
 LL |                 if selection.1.as_ref().unwrap().contains(selection.0) {
-   |                               +++++++++
+   |                                +++++++++
 
 error: aborting due to 2 previous errors
 
diff --git a/src/test/ui/unop-move-semantics.stderr b/src/test/ui/unop-move-semantics.stderr
index 14052486cbb..65d866c716e 100644
--- a/src/test/ui/unop-move-semantics.stderr
+++ b/src/test/ui/unop-move-semantics.stderr
@@ -46,13 +46,25 @@ error[E0507]: cannot move out of `*m` which is behind a mutable reference
   --> $DIR/unop-move-semantics.rs:24:6
    |
 LL |     !*m;
-   |      ^^ move occurs because `*m` has type `T`, which does not implement the `Copy` trait
+   |     -^^
+   |     ||
+   |     |move occurs because `*m` has type `T`, which does not implement the `Copy` trait
+   |     `*m` moved due to usage in operator
+   |
+note: calling this operator moves the left-hand side
+  --> $SRC_DIR/core/src/ops/bit.rs:LL:COL
+   |
+LL |     fn not(self) -> Self::Output;
+   |            ^^^^
 
 error[E0507]: cannot move out of `*n` which is behind a shared reference
   --> $DIR/unop-move-semantics.rs:26:6
    |
 LL |     !*n;
-   |      ^^ move occurs because `*n` has type `T`, which does not implement the `Copy` trait
+   |     -^^
+   |     ||
+   |     |move occurs because `*n` has type `T`, which does not implement the `Copy` trait
+   |     `*n` moved due to usage in operator
 
 error: aborting due to 5 previous errors