@@ -434,21 +434,50 @@ void CopyPropagation::run() {
434
434
}
435
435
}
436
436
437
+ // canonicalizer performs all modifications through deleter's callbacks, so we
438
+ // don't need to explicitly check for changes.
439
+ CanonicalizeOSSALifetime canonicalizer (pruneDebug, poisonRefs,
440
+ accessBlockAnalysis, domTree, deleter);
441
+
437
442
// NOTE: We assume that the function is in reverse post order so visiting the
438
443
// blocks and pushing begin_borrows as we see them and then popping them
439
444
// off the end will result in shrinking inner borrow scopes first.
440
445
while (auto *bbi = beginBorrowsToShrink.pop ()) {
441
- SmallVector<CopyValueInst *, 4 > modifiedCopyValueInsts;
442
- changed |= shrinkBorrowScope (bbi, deleter, modifiedCopyValueInsts);
443
- for (auto *cvi : modifiedCopyValueInsts)
444
- defWorklist.updateForCopy (cvi);
446
+ bool firstRun = true ;
447
+ // Run the sequence of utilities:
448
+ // - ShrinkBorrowScope
449
+ // - CanonicalizeOSSALifetime
450
+ // - LexicalDestroyFolder
451
+ // at least once and then until each stops making changes.
452
+ while (true ) {
453
+ SmallVector<CopyValueInst *, 4 > modifiedCopyValueInsts;
454
+ auto shrunk = shrinkBorrowScope (bbi, deleter, modifiedCopyValueInsts);
455
+ for (auto *cvi : modifiedCopyValueInsts)
456
+ defWorklist.updateForCopy (cvi);
457
+ changed |= shrunk;
458
+ if (!shrunk && !firstRun)
459
+ break ;
460
+
461
+ // If borrowed value is not owned, neither CanonicalizeOSSALifetime nor
462
+ // LexicalDestroyFolding will do anything with it. Just bail out now.
463
+ auto borrowee = bbi->getOperand ();
464
+ if (borrowee.getOwnershipKind () != OwnershipKind::Owned)
465
+ break ;
466
+
467
+ auto canonicalized = canonicalizer.canonicalizeValueLifetime (borrowee);
468
+ if (!canonicalized && !firstRun)
469
+ break ;
470
+
471
+ auto folded = foldDestroysOfCopiedLexicalBorrow (bbi, *domTree, deleter);
472
+ if (!folded)
473
+ break ;
474
+ // We don't add the produced move_value instruction to the worklist
475
+ // because it can't handle propagation.
476
+ firstRun = false ;
477
+ }
445
478
}
446
479
deleter.cleanupDeadInstructions ();
447
480
448
- // canonicalizer performs all modifications through deleter's callbacks, so we
449
- // don't need to explicitly check for changes.
450
- CanonicalizeOSSALifetime canonicalizer (pruneDebug, poisonRefs,
451
- accessBlockAnalysis, domTree, deleter);
452
481
// For now, only modify forwarding instructions
453
482
// At -Onone, we do nothing but rewrite copies of owned values.
454
483
if (canonicalizeBorrows) {
0 commit comments