|
1 | 1 | use rustc_middle::mir::patch::MirPatch;
|
2 | 2 | use rustc_middle::mir::*;
|
3 |
| -use rustc_middle::ty::{self, Ty, TyCtxt}; |
| 3 | +use rustc_middle::ty::{Ty, TyCtxt}; |
4 | 4 | use std::fmt::Debug;
|
5 | 5 |
|
6 | 6 | use super::simplify::simplify_cfg;
|
@@ -88,10 +88,6 @@ use super::simplify::simplify_cfg;
|
88 | 88 | /// | ... |
|
89 | 89 | /// =================
|
90 | 90 | /// ```
|
91 |
| -/// |
92 |
| -/// This is only correct for some `P`, since `P` is now computed outside the original `switchInt`. |
93 |
| -/// The filter on which `P` are allowed (together with discussion of its correctness) is found in |
94 |
| -/// `may_hoist`. |
95 | 91 | pub struct EarlyOtherwiseBranch;
|
96 | 92 |
|
97 | 93 | impl<'tcx> MirPass<'tcx> for EarlyOtherwiseBranch {
|
@@ -258,54 +254,6 @@ impl<'tcx> MirPass<'tcx> for EarlyOtherwiseBranch {
|
258 | 254 | }
|
259 | 255 | }
|
260 | 256 |
|
261 |
| -/// Returns true if computing the discriminant of `place` may be hoisted out of the branch |
262 |
| -fn may_hoist<'tcx>(tcx: TyCtxt<'tcx>, body: &Body<'tcx>, place: Place<'tcx>) -> bool { |
263 |
| - for (place, proj) in place.iter_projections() { |
264 |
| - match proj { |
265 |
| - // Dereferencing in the computation of `place` might cause issues from one of two |
266 |
| - // categories. First, the referent might be invalid. We protect against this by |
267 |
| - // dereferencing references only (not pointers). Second, the use of a reference may |
268 |
| - // invalidate other references that are used later (for aliasing reasons). Consider |
269 |
| - // where such an invalidated reference may appear: |
270 |
| - // - In `Q`: Not possible since `Q` is used as the operand of a `SwitchInt` and so |
271 |
| - // cannot contain referenced data. |
272 |
| - // - In `BBU`: Not possible since that block contains only the `unreachable` terminator |
273 |
| - // - In `BBC.2, BBD.2`: Not possible, since `discriminant(P)` was computed prior to |
274 |
| - // reaching that block in the input to our transformation, and so any data |
275 |
| - // invalidated by that computation could not have been used there. |
276 |
| - // - In `BB9`: Not possible since control flow might have reached `BB9` via the |
277 |
| - // `otherwise` branch in `BBC, BBD` in the input to our transformation, which would |
278 |
| - // have invalidated the data when computing `discriminant(P)` |
279 |
| - // So dereferencing here is correct. |
280 |
| - ProjectionElem::Deref => match place.ty(body.local_decls(), tcx).ty.kind() { |
281 |
| - ty::Ref(..) => {} |
282 |
| - _ => return false, |
283 |
| - }, |
284 |
| - // Field projections are always valid |
285 |
| - ProjectionElem::Field(..) => {} |
286 |
| - // We cannot allow |
287 |
| - // downcasts either, since the correctness of the downcast may depend on the parent |
288 |
| - // branch being taken. An easy example of this is |
289 |
| - // ``` |
290 |
| - // Q = discriminant(_3) |
291 |
| - // P = (_3 as Variant) |
292 |
| - // ``` |
293 |
| - // However, checking if the child and parent place are the same and only erroring then |
294 |
| - // is not sufficient either, since the `discriminant(_3) == 1` (or whatever) check may |
295 |
| - // be replaced by another optimization pass with any other condition that can be proven |
296 |
| - // equivalent. |
297 |
| - ProjectionElem::Downcast(..) => { |
298 |
| - return false; |
299 |
| - } |
300 |
| - // We cannot allow indexing since the index may be out of bounds. |
301 |
| - _ => { |
302 |
| - return false; |
303 |
| - } |
304 |
| - } |
305 |
| - } |
306 |
| - true |
307 |
| -} |
308 |
| - |
309 | 257 | #[derive(Debug)]
|
310 | 258 | struct OptimizationData<'tcx> {
|
311 | 259 | destination: BasicBlock,
|
@@ -379,11 +327,6 @@ fn evaluate_candidate<'tcx>(
|
379 | 327 | let (_, Rvalue::Discriminant(child_place)) = &**boxed else {
|
380 | 328 | return None;
|
381 | 329 | };
|
382 |
| - // Verify that the optimization is legal in general |
383 |
| - // We can hoist evaluating the child discriminant out of the branch |
384 |
| - if !may_hoist(tcx, body, *child_place) { |
385 |
| - return None; |
386 |
| - } |
387 | 330 | *child_place
|
388 | 331 | } else {
|
389 | 332 | let TerminatorKind::SwitchInt { discr, .. } = &bbs[child].terminator().kind else {
|
|
0 commit comments