-
Notifications
You must be signed in to change notification settings - Fork 14k
[mlir][spirv] Add definition for GL Length #144041
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
@llvm/pr-subscribers-mlir-spirv @llvm/pr-subscribers-mlir Author: Igor Wodiany (IgWod-IMG) ChangesFull diff: https://github.com/llvm/llvm-project/pull/144041.diff 3 Files Affected:
diff --git a/mlir/include/mlir/Dialect/SPIRV/IR/SPIRVGLOps.td b/mlir/include/mlir/Dialect/SPIRV/IR/SPIRVGLOps.td
index 2ec61758ba8ef..8c4da9b2dce18 100644
--- a/mlir/include/mlir/Dialect/SPIRV/IR/SPIRVGLOps.td
+++ b/mlir/include/mlir/Dialect/SPIRV/IR/SPIRVGLOps.td
@@ -1160,6 +1160,46 @@ def SPIRV_GLFMixOp :
// -----
+def SPIRV_GLLengthOp : SPIRV_GLOp<"Length", 66, [
+ Pure,
+ TypesMatchWith<"result type must match operand element type",
+ "operand", "result",
+ "::mlir::getElementTypeOrSelf($_self)">
+ ]> {
+ let summary = "Return the length of a vector x";
+
+ let description = [{
+ Result is the length of vector x, i.e., sqrt(x[0]**2 + x[1]**2 + ...).
+
+ The operand x must be a scalar or vector whose component type is floating-point.
+
+ Result Type must be a scalar of the same type as the component type of x.
+
+ #### Example:
+
+ ```mlir
+ %2 = spirv.GL.Length %0 : vector<3xf32> -> f32
+ %3 = spirv.GL.Length %1 : f32 -> f32
+ ```
+ }];
+
+ let arguments = (ins
+ SPIRV_ScalarOrVectorOf<SPIRV_Float>:$operand
+ );
+
+ let results = (outs
+ SPIRV_Float:$result
+ );
+
+ let assemblyFormat = [{
+ $operand attr-dict `:` type($operand) `->` type($result)
+ }];
+
+ let hasVerifier = 0;
+}
+
+// -----
+
def SPIRV_GLDistanceOp : SPIRV_GLOp<"Distance", 67, [
Pure,
AllTypesMatch<["p0", "p1"]>,
diff --git a/mlir/test/Dialect/SPIRV/IR/gl-ops.mlir b/mlir/test/Dialect/SPIRV/IR/gl-ops.mlir
index 2b75767feaf92..f49be21fcf783 100644
--- a/mlir/test/Dialect/SPIRV/IR/gl-ops.mlir
+++ b/mlir/test/Dialect/SPIRV/IR/gl-ops.mlir
@@ -983,3 +983,69 @@ func.func @unpack_half_2x16_scalar_out(%arg0 : i32) -> () {
%0 = spirv.GL.UnpackHalf2x16 %arg0 : i32 -> f32
return
}
+
+// -----
+
+//===----------------------------------------------------------------------===//
+// spirv.GL.Length
+//===----------------------------------------------------------------------===//
+
+func.func @length(%arg0 : f32) -> () {
+ // CHECK: spirv.GL.Length {{%.*}} : f32 -> f32
+ %0 = spirv.GL.Length %arg0 : f32 -> f32
+ return
+}
+
+func.func @lengthvec(%arg0 : vector<3xf32>) -> () {
+ // CHECK: spirv.GL.Length {{%.*}} : vector<3xf32> -> f32
+ %0 = spirv.GL.Length %arg0 : vector<3xf32> -> f32
+ return
+}
+
+// -----
+
+func.func @length_i32_in(%arg0 : i32) -> () {
+ // expected-error @+1 {{op operand #0 must be 16/32/64-bit float or vector of 16/32/64-bit float values of length 2/3/4/8/16, but got 'i32'}}
+ %0 = spirv.GL.Length %arg0 : i32 -> f32
+ return
+}
+
+// -----
+
+func.func @length_f16_in(%arg0 : f16) -> () {
+ // expected-error @+1 {{op failed to verify that result type must match operand element type}}
+ %0 = spirv.GL.Length %arg0 : f16 -> f32
+ return
+}
+
+// -----
+
+func.func @length_i32vec_in(%arg0 : vector<3xi32>) -> () {
+ // expected-error @+1 {{op operand #0 must be 16/32/64-bit float or vector of 16/32/64-bit float values of length 2/3/4/8/16, but got 'vector<3xi32>'}}
+ %0 = spirv.GL.Length %arg0 : vector<3xi32> -> f32
+ return
+}
+
+// -----
+
+func.func @length_f16vec_in(%arg0 : vector<3xf16>) -> () {
+ // expected-error @+1 {{op failed to verify that result type must match operand element type}}
+ %0 = spirv.GL.Length %arg0 : vector<3xf16> -> f32
+ return
+}
+
+// -----
+
+func.func @length_i32_out(%arg0 : vector<3xf32>) -> () {
+ // expected-error @+1 {{op result #0 must be 16/32/64-bit float, but got 'i32'}}
+ %0 = spirv.GL.Length %arg0 : vector<3xf32> -> i32
+ return
+}
+
+// -----
+
+func.func @length_vec_out(%arg0 : vector<3xf32>) -> () {
+ // expected-error @+1 {{op result #0 must be 16/32/64-bit float, but got 'vector<3xf32>'}}
+ %0 = spirv.GL.Length %arg0 : vector<3xf32> -> vector<3xf32>
+ return
+}
diff --git a/mlir/test/Target/SPIRV/gl-ops.mlir b/mlir/test/Target/SPIRV/gl-ops.mlir
index eacf36bfba9ce..832f7ea2fe314 100644
--- a/mlir/test/Target/SPIRV/gl-ops.mlir
+++ b/mlir/test/Target/SPIRV/gl-ops.mlir
@@ -128,6 +128,10 @@ spirv.module Logical GLSL450 requires #spirv.vce<v1.0, [Shader], []> {
%8 = spirv.GL.FindSMsb %arg3 : vector<3xi32>
// CHECK: {{%.*}} = spirv.GL.FindUMsb {{%.*}} : vector<3xi32>
%9 = spirv.GL.FindUMsb %arg3 : vector<3xi32>
+ // CHECK: {{%.*}} = spirv.GL.Length {{%.*}} : f32 -> f32
+ %10 = spirv.GL.Length %arg0 : f32 -> f32
+ // CHECK: {{%.*}} = spirv.GL.Length {{%.*}} : vector<3xf32> -> f32
+ %11 = spirv.GL.Length %arg1 : vector<3xf32> -> f32
spirv.Return
}
|
I have added the canonicalizer. I've considered whether I should put it in the GL canonicalizer, but since in here we transform GL op into GL op, the op availability should not be an issues. |
Build failures are unrelated to this change. The problem has been already reported in #144179. |
I looked at this a little bit more closely and I think gl canonicalization is separated out mostly to better organize the code, similar how we have group op definitions in .td files (unlike most dialect that put all ops together). I don't see any logic that decides availability, unless I missed something. One caveat is that gl canon patterns don't run with the generic |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm going to approve but I think it'd make more sense for the canon pattern to be with other gl patterns.
The comment in the header file:
Having said that, I agree it does make sense to put it with other GL ops -- it is only useful if GL ops are available anyway and it will make the code cleaner. I'll update this PR. |
Oh, I understand what you mean by availability now. Right, we wouldn't want to canonicalize |
So these are the buckets of spirv canon patterns:
|
I'm glad we're on the same page now :) I think it makes more sense to have all GL canonicalization in one place both from code organization perspective and from user interface -- I think it'd be a bit confusing if some GL canonicalization is run with default canonicalization and some with GL specific canonicalization.
I guess from now on we should be consistent and in both cases run those pattern as a part of gl/cl canonicalization. |
No description provided.