blob: ed08779c10266ddcaa4a2f90db0988106b428c1b [file] [log] [blame]
// RUN: mlir-opt --arith-emulate-wide-int="widest-int-supported=32" %s | FileCheck %s
// Expect no conversions, i32 is supported.
// CHECK-LABEL: func @addi_same_i32
// CHECK-SAME: ([[ARG:%.+]]: i32) -> i32
// CHECK-NEXT: [[X:%.+]] = arith.addi [[ARG]], [[ARG]] : i32
// CHECK-NEXT: return [[X]] : i32
func.func @addi_same_i32(%a : i32) -> i32 {
%x = arith.addi %a, %a : i32
return %x : i32
}
// Expect no conversions, index is not sized.
// CHECK-LABEL: func @addi_same_index
// CHECK-SAME: ([[ARG:%.+]]: index) -> index
// CHECK-NEXT: [[X:%.+]] = arith.addi [[ARG]], [[ARG]] : index
// CHECK-NEXT: return [[X]] : index
func.func @addi_same_index(%a : index) -> index {
%x = arith.addi %a, %a : index
return %x : index
}
// Expect no conversions, f64 is not an integer type.
// CHECK-LABEL: func @identity_f64
// CHECK-SAME: ([[ARG:%.+]]: f64) -> f64
// CHECK-NEXT: return [[ARG]] : f64
func.func @identity_f64(%a : f64) -> f64 {
return %a : f64
}
// Expect no conversions, i32 is supported.
// CHECK-LABEL: func @addi_same_vector_i32
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[X:%.+]] = arith.addi [[ARG]], [[ARG]] : vector<2xi32>
// CHECK-NEXT: return [[X]] : vector<2xi32>
func.func @addi_same_vector_i32(%a : vector<2xi32>) -> vector<2xi32> {
%x = arith.addi %a, %a : vector<2xi32>
return %x : vector<2xi32>
}
// CHECK-LABEL: func @identity_scalar
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: return [[ARG]] : vector<2xi32>
func.func @identity_scalar(%x : i64) -> i64 {
return %x : i64
}
// CHECK-LABEL: func @identity_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<4x2xi32>) -> vector<4x2xi32>
// CHECK-NEXT: return [[ARG]] : vector<4x2xi32>
func.func @identity_vector(%x : vector<4xi64>) -> vector<4xi64> {
return %x : vector<4xi64>
}
// CHECK-LABEL: func @identity_vector2d
// CHECK-SAME: ([[ARG:%.+]]: vector<3x4x2xi32>) -> vector<3x4x2xi32>
// CHECK-NEXT: return [[ARG]] : vector<3x4x2xi32>
func.func @identity_vector2d(%x : vector<3x4xi64>) -> vector<3x4xi64> {
return %x : vector<3x4xi64>
}
// CHECK-LABEL: func @call
// CHECK-SAME: ([[ARG:%.+]]: vector<4x2xi32>) -> vector<4x2xi32>
// CHECK-NEXT: [[RES:%.+]] = call @identity_vector([[ARG]]) : (vector<4x2xi32>) -> vector<4x2xi32>
// CHECK-NEXT: return [[RES]] : vector<4x2xi32>
func.func @call(%a : vector<4xi64>) -> vector<4xi64> {
%res = func.call @identity_vector(%a) : (vector<4xi64>) -> vector<4xi64>
return %res : vector<4xi64>
}
// CHECK-LABEL: func @constant_scalar
// CHECK-SAME: () -> vector<2xi32>
// CHECK-NEXT: [[C0:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[C1:%.+]] = arith.constant dense<[0, 1]> : vector<2xi32>
// CHECK-NEXT: [[C2:%.+]] = arith.constant dense<[-7, -1]> : vector<2xi32>
// CHECK-NEXT: return [[C0]] : vector<2xi32>
func.func @constant_scalar() -> i64 {
%c0 = arith.constant 0 : i64
%c1 = arith.constant 4294967296 : i64
%c2 = arith.constant -7 : i64
return %c0 : i64
}
// CHECK-LABEL: func @constant_vector
// CHECK-SAME: () -> vector<3x2xi32>
// CHECK-NEXT: [[C0:%.+]] = arith.constant dense
// CHECK-SAME{LITERAL}: <[[0, 1], [0, 1], [0, 1]]> : vector<3x2xi32>
// CHECK-NEXT: [[C1:%.+]] = arith.constant dense
// CHECK-SAME{LITERAL}: <[[0, 0], [1, 0], [-2, -1]]> : vector<3x2xi32>
// CHECK-NEXT: return [[C0]] : vector<3x2xi32>
func.func @constant_vector() -> vector<3xi64> {
%c0 = arith.constant dense<4294967296> : vector<3xi64>
%c1 = arith.constant dense<[0, 1, -2]> : vector<3xi64>
return %c0 : vector<3xi64>
}
// CHECK-LABEL: func @addi_scalar_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[SUM_L:%.+]], [[CB:%.+]] = arith.addui_extended [[LOW0]], [[LOW1]] : i32, i1
// CHECK-NEXT: [[CARRY:%.+]] = arith.extui [[CB]] : i1 to i32
// CHECK-NEXT: [[SUM_H0:%.+]] = arith.addi [[CARRY]], [[HIGH0]] : i32
// CHECK-NEXT: [[SUM_H1:%.+]] = arith.addi [[SUM_H0]], [[HIGH1]] : i32
// CHECK: [[INS0:%.+]] = vector.insert [[SUM_L]], {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[SUM_H1]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @addi_scalar_a_b(%a : i64, %b : i64) -> i64 {
%x = arith.addi %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @addi_vector_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<4x2xi32>, [[ARG1:%.+]]: vector<4x2xi32>) -> vector<4x2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract_strided_slice [[ARG0]] {offsets = [0, 0], sizes = [4, 1], strides = [1, 1]} : vector<4x2xi32> to vector<4x1xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract_strided_slice [[ARG0]] {offsets = [0, 1], sizes = [4, 1], strides = [1, 1]} : vector<4x2xi32> to vector<4x1xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract_strided_slice [[ARG1]] {offsets = [0, 0], sizes = [4, 1], strides = [1, 1]} : vector<4x2xi32> to vector<4x1xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract_strided_slice [[ARG1]] {offsets = [0, 1], sizes = [4, 1], strides = [1, 1]} : vector<4x2xi32> to vector<4x1xi32>
// CHECK-NEXT: [[SUM_L:%.+]], [[CB:%.+]] = arith.addui_extended [[LOW0]], [[LOW1]] : vector<4x1xi32>, vector<4x1xi1>
// CHECK-NEXT: [[CARRY:%.+]] = arith.extui [[CB]] : vector<4x1xi1> to vector<4x1xi32>
// CHECK-NEXT: [[SUM_H0:%.+]] = arith.addi [[CARRY]], [[HIGH0]] : vector<4x1xi32>
// CHECK-NEXT: [[SUM_H1:%.+]] = arith.addi [[SUM_H0]], [[HIGH1]] : vector<4x1xi32>
// CHECK: [[INS0:%.+]] = vector.insert_strided_slice [[SUM_L]], {{%.+}} {offsets = [0, 0], strides = [1, 1]} : vector<4x1xi32> into vector<4x2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert_strided_slice [[SUM_H1]], [[INS0]] {offsets = [0, 1], strides = [1, 1]} : vector<4x1xi32> into vector<4x2xi32>
// CHECK-NEXT: return [[INS1]] : vector<4x2xi32>
func.func @addi_vector_a_b(%a : vector<4xi64>, %b : vector<4xi64>) -> vector<4xi64> {
%x = arith.addi %a, %b : vector<4xi64>
return %x : vector<4xi64>
}
// CHECK-LABEL: func.func @cmpi_eq_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK-NEXT: [[LHSLOW:%.+]] = vector.extract [[LHS]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[LHSHIGH:%.+]] = vector.extract [[LHS]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[RHSLOW:%.+]] = vector.extract [[RHS]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[RHSHIGH:%.+]] = vector.extract [[RHS]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[CLOW:%.+]] = arith.cmpi eq, [[LHSLOW]], [[RHSLOW]] : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.andi [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_eq_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi eq, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_eq_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3xi1>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract_strided_slice [[ARG0]] {offsets = [0, 0], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract_strided_slice [[ARG0]] {offsets = [0, 1], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract_strided_slice [[ARG1]] {offsets = [0, 0], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract_strided_slice [[ARG1]] {offsets = [0, 1], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[CLOW:%.+]] = arith.cmpi eq, [[LOW0]], [[LOW1]] : vector<3x1xi32>
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi eq, [[HIGH0]], [[HIGH1]] : vector<3x1xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.andi [[CLOW]], [[CHIGH]] : vector<3x1xi1>
// CHECK-NEXT: [[CAST:%.+]] = vector.shape_cast [[RES]] : vector<3x1xi1> to vector<3xi1>
// CHECK: return [[CAST]] : vector<3xi1>
func.func @cmpi_eq_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi1> {
%r = arith.cmpi eq, %a, %b : vector<3xi64>
return %r : vector<3xi1>
}
// CHECK-LABEL: func.func @cmpi_ne_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK-NEXT: [[LHSLOW:%.+]] = vector.extract [[LHS]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[LHSHIGH:%.+]] = vector.extract [[LHS]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[RHSLOW:%.+]] = vector.extract [[RHS]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[RHSHIGH:%.+]] = vector.extract [[RHS]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[CLOW:%.+]] = arith.cmpi ne, [[LHSLOW]], [[RHSLOW]] : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi ne, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.ori [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_ne_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi ne, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_ne_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3xi1>
// CHECK: [[CLOW:%.+]] = arith.cmpi ne, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi ne, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.ori [[CLOW]], [[CHIGH]] : vector<3x1xi1>
// CHECK-NEXT: [[CAST:%.+]] = vector.shape_cast [[RES]] : vector<3x1xi1> to vector<3xi1>
// CHECK: return [[CAST]] : vector<3xi1>
func.func @cmpi_ne_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi1> {
%r = arith.cmpi ne, %a, %b : vector<3xi64>
return %r : vector<3xi1>
}
// CHECK-LABEL: func.func @cmpi_sge_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK-NEXT: [[LHSLOW:%.+]] = vector.extract [[LHS]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[LHSHIGH:%.+]] = vector.extract [[LHS]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[RHSLOW:%.+]] = vector.extract [[RHS]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[RHSHIGH:%.+]] = vector.extract [[RHS]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[CLOW:%.+]] = arith.cmpi uge, [[LHSLOW]], [[RHSLOW]] : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi sge, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_sge_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi sge, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_sge_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3xi1>
// CHECK: [[CLOW:%.+]] = arith.cmpi uge, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: [[CHIGH:%.+]] = arith.cmpi sge, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : vector<3x1xi1>
// CHECK-NEXT: [[CAST:%.+]] = vector.shape_cast [[RES]] : vector<3x1xi1> to vector<3xi1>
// CHECK: return [[CAST]] : vector<3xi1>
func.func @cmpi_sge_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi1> {
%r = arith.cmpi sge, %a, %b : vector<3xi64>
return %r : vector<3xi1>
}
// CHECK-LABEL: func.func @cmpi_sgt_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi ugt, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi sgt, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_sgt_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi sgt, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_sle_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi ule, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi sle, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_sle_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi sle, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_slt_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi ult, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi slt, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_slt_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi slt, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_uge_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi uge, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi uge, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_uge_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi uge, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_ugt_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi ugt, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi ugt, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_ugt_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi ugt, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_ule_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi ule, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi ule, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_ule_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi ule, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func.func @cmpi_ult_scalar
// CHECK-SAME: ([[LHS:%.+]]: vector<2xi32>, [[RHS:%.+]]: vector<2xi32>)
// CHECK: [[CLOW:%.+]] = arith.cmpi ult, {{%.+}}, {{%.+}} : i32
// CHECK-NEXT: [[CHIGH:%.+]] = arith.cmpi ult, [[LHSHIGH:%.+]], [[RHSHIGH:%.+]] : i32
// CHECK-NEXT: [[HIGHEQ:%.+]] = arith.cmpi eq, [[LHSHIGH]], [[RHSHIGH]] : i32
// CHECK-NEXT: [[RES:%.+]] = arith.select [[HIGHEQ]], [[CLOW]], [[CHIGH]] : i1
// CHECK: return [[RES]] : i1
func.func @cmpi_ult_scalar(%a : i64, %b : i64) -> i1 {
%r = arith.cmpi ult, %a, %b : i64
return %r : i1
}
// CHECK-LABEL: func @extsi_scalar
// CHECK-SAME: ([[ARG:%.+]]: i16) -> vector<2xi32>
// CHECK-NEXT: [[EXT:%.+]] = arith.extsi [[ARG]] : i16 to i32
// CHECK-NEXT: [[SZ:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[SB:%.+]] = arith.cmpi slt, [[EXT]], [[SZ]] : i32
// CHECK-NEXT: [[SV:%.+]] = arith.extsi [[SB]] : i1 to i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[EXT]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[SV]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK: return [[INS1]] : vector<2xi32>
func.func @extsi_scalar(%a : i16) -> i64 {
%r = arith.extsi %a : i16 to i64
return %r : i64
}
// CHECK-LABEL: func @extsi_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3xi16>) -> vector<3x2xi32>
// CHECK-NEXT: [[SHAPE:%.+]] = vector.shape_cast [[ARG]] : vector<3xi16> to vector<3x1xi16>
// CHECK-NEXT: [[EXT:%.+]] = arith.extsi [[SHAPE]] : vector<3x1xi16> to vector<3x1xi32>
// CHECK-NEXT: [[CSTE:%.+]] = arith.constant dense<0> : vector<3x1xi32>
// CHECK-NEXT: [[CMP:%.+]] = arith.cmpi slt, [[EXT]], [[CSTE]] : vector<3x1xi32>
// CHECK-NEXT: [[HIGH:%.+]] = arith.extsi [[CMP]] : vector<3x1xi1> to vector<3x1xi32>
// CHECK-NEXT: [[CSTZ:%.+]] = arith.constant dense<0> : vector<3x2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert_strided_slice [[EXT]], [[CSTZ]] {offsets = [0, 0], strides = [1, 1]} : vector<3x1xi32> into vector<3x2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert_strided_slice [[HIGH]], [[INS0]] {offsets = [0, 1], strides = [1, 1]} : vector<3x1xi32> into vector<3x2xi32>
// CHECK-NEXT: return [[INS1]] : vector<3x2xi32>
func.func @extsi_vector(%a : vector<3xi16>) -> vector<3xi64> {
%r = arith.extsi %a : vector<3xi16> to vector<3xi64>
return %r : vector<3xi64>
}
// CHECK-LABEL: func @extui_scalar1
// CHECK-SAME: ([[ARG:%.+]]: i16) -> vector<2xi32>
// CHECK-NEXT: [[EXT:%.+]] = arith.extui [[ARG]] : i16 to i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[EXT]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK: return [[INS0]] : vector<2xi32>
func.func @extui_scalar1(%a : i16) -> i64 {
%r = arith.extui %a : i16 to i64
return %r : i64
}
// CHECK-LABEL: func @extui_scalar2
// CHECK-SAME: ([[ARG:%.+]]: i32) -> vector<2xi32>
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[ARG]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK: return [[INS0]] : vector<2xi32>
func.func @extui_scalar2(%a : i32) -> i64 {
%r = arith.extui %a : i32 to i64
return %r : i64
}
// CHECK-LABEL: func @extui_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3xi16>) -> vector<3x2xi32>
// CHECK-NEXT: [[SHAPE:%.+]] = vector.shape_cast [[ARG]] : vector<3xi16> to vector<3x1xi16>
// CHECK-NEXT: [[EXT:%.+]] = arith.extui [[SHAPE]] : vector<3x1xi16> to vector<3x1xi32>
// CHECK-NEXT: [[CST:%.+]] = arith.constant dense<0> : vector<3x2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert_strided_slice [[EXT]], [[CST]] {offsets = [0, 0], strides = [1, 1]} : vector<3x1xi32> into vector<3x2xi32>
// CHECK: return [[INS0]] : vector<3x2xi32>
func.func @extui_vector(%a : vector<3xi16>) -> vector<3xi64> {
%r = arith.extui %a : vector<3xi16> to vector<3xi64>
return %r : vector<3xi64>
}
// CHECK-LABEL: func @index_cast_int_to_index_scalar
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> index
// CHECK-NEXT: [[EXT:%.+]] = vector.extract [[ARG]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.index_cast [[EXT]] : i32 to index
// CHECK-NEXT: return [[RES]] : index
func.func @index_cast_int_to_index_scalar(%a : i64) -> index {
%r = arith.index_cast %a : i64 to index
return %r : index
}
// CHECK-LABEL: func @index_cast_int_to_index_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3x2xi32>) -> vector<3xindex>
// CHECK-NEXT: [[EXT:%.+]] = vector.extract_strided_slice [[ARG]] {offsets = [0, 0], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[SHAPE:%.+]] = vector.shape_cast [[EXT]] : vector<3x1xi32> to vector<3xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.index_cast [[SHAPE]] : vector<3xi32> to vector<3xindex>
// CHECK-NEXT: return [[RES]] : vector<3xindex>
func.func @index_cast_int_to_index_vector(%a : vector<3xi64>) -> vector<3xindex> {
%r = arith.index_cast %a : vector<3xi64> to vector<3xindex>
return %r : vector<3xindex>
}
// CHECK-LABEL: func @index_castui_int_to_index_scalar
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> index
// CHECK-NEXT: [[EXT:%.+]] = vector.extract [[ARG]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.index_castui [[EXT]] : i32 to index
// CHECK-NEXT: return [[RES]] : index
func.func @index_castui_int_to_index_scalar(%a : i64) -> index {
%r = arith.index_castui %a : i64 to index
return %r : index
}
// CHECK-LABEL: func @index_castui_int_to_index_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3x2xi32>) -> vector<3xindex>
// CHECK-NEXT: [[EXT:%.+]] = vector.extract_strided_slice [[ARG]] {offsets = [0, 0], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[SHAPE:%.+]] = vector.shape_cast [[EXT]] : vector<3x1xi32> to vector<3xi32>
// CHECK-NEXT: [[RES:%.+]] = arith.index_castui [[SHAPE]] : vector<3xi32> to vector<3xindex>
// CHECK-NEXT: return [[RES]] : vector<3xindex>
func.func @index_castui_int_to_index_vector(%a : vector<3xi64>) -> vector<3xindex> {
%r = arith.index_castui %a : vector<3xi64> to vector<3xindex>
return %r : vector<3xindex>
}
// CHECK-LABEL: func @index_cast_index_to_int_scalar
// CHECK-SAME: ([[ARG:%.+]]: index) -> vector<2xi32>
// CHECK-NEXT: [[CAST:%.+]] = arith.index_cast [[ARG]] : index to i32
// CHECK-NEXT: [[C0I32:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[NEG:%.+]] = arith.cmpi slt, [[CAST]], [[C0I32]] : i32
// CHECK-NEXT: [[EXT:%.+]] = arith.extsi [[NEG]] : i1 to i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[CAST]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[EXT]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @index_cast_index_to_int_scalar(%a : index) -> i64 {
%r = arith.index_cast %a : index to i64
return %r : i64
}
// CHECK-LABEL: func @index_cast_index_to_int_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3xindex>) -> vector<3x2xi32>
// CHECK-NEXT: arith.index_cast [[ARG]] : vector<3xindex> to vector<3xi32>
// CHECK-NEXT: vector.shape_cast
// CHECK-NEXT: arith.constant dense<0> : vector<3x1xi32>
// CHECK-NEXT: arith.cmpi slt
// CHECK-NEXT: arith.extsi
// CHECK-NEXT: arith.constant dense<0> : vector<3x2xi32>
// CHECK-NEXT: vector.insert_strided_slice
// CHECK-NEXT: vector.insert_strided_slice
// CHECK-NEXT: return {{%.+}} : vector<3x2xi32>
func.func @index_cast_index_to_int_vector(%a : vector<3xindex>) -> vector<3xi64> {
%r = arith.index_cast %a : vector<3xindex> to vector<3xi64>
return %r : vector<3xi64>
}
// CHECK-LABEL: func @index_castui_index_to_int_scalar
// CHECK-SAME: ([[ARG:%.+]]: index) -> vector<2xi32>
// CHECK-NEXT: [[CAST:%.+]] = arith.index_castui [[ARG]] : index to i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[RES:%.+]] = vector.insert [[CAST]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: return [[RES]] : vector<2xi32>
func.func @index_castui_index_to_int_scalar(%a : index) -> i64 {
%r = arith.index_castui %a : index to i64
return %r : i64
}
// CHECK-LABEL: func @index_castui_index_to_int_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3xindex>) -> vector<3x2xi32>
// CHECK-NEXT: [[CAST:%.+]] = arith.index_castui [[ARG]] : vector<3xindex> to vector<3xi32>
// CHECK-NEXT: [[SHAPE:%.+]] = vector.shape_cast [[CAST]] : vector<3xi32> to vector<3x1xi32>
// CHECK-NEXT: [[CST:%.+]] = arith.constant dense<0> : vector<3x2xi32>
// CHECK-NEXT: [[RES:%.+]] = vector.insert_strided_slice [[SHAPE]], [[CST]] {offsets = [0, 0], strides = [1, 1]} : vector<3x1xi32> into vector<3x2xi32>
// CHECK-NEXT: return [[RES]] : vector<3x2xi32>
func.func @index_castui_index_to_int_vector(%a : vector<3xindex>) -> vector<3xi64> {
%r = arith.index_castui %a : vector<3xindex> to vector<3xi64>
return %r : vector<3xi64>
}
// CHECK-LABEL: func @trunci_scalar1
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> i32
// CHECK-NEXT: [[EXT:%.+]] = vector.extract [[ARG]][0] : i32 from vector<2xi32>
// CHECK-NEXT: return [[EXT]] : i32
func.func @trunci_scalar1(%a : i64) -> i32 {
%b = arith.trunci %a : i64 to i32
return %b : i32
}
// CHECK-LABEL: func @trunci_scalar2
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> i16
// CHECK-NEXT: [[EXTR:%.+]] = vector.extract [[ARG]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[TRNC:%.+]] = arith.trunci [[EXTR]] : i32 to i16
// CHECK-NEXT: return [[TRNC]] : i16
func.func @trunci_scalar2(%a : i64) -> i16 {
%b = arith.trunci %a : i64 to i16
return %b : i16
}
// CHECK-LABEL: func @trunci_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3x2xi32>) -> vector<3xi16>
// CHECK-NEXT: [[EXTR:%.+]] = vector.extract_strided_slice [[ARG]] {offsets = [0, 0], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[SHAPE:%.+]] = vector.shape_cast [[EXTR]] : vector<3x1xi32> to vector<3xi32>
// CHECK-NEXT: [[TRNC:%.+]] = arith.trunci [[SHAPE]] : vector<3xi32> to vector<3xi16>
// CHECK-NEXT: return [[TRNC]] : vector<3xi16>
func.func @trunci_vector(%a : vector<3xi64>) -> vector<3xi16> {
%b = arith.trunci %a : vector<3xi64> to vector<3xi16>
return %b : vector<3xi16>
}
// CHECK-LABEL: func @maxui_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK: arith.cmpi ugt
// CHECK: arith.cmpi ugt
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: [[INS0:%.+]] = vector.insert {{%.+}}, {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert {{%.+}}, [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @maxui_scalar(%a : i64, %b : i64) -> i64 {
%x = arith.maxui %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @maxui_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: arith.cmpi ugt
// CHECK: arith.cmpi ugt
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @maxui_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.maxui %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func @maxsi_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK: arith.cmpi ugt
// CHECK: arith.cmpi sgt
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: [[INS0:%.+]] = vector.insert {{%.+}}, {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert {{%.+}}, [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @maxsi_scalar(%a : i64, %b : i64) -> i64 {
%x = arith.maxsi %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @maxsi_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: arith.cmpi ugt
// CHECK: arith.cmpi sgt
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @maxsi_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.maxsi %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func @minui_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK: arith.cmpi ult
// CHECK: arith.cmpi ult
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: [[INS0:%.+]] = vector.insert {{%.+}}, {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert {{%.+}}, [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @minui_scalar(%a : i64, %b : i64) -> i64 {
%x = arith.minui %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @minui_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: arith.cmpi ult
// CHECK: arith.cmpi ult
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @minui_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.minui %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func @minsi_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK: arith.cmpi ult
// CHECK: arith.cmpi slt
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: [[INS0:%.+]] = vector.insert {{%.+}}, {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert {{%.+}}, [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @minsi_scalar(%a : i64, %b : i64) -> i64 {
%x = arith.minsi %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @minsi_vector
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: arith.cmpi ult
// CHECK: arith.cmpi slt
// CHECK: arith.cmpi eq
// CHECK: arith.select
// CHECK: arith.select
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @minsi_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.minsi %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func.func @select_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>, [[ARG2:%.+]]: i1)
// CHECK-SAME: -> vector<2xi32>
// CHECK-NEXT: [[TLOW:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[THIGH:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[FLOW:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[FHIGH:%.+]] = vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[SLOW:%.+]] = arith.select [[ARG2]], [[TLOW]], [[FLOW]] : i32
// CHECK-NEXT: [[SHIGH:%.+]] = arith.select [[ARG2]], [[THIGH]], [[FHIGH]] : i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[SLOW]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[SHIGH]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK: return [[INS1]] : vector<2xi32>
func.func @select_scalar(%a : i64, %b : i64, %c : i1) -> i64 {
%r = arith.select %c, %a, %b : i64
return %r : i64
}
// CHECK-LABEL: func.func @select_vector_whole
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>, [[ARG2:%.+]]: i1)
// CHECK-SAME: -> vector<3x2xi32>
// CHECK: arith.select {{%.+}}, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: arith.select {{%.+}}, {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{%.+}} : vector<3x2xi32>
func.func @select_vector_whole(%a : vector<3xi64>, %b : vector<3xi64>, %c : i1) -> vector<3xi64> {
%r = arith.select %c, %a, %b : vector<3xi64>
return %r : vector<3xi64>
}
// CHECK-LABEL: func.func @select_vector_elementwise
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>, [[ARG2:%.+]]: vector<3xi1>)
// CHECK-SAME: -> vector<3x2xi32>
// CHECK: arith.select {{%.+}}, {{%.+}}, {{%.+}} : vector<3x1xi1>, vector<3x1xi32>
// CHECK-NEXT: arith.select {{%.+}}, {{%.+}}, {{%.+}} : vector<3x1xi1>, vector<3x1xi32>
// CHECK: return {{%.+}} : vector<3x2xi32>
func.func @select_vector_elementwise(%a : vector<3xi64>, %b : vector<3xi64>, %c : vector<3xi1>) -> vector<3xi64> {
%r = arith.select %c, %a, %b : vector<3xi1>, vector<3xi64>
return %r : vector<3xi64>
}
// CHECK-LABEL: func.func @muli_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract [[ARG1]][1] : i32 from vector<2xi32>
//
// CHECK-DAG: [[RESLOW:%.+]], [[HI0:%.+]] = arith.mului_extended [[LOW0]], [[LOW1]] : i32
// CHECK-DAG: [[HI1:%.+]] = arith.muli [[LOW0]], [[HIGH1]] : i32
// CHECK-DAG: [[HI2:%.+]] = arith.muli [[HIGH0]], [[LOW1]] : i32
// CHECK-NEXT: [[RESHI1:%.+]] = arith.addi [[HI0]], [[HI1]] : i32
// CHECK-NEXT: [[RESHI2:%.+]] = arith.addi [[RESHI1]], [[HI2]] : i32
//
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[RESLOW]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[RESHI2]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @muli_scalar(%a : i64, %b : i64) -> i64 {
%m = arith.muli %a, %b : i64
return %m : i64
}
// CHECK-LABEL: func.func @muli_vector
// CHECK-SAME: ({{%.+}}: vector<3x2xi32>, {{%.+}}: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK-DAG: arith.mului_extended
// CHECK-DAG: arith.muli
// CHECK-DAG: arith.muli
// CHECK-NEXT: arith.addi
// CHECK-NEXT: arith.addi
// CHECK: return {{%.+}} : vector<3x2xi32>
func.func @muli_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%m = arith.muli %a, %b : vector<3xi64>
return %m : vector<3xi64>
}
// CHECK-LABEL: func.func @shli_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[CST0:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[CST32:%.+]] = arith.constant 32 : i32
// CHECK-NEXT: [[OOB:%.+]] = arith.cmpi uge, [[LOW1]], [[CST32]] : i32
// CHECK-NEXT: [[SHLOW0:%.+]] = arith.shli [[LOW0]], [[LOW1]] : i32
// CHECK-NEXT: [[RES0:%.+]] = arith.select [[OOB]], [[CST0]], [[SHLOW0]] : i32
// CHECK-NEXT: [[SHAMT:%.+]] = arith.select [[OOB]], [[CST32]], [[LOW1]] : i32
// CHECK-NEXT: [[RSHAMT:%.+]] = arith.subi [[CST32]], [[SHAMT]] : i32
// CHECK-NEXT: [[SHRHIGH0:%.+]] = arith.shrui [[LOW0]], [[RSHAMT]] : i32
// CHECK-NEXT: [[LSHAMT:%.+]] = arith.subi [[LOW1]], [[CST32]] : i32
// CHECK-NEXT: [[SHLHIGH0:%.+]] = arith.shli [[LOW0]], [[LSHAMT]] : i32
// CHECK-NEXT: [[SHLHIGH1:%.+]] = arith.shli [[HIGH0]], [[LOW1]] : i32
// CHECK-NEXT: [[RES1HIGH:%.+]] = arith.select [[OOB]], [[CST0]], [[SHLHIGH1]] : i32
// CHECK-NEXT: [[RES1LOW:%.+]] = arith.select [[OOB]], [[SHLHIGH0]], [[SHRHIGH0]] : i32
// CHECK-NEXT: [[RES1:%.+]] = arith.ori [[RES1LOW]], [[RES1HIGH]] : i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[RES0]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[RES1]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @shli_scalar(%a : i64, %b : i64) -> i64 {
%c = arith.shli %a, %b : i64
return %c : i64
}
// CHECK-LABEL: func.func @shli_vector
// CHECK-SAME: ({{%.+}}: vector<3x2xi32>, {{%.+}}: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: {{%.+}} = arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: {{%.+}} = arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: {{%.+}} = arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: {{%.+}} = arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{%.+}} : vector<3x2xi32>
func.func @shli_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%m = arith.shli %a, %b : vector<3xi64>
return %m : vector<3xi64>
}
// CHECK-LABEL: func.func @shrui_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[CST0:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[CST32:%.+]] = arith.constant 32 : i32
// CHECK-DAG: [[OOB:%.+]] = arith.cmpi uge, [[LOW1]], [[CST32]] : i32
// CHECK-DAG: [[SHLOW0:%.+]] = arith.shrui [[LOW0]], [[LOW1]] : i32
// CHECK-NEXT: [[RES0LOW:%.+]] = arith.select [[OOB]], [[CST0]], [[SHLOW0]] : i32
// CHECK-NEXT: [[SHRHIGH0:%.+]] = arith.shrui [[HIGH0]], [[LOW1]] : i32
// CHECK-NEXT: [[RESLOW1:%.+]] = arith.select [[OOB]], [[CST0]], [[SHRHIGH0]] : i32
// CHECK-NEXT: [[SHAMT:%.+]] = arith.select [[OOB]], [[CST32]], [[LOW1]] : i32
// CHECK-NEXT: [[LSHAMT:%.+]] = arith.subi [[CST32]], [[SHAMT]] : i32
// CHECK-NEXT: [[SHLHIGH0:%.+]] = arith.shli [[HIGH0]], [[LSHAMT]] : i32
// CHECK-NEXT: [[RSHAMT:%.+]] = arith.subi [[LOW1]], [[CST32]] : i32
// CHECK-NEXT: [[SHRHIGH0:%.+]] = arith.shrui [[HIGH0]], [[RSHAMT]] : i32
// CHECK-NEXT: [[RES0HIGH:%.+]] = arith.select [[OOB]], [[SHRHIGH0]], [[SHLHIGH0]] : i32
// CHECK-NEXT: [[RES0:%.+]] = arith.ori [[RES0LOW]], [[RES0HIGH]] : i32
// CHECK-NEXT: [[VZ:%.+]] = arith.constant dense<0> : vector<2xi32>
// CHECK-NEXT: [[INS0:%.+]] = vector.insert [[RES0]], [[VZ]] [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[RESLOW1]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @shrui_scalar(%a : i64, %b : i64) -> i64 {
%c = arith.shrui %a, %b : i64
return %c : i64
}
// CHECK-LABEL: func.func @shrui_scalar_cst_2
// CHECK-SAME: ({{%.+}}: vector<2xi32>) -> vector<2xi32>
// CHECK: return {{%.+}} : vector<2xi32>
func.func @shrui_scalar_cst_2(%a : i64) -> i64 {
%b = arith.constant 2 : i64
%c = arith.shrui %a, %b : i64
return %c : i64
}
// CHECK-LABEL: func.func @shrui_scalar_cst_36
// CHECK-SAME: ({{%.+}}: vector<2xi32>) -> vector<2xi32>
// CHECK: return {{%.+}} : vector<2xi32>
func.func @shrui_scalar_cst_36(%a : i64) -> i64 {
%b = arith.constant 36 : i64
%c = arith.shrui %a, %b : i64
return %c : i64
}
// CHECK-LABEL: func.func @shrui_vector
// CHECK-SAME: ({{%.+}}: vector<3x2xi32>, {{%.+}}: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: {{%.+}} = arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: {{%.+}} = arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: {{%.+}} = arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: {{%.+}} = arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{%.+}} : vector<3x2xi32>
func.func @shrui_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%m = arith.shrui %a, %b : vector<3xi64>
return %m : vector<3xi64>
}
// CHECK-LABEL: func.func @shrsi_scalar
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[CST0:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[NEG:%.+]] = arith.cmpi slt, [[HIGH0]], [[CST0]] : i32
// CHECK-NEXT: [[NEGEXT:%.+]] = arith.extsi [[NEG]] : i1 to i32
// CHECK: [[CST64:%.+]] = arith.constant 64 : i32
// CHECK-NEXT: [[SIGNBITS:%.+]] = arith.subi [[CST64]], [[LOW1]] : i32
// CHECK: arith.shli
// CHECK: arith.shrui
// CHECK: arith.shli
// CHECK: arith.shli
// CHECK: arith.shrui
// CHECK: arith.shrui
// CHECK: arith.shli
// CHECK: arith.shrui
// CHECK: return {{%.+}} : vector<2xi32>
func.func @shrsi_scalar(%a : i64, %b : i64) -> i64 {
%c = arith.shrsi %a, %b : i64
return %c : i64
}
// CHECK-LABEL: func.func @shrsi_vector
// CHECK-SAME: ({{%.+}}: vector<3x2xi32>, {{%.+}}: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shli {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: arith.shrui {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{%.+}} : vector<3x2xi32>
func.func @shrsi_vector(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%m = arith.shrsi %a, %b : vector<3xi64>
return %m : vector<3xi64>
}
// CHECK-LABEL: func @andi_scalar_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[RES0:%.+]] = arith.andi [[LOW0]], [[LOW1]] : i32
// CHECK-NEXT: [[RES1:%.+]] = arith.andi [[HIGH0]], [[HIGH1]] : i32
// CHECK: [[INS0:%.+]] = vector.insert [[RES0]], {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[RES1]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @andi_scalar_a_b(%a : i64, %b : i64) -> i64 {
%x = arith.andi %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @andi_vector_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: {{%.+}} = arith.andi {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: {{%.+}} = arith.andi {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @andi_vector_a_b(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.andi %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func @ori_scalar_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[RES0:%.+]] = arith.ori [[LOW0]], [[LOW1]] : i32
// CHECK-NEXT: [[RES1:%.+]] = arith.ori [[HIGH0]], [[HIGH1]] : i32
// CHECK: [[INS0:%.+]] = vector.insert [[RES0]], {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[RES1]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @ori_scalar_a_b(%a : i64, %b : i64) -> i64 {
%x = arith.ori %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @ori_vector_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: {{%.+}} = arith.ori {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: {{%.+}} = arith.ori {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @ori_vector_a_b(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.ori %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func @xori_scalar_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<2xi32>, [[ARG1:%.+]]: vector<2xi32>) -> vector<2xi32>
// CHECK-NEXT: [[LOW0:%.+]] = vector.extract [[ARG0]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH0:%.+]] = vector.extract [[ARG0]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[LOW1:%.+]] = vector.extract [[ARG1]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HIGH1:%.+]] = vector.extract [[ARG1]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[RES0:%.+]] = arith.xori [[LOW0]], [[LOW1]] : i32
// CHECK-NEXT: [[RES1:%.+]] = arith.xori [[HIGH0]], [[HIGH1]] : i32
// CHECK: [[INS0:%.+]] = vector.insert [[RES0]], {{%.+}} [0] : i32 into vector<2xi32>
// CHECK-NEXT: [[INS1:%.+]] = vector.insert [[RES1]], [[INS0]] [1] : i32 into vector<2xi32>
// CHECK-NEXT: return [[INS1]] : vector<2xi32>
func.func @xori_scalar_a_b(%a : i64, %b : i64) -> i64 {
%x = arith.xori %a, %b : i64
return %x : i64
}
// CHECK-LABEL: func @xori_vector_a_b
// CHECK-SAME: ([[ARG0:%.+]]: vector<3x2xi32>, [[ARG1:%.+]]: vector<3x2xi32>) -> vector<3x2xi32>
// CHECK: {{%.+}} = arith.xori {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK-NEXT: {{%.+}} = arith.xori {{%.+}}, {{%.+}} : vector<3x1xi32>
// CHECK: return {{.+}} : vector<3x2xi32>
func.func @xori_vector_a_b(%a : vector<3xi64>, %b : vector<3xi64>) -> vector<3xi64> {
%x = arith.xori %a, %b : vector<3xi64>
return %x : vector<3xi64>
}
// CHECK-LABEL: func @uitofp_i64_f64
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> f64
// CHECK-NEXT: [[LOW:%.+]] = vector.extract [[ARG]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HI:%.+]] = vector.extract [[ARG]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[CST0:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[HIEQ0:%.+]] = arith.cmpi eq, [[HI]], [[CST0]] : i32
// CHECK-NEXT: [[LOWFP:%.+]] = arith.uitofp [[LOW]] : i32 to f64
// CHECK-NEXT: [[HIFP:%.+]] = arith.uitofp [[HI]] : i32 to f64
// CHECK-NEXT: [[POW:%.+]] = arith.constant 0x41F0000000000000 : f64
// CHECK-NEXT: [[RESHI:%.+]] = arith.mulf [[HIFP]], [[POW]] : f64
// CHECK-NEXT: [[RES:%.+]] = arith.addf [[LOWFP]], [[RESHI]] : f64
// CHECK-NEXT: [[SEL:%.+]] = arith.select [[HIEQ0]], [[LOWFP]], [[RES]] : f64
// CHECK-NEXT: return [[SEL]] : f64
func.func @uitofp_i64_f64(%a : i64) -> f64 {
%r = arith.uitofp %a : i64 to f64
return %r : f64
}
// CHECK-LABEL: func @uitofp_i64_f64_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3x2xi32>) -> vector<3xf64>
// CHECK-NEXT: [[EXTLOW:%.+]] = vector.extract_strided_slice [[ARG]] {offsets = [0, 0], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[EXTHI:%.+]] = vector.extract_strided_slice [[ARG]] {offsets = [0, 1], sizes = [3, 1], strides = [1, 1]} : vector<3x2xi32> to vector<3x1xi32>
// CHECK-NEXT: [[LOW:%.+]] = vector.shape_cast [[EXTLOW]] : vector<3x1xi32> to vector<3xi32>
// CHECK-NEXT: [[HI:%.+]] = vector.shape_cast [[EXTHI]] : vector<3x1xi32> to vector<3xi32>
// CHECK-NEXT: [[CST0:%.+]] = arith.constant dense<0> : vector<3xi32>
// CHECK-NEXT: [[HIEQ0:%.+]] = arith.cmpi eq, [[HI]], [[CST0]] : vector<3xi32>
// CHECK-NEXT: [[LOWFP:%.+]] = arith.uitofp [[LOW]] : vector<3xi32> to vector<3xf64>
// CHECK-NEXT: [[HIFP:%.+]] = arith.uitofp [[HI]] : vector<3xi32> to vector<3xf64>
// CHECK-NEXT: [[POW:%.+]] = arith.constant dense<0x41F0000000000000> : vector<3xf64>
// CHECK-NEXT: [[RESHI:%.+]] = arith.mulf [[HIFP]], [[POW]] : vector<3xf64>
// CHECK-NEXT: [[RES:%.+]] = arith.addf [[LOWFP]], [[RESHI]] : vector<3xf64>
// CHECK-NEXT: [[SEL:%.+]] = arith.select [[HIEQ0]], [[LOWFP]], [[RES]] : vector<3xi1>, vector<3xf64>
// CHECK-NEXT: return [[SEL]] : vector<3xf64>
func.func @uitofp_i64_f64_vector(%a : vector<3xi64>) -> vector<3xf64> {
%r = arith.uitofp %a : vector<3xi64> to vector<3xf64>
return %r : vector<3xf64>
}
// CHECK-LABEL: func @uitofp_i64_f16
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> f16
// CHECK-NEXT: [[LOW:%.+]] = vector.extract [[ARG]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[HI:%.+]] = vector.extract [[ARG]][1] : i32 from vector<2xi32>
// CHECK-NEXT: [[CST0:%.+]] = arith.constant 0 : i32
// CHECK-NEXT: [[HIEQ0:%.+]] = arith.cmpi eq, [[HI]], [[CST0]] : i32
// CHECK-NEXT: [[LOWFP:%.+]] = arith.uitofp [[LOW]] : i32 to f16
// CHECK-NEXT: [[HIFP:%.+]] = arith.uitofp [[HI]] : i32 to f16
// CHECK-NEXT: [[POW:%.+]] = arith.constant 0x7C00 : f16
// CHECK-NEXT: [[RESHI:%.+]] = arith.mulf [[HIFP]], [[POW]] : f16
// CHECK-NEXT: [[RES:%.+]] = arith.addf [[LOWFP]], [[RESHI]] : f16
// CHECK-NEXT: [[SEL:%.+]] = arith.select [[HIEQ0]], [[LOWFP]], [[RES]] : f16
// CHECK-NEXT: return [[SEL]] : f16
func.func @uitofp_i64_f16(%a : i64) -> f16 {
%r = arith.uitofp %a : i64 to f16
return %r : f16
}
// CHECK-LABEL: func @sitofp_i64_f64
// CHECK-SAME: ([[ARG:%.+]]: vector<2xi32>) -> f64
// CHECK: [[VONES:%.+]] = arith.constant dense<-1> : vector<2xi32>
// CHECK: [[ONES1:%.+]] = vector.extract [[VONES]][0] : i32 from vector<2xi32>
// CHECK-NEXT: [[ONES2:%.+]] = vector.extract [[VONES]][1] : i32 from vector<2xi32>
// CHECK: arith.xori {{%.+}}, [[ONES1]] : i32
// CHECK-NEXT: arith.xori {{%.+}}, [[ONES2]] : i32
// CHECK: [[CST0:%.+]] = arith.constant 0 : i32
// CHECK: [[HIEQ0:%.+]] = arith.cmpi eq, [[HI:%.+]], [[CST0]] : i32
// CHECK-NEXT: [[LOWFP:%.+]] = arith.uitofp [[LOW:%.+]] : i32 to f64
// CHECK-NEXT: [[HIFP:%.+]] = arith.uitofp [[HI]] : i32 to f64
// CHECK-NEXT: [[POW:%.+]] = arith.constant 0x41F0000000000000 : f64
// CHECK-NEXT: [[RESHI:%.+]] = arith.mulf [[HIFP]], [[POW]] : f64
// CHECK-NEXT: [[RES:%.+]] = arith.addf [[LOWFP]], [[RESHI]] : f64
// CHECK-NEXT: [[SEL:%.+]] = arith.select [[HIEQ0]], [[LOWFP]], [[RES]] : f64
// CHECK-NEXT: [[NEG:%.+]] = arith.negf [[SEL]] : f64
// CHECK-NEXT: [[FINAL:%.+]] = arith.select %{{.+}}, [[NEG]], [[SEL]] : f64
// CHECK-NEXT: return [[FINAL]] : f64
func.func @sitofp_i64_f64(%a : i64) -> f64 {
%r = arith.sitofp %a : i64 to f64
return %r : f64
}
// CHECK-LABEL: func @sitofp_i64_f64_vector
// CHECK-SAME: ([[ARG:%.+]]: vector<3x2xi32>) -> vector<3xf64>
// CHECK: [[VONES:%.+]] = arith.constant dense<-1> : vector<3x2xi32>
// CHECK: arith.xori
// CHECK-NEXT: arith.xori
// CHECK: [[HIEQ0:%.+]] = arith.cmpi eq, [[HI:%.+]], [[CST0:%.+]] : vector<3xi32>
// CHECK-NEXT: [[LOWFP:%.+]] = arith.uitofp [[LOW:%.+]] : vector<3xi32> to vector<3xf64>
// CHECK-NEXT: [[HIFP:%.+]] = arith.uitofp [[HI:%.+]] : vector<3xi32> to vector<3xf64>
// CHECK-NEXT: [[POW:%.+]] = arith.constant dense<0x41F0000000000000> : vector<3xf64>
// CHECK-NEXT: [[RESHI:%.+]] = arith.mulf [[HIFP]], [[POW]] : vector<3xf64>
// CHECK-NEXT: [[RES:%.+]] = arith.addf [[LOWFP]], [[RESHI]] : vector<3xf64>
// CHECK-NEXT: [[SEL:%.+]] = arith.select [[HIEQ0]], [[LOWFP]], [[RES]] : vector<3xi1>, vector<3xf64>
// CHECK-NEXT: [[NEG:%.+]] = arith.negf [[SEL]] : vector<3xf64>
// CHECK-NEXT: [[FINAL:%.+]] = arith.select %{{.+}}, [[NEG]], [[SEL]] : vector<3xi1>, vector<3xf64>
// CHECK-NEXT: return [[FINAL]] : vector<3xf64>
func.func @sitofp_i64_f64_vector(%a : vector<3xi64>) -> vector<3xf64> {
%r = arith.sitofp %a : vector<3xi64> to vector<3xf64>
return %r : vector<3xf64>
}