diff --git a/src/librustc_typeck/coherence/builtin.rs b/src/librustc_typeck/coherence/builtin.rs index e5a52a1f6ac6..99c6ba457faa 100644 --- a/src/librustc_typeck/coherence/builtin.rs +++ b/src/librustc_typeck/coherence/builtin.rs @@ -223,6 +223,13 @@ fn visit_implementation_of_dispatch_from_dyn<'a, 'tcx>( return } + if def_a.repr.c() || def_a.repr.packed() { + create_err( + "structs implementing `DispatchFromDyn` may not have \ + `#[repr(packed)]` or `#[repr(C)]`" + ).emit(); + } + let fields = &def_a.non_enum_variant().fields; let coerced_fields = fields.iter().filter_map(|field| { diff --git a/src/test/ui/invalid_dispatch_from_dyn_impls.rs b/src/test/ui/invalid_dispatch_from_dyn_impls.rs index 101e1eb6e307..1cf5c73ab138 100644 --- a/src/test/ui/invalid_dispatch_from_dyn_impls.rs +++ b/src/test/ui/invalid_dispatch_from_dyn_impls.rs @@ -41,4 +41,12 @@ struct NothingToCoerce { impl DispatchFromDyn> for NothingToCoerce {} //~^ ERROR [E0378] +#[repr(C)] +struct HasReprC(Box); + +impl DispatchFromDyn> for HasReprC +where + T: Unsize, +{} //~^^^ ERROR [E0378] + fn main() {} diff --git a/src/test/ui/invalid_dispatch_from_dyn_impls.stderr b/src/test/ui/invalid_dispatch_from_dyn_impls.stderr index f4affb855146..82186b67d97f 100644 --- a/src/test/ui/invalid_dispatch_from_dyn_impls.stderr +++ b/src/test/ui/invalid_dispatch_from_dyn_impls.stderr @@ -27,6 +27,15 @@ error[E0378]: the trait `DispatchFromDyn` may only be implemented for a coercion LL | impl DispatchFromDyn> for NothingToCoerce {} | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -error: aborting due to 3 previous errors +error[E0378]: structs implementing `DispatchFromDyn` may not have `#[repr(packed)]` or `#[repr(C)]` + --> $DIR/invalid_dispatch_from_dyn_impls.rs:47:1 + | +LL | / impl DispatchFromDyn> for HasReprC +LL | | where +LL | | T: Unsize, +LL | | {} //~^^^ ERROR [E0378] + | |__^ + +error: aborting due to 4 previous errors For more information about this error, try `rustc --explain E0378`.