Skip to content

Commit

Permalink
Rollup merge of #91898 - compiler-errors:dont_suggest_closure_return_…
Browse files Browse the repository at this point in the history
…type, r=lcnr

Make `TyS::is_suggestable` check for non-suggestable types structually

Not sure if I went overboard checking substs in dyn types, etc. Let me know if I should simplify this function.

Fixes #91832
  • Loading branch information
matthiaskrgr authored Dec 15, 2021
2 parents 700670f + f29fb47 commit b507174
Show file tree
Hide file tree
Showing 30 changed files with 112 additions and 99 deletions.
64 changes: 54 additions & 10 deletions compiler/rustc_middle/src/ty/diagnostics.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,12 @@
//! Diagnostics related methods for `TyS`.

use crate::ty::subst::{GenericArg, GenericArgKind};
use crate::ty::TyKind::*;
use crate::ty::{InferTy, TyCtxt, TyS};
use crate::ty::{
ConstKind, ExistentialPredicate, ExistentialProjection, ExistentialTraitRef, InferTy,
ProjectionTy, TyCtxt, TyS, TypeAndMut,
};

use rustc_errors::{Applicability, DiagnosticBuilder};
use rustc_hir as hir;
use rustc_hir::def_id::DefId;
Expand Down Expand Up @@ -63,16 +68,55 @@ impl<'tcx> TyS<'tcx> {

/// Whether the type can be safely suggested during error recovery.
pub fn is_suggestable(&self) -> bool {
!matches!(
self.kind(),
fn generic_arg_is_suggestible(arg: GenericArg<'_>) -> bool {
match arg.unpack() {
GenericArgKind::Type(ty) => ty.is_suggestable(),
GenericArgKind::Const(c) => const_is_suggestable(c.val),
_ => true,
}
}

fn const_is_suggestable(kind: ConstKind<'_>) -> bool {
match kind {
ConstKind::Infer(..)
| ConstKind::Bound(..)
| ConstKind::Placeholder(..)
| ConstKind::Error(..) => false,
_ => true,
}
}

// FIXME(compiler-errors): Some types are still not good to suggest,
// specifically references with lifetimes within the function. Not
//sure we have enough information to resolve whether a region is
// temporary, so I'll leave this as a fixme.

match self.kind() {
Opaque(..)
| FnDef(..)
| FnPtr(..)
| Dynamic(..)
| Closure(..)
| Infer(..)
| Projection(..)
)
| FnDef(..)
| Closure(..)
| Infer(..)
| Generator(..)
| GeneratorWitness(..)
| Bound(_, _)
| Placeholder(_)
| Error(_) => false,
Dynamic(dty, _) => dty.iter().all(|pred| match pred.skip_binder() {
ExistentialPredicate::Trait(ExistentialTraitRef { substs, .. }) => {
substs.iter().all(generic_arg_is_suggestible)
}
ExistentialPredicate::Projection(ExistentialProjection { substs, ty, .. }) => {
ty.is_suggestable() && substs.iter().all(generic_arg_is_suggestible)
}
_ => true,
}),
Projection(ProjectionTy { substs: args, .. }) | Adt(_, args) | Tuple(args) => {
args.iter().all(generic_arg_is_suggestible)
}
Slice(ty) | RawPtr(TypeAndMut { ty, .. }) | Ref(_, ty, _) => ty.is_suggestable(),
Array(ty, c) => ty.is_suggestable() && const_is_suggestable(c.val),
_ => true,
}
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ trait Tr {
//~^ ERROR mismatched types
//~| NOTE expected associated type, found `()`
//~| NOTE expected associated type `<Self as Tr>::A`
//~| NOTE this expression has type `<Self as Tr>::A`
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,15 @@ LL | type A = ();
| ------------ associated type defaults can't be assumed inside the trait defining them
...
LL | let () = p;
| ^^ expected associated type, found `()`
| ^^ - this expression has type `<Self as Tr>::A`
| |
| expected associated type, found `()`
|
= note: expected associated type `<Self as Tr>::A`
found unit type `()`

error[E0308]: mismatched types
--> $DIR/defaults-in-other-trait-items.rs:35:25
--> $DIR/defaults-in-other-trait-items.rs:36:25
|
LL | type Ty = u8;
| ------------- associated type defaults can't be assumed inside the trait defining them
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,7 @@ error[E0308]: mismatched types
--> $DIR/default-match-bindings-forbidden.rs:6:5
|
LL | (x, y) = &(1, 2);
| ^^^^^^ ------- this expression has type `&({integer}, {integer})`
| |
| expected reference, found tuple
| ^^^^^^ expected reference, found tuple
|
= note: expected type `&({integer}, {integer})`
found tuple `(_, _)`
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,7 @@ error[E0308]: mismatched types
--> $DIR/tuple_destructure_fail.rs:8:5
|
LL | (a, a, b) = (1, 2);
| ^^^^^^^^^ ------ this expression has type `({integer}, {integer})`
| |
| expected a tuple with 2 elements, found one with 3 elements
| ^^^^^^^^^ expected a tuple with 2 elements, found one with 3 elements
|
= note: expected type `({integer}, {integer})`
found tuple `(_, _, _)`
Expand All @@ -29,9 +27,7 @@ error[E0308]: mismatched types
--> $DIR/tuple_destructure_fail.rs:10:5
|
LL | (_,) = (1, 2);
| ^^^^ ------ this expression has type `({integer}, {integer})`
| |
| expected a tuple with 2 elements, found one with 1 element
| ^^^^ expected a tuple with 2 elements, found one with 1 element
|
= note: expected type `({integer}, {integer})`
found tuple `(_,)`
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/exclusive_range_pattern_syntax_collision.rs:6:13
|
LL | match [5..4, 99..105, 43..44] {
| ----------------------- this expression has type `[std::ops::Range<{integer}>; 3]`
LL | [_, 99.., _] => {},
| ^^ expected struct `std::ops::Range`, found integer
|
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@ LL | [_, 99..] => {},
error[E0308]: mismatched types
--> $DIR/exclusive_range_pattern_syntax_collision2.rs:6:13
|
LL | match [5..4, 99..105, 43..44] {
| ----------------------- this expression has type `[std::ops::Range<{integer}>; 3]`
LL | [_, 99..] => {},
| ^^ expected struct `std::ops::Range`, found integer
|
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/exclusive_range_pattern_syntax_collision3.rs:6:12
|
LL | match [5..4, 99..105, 43..44] {
| ----------------------- this expression has type `[std::ops::Range<{integer}>; 3]`
LL | [..9, 99..100, _] => {},
| ^ expected struct `std::ops::Range`, found integer
|
Expand All @@ -12,8 +10,6 @@ LL | [..9, 99..100, _] => {},
error[E0308]: mismatched types
--> $DIR/exclusive_range_pattern_syntax_collision3.rs:6:15
|
LL | match [5..4, 99..105, 43..44] {
| ----------------------- this expression has type `[std::ops::Range<{integer}>; 3]`
LL | [..9, 99..100, _] => {},
| ^^ --- this is of type `{integer}`
| |
Expand All @@ -25,8 +21,6 @@ LL | [..9, 99..100, _] => {},
error[E0308]: mismatched types
--> $DIR/exclusive_range_pattern_syntax_collision3.rs:6:19
|
LL | match [5..4, 99..105, 43..44] {
| ----------------------- this expression has type `[std::ops::Range<{integer}>; 3]`
LL | [..9, 99..100, _] => {},
| -- ^^^ expected struct `std::ops::Range`, found integer
| |
Expand Down
2 changes: 0 additions & 2 deletions src/test/ui/half-open-range-patterns/pat-tuple-5.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/pat-tuple-5.rs:8:10
|
LL | match (0, 1) {
| ------ this expression has type `({integer}, {integer})`
LL | (PAT ..) => {}
| ^^^ expected tuple, found `u8`
|
Expand Down
2 changes: 0 additions & 2 deletions src/test/ui/issues/issue-11844.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/issue-11844.rs:6:9
|
LL | match a {
| - this expression has type `Option<Box<{integer}>>`
LL | Ok(a) =>
| ^^^^^ expected enum `Option`, found enum `Result`
|
Expand Down
5 changes: 0 additions & 5 deletions src/test/ui/issues/issue-12552.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/issue-12552.rs:6:5
|
LL | match t {
| - this expression has type `Result<_, {integer}>`
LL | Some(k) => match k {
| ^^^^^^^ expected enum `Result`, found enum `Option`
|
Expand All @@ -12,9 +10,6 @@ LL | Some(k) => match k {
error[E0308]: mismatched types
--> $DIR/issue-12552.rs:9:5
|
LL | match t {
| - this expression has type `Result<_, {integer}>`
...
LL | None => ()
| ^^^^ expected enum `Result`, found enum `Option`
|
Expand Down
5 changes: 0 additions & 5 deletions src/test/ui/issues/issue-13466.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/issue-13466.rs:8:9
|
LL | let _x: usize = match Some(1) {
| ------- this expression has type `Option<{integer}>`
LL | Ok(u) => u,
| ^^^^^ expected enum `Option`, found enum `Result`
|
Expand All @@ -12,9 +10,6 @@ LL | Ok(u) => u,
error[E0308]: mismatched types
--> $DIR/issue-13466.rs:14:9
|
LL | let _x: usize = match Some(1) {
| ------- this expression has type `Option<{integer}>`
...
LL | Err(e) => panic!(e)
| ^^^^^^ expected enum `Option`, found enum `Result`
|
Expand Down
2 changes: 0 additions & 2 deletions src/test/ui/issues/issue-3680.stderr
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
error[E0308]: mismatched types
--> $DIR/issue-3680.rs:3:9
|
LL | match None {
| ---- this expression has type `Option<_>`
LL | Err(_) => ()
| ^^^^^^ expected enum `Option`, found enum `Result`
|
Expand Down
6 changes: 3 additions & 3 deletions src/test/ui/issues/issue-66706.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -36,23 +36,23 @@ error[E0308]: mismatched types
--> $DIR/issue-66706.rs:2:5
|
LL | fn a() {
| - help: try adding a return type: `-> [{integer}; _]`
| - possibly return type missing here?
LL | [0; [|_: _ &_| ()].len()]
| ^^^^^^^^^^^^^^^^^^^^^^^^^ expected `()`, found array `[{integer}; _]`

error[E0308]: mismatched types
--> $DIR/issue-66706.rs:14:5
|
LL | fn c() {
| - help: try adding a return type: `-> [{integer}; _]`
| - possibly return type missing here?
LL | [0; [|&_: _ &_| {}; 0 ].len()]
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `()`, found array `[{integer}; _]`

error[E0308]: mismatched types
--> $DIR/issue-66706.rs:20:5
|
LL | fn d() {
| - help: try adding a return type: `-> [{integer}; _]`
| - possibly return type missing here?
LL | [0; match [|f @ &ref _| () ] {} ]
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ expected `()`, found array `[{integer}; _]`

Expand Down
2 changes: 0 additions & 2 deletions src/test/ui/issues/issue-72574-1.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,6 @@ LL | (_a, _x @ ..) => {}
error[E0308]: mismatched types
--> $DIR/issue-72574-1.rs:4:9
|
LL | match x {
| - this expression has type `({integer}, {integer}, {integer})`
LL | (_a, _x @ ..) => {}
| ^^^^^^^^^^^^^ expected a tuple with 3 elements, found one with 2 elements
|
Expand Down
2 changes: 0 additions & 2 deletions src/test/ui/mismatched_types/E0409.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,6 @@ LL | (0, ref y) | (y, 0) => {}
error[E0308]: mismatched types
--> $DIR/E0409.rs:5:23
|
LL | match x {
| - this expression has type `({integer}, {integer})`
LL | (0, ref y) | (y, 0) => {}
| ----- ^ expected `&{integer}`, found integer
| |
Expand Down
6 changes: 0 additions & 6 deletions src/test/ui/mut/mut-pattern-mismatched.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,6 @@ error[E0308]: mismatched types
|
LL | let &_
| ^^ types differ in mutability
...
LL | = foo;
| --- this expression has type `&mut {integer}`
|
= note: expected mutable reference `&mut {integer}`
found reference `&_`
Expand All @@ -15,9 +12,6 @@ error[E0308]: mismatched types
|
LL | let &mut _
| ^^^^^^ types differ in mutability
...
LL | = bar;
| --- this expression has type `&{integer}`
|
= note: expected reference `&{integer}`
found mutable reference `&mut _`
Expand Down
6 changes: 2 additions & 4 deletions src/test/ui/never_type/diverging-tuple-parts-39485.stderr
Original file line number Diff line number Diff line change
@@ -1,15 +1,13 @@
error[E0308]: mismatched types
--> $DIR/diverging-tuple-parts-39485.rs:8:5
|
LL | fn g() {
| - possibly return type missing here?
LL | &panic!()
| ^^^^^^^^^ expected `()`, found reference
|
= note: expected unit type `()`
found reference `&_`
help: try adding a return type
|
LL | fn g() -> &_ {
| +++++
help: consider removing the borrow
|
LL - &panic!()
Expand Down
5 changes: 2 additions & 3 deletions src/test/ui/or-patterns/already-bound-name.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -86,9 +86,8 @@ error[E0308]: mismatched types
--> $DIR/already-bound-name.rs:30:32
|
LL | let (B(A(a, _) | B(a)) | A(a, A(a, _) | B(a))) = B(B(1));
| - ^ ------- this expression has type `E<E<{integer}>>`
| | |
| | expected integer, found enum `E`
| - ^ expected integer, found enum `E`
| |
| first introduced with type `{integer}` here
|
= note: expected type `{integer}`
Expand Down
5 changes: 2 additions & 3 deletions src/test/ui/or-patterns/inconsistent-modes.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -65,9 +65,8 @@ error[E0308]: mismatched types
--> $DIR/inconsistent-modes.rs:13:32
|
LL | let (Ok((ref a, b)) | Err((ref mut a, ref b))) = Ok((0, &0));
| ----- ^^^^^^^^^ ----------- this expression has type `Result<({integer}, &{integer}), (_, _)>`
| | |
| | types differ in mutability
| ----- ^^^^^^^^^ types differ in mutability
| |
| first introduced with type `&{integer}` here
|
= note: expected type `&{integer}`
Expand Down
4 changes: 1 addition & 3 deletions src/test/ui/pattern/issue-74702.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,7 @@ error[E0308]: mismatched types
--> $DIR/issue-74702.rs:2:9
|
LL | let (foo @ ..,) = (0, 0);
| ^^^^^^^^^^^ ------ this expression has type `({integer}, {integer})`
| |
| expected a tuple with 2 elements, found one with 1 element
| ^^^^^^^^^^^ expected a tuple with 2 elements, found one with 1 element
|
= note: expected tuple `({integer}, {integer})`
found tuple `(_,)`
Expand Down
5 changes: 0 additions & 5 deletions src/test/ui/pattern/pat-tuple-overfield.stderr
Original file line number Diff line number Diff line change
Expand Up @@ -150,8 +150,6 @@ LL | E1::Z0 => {}
error[E0308]: mismatched types
--> $DIR/pat-tuple-overfield.rs:19:9
|
LL | match (1, 2, 3) {
| --------- this expression has type `({integer}, {integer}, {integer})`
LL | (1, 2, 3, 4) => {}
| ^^^^^^^^^^^^ expected a tuple with 3 elements, found one with 4 elements
|
Expand All @@ -161,9 +159,6 @@ LL | (1, 2, 3, 4) => {}
error[E0308]: mismatched types
--> $DIR/pat-tuple-overfield.rs:20:9
|
LL | match (1, 2, 3) {
| --------- this expression has type `({integer}, {integer}, {integer})`
LL | (1, 2, 3, 4) => {}
LL | (1, 2, .., 3, 4) => {}
| ^^^^^^^^^^^^^^^^ expected a tuple with 3 elements, found one with 4 elements
|
Expand Down
Loading

0 comments on commit b507174

Please sign in to comment.