Skip to content

Commit c8ee337

Browse files
committed
Use structured suggestion for impl T to Box<dyn T>
1 parent d778203 commit c8ee337

File tree

4 files changed

+50
-34
lines changed

4 files changed

+50
-34
lines changed

compiler/rustc_typeck/src/check/coercion.rs

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
3838
use crate::astconv::AstConv;
3939
use crate::check::FnCtxt;
40-
use rustc_errors::{struct_span_err, DiagnosticBuilder};
40+
use rustc_errors::{struct_span_err, Applicability, DiagnosticBuilder};
4141
use rustc_hir as hir;
4242
use rustc_infer::infer::type_variable::{TypeVariableOrigin, TypeVariableOriginKind};
4343
use rustc_infer::infer::{Coercion, InferOk, InferResult};
@@ -1523,10 +1523,12 @@ impl<'tcx, 'exprs, E: AsCoercionSite> CoerceMany<'tcx, 'exprs, E> {
15231523
};
15241524
if has_impl {
15251525
if is_object_safe {
1526-
err.help(&format!(
1527-
"you can instead return a boxed trait object using `Box<dyn {}>`",
1528-
&snippet[5..]
1529-
));
1526+
err.span_suggestion_verbose(
1527+
return_sp,
1528+
"you could change the return type to be a boxed trait object",
1529+
format!("Box<dyn {}>", &snippet[5..]),
1530+
Applicability::MachineApplicable,
1531+
);
15301532
} else {
15311533
err.help(&format!(
15321534
"if the trait `{}` were object safe, you could return a boxed trait object",

src/test/ui/impl-trait/object-unsafe-trait-in-return-position-impl-trait.stderr

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,9 +30,12 @@ LL | B
3030
|
3131
= note: to return `impl Trait`, all returned values must be of the same type
3232
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
33-
= help: you can instead return a boxed trait object using `Box<dyn ObjectSafe>`
3433
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
3534
= help: alternatively, create a new `enum` with a variant for each returned type
35+
help: you could change the return type to be a boxed trait object
36+
|
37+
LL | fn cat() -> Box<dyn ObjectSafe> {
38+
| ^^^^^^^^^^^^^^^^^^^
3639

3740
error: aborting due to 2 previous errors
3841

src/test/ui/point-to-type-err-cause-on-impl-trait-return.rs

Lines changed: 9 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -2,48 +2,42 @@ fn foo() -> impl std::fmt::Display {
22
if false {
33
return 0i32;
44
}
5-
1u32
6-
//~^ ERROR mismatched types
5+
1u32 //~ ERROR mismatched types
76
}
87

98
fn bar() -> impl std::fmt::Display {
109
if false {
1110
return 0i32;
1211
} else {
13-
return 1u32;
14-
//~^ ERROR mismatched types
12+
return 1u32; //~ ERROR mismatched types
1513
}
1614
}
1715

1816
fn baz() -> impl std::fmt::Display {
1917
if false {
2018
return 0i32;
2119
} else {
22-
1u32
23-
//~^ ERROR mismatched types
20+
1u32 //~ ERROR mismatched types
2421
}
2522
}
2623

2724
fn qux() -> impl std::fmt::Display {
2825
if false {
2926
0i32
3027
} else {
31-
1u32
32-
//~^ ERROR `if` and `else` have incompatible types
28+
1u32 //~ ERROR `if` and `else` have incompatible types
3329
}
3430
}
3531

3632
fn bat() -> impl std::fmt::Display {
3733
match 13 {
3834
0 => return 0i32,
39-
_ => 1u32,
40-
//~^ ERROR mismatched types
35+
_ => 1u32, //~ ERROR mismatched types
4136
}
4237
}
4338

4439
fn can() -> impl std::fmt::Display {
45-
match 13 {
46-
//~^ ERROR mismatched types
40+
match 13 { //~ ERROR mismatched types
4741
0 => return 0i32,
4842
1 => 1u32,
4943
_ => 2u32,
@@ -56,8 +50,9 @@ fn cat() -> impl std::fmt::Display {
5650
return 0i32;
5751
}
5852
_ => {
59-
1u32
60-
//~^ ERROR mismatched types
53+
1u32 //~ ERROR mismatched types
54+
}
55+
}
6156
}
6257
}
6358
}

src/test/ui/point-to-type-err-cause-on-impl-trait-return.stderr

Lines changed: 30 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -12,12 +12,15 @@ LL | 1u32
1212
|
1313
= note: to return `impl Trait`, all returned values must be of the same type
1414
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
15-
= help: you can instead return a boxed trait object using `Box<dyn std::fmt::Display>`
1615
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
1716
= help: alternatively, create a new `enum` with a variant for each returned type
17+
help: you could change the return type to be a boxed trait object
18+
|
19+
LL | fn foo() -> Box<dyn std::fmt::Display> {
20+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
1821

1922
error[E0308]: mismatched types
20-
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:13:16
23+
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:12:16
2124
|
2225
LL | fn bar() -> impl std::fmt::Display {
2326
| ---------------------- expected because this return type...
@@ -30,12 +33,15 @@ LL | return 1u32;
3033
|
3134
= note: to return `impl Trait`, all returned values must be of the same type
3235
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
33-
= help: you can instead return a boxed trait object using `Box<dyn std::fmt::Display>`
3436
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
3537
= help: alternatively, create a new `enum` with a variant for each returned type
38+
help: you could change the return type to be a boxed trait object
39+
|
40+
LL | fn bar() -> Box<dyn std::fmt::Display> {
41+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
3642

3743
error[E0308]: mismatched types
38-
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:22:9
44+
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:20:9
3945
|
4046
LL | fn baz() -> impl std::fmt::Display {
4147
| ---------------------- expected because this return type...
@@ -48,25 +54,27 @@ LL | 1u32
4854
|
4955
= note: to return `impl Trait`, all returned values must be of the same type
5056
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
51-
= help: you can instead return a boxed trait object using `Box<dyn std::fmt::Display>`
5257
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
5358
= help: alternatively, create a new `enum` with a variant for each returned type
59+
help: you could change the return type to be a boxed trait object
60+
|
61+
LL | fn baz() -> Box<dyn std::fmt::Display> {
62+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
5463

5564
error[E0308]: `if` and `else` have incompatible types
56-
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:31:9
65+
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:28:9
5766
|
5867
LL | / if false {
5968
LL | | 0i32
6069
| | ---- expected because of this
6170
LL | | } else {
6271
LL | | 1u32
6372
| | ^^^^ expected `i32`, found `u32`
64-
LL | |
6573
LL | | }
6674
| |_____- `if` and `else` have incompatible types
6775

6876
error[E0308]: mismatched types
69-
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:39:14
77+
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:35:14
7078
|
7179
LL | fn bat() -> impl std::fmt::Display {
7280
| ---------------------- expected because this return type...
@@ -78,17 +86,19 @@ LL | _ => 1u32,
7886
|
7987
= note: to return `impl Trait`, all returned values must be of the same type
8088
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
81-
= help: you can instead return a boxed trait object using `Box<dyn std::fmt::Display>`
8289
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
8390
= help: alternatively, create a new `enum` with a variant for each returned type
91+
help: you could change the return type to be a boxed trait object
92+
|
93+
LL | fn bat() -> Box<dyn std::fmt::Display> {
94+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
8495

8596
error[E0308]: mismatched types
86-
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:45:5
97+
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:40:5
8798
|
8899
LL | fn can() -> impl std::fmt::Display {
89100
| ---------------------- expected because this return type...
90101
LL | / match 13 {
91-
LL | |
92102
LL | | 0 => return 0i32,
93103
| | ---- ...is found to be `i32` here
94104
LL | | 1 => 1u32,
@@ -98,12 +108,15 @@ LL | | }
98108
|
99109
= note: to return `impl Trait`, all returned values must be of the same type
100110
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
101-
= help: you can instead return a boxed trait object using `Box<dyn std::fmt::Display>`
102111
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
103112
= help: alternatively, create a new `enum` with a variant for each returned type
113+
help: you could change the return type to be a boxed trait object
114+
|
115+
LL | fn can() -> Box<dyn std::fmt::Display> {
116+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
104117

105118
error[E0308]: mismatched types
106-
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:59:13
119+
--> $DIR/point-to-type-err-cause-on-impl-trait-return.rs:53:13
107120
|
108121
LL | fn cat() -> impl std::fmt::Display {
109122
| ---------------------- expected because this return type...
@@ -116,9 +129,12 @@ LL | 1u32
116129
|
117130
= note: to return `impl Trait`, all returned values must be of the same type
118131
= note: for information on `impl Trait`, see <https://doc.rust-lang.org/book/ch10-02-traits.html#returning-types-that-implement-traits>
119-
= help: you can instead return a boxed trait object using `Box<dyn std::fmt::Display>`
120132
= note: for information on trait objects, see <https://doc.rust-lang.org/book/ch17-02-trait-objects.html#using-trait-objects-that-allow-for-values-of-different-types>
121133
= help: alternatively, create a new `enum` with a variant for each returned type
134+
help: you could change the return type to be a boxed trait object
135+
|
136+
LL | fn cat() -> Box<dyn std::fmt::Display> {
137+
| ^^^^^^^^^^^^^^^^^^^^^^^^^^
122138

123139
error: aborting due to 7 previous errors
124140

0 commit comments

Comments
 (0)