[Mlir-commits] [mlir] [mlir][Transform] Fix crash in SequenceOp::getEffects when body region is empty (PR #185063)

Mehdi Amini llvmlistbot at llvm.org
Wed Mar 18 09:47:15 PDT 2026


https://github.com/joker-eph updated https://github.com/llvm/llvm-project/pull/185063

>From d7aabe9b50bed126f79059f23c43e250fcb84020 Mon Sep 17 00:00:00 2001
From: Mehdi Amini <joker.eph at gmail.com>
Date: Fri, 6 Mar 2026 05:58:14 -0800
Subject: [PATCH] [mlir][Transform] Fix crash in SequenceOp::getEffects when
 body region is empty

When walking operations post-order and erasing blocks, the inner body block of
a nested transform.sequence can be erased while the outer op is still alive.
If printAsOperand is called on the outer block at that point, it triggers
verification, which calls SequenceOp::getEffects -> getPotentialTopLevelEffects
-> getBodyBlock() -> Region::front() on an empty region, causing an assertion
failure in ilist_iterator ('\!NodePtr->isKnownSentinel()').

Fix by checking that the body region is non-empty before passing its front block
to detail::getPotentialTopLevelEffects in the PossibleTopLevelTransformOpTrait.

Fixes #60213

Assisted-by: Claude Code
---
 .../Transform/Interfaces/TransformInterfaces.h      |  5 ++++-
 mlir/test/Dialect/Transform/ops-invalid.mlir        | 13 +++++++++++++
 2 files changed, 17 insertions(+), 1 deletion(-)

diff --git a/mlir/include/mlir/Dialect/Transform/Interfaces/TransformInterfaces.h b/mlir/include/mlir/Dialect/Transform/Interfaces/TransformInterfaces.h
index c2ceaba1128a3..c32d4a81a63ab 100644
--- a/mlir/include/mlir/Dialect/Transform/Interfaces/TransformInterfaces.h
+++ b/mlir/include/mlir/Dialect/Transform/Interfaces/TransformInterfaces.h
@@ -1169,9 +1169,12 @@ class PossibleTopLevelTransformOpTrait
   /// Populates `effects` with side effects implied by this trait.
   void getPotentialTopLevelEffects(
       SmallVectorImpl<MemoryEffects::EffectInstance> &effects) {
+    Region &region = this->getOperation()->getRegion(0);
+    if (region.empty())
+      return;
     detail::getPotentialTopLevelEffects(
         this->getOperation(), cast<OpTy>(this->getOperation()).getRoot(),
-        *getBodyBlock(), effects);
+        region.front(), effects);
   }
 
   /// Sets up the mapping between the entry block of the given region of this op
diff --git a/mlir/test/Dialect/Transform/ops-invalid.mlir b/mlir/test/Dialect/Transform/ops-invalid.mlir
index 6d4e00822f419..c098025f6c456 100644
--- a/mlir/test/Dialect/Transform/ops-invalid.mlir
+++ b/mlir/test/Dialect/Transform/ops-invalid.mlir
@@ -972,3 +972,16 @@ module attributes { transform.with_named_sequence } {
     "transform.yield"() : () -> ()
   }) : () -> ()
 }
+
+// -----
+
+// Regression test for https://github.com/llvm/llvm-project/issues/60213:
+// Verifying a transform.sequence with an empty body region must not crash.
+// Previously, verifyTransformOpInterface called getEffects, which called
+// getBodyBlock() -> Region::front() on an empty region, causing an assertion.
+transform.sequence failures(propagate) {
+^bb0(%arg0: !pdl.operation):
+// expected-error @below {{region #0 ('body') failed to verify constraint: region with 1 blocks}}
+  "transform.sequence"(%arg0) <{failure_propagation_mode = 1 : i32, operandSegmentSizes = array<i32: 1, 0>}> ({
+  }) : (!pdl.operation) -> ()
+}



More information about the Mlir-commits mailing list