cranelift: Fix bint implementation on interpreter (#4299)
* cranelift: Fix `bint` implementation on interpreter The interpreter was returning -1 instead of 1 for positive values. This also extends the bint test suite to cover all types. * cranelift: Restrict `bint` to scalar values only
This commit is contained in:
@@ -718,6 +718,12 @@ pub(crate) fn define(
|
|||||||
.build(),
|
.build(),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
let ScalarBool = &TypeVar::new(
|
||||||
|
"ScalarBool",
|
||||||
|
"A scalar boolean type",
|
||||||
|
TypeSetBuilder::new().bools(Interval::All).build(),
|
||||||
|
);
|
||||||
|
|
||||||
let iB = &TypeVar::new(
|
let iB = &TypeVar::new(
|
||||||
"iB",
|
"iB",
|
||||||
"A scalar integer type",
|
"A scalar integer type",
|
||||||
@@ -3331,13 +3337,10 @@ pub(crate) fn define(
|
|||||||
|
|
||||||
let IntTo = &TypeVar::new(
|
let IntTo = &TypeVar::new(
|
||||||
"IntTo",
|
"IntTo",
|
||||||
"An integer type with the same number of lanes",
|
"A scalar integer type",
|
||||||
TypeSetBuilder::new()
|
TypeSetBuilder::new().ints(Interval::All).build(),
|
||||||
.ints(Interval::All)
|
|
||||||
.simd_lanes(Interval::All)
|
|
||||||
.build(),
|
|
||||||
);
|
);
|
||||||
let x = &Operand::new("x", Bool);
|
let x = &Operand::new("x", ScalarBool);
|
||||||
let a = &Operand::new("a", IntTo);
|
let a = &Operand::new("a", IntTo);
|
||||||
|
|
||||||
ig.push(
|
ig.push(
|
||||||
@@ -3346,8 +3349,7 @@ pub(crate) fn define(
|
|||||||
r#"
|
r#"
|
||||||
Convert `x` to an integer.
|
Convert `x` to an integer.
|
||||||
|
|
||||||
True maps to 1 and false maps to 0. The result type must have the same
|
True maps to 1 and false maps to 0.
|
||||||
number of vector lanes as the input.
|
|
||||||
"#,
|
"#,
|
||||||
&formats.unary,
|
&formats.unary,
|
||||||
)
|
)
|
||||||
@@ -3355,6 +3357,17 @@ pub(crate) fn define(
|
|||||||
.operands_out(vec![a]),
|
.operands_out(vec![a]),
|
||||||
);
|
);
|
||||||
|
|
||||||
|
let IntTo = &TypeVar::new(
|
||||||
|
"IntTo",
|
||||||
|
"An integer type with the same number of lanes",
|
||||||
|
TypeSetBuilder::new()
|
||||||
|
.ints(Interval::All)
|
||||||
|
.simd_lanes(Interval::All)
|
||||||
|
.build(),
|
||||||
|
);
|
||||||
|
let x = &Operand::new("x", Bool);
|
||||||
|
let a = &Operand::new("a", IntTo);
|
||||||
|
|
||||||
ig.push(
|
ig.push(
|
||||||
Inst::new(
|
Inst::new(
|
||||||
"bmask",
|
"bmask",
|
||||||
|
|||||||
@@ -1,7 +1,91 @@
|
|||||||
|
test interpret
|
||||||
test run
|
test run
|
||||||
target aarch64
|
target aarch64
|
||||||
target x86_64
|
target x86_64
|
||||||
|
|
||||||
|
function %bint_b1_i8_true() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 true
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i8_true() == 1
|
||||||
|
|
||||||
|
function %bint_b1_i8_false() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 false
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i8_false() == 0
|
||||||
|
|
||||||
|
function %bint_b1_i16_true() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 true
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i16_true() == 1
|
||||||
|
|
||||||
|
function %bint_b1_i16_false() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 false
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i16_fals() == 0
|
||||||
|
|
||||||
|
function %bint_b1_i32_true() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 true
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i32_true() == 1
|
||||||
|
|
||||||
|
function %bint_b1_i32_false() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 false
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i32_fals() == 0
|
||||||
|
|
||||||
|
function %bint_b1_i64_true() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 true
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i64_true() == 1
|
||||||
|
|
||||||
|
function %bint_b1_i64_false() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 false
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i64_fals() == 0
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function %bint_b8_i8_true() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 true
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i8_true() == 1
|
||||||
|
|
||||||
|
function %bint_b8_i8_false() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 false
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i8_false() == 0
|
||||||
|
|
||||||
function %bint_b8_i16_true() -> i16 {
|
function %bint_b8_i16_true() -> i16 {
|
||||||
block0:
|
block0:
|
||||||
v0 = bconst.b8 true
|
v0 = bconst.b8 true
|
||||||
@@ -10,6 +94,65 @@ block0:
|
|||||||
}
|
}
|
||||||
; run: %bint_b8_i16_true() == 1
|
; run: %bint_b8_i16_true() == 1
|
||||||
|
|
||||||
|
function %bint_b8_i16_false() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 false
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i16_fals() == 0
|
||||||
|
|
||||||
|
function %bint_b8_i32_true() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 true
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i32_true() == 1
|
||||||
|
|
||||||
|
function %bint_b8_i32_false() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 false
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i32_fals() == 0
|
||||||
|
|
||||||
|
function %bint_b8_i64_true() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 true
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i64_true() == 1
|
||||||
|
|
||||||
|
function %bint_b8_i64_false() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 false
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i64_fals() == 0
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function %bint_b16_i8_true() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 true
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i8_true() == 1
|
||||||
|
|
||||||
|
function %bint_b16_i8_false() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 false
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i8_fals() == 0
|
||||||
|
|
||||||
function %bint_b16_i16_true() -> i16 {
|
function %bint_b16_i16_true() -> i16 {
|
||||||
block0:
|
block0:
|
||||||
@@ -17,16 +160,7 @@ block0:
|
|||||||
v1 = bint.i16 v0
|
v1 = bint.i16 v0
|
||||||
return v1
|
return v1
|
||||||
}
|
}
|
||||||
; run: %bint_b16_i16_true() == 1
|
; run: %bint_b16_i16_tru() == 1
|
||||||
|
|
||||||
function %bint_b8_i16_false() -> i16 {
|
|
||||||
block0:
|
|
||||||
v0 = bconst.b8 false
|
|
||||||
v1 = bint.i16 v0
|
|
||||||
return v1
|
|
||||||
}
|
|
||||||
; run: %bint_b8_i16_false() == 0
|
|
||||||
|
|
||||||
|
|
||||||
function %bint_b16_i16_false() -> i16 {
|
function %bint_b16_i16_false() -> i16 {
|
||||||
block0:
|
block0:
|
||||||
@@ -34,4 +168,172 @@ block0:
|
|||||||
v1 = bint.i16 v0
|
v1 = bint.i16 v0
|
||||||
return v1
|
return v1
|
||||||
}
|
}
|
||||||
; run: %bint_b16_i16_false() == 0
|
; run: %bint_b16_i16_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b16_i32_true() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 true
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i32_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b16_i32_false() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 false
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i32_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b16_i64_true() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 true
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i64_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b16_i64_false() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 false
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i64_fal() == 0
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function %bint_b32_i8_true() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 true
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i8_true() == 1
|
||||||
|
|
||||||
|
function %bint_b32_i8_false() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 false
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i8_fals() == 0
|
||||||
|
|
||||||
|
function %bint_b32_i16_true() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 true
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i16_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b32_i16_false() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 false
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i16_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b32_i32_true() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 true
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i32_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b32_i32_false() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 false
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i32_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b32_i64_true() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 true
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i64_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b32_i64_false() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 false
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i64_fal() == 0
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
function %bint_b64_i8_true() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 true
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i8_true() == 1
|
||||||
|
|
||||||
|
function %bint_b64_i8_false() -> i8 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 false
|
||||||
|
v1 = bint.i8 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i8_fals() == 0
|
||||||
|
|
||||||
|
function %bint_b64_i16_true() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 true
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i16_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b64_i16_false() -> i16 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 false
|
||||||
|
v1 = bint.i16 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i16_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b64_i32_true() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 true
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i32_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b64_i32_false() -> i32 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 false
|
||||||
|
v1 = bint.i32 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i32_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b64_i64_true() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 true
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i64_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b64_i64_false() -> i64 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 false
|
||||||
|
v1 = bint.i64 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i64_fal() == 0
|
||||||
|
|||||||
@@ -1,12 +1,85 @@
|
|||||||
|
test interpret
|
||||||
test run
|
test run
|
||||||
set enable_llvm_abi_extensions=true
|
set enable_llvm_abi_extensions=true
|
||||||
target aarch64
|
target aarch64
|
||||||
target x86_64
|
target x86_64
|
||||||
|
|
||||||
function %bint_b8_i128() -> i128 {
|
function %bint_b1_i128_true() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 true
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i128_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b1_i128_false() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b1 false
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b1_i128_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b8_i128_true() -> i128 {
|
||||||
block0:
|
block0:
|
||||||
v0 = bconst.b8 true
|
v0 = bconst.b8 true
|
||||||
v1 = bint.i128 v0
|
v1 = bint.i128 v0
|
||||||
return v1
|
return v1
|
||||||
}
|
}
|
||||||
; run: %bint_b8_i128() == 1
|
; run: %bint_b8_i128_tru() == 1
|
||||||
|
|
||||||
|
function %bint_b8_i128_false() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b8 false
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b8_i128_fal() == 0
|
||||||
|
|
||||||
|
function %bint_b16_i128_true() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 true
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i128_tr() == 1
|
||||||
|
|
||||||
|
function %bint_b16_i128_false() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b16 false
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b16_i128_fa() == 0
|
||||||
|
|
||||||
|
function %bint_b32_i128_true() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 true
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i128_tr() == 1
|
||||||
|
|
||||||
|
function %bint_b32_i128_false() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b32 false
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b32_i128_fa() == 0
|
||||||
|
|
||||||
|
function %bint_b64_i128_true() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 true
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i128_tr() == 1
|
||||||
|
|
||||||
|
function %bint_b64_i128_false() -> i128 {
|
||||||
|
block0:
|
||||||
|
v0 = bconst.b64 false
|
||||||
|
v1 = bint.i128 v0
|
||||||
|
return v1
|
||||||
|
}
|
||||||
|
; run: %bint_b64_i128_fa() == 0
|
||||||
|
|||||||
@@ -716,11 +716,15 @@ where
|
|||||||
| Opcode::ScalarToVector
|
| Opcode::ScalarToVector
|
||||||
| Opcode::Breduce
|
| Opcode::Breduce
|
||||||
| Opcode::Bextend
|
| Opcode::Bextend
|
||||||
| Opcode::Bint
|
|
||||||
| Opcode::Ireduce => assign(Value::convert(
|
| Opcode::Ireduce => assign(Value::convert(
|
||||||
arg(0)?,
|
arg(0)?,
|
||||||
ValueConversionKind::Exact(ctrl_ty),
|
ValueConversionKind::Exact(ctrl_ty),
|
||||||
)?),
|
)?),
|
||||||
|
Opcode::Bint => {
|
||||||
|
let bool = arg(0)?.into_bool()?;
|
||||||
|
let int = if bool { 1 } else { 0 };
|
||||||
|
assign(Value::int(int, ctrl_ty)?)
|
||||||
|
}
|
||||||
Opcode::Snarrow | Opcode::Unarrow | Opcode::Uunarrow => {
|
Opcode::Snarrow | Opcode::Unarrow | Opcode::Uunarrow => {
|
||||||
let arg0 = extractlanes(&arg(0)?, ctrl_ty.lane_type())?;
|
let arg0 = extractlanes(&arg(0)?, ctrl_ty.lane_type())?;
|
||||||
let arg1 = extractlanes(&arg(1)?, ctrl_ty.lane_type())?;
|
let arg1 = extractlanes(&arg(1)?, ctrl_ty.lane_type())?;
|
||||||
|
|||||||
Reference in New Issue
Block a user