-
Notifications
You must be signed in to change notification settings - Fork 14.3k
[MLIR][Arith] Add ExpandOps to convertArithToLLVM #117305
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
Hey Hugo, thanks for sending this! This is marked as draft, so I presume not yet ready for reviewing? |
@llvm/pr-subscribers-mlir Author: Hugo Trachino (nujaa) ChangesArith Floor and Ceil ops would not get lowered when running --convert-arith-to-llvm. Full diff: https://github.com/llvm/llvm-project/pull/117305.diff 2 Files Affected:
diff --git a/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp b/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp
index aac24f113d891f..b1a971e3e9e8eb 100644
--- a/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp
+++ b/mlir/lib/Conversion/ArithToLLVM/ArithToLLVM.cpp
@@ -13,6 +13,7 @@
#include "mlir/Conversion/LLVMCommon/ConversionTarget.h"
#include "mlir/Conversion/LLVMCommon/VectorPattern.h"
#include "mlir/Dialect/Arith/IR/Arith.h"
+#include "mlir/Dialect/Arith/Transforms/Passes.h"
#include "mlir/Dialect/LLVMIR/LLVMAttrs.h"
#include "mlir/Dialect/LLVMIR/LLVMDialect.h"
#include "mlir/IR/TypeUtilities.h"
@@ -477,7 +478,8 @@ struct ArithToLLVMConversionPass
options.overrideIndexBitwidth(indexBitwidth);
LLVMTypeConverter converter(&getContext(), options);
- mlir::arith::populateArithToLLVMConversionPatterns(converter, patterns);
+ arith::populateArithExpandOpsPatterns(patterns);
+ arith::populateArithToLLVMConversionPatterns(converter, patterns);
if (failed(applyPartialConversion(getOperation(), target,
std::move(patterns))))
@@ -503,6 +505,7 @@ struct ArithToLLVMDialectInterface : public ConvertToLLVMPatternInterface {
void populateConvertToLLVMConversionPatterns(
ConversionTarget &target, LLVMTypeConverter &typeConverter,
RewritePatternSet &patterns) const final {
+ arith::populateArithExpandOpsPatterns(patterns);
arith::populateArithToLLVMConversionPatterns(typeConverter, patterns);
}
};
diff --git a/mlir/test/Conversion/ArithToLLVM/arith-to-llvm.mlir b/mlir/test/Conversion/ArithToLLVM/arith-to-llvm.mlir
index 64c40f1aba43bc..a9dcc0a16b3dbd 100644
--- a/mlir/test/Conversion/ArithToLLVM/arith-to-llvm.mlir
+++ b/mlir/test/Conversion/ArithToLLVM/arith-to-llvm.mlir
@@ -540,6 +540,68 @@ func.func @select(%arg0 : i1, %arg1 : i32, %arg2 : i32) -> i32 {
// -----
+// CHECK-LABEL: @ceildivsi
+// CHECK-SAME: %[[ARG0:.*]]: i64) -> i64
+func.func @ceildivsi(%arg0 : i64) -> i64 {
+ // CHECK: %[[CST0:.*]] = llvm.mlir.constant(1 : i64) : i64
+ // CHECK: %[[CST1:.*]] = llvm.mlir.constant(0 : i64) : i64
+ // CHECK: %[[CST2:.*]] = llvm.mlir.constant(-1 : i64) : i64
+ // CHECK: %[[CMP0:.*]] = llvm.icmp "sgt" %[[ARG0]], %[[CST1]] : i64
+ // CHECK: %[[SEL0:.*]] = llvm.select %[[CMP0]], %[[CST2]], %[[CST0]] : i1, i64
+ // CHECK: %[[ADD0:.*]] = llvm.add %[[SEL0]], %[[ARG0]] : i64
+ // CHECK: %[[DIV0:.*]] = llvm.sdiv %[[ADD0]], %[[ARG0]] : i64
+ // CHECK: %[[ADD1:.*]] = llvm.add %[[DIV0]], %[[CST0]] : i64
+ // CHECK: %[[SUB0:.*]] = llvm.sub %[[CST1]], %[[ARG0]] : i64
+ // CHECK: %[[DIV1:.*]] = llvm.sdiv %[[SUB0]], %[[ARG0]] : i64
+ // CHECK: %[[SUB1:.*]] = llvm.sub %[[CST1]], %[[DIV1]] : i64
+ // CHECK: %[[CMP1:.*]] = llvm.icmp "slt" %[[ARG0]], %[[CST1]] : i64
+ // CHECK: %[[CMP2:.*]] = llvm.icmp "sgt" %[[ARG0]], %[[CST1]] : i64
+ // CHECK: %[[CMP3:.*]] = llvm.icmp "slt" %[[ARG0]], %[[CST1]] : i64
+ // CHECK: %[[CMP4:.*]] = llvm.icmp "sgt" %[[ARG0]], %[[CST1]] : i64
+ // CHECK: %[[AND0:.*]] = llvm.and %[[CMP1]], %[[CMP3]] : i1
+ // CHECK: %[[AND1:.*]] = llvm.and %[[CMP2]], %[[CMP4]] : i1
+ // CHECK: %[[OR:.*]] = llvm.or %[[AND0]], %[[AND1]] : i1
+ // CHECK: %[[SEL1:.*]] = llvm.select %[[OR]], %[[ADD1]], %[[SUB1]] : i1, i64
+ %0 = arith.ceildivsi %arg0, %arg0 : i64
+ return %0: i64
+}
+
+// CHECK-LABEL: @ceildivui
+// CHECK-SAME: %[[ARG0:.*]]: i32) -> i32
+func.func @ceildivui(%arg0 : i32) -> i32 {
+// CHECK: %[[CST0:.*]] = llvm.mlir.constant(0 : i32) : i32
+// CHECK: %[[CMP0:.*]] = llvm.icmp "eq" %[[ARG0]], %[[CST0]] : i32
+// CHECK: %[[CST1:.*]] = llvm.mlir.constant(1 : i32) : i32
+// CHECK: %[[SUB0:.*]] = llvm.sub %[[ARG0]], %[[CST1]] : i32
+// CHECK: %[[DIV0:.*]] = llvm.udiv %[[SUB0]], %[[ARG0]] : i32
+// CHECK: %[[ADD0:.*]] = llvm.add %[[DIV0]], %[[CST1]] : i32
+// CHECK: %[[SEL0:.*]] = llvm.select %[[CMP0]], %[[CST0]], %[[ADD0]] : i1, i32
+ %0 = arith.ceildivui %arg0, %arg0 : i32
+ return %0: i32
+}
+
+// -----
+
+// CHECK-LABEL: @floordivsi
+// CHECK-SAME: %[[ARG0:.*]]: i32, %[[ARG1:.*]]: i32) -> i32
+func.func @floordivsi(%arg0 : i32, %arg1 : i32) -> i32 {
+ // CHECK: %[[SDIV:.*]] = llvm.sdiv %[[ARG0]], %[[ARG1]] : i32
+ // CHECK: %[[MUL0:.*]] = llvm.mul %[[SDIV]], %[[ARG1]] : i32
+ // CHECK: %[[CMP0:.*]] = llvm.icmp "ne" %[[ARG0]], %[[MUL0]] : i32
+ // CHECK: %[[CST0:.*]] = llvm.mlir.constant(0 : i32) : i32
+ // CHECK: %[[CMP1:.*]] = llvm.icmp "slt" %[[ARG0]], %[[CST0]] : i32
+ // CHECK: %[[CMP2:.*]] = llvm.icmp "slt" %[[ARG1]], %[[CST0]] : i32
+ // CHECK: %[[CMP3:.*]] = llvm.icmp "ne" %[[CMP1]], %[[CMP2]] : i1
+ // CHECK: %[[AND:.*]] = llvm.and %[[CMP0]], %[[CMP3]] : i1
+ // CHECK: %[[CST1:.*]] = llvm.mlir.constant(-1 : i32) : i32
+ // CHECK: %[[ADD:.*]] = llvm.add %[[SDIV]], %[[CST1]] : i32
+ // CHECK: %[[SEL:.*]] = llvm.select %[[AND]], %[[ADD]], %[[SDIV]] : i1, i32
+ %0 = arith.floordivsi %arg0, %arg1 : i32
+ return %0 : i32
+}
+
+// -----
+
// CHECK-LABEL: @minmaxi
func.func @minmaxi(%arg0 : i32, %arg1 : i32) -> i32 {
// CHECK: = llvm.intr.smin(%arg0, %arg1) : (i32, i32) -> i32
|
Sorry I forgot to submit it after running the draft tests. 🙄 |
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.
Given the context, I'll argue for mlir::arith::populateCeilFloorDivExpandOpsPatterns
specifically.
The other "expand" patterns include things like expanding minsi
or maxui
, which have LLVM lowerings, and we don't want to add those here.
@@ -503,6 +505,7 @@ struct ArithToLLVMDialectInterface : public ConvertToLLVMPatternInterface { | |||
void populateConvertToLLVMConversionPatterns( | |||
ConversionTarget &target, LLVMTypeConverter &typeConverter, | |||
RewritePatternSet &patterns) const final { | |||
arith::populateArithExpandOpsPatterns(patterns); | |||
arith::populateArithToLLVMConversionPatterns(typeConverter, patterns); | |||
} | |||
}; |
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.
This pass is kind of deprecated: we're supposed to migrate to --convert-to-llvm
.
I'm concerned by additions here that wouldn't carry over to --convert-to-llvm
!
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 am not completely sure of what you mean.
The tests mlir/test/Conversion/ArithToLLVM/arith-to-llvm.mlir
calls both convert-arith-to-llvm
and --convert-to-llvm
. If either arith-to-llvm or convert-to-llvm is updated, the other must be updated as well.
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.
@nujaa , wouldn't adding this in "ConvertToLLVMPass.cpp" instead also work?
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 confused because you're only changing the ArithToLLVMConversionPass
here, so was this behavior already implemented in the convert-to-llvm
flow and you're just catching up?
(I guess that makes my point as well somehow: we should remove the convert-arith-to-llvm
pass: it does not provide anything that convert-to-llvm
can't do, hopefully).
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.
@nujaa , wouldn't adding this in "ConvertToLLVMPass.cpp" instead also work?
I think it is Arith specific and should not be part of generic ConvertToLLVMPass
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.
so was this behavior already implemented in the
convert-to-llvm
flow and you're just catching up?
Neither arith-to-llvm nor convert-to-llvm was not expanding ops. As the test runs both with the same CHECK-lines.
Good catch, thanks. |
✅ With the latest revision this PR passed the C/C++ code formatter. |
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.
Removing my hold
A dependency on MLIRArithTransforms seems to be missing, CI is failing: /usr/bin/ld: tools/mlir/lib/Conversion/ArithToLLVM/CMakeFiles/obj.MLIRArithToLLVM.dir/ArithToLLVM.cpp.o: in function See: |
Another option is to move that code that into MLIRArithUtils if we do not want to depend on MLIRArithTransforms |
Failing bot: * https://lab.llvm.org/buildbot/#/builders/138/builds/729 Also, not all discussions have been resolved: * llvm#117305 (comment) This reverts commit 2c739df.
Reverted. @nujaa , this shouldn't land while there's an ongoing design discussion on the suitable placement of these patterns. EDIT Just to clarify. I know @krzysz00 has already approved this.That was effectively LGTM without any qualification (we're missing "explicit" LGTM, but that's beside the point). From How Patch is Accepted:
I just don't believe that all feedback has been addressed - especially given that the discussion continued post-LGTM :) And then the failing bot. |
Yes, Sorry, I didn't see the upper comments until I merged following the approval and passing tests. My bad. |
No worries, I also find GitHub quite tricky to navigate. Note that we have a very liberal "revert" policy in LLVM - please don't let this discourage you from contributing! :) |
Alright. Thanks both for reverting, pointing it out and the motivation. I could not find guidelines on how to revert a commit without going through the MR review process. Do I simply push the revert commit without waiting for approval ? Before I submit any fix, I would like to make sure of a few things :
If I am not mistaken,
I think Thanks again all for your patience. |
There's a few relevant parts to consider here. First, the revert policy: And indeed, it does not discuss "how". However, note:
And then, under obtaining-commit-access
From my experience, "reverts" are where you tend to 100% rely on your judgement - it's the easiest and quickest way to fix buildbot failures. In more complex situation (e.g. no buildbot breakage upstream, but some issues downstream), we tend use PRs. But even then, if a repro has been shared, folks tend to revert. This way patch authors are not under pressure to fix immediately (sometimes that's just physically not possible).
No worries Hugo, this is standard practice ;-) |
OK, this is what we were missing :) And apologies, I forgot how Like you said, llvm-project/mlir/lib/Conversion/ConvertToLLVM/ConvertToLLVMPass.cpp Lines 118 to 122 in 52b9d0b
And that's what's being updated here. But you are also updating the
Is this accurate?
Considering Mehdi's comment re this path being deprecated in favour of |
The confusion to me came from comments like:
I think an answer that would have resolved the discussion immediately could have been along the line of:
We should be all good now I think. |
Arith Floor and Ceil ops would not get lowered when running --convert-arith-to-llvm.
… (Reland) (#118839) When running `convert-to-llvm`, `ceildiv` and `floordiv` ops, which do not have direct llvm conversion pattern, would not get lowered to llvm dialect. This patch adds CeilFloorDivExpandOpsPatterns to both `convert-to-llvm` and `arith-to-llvm` (deprecated) lowering those ops to lower level arith ops which can be lowered to llvm using LLVM conversion. Reland of #117305 after buildbot failures. See: https://lab.llvm.org/buildbot/#/builders/80/builds/7168 https://lab.llvm.org/buildbot/#/builders/130/builds/7036 https://lab.llvm.org/buildbot/#/builders/138/builds/7290 Added dependence to ArithTransforms in ArithToLLVM. In previous discussion, it has been suggested to move the CeilFloorDivExpandOpsPatterns to ArithUtils but I think linking ArithTransforms makes more sense as otherwise : * ArithToLLVM needs a new dependency to ArithUtils * ArithUtils needs new dependency to ArithTransforms or move the patterns as well which will create more dependencies * It creates lots of code motion which makes it hard to review.
Arith Floor and Ceil ops would not get lowered when running --convert-arith-to-llvm.