brintos

brintos / llvm-project-archived public Read only

0
0
Text · 30.4 KiB · ed6407a Raw
759 lines · plain
1// RUN: mlir-opt -split-input-file -convert-pdl-to-pdl-interp %s | FileCheck %s2 3// CHECK-LABEL: module @empty_module4module @empty_module {5// CHECK: func @matcher(%{{.*}}: !pdl.operation)6// CHECK-NEXT: pdl_interp.finalize7}8 9// -----10 11// CHECK-LABEL: module @simple12module @simple {13  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)14  // CHECK:   pdl_interp.check_operation_name of %[[ROOT]] is "foo.op" -> ^bb2, ^bb115  // CHECK: ^bb1:16  // CHECK:   pdl_interp.finalize17  // CHECK: ^bb2:18  // CHECK:   pdl_interp.check_operand_count of %[[ROOT]] is 0 -> ^bb3, ^bb119  // CHECK: ^bb3:20  // CHECK:   pdl_interp.check_result_count of %[[ROOT]] is 0 -> ^bb4, ^bb121  // CHECK: ^bb4:22  // CHECK:   pdl_interp.record_match @rewriters::@pdl_generated_rewriter23  // CHECK-SAME: benefit(1), loc([%[[ROOT]]]), root("foo.op") -> ^bb124 25  // CHECK: module @rewriters26  // CHECK:   func @pdl_generated_rewriter(%[[REWRITE_ROOT:.*]]: !pdl.operation)27  // CHECK:     pdl_interp.apply_rewrite "rewriter"(%[[REWRITE_ROOT]]28  // CHECK:     pdl_interp.finalize29  pdl.pattern : benefit(1) {30    %root = operation "foo.op"31    rewrite %root with "rewriter"32  }33}34 35// -----36 37// CHECK-LABEL: module @attributes38module @attributes {39  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)40  // Check the value of "attr".41  // CHECK-DAG:   %[[ATTR:.*]] = pdl_interp.get_attribute "attr" of %[[ROOT]]42  // CHECK-DAG:   pdl_interp.is_not_null %[[ATTR]] : !pdl.attribute43  // CHECK-DAG:   pdl_interp.check_attribute %[[ATTR]] is 10 : i6444 45  // Check the type of "attr1".46  // CHECK-DAG:   %[[ATTR1:.*]] = pdl_interp.get_attribute "attr1" of %[[ROOT]]47  // CHECK-DAG:   pdl_interp.is_not_null %[[ATTR1]] : !pdl.attribute48  // CHECK-DAG:   %[[ATTR1_TYPE:.*]] = pdl_interp.get_attribute_type of %[[ATTR1]]49  // CHECK-DAG:   pdl_interp.check_type %[[ATTR1_TYPE]] is i6450  pdl.pattern : benefit(1) {51    %type = type : i6452    %attr = attribute = 10 : i6453    %attr1 = attribute : %type54    %root = operation {"attr" = %attr, "attr1" = %attr1}55    rewrite %root with "rewriter"56  }57}58 59// -----60 61// CHECK-LABEL: module @constraints62module @constraints {63  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)64  // CHECK-DAG:   %[[INPUT:.*]] = pdl_interp.get_operand 0 of %[[ROOT]]65  // CHECK-DAG:   %[[INPUT1:.*]] = pdl_interp.get_operand 1 of %[[ROOT]]66  // CHECK-DAG:   %[[RESULT:.*]] = pdl_interp.get_result 0 of %[[ROOT]]67  // CHECK:       pdl_interp.apply_constraint "multi_constraint"(%[[INPUT]], %[[INPUT1]], %[[RESULT]]68 69  pdl.pattern : benefit(1) {70    %input0 = operand71    %input1 = operand72    %root = operation(%input0, %input1 : !pdl.value, !pdl.value)73    %result0 = result 0 of %root74 75    pdl.apply_native_constraint "multi_constraint"(%input0, %input1, %result0 : !pdl.value, !pdl.value, !pdl.value)76    rewrite %root with "rewriter"77  }78}79 80// -----81 82// CHECK-LABEL: module @constraint_with_result83module @constraint_with_result {84  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)85  // CHECK: %[[ATTR:.*]] = pdl_interp.apply_constraint "check_op_and_get_attr_constr"(%[[ROOT]]86  // CHECK: pdl_interp.record_match @rewriters::@pdl_generated_rewriter(%[[ROOT]], %[[ATTR]] : !pdl.operation, !pdl.attribute)87  pdl.pattern : benefit(1) {88    %root = operation89    %attr = pdl.apply_native_constraint "check_op_and_get_attr_constr"(%root : !pdl.operation) : !pdl.attribute90    rewrite %root with "rewriter"(%attr : !pdl.attribute)91  }92}93 94// -----95 96// CHECK-LABEL: module @constraint_with_unused_result97module @constraint_with_unused_result {98  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)99  // CHECK: %[[ATTR:.*]] = pdl_interp.apply_constraint "check_op_and_get_attr_constr"(%[[ROOT]]100  // CHECK: pdl_interp.record_match @rewriters::@pdl_generated_rewriter(%[[ROOT]] : !pdl.operation)101  pdl.pattern : benefit(1) {102    %root = operation103    %attr = pdl.apply_native_constraint "check_op_and_get_attr_constr"(%root : !pdl.operation) : !pdl.attribute104    rewrite %root with "rewriter"105  }106}107 108// -----109 110// CHECK-LABEL: module @constraint_with_result_multiple111module @constraint_with_result_multiple {112  // check that native constraints work as expected even when multiple identical constraints are fused113 114  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)115  // CHECK: %[[ATTR:.*]] = pdl_interp.apply_constraint "check_op_and_get_attr_constr"(%[[ROOT]]116  // CHECK-NOT: pdl_interp.apply_constraint "check_op_and_get_attr_constr"117  // CHECK: pdl_interp.record_match @rewriters::@pdl_generated_rewriter_0(%[[ROOT]], %[[ATTR]]  : !pdl.operation, !pdl.attribute)118  // CHECK: pdl_interp.record_match @rewriters::@pdl_generated_rewriter(%[[ROOT]], %[[ATTR]] : !pdl.operation, !pdl.attribute)119  pdl.pattern : benefit(1) {120    %root = operation121    %attr = pdl.apply_native_constraint "check_op_and_get_attr_constr"(%root : !pdl.operation) : !pdl.attribute122    rewrite %root with "rewriter"(%attr : !pdl.attribute)123  }124  pdl.pattern : benefit(1) {125    %root = operation126    %attr = pdl.apply_native_constraint "check_op_and_get_attr_constr"(%root : !pdl.operation) : !pdl.attribute127    rewrite %root with "rewriter"(%attr : !pdl.attribute)128  }129}130 131// -----132 133// CHECK-LABEL: module @negated_constraint134module @negated_constraint {135  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)136  // CHECK: pdl_interp.apply_constraint "constraint"(%[[ROOT]] : !pdl.operation) {isNegated = true}137  // CHECK: pdl_interp.record_match @rewriters::@pdl_generated_rewriter(%[[ROOT]] : !pdl.operation)138  pdl.pattern : benefit(1) {139    %root = operation140    pdl.apply_native_constraint "constraint"(%root : !pdl.operation) {isNegated = true}141    rewrite %root with "rewriter"142  }143}144 145// -----146 147// CHECK-LABEL: module @inputs148module @inputs {149  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)150  // CHECK-DAG: pdl_interp.check_operand_count of %[[ROOT]] is 2151 152  // Get the input and check the type.153  // CHECK-DAG:   %[[INPUT:.*]] = pdl_interp.get_operand 0 of %[[ROOT]]154  // CHECK-DAG:   pdl_interp.is_not_null %[[INPUT]] : !pdl.value155  // CHECK-DAG:   %[[INPUT_TYPE:.*]] = pdl_interp.get_value_type of %[[INPUT]]156  // CHECK-DAG:   pdl_interp.check_type %[[INPUT_TYPE]] is i64157 158  // Get the second operand and check that it is equal to the first.159  // CHECK-DAG:  %[[INPUT1:.*]] = pdl_interp.get_operand 1 of %[[ROOT]]160  // CHECK-DAG:  pdl_interp.are_equal %[[INPUT]], %[[INPUT1]] : !pdl.value161  pdl.pattern : benefit(1) {162    %type = type : i64163    %input = operand : %type164    %root = operation(%input, %input : !pdl.value, !pdl.value)165    rewrite %root with "rewriter"166  }167}168 169// -----170 171// CHECK-LABEL: module @variadic_inputs172module @variadic_inputs {173  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)174  // CHECK-DAG: pdl_interp.check_operand_count of %[[ROOT]] is at_least 2175 176  // The first operand has a known index.177  // CHECK-DAG:   %[[INPUT:.*]] = pdl_interp.get_operand 0 of %[[ROOT]]178  // CHECK-DAG:   pdl_interp.is_not_null %[[INPUT]] : !pdl.value179 180  // The second operand is a group of unknown size, with a type constraint.181  // CHECK-DAG:   %[[VAR_INPUTS:.*]] = pdl_interp.get_operands 1 of %[[ROOT]] : !pdl.range<value>182  // CHECK-DAG:   pdl_interp.is_not_null %[[VAR_INPUTS]] : !pdl.range<value>183 184  // CHECK-DAG:   %[[INPUT_TYPE:.*]] = pdl_interp.get_value_type of %[[VAR_INPUTS]] : !pdl.range<type>185  // CHECK-DAG:   pdl_interp.check_types %[[INPUT_TYPE]] are [i64]186 187  // The third operand is at an unknown offset due to operand 2, but is expected188  // to be of size 1.189  // CHECK-DAG:  %[[INPUT2:.*]] = pdl_interp.get_operands 2 of %[[ROOT]] : !pdl.value190  // CHECK-DAG:  pdl_interp.are_equal %[[INPUT]], %[[INPUT2]] : !pdl.value191  pdl.pattern : benefit(1) {192    %types = types : [i64]193    %inputs = operands : %types194    %input = operand195    %root = operation(%input, %inputs, %input : !pdl.value, !pdl.range<value>, !pdl.value)196    rewrite %root with "rewriter"197  }198}199 200// -----201 202// CHECK-LABEL: module @single_operand_range203module @single_operand_range {204  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)205 206  // Check that the operand range is treated as all of the operands of the207  // operation.208  // CHECK-DAG:   %[[RESULTS:.*]] = pdl_interp.get_operands of %[[ROOT]]209  // CHECK-DAG:   %[[RESULT_TYPES:.*]] = pdl_interp.get_value_type of %[[RESULTS]] : !pdl.range<type>210  // CHECK-DAG:   pdl_interp.check_types %[[RESULT_TYPES]] are [i64]211 212  // The operand count is unknown, so there is no need to check for it.213  // CHECK-NOT: pdl_interp.check_operand_count214  pdl.pattern : benefit(1) {215    %types = types : [i64]216    %operands = operands : %types217    %root = operation(%operands : !pdl.range<value>)218    rewrite %root with "rewriter"219  }220}221 222// -----223 224// CHECK-LABEL: module @results225module @results {226  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)227  // CHECK:   pdl_interp.check_result_count of %[[ROOT]] is 2228 229  // Get the result and check the type.230  // CHECK-DAG:   %[[RESULT:.*]] = pdl_interp.get_result 0 of %[[ROOT]]231  // CHECK-DAG:   pdl_interp.is_not_null %[[RESULT]] : !pdl.value232  // CHECK-DAG:   %[[RESULT_TYPE:.*]] = pdl_interp.get_value_type of %[[RESULT]]233  // CHECK-DAG:   pdl_interp.check_type %[[RESULT_TYPE]] is i32234 235  // The second result doesn't have any constraints, so we don't generate an236  // access for it.237  // CHECK-NOT:   pdl_interp.get_result 1 of %[[ROOT]]238  pdl.pattern : benefit(1) {239    %type1 = type : i32240    %type2 = type241    %root = operation -> (%type1, %type2 : !pdl.type, !pdl.type)242    rewrite %root with "rewriter"243  }244}245 246// -----247 248// CHECK-LABEL: module @variadic_results249module @variadic_results {250  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)251  // CHECK-DAG: pdl_interp.check_result_count of %[[ROOT]] is at_least 2252 253  // The first result has a known index.254  // CHECK-DAG:   %[[RESULT:.*]] = pdl_interp.get_result 0 of %[[ROOT]]255  // CHECK-DAG:   pdl_interp.is_not_null %[[RESULT]] : !pdl.value256 257  // The second result is a group of unknown size, with a type constraint.258  // CHECK-DAG:   %[[VAR_RESULTS:.*]] = pdl_interp.get_results 1 of %[[ROOT]] : !pdl.range<value>259  // CHECK-DAG:   pdl_interp.is_not_null %[[VAR_RESULTS]] : !pdl.range<value>260 261  // CHECK-DAG:   %[[RESULT_TYPE:.*]] = pdl_interp.get_value_type of %[[VAR_RESULTS]] : !pdl.range<type>262  // CHECK-DAG:   pdl_interp.check_types %[[RESULT_TYPE]] are [i64]263 264  // The third result is at an unknown offset due to result 1, but is expected265  // to be of size 1.266  // CHECK-DAG:  %[[RESULT2:.*]] = pdl_interp.get_results 2 of %[[ROOT]] : !pdl.value267  // CHECK-DAG:   pdl_interp.is_not_null %[[RESULT2]] : !pdl.value268  pdl.pattern : benefit(1) {269    %types = types : [i64]270    %type = type271    %root = operation -> (%type, %types, %type : !pdl.type, !pdl.range<type>, !pdl.type)272    rewrite %root with "rewriter"273  }274}275 276// -----277 278// CHECK-LABEL: module @single_result_range279module @single_result_range {280  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)281 282  // Check that the result range is treated as all of the results of the283  // operation.284  // CHECK-DAG:   %[[RESULTS:.*]] = pdl_interp.get_results of %[[ROOT]]285  // CHECK-DAG:   %[[RESULT_TYPES:.*]] = pdl_interp.get_value_type of %[[RESULTS]] : !pdl.range<type>286  // CHECK-DAG:   pdl_interp.check_types %[[RESULT_TYPES]] are [i64]287 288  // The result count is unknown, so there is no need to check for it.289  // CHECK-NOT: pdl_interp.check_result_count290  pdl.pattern : benefit(1) {291    %types = types : [i64]292    %root = operation -> (%types : !pdl.range<type>)293    rewrite %root with "rewriter"294  }295}296 297// -----298 299// CHECK-LABEL: module @results_as_operands300module @results_as_operands {301  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)302 303  // Get the first result and check it matches the first operand.304  // CHECK-DAG:   %[[OPERAND_0:.*]] = pdl_interp.get_operand 0 of %[[ROOT]]305  // CHECK-DAG:   %[[DEF_OP_0:.*]] = pdl_interp.get_defining_op of %[[OPERAND_0]]306  // CHECK-DAG:   %[[RESULT_0:.*]] = pdl_interp.get_result 0 of %[[DEF_OP_0]]307  // CHECK-DAG:   pdl_interp.are_equal %[[RESULT_0]], %[[OPERAND_0]]308 309  // Get the second result and check it matches the second operand.310  // CHECK-DAG:   %[[OPERAND_1:.*]] = pdl_interp.get_operand 1 of %[[ROOT]]311  // CHECK-DAG:   %[[DEF_OP_1:.*]] = pdl_interp.get_defining_op of %[[OPERAND_1]]312  // CHECK-DAG:   %[[RESULT_1:.*]] = pdl_interp.get_result 1 of %[[DEF_OP_1]]313  // CHECK-DAG:   pdl_interp.are_equal %[[RESULT_1]], %[[OPERAND_1]]314 315  // Check that the parent operation of both results is the same.316  // CHECK-DAG:   pdl_interp.are_equal %[[DEF_OP_0]], %[[DEF_OP_1]]317 318  pdl.pattern : benefit(1) {319    %type1 = type : i32320    %type2 = type321    %inputOp = operation -> (%type1, %type2 : !pdl.type, !pdl.type)322    %result1 = result 0 of %inputOp323    %result2 = result 1 of %inputOp324 325    %root = operation(%result1, %result2 : !pdl.value, !pdl.value)326    rewrite %root with "rewriter"327  }328}329 330// -----331 332// CHECK-LABEL: module @single_result_range_as_operands333module @single_result_range_as_operands {334  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)335  // CHECK-DAG:  %[[OPERANDS:.*]] = pdl_interp.get_operands of %[[ROOT]] : !pdl.range<value>336  // CHECK-DAG:  %[[OP:.*]] = pdl_interp.get_defining_op of %[[OPERANDS]] : !pdl.range<value>337  // CHECK-DAG:  pdl_interp.is_not_null %[[OP]]338  // CHECK-DAG:  %[[RESULTS:.*]] = pdl_interp.get_results of %[[OP]] : !pdl.range<value>339  // CHECK-DAG:  pdl_interp.are_equal %[[RESULTS]], %[[OPERANDS]] : !pdl.range<value>340 341  pdl.pattern : benefit(1) {342    %types = types343    %inputOp = operation -> (%types : !pdl.range<type>)344    %results = results of %inputOp345 346    %root = operation(%results : !pdl.range<value>)347    rewrite %root with "rewriter"348  }349}350 351// -----352 353// CHECK-LABEL: module @switch_single_result_type354module @switch_single_result_type {355  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)356  // CHECK:   %[[RESULT:.*]] = pdl_interp.get_result 0 of %[[ROOT]]357  // CHECK:   %[[RESULT_TYPE:.*]] = pdl_interp.get_value_type of %[[RESULT]]358  // CHECK:   pdl_interp.switch_type %[[RESULT_TYPE]] to [i32, i64]359  pdl.pattern : benefit(1) {360    %type = type : i32361    %root = operation -> (%type : !pdl.type)362    rewrite %root with "rewriter"363  }364  pdl.pattern : benefit(1) {365    %type = type : i64366    %root = operation -> (%type : !pdl.type)367    rewrite %root with "rewriter"368  }369}370 371// -----372 373// CHECK-LABEL: module @switch_result_types374module @switch_result_types {375  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)376  // CHECK:   %[[RESULTS:.*]] = pdl_interp.get_results of %[[ROOT]]377  // CHECK:   %[[RESULT_TYPES:.*]] = pdl_interp.get_value_type of %[[RESULTS]]378  // CHECK:   pdl_interp.switch_types %[[RESULT_TYPES]] to {{\[\[}}i32], [i64, i32]]379  pdl.pattern : benefit(1) {380    %types = types : [i32]381    %root = operation -> (%types : !pdl.range<type>)382    rewrite %root with "rewriter"383  }384  pdl.pattern : benefit(1) {385    %types = types : [i64, i32]386    %root = operation -> (%types : !pdl.range<type>)387    rewrite %root with "rewriter"388  }389}390 391// -----392 393// CHECK-LABEL: module @switch_operand_count_at_least394module @switch_operand_count_at_least {395  // Check that when there are multiple "at_least" checks, the failure branch396  // goes to the next one in increasing order.397 398  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)399  // CHECK: pdl_interp.check_operand_count of %[[ROOT]] is at_least 1 -> ^[[PATTERN_1_NEXT_BLOCK:.*]],400  // CHECK: ^bb2:401  // CHECK-NEXT: pdl_interp.check_operand_count of %[[ROOT]] is at_least 2402  // CHECK: ^[[PATTERN_1_NEXT_BLOCK]]:403  // CHECK-NEXT: {{.*}} -> ^{{.*}}, ^bb2404  pdl.pattern : benefit(1) {405    %operand = operand406    %operands = operands407    %root = operation(%operand, %operands : !pdl.value, !pdl.range<value>)408    rewrite %root with "rewriter"409  }410  pdl.pattern : benefit(1) {411    %operand = operand412    %operand2 = operand413    %operands = operands414    %root = operation(%operand, %operand2, %operands : !pdl.value, !pdl.value, !pdl.range<value>)415    rewrite %root with "rewriter"416  }417}418 419// -----420 421// CHECK-LABEL: module @switch_result_count_at_least422module @switch_result_count_at_least {423  // Check that when there are multiple "at_least" checks, the failure branch424  // goes to the next one in increasing order.425 426  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)427  // CHECK: pdl_interp.check_result_count of %[[ROOT]] is at_least 1 -> ^[[PATTERN_1_NEXT_BLOCK:.*]],428  // CHECK: ^[[PATTERN_2_BLOCK:[a-zA-Z_0-9]*]]:429  // CHECK: pdl_interp.check_result_count of %[[ROOT]] is at_least 2430  // CHECK: ^[[PATTERN_1_NEXT_BLOCK]]:431  // CHECK-NEXT: pdl_interp.get_result432  // CHECK-NEXT: pdl_interp.is_not_null {{.*}} -> ^{{.*}}, ^[[PATTERN_2_BLOCK]]433  pdl.pattern : benefit(1) {434    %type = type435    %types = types436    %root = operation -> (%type, %types : !pdl.type, !pdl.range<type>)437    rewrite %root with "rewriter"438  }439  pdl.pattern : benefit(1) {440    %type = type441    %type2 = type442    %types = types443    %root = operation -> (%type, %type2, %types : !pdl.type, !pdl.type, !pdl.range<type>)444    rewrite %root with "rewriter"445  }446}447 448 449// -----450 451// CHECK-LABEL: module @predicate_ordering452module @predicate_ordering {453  // Check that the result is checked for null first, before applying the454  // constraint. The null check is prevalent in both patterns, so should be455  // prioritized first.456 457  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)458  // CHECK:   %[[RESULT:.*]] = pdl_interp.get_result 0 of %[[ROOT]]459  // CHECK-NEXT: pdl_interp.is_not_null %[[RESULT]]460  // CHECK:   %[[RESULT_TYPE:.*]] = pdl_interp.get_value_type of %[[RESULT]]461  // CHECK: pdl_interp.apply_constraint "typeConstraint"(%[[RESULT_TYPE]]462 463  pdl.pattern : benefit(1) {464    %resultType = type465    pdl.apply_native_constraint "typeConstraint"(%resultType : !pdl.type)466    %root = operation -> (%resultType : !pdl.type)467    rewrite %root with "rewriter"468  }469 470  pdl.pattern : benefit(1) {471    %resultType = type472    %apply = operation -> (%resultType : !pdl.type)473    rewrite %apply with "rewriter"474  }475}476 477 478// -----479 480// CHECK-LABEL: module @multi_root481module @multi_root {482  // Check the lowering of a simple two-root pattern.483  // This checks that we correctly generate the pdl_interp.choose_op operation484  // and tie the break between %root1 and %root2 in favor of %root1.485 486  // CHECK: func @matcher(%[[ROOT1:.*]]: !pdl.operation)487  // CHECK-DAG: %[[VAL1:.*]] = pdl_interp.get_operand 0 of %[[ROOT1]]488  // CHECK-DAG: %[[OP1:.*]] = pdl_interp.get_defining_op of %[[VAL1]]489  // CHECK-DAG: %[[OPS:.*]] = pdl_interp.get_users of %[[VAL1]] : !pdl.value490  // CHECK-DAG: pdl_interp.foreach %[[ROOT2:.*]] : !pdl.operation in %[[OPS]]491  // CHECK-DAG:   %[[OPERANDS:.*]] = pdl_interp.get_operand 0 of %[[ROOT2]]492  // CHECK-DAG:   pdl_interp.are_equal %[[OPERANDS]], %[[VAL1]] : !pdl.value -> ^{{.*}}, ^[[CONTINUE:.*]]493  // CHECK-DAG:   pdl_interp.continue494  // CHECK-DAG:   %[[VAL2:.*]] = pdl_interp.get_operand 1 of %[[ROOT2]]495  // CHECK-DAG:   %[[OP2:.*]] = pdl_interp.get_defining_op of %[[VAL2]]496  // CHECK-DAG:   pdl_interp.is_not_null %[[OP1]] : !pdl.operation -> ^{{.*}}, ^[[CONTINUE]]497  // CHECK-DAG:   pdl_interp.is_not_null %[[OP2]] : !pdl.operation498  // CHECK-DAG:   pdl_interp.is_not_null %[[VAL1]] : !pdl.value499  // CHECK-DAG:   pdl_interp.is_not_null %[[VAL2]] : !pdl.value500  // CHECK-DAG:   pdl_interp.is_not_null %[[ROOT2]] : !pdl.operation501 502  pdl.pattern @rewrite_multi_root : benefit(1) {503    %input1 = operand504    %input2 = operand505    %type = type506    %op1 = operation(%input1 : !pdl.value) -> (%type : !pdl.type)507    %val1 = result 0 of %op1508    %root1 = operation(%val1 : !pdl.value)509    %op2 = operation(%input2 : !pdl.value) -> (%type : !pdl.type)510    %val2 = result 0 of %op2511    %root2 = operation(%val1, %val2 : !pdl.value, !pdl.value)512    rewrite %root1 with "rewriter"(%root2 : !pdl.operation)513  }514}515 516 517// -----518 519// CHECK-LABEL: module @overlapping_roots520module @overlapping_roots {521  // Check the lowering of a degenerate two-root pattern, where one root522  // is in the subtree rooted at another.523 524  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)525  // CHECK-DAG: %[[VAL:.*]] = pdl_interp.get_operand 0 of %[[ROOT]]526  // CHECK-DAG: %[[OP:.*]] = pdl_interp.get_defining_op of %[[VAL]]527  // CHECK-DAG: %[[INPUT1:.*]] = pdl_interp.get_operand 0 of %[[OP]]528  // CHECK-DAG: %[[INPUT2:.*]] = pdl_interp.get_operand 1 of %[[OP]]529  // CHECK-DAG: pdl_interp.is_not_null %[[VAL]] : !pdl.value530  // CHECK-DAG: pdl_interp.is_not_null %[[OP]] : !pdl.operation531  // CHECK-DAG: pdl_interp.is_not_null %[[INPUT1]] : !pdl.value532  // CHECK-DAG: pdl_interp.is_not_null %[[INPUT2]] : !pdl.value533 534  pdl.pattern @rewrite_overlapping_roots : benefit(1) {535    %input1 = operand536    %input2 = operand537    %type = type538    %op = operation(%input1, %input2 : !pdl.value, !pdl.value) -> (%type : !pdl.type)539    %val = result 0 of %op540    %root = operation(%val : !pdl.value)541    rewrite with "rewriter"(%root : !pdl.operation)542  }543}544 545// -----546 547// CHECK-LABEL: module @force_overlapped_root548module @force_overlapped_root {549  // Check the lowering of a degenerate two-root pattern, where one root550  // is in the subtree rooted at another, and we are forced to use this551  // root as the root of the search tree.552 553  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)554  // CHECK-DAG: %[[VAL:.*]] = pdl_interp.get_result 0 of %[[ROOT]]555  // CHECK-DAG: pdl_interp.check_operand_count of %[[ROOT]] is 2556  // CHECK-DAG: pdl_interp.check_result_count of %[[ROOT]] is 1557  // CHECK-DAG: %[[INPUT2:.*]] = pdl_interp.get_operand 1 of %[[ROOT]]558  // CHECK-DAG: pdl_interp.is_not_null %[[INPUT2]] : !pdl.value559  // CHECK-DAG: %[[INPUT1:.*]] = pdl_interp.get_operand 0 of %[[ROOT]]560  // CHECK-DAG: pdl_interp.is_not_null %[[INPUT1]] : !pdl.value561  // CHECK-DAG: %[[OPS:.*]] = pdl_interp.get_users of %[[VAL]] : !pdl.value562  // CHECK-DAG: pdl_interp.foreach %[[OP:.*]] : !pdl.operation in %[[OPS]]563  // CHECK-DAG:   pdl_interp.is_not_null %[[OP]] : !pdl.operation564  // CHECK-DAG:   pdl_interp.check_operand_count of %[[OP]] is 1565 566  pdl.pattern @rewrite_forced_overlapped_root : benefit(1) {567    %input1 = operand568    %input2 = operand569    %type = type570    %root = operation(%input1, %input2 : !pdl.value, !pdl.value) -> (%type : !pdl.type)571    %val = result 0 of %root572    %op = operation(%val : !pdl.value)573    rewrite %root with "rewriter"(%op : !pdl.operation)574  }575}576 577// -----578 579// CHECK-LABEL: module @variadic_results_all580module @variadic_results_all {581  // Check the correct lowering when using all results of an operation582  // and passing it them as operands to another operation.583 584  // CHECK: func @matcher(%[[ROOT:.*]]: !pdl.operation)585  // CHECK-DAG: pdl_interp.check_operand_count of %[[ROOT]] is 0586  // CHECK-DAG: %[[VALS:.*]] = pdl_interp.get_results of %[[ROOT]] : !pdl.range<value>587  // CHECK-DAG: %[[VAL0:.*]] = pdl_interp.extract 0 of %[[VALS]]588  // CHECK-DAG: %[[OPS:.*]] = pdl_interp.get_users of %[[VAL0]] : !pdl.value589  // CHECK-DAG: pdl_interp.foreach %[[OP:.*]] : !pdl.operation in %[[OPS]]590  // CHECK-DAG:   %[[OPERANDS:.*]] = pdl_interp.get_operands of %[[OP]]591  // CHECK-DAG:    pdl_interp.are_equal %[[OPERANDS]], %[[VALS]] : !pdl.range<value> -> ^{{.*}}, ^[[CONTINUE:.*]]592  // CHECK-DAG:   pdl_interp.is_not_null %[[OP]]593  // CHECK-DAG:   pdl_interp.check_result_count of %[[OP]] is 0594  pdl.pattern @variadic_results_all : benefit(1) {595    %types = types596    %root = operation -> (%types : !pdl.range<type>)597    %vals = results of %root598    %op = operation(%vals : !pdl.range<value>)599    rewrite %root with "rewriter"(%op : !pdl.operation)600  }601}602 603// -----604 605// CHECK-LABEL: module @variadic_results_at606module @variadic_results_at {607  // Check the correct lowering when using selected results of an operation608  // and passing it them as an operand to another operation.609 610  // CHECK: func @matcher(%[[ROOT1:.*]]: !pdl.operation)611  // CHECK-DAG: %[[VALS:.*]] = pdl_interp.get_operands 0 of %[[ROOT1]] : !pdl.range<value>612  // CHECK-DAG: %[[OP:.*]] = pdl_interp.get_defining_op of %[[VALS]] : !pdl.range<value>613  // CHECK-DAG: pdl_interp.is_not_null %[[OP]] : !pdl.operation614  // CHECK-DAG: pdl_interp.check_operand_count of %[[ROOT1]] is at_least 1615  // CHECK-DAG: pdl_interp.check_result_count of %[[ROOT1]] is 0616  // CHECK-DAG: %[[VAL:.*]] = pdl_interp.get_operands 1 of %[[ROOT1]] : !pdl.value617  // CHECK-DAG: pdl_interp.is_not_null %[[VAL]]618  // CHECK-DAG: pdl_interp.is_not_null %[[VALS]]619  // CHECK-DAG: %[[VAL0:.*]] = pdl_interp.extract 0 of %[[VALS]]620  // CHECK-DAG: %[[ROOTS2:.*]] = pdl_interp.get_users of %[[VAL0]] : !pdl.value621  // CHECK-DAG: pdl_interp.foreach %[[ROOT2:.*]] : !pdl.operation in %[[ROOTS2]] {622  // CHECK-DAG:   %[[OPERANDS:.*]] = pdl_interp.get_operands 1 of %[[ROOT2]]623  // CHECK-DAG:   pdl_interp.are_equal %[[OPERANDS]], %[[VALS]] : !pdl.range<value> -> ^{{.*}}, ^[[CONTINUE:.*]]624  // CHECK-DAG:   pdl_interp.is_not_null %[[ROOT2]]625  // CHECK-DAG:   pdl_interp.check_operand_count of %[[ROOT2]] is at_least 1626  // CHECK-DAG:   pdl_interp.check_result_count of %[[ROOT2]] is 0627  // CHECK-DAG:   pdl_interp.check_operand_count of %[[OP]] is 0628  // CHECK-DAG:   pdl_interp.check_result_count of %[[OP]] is at_least 1629  pdl.pattern @variadic_results_at : benefit(1) {630    %type = type631    %types = types632    %val = operand633    %op = operation -> (%types, %type : !pdl.range<type>, !pdl.type)634    %vals = results 0 of %op -> !pdl.range<value>635    %root1 = operation(%vals, %val : !pdl.range<value>, !pdl.value)636    %root2 = operation(%val, %vals : !pdl.value, !pdl.range<value>)637    rewrite with "rewriter"(%root1, %root2 : !pdl.operation, !pdl.operation)638  }639}640 641// -----642 643// CHECK-LABEL: module @attribute_literal644module @attribute_literal {645  // CHECK: func @matcher(%{{.*}}: !pdl.operation)646  // CHECK: %[[ATTR:.*]] = pdl_interp.create_attribute 10 : i64647  // CHECK: pdl_interp.apply_constraint "constraint"(%[[ATTR]] : !pdl.attribute)648 649  // Check the correct lowering of an attribute that hasn't been bound.650  pdl.pattern : benefit(1) {651    %attr = attribute = 10652    pdl.apply_native_constraint "constraint"(%attr: !pdl.attribute)653 654    %root = operation655    rewrite %root with "rewriter"656  }657}658 659// -----660 661// CHECK-LABEL: module @type_literal662module @type_literal {663  // CHECK: func @matcher(%{{.*}}: !pdl.operation)664  // CHECK: %[[TYPE:.*]] = pdl_interp.create_type i32665  // CHECK: %[[TYPES:.*]] = pdl_interp.create_types [i32, i64]666  // CHECK: pdl_interp.apply_constraint "constraint"(%[[TYPE]], %[[TYPES]] : !pdl.type, !pdl.range<type>)667 668  // Check the correct lowering of a type that hasn't been bound.669  pdl.pattern : benefit(1) {670    %type = type : i32671    %types = types : [i32, i64]672    pdl.apply_native_constraint "constraint"(%type, %types: !pdl.type, !pdl.range<type>)673 674    %root = operation675    rewrite %root with "rewriter"676  }677}678 679// -----680 681// CHECK-LABEL: module @common_connector682module @common_connector {683  // Check the correct lowering when multiple roots are using the same684  // connector.685 686  // CHECK: func @matcher(%[[ROOTC:.*]]: !pdl.operation)687  // CHECK-DAG: %[[VAL2:.*]] = pdl_interp.get_operand 0 of %[[ROOTC]]688  // CHECK-DAG: %[[INTER:.*]] = pdl_interp.get_defining_op of %[[VAL2]] : !pdl.value689  // CHECK-DAG: pdl_interp.is_not_null %[[INTER]] : !pdl.operation -> ^bb2, ^bb1690  // CHECK-DAG: %[[VAL1:.*]] = pdl_interp.get_operand 0 of %[[INTER]]691  // CHECK-DAG: %[[OP:.*]] = pdl_interp.get_defining_op of %[[VAL1]] : !pdl.value692  // CHECK-DAG: pdl_interp.is_not_null %[[OP]]693  // CHECK-DAG: %[[VAL0:.*]] = pdl_interp.get_result 0 of %[[OP]]694  // CHECK-DAG: %[[ROOTS:.*]] = pdl_interp.get_users of %[[VAL0]] : !pdl.value695  // CHECK-DAG: pdl_interp.foreach %[[ROOTA:.*]] : !pdl.operation in %[[ROOTS]] {696  // CHECK-DAG:   pdl_interp.is_not_null %[[ROOTA]] : !pdl.operation -> ^{{.*}}, ^[[CONTA:.*]]697  // CHECK-DAG:   pdl_interp.continue698  // CHECK-DAG:   pdl_interp.foreach %[[ROOTB:.*]] : !pdl.operation in %[[ROOTS]] {699  // CHECK-DAG:     pdl_interp.is_not_null %[[ROOTB]] : !pdl.operation -> ^{{.*}}, ^[[CONTB:.*]]700  // CHECK-DAG:     %[[ROOTA_OP:.*]] = pdl_interp.get_operand 0 of %[[ROOTA]]701  // CHECK-DAG:     pdl_interp.are_equal %[[ROOTA_OP]], %[[VAL0]] : !pdl.value702  // CHECK-DAG:     %[[ROOTB_OP:.*]] = pdl_interp.get_operand 0 of %[[ROOTB]]703  // CHECK-DAG:     pdl_interp.are_equal %[[ROOTB_OP]], %[[VAL0]] : !pdl.value704  // CHECK-DAG:    } -> ^[[CONTA:.*]]705  pdl.pattern @common_connector : benefit(1) {706      %type = type707      %op = operation -> (%type, %type : !pdl.type, !pdl.type)708      %val0 = result 0 of %op709      %val1 = result 1 of %op710      %rootA = operation (%val0 : !pdl.value)711      %rootB = operation (%val0 : !pdl.value)712      %inter = operation (%val1 : !pdl.value) -> (%type : !pdl.type)713      %val2 = result 0 of %inter714      %rootC = operation (%val2 : !pdl.value)715      rewrite with "rewriter"(%rootA, %rootB, %rootC : !pdl.operation, !pdl.operation, !pdl.operation)716  }717}718 719// -----720 721// CHECK-LABEL: module @common_connector_range722module @common_connector_range {723  // Check the correct lowering when multiple roots are using the same724  // connector range.725 726  // CHECK: func @matcher(%[[ROOTC:.*]]: !pdl.operation)727  // CHECK-DAG: %[[VALS2:.*]] = pdl_interp.get_operands of %[[ROOTC]] : !pdl.range<value>728  // CHECK-DAG: %[[INTER:.*]] = pdl_interp.get_defining_op of %[[VALS2]] : !pdl.range<value>729  // CHECK-DAG: pdl_interp.is_not_null %[[INTER]] : !pdl.operation -> ^bb2, ^bb1730  // CHECK-DAG: %[[VALS1:.*]] = pdl_interp.get_operands of %[[INTER]] : !pdl.range<value>731  // CHECK-DAG: %[[OP:.*]] = pdl_interp.get_defining_op of %[[VALS1]] : !pdl.range<value>732  // CHECK-DAG: pdl_interp.is_not_null %[[OP]]733  // CHECK-DAG: %[[VALS0:.*]] = pdl_interp.get_results 0 of %[[OP]]734  // CHECK-DAG: %[[VAL0:.*]] = pdl_interp.extract 0 of %[[VALS0]] : !pdl.value735  // CHECK-DAG: %[[ROOTS:.*]] = pdl_interp.get_users of %[[VAL0]] : !pdl.value736  // CHECK-DAG: pdl_interp.foreach %[[ROOTA:.*]] : !pdl.operation in %[[ROOTS]] {737  // CHECK-DAG:   pdl_interp.is_not_null %[[ROOTA]] : !pdl.operation -> ^{{.*}}, ^[[CONTA:.*]]738  // CHECK-DAG:   pdl_interp.continue739  // CHECK-DAG:   pdl_interp.foreach %[[ROOTB:.*]] : !pdl.operation in %[[ROOTS]] {740  // CHECK-DAG:     pdl_interp.is_not_null %[[ROOTB]] : !pdl.operation -> ^{{.*}}, ^[[CONTB:.*]]741  // CHECK-DAG:     %[[ROOTA_OPS:.*]] = pdl_interp.get_operands of %[[ROOTA]]742  // CHECK-DAG:     pdl_interp.are_equal %[[ROOTA_OPS]], %[[VALS0]] : !pdl.range<value>743  // CHECK-DAG:     %[[ROOTB_OPS:.*]] = pdl_interp.get_operands of %[[ROOTB]]744  // CHECK-DAG:     pdl_interp.are_equal %[[ROOTB_OPS]], %[[VALS0]] : !pdl.range<value>745  // CHECK-DAG:    } -> ^[[CONTA:.*]]746  pdl.pattern @common_connector_range : benefit(1) {747    %types = types748    %op = operation -> (%types, %types : !pdl.range<type>, !pdl.range<type>)749    %vals0 = results 0 of %op -> !pdl.range<value>750    %vals1 = results 1 of %op -> !pdl.range<value>751    %rootA = operation (%vals0 : !pdl.range<value>)752    %rootB = operation (%vals0 : !pdl.range<value>)753    %inter = operation (%vals1 : !pdl.range<value>) -> (%types : !pdl.range<type>)754    %vals2 = results of %inter755    %rootC = operation (%vals2 : !pdl.range<value>)756    rewrite with "rewriter"(%rootA, %rootB, %rootC : !pdl.operation, !pdl.operation, !pdl.operation)757  }758}759