diff --git a/mlir/test/lib/TestDialect/TestOps.td b/mlir/test/lib/TestDialect/TestOps.td index 890c1c6b4982..84f2f37db44e 100644 --- a/mlir/test/lib/TestDialect/TestOps.td +++ b/mlir/test/lib/TestDialect/TestOps.td @@ -219,6 +219,59 @@ def : Pat<(OpD $input), (OpF $input), [], (addBenefit 10)>; def : Pat<(OpG $input), (OpB $input, ConstantAttr:$attr)>; def : Pat<(OpG (OpG $input)), (OpB $input, ConstantAttr:$attr)>; +// Test NativeCodeCall. +def OpNativeCodeCall1 : TEST_Op<"native_code_call1"> { + let arguments = (ins + I32:$input1, I32:$input2, + BoolAttr:$choice, + I64Attr:$attr1, I64Attr:$attr2 + ); + let results = (outs I32:$output); +} +def OpNativeCodeCall2 : TEST_Op<"native_code_call2"> { + let arguments = (ins I32:$input, I64ArrayAttr:$attr); + let results = (outs I32:$output); +} +// Native code call to invoke a C++ function +def CreateOperand: NativeCodeCall<"chooseOperand($0, $1, $2)">; +// Native code call to invoke a C++ expression +def CreateArraryAttr: NativeCodeCall<"$_builder.getArrayAttr({$0, $1})">; +// Test that we can use NativeCodeCall to create operand and attribute. +// This pattern chooses between $input1 and $input2 according to $choice and +// it combines $attr1 and $attr2 into an array attribute. +def : Pat<(OpNativeCodeCall1 $input1, $input2, + ConstBoolAttrTrue:$choice, $attr1, $attr2), + (OpNativeCodeCall2 (CreateOperand $input1, $input2, $choice), + (CreateArraryAttr $attr1, $attr2))>; +// Note: the following is just for testing purpose. +// Should use the replaceWithValue directive instead. +def UseOpResult: NativeCodeCall<"$0">; +// Test that we can use NativeCodeCall to create result. +def : Pat<(OpNativeCodeCall1 $input1, $input2, + ConstBoolAttrFalse, $attr1, $attr2), + (UseOpResult $input2)>; + +// Test AllAttrConstraintsOf. +def OpAllAttrConstraint1 : TEST_Op<"all_attr_constraint_of1"> { + let arguments = (ins I64ArrayAttr:$attr); + let results = (outs I32:$output); +} +def OpAllAttrConstraint2 : TEST_Op<"all_attr_constraint_of2"> { + let arguments = (ins I64ArrayAttr:$attr); + let results = (outs I32:$output); +} +def Constraint0 : AttrConstraint< + CPred<"$_self.cast().getValue()[0]." + "cast().getInt() == 0">, + "[0] == 0">; +def Constraint1 : AttrConstraint< + CPred<"$_self.cast().getValue()[1]." + "cast().getInt() == 1">, + "[1] == 1">; +def : Pat<(OpAllAttrConstraint1 + AllAttrConstraintsOf<[Constraint0, Constraint1]>:$attr), + (OpAllAttrConstraint2 $attr)>; + //===----------------------------------------------------------------------===// // Test Patterns (Attributes) diff --git a/mlir/test/lib/TestDialect/TestPatterns.cpp b/mlir/test/lib/TestDialect/TestPatterns.cpp index bde01f76e35f..096b4545bb66 100644 --- a/mlir/test/lib/TestDialect/TestPatterns.cpp +++ b/mlir/test/lib/TestDialect/TestPatterns.cpp @@ -21,6 +21,11 @@ #include "mlir/Transforms/DialectConversion.h" using namespace mlir; +// Native function for testing NativeCodeCall +static Value *chooseOperand(Value *input1, Value *input2, BoolAttr choice) { + return choice.getValue() ? input1 : input2; +} + namespace { #include "TestPatterns.inc" } // end anonymous namespace diff --git a/mlir/test/mlir-tblgen/pattern-NativeCodeCall.td b/mlir/test/mlir-tblgen/pattern-NativeCodeCall.td deleted file mode 100644 index 015a3c31be9b..000000000000 --- a/mlir/test/mlir-tblgen/pattern-NativeCodeCall.td +++ /dev/null @@ -1,42 +0,0 @@ -// RUN: mlir-tblgen -gen-rewriters -I %S/../../include %s | FileCheck %s - -include "mlir/IR/OpBase.td" - -def Test_Dialect : Dialect { - let name = "test"; - let cppNamespace = "NS"; -} -class NS_Op traits> : - Op; - -def CreateOperand : NativeCodeCall<"buildOperand($0, $1)">; -def CreateArrayAttr : NativeCodeCall<"$_builder.getArrayAttr({$0, $1})">; -def CreateOpResult : NativeCodeCall<"buildOp($0, $1)">; - -def NS_AOp : NS_Op<"a_op", []> { - let arguments = (ins I32:$input1, I32:$input2, I32Attr:$attr); - let results = (outs I32:$output); -} - -def NS_BOp : NS_Op<"b_op", []> { - let arguments = (ins I32:$input, I32Attr:$attr); - let results = (outs I32:$output); -} - -def TestCreateOpResult : Pat< - (NS_BOp $input, $attr), - (CreateOpResult $input, $attr)>; - -// CHECK-LABEL: TestCreateOpResult - -// CHECK: rewriter.replaceOp(op, {buildOp(s.input, s.attr)}); - -def TestCreateOperandAndAttr : Pat< - (NS_AOp $input1, $input2, $attr), - (NS_BOp (CreateOperand $input1, $input2), (CreateArrayAttr $attr, $attr))>; - -// CHECK-LABEL: TestCreateOperandAndAttr - -// CHECK: rewriter.create -// CHECK-NEXT: buildOperand(s.input1, s.input2), -// CHECK-NEXT: rewriter.getArrayAttr({s.attr, s.attr}) diff --git a/mlir/test/mlir-tblgen/pattern-allof-attr.td b/mlir/test/mlir-tblgen/pattern-allof-attr.td deleted file mode 100644 index 38f73ff9b67f..000000000000 --- a/mlir/test/mlir-tblgen/pattern-allof-attr.td +++ /dev/null @@ -1,41 +0,0 @@ -// RUN: mlir-tblgen -gen-rewriters -I %S/../../include %s | FileCheck %s - -include "mlir/IR/OpBase.td" - -def Test_Dialect : Dialect { - let name = "test"; -} -class NS_Op traits> : - Op; - -def FirstConstraint : AttrConstraint, - "first constraint">; -def SecondConstraint : AttrConstraint, - "second constraint">; -def ThirdConstraint : AttrConstraint, - "third constraint">; - -def OpA : NS_Op<"op_a", []> { - let arguments = (ins - I32Attr:$attr - ); - - let results = (outs I32:$result); -} - -def : Pat< - (OpA AllAttrConstraintsOf< - [FirstConstraint, - SecondConstraint, - ThirdConstraint]>:$more), - (OpA $more)>; - -// Test combining AttrConstraint during pattern match. -// --- - -// CHECK-LABEL: struct GeneratedConvert0 - -// CHECK: auto attr = op0->getAttrOfType("attr"); -// CHECK: if (!(((FirstConstraint)) && ((SecondConstraint)) && ((ThirdConstraint)))) return matchFailure(); -// CHECK-NEXT: s.more = attr; - diff --git a/mlir/test/mlir-tblgen/pattern.mlir b/mlir/test/mlir-tblgen/pattern.mlir index 9dbf24d1dd1b..0633d282ba68 100644 --- a/mlir/test/mlir-tblgen/pattern.mlir +++ b/mlir/test/mlir-tblgen/pattern.mlir @@ -21,6 +21,26 @@ func @verifyBenefit(%arg0 : i32) -> i32 { return %0 : i32 } +// CHECK-LABEL: verifyNativeCodeCall +func @verifyNativeCodeCall(%arg0: i32, %arg1: i32) -> (i32, i32) { + // CHECK: %0 = "test.native_code_call2"(%arg0) {attr = [42, 24]} : (i32) -> i32 + // CHECK: return %0, %arg1 + %0 = "test.native_code_call1"(%arg0, %arg1) {choice = true, attr1 = 42, attr2 = 24} : (i32, i32) -> (i32) + %1 = "test.native_code_call1"(%arg0, %arg1) {choice = false, attr1 = 42, attr2 = 24} : (i32, i32) -> (i32) + return %0, %1: i32, i32 +} + +// CHECK-LABEL: verifyAllAttrConstraintOf +func @verifyAllAttrConstraintOf() -> (i32, i32, i32) { + // CHECK: "test.all_attr_constraint_of2" + %0 = "test.all_attr_constraint_of1"() {attr = [0, 1]} : () -> (i32) + // CHECK: "test.all_attr_constraint_of1" + %1 = "test.all_attr_constraint_of1"() {attr = [0, 2]} : () -> (i32) + // CHECK: "test.all_attr_constraint_of1" + %2 = "test.all_attr_constraint_of1"() {attr = [-1, 1]} : () -> (i32) + return %0, %1, %2: i32, i32, i32 +} + //===----------------------------------------------------------------------===// // Test Attributes //===----------------------------------------------------------------------===//