@@ -349,8 +349,8 @@ impl<'tcx> PoloniusOutOfScopePrecomputer<'_, 'tcx> {
349
349
// - placeholders or free regions themselves,
350
350
// - or also transitively outlive a free region.
351
351
//
352
- // That is to say, if there are member constraints here, the loan escapes the
353
- // function and cannot go out of scope. We can early return.
352
+ // That is to say, if there are member constraints here, the loan escapes the function
353
+ // and cannot go out of scope. We can early return.
354
354
//
355
355
// 2. Via regions that are live at all points: placeholders and free regions.
356
356
//
@@ -364,36 +364,32 @@ impl<'tcx> PoloniusOutOfScopePrecomputer<'_, 'tcx> {
364
364
return ;
365
365
}
366
366
367
- // 3. Via outlives successors, which we want to record and traverse: we add them
368
- // to the worklist stack
367
+ // 3. Via outlives successors, which we want to record and traverse: we add them to the
368
+ // worklist stack
369
369
for & succ_scc in sccs. successors ( scc) {
370
370
if self . reachability . insert ( succ_scc) {
371
371
self . reachability_stack . push ( succ_scc) ;
372
372
}
373
373
}
374
374
}
375
375
376
- // We visit one BB at a time. The complication is that we may start in the
377
- // middle of the first BB visited (the one containing `location`), in which
378
- // case we may have to later on process the first part of that BB if there
379
- // is a path back to its start.
376
+ // We visit one BB at a time. The complication is that we may start in the middle of the
377
+ // first BB visited (the one containing `issued_location`), in which case we may have to
378
+ // later on process the first part of that BB if there is a path back to its start.
380
379
381
- // For visited BBs, we record the index of the first statement processed.
382
- // (In fully processed BBs this index is 0.) Note also that we add BBs to
383
- // `visited` once they are added to `stack`, before they are actually
384
- // processed, because this avoids the need to look them up again on
385
- // completion.
380
+ // For visited BBs, we record the index of the first statement processed. (In fully
381
+ // processed BBs this index is 0.) Note also that we add BBs to `visited` once they are
382
+ // added to `stack`, before they are actually processed, because this avoids the need to
383
+ // look them up again on completion.
386
384
self . visited . insert ( issued_location. block ) ;
387
385
386
+ let first_block = issued_location. block ;
388
387
let mut first_lo = issued_location. statement_index ;
389
388
let first_hi = self . body [ issued_location. block ] . statements . len ( ) ;
390
389
391
390
self . visit_stack . push ( StackEntry { bb : issued_location. block , lo : first_lo, hi : first_hi } ) ;
392
391
393
- while let Some ( StackEntry { bb, lo, hi } ) = self . visit_stack . pop ( ) {
394
- // If we process the first part of the first basic block (i.e. we encounter that block
395
- // for the second time), we no longer have to visit its successors again.
396
- let mut finished_early = bb == issued_location. block && hi != first_hi;
392
+ ' preorder: while let Some ( StackEntry { bb, lo, hi } ) = self . visit_stack . pop ( ) {
397
393
for i in lo..=hi {
398
394
let location = Location { block : bb, statement_index : i } ;
399
395
@@ -419,44 +415,42 @@ impl<'tcx> PoloniusOutOfScopePrecomputer<'_, 'tcx> {
419
415
}
420
416
}
421
417
422
- // If no live region is reachable from the issuing region, then the loan is
423
- // killed at this point, and goes out of scope.
418
+ // If no live region is reachable from the issuing region, then the loan is killed
419
+ // at this point, and goes out of scope. We also can skip visiting successor
420
+ // locations.
424
421
if !issuing_region_can_reach_live_regions {
425
422
debug ! ( "loan {:?} gets killed at {:?}" , loan_idx, location) ;
426
423
self . loans_out_of_scope_at_location . entry ( location) . or_default ( ) . push ( loan_idx) ;
427
- finished_early = true ;
428
- break ;
424
+ continue ' preorder;
429
425
}
430
426
}
431
427
432
- if !finished_early {
433
- // Add successor BBs to the work list, if necessary.
434
- let bb_data = & self . body [ bb] ;
435
- debug_assert ! ( hi == bb_data. statements. len( ) ) ;
436
- for succ_bb in bb_data. terminator ( ) . successors ( ) {
437
- if !self . visited . insert ( succ_bb) {
438
- if succ_bb == issued_location. block && first_lo > 0 {
439
- // `succ_bb` has been seen before. If it wasn't fully processed, add its
440
- // first part to `visit_stack` for processing.
441
- self . visit_stack . push ( StackEntry {
442
- bb : succ_bb,
443
- lo : 0 ,
444
- hi : first_lo - 1 ,
445
- } ) ;
446
-
447
- // And update this entry with 0, to represent the whole BB being
448
- // processed.
449
- first_lo = 0 ;
450
- }
451
- } else {
452
- // `succ_bb` hasn't been seen before. Add it to `visit_stack` for
453
- // processing.
454
- self . visit_stack . push ( StackEntry {
455
- bb : succ_bb,
456
- lo : 0 ,
457
- hi : self . body [ succ_bb] . statements . len ( ) ,
458
- } ) ;
428
+ // If we process the first part of the first basic block (i.e. we encounter that block
429
+ // for the second time), we no longer have to visit its successors again.
430
+ if bb == first_block && hi != first_hi {
431
+ continue ;
432
+ }
433
+
434
+ // Add successor BBs to the work list, if necessary.
435
+ let bb_data = & self . body [ bb] ;
436
+ debug_assert ! ( hi == bb_data. statements. len( ) ) ;
437
+ for succ_bb in bb_data. terminator ( ) . successors ( ) {
438
+ if !self . visited . insert ( succ_bb) {
439
+ if succ_bb == first_block && first_lo > 0 {
440
+ // `succ_bb` has been seen before. If it wasn't fully processed, add its
441
+ // first part to the stack for processing.
442
+ self . visit_stack . push ( StackEntry { bb : succ_bb, lo : 0 , hi : first_lo - 1 } ) ;
443
+
444
+ // And update this entry with 0, to represent the whole BB being processed.
445
+ first_lo = 0 ;
459
446
}
447
+ } else {
448
+ // `succ_bb` hasn't been seen before. Add it to the stack for processing.
449
+ self . visit_stack . push ( StackEntry {
450
+ bb : succ_bb,
451
+ lo : 0 ,
452
+ hi : self . body [ succ_bb] . statements . len ( ) ,
453
+ } ) ;
460
454
}
461
455
}
462
456
}
0 commit comments