[Mlir-commits] [mlir] c54cb1b - [mlir][linalg] Emit proper diagnostic instead of crashing in SelectOp with index type (#183652)

llvmlistbot at llvm.org llvmlistbot at llvm.org
Mon Mar 9 04:50:17 PDT 2026


Author: Mehdi Amini
Date: 2026-03-09T12:50:13+01:00
New Revision: c54cb1b81482b7edf1a2d8a78188642a5aacb0de

URL: https://github.com/llvm/llvm-project/commit/c54cb1b81482b7edf1a2d8a78188642a5aacb0de
DIFF: https://github.com/llvm/llvm-project/commit/c54cb1b81482b7edf1a2d8a78188642a5aacb0de.diff

LOG: [mlir][linalg] Emit proper diagnostic instead of crashing in SelectOp with index type (#183652)

`buildTernaryFn` for `TernaryFn::select` called `llvm_unreachable` when
the operand types were not `i1`, integer, or floating-point (e.g.,
`index` type).
Instead delegate this checking to the IR verifier: we don't need to
duplicate the checks from the verifier in an assertion here.

Fixes #179046

Assisted-by: Claude Code

Added: 
    

Modified: 
    mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
    mlir/test/Dialect/Linalg/named-ops-fail.mlir
    mlir/test/Dialect/Linalg/named-ops.mlir

Removed: 
    


################################################################################
diff  --git a/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp b/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
index 37b549a7fcd7f..ad2909f656eea 100644
--- a/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
+++ b/mlir/lib/Dialect/Linalg/IR/LinalgOps.cpp
@@ -619,17 +619,10 @@ class RegionBuilderHelper {
   // Build the ternary functions defined by OpDSL.
   Value buildTernaryFn(TernaryFn ternaryFn, Value arg0, Value arg1, Value arg2,
                        function_ref<InFlightDiagnostic()> emitError = {}) {
-    bool headBool =
-        isInteger(arg0) && arg0.getType().getIntOrFloatBitWidth() == 1;
-    bool tailFloatingPoint =
-        isFloatingPoint(arg0) && isFloatingPoint(arg1) && isFloatingPoint(arg2);
-    bool tailInteger = isInteger(arg0) && isInteger(arg1) && isInteger(arg2);
     OpBuilder::InsertionGuard g(builder);
     builder.setInsertionPointToEnd(&block);
     switch (ternaryFn) {
     case TernaryFn::select:
-      if (!headBool && !(tailFloatingPoint || tailInteger))
-        llvm_unreachable("unsupported non numeric type");
       return arith::SelectOp::create(builder, arg0.getLoc(), arg0, arg1, arg2);
     }
     if (emitError) {

diff  --git a/mlir/test/Dialect/Linalg/named-ops-fail.mlir b/mlir/test/Dialect/Linalg/named-ops-fail.mlir
index 316ed8014ab7f..bf9c1b705f157 100644
--- a/mlir/test/Dialect/Linalg/named-ops-fail.mlir
+++ b/mlir/test/Dialect/Linalg/named-ops-fail.mlir
@@ -349,3 +349,36 @@ func.func @select_wrong_condition_type(%arg0: memref<4x8x16xf32>, %arg1: memref<
   linalg.select ins(%arg0, %arg1, %arg2 : memref<4x8x16xf32>, memref<4x8x16xf32>, memref<4x8x16xf32>) outs(%arg3: memref<4x8x16xf32>)
   return
 }
+
+// -----
+
+// linalg.select with all-integer operands
+func.func @select_all_integer(%arg0: memref<4x8x16xi32>, %arg1: memref<4x8x16xi32>, %arg2: memref<4x8x16xi32>, %arg3: memref<4x8x16xi32>) {
+  // CHECK: op operand #0 must be bool-like, but got 'i32'
+  linalg.select ins(%arg0, %arg1, %arg2 : memref<4x8x16xi32>, memref<4x8x16xi32>, memref<4x8x16xi32>) outs(%arg3: memref<4x8x16xi32>)
+  return
+}
+
+// -----
+
+// Regression test: linalg.select with index type operands should emit a
+// diagnostic instead of crashing (https://github.com/llvm/llvm-project/issues/179046).
+func.func @select_invalid_index_type(%cond: index, %a: index, %b: index,
+                                     %out: tensor<1xindex>) -> tensor<1xindex> {
+  // CHECK: op operand #0 must be bool-like, but got 'index'
+  %0 = linalg.select ins(%cond, %a, %b : index, index, index)
+                     outs(%out : tensor<1xindex>) -> tensor<1xindex>
+  return %0 : tensor<1xindex>
+}
+
+// -----
+
+// linalg.select with an integer (non-i1) condition and floating-point values:
+func.func @select_invalid_integer_cond_float_values(%cond: tensor<4xi32>,
+    %a: tensor<4xf32>, %b: tensor<4xf32>,
+    %out: tensor<4xf32>) -> tensor<4xf32> {
+// CHECK: op operand #0 must be bool-like, but got 'i32'
+  %0 = linalg.select ins(%cond, %a, %b : tensor<4xi32>, tensor<4xf32>, tensor<4xf32>)
+                     outs(%out : tensor<4xf32>) -> tensor<4xf32>
+  return %0 : tensor<4xf32>
+}

diff  --git a/mlir/test/Dialect/Linalg/named-ops.mlir b/mlir/test/Dialect/Linalg/named-ops.mlir
index 1e356c8fb4e72..8068c23a4a0fd 100644
--- a/mlir/test/Dialect/Linalg/named-ops.mlir
+++ b/mlir/test/Dialect/Linalg/named-ops.mlir
@@ -2718,6 +2718,20 @@ func.func @select_tensor(%arg0: tensor<4x8x16xi1>, %arg1: tensor<4x8x16xf32>, %a
   return %1 : tensor<4x8x16xf32>
 }
 
+// -----
+
+// CHECK-LABEL: func @select_integer_values
+// linalg.select with i1 condition and integer values: headBool=true (i1 bitwidth==1)
+// → valid, arith.select accepts i1 as condition regardless of value types.
+func.func @select_integer_values(%arg0: tensor<4x8x16xi1>, %arg1: tensor<4x8x16xi32>, %arg2: tensor<4x8x16xi32>) -> tensor<4x8x16xi32> {
+  %0 = tensor.empty() : tensor<4x8x16xi32>
+  // CHECK: linalg.select
+  // CHECK-SAME: ins(%{{.+}}, %{{.+}}, %{{.+}} : tensor<4x8x16xi1>, tensor<4x8x16xi32>, tensor<4x8x16xi32>)
+  // CHECK-SAME: outs(%{{.+}} : tensor<4x8x16xi32>)
+  %1 = linalg.select ins(%arg0, %arg1, %arg2 : tensor<4x8x16xi1>, tensor<4x8x16xi32>, tensor<4x8x16xi32>) outs(%0: tensor<4x8x16xi32>) -> tensor<4x8x16xi32>
+  return %1 : tensor<4x8x16xi32>
+}
+
 //===----------------------------------------------------------------------===//
 // linalg.pack + linalg.unpack
 //===----------------------------------------------------------------------===//


        


More information about the Mlir-commits mailing list