Skip to content

Commit 4a3a6fd

Browse files
authored
Unrolled build for #142542
Rollup merge of #142542 - cjgillot:invalidate-simplify-cfg, r=SparrowLii Manually invalidate caches in SimplifyCfg. The current `SimplifyCfg` pass unconditionally invalidates CFG caches. This is unfortunate if there are no modifications that require this invalidation.
2 parents 86d0aef + a2d9687 commit 4a3a6fd

File tree

1 file changed

+16
-3
lines changed

1 file changed

+16
-3
lines changed

compiler/rustc_mir_transform/src/simplify.rs

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -74,7 +74,11 @@ impl SimplifyCfg {
7474
}
7575

7676
pub(super) fn simplify_cfg<'tcx>(tcx: TyCtxt<'tcx>, body: &mut Body<'tcx>) {
77-
CfgSimplifier::new(tcx, body).simplify();
77+
if CfgSimplifier::new(tcx, body).simplify() {
78+
// `simplify` returns that it changed something. We must invalidate the CFG caches as they
79+
// are not consistent with the modified CFG any more.
80+
body.basic_blocks.invalidate_cfg_cache();
81+
}
7882
remove_dead_blocks(body);
7983

8084
// FIXME: Should probably be moved into some kind of pass manager
@@ -121,19 +125,24 @@ impl<'a, 'tcx> CfgSimplifier<'a, 'tcx> {
121125
// Preserve `SwitchInt` reads on built and analysis MIR, or if `-Zmir-preserve-ub`.
122126
let preserve_switch_reads = matches!(body.phase, MirPhase::Built | MirPhase::Analysis(_))
123127
|| tcx.sess.opts.unstable_opts.mir_preserve_ub;
124-
let basic_blocks = body.basic_blocks_mut();
128+
// Do not clear caches yet. The caller to `simplify` will do it if anything changed.
129+
let basic_blocks = body.basic_blocks.as_mut_preserves_cfg();
125130

126131
CfgSimplifier { preserve_switch_reads, basic_blocks, pred_count }
127132
}
128133

129-
fn simplify(mut self) {
134+
/// Returns whether we actually simplified anything. In that case, the caller *must* invalidate
135+
/// the CFG caches of the MIR body.
136+
#[must_use]
137+
fn simplify(mut self) -> bool {
130138
self.strip_nops();
131139

132140
// Vec of the blocks that should be merged. We store the indices here, instead of the
133141
// statements itself to avoid moving the (relatively) large statements twice.
134142
// We do not push the statements directly into the target block (`bb`) as that is slower
135143
// due to additional reallocations
136144
let mut merged_blocks = Vec::new();
145+
let mut outer_changed = false;
137146
loop {
138147
let mut changed = false;
139148

@@ -177,7 +186,11 @@ impl<'a, 'tcx> CfgSimplifier<'a, 'tcx> {
177186
if !changed {
178187
break;
179188
}
189+
190+
outer_changed = true;
180191
}
192+
193+
outer_changed
181194
}
182195

183196
/// This function will return `None` if

0 commit comments

Comments
 (0)