about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--clippy_lints/src/from_over_into.rs14
-rw-r--r--tests/ui/from_over_into.fixed11
-rw-r--r--tests/ui/from_over_into.rs11
-rw-r--r--tests/ui/from_over_into.stderr18
4 files changed, 46 insertions, 8 deletions
diff --git a/clippy_lints/src/from_over_into.rs b/clippy_lints/src/from_over_into.rs
index 6da5567d9c7..be887b03ae4 100644
--- a/clippy_lints/src/from_over_into.rs
+++ b/clippy_lints/src/from_over_into.rs
@@ -176,8 +176,8 @@ fn convert_to_from(
         return None;
     };
     let body = cx.tcx.hir_body(body_id);
-    let [input] = body.params else { return None };
-    let PatKind::Binding(.., self_ident, None) = input.pat.kind else {
+    let [self_param] = body.params else { return None };
+    let PatKind::Binding(.., self_ident, None) = self_param.pat.kind else {
         return None;
     };
 
@@ -194,12 +194,12 @@ fn convert_to_from(
         // impl Into<T> for U  ->  impl Into<T> for T
         //                  ~                       ~
         (self_ty.span, into.to_owned()),
-        // fn into(self) -> T  ->  fn from(self) -> T
-        //    ~~~~                    ~~~~
+        // fn into(self: U) -> T  ->  fn from(self) -> T
+        //    ~~~~                       ~~~~
         (impl_item.ident.span, String::from("from")),
-        // fn into([mut] self) -> T  ->  fn into([mut] v: T) -> T
-        //               ~~~~                          ~~~~
-        (self_ident.span, format!("val: {from}")),
+        // fn into([mut] self: U) -> T  ->  fn into([mut] val: T) -> T
+        //               ~~~~~~~                          ~~~~~~
+        (self_ident.span.to(self_param.ty_span), format!("val: {from}")),
     ];
 
     if let FnRetTy::Return(_) = sig.decl.output {
diff --git a/tests/ui/from_over_into.fixed b/tests/ui/from_over_into.fixed
index 7d6780a0e02..7229e5a2d35 100644
--- a/tests/ui/from_over_into.fixed
+++ b/tests/ui/from_over_into.fixed
@@ -105,4 +105,15 @@ fn issue_12138() {
     }
 }
 
+fn issue_112502() {
+    struct MyInt(i64);
+
+    impl From<MyInt> for i64 {
+        //~^ from_over_into
+        fn from(val: MyInt) -> Self {
+            val.0
+        }
+    }
+}
+
 fn main() {}
diff --git a/tests/ui/from_over_into.rs b/tests/ui/from_over_into.rs
index 387ddde359c..9c75969c5c1 100644
--- a/tests/ui/from_over_into.rs
+++ b/tests/ui/from_over_into.rs
@@ -105,4 +105,15 @@ fn issue_12138() {
     }
 }
 
+fn issue_112502() {
+    struct MyInt(i64);
+
+    impl Into<i64> for MyInt {
+        //~^ from_over_into
+        fn into(self: MyInt) -> i64 {
+            self.0
+        }
+    }
+}
+
 fn main() {}
diff --git a/tests/ui/from_over_into.stderr b/tests/ui/from_over_into.stderr
index a564bccbaf7..fe779544dd5 100644
--- a/tests/ui/from_over_into.stderr
+++ b/tests/ui/from_over_into.stderr
@@ -107,5 +107,21 @@ LL |
 LL ~         fn from(val: Hello) {}
    |
 
-error: aborting due to 7 previous errors
+error: an implementation of `From` is preferred since it gives you `Into<_>` for free where the reverse isn't true
+  --> tests/ui/from_over_into.rs:111:5
+   |
+LL |     impl Into<i64> for MyInt {
+   |     ^^^^^^^^^^^^^^^^^^^^^^^^
+   |
+   = help: `impl From<Local> for Foreign` is allowed by the orphan rules, for more information see
+           https://doc.rust-lang.org/reference/items/implementations.html#trait-implementation-coherence
+help: replace the `Into` implementation with `From<issue_112502::MyInt>`
+   |
+LL ~     impl From<MyInt> for i64 {
+LL |
+LL ~         fn from(val: MyInt) -> Self {
+LL ~             val.0
+   |
+
+error: aborting due to 8 previous errors