[Mlir-commits] [mlir] [MLIR] [Mem2Reg] Fix unused block argument removal logic (PR #188484)
Tobias Gysi
llvmlistbot at llvm.org
Wed Mar 25 07:56:20 PDT 2026
=?utf-8?q?Théo?= Degioanni <tdegioanni at nvidia.com>,
=?utf-8?q?Théo?= Degioanni <tdegioanni at nvidia.com>,
=?utf-8?q?Théo?= Degioanni <tdegioanni at nvidia.com>,
=?utf-8?q?Théo?= Degioanni <tdegioanni at nvidia.com>
Message-ID:
In-Reply-To: <llvm.org/llvm/llvm-project/pull/188484 at github.com>
================
@@ -757,46 +769,96 @@ void MemorySlotPromoter::removeBlockingUses(Region *region) {
builder.setInsertionPointAfter(toPromote);
if (toPromoteBasic.removeBlockingUses(blockingUsesMap[toPromote],
builder) == DeletionKind::Delete)
- toErase.push_back(toPromote);
+ toErase.insert(toPromote);
if (toPromoteBasic.requiresReplacedValues())
toVisitReplacedValues.push_back(toPromoteBasic);
}
}
-void MemorySlotPromoter::linkMergePoints() {
- // We want to eliminate unused block arguments. In case connecting a block
- // argument to its predecessor would trigger the use of the predecessor's
- // unused block argument, we need to process merge points in an expanding
- // worklist, `mergePointArgsToProcess`.
+void MemorySlotPromoter::removeUnusedItems() {
+ // We want to eliminate unused block arguments. Because block arguments can be
+ // used to populate other block arguments, there might be cycles of arguments
+ // that are only used to populate each-other. We therefore need a small
+ // dataflow analysis to identify which block arguments are truly used.
SmallPtrSet<BlockArgument, 8> mergePointArgsUnused;
- SmallVector<BlockArgument> mergePointArgsToProcess;
+ SmallVector<BlockArgument> usedMergePointArgsToProcess;
+
+ // First, separate the block arguments that are not used or only used for the
+ // purpose of populating a merge point block argument from the others. These
+ // block arguments are potentially unused. Meanwhile, arguments that are
+ // definitely used will be the starting point of the propagation of the
+ // analysis.
+ auto isDefinitelyUsed = [&](BlockArgument arg) {
+ for (auto &use : arg.getUses()) {
+ if (llvm::is_contained(toErase, use.getOwner()))
+ continue;
+
+ // We now want to detect whether the use is to populate a merge point
+ // block argument. If it is not, the argument is definitely used.
+
+ auto branchOp = dyn_cast<BranchOpInterface>(use.getOwner());
+ if (!branchOp)
+ return true;
+
+ auto successorArgument =
+ branchOp.getSuccessorBlockArgument(use.getOperandNumber());
+ if (!successorArgument.has_value())
----------------
gysit wrote:
```suggestion
if (!successorArgument)
```
nit: I believe the `has_value` is redundant assuming this is an optional? Also maybe we can spell out the type on line 804?
https://github.com/llvm/llvm-project/pull/188484
More information about the Mlir-commits
mailing list