about summary refs log tree commit diff
diff options
context:
space:
mode:
authorEsteban Küber <esteban@kuber.com.ar>2021-01-17 16:48:52 -0800
committerEsteban Küber <esteban@kuber.com.ar>2021-01-17 16:48:52 -0800
commit70a43e07f6887dd1de62a9bbbc77b4a0c6e8d0d8 (patch)
tree4ecaa2af68e7fb2af8d66206321358e0328e4552
parent2e46cb38f174a4112fcfeecf6d4235f18830552f (diff)
downloadrust-70a43e07f6887dd1de62a9bbbc77b4a0c6e8d0d8.tar.gz
rust-70a43e07f6887dd1de62a9bbbc77b4a0c6e8d0d8.zip
Fix structured suggestion for explicit `drop` call
-rw-r--r--compiler/rustc_typeck/src/check/callee.rs18
-rw-r--r--compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs2
-rw-r--r--compiler/rustc_typeck/src/check/method/confirm.rs1
-rw-r--r--src/test/ui/error-codes/E0040.fixed18
-rw-r--r--src/test/ui/error-codes/E0040.rs3
-rw-r--r--src/test/ui/error-codes/E0040.stderr10
-rw-r--r--src/test/ui/explicit/explicit-call-to-dtor.fixed16
-rw-r--r--src/test/ui/explicit/explicit-call-to-dtor.rs2
-rw-r--r--src/test/ui/explicit/explicit-call-to-dtor.stderr10
-rw-r--r--src/test/ui/explicit/explicit-call-to-supertrait-dtor.fixed26
-rw-r--r--src/test/ui/explicit/explicit-call-to-supertrait-dtor.rs5
-rw-r--r--src/test/ui/explicit/explicit-call-to-supertrait-dtor.stderr10
-rw-r--r--src/test/ui/illegal-ufcs-drop.fixed10
-rw-r--r--src/test/ui/illegal-ufcs-drop.rs1
-rw-r--r--src/test/ui/illegal-ufcs-drop.stderr2
15 files changed, 107 insertions, 27 deletions
diff --git a/compiler/rustc_typeck/src/check/callee.rs b/compiler/rustc_typeck/src/check/callee.rs
index 116b079e742..4836418b3c2 100644
--- a/compiler/rustc_typeck/src/check/callee.rs
+++ b/compiler/rustc_typeck/src/check/callee.rs
@@ -25,24 +25,24 @@ pub fn check_legal_trait_for_method_call(
     tcx: TyCtxt<'_>,
     span: Span,
     receiver: Option<Span>,
+    expr_span: Span,
     trait_id: DefId,
 ) {
     if tcx.lang_items().drop_trait() == Some(trait_id) {
         let mut err = struct_span_err!(tcx.sess, span, E0040, "explicit use of destructor method");
         err.span_label(span, "explicit destructor calls not allowed");
 
-        let snippet = receiver
+        let (sp, suggestion) = receiver
             .and_then(|s| tcx.sess.source_map().span_to_snippet(s).ok())
-            .unwrap_or_default();
-
-        let suggestion =
-            if snippet.is_empty() { "drop".to_string() } else { format!("drop({})", snippet) };
+            .filter(|snippet| !snippet.is_empty())
+            .map(|snippet| (expr_span, format!("drop({})", snippet)))
+            .unwrap_or_else(|| (span, "drop".to_string()));
 
         err.span_suggestion(
-            span,
-            &format!("consider using `drop` function: `{}`", suggestion),
-            String::new(),
-            Applicability::Unspecified,
+            sp,
+            "consider using `drop` function",
+            suggestion,
+            Applicability::MaybeIncorrect,
         );
 
         err.emit();
diff --git a/compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs b/compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs
index 47799c95fc0..8e9074ba3a2 100644
--- a/compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs
+++ b/compiler/rustc_typeck/src/check/fn_ctxt/_impl.rs
@@ -1163,7 +1163,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
                 debug!("instantiate_value_path: def_id={:?} container={:?}", def_id, container);
                 match container {
                     ty::TraitContainer(trait_did) => {
-                        callee::check_legal_trait_for_method_call(tcx, span, None, trait_did)
+                        callee::check_legal_trait_for_method_call(tcx, span, None, span, trait_did)
                     }
                     ty::ImplContainer(impl_def_id) => {
                         if segments.len() == 1 {
diff --git a/compiler/rustc_typeck/src/check/method/confirm.rs b/compiler/rustc_typeck/src/check/method/confirm.rs
index e604419f413..2ff9607726d 100644
--- a/compiler/rustc_typeck/src/check/method/confirm.rs
+++ b/compiler/rustc_typeck/src/check/method/confirm.rs
@@ -507,6 +507,7 @@ impl<'a, 'tcx> ConfirmContext<'a, 'tcx> {
                 self.tcx,
                 self.span,
                 Some(self.self_expr.span),
+                self.call_expr.span,
                 trait_def_id,
             ),
             ty::ImplContainer(..) => {}
diff --git a/src/test/ui/error-codes/E0040.fixed b/src/test/ui/error-codes/E0040.fixed
new file mode 100644
index 00000000000..139dc8f9496
--- /dev/null
+++ b/src/test/ui/error-codes/E0040.fixed
@@ -0,0 +1,18 @@
+// run-rustfix
+struct Foo {
+    x: i32,
+}
+
+impl Drop for Foo {
+    fn drop(&mut self) {
+        println!("kaboom");
+    }
+}
+
+fn main() {
+    let mut x = Foo { x: -7 };
+    x.x = 0;
+    println!("{}", x.x);
+    drop(x);
+    //~^ ERROR E0040
+}
diff --git a/src/test/ui/error-codes/E0040.rs b/src/test/ui/error-codes/E0040.rs
index 113efae82c5..9ffc42d0c78 100644
--- a/src/test/ui/error-codes/E0040.rs
+++ b/src/test/ui/error-codes/E0040.rs
@@ -1,3 +1,4 @@
+// run-rustfix
 struct Foo {
     x: i32,
 }
@@ -10,6 +11,8 @@ impl Drop for Foo {
 
 fn main() {
     let mut x = Foo { x: -7 };
+    x.x = 0;
+    println!("{}", x.x);
     x.drop();
     //~^ ERROR E0040
 }
diff --git a/src/test/ui/error-codes/E0040.stderr b/src/test/ui/error-codes/E0040.stderr
index 69cf28b2970..9fcda1a9385 100644
--- a/src/test/ui/error-codes/E0040.stderr
+++ b/src/test/ui/error-codes/E0040.stderr
@@ -1,11 +1,11 @@
 error[E0040]: explicit use of destructor method
-  --> $DIR/E0040.rs:13:7
+  --> $DIR/E0040.rs:16:7
    |
 LL |     x.drop();
-   |       ^^^^
-   |       |
-   |       explicit destructor calls not allowed
-   |       help: consider using `drop` function: `drop(x)`
+   |     --^^^^--
+   |     | |
+   |     | explicit destructor calls not allowed
+   |     help: consider using `drop` function: `drop(x)`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/explicit/explicit-call-to-dtor.fixed b/src/test/ui/explicit/explicit-call-to-dtor.fixed
new file mode 100644
index 00000000000..91a4ca608da
--- /dev/null
+++ b/src/test/ui/explicit/explicit-call-to-dtor.fixed
@@ -0,0 +1,16 @@
+// run-rustfix
+struct Foo {
+    x: isize
+}
+
+impl Drop for Foo {
+    fn drop(&mut self) {
+        println!("kaboom");
+    }
+}
+
+fn main() {
+    let x = Foo { x: 3 };
+    println!("{}", x.x);
+    drop(x);   //~ ERROR explicit use of destructor method
+}
diff --git a/src/test/ui/explicit/explicit-call-to-dtor.rs b/src/test/ui/explicit/explicit-call-to-dtor.rs
index a6f9acc37a1..0656871eb1b 100644
--- a/src/test/ui/explicit/explicit-call-to-dtor.rs
+++ b/src/test/ui/explicit/explicit-call-to-dtor.rs
@@ -1,3 +1,4 @@
+// run-rustfix
 struct Foo {
     x: isize
 }
@@ -10,5 +11,6 @@ impl Drop for Foo {
 
 fn main() {
     let x = Foo { x: 3 };
+    println!("{}", x.x);
     x.drop();   //~ ERROR explicit use of destructor method
 }
diff --git a/src/test/ui/explicit/explicit-call-to-dtor.stderr b/src/test/ui/explicit/explicit-call-to-dtor.stderr
index 5ebe4ee4b90..f3c9bf6cccd 100644
--- a/src/test/ui/explicit/explicit-call-to-dtor.stderr
+++ b/src/test/ui/explicit/explicit-call-to-dtor.stderr
@@ -1,11 +1,11 @@
 error[E0040]: explicit use of destructor method
-  --> $DIR/explicit-call-to-dtor.rs:13:7
+  --> $DIR/explicit-call-to-dtor.rs:15:7
    |
 LL |     x.drop();
-   |       ^^^^
-   |       |
-   |       explicit destructor calls not allowed
-   |       help: consider using `drop` function: `drop(x)`
+   |     --^^^^--
+   |     | |
+   |     | explicit destructor calls not allowed
+   |     help: consider using `drop` function: `drop(x)`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/explicit/explicit-call-to-supertrait-dtor.fixed b/src/test/ui/explicit/explicit-call-to-supertrait-dtor.fixed
new file mode 100644
index 00000000000..47c4c9f67b6
--- /dev/null
+++ b/src/test/ui/explicit/explicit-call-to-supertrait-dtor.fixed
@@ -0,0 +1,26 @@
+// run-rustfix
+struct Foo {
+    x: isize
+}
+
+#[allow(drop_bounds)]
+trait Bar: Drop {
+    fn blah(&self);
+}
+
+impl Drop for Foo {
+    fn drop(&mut self) {
+        println!("kaboom");
+    }
+}
+
+impl Bar for Foo {
+    fn blah(&self) {
+        drop(self);    //~ ERROR explicit use of destructor method
+    }
+}
+
+fn main() {
+    let x = Foo { x: 3 };
+    println!("{}", x.x);
+}
diff --git a/src/test/ui/explicit/explicit-call-to-supertrait-dtor.rs b/src/test/ui/explicit/explicit-call-to-supertrait-dtor.rs
index ff56b9a8ae4..c698de50c75 100644
--- a/src/test/ui/explicit/explicit-call-to-supertrait-dtor.rs
+++ b/src/test/ui/explicit/explicit-call-to-supertrait-dtor.rs
@@ -1,8 +1,10 @@
+// run-rustfix
 struct Foo {
     x: isize
 }
 
-trait Bar : Drop {
+#[allow(drop_bounds)]
+trait Bar: Drop {
     fn blah(&self);
 }
 
@@ -20,4 +22,5 @@ impl Bar for Foo {
 
 fn main() {
     let x = Foo { x: 3 };
+    println!("{}", x.x);
 }
diff --git a/src/test/ui/explicit/explicit-call-to-supertrait-dtor.stderr b/src/test/ui/explicit/explicit-call-to-supertrait-dtor.stderr
index cd3fb3119a5..7f5106eb57e 100644
--- a/src/test/ui/explicit/explicit-call-to-supertrait-dtor.stderr
+++ b/src/test/ui/explicit/explicit-call-to-supertrait-dtor.stderr
@@ -1,11 +1,11 @@
 error[E0040]: explicit use of destructor method
-  --> $DIR/explicit-call-to-supertrait-dtor.rs:17:14
+  --> $DIR/explicit-call-to-supertrait-dtor.rs:19:14
    |
 LL |         self.drop();
-   |              ^^^^
-   |              |
-   |              explicit destructor calls not allowed
-   |              help: consider using `drop` function: `drop(self)`
+   |         -----^^^^--
+   |         |    |
+   |         |    explicit destructor calls not allowed
+   |         help: consider using `drop` function: `drop(self)`
 
 error: aborting due to previous error
 
diff --git a/src/test/ui/illegal-ufcs-drop.fixed b/src/test/ui/illegal-ufcs-drop.fixed
new file mode 100644
index 00000000000..d73b391be06
--- /dev/null
+++ b/src/test/ui/illegal-ufcs-drop.fixed
@@ -0,0 +1,10 @@
+// run-rustfix
+struct Foo;
+
+impl Drop for Foo {
+    fn drop(&mut self) {}
+}
+
+fn main() {
+    drop(&mut Foo) //~ ERROR explicit use of destructor method
+}
diff --git a/src/test/ui/illegal-ufcs-drop.rs b/src/test/ui/illegal-ufcs-drop.rs
index 5c072663eda..11411f55494 100644
--- a/src/test/ui/illegal-ufcs-drop.rs
+++ b/src/test/ui/illegal-ufcs-drop.rs
@@ -1,3 +1,4 @@
+// run-rustfix
 struct Foo;
 
 impl Drop for Foo {
diff --git a/src/test/ui/illegal-ufcs-drop.stderr b/src/test/ui/illegal-ufcs-drop.stderr
index 57c99739afd..91f47d5e456 100644
--- a/src/test/ui/illegal-ufcs-drop.stderr
+++ b/src/test/ui/illegal-ufcs-drop.stderr
@@ -1,5 +1,5 @@
 error[E0040]: explicit use of destructor method
-  --> $DIR/illegal-ufcs-drop.rs:8:5
+  --> $DIR/illegal-ufcs-drop.rs:9:5
    |
 LL |     Drop::drop(&mut Foo)
    |     ^^^^^^^^^^