brintos

brintos / llvm-project-archived public Read only

0
0
Text · 23.2 KiB · 94dfcea Raw
586 lines · plain
1// RUN: mlir-opt -pass-pipeline="builtin.module(func.func(convert-math-to-llvm,convert-arith-to-llvm),convert-func-to-llvm,convert-cf-to-llvm,reconcile-unrealized-casts)" %s | FileCheck %s2 3// RUN: mlir-opt -pass-pipeline="builtin.module(func.func(convert-math-to-llvm,convert-arith-to-llvm{index-bitwidth=32}),convert-func-to-llvm{index-bitwidth=32},convert-cf-to-llvm{index-bitwidth=32},reconcile-unrealized-casts)" %s | FileCheck --check-prefix=CHECK32 %s4 5// RUN: mlir-opt -pass-pipeline="builtin.module(func.func(convert-math-to-llvm,convert-arith-to-llvm),convert-func-to-llvm,reconcile-unrealized-casts)" %s | FileCheck --check-prefix=CHECK-NO-CF %s6 7// RUN: mlir-opt -transform-interpreter %s | FileCheck --check-prefix=CHECK32 %s8 9// Same below, but using the `ConvertToLLVMPatternInterface` entry point10// and the generic `convert-to-llvm` pass.11// RUN: mlir-opt --convert-to-llvm="filter-dialects=arith,cf,func,math" %s | FileCheck %s12// RUN: mlir-opt --convert-to-llvm="filter-dialects=arith,cf,func,math allow-pattern-rollback=0" %s | FileCheck %s13 14// CHECK-LABEL: func @empty() {15// CHECK-NEXT:  llvm.return16// CHECK-NEXT: }17func.func @empty() {18^bb0:19  return20}21 22// CHECK-LABEL: llvm.func @body(i64)23func.func private @body(index)24 25// CHECK-LABEL: func @simple_loop() {26// CHECK32-LABEL: func @simple_loop() {27func.func @simple_loop() {28^bb0:29// CHECK-NEXT:  llvm.br ^bb130// CHECK32-NEXT:  llvm.br ^bb131  cf.br ^bb132 33// CHECK-NEXT: ^bb1:	// pred: ^bb034// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i6435// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(42 : index) : i6436// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)37// CHECK32-NEXT: ^bb1:	// pred: ^bb038// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i3239// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(42 : index) : i3240// CHECK32-NEXT:  llvm.br ^bb2({{.*}} : i32)41^bb1:	// pred: ^bb042  %c1 = arith.constant 1 : index43  %c42 = arith.constant 42 : index44  cf.br ^bb2(%c1 : index)45 46// CHECK:      ^bb2({{.*}}: i64):	// 2 preds: ^bb1, ^bb347// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i6448// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb3, ^bb449// CHECK32:      ^bb2({{.*}}: i32):	// 2 preds: ^bb1, ^bb350// CHECK32-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i3251// CHECK32-NEXT:  llvm.cond_br {{.*}}, ^bb3, ^bb452^bb2(%0: index):	// 2 preds: ^bb1, ^bb353  %1 = arith.cmpi slt, %0, %c42 : index54  cf.cond_br %1, ^bb3, ^bb455 56// CHECK:      ^bb3:	// pred: ^bb257// CHECK-NEXT:  llvm.call @body({{.*}}) : (i64) -> ()58// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i6459// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i6460// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)61// CHECK32:      ^bb3:	// pred: ^bb262// CHECK32-NEXT:  llvm.call @body({{.*}}) : (i32) -> ()63// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i3264// CHECK32-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i3265// CHECK32-NEXT:  llvm.br ^bb2({{.*}} : i32)66^bb3:	// pred: ^bb267  call @body(%0) : (index) -> ()68  %c1_0 = arith.constant 1 : index69  %2 = arith.addi %0, %c1_0 : index70  cf.br ^bb2(%2 : index)71 72// CHECK:      ^bb4:	// pred: ^bb273// CHECK-NEXT:  llvm.return74^bb4:	// pred: ^bb275  return76}77 78// CHECK-LABEL: func @simple_caller() {79// CHECK-NEXT:  llvm.call @simple_loop() : () -> ()80// CHECK-NEXT:  llvm.return81// CHECK-NEXT: }82func.func @simple_caller() {83^bb0:84  call @simple_loop() : () -> ()85  return86}87 88// Check that function call attributes persist during conversion.89// CHECK-LABEL: @call_with_attributes90func.func @call_with_attributes() {91  // CHECK: llvm.call @simple_loop() {baz = [1, 2, 3, 4], foo = "bar"} : () -> ()92  call @simple_loop() {foo="bar", baz=[1,2,3,4]} : () -> ()93  return94}95 96// CHECK-LABEL: func @ml_caller() {97// CHECK-NEXT:  llvm.call @simple_loop() : () -> ()98// CHECK-NEXT:  llvm.call @more_imperfectly_nested_loops() : () -> ()99// CHECK-NEXT:  llvm.return100// CHECK-NEXT: }101func.func @ml_caller() {102^bb0:103  call @simple_loop() : () -> ()104  call @more_imperfectly_nested_loops() : () -> ()105  return106}107 108// CHECK-LABEL: llvm.func @body_args(i64) -> i64109// CHECK32-LABEL: llvm.func @body_args(i32) -> i32110// CHECK-NO-CF-LABEL: llvm.func @body_args(i64) -> i64111func.func private @body_args(index) -> index112// CHECK-LABEL: llvm.func @other(i64, i32) -> i32113// CHECK32-LABEL: llvm.func @other(i32, i32) -> i32114func.func private @other(index, i32) -> i32115 116// CHECK-LABEL: func @func_args(%arg0: i32, %arg1: i32) -> i32 {117// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(0 : i32) : i32118// CHECK-NEXT:  llvm.br ^bb1119// CHECK32-LABEL: func @func_args(%arg0: i32, %arg1: i32) -> i32 {120// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(0 : i32) : i32121// CHECK32-NEXT:  llvm.br ^bb1122func.func @func_args(i32, i32) -> i32 {123^bb0(%arg0: i32, %arg1: i32):124  %c0_i32 = arith.constant 0 : i32125  cf.br ^bb1126 127// CHECK-NEXT: ^bb1:	// pred: ^bb0128// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(0 : index) : i64129// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(42 : index) : i64130// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)131// CHECK32-NEXT: ^bb1:	// pred: ^bb0132// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(0 : index) : i32133// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(42 : index) : i32134// CHECK32-NEXT:  llvm.br ^bb2({{.*}} : i32)135^bb1:	// pred: ^bb0136  %c0 = arith.constant 0 : index137  %c42 = arith.constant 42 : index138  cf.br ^bb2(%c0 : index)139 140// CHECK-NEXT: ^bb2({{.*}}: i64):	// 2 preds: ^bb1, ^bb3141// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i64142// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb3, ^bb4143// CHECK32-NEXT: ^bb2({{.*}}: i32):	// 2 preds: ^bb1, ^bb3144// CHECK32-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i32145// CHECK32-NEXT:  llvm.cond_br {{.*}}, ^bb3, ^bb4146^bb2(%0: index):	// 2 preds: ^bb1, ^bb3147  %1 = arith.cmpi slt, %0, %c42 : index148  cf.cond_br %1, ^bb3, ^bb4149 150// CHECK-NEXT: ^bb3:	// pred: ^bb2151// CHECK-NEXT:  {{.*}} = llvm.call @body_args({{.*}}) : (i64) -> i64152// CHECK-NEXT:  {{.*}} = llvm.call @other({{.*}}, %arg0) : (i64, i32) -> i32153// CHECK-NEXT:  {{.*}} = llvm.call @other({{.*}}, {{.*}}) : (i64, i32) -> i32154// CHECK-NEXT:  {{.*}} = llvm.call @other({{.*}}, %arg1) : (i64, i32) -> i32155// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i64156// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i64157// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)158// CHECK32-NEXT: ^bb3:	// pred: ^bb2159// CHECK32-NEXT:  {{.*}} = llvm.call @body_args({{.*}}) : (i32) -> i32160// CHECK32-NEXT:  {{.*}} = llvm.call @other({{.*}}, %arg0) : (i32, i32) -> i32161// CHECK32-NEXT:  {{.*}} = llvm.call @other({{.*}}, {{.*}}) : (i32, i32) -> i32162// CHECK32-NEXT:  {{.*}} = llvm.call @other({{.*}}, %arg1) : (i32, i32) -> i32163// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i32164// CHECK32-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i32165// CHECK32-NEXT:  llvm.br ^bb2({{.*}} : i32)166^bb3:	// pred: ^bb2167  %2 = call @body_args(%0) : (index) -> index168  %3 = call @other(%2, %arg0) : (index, i32) -> i32169  %4 = call @other(%2, %3) : (index, i32) -> i32170  %5 = call @other(%2, %arg1) : (index, i32) -> i32171  %c1 = arith.constant 1 : index172  %6 = arith.addi %0, %c1 : index173  cf.br ^bb2(%6 : index)174 175// CHECK-NEXT: ^bb4:	// pred: ^bb2176// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(0 : index) : i64177// CHECK-NEXT:  {{.*}} = llvm.call @other({{.*}}, {{.*}}) : (i64, i32) -> i32178// CHECK-NEXT:  llvm.return {{.*}} : i32179// CHECK32-NEXT: ^bb4:	// pred: ^bb2180// CHECK32-NEXT:  {{.*}} = llvm.mlir.constant(0 : index) : i32181// CHECK32-NEXT:  {{.*}} = llvm.call @other({{.*}}, {{.*}}) : (i32, i32) -> i32182// CHECK32-NEXT:  llvm.return {{.*}} : i32183^bb4:	// pred: ^bb2184  %c0_0 = arith.constant 0 : index185  %7 = call @other(%c0_0, %c0_i32) : (index, i32) -> i32186  return %7 : i32187}188 189// CHECK-LABEL: llvm.func @pre(i64)190// CHECK32-LABEL: llvm.func @pre(i32)191func.func private @pre(index)192 193// CHECK-LABEL: llvm.func @body2(i64, i64)194// CHECK32-LABEL: llvm.func @body2(i32, i32)195func.func private @body2(index, index)196 197// CHECK-LABEL: llvm.func @post(i64)198// CHECK32-LABEL: llvm.func @post(i32)199func.func private @post(index)200 201// CHECK-LABEL: func @imperfectly_nested_loops() {202// CHECK-NEXT:  llvm.br ^bb1203func.func @imperfectly_nested_loops() {204^bb0:205  cf.br ^bb1206 207// CHECK-NEXT: ^bb1:	// pred: ^bb0208// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(0 : index) : i64209// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(42 : index) : i64210// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)211^bb1:	// pred: ^bb0212  %c0 = arith.constant 0 : index213  %c42 = arith.constant 42 : index214  cf.br ^bb2(%c0 : index)215 216// CHECK-NEXT: ^bb2({{.*}}: i64):	// 2 preds: ^bb1, ^bb7217// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i64218// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb3, ^bb8219^bb2(%0: index):	// 2 preds: ^bb1, ^bb7220  %1 = arith.cmpi slt, %0, %c42 : index221  cf.cond_br %1, ^bb3, ^bb8222 223// CHECK-NEXT: ^bb3:224// CHECK-NEXT:  llvm.call @pre({{.*}}) : (i64) -> ()225// CHECK-NEXT:  llvm.br ^bb4226^bb3:	// pred: ^bb2227  call @pre(%0) : (index) -> ()228  cf.br ^bb4229 230// CHECK-NEXT: ^bb4:	// pred: ^bb3231// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(7 : index) : i64232// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(56 : index) : i64233// CHECK-NEXT:  llvm.br ^bb5({{.*}} : i64)234^bb4:	// pred: ^bb3235  %c7 = arith.constant 7 : index236  %c56 = arith.constant 56 : index237  cf.br ^bb5(%c7 : index)238 239// CHECK-NEXT: ^bb5({{.*}}: i64):	// 2 preds: ^bb4, ^bb6240// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i64241// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb6, ^bb7242^bb5(%2: index):	// 2 preds: ^bb4, ^bb6243  %3 = arith.cmpi slt, %2, %c56 : index244  cf.cond_br %3, ^bb6, ^bb7245 246// CHECK-NEXT: ^bb6:	// pred: ^bb5247// CHECK-NEXT:  llvm.call @body2({{.*}}, {{.*}}) : (i64, i64) -> ()248// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(2 : index) : i64249// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i64250// CHECK-NEXT:  llvm.br ^bb5({{.*}} : i64)251^bb6:	// pred: ^bb5252  call @body2(%0, %2) : (index, index) -> ()253  %c2 = arith.constant 2 : index254  %4 = arith.addi %2, %c2 : index255  cf.br ^bb5(%4 : index)256 257// CHECK-NEXT: ^bb7:	// pred: ^bb5258// CHECK-NEXT:  llvm.call @post({{.*}}) : (i64) -> ()259// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i64260// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i64261// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)262^bb7:	// pred: ^bb5263  call @post(%0) : (index) -> ()264  %c1 = arith.constant 1 : index265  %5 = arith.addi %0, %c1 : index266  cf.br ^bb2(%5 : index)267 268// CHECK-NEXT: ^bb8:	// pred: ^bb2269// CHECK-NEXT:  llvm.return270^bb8:	// pred: ^bb2271  return272}273 274// CHECK-LABEL: llvm.func @mid(i64)275func.func private @mid(index)276 277// CHECK-LABEL: llvm.func @body3(i64, i64)278func.func private @body3(index, index)279 280// A complete function transformation check.281// CHECK-LABEL: func @more_imperfectly_nested_loops() {282// CHECK-NEXT:  llvm.br ^bb1283// CHECK-NEXT:^bb1:	// pred: ^bb0284// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(0 : index) : i64285// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(42 : index) : i64286// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)287// CHECK-NEXT:^bb2({{.*}}: i64):	// 2 preds: ^bb1, ^bb11288// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i64289// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb3, ^bb12290// CHECK-NEXT:^bb3:	// pred: ^bb2291// CHECK-NEXT:  llvm.call @pre({{.*}}) : (i64) -> ()292// CHECK-NEXT:  llvm.br ^bb4293// CHECK-NEXT:^bb4:	// pred: ^bb3294// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(7 : index) : i64295// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(56 : index) : i64296// CHECK-NEXT:  llvm.br ^bb5({{.*}} : i64)297// CHECK-NEXT:^bb5({{.*}}: i64):	// 2 preds: ^bb4, ^bb6298// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i64299// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb6, ^bb7300// CHECK-NEXT:^bb6:	// pred: ^bb5301// CHECK-NEXT:  llvm.call @body2({{.*}}, {{.*}}) : (i64, i64) -> ()302// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(2 : index) : i64303// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i64304// CHECK-NEXT:  llvm.br ^bb5({{.*}} : i64)305// CHECK-NEXT:^bb7:	// pred: ^bb5306// CHECK-NEXT:  llvm.call @mid({{.*}}) : (i64) -> ()307// CHECK-NEXT:  llvm.br ^bb8308// CHECK-NEXT:^bb8:	// pred: ^bb7309// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(18 : index) : i64310// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(37 : index) : i64311// CHECK-NEXT:  llvm.br ^bb9({{.*}} : i64)312// CHECK-NEXT:^bb9({{.*}}: i64):	// 2 preds: ^bb8, ^bb10313// CHECK-NEXT:  {{.*}} = llvm.icmp "slt" {{.*}}, {{.*}} : i64314// CHECK-NEXT:  llvm.cond_br {{.*}}, ^bb10, ^bb11315// CHECK-NEXT:^bb10:	// pred: ^bb9316// CHECK-NEXT:  llvm.call @body3({{.*}}, {{.*}}) : (i64, i64) -> ()317// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(3 : index) : i64318// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i64319// CHECK-NEXT:  llvm.br ^bb9({{.*}} : i64)320// CHECK-NEXT:^bb11:	// pred: ^bb9321// CHECK-NEXT:  llvm.call @post({{.*}}) : (i64) -> ()322// CHECK-NEXT:  {{.*}} = llvm.mlir.constant(1 : index) : i64323// CHECK-NEXT:  {{.*}} = llvm.add {{.*}}, {{.*}} : i64324// CHECK-NEXT:  llvm.br ^bb2({{.*}} : i64)325// CHECK-NEXT:^bb12:	// pred: ^bb2326// CHECK-NEXT:  llvm.return327// CHECK-NEXT: }328func.func @more_imperfectly_nested_loops() {329^bb0:330  cf.br ^bb1331^bb1:	// pred: ^bb0332  %c0 = arith.constant 0 : index333  %c42 = arith.constant 42 : index334  cf.br ^bb2(%c0 : index)335^bb2(%0: index):	// 2 preds: ^bb1, ^bb11336  %1 = arith.cmpi slt, %0, %c42 : index337  cf.cond_br %1, ^bb3, ^bb12338^bb3:	// pred: ^bb2339  call @pre(%0) : (index) -> ()340  cf.br ^bb4341^bb4:	// pred: ^bb3342  %c7 = arith.constant 7 : index343  %c56 = arith.constant 56 : index344  cf.br ^bb5(%c7 : index)345^bb5(%2: index):	// 2 preds: ^bb4, ^bb6346  %3 = arith.cmpi slt, %2, %c56 : index347  cf.cond_br %3, ^bb6, ^bb7348^bb6:	// pred: ^bb5349  call @body2(%0, %2) : (index, index) -> ()350  %c2 = arith.constant 2 : index351  %4 = arith.addi %2, %c2 : index352  cf.br ^bb5(%4 : index)353^bb7:	// pred: ^bb5354  call @mid(%0) : (index) -> ()355  cf.br ^bb8356^bb8:	// pred: ^bb7357  %c18 = arith.constant 18 : index358  %c37 = arith.constant 37 : index359  cf.br ^bb9(%c18 : index)360^bb9(%5: index):	// 2 preds: ^bb8, ^bb10361  %6 = arith.cmpi slt, %5, %c37 : index362  cf.cond_br %6, ^bb10, ^bb11363^bb10:	// pred: ^bb9364  call @body3(%0, %5) : (index, index) -> ()365  %c3 = arith.constant 3 : index366  %7 = arith.addi %5, %c3 : index367  cf.br ^bb9(%7 : index)368^bb11:	// pred: ^bb9369  call @post(%0) : (index) -> ()370  %c1 = arith.constant 1 : index371  %8 = arith.addi %0, %c1 : index372  cf.br ^bb2(%8 : index)373^bb12:	// pred: ^bb2374  return375}376 377// CHECK-LABEL: llvm.func @get_i64() -> i64378func.func private @get_i64() -> (i64)379// CHECK-LABEL: llvm.func @get_f32() -> f32380func.func private @get_f32() -> (f32)381// CHECK-LABEL: llvm.func @get_c16() -> !llvm.struct<(f16, f16)>382func.func private @get_c16() -> (complex<f16>)383// CHECK-LABEL: llvm.func @get_c32() -> !llvm.struct<(f32, f32)>384func.func private @get_c32() -> (complex<f32>)385// CHECK-LABEL: llvm.func @get_c64() -> !llvm.struct<(f64, f64)>386func.func private @get_c64() -> (complex<f64>)387// CHECK-LABEL: llvm.func @get_memref() -> !llvm.struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>388// CHECK32-LABEL: llvm.func @get_memref() -> !llvm.struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>389func.func private @get_memref() -> (memref<42x?x10x?xf32>)390 391// CHECK-LABEL: llvm.func @multireturn() -> !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)> {392// CHECK32-LABEL: llvm.func @multireturn() -> !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)> {393func.func @multireturn() -> (i64, f32, memref<42x?x10x?xf32>) {394^bb0:395// CHECK-NEXT:  {{.*}} = llvm.call @get_i64() : () -> i64396// CHECK-NEXT:  {{.*}} = llvm.call @get_f32() : () -> f32397// CHECK-NEXT:  {{.*}} = llvm.call @get_memref() : () -> !llvm.struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>398// CHECK32-NEXT:  {{.*}} = llvm.call @get_i64() : () -> i64399// CHECK32-NEXT:  {{.*}} = llvm.call @get_f32() : () -> f32400// CHECK32-NEXT:  {{.*}} = llvm.call @get_memref() : () -> !llvm.struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>401  %0 = call @get_i64() : () -> (i64)402  %1 = call @get_f32() : () -> (f32)403  %2 = call @get_memref() : () -> (memref<42x?x10x?xf32>)404// CHECK-NEXT:  {{.*}} = llvm.mlir.poison : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>405// CHECK-NEXT:  {{.*}} = llvm.insertvalue {{.*}}, {{.*}}[0] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>406// CHECK-NEXT:  {{.*}} = llvm.insertvalue {{.*}}, {{.*}}[1] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>407// CHECK-NEXT:  {{.*}} = llvm.insertvalue {{.*}}, {{.*}}[2] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>408// CHECK-NEXT:  llvm.return {{.*}} : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>409// CHECK32-NEXT:  {{.*}} = llvm.mlir.poison : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>410// CHECK32-NEXT:  {{.*}} = llvm.insertvalue {{.*}}, {{.*}}[0] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>411// CHECK32-NEXT:  {{.*}} = llvm.insertvalue {{.*}}, {{.*}}[1] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>412// CHECK32-NEXT:  {{.*}} = llvm.insertvalue {{.*}}, {{.*}}[2] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>413// CHECK32-NEXT:  llvm.return {{.*}} : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>414  return %0, %1, %2 : i64, f32, memref<42x?x10x?xf32>415}416 417 418// CHECK-LABEL: llvm.func @multireturn_caller() {419// CHECK32-LABEL: llvm.func @multireturn_caller() {420func.func @multireturn_caller() {421^bb0:422// CHECK-NEXT:  {{.*}} = llvm.call @multireturn() : () -> !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>423// CHECK-NEXT:  {{.*}} = llvm.extractvalue {{.*}}[0] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>424// CHECK-NEXT:  {{.*}} = llvm.extractvalue {{.*}}[1] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>425// CHECK-NEXT:  {{.*}} = llvm.extractvalue {{.*}}[2] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i64, array<4 x i64>, array<4 x i64>)>)>426// CHECK32-NEXT:  {{.*}} = llvm.call @multireturn() : () -> !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>427// CHECK32-NEXT:  {{.*}} = llvm.extractvalue {{.*}}[0] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>428// CHECK32-NEXT:  {{.*}} = llvm.extractvalue {{.*}}[1] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>429// CHECK32-NEXT:  {{.*}} = llvm.extractvalue {{.*}}[2] : !llvm.struct<(i64, f32, struct<(ptr, ptr, i32, array<4 x i32>, array<4 x i32>)>)>430  %0:3 = call @multireturn() : () -> (i64, f32, memref<42x?x10x?xf32>)431  %1 = arith.constant 42 : i64432// CHECK:       {{.*}} = llvm.add {{.*}}, {{.*}} : i64433  %2 = arith.addi %0#0, %1 : i64434  %3 = arith.constant 42.0 : f32435// CHECK:       {{.*}} = llvm.fadd {{.*}}, {{.*}} : f32436  %4 = arith.addf %0#1, %3 : f32437  %5 = arith.constant 0 : index438  return439}440 441// CHECK-LABEL: @dfs_block_order442func.func @dfs_block_order(%arg0: i32) -> (i32) {443// CHECK-NEXT:  %[[CST:.*]] = llvm.mlir.constant(42 : i32) : i32444  %0 = arith.constant 42 : i32445// CHECK-NEXT:  llvm.br ^bb2446  cf.br ^bb2447 448// CHECK-NEXT: ^bb1:449// CHECK-NEXT:  %[[ADD:.*]] = llvm.add %arg0, %[[CST]] : i32450// CHECK-NEXT:  llvm.return %[[ADD]] : i32451^bb1:452  %2 = arith.addi %arg0, %0 : i32453  return %2 : i32454 455// CHECK-NEXT: ^bb2:456^bb2:457// CHECK-NEXT:  llvm.br ^bb1458  cf.br ^bb1459}460 461// CHECK-LABEL: func @ceilf(462// CHECK-SAME: f32463func.func @ceilf(%arg0 : f32) {464  // CHECK: llvm.intr.ceil(%arg0) : (f32) -> f32465  %0 = math.ceil %arg0 : f32466  func.return467}468 469// CHECK-LABEL: func @floorf(470// CHECK-SAME: f32471func.func @floorf(%arg0 : f32) {472  // CHECK: llvm.intr.floor(%arg0) : (f32) -> f32473  %0 = math.floor %arg0 : f32474  func.return475}476 477// Wrap the following tests in a module to control the place where478// `llvm.func @abort()` is produced.479module {480// Lowers `cf.assert` to a function call to `abort` if the assertion is violated.481// CHECK: llvm.func @abort()482// CHECK-LABEL: @assert_test_function483// CHECK-SAME:  (%[[ARG:.*]]: i1)484func.func @assert_test_function(%arg : i1) {485  // CHECK: llvm.cond_br %[[ARG]], ^[[CONTINUATION_BLOCK:.*]], ^[[FAILURE_BLOCK:.*]]486  // CHECK: ^[[CONTINUATION_BLOCK]]:487  // CHECK: llvm.return488  // CHECK: ^[[FAILURE_BLOCK]]:489  // CHECK: llvm.call @abort() : () -> ()490  // CHECK: llvm.unreachable491  cf.assert %arg, "Computer says no"492  return493}494}495 496// This should not trigger an assertion by creating an LLVM::CallOp with a497// nullptr result type.498 499// CHECK-LABEL: @call_zero_result_func500func.func @call_zero_result_func() {501  // CHECK: call @zero_result_func502  call @zero_result_func() : () -> ()503  return504}505func.func private @zero_result_func()506 507// CHECK-LABEL: func @fmaf(508// CHECK-SAME: %[[ARG0:.*]]: f32509// CHECK-SAME: %[[ARG1:.*]]: vector<4xf32>510func.func @fmaf(%arg0: f32, %arg1: vector<4xf32>) {511  // CHECK: %[[S:.*]] = llvm.intr.fma(%[[ARG0]], %[[ARG0]], %[[ARG0]]) : (f32, f32, f32) -> f32512  %0 = math.fma %arg0, %arg0, %arg0 : f32513  // CHECK: %[[V:.*]] = llvm.intr.fma(%[[ARG1]], %[[ARG1]], %[[ARG1]]) : (vector<4xf32>, vector<4xf32>, vector<4xf32>) -> vector<4xf32>514  %1 = math.fma %arg1, %arg1, %arg1 : vector<4xf32>515  func.return516}517 518// CHECK-LABEL: func @switchi8(519func.func @switchi8(%arg0 : i8) -> i32 {520  cf.switch %arg0 : i8, [521    default: ^bb1,522    42: ^bb1,523    43: ^bb3524  ]525^bb1:526  %c_1 = arith.constant 1 : i32527  func.return %c_1 : i32528^bb3:529  %c_42 = arith.constant 42 : i32530  func.return %c_42: i32531}532// CHECK:     llvm.switch %arg0 : i8, ^bb1 [533// CHECK-NEXT:       42: ^bb1,534// CHECK-NEXT:       43: ^bb2535// CHECK-NEXT:     ]536// CHECK:   ^bb1:  // 2 preds: ^bb0, ^bb0537// CHECK-NEXT:     %[[E0:.+]] = llvm.mlir.constant(1 : i32) : i32538// CHECK-NEXT:     llvm.return %[[E0]] : i32539// CHECK:   ^bb2:  // pred: ^bb0540// CHECK-NEXT:     %[[E1:.+]] = llvm.mlir.constant(42 : i32) : i32541// CHECK-NEXT:     llvm.return %[[E1]] : i32542// CHECK-NEXT:   }543 544// Convert the entry block but not the unstructured control flow.545 546// CHECK-NO-CF-LABEL: llvm.func @index_arg(547//  CHECK-NO-CF-SAME:     %[[arg0:.*]]: i64) -> i64 {548//       CHECK-NO-CF:   %[[cast:.*]] = builtin.unrealized_conversion_cast %[[arg0]] : i64 to index549//       CHECK-NO-CF:   cf.br ^[[bb1:.*]](%[[cast]] : index)550//       CHECK-NO-CF: ^[[bb1]](%[[arg1:.*]]: index):551//       CHECK-NO-CF:   %[[cast2:.*]] = builtin.unrealized_conversion_cast %[[arg1]] : index to i64552//       CHECK-NO-CF:   llvm.return %[[cast2]] : i64553func.func @index_arg(%arg0: index) -> index {554  cf.br ^bb1(%arg0 : index)555^bb1(%arg1: index):556  return %arg1 : index557}558 559// There is no type conversion rule for tf32, so vector<1xtf32> and, therefore,560// the func op cannot be converted.561// CHECK: func.func @non_convertible_arg_type({{.*}}: vector<1xtf32>)562// CHECK:   llvm.return563func.func @non_convertible_arg_type(%arg: vector<1xtf32>) {564  return565}566 567module attributes {transform.with_named_sequence} {568  transform.named_sequence @__transform_main(%toplevel_module: !transform.any_op {transform.readonly}) {569    %func = transform.structured.match ops{["func.func"]} in %toplevel_module570      : (!transform.any_op) -> !transform.any_op571    transform.apply_conversion_patterns to %func {572      transform.apply_conversion_patterns.dialect_to_llvm "math"573      transform.apply_conversion_patterns.dialect_to_llvm "arith"574      transform.apply_conversion_patterns.dialect_to_llvm "cf"575      transform.apply_conversion_patterns.func.func_to_llvm576    } with type_converter {577      transform.apply_conversion_patterns.memref.memref_to_llvm_type_converter578        {index_bitwidth = 32, use_opaque_pointers = true}579    } {580      legal_dialects = ["llvm"],581      partial_conversion582    } : !transform.any_op583    transform.yield584  }585}586