diff options
| -rw-r--r-- | compiler/rustc_mir_transform/src/gvn.rs | 15 | ||||
| -rw-r--r-- | tests/mir-opt/gvn.dereference_indexing.GVN.panic-abort.diff | 3 | ||||
| -rw-r--r-- | tests/mir-opt/gvn.dereference_indexing.GVN.panic-unwind.diff | 3 |
3 files changed, 15 insertions, 6 deletions
diff --git a/compiler/rustc_mir_transform/src/gvn.rs b/compiler/rustc_mir_transform/src/gvn.rs index dc99b67a1e8..952da2cdf72 100644 --- a/compiler/rustc_mir_transform/src/gvn.rs +++ b/compiler/rustc_mir_transform/src/gvn.rs @@ -756,7 +756,13 @@ impl<'body, 'tcx> VnState<'body, 'tcx> { && let Some(v) = self.simplify_place_value(&mut pointee, location) { value = v; - place_ref = pointee.project_deeper(&place.projection[index..], self.tcx).as_ref(); + // `pointee` holds a `Place`, so `ProjectionElem::Index` holds a `Local`. + // That local is SSA, but we otherwise have no guarantee on that local's value at + // the current location compared to its value where `pointee` was borrowed. + if pointee.projection.iter().all(|elem| !matches!(elem, ProjectionElem::Index(_))) { + place_ref = + pointee.project_deeper(&place.projection[index..], self.tcx).as_ref(); + } } if let Some(local) = self.try_as_local(value, location) { // Both `local` and `Place { local: place.local, projection: projection[..index] }` @@ -774,7 +780,12 @@ impl<'body, 'tcx> VnState<'body, 'tcx> { && let Some(v) = self.simplify_place_value(&mut pointee, location) { value = v; - place_ref = pointee.project_deeper(&[], self.tcx).as_ref(); + // `pointee` holds a `Place`, so `ProjectionElem::Index` holds a `Local`. + // That local is SSA, but we otherwise have no guarantee on that local's value at + // the current location compared to its value where `pointee` was borrowed. + if pointee.projection.iter().all(|elem| !matches!(elem, ProjectionElem::Index(_))) { + place_ref = pointee.project_deeper(&[], self.tcx).as_ref(); + } } if let Some(new_local) = self.try_as_local(value, location) { place_ref = PlaceRef { local: new_local, projection: &[] }; diff --git a/tests/mir-opt/gvn.dereference_indexing.GVN.panic-abort.diff b/tests/mir-opt/gvn.dereference_indexing.GVN.panic-abort.diff index 1a07638cbaf..9bdcc2f108a 100644 --- a/tests/mir-opt/gvn.dereference_indexing.GVN.panic-abort.diff +++ b/tests/mir-opt/gvn.dereference_indexing.GVN.panic-abort.diff @@ -43,8 +43,7 @@ + nop; StorageLive(_8); StorageLive(_9); -- _9 = copy (*_3); -+ _9 = copy _1[_4]; + _9 = copy (*_3); _8 = opaque::<u8>(move _9) -> [return: bb2, unwind unreachable]; } diff --git a/tests/mir-opt/gvn.dereference_indexing.GVN.panic-unwind.diff b/tests/mir-opt/gvn.dereference_indexing.GVN.panic-unwind.diff index 6e67b66e783..f38bc51adc4 100644 --- a/tests/mir-opt/gvn.dereference_indexing.GVN.panic-unwind.diff +++ b/tests/mir-opt/gvn.dereference_indexing.GVN.panic-unwind.diff @@ -43,8 +43,7 @@ + nop; StorageLive(_8); StorageLive(_9); -- _9 = copy (*_3); -+ _9 = copy _1[_4]; + _9 = copy (*_3); _8 = opaque::<u8>(move _9) -> [return: bb2, unwind continue]; } |
