about summary refs log tree commit diff
path: root/compiler/rustc_hir_analysis
diff options
context:
space:
mode:
authorMichael Goulet <michael@errs.io>2025-01-08 00:28:47 +0000
committerMichael Goulet <michael@errs.io>2025-01-08 00:28:47 +0000
commit3c3186148e4a66a507e606f191c35ed49d873b08 (patch)
tree9ffe97bddbaed9c6bc1b684c75dfdda1f00b0e3c /compiler/rustc_hir_analysis
parentad211ced81509462cdfe4c29ed10f97279a0acae (diff)
downloadrust-3c3186148e4a66a507e606f191c35ed49d873b08.tar.gz
rust-3c3186148e4a66a507e606f191c35ed49d873b08.zip
Don't allow transmuting ZSTs in dispatch_from_dyn impl
Diffstat (limited to 'compiler/rustc_hir_analysis')
-rw-r--r--compiler/rustc_hir_analysis/messages.ftl2
-rw-r--r--compiler/rustc_hir_analysis/src/coherence/builtin.rs17
2 files changed, 14 insertions, 5 deletions
diff --git a/compiler/rustc_hir_analysis/messages.ftl b/compiler/rustc_hir_analysis/messages.ftl
index 0c3ed9b5c60..d7ab6eca84b 100644
--- a/compiler/rustc_hir_analysis/messages.ftl
+++ b/compiler/rustc_hir_analysis/messages.ftl
@@ -135,7 +135,7 @@ hir_analysis_dispatch_from_dyn_multi = implementing the `DispatchFromDyn` trait
 
 hir_analysis_dispatch_from_dyn_repr = structs implementing `DispatchFromDyn` may not have `#[repr(packed)]` or `#[repr(C)]`
 
-hir_analysis_dispatch_from_dyn_zst = the trait `DispatchFromDyn` may only be implemented for structs containing the field being coerced, ZST fields with 1 byte alignment, and nothing else
+hir_analysis_dispatch_from_dyn_zst = the trait `DispatchFromDyn` may only be implemented for structs containing the field being coerced, ZST fields with 1 byte alignment that don't mention type/const generics, and nothing else
     .note = extra field `{$name}` of type `{$ty}` is not allowed
 
 hir_analysis_drop_impl_negative = negative `Drop` impls are not supported
diff --git a/compiler/rustc_hir_analysis/src/coherence/builtin.rs b/compiler/rustc_hir_analysis/src/coherence/builtin.rs
index 3b98f358b1e..760c09a1e72 100644
--- a/compiler/rustc_hir_analysis/src/coherence/builtin.rs
+++ b/compiler/rustc_hir_analysis/src/coherence/builtin.rs
@@ -259,16 +259,25 @@ fn visit_implementation_of_dispatch_from_dyn(checker: &Checker<'_>) -> Result<()
             let coerced_fields = fields
                 .iter()
                 .filter(|field| {
+                    // Ignore PhantomData fields
+                    if tcx.type_of(field.did).instantiate_identity().is_phantom_data() {
+                        return false;
+                    }
+
                     let ty_a = field.ty(tcx, args_a);
                     let ty_b = field.ty(tcx, args_b);
 
+                    // Allow 1-ZSTs that don't mention type params.
+                    //
+                    // Allowing type params here would allow us to possibly transmute
+                    // between ZSTs, which may be used to create library unsoundness.
                     if let Ok(layout) =
                         tcx.layout_of(infcx.typing_env(param_env).as_query_input(ty_a))
+                        && layout.is_1zst()
+                        && !ty_a.has_non_region_param()
                     {
-                        if layout.is_1zst() {
-                            // ignore 1-ZST fields
-                            return false;
-                        }
+                        // ignore 1-ZST fields
+                        return false;
                     }
 
                     if ty_a == ty_b {