Skip to content

Commit e2cde91

Browse files
committed
Remove separation between generator_drop and unwind paths
1 parent dd2eabc commit e2cde91

File tree

1 file changed

+28
-53
lines changed

1 file changed

+28
-53
lines changed

Diff for: src/librustc_mir/build/scope.rs

+28-53
Original file line numberDiff line numberDiff line change
@@ -124,7 +124,10 @@ pub struct Scope<'tcx> {
124124
/// The cache for drop chain on "generator drop" exit.
125125
cached_generator_drop: Option<BasicBlock>,
126126

127-
/// The cache for drop chain on "unwind" exit.
127+
/// The cache for drop chain on "unwind" exit. This block
128+
/// contains code to run the current drop and all the preceding
129+
/// drops (i.e., those having lower index in Drop’s Scope drop
130+
/// array)
128131
cached_unwind: CachedBlock,
129132
}
130133

@@ -141,21 +144,7 @@ struct DropData<'tcx> {
141144
}
142145

143146
#[derive(Debug, Default, Clone, Copy)]
144-
pub(crate) struct CachedBlock {
145-
/// The cached block for the cleanups-on-diverge path. This block
146-
/// contains code to run the current drop and all the preceding
147-
/// drops (i.e., those having lower index in Drop’s Scope drop
148-
/// array)
149-
unwind: Option<BasicBlock>,
150-
151-
/// The cached block for unwinds during cleanups-on-generator-drop path
152-
///
153-
/// This is split from the standard unwind path here to prevent drop
154-
/// elaboration from creating drop flags that would have to be captured
155-
/// by the generator. I'm not sure how important this optimization is,
156-
/// but it is here.
157-
generator_drop: Option<BasicBlock>,
158-
}
147+
pub(crate) struct CachedBlock(Option<BasicBlock>);
159148

160149
#[derive(Debug)]
161150
pub(crate) enum DropKind {
@@ -181,24 +170,15 @@ pub struct BreakableScope<'tcx> {
181170

182171
impl CachedBlock {
183172
fn invalidate(&mut self) {
184-
self.generator_drop = None;
185-
self.unwind = None;
173+
self.0 = None;
186174
}
187175

188-
fn get(&self, generator_drop: bool) -> Option<BasicBlock> {
189-
if generator_drop {
190-
self.generator_drop
191-
} else {
192-
self.unwind
193-
}
176+
fn get(&self) -> Option<BasicBlock> {
177+
self.0
194178
}
195179

196-
fn ref_mut(&mut self, generator_drop: bool) -> &mut Option<BasicBlock> {
197-
if generator_drop {
198-
&mut self.generator_drop
199-
} else {
200-
&mut self.unwind
201-
}
180+
fn ref_mut(&mut self) -> &mut Option<BasicBlock> {
181+
&mut self.0
202182
}
203183
}
204184

@@ -378,7 +358,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
378358
assert_eq!(scope.region_scope, region_scope.0);
379359

380360
let unwind_to = self.scopes.last().and_then(|next_scope| {
381-
next_scope.cached_unwind.get(false)
361+
next_scope.cached_unwind.get()
382362
}).unwrap_or_else(|| self.resume_block());
383363

384364
unpack!(block = build_scope_drops(
@@ -387,7 +367,6 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
387367
block,
388368
unwind_to,
389369
self.arg_count,
390-
false,
391370
));
392371

393372
block.unit()
@@ -442,7 +421,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
442421
}
443422
};
444423

445-
let unwind_to = next_scope.cached_unwind.get(false).unwrap_or_else(|| {
424+
let unwind_to = next_scope.cached_unwind.get().unwrap_or_else(|| {
446425
debug_assert!(!may_panic, "cached block not present?");
447426
START_BLOCK
448427
});
@@ -453,7 +432,6 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
453432
block,
454433
unwind_to,
455434
self.arg_count,
456-
false,
457435
));
458436

459437
scope = next_scope;
@@ -470,7 +448,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
470448
/// None indicates there’s no cleanup to do at this point.
471449
pub fn generator_drop_cleanup(&mut self) -> Option<BasicBlock> {
472450
// Fill in the cache for unwinds
473-
self.diverge_cleanup_gen(true);
451+
self.diverge_cleanup_gen();
474452

475453
let src_info = self.scopes[0].source_info(self.fn_span);
476454
let resume_block = self.resume_block();
@@ -496,7 +474,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
496474
};
497475

498476
let unwind_to = scopes.peek().as_ref().map(|scope| {
499-
scope.cached_unwind.get(true).unwrap_or_else(|| {
477+
scope.cached_unwind.get().unwrap_or_else(|| {
500478
span_bug!(src_info.span, "cached block not present?")
501479
})
502480
}).unwrap_or(resume_block);
@@ -507,7 +485,6 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
507485
block,
508486
unwind_to,
509487
self.arg_count,
510-
true,
511488
));
512489
}
513490

@@ -760,7 +737,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
760737
/// This path terminates in Resume. Returns the start of the path.
761738
/// See module comment for more details.
762739
pub fn diverge_cleanup(&mut self) -> BasicBlock {
763-
self.diverge_cleanup_gen(false)
740+
self.diverge_cleanup_gen()
764741
}
765742

766743
fn resume_block(&mut self) -> BasicBlock {
@@ -779,7 +756,7 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
779756
}
780757
}
781758

782-
fn diverge_cleanup_gen(&mut self, generator_drop: bool) -> BasicBlock {
759+
fn diverge_cleanup_gen(&mut self) -> BasicBlock {
783760
// Build up the drops in **reverse** order. The end result will
784761
// look like:
785762
//
@@ -793,15 +770,15 @@ impl<'a, 'gcx, 'tcx> Builder<'a, 'gcx, 'tcx> {
793770

794771
// Find the last cached block
795772
let (mut target, first_uncached) = if let Some(cached_index) = self.scopes.iter()
796-
.rposition(|scope| scope.cached_unwind.get(generator_drop).is_some()) {
797-
(self.scopes[cached_index].cached_unwind.get(generator_drop).unwrap(), cached_index + 1)
773+
.rposition(|scope| scope.cached_unwind.get().is_some()) {
774+
(self.scopes[cached_index].cached_unwind.get().unwrap(), cached_index + 1)
798775
} else {
799776
(self.resume_block(), 0)
800777
};
801778

802779
for scope in self.scopes[first_uncached..].iter_mut() {
803780
target = build_diverge_scope(&mut self.cfg, scope.region_scope_span,
804-
scope, target, generator_drop, self.is_generator);
781+
scope, target, self.is_generator);
805782
}
806783

807784
target
@@ -881,7 +858,6 @@ fn build_scope_drops<'tcx>(
881858
mut block: BasicBlock,
882859
last_unwind_to: BasicBlock,
883860
arg_count: usize,
884-
generator_drop: bool,
885861
) -> BlockAnd<()> {
886862
debug!("build_scope_drops({:?} -> {:?}", block, scope);
887863

@@ -902,7 +878,7 @@ fn build_scope_drops<'tcx>(
902878

903879
let mut unwind_blocks = scope.drops.iter().rev().filter_map(|drop_data| {
904880
if let DropKind::Value { cached_block } = drop_data.kind {
905-
Some(cached_block.get(generator_drop).unwrap_or_else(|| {
881+
Some(cached_block.get().unwrap_or_else(|| {
906882
span_bug!(drop_data.span, "cached block not present?")
907883
}))
908884
} else {
@@ -946,13 +922,12 @@ fn build_scope_drops<'tcx>(
946922
block.unit()
947923
}
948924

949-
fn build_diverge_scope<'tcx>(cfg: &mut CFG<'tcx>,
950-
span: Span,
951-
scope: &mut Scope<'tcx>,
952-
mut target: BasicBlock,
953-
generator_drop: bool,
954-
is_generator: bool)
955-
-> BasicBlock
925+
fn build_diverge_scope(cfg: &mut CFG<'tcx>,
926+
span: Span,
927+
scope: &mut Scope<'tcx>,
928+
mut target: BasicBlock,
929+
is_generator: bool)
930+
-> BasicBlock
956931
{
957932
// Build up the drops in **reverse** order. The end result will
958933
// look like:
@@ -1004,7 +979,7 @@ fn build_diverge_scope<'tcx>(cfg: &mut CFG<'tcx>,
1004979
}
1005980
DropKind::Storage => {}
1006981
DropKind::Value { ref mut cached_block } => {
1007-
let cached_block = cached_block.ref_mut(generator_drop);
982+
let cached_block = cached_block.ref_mut();
1008983
target = if let Some(cached_block) = *cached_block {
1009984
storage_deads.clear();
1010985
target_built_by_us = false;
@@ -1027,7 +1002,7 @@ fn build_diverge_scope<'tcx>(cfg: &mut CFG<'tcx>,
10271002
};
10281003
}
10291004
push_storage_deads(cfg, &mut target, &mut storage_deads, target_built_by_us, source_scope);
1030-
*scope.cached_unwind.ref_mut(generator_drop) = Some(target);
1005+
*scope.cached_unwind.ref_mut() = Some(target);
10311006

10321007
assert!(storage_deads.is_empty());
10331008
debug!("build_diverge_scope({:?}, {:?}) = {:?}", scope, span, target);

0 commit comments

Comments
 (0)