Skip to content

Commit bbc94ed

Browse files
authored
Rollup merge of #88525 - notriddle:notriddle/coherence-dyn-auto-trait, r=petrochenkov
fix(rustc_typeck): produce better errors for dyn auto trait Fixes #85026
2 parents 75b2ae5 + 6e70678 commit bbc94ed

File tree

5 files changed

+71
-0
lines changed

5 files changed

+71
-0
lines changed

compiler/rustc_error_codes/src/error_codes.rs

+1
Original file line numberDiff line numberDiff line change
@@ -480,6 +480,7 @@ E0781: include_str!("./error_codes/E0781.md"),
480480
E0782: include_str!("./error_codes/E0782.md"),
481481
E0783: include_str!("./error_codes/E0783.md"),
482482
E0784: include_str!("./error_codes/E0784.md"),
483+
E0785: include_str!("./error_codes/E0785.md"),
483484
;
484485
// E0006, // merged with E0005
485486
// E0008, // cannot bind by-move into a pattern guard
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
An inherent `impl` was written on a dyn auto trait.
2+
3+
Erroneous code example:
4+
5+
```compile_fail,E0785
6+
#![feature(auto_traits)]
7+
8+
auto trait AutoTrait {}
9+
10+
impl dyn AutoTrait {}
11+
```
12+
13+
Dyn objects allow any number of auto traits, plus at most one non-auto trait.
14+
The non-auto trait becomes the "principal trait".
15+
16+
When checking if an impl on a dyn trait is coherent, the principal trait is
17+
normally the only one considered. Since the erroneous code has no principal
18+
trait, it cannot be implemented at all.
19+
20+
Working example:
21+
22+
```
23+
#![feature(auto_traits)]
24+
25+
trait PrincipalTrait {}
26+
27+
auto trait AutoTrait {}
28+
29+
impl dyn PrincipalTrait + AutoTrait + Send {}
30+
```

compiler/rustc_typeck/src/coherence/inherent_impls.rs

+11
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,17 @@ impl ItemLikeVisitor<'v> for InherentCollect<'tcx> {
6060
ty::Dynamic(ref data, ..) if data.principal_def_id().is_some() => {
6161
self.check_def_id(item, data.principal_def_id().unwrap());
6262
}
63+
ty::Dynamic(..) => {
64+
struct_span_err!(
65+
self.tcx.sess,
66+
ty.span,
67+
E0785,
68+
"cannot define inherent `impl` for a dyn auto trait"
69+
)
70+
.span_label(ty.span, "impl requires at least one non-auto trait")
71+
.note("define and implement a new trait or type instead")
72+
.emit();
73+
}
6374
ty::Bool => {
6475
self.check_primitive_impl(
6576
item.def_id,

src/test/ui/coherence/issue-85026.rs

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
#![feature(auto_traits)]
2+
auto trait AutoTrait {}
3+
4+
// You cannot impl your own `dyn AutoTrait`.
5+
impl dyn AutoTrait {} //~ERROR E0785
6+
7+
// You cannot impl someone else's `dyn AutoTrait`
8+
impl dyn Unpin {} //~ERROR E0785
9+
10+
fn main() {}
+19
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
error[E0785]: cannot define inherent `impl` for a dyn auto trait
2+
--> $DIR/issue-85026.rs:5:6
3+
|
4+
LL | impl dyn AutoTrait {}
5+
| ^^^^^^^^^^^^^ impl requires at least one non-auto trait
6+
|
7+
= note: define and implement a new trait or type instead
8+
9+
error[E0785]: cannot define inherent `impl` for a dyn auto trait
10+
--> $DIR/issue-85026.rs:8:6
11+
|
12+
LL | impl dyn Unpin {}
13+
| ^^^^^^^^^ impl requires at least one non-auto trait
14+
|
15+
= note: define and implement a new trait or type instead
16+
17+
error: aborting due to 2 previous errors
18+
19+
For more information about this error, try `rustc --explain E0785`.

0 commit comments

Comments
 (0)