From 1f463ac40735529abd7343bb8a12a1888bb623df Mon Sep 17 00:00:00 2001 From: Michael Goulet Date: Thu, 4 Aug 2022 03:05:57 +0000 Subject: [PATCH] Resolve vars before emitting coerce error --- compiler/rustc_typeck/src/check/coercion.rs | 3 +- src/test/ui/expr/if/if-branch-types.stderr | 5 ++ .../ui/expr/if/if-else-type-mismatch.stderr | 10 +++ .../type-mismatch-signature-deduction.stderr | 6 ++ src/test/ui/impl-trait/equality.stderr | 7 +- ...trait-in-return-position-impl-trait.stderr | 4 +- ...type-err-cause-on-impl-trait-return.stderr | 67 +++++++++++++++++-- .../dont-point-return-on-E0308.stderr | 2 +- .../ui/mismatched_types/issue-84976.stderr | 5 ++ src/test/ui/reify-intrinsic.stderr | 3 + .../type-alias-impl-trait/issue-74280.stderr | 2 +- 11 files changed, 102 insertions(+), 12 deletions(-) diff --git a/compiler/rustc_typeck/src/check/coercion.rs b/compiler/rustc_typeck/src/check/coercion.rs index b75a2f3edd9..b659eab5ca4 100644 --- a/compiler/rustc_typeck/src/check/coercion.rs +++ b/compiler/rustc_typeck/src/check/coercion.rs @@ -1478,6 +1478,7 @@ pub(crate) fn coerce_inner<'a>( // type) (self.final_ty.unwrap_or(self.expected_ty), expression_ty) }; + let (expected, found) = fcx.resolve_vars_if_possible((expected, found)); let mut err; let mut unsized_return = false; @@ -1663,7 +1664,7 @@ fn report_return_mismatched_types<'a>( sp, &format!( "return type inferred to be `{}` here", - fcx.resolve_vars_if_possible(expected) + expected ), ); } diff --git a/src/test/ui/expr/if/if-branch-types.stderr b/src/test/ui/expr/if/if-branch-types.stderr index 14f02163a83..d2bba88211e 100644 --- a/src/test/ui/expr/if/if-branch-types.stderr +++ b/src/test/ui/expr/if/if-branch-types.stderr @@ -5,6 +5,11 @@ LL | let x = if true { 10i32 } else { 10u32 }; | ----- ^^^^^ expected `i32`, found `u32` | | | expected because of this + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | let x = if true { 10i32 } else { 10i32 }; + | ~~~ error: aborting due to previous error diff --git a/src/test/ui/expr/if/if-else-type-mismatch.stderr b/src/test/ui/expr/if/if-else-type-mismatch.stderr index 9fa190d6c9d..f1fffdb1e7e 100644 --- a/src/test/ui/expr/if/if-else-type-mismatch.stderr +++ b/src/test/ui/expr/if/if-else-type-mismatch.stderr @@ -10,6 +10,11 @@ LL | | 2u32 | | ^^^^ expected `i32`, found `u32` LL | | }; | |_____- `if` and `else` have incompatible types + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 2i32 + | ~~~ error[E0308]: `if` and `else` have incompatible types --> $DIR/if-else-type-mismatch.rs:8:38 @@ -18,6 +23,11 @@ LL | let _ = if true { 42i32 } else { 42u32 }; | ----- ^^^^^ expected `i32`, found `u32` | | | expected because of this + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | let _ = if true { 42i32 } else { 42i32 }; + | ~~~ error[E0308]: `if` and `else` have incompatible types --> $DIR/if-else-type-mismatch.rs:13:9 diff --git a/src/test/ui/generator/type-mismatch-signature-deduction.stderr b/src/test/ui/generator/type-mismatch-signature-deduction.stderr index 7938fc8097c..b98da1ed8be 100644 --- a/src/test/ui/generator/type-mismatch-signature-deduction.stderr +++ b/src/test/ui/generator/type-mismatch-signature-deduction.stderr @@ -11,6 +11,12 @@ note: return type inferred to be `Result<{integer}, _>` here | LL | return Ok(6); | ^^^^^ +help: try wrapping the expression in a variant of `Result` + | +LL | Ok(5) + | +++ + +LL | Err(5) + | ++++ + error[E0271]: type mismatch resolving `<[generator@$DIR/type-mismatch-signature-deduction.rs:7:5: 7:7] as Generator>::Return == i32` --> $DIR/type-mismatch-signature-deduction.rs:5:13 diff --git a/src/test/ui/impl-trait/equality.stderr b/src/test/ui/impl-trait/equality.stderr index f14b447b077..d4a3495515c 100644 --- a/src/test/ui/impl-trait/equality.stderr +++ b/src/test/ui/impl-trait/equality.stderr @@ -12,10 +12,15 @@ error[E0308]: mismatched types --> $DIR/equality.rs:15:5 | LL | fn two(x: bool) -> impl Foo { - | -------- expected `_` because of return type + | -------- expected `i32` because of return type ... LL | 0_u32 | ^^^^^ expected `i32`, found `u32` + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 0_i32 + | ~~~ error[E0277]: cannot add `impl Foo` to `u32` --> $DIR/equality.rs:24:11 diff --git a/src/test/ui/impl-trait/object-unsafe-trait-in-return-position-impl-trait.stderr b/src/test/ui/impl-trait/object-unsafe-trait-in-return-position-impl-trait.stderr index 5ca01a59376..d6f5a1ac25b 100644 --- a/src/test/ui/impl-trait/object-unsafe-trait-in-return-position-impl-trait.stderr +++ b/src/test/ui/impl-trait/object-unsafe-trait-in-return-position-impl-trait.stderr @@ -2,7 +2,7 @@ error[E0308]: mismatched types --> $DIR/object-unsafe-trait-in-return-position-impl-trait.rs:36:5 | LL | fn can() -> impl NotObjectSafe { - | ------------------ expected `_` because of return type + | ------------------ expected `A` because of return type ... LL | B | ^ expected struct `A`, found struct `B` @@ -11,7 +11,7 @@ error[E0308]: mismatched types --> $DIR/object-unsafe-trait-in-return-position-impl-trait.rs:43:5 | LL | fn cat() -> impl ObjectSafe { - | --------------- expected `_` because of return type + | --------------- expected `A` because of return type ... LL | B | ^ expected struct `A`, found struct `B` diff --git a/src/test/ui/impl-trait/point-to-type-err-cause-on-impl-trait-return.stderr b/src/test/ui/impl-trait/point-to-type-err-cause-on-impl-trait-return.stderr index 10510c1754e..11c1072f02c 100644 --- a/src/test/ui/impl-trait/point-to-type-err-cause-on-impl-trait-return.stderr +++ b/src/test/ui/impl-trait/point-to-type-err-cause-on-impl-trait-return.stderr @@ -2,28 +2,43 @@ error[E0308]: mismatched types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:5:5 | LL | fn foo() -> impl std::fmt::Display { - | ---------------------- expected `_` because of return type + | ---------------------- expected `i32` because of return type ... LL | 1u32 | ^^^^ expected `i32`, found `u32` + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 1i32 + | ~~~ error[E0308]: mismatched types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:12:16 | LL | fn bar() -> impl std::fmt::Display { - | ---------------------- expected `_` because of return type + | ---------------------- expected `i32` because of return type ... LL | return 1u32; | ^^^^ expected `i32`, found `u32` + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | return 1i32; + | ~~~ error[E0308]: mismatched types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:20:9 | LL | fn baz() -> impl std::fmt::Display { - | ---------------------- expected `_` because of return type + | ---------------------- expected `i32` because of return type ... LL | 1u32 | ^^^^ expected `i32`, found `u32` + | +help: you can convert a `u32` to an `i32` and panic if the converted value doesn't fit + | +LL | }.try_into().unwrap() + | ++++++++++++++++++++ error[E0308]: `if` and `else` have incompatible types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:28:9 @@ -36,36 +51,56 @@ LL | | 1u32 | | ^^^^ expected `i32`, found `u32` LL | | } | |_____- `if` and `else` have incompatible types + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 1i32 + | ~~~ error[E0308]: mismatched types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:35:14 | LL | fn bat() -> impl std::fmt::Display { - | ---------------------- expected `_` because of return type + | ---------------------- expected `i32` because of return type ... LL | _ => 1u32, | ^^^^ expected `i32`, found `u32` + | +help: you can convert a `u32` to an `i32` and panic if the converted value doesn't fit + | +LL | }.try_into().unwrap() + | ++++++++++++++++++++ error[E0308]: mismatched types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:40:5 | LL | fn can() -> impl std::fmt::Display { - | ---------------------- expected `_` because of return type + | ---------------------- expected `i32` because of return type LL | / match 13 { LL | | 0 => return 0i32, LL | | 1 => 1u32, LL | | _ => 2u32, LL | | } | |_____^ expected `i32`, found `u32` + | +help: you can convert a `u32` to an `i32` and panic if the converted value doesn't fit + | +LL | }.try_into().unwrap() + | ++++++++++++++++++++ error[E0308]: mismatched types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:53:13 | LL | fn cat() -> impl std::fmt::Display { - | ---------------------- expected `_` because of return type + | ---------------------- expected `i32` because of return type ... LL | 1u32 | ^^^^ expected `i32`, found `u32` + | +help: you can convert a `u32` to an `i32` and panic if the converted value doesn't fit + | +LL | }.try_into().unwrap() + | ++++++++++++++++++++ error[E0308]: `match` arms have incompatible types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:61:14 @@ -78,6 +113,11 @@ LL | | 1 => 1u32, LL | | _ => 2u32, LL | | } | |_____- `match` arms have incompatible types + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 1 => 1i32, + | ~~~ error[E0308]: `if` and `else` have incompatible types --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:97:9 @@ -90,6 +130,11 @@ LL | | 1u32 | | ^^^^ expected `i32`, found `u32` LL | | } | |_____- `if` and `else` have incompatible types + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 1i32 + | ~~~ error[E0746]: return type cannot have an unboxed trait object --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:66:13 @@ -125,6 +170,11 @@ LL | | 1 => 1u32, LL | | _ => 2u32, LL | | } | |_____- `match` arms have incompatible types + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 1 => 1i32, + | ~~~ error[E0746]: return type cannot have an unboxed trait object --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:77:13 @@ -164,6 +214,11 @@ LL | | 1u32 | | ^^^^ expected `i32`, found `u32` LL | | } | |_____- `if` and `else` have incompatible types + | +help: change the type of the numeric literal from `u32` to `i32` + | +LL | 1i32 + | ~~~ error[E0746]: return type cannot have an unboxed trait object --> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:85:13 diff --git a/src/test/ui/mismatched_types/dont-point-return-on-E0308.stderr b/src/test/ui/mismatched_types/dont-point-return-on-E0308.stderr index e79ab537b4c..13942682d28 100644 --- a/src/test/ui/mismatched_types/dont-point-return-on-E0308.stderr +++ b/src/test/ui/mismatched_types/dont-point-return-on-E0308.stderr @@ -1,5 +1,5 @@ error[E0308]: mismatched types - --> $DIR/dont-point-return-on-E0308.rs:10:11 + --> $DIR/dont-point-return-on-E0308.rs:11:11 | LL | f(()); | - ^^ diff --git a/src/test/ui/mismatched_types/issue-84976.stderr b/src/test/ui/mismatched_types/issue-84976.stderr index f8f2b1f0f57..9157566e3a7 100644 --- a/src/test/ui/mismatched_types/issue-84976.stderr +++ b/src/test/ui/mismatched_types/issue-84976.stderr @@ -3,6 +3,11 @@ error[E0308]: mismatched types | LL | length = { foo(&length) }; | ^^^^^^^^^^^^ expected `u32`, found `i32` + | +help: you can convert an `i32` to a `u32` and panic if the converted value doesn't fit + | +LL | length = { foo(&length).try_into().unwrap() }; + | ++++++++++++++++++++ error[E0308]: mismatched types --> $DIR/issue-84976.rs:17:14 diff --git a/src/test/ui/reify-intrinsic.stderr b/src/test/ui/reify-intrinsic.stderr index 360557fb520..f78f1d822bf 100644 --- a/src/test/ui/reify-intrinsic.stderr +++ b/src/test/ui/reify-intrinsic.stderr @@ -23,6 +23,9 @@ LL | std::intrinsics::unlikely, | = note: expected fn item `extern "rust-intrinsic" fn(_) -> _ {likely}` found fn item `extern "rust-intrinsic" fn(_) -> _ {unlikely}` + = note: different `fn` items always have unique types, even if their signatures are the same + = help: change the expected type to be function pointer `extern "rust-intrinsic" fn(bool) -> bool` + = help: if the expected type is due to type inference, cast the expected `fn` to a function pointer: `likely as extern "rust-intrinsic" fn(bool) -> bool` error: aborting due to 3 previous errors diff --git a/src/test/ui/type-alias-impl-trait/issue-74280.stderr b/src/test/ui/type-alias-impl-trait/issue-74280.stderr index 5ed29e0ac94..66886db6eb9 100644 --- a/src/test/ui/type-alias-impl-trait/issue-74280.stderr +++ b/src/test/ui/type-alias-impl-trait/issue-74280.stderr @@ -2,7 +2,7 @@ error[E0308]: mismatched types --> $DIR/issue-74280.rs:9:5 | LL | fn test() -> Test { - | ---- expected `_` because of return type + | ---- expected `()` because of return type LL | let y = || -> Test { () }; LL | 7 | ^ expected `()`, found integer