Skip to content

Commit 0589cd0

Browse files
committed
mir opt: fix subtype handling
1 parent 46af169 commit 0589cd0

File tree

2 files changed

+20
-0
lines changed

2 files changed

+20
-0
lines changed

compiler/rustc_mir_transform/src/dest_prop.rs

+13
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,10 @@
3737
//! if they do not consistently refer to the same place in memory. This is satisfied if they do
3838
//! not contain any indirection through a pointer or any indexing projections.
3939
//!
40+
//! * `p` and `q` must have the **same type**. If we replace a local with a subtype or supertype,
41+
//! we may end up with a differnet vtable for that local. See the `subtyping-impacts-selection`
42+
//! tests for an example where that causes issues.
43+
//!
4044
//! * We need to make sure that the goal of "merging the memory" is actually structurally possible
4145
//! in MIR. For example, even if all the other conditions are satisfied, there is no way to
4246
//! "merge" `_5.foo` and `_6.bar`. For now, we ensure this by requiring that both `p` and `q` are
@@ -134,6 +138,7 @@ use crate::MirPass;
134138
use rustc_data_structures::fx::FxHashMap;
135139
use rustc_index::bit_set::BitSet;
136140
use rustc_middle::mir::visit::{MutVisitor, PlaceContext, Visitor};
141+
use rustc_middle::mir::HasLocalDecls;
137142
use rustc_middle::mir::{dump_mir, PassWhere};
138143
use rustc_middle::mir::{
139144
traversal, Body, InlineAsmOperand, Local, LocalKind, Location, Operand, Place, Rvalue,
@@ -769,6 +774,14 @@ impl<'tcx> Visitor<'tcx> for FindAssignments<'_, '_, 'tcx> {
769774
return;
770775
}
771776

777+
// As described at the top of this file, we do not touch locals which have different types.
778+
let src_ty = self.body.local_decls()[src].ty;
779+
let dest_ty = self.body.local_decls()[dest].ty;
780+
if src_ty != dest_ty {
781+
trace!("skipped `{src:?} = {dest:?}` due to subtyping: {src_ty} != {dest_ty}");
782+
return;
783+
}
784+
772785
// Also, we need to make sure that MIR actually allows the `src` to be removed
773786
if is_local_required(src, self.body) {
774787
return;

compiler/rustc_mir_transform/src/ssa.rs

+7
Original file line numberDiff line numberDiff line change
@@ -271,6 +271,13 @@ fn compute_copy_classes(ssa: &mut SsaLocals, body: &Body<'_>) {
271271
else { continue };
272272

273273
let Some(rhs) = place.as_local() else { continue };
274+
let local_ty = body.local_decls()[local].ty;
275+
let rhs_ty = body.local_decls()[rhs].ty;
276+
if local_ty != rhs_ty {
277+
trace!("skipped `{local:?} = {rhs:?}` due to subtyping: {local_ty} != {rhs_ty}");
278+
continue;
279+
}
280+
274281
if !ssa.is_ssa(rhs) {
275282
continue;
276283
}

0 commit comments

Comments
 (0)