Revert PR #114052 to fix invalid suggestion

This commit is contained in:
Urgau 2023-08-17 14:09:32 +02:00
parent aa864a7622
commit 1c73248b67
9 changed files with 73 additions and 61 deletions

View File

@ -53,7 +53,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
|| self.suggest_no_capture_closure(err, expected, expr_ty) || self.suggest_no_capture_closure(err, expected, expr_ty)
|| self.suggest_boxing_when_appropriate(err, expr.span, expr.hir_id, expected, expr_ty) || self.suggest_boxing_when_appropriate(err, expr.span, expr.hir_id, expected, expr_ty)
|| self.suggest_block_to_brackets_peeling_refs(err, expr, expr_ty, expected) || self.suggest_block_to_brackets_peeling_refs(err, expr, expr_ty, expected)
|| self.suggest_copied_cloned_or_as_ref(err, expr, expr_ty, expected, expected_ty_expr) || self.suggest_copied_cloned_or_as_ref(err, expr, expr_ty, expected)
|| self.suggest_clone_for_ref(err, expr, expr_ty, expected) || self.suggest_clone_for_ref(err, expr, expr_ty, expected)
|| self.suggest_into(err, expr, expr_ty, expected) || self.suggest_into(err, expr, expr_ty, expected)
|| self.suggest_floating_point_literal(err, expr, expected) || self.suggest_floating_point_literal(err, expr, expected)

View File

@ -253,7 +253,7 @@ impl HelpUseLatestEdition {
} }
#[derive(Subdiagnostic)] #[derive(Subdiagnostic)]
pub enum OptionResultRefMismatch<'tcx> { pub enum OptionResultRefMismatch {
#[suggestion( #[suggestion(
hir_typeck_option_result_copied, hir_typeck_option_result_copied,
code = ".copied()", code = ".copied()",
@ -276,19 +276,20 @@ pub enum OptionResultRefMismatch<'tcx> {
span: Span, span: Span,
def_path: String, def_path: String,
}, },
#[suggestion( // FIXME: #114050
hir_typeck_option_result_asref, // #[suggestion(
code = ".as_ref()", // hir_typeck_option_result_asref,
style = "verbose", // code = ".as_ref()",
applicability = "machine-applicable" // style = "verbose",
)] // applicability = "machine-applicable"
AsRef { // )]
#[primary_span] // AsRef {
span: Span, // #[primary_span]
def_path: String, // span: Span,
expected_ty: Ty<'tcx>, // def_path: String,
expr_ty: Ty<'tcx>, // expected_ty: Ty<'tcx>,
}, // expr_ty: Ty<'tcx>,
// },
} }
#[derive(Diagnostic)] #[derive(Diagnostic)]

View File

@ -1097,7 +1097,6 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
expr: &hir::Expr<'_>, expr: &hir::Expr<'_>,
expr_ty: Ty<'tcx>, expr_ty: Ty<'tcx>,
expected_ty: Ty<'tcx>, expected_ty: Ty<'tcx>,
expected_ty_expr: Option<&'tcx hir::Expr<'tcx>>,
) -> bool { ) -> bool {
let ty::Adt(adt_def, args) = expr_ty.kind() else { let ty::Adt(adt_def, args) = expr_ty.kind() else {
return false; return false;
@ -1115,7 +1114,7 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
{ {
let expr_inner_ty = args.type_at(0); let expr_inner_ty = args.type_at(0);
let expected_inner_ty = expected_args.type_at(0); let expected_inner_ty = expected_args.type_at(0);
if let &ty::Ref(_, ty, mutability) = expr_inner_ty.kind() if let &ty::Ref(_, ty, _mutability) = expr_inner_ty.kind()
&& self.can_eq(self.param_env, ty, expected_inner_ty) && self.can_eq(self.param_env, ty, expected_inner_ty)
{ {
let def_path = self.tcx.def_path_str(adt_def.did()); let def_path = self.tcx.def_path_str(adt_def.did());
@ -1124,14 +1123,6 @@ impl<'a, 'tcx> FnCtxt<'a, 'tcx> {
errors::OptionResultRefMismatch::Copied { errors::OptionResultRefMismatch::Copied {
span, def_path span, def_path
} }
} else if let Some(expected_ty_expr) = expected_ty_expr
// FIXME: suggest changes to both expressions to convert both to
// Option/Result<&T>
&& mutability.is_not()
{
errors::OptionResultRefMismatch::AsRef {
span: expected_ty_expr.span.shrink_to_hi(), expected_ty, expr_ty, def_path
}
} else if let Some(clone_did) = self.tcx.lang_items().clone_trait() } else if let Some(clone_did) = self.tcx.lang_items().clone_trait()
&& rustc_trait_selection::traits::type_known_to_meet_bound_modulo_regions( && rustc_trait_selection::traits::type_known_to_meet_bound_modulo_regions(
self, self,

View File

@ -1,13 +0,0 @@
// run-rustfix
use std::fmt::Debug;
pub fn foo<I: Iterator>(mut iter: I, value: &I::Item)
where
I::Item: Eq + Debug,
{
debug_assert_eq!(iter.next().as_ref(), Some(value));
//~^ ERROR mismatched types
}
fn main() {}

View File

@ -1,5 +1,3 @@
// run-rustfix
use std::fmt::Debug; use std::fmt::Debug;
pub fn foo<I: Iterator>(mut iter: I, value: &I::Item) pub fn foo<I: Iterator>(mut iter: I, value: &I::Item)

View File

@ -1,15 +1,11 @@
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/dont-suggest-cyclic-constraint.rs:9:35 --> $DIR/dont-suggest-cyclic-constraint.rs:7:35
| |
LL | debug_assert_eq!(iter.next(), Some(value)); LL | debug_assert_eq!(iter.next(), Some(value));
| ^^^^^^^^^^^ expected `Option<<I as Iterator>::Item>`, found `Option<&<I as Iterator>::Item>` | ^^^^^^^^^^^ expected `Option<<I as Iterator>::Item>`, found `Option<&<I as Iterator>::Item>`
| |
= note: expected enum `Option<<I as Iterator>::Item>` = note: expected enum `Option<<I as Iterator>::Item>`
found enum `Option<&<I as Iterator>::Item>` found enum `Option<&<I as Iterator>::Item>`
help: use `Option::as_ref` to convert `Option<<I as Iterator>::Item>` to `Option<&<I as Iterator>::Item>`
|
LL | debug_assert_eq!(iter.next().as_ref(), Some(value));
| +++++++++
error: aborting due to previous error error: aborting due to previous error

View File

@ -2,6 +2,16 @@
fn expect<T>(_: T) {} fn expect<T>(_: T) {}
struct Issue114925 {
x: Option<String>,
}
fn issue_114925(lol: &mut Issue114925, x: Option<&String>) {
lol.x = x.clone().cloned();
//~^ ERROR mismatched types
//~| HELP use `Option::cloned` to clone the value inside the `Option`
}
fn main() { fn main() {
let x = Some(&()); let x = Some(&());
expect::<Option<()>>(x.copied()); expect::<Option<()>>(x.copied());
@ -24,10 +34,10 @@ fn main() {
let s = String::new(); let s = String::new();
let x = Some(s.clone()); let x = Some(s.clone());
let y = Some(&s); let y = Some(&s);
println!("{}", x.as_ref() == y); println!("{}", x == y.cloned());
//~^ ERROR mismatched types //~^ ERROR mismatched types
//~| HELP use `Option::as_ref` to convert `Option<String>` to `Option<&String>` //~| HELP use `Option::cloned` to clone the value inside the `Option`
//FIXME(#114050) ~| HELP use `Option::as_ref` to convert `Option<String>` to `Option<&String>`
let mut s = (); let mut s = ();
let x = Some(s); let x = Some(s);
@ -42,4 +52,6 @@ fn main() {
println!("{}", x == y.cloned()); println!("{}", x == y.cloned());
//~^ ERROR mismatched types //~^ ERROR mismatched types
//~| HELP use `Option::cloned` to clone the value inside the `Option` //~| HELP use `Option::cloned` to clone the value inside the `Option`
issue_114925(&mut Issue114925 { x: None }, None);
} }

View File

@ -2,6 +2,16 @@
fn expect<T>(_: T) {} fn expect<T>(_: T) {}
struct Issue114925 {
x: Option<String>,
}
fn issue_114925(lol: &mut Issue114925, x: Option<&String>) {
lol.x = x.clone();
//~^ ERROR mismatched types
//~| HELP use `Option::cloned` to clone the value inside the `Option`
}
fn main() { fn main() {
let x = Some(&()); let x = Some(&());
expect::<Option<()>>(x); expect::<Option<()>>(x);
@ -26,8 +36,8 @@ fn main() {
let y = Some(&s); let y = Some(&s);
println!("{}", x == y); println!("{}", x == y);
//~^ ERROR mismatched types //~^ ERROR mismatched types
//~| HELP use `Option::as_ref` to convert `Option<String>` to `Option<&String>` //~| HELP use `Option::cloned` to clone the value inside the `Option`
//FIXME(#114050) ~| HELP use `Option::as_ref` to convert `Option<String>` to `Option<&String>`
let mut s = (); let mut s = ();
let x = Some(s); let x = Some(s);
@ -42,4 +52,6 @@ fn main() {
println!("{}", x == y); println!("{}", x == y);
//~^ ERROR mismatched types //~^ ERROR mismatched types
//~| HELP use `Option::cloned` to clone the value inside the `Option` //~| HELP use `Option::cloned` to clone the value inside the `Option`
issue_114925(&mut Issue114925 { x: None }, None);
} }

View File

@ -1,5 +1,20 @@
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:7:26 --> $DIR/copied-and-cloned.rs:10:13
|
LL | lol.x = x.clone();
| ----- ^^^^^^^^^ expected `Option<String>`, found `Option<&String>`
| |
| expected due to the type of this binding
|
= note: expected enum `Option<String>`
found enum `Option<&String>`
help: use `Option::cloned` to clone the value inside the `Option`
|
LL | lol.x = x.clone().cloned();
| +++++++++
error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:17:26
| |
LL | expect::<Option<()>>(x); LL | expect::<Option<()>>(x);
| -------------------- ^ expected `Option<()>`, found `Option<&()>` | -------------------- ^ expected `Option<()>`, found `Option<&()>`
@ -19,7 +34,7 @@ LL | expect::<Option<()>>(x.copied());
| +++++++++ | +++++++++
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:11:30 --> $DIR/copied-and-cloned.rs:21:30
| |
LL | expect::<Result<(), ()>>(x); LL | expect::<Result<(), ()>>(x);
| ------------------------ ^ expected `Result<(), ()>`, found `Result<&(), _>` | ------------------------ ^ expected `Result<(), ()>`, found `Result<&(), _>`
@ -39,7 +54,7 @@ LL | expect::<Result<(), ()>>(x.copied());
| +++++++++ | +++++++++
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:16:30 --> $DIR/copied-and-cloned.rs:26:30
| |
LL | expect::<Option<String>>(x); LL | expect::<Option<String>>(x);
| ------------------------ ^ expected `Option<String>`, found `Option<&String>` | ------------------------ ^ expected `Option<String>`, found `Option<&String>`
@ -59,7 +74,7 @@ LL | expect::<Option<String>>(x.cloned());
| +++++++++ | +++++++++
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:20:34 --> $DIR/copied-and-cloned.rs:30:34
| |
LL | expect::<Result<String, ()>>(x); LL | expect::<Result<String, ()>>(x);
| ---------------------------- ^ expected `Result<String, ()>`, found `Result<&String, _>` | ---------------------------- ^ expected `Result<String, ()>`, found `Result<&String, _>`
@ -79,20 +94,20 @@ LL | expect::<Result<String, ()>>(x.cloned());
| +++++++++ | +++++++++
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:27:25 --> $DIR/copied-and-cloned.rs:37:25
| |
LL | println!("{}", x == y); LL | println!("{}", x == y);
| ^ expected `Option<String>`, found `Option<&String>` | ^ expected `Option<String>`, found `Option<&String>`
| |
= note: expected enum `Option<String>` = note: expected enum `Option<String>`
found enum `Option<&String>` found enum `Option<&String>`
help: use `Option::as_ref` to convert `Option<String>` to `Option<&String>` help: use `Option::cloned` to clone the value inside the `Option`
| |
LL | println!("{}", x.as_ref() == y); LL | println!("{}", x == y.cloned());
| +++++++++ | +++++++++
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:35:25 --> $DIR/copied-and-cloned.rs:45:25
| |
LL | println!("{}", x == y); LL | println!("{}", x == y);
| ^ expected `Option<()>`, found `Option<&mut ()>` | ^ expected `Option<()>`, found `Option<&mut ()>`
@ -105,7 +120,7 @@ LL | println!("{}", x == y.copied());
| +++++++++ | +++++++++
error[E0308]: mismatched types error[E0308]: mismatched types
--> $DIR/copied-and-cloned.rs:42:25 --> $DIR/copied-and-cloned.rs:52:25
| |
LL | println!("{}", x == y); LL | println!("{}", x == y);
| ^ expected `Option<String>`, found `Option<&mut String>` | ^ expected `Option<String>`, found `Option<&mut String>`
@ -117,6 +132,6 @@ help: use `Option::cloned` to clone the value inside the `Option`
LL | println!("{}", x == y.cloned()); LL | println!("{}", x == y.cloned());
| +++++++++ | +++++++++
error: aborting due to 7 previous errors error: aborting due to 8 previous errors
For more information about this error, try `rustc --explain E0308`. For more information about this error, try `rustc --explain E0308`.