Skip to content

Commit 6ab449b

Browse files
committed
riscv64: Implement SIMD fcvt_to_{u,s}int_sat
1 parent 2b0cd0b commit 6ab449b

6 files changed

Lines changed: 129 additions & 23 deletions

File tree

build.rs

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -254,14 +254,7 @@ fn ignore(testsuite: &str, testname: &str, strategy: &str) -> bool {
254254
return true;
255255
}
256256

257-
let known_failure = [
258-
"issue_3327_bnot_lowering",
259-
"simd_i32x4_trunc_sat_f32x4",
260-
"simd_i32x4_trunc_sat_f64x2",
261-
"simd_load",
262-
"simd_splat",
263-
]
264-
.contains(&testname);
257+
let known_failure = ["issue_3327_bnot_lowering"].contains(&testname);
265258

266259
known_failure
267260
}

cranelift/codegen/src/isa/riscv64/lower.isle

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1629,20 +1629,29 @@
16291629
(gen_fcvt_int $false v $false from to))
16301630

16311631
;;;;; Rules for `fcvt_to_sint`;;;;;;;;;
1632-
(rule
1633-
(lower (has_type to (fcvt_to_sint v @ (value_type from))))
1632+
(rule 0 (lower (has_type to (fcvt_to_sint v @ (value_type (ty_scalar_float from)))))
16341633
(gen_fcvt_int $false v $true from to))
16351634

16361635
;;;;; Rules for `fcvt_to_sint_sat`;;;;;;;;;
1637-
(rule
1638-
(lower (has_type to (fcvt_to_sint_sat v @ (value_type from))))
1636+
(rule 0 (lower (has_type to (fcvt_to_sint_sat v @ (value_type (ty_scalar_float from)))))
16391637
(gen_fcvt_int $true v $true from to))
16401638

1639+
(rule 1 (lower (has_type (ty_vec_fits_in_register _) (fcvt_to_sint_sat v @ (value_type from_ty))))
1640+
(if-let (imm5_from_u64 zero) (u64_add 0 0))
1641+
(let ((is_nan VReg (rv_vmfne_vv v v (unmasked) from_ty))
1642+
(cvt VReg (rv_vfcvt_rtz_x_f_v v (unmasked) from_ty)))
1643+
(rv_vmerge_vim cvt zero is_nan from_ty)))
1644+
16411645
;;;;; Rules for `fcvt_to_uint_sat`;;;;;;;;;
1642-
(rule
1643-
(lower (has_type to (fcvt_to_uint_sat v @ (value_type from))))
1646+
(rule 0 (lower (has_type to (fcvt_to_uint_sat v @ (value_type (ty_scalar_float from)))))
16441647
(gen_fcvt_int $true v $false from to))
16451648

1649+
(rule 1 (lower (has_type (ty_vec_fits_in_register _) (fcvt_to_uint_sat v @ (value_type from_ty))))
1650+
(if-let (imm5_from_u64 zero) (u64_add 0 0))
1651+
(let ((is_nan VReg (rv_vmfne_vv v v (unmasked) from_ty))
1652+
(cvt VReg (rv_vfcvt_rtz_xu_f_v v (unmasked) from_ty)))
1653+
(rv_vmerge_vim cvt zero is_nan from_ty)))
1654+
16461655
;;;;; Rules for `fcvt_from_sint`;;;;;;;;;
16471656
(rule 0 (lower (has_type (ty_scalar_float to) (fcvt_from_sint v @ (value_type from_ty))))
16481657
(let ((float_op FpuOPRR (int_convert_2_float_op from_ty $true to))
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
test compile precise-output
2+
set unwind_info=false
3+
target riscv64 has_v
4+
5+
function %fcvt_to_sint_sat(f32x4) -> i32x4 {
6+
block0(v0:f32x4):
7+
v1 = fcvt_to_sint_sat.i32x4 v0
8+
return v1
9+
}
10+
11+
; VCode:
12+
; add sp,-16
13+
; sd ra,8(sp)
14+
; sd fp,0(sp)
15+
; mv fp,sp
16+
; block0:
17+
; vle8.v v1,16(fp) #avl=16, #vtype=(e8, m1, ta, ma)
18+
; vmfne.vv v0,v1,v1 #avl=4, #vtype=(e32, m1, ta, ma)
19+
; vfcvt.rtz.x.f.v v6,v1 #avl=4, #vtype=(e32, m1, ta, ma)
20+
; vmerge.vim v8,v6,0,v0.t #avl=4, #vtype=(e32, m1, ta, ma)
21+
; vse8.v v8,0(a0) #avl=16, #vtype=(e8, m1, ta, ma)
22+
; ld ra,8(sp)
23+
; ld fp,0(sp)
24+
; add sp,+16
25+
; ret
26+
;
27+
; Disassembled:
28+
; block0: ; offset 0x0
29+
; addi sp, sp, -0x10
30+
; sd ra, 8(sp)
31+
; sd s0, 0(sp)
32+
; ori s0, sp, 0
33+
; block1: ; offset 0x10
34+
; .byte 0x57, 0x70, 0x08, 0xcc
35+
; addi t6, s0, 0x10
36+
; .byte 0x87, 0x80, 0x0f, 0x02
37+
; .byte 0x57, 0x70, 0x02, 0xcd
38+
; .byte 0x57, 0x90, 0x10, 0x72
39+
; .byte 0x57, 0x93, 0x13, 0x4a
40+
; .byte 0x57, 0x34, 0x60, 0x5c
41+
; .byte 0x57, 0x70, 0x08, 0xcc
42+
; .byte 0x27, 0x04, 0x05, 0x02
43+
; ld ra, 8(sp)
44+
; ld s0, 0(sp)
45+
; addi sp, sp, 0x10
46+
; ret
47+
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
test compile precise-output
2+
set unwind_info=false
3+
target riscv64 has_v
4+
5+
function %fcvt_to_uint_sat(f32x4) -> i32x4 {
6+
block0(v0:f32x4):
7+
v1 = fcvt_to_uint_sat.i32x4 v0
8+
return v1
9+
}
10+
11+
; VCode:
12+
; add sp,-16
13+
; sd ra,8(sp)
14+
; sd fp,0(sp)
15+
; mv fp,sp
16+
; block0:
17+
; vle8.v v1,16(fp) #avl=16, #vtype=(e8, m1, ta, ma)
18+
; vmfne.vv v0,v1,v1 #avl=4, #vtype=(e32, m1, ta, ma)
19+
; vfcvt.rtz.xu.f.v v6,v1 #avl=4, #vtype=(e32, m1, ta, ma)
20+
; vmerge.vim v8,v6,0,v0.t #avl=4, #vtype=(e32, m1, ta, ma)
21+
; vse8.v v8,0(a0) #avl=16, #vtype=(e8, m1, ta, ma)
22+
; ld ra,8(sp)
23+
; ld fp,0(sp)
24+
; add sp,+16
25+
; ret
26+
;
27+
; Disassembled:
28+
; block0: ; offset 0x0
29+
; addi sp, sp, -0x10
30+
; sd ra, 8(sp)
31+
; sd s0, 0(sp)
32+
; ori s0, sp, 0
33+
; block1: ; offset 0x10
34+
; .byte 0x57, 0x70, 0x08, 0xcc
35+
; addi t6, s0, 0x10
36+
; .byte 0x87, 0x80, 0x0f, 0x02
37+
; .byte 0x57, 0x70, 0x02, 0xcd
38+
; .byte 0x57, 0x90, 0x10, 0x72
39+
; .byte 0x57, 0x13, 0x13, 0x4a
40+
; .byte 0x57, 0x34, 0x60, 0x5c
41+
; .byte 0x57, 0x70, 0x08, 0xcc
42+
; .byte 0x27, 0x04, 0x05, 0x02
43+
; ld ra, 8(sp)
44+
; ld s0, 0(sp)
45+
; addi sp, sp, 0x10
46+
; ret
47+
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
test interpret
2+
test run
3+
target aarch64
4+
target s390x
5+
target x86_64
6+
target x86_64 sse41
7+
target x86_64 sse42
8+
target x86_64 sse42 has_avx
9+
target riscv64 has_v
10+
11+
function %fcvt_to_sint_sat(f32x4) -> i32x4 {
12+
block0(v0:f32x4):
13+
v1 = fcvt_to_sint_sat.i32x4 v0
14+
return v1
15+
}
16+
; run: %fcvt_to_sint_sat([0x0.0 -0x1.0 0x1.0 0x1.0p100]) == [0 -1 1 0x7FFFFFFF]
17+
; run: %fcvt_to_sint_sat([-0x8.1 0x0.0 0x0.0 -0x1.0p100]) == [-8 0 0 0x80000000]
18+
; run: %fcvt_to_sint_sat([+NaN +NaN +NaN +NaN]) == [0 0 0 0]

cranelift/filetests/filetests/runtests/simd-conversion.clif renamed to cranelift/filetests/filetests/runtests/simd-fcvt-to-uint-sat.clif

Lines changed: 1 addition & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,15 +6,7 @@ target x86_64
66
target x86_64 sse41
77
target x86_64 sse42
88
target x86_64 sse42 has_avx
9-
10-
function %fcvt_to_sint_sat(f32x4) -> i32x4 {
11-
block0(v0:f32x4):
12-
v1 = fcvt_to_sint_sat.i32x4 v0
13-
return v1
14-
}
15-
; run: %fcvt_to_sint_sat([0x0.0 -0x1.0 0x1.0 0x1.0p100]) == [0 -1 1 0x7FFFFFFF]
16-
; run: %fcvt_to_sint_sat([-0x8.1 0x0.0 0x0.0 -0x1.0p100]) == [-8 0 0 0x80000000]
17-
; run: %fcvt_to_sint_sat([+NaN +NaN +NaN +NaN]) == [0 0 0 0]
9+
target riscv64 has_v
1810

1911
function %fcvt_to_uint_sat(f32x4) -> i32x4 {
2012
block0(v0:f32x4):

0 commit comments

Comments
 (0)