target/arm: Implement FPCR.AH semantics for SVE FMIN/FMAX immediate

Implement the FPCR.AH semantics for the SVE FMAX and FMIN operations
that take an immediate as the second operand.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
This commit is contained in:
Peter Maydell 2025-02-01 16:39:32 +00:00
parent dac3a42f39
commit bf92725bb2
3 changed files with 45 additions and 2 deletions

View File

@ -1231,6 +1231,20 @@ DEF_HELPER_FLAGS_6(sve_fmins_s, TCG_CALL_NO_RWG,
DEF_HELPER_FLAGS_6(sve_fmins_d, TCG_CALL_NO_RWG, DEF_HELPER_FLAGS_6(sve_fmins_d, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32) void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_6(sve_ah_fmaxs_h, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_6(sve_ah_fmaxs_s, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_6(sve_ah_fmaxs_d, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_6(sve_ah_fmins_h, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_6(sve_ah_fmins_s, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_6(sve_ah_fmins_d, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, i64, fpst, i32)
DEF_HELPER_FLAGS_5(sve_fcvt_sh, TCG_CALL_NO_RWG, DEF_HELPER_FLAGS_5(sve_fcvt_sh, TCG_CALL_NO_RWG,
void, ptr, ptr, ptr, fpst, i32) void, ptr, ptr, ptr, fpst, i32)
DEF_HELPER_FLAGS_5(sve_fcvt_dh, TCG_CALL_NO_RWG, DEF_HELPER_FLAGS_5(sve_fcvt_dh, TCG_CALL_NO_RWG,

View File

@ -4459,6 +4459,14 @@ DO_ZPZS_FP(sve_fmins_h, float16, H1_2, float16_min)
DO_ZPZS_FP(sve_fmins_s, float32, H1_4, float32_min) DO_ZPZS_FP(sve_fmins_s, float32, H1_4, float32_min)
DO_ZPZS_FP(sve_fmins_d, float64, H1_8, float64_min) DO_ZPZS_FP(sve_fmins_d, float64, H1_8, float64_min)
DO_ZPZS_FP(sve_ah_fmaxs_h, float16, H1_2, helper_vfp_ah_maxh)
DO_ZPZS_FP(sve_ah_fmaxs_s, float32, H1_4, helper_vfp_ah_maxs)
DO_ZPZS_FP(sve_ah_fmaxs_d, float64, H1_8, helper_vfp_ah_maxd)
DO_ZPZS_FP(sve_ah_fmins_h, float16, H1_2, helper_vfp_ah_minh)
DO_ZPZS_FP(sve_ah_fmins_s, float32, H1_4, helper_vfp_ah_mins)
DO_ZPZS_FP(sve_ah_fmins_d, float64, H1_8, helper_vfp_ah_mind)
/* Fully general two-operand expander, controlled by a predicate, /* Fully general two-operand expander, controlled by a predicate,
* With the extra float_status parameter. * With the extra float_status parameter.
*/ */

View File

@ -3821,14 +3821,35 @@ static bool do_fp_imm(DisasContext *s, arg_rpri_esz *a, uint64_t imm,
TRANS_FEAT(NAME##_zpzi, aa64_sve, do_fp_imm, a, \ TRANS_FEAT(NAME##_zpzi, aa64_sve, do_fp_imm, a, \
name##_const[a->esz][a->imm], name##_fns[a->esz]) name##_const[a->esz][a->imm], name##_fns[a->esz])
#define DO_FP_AH_IMM(NAME, name, const0, const1) \
static gen_helper_sve_fp2scalar * const name##_fns[4] = { \
NULL, gen_helper_sve_##name##_h, \
gen_helper_sve_##name##_s, \
gen_helper_sve_##name##_d \
}; \
static gen_helper_sve_fp2scalar * const name##_ah_fns[4] = { \
NULL, gen_helper_sve_ah_##name##_h, \
gen_helper_sve_ah_##name##_s, \
gen_helper_sve_ah_##name##_d \
}; \
static uint64_t const name##_const[4][2] = { \
{ -1, -1 }, \
{ float16_##const0, float16_##const1 }, \
{ float32_##const0, float32_##const1 }, \
{ float64_##const0, float64_##const1 }, \
}; \
TRANS_FEAT(NAME##_zpzi, aa64_sve, do_fp_imm, a, \
name##_const[a->esz][a->imm], \
s->fpcr_ah ? name##_ah_fns[a->esz] : name##_fns[a->esz])
DO_FP_IMM(FADD, fadds, half, one) DO_FP_IMM(FADD, fadds, half, one)
DO_FP_IMM(FSUB, fsubs, half, one) DO_FP_IMM(FSUB, fsubs, half, one)
DO_FP_IMM(FMUL, fmuls, half, two) DO_FP_IMM(FMUL, fmuls, half, two)
DO_FP_IMM(FSUBR, fsubrs, half, one) DO_FP_IMM(FSUBR, fsubrs, half, one)
DO_FP_IMM(FMAXNM, fmaxnms, zero, one) DO_FP_IMM(FMAXNM, fmaxnms, zero, one)
DO_FP_IMM(FMINNM, fminnms, zero, one) DO_FP_IMM(FMINNM, fminnms, zero, one)
DO_FP_IMM(FMAX, fmaxs, zero, one) DO_FP_AH_IMM(FMAX, fmaxs, zero, one)
DO_FP_IMM(FMIN, fmins, zero, one) DO_FP_AH_IMM(FMIN, fmins, zero, one)
#undef DO_FP_IMM #undef DO_FP_IMM