diff options
author | Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk> | 2019-06-16 13:37:42 +0100 |
---|---|---|
committer | David Gibson <david@gibson.dropbear.id.au> | 2019-07-02 09:43:58 +1000 |
commit | e0d6a362be2172177f34eb0d9c8cb5118ee6607d (patch) | |
tree | 7229c1fe84421ea38915276b0193c0f8be4062e7 | |
parent | 99125c7499d1f7479e48340f622647e02f73da0f (diff) |
target/ppc: introduce separate generator and helper for xscvqpdp
Rather than perform the VSR register decoding within the helper itself,
introduce a new generator and helper function which perform the decode based
upon xT and xB at translation time.
The xscvqpdp helper is the only 2 parameter xT/xB implementation that requires
the opcode to be passed as an additional parameter, so handling this separately
allows us to optimise the conversion in the next commit.
Signed-off-by: Mark Cave-Ayland <mark.cave-ayland@ilande.co.uk>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Message-Id: <20190616123751.781-7-mark.cave-ayland@ilande.co.uk>
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
-rw-r--r-- | target/ppc/fpu_helper.c | 5 | ||||
-rw-r--r-- | target/ppc/helper.h | 2 | ||||
-rw-r--r-- | target/ppc/translate/vsx-impl.inc.c | 18 |
3 files changed, 20 insertions, 5 deletions
diff --git a/target/ppc/fpu_helper.c b/target/ppc/fpu_helper.c index 012dfdac3e..230ee2f072 100644 --- a/target/ppc/fpu_helper.c +++ b/target/ppc/fpu_helper.c @@ -2899,10 +2899,9 @@ VSX_CVT_FP_TO_FP_HP(xvcvhpsp, 4, float16, float32, VsrH(2 * i + 1), VsrW(i), 0) * xscvqpdp isn't using VSX_CVT_FP_TO_FP() because xscvqpdpo will be * added to this later. */ -void helper_xscvqpdp(CPUPPCState *env, uint32_t opcode) +void helper_xscvqpdp(CPUPPCState *env, uint32_t opcode, + ppc_vsr_t *xt, ppc_vsr_t *xb) { - ppc_vsr_t *xt = &env->vsr[xT(opcode)]; - ppc_vsr_t *xb = &env->vsr[xB(opcode)]; ppc_vsr_t t = { }; float_status tstat; diff --git a/target/ppc/helper.h b/target/ppc/helper.h index f6a97cedc6..5d15166988 100644 --- a/target/ppc/helper.h +++ b/target/ppc/helper.h @@ -405,7 +405,7 @@ DEF_HELPER_2(xscvdphp, void, env, i32) DEF_HELPER_2(xscvdpqp, void, env, i32) DEF_HELPER_2(xscvdpsp, void, env, i32) DEF_HELPER_2(xscvdpspn, i64, env, i64) -DEF_HELPER_2(xscvqpdp, void, env, i32) +DEF_HELPER_4(xscvqpdp, void, env, i32, vsr, vsr) DEF_HELPER_2(xscvqpsdz, void, env, i32) DEF_HELPER_2(xscvqpswz, void, env, i32) DEF_HELPER_2(xscvqpudz, void, env, i32) diff --git a/target/ppc/translate/vsx-impl.inc.c b/target/ppc/translate/vsx-impl.inc.c index b24be00ccf..ffbe3b0fac 100644 --- a/target/ppc/translate/vsx-impl.inc.c +++ b/target/ppc/translate/vsx-impl.inc.c @@ -999,6 +999,23 @@ VSX_CMP(xvcmpgesp, 0x0C, 0x0A, 0, PPC2_VSX) VSX_CMP(xvcmpgtsp, 0x0C, 0x09, 0, PPC2_VSX) VSX_CMP(xvcmpnesp, 0x0C, 0x0B, 0, PPC2_VSX) +static void gen_xscvqpdp(DisasContext *ctx) +{ + TCGv_i32 opc; + TCGv_ptr xt, xb; + if (unlikely(!ctx->vsx_enabled)) { + gen_exception(ctx, POWERPC_EXCP_VSXU); + return; + } + opc = tcg_const_i32(ctx->opcode); + xt = gen_vsr_ptr(xT(ctx->opcode)); + xb = gen_vsr_ptr(xB(ctx->opcode)); + gen_helper_xscvqpdp(cpu_env, opc, xt, xb); + tcg_temp_free_i32(opc); + tcg_temp_free_ptr(xt); + tcg_temp_free_ptr(xb); +} + #define GEN_VSX_HELPER_2(name, op1, op2, inval, type) \ static void gen_##name(DisasContext *ctx) \ { \ @@ -1087,7 +1104,6 @@ GEN_VSX_HELPER_2(xscvdphp, 0x16, 0x15, 0x11, PPC2_ISA300) GEN_VSX_HELPER_2(xscvdpsp, 0x12, 0x10, 0, PPC2_VSX) GEN_VSX_HELPER_2(xscvdpqp, 0x04, 0x1A, 0x16, PPC2_ISA300) GEN_VSX_HELPER_XT_XB_ENV(xscvdpspn, 0x16, 0x10, 0, PPC2_VSX207) -GEN_VSX_HELPER_2(xscvqpdp, 0x04, 0x1A, 0x14, PPC2_ISA300) GEN_VSX_HELPER_2(xscvqpsdz, 0x04, 0x1A, 0x19, PPC2_ISA300) GEN_VSX_HELPER_2(xscvqpswz, 0x04, 0x1A, 0x09, PPC2_ISA300) GEN_VSX_HELPER_2(xscvqpudz, 0x04, 0x1A, 0x11, PPC2_ISA300) |