@@ -2256,3 +2256,7 @@ DEF_HELPER_FLAGS_5(sve2_fcvtlt_hs, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, ptr, i32)
DEF_HELPER_FLAGS_5(sve2_fcvtlt_sd, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, ptr, i32)
+
+DEF_HELPER_FLAGS_4(flogb_h, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+DEF_HELPER_FLAGS_4(flogb_s, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
+DEF_HELPER_FLAGS_4(flogb_d, TCG_CALL_NO_RWG, void, ptr, ptr, ptr, i32)
@@ -1581,3 +1581,6 @@ FCVTNT_sh 01100100 10 0010 00 101 ... ..... ..... @rd_pg_rn_e0
FCVTLT_hs 01100100 10 0010 01 101 ... ..... ..... @rd_pg_rn_e0
FCVTNT_ds 01100100 11 0010 10 101 ... ..... ..... @rd_pg_rn_e0
FCVTLT_sd 01100100 11 0010 11 101 ... ..... ..... @rd_pg_rn_e0
+
+### SVE2 floating-point convert to integer
+FLOGB 01100101 00 011 esz:2 0101 pg:3 rn:5 rd:5 &rpr_esz
@@ -1121,6 +1121,55 @@ DO_ZPZ_D(sve2_sqneg_d, uint64_t, DO_SQNEG)
DO_ZPZ(sve2_urecpe_s, uint32_t, H1_4, helper_recpe_u32)
DO_ZPZ(sve2_ursqrte_s, uint32_t, H1_4, helper_rsqrte_u32)
+static int16_t do_float16_logb_as_int(float16 a)
+{
+ if (float16_is_normal(a)) {
+ return extract16(a, 10, 5) - 15;
+ } else if (float16_is_infinity(a)) {
+ return INT16_MAX;
+ } else if (float16_is_any_nan(a) || float16_is_zero(a)) {
+ return INT16_MIN;
+ } else {
+ /* denormal */
+ int shift = 6 - clz32(extract16(a, 0, 10)) - 16;
+ return -15 - shift + 1;
+ }
+}
+
+static int32_t do_float32_logb_as_int(float32 a)
+{
+ if (float32_is_normal(a)) {
+ return extract32(a, 23, 8) - 127;
+ } else if (float32_is_infinity(a)) {
+ return INT32_MAX;
+ } else if (float32_is_any_nan(a) || float32_is_zero(a)) {
+ return INT32_MIN;
+ } else {
+ /* denormal */
+ int shift = 9 - clz32(extract32(a, 0, 23));
+ return -127 - shift + 1;
+ }
+}
+
+static int64_t do_float64_logb_as_int(float64 a)
+{
+ if (float64_is_normal(a)) {
+ return extract64(a, 52, 11) - 1023;
+ } else if (float64_is_infinity(a)) {
+ return INT64_MAX;
+ } else if (float64_is_any_nan(a) || float64_is_zero(a)) {
+ return INT64_MIN;
+ } else {
+ /* denormal */
+ int shift = 12 - clz64(extract64(a, 0, 52));
+ return -1023 - shift + 1;
+ }
+}
+
+DO_ZPZ(flogb_h, float16, H1_2, do_float16_logb_as_int)
+DO_ZPZ(flogb_s, float32, H1_4, do_float32_logb_as_int)
+DO_ZPZ(flogb_d, float64, , do_float64_logb_as_int)
+
/* Three-operand expander, unpredicated, in which the third operand is "wide".
*/
#define DO_ZZW(NAME, TYPE, TYPEW, H, OP) \
@@ -7841,3 +7841,12 @@ static bool trans_FCVTXNT_ds(DisasContext *s, arg_rpr_esz *a)
}
return do_frint_mode(s, a, float_round_to_odd, gen_helper_sve2_fcvtnt_ds);
}
+
+static bool trans_FLOGB(DisasContext *s, arg_rpr_esz *a)
+{
+ static gen_helper_gvec_3 * const fns[] = {
+ NULL, gen_helper_flogb_h,
+ gen_helper_flogb_s, gen_helper_flogb_d
+ };
+ return do_sve2_zpz_ool(s, a, fns[a->esz]);
+}