Skip to content

Commit

Permalink
target/ppc: Moved XSTSTDC[QDS]P to decodetree
Browse files Browse the repository at this point in the history
Moved XSTSTDCSP, XSTSTDCDP and XSTSTDCQP to decodetree and moved some of
its decoding away from the helper as previously the DCMX, XB and BF were
calculated in the helper with the help of cpu_env, now that part was
moved to the decodetree with the rest.

xvtstdcsp:
rept    loop    master             patch
8       12500   1,85393600         1,94683600 (+5.0%)
25      4000    1,78779800         1,92479000 (+7.7%)
100     1000    2,12775000         2,28895500 (+7.6%)
500     200     2,99655300         3,23102900 (+7.8%)
2500    40      6,89082200         7,44827500 (+8.1%)
8000    12     17,50585500        18,95152100 (+8.3%)

xvtstdcdp:
rept    loop    master             patch
8       12500   1,39043100         1,33539800 (-4.0%)
25      4000    1,35731800         1,37347800 (+1.2%)
100     1000    1,51514800         1,56053000 (+3.0%)
500     200     2,21014400         2,47906000 (+12.2%)
2500    40      5,39488200         6,68766700 (+24.0%)
8000    12     13,98623900        18,17661900 (+30.0%)

xvtstdcdp:
rept    loop    master             patch
8       12500   1,35123800         1,34455800 (-0.5%)
25      4000    1,36441200         1,36759600 (+0.2%)
100     1000    1,49763500         1,54138400 (+2.9%)
500     200     2,19020200         2,46196400 (+12.4%)
2500    40      5,39265700         6,68147900 (+23.9%)
8000    12     14,04163600        18,19669600 (+29.6%)

As some values are now decoded outside the helper and passed to it as an
argument the number of arguments of the helper increased, the number
of TCGop needed to load the arguments increased. I suspect that's why
the slow-down in the tests with a high REPT but low LOOP.

Signed-off-by: Lucas Mateus Castro (alqotel) <lucas.araujo@eldorado.org.br>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Message-Id: <20221019125040.48028-12-lucas.araujo@eldorado.org.br>
Signed-off-by: Daniel Henrique Barboza <danielhb413@gmail.com>
  • Loading branch information
Lucas Mateus Castro (alqotel) authored and danielhb committed Oct 28, 2022
1 parent a70a524 commit da3c53b
Show file tree
Hide file tree
Showing 5 changed files with 60 additions and 90 deletions.
114 changes: 34 additions & 80 deletions target/ppc/fpu_helper.c
Expand Up @@ -3241,63 +3241,6 @@ void helper_XVXSIGSP(ppc_vsr_t *xt, ppc_vsr_t *xb)
*xt = t;
}

/*
* VSX_TEST_DC - VSX floating point test data class
* op - instruction mnemonic
* nels - number of elements (1, 2 or 4)
* xbn - VSR register number
* tp - type (float32 or float64)
* fld - vsr_t field (VsrD(*) or VsrW(*))
* tfld - target vsr_t field (VsrD(*) or VsrW(*))
* fld_max - target field max
* scrf - set result in CR and FPCC
*/
#define VSX_TEST_DC(op, nels, xbn, tp, fld, tfld, fld_max, scrf) \
void helper_##op(CPUPPCState *env, uint32_t opcode) \
{ \
ppc_vsr_t *xt = &env->vsr[xT(opcode)]; \
ppc_vsr_t *xb = &env->vsr[xbn]; \
ppc_vsr_t t = { }; \
uint32_t i, sign, dcmx; \
uint32_t cc, match = 0; \
\
if (!scrf) { \
dcmx = DCMX_XV(opcode); \
} else { \
t = *xt; \
dcmx = DCMX(opcode); \
} \
\
for (i = 0; i < nels; i++) { \
sign = tp##_is_neg(xb->fld); \
if (tp##_is_any_nan(xb->fld)) { \
match = extract32(dcmx, 6, 1); \
} else if (tp##_is_infinity(xb->fld)) { \
match = extract32(dcmx, 4 + !sign, 1); \
} else if (tp##_is_zero(xb->fld)) { \
match = extract32(dcmx, 2 + !sign, 1); \
} else if (tp##_is_zero_or_denormal(xb->fld)) { \
match = extract32(dcmx, 0 + !sign, 1); \
} \
\
if (scrf) { \
cc = sign << CRF_LT_BIT | match << CRF_EQ_BIT; \
env->fpscr &= ~FP_FPCC; \
env->fpscr |= cc << FPSCR_FPCC; \
env->crf[BF(opcode)] = cc; \
} else { \
t.tfld = match ? fld_max : 0; \
} \
match = 0; \
} \
if (!scrf) { \
*xt = t; \
} \
}

VSX_TEST_DC(xststdcdp, 1, xB(opcode), float64, VsrD(0), VsrD(0), 0, 1)
VSX_TEST_DC(xststdcqp, 1, (rB(opcode) + 32), float128, f128, VsrD(0), 0, 1)

#define VSX_TSTDC(tp) \
static int32_t tp##_tstdc(tp b, uint32_t dcmx) \
{ \
Expand All @@ -3317,6 +3260,7 @@ static int32_t tp##_tstdc(tp b, uint32_t dcmx) \

VSX_TSTDC(float32)
VSX_TSTDC(float64)
VSX_TSTDC(float128)
#undef VSX_TSTDC

void helper_XVTSTDCDP(ppc_vsr_t *t, ppc_vsr_t *b, uint64_t dcmx, uint32_t v)
Expand All @@ -3335,34 +3279,44 @@ void helper_XVTSTDCSP(ppc_vsr_t *t, ppc_vsr_t *b, uint64_t dcmx, uint32_t v)
}
}

void helper_xststdcsp(CPUPPCState *env, uint32_t opcode, ppc_vsr_t *xb)
static bool not_SP_value(float64 val)
{
uint32_t dcmx, sign, exp;
uint32_t cc, match = 0, not_sp = 0;
float64 arg = xb->VsrD(0);
float64 arg_sp;

dcmx = DCMX(opcode);
exp = (arg >> 52) & 0x7FF;
sign = float64_is_neg(arg);

if (float64_is_any_nan(arg)) {
match = extract32(dcmx, 6, 1);
} else if (float64_is_infinity(arg)) {
match = extract32(dcmx, 4 + !sign, 1);
} else if (float64_is_zero(arg)) {
match = extract32(dcmx, 2 + !sign, 1);
} else if (float64_is_zero_or_denormal(arg) || (exp > 0 && exp < 0x381)) {
match = extract32(dcmx, 0 + !sign, 1);
}

arg_sp = helper_todouble(helper_tosingle(arg));
not_sp = arg != arg_sp;
return val != helper_todouble(helper_tosingle(val));
}

/*
* VSX_XS_TSTDC - VSX Scalar Test Data Class
* NAME - instruction name
* FLD - vsr_t field (VsrD(0) or f128)
* TP - type (float64 or float128)
*/
#define VSX_XS_TSTDC(NAME, FLD, TP) \
void helper_##NAME(CPUPPCState *env, uint32_t bf, \
uint32_t dcmx, ppc_vsr_t *b) \
{ \
uint32_t cc, match, sign = TP##_is_neg(b->FLD); \
match = TP##_tstdc(b->FLD, dcmx); \
cc = sign << CRF_LT_BIT | match << CRF_EQ_BIT; \
env->fpscr &= ~FP_FPCC; \
env->fpscr |= cc << FPSCR_FPCC; \
env->crf[bf] = cc; \
}

VSX_XS_TSTDC(XSTSTDCDP, VsrD(0), float64)
VSX_XS_TSTDC(XSTSTDCQP, f128, float128)
#undef VSX_XS_TSTDC

void helper_XSTSTDCSP(CPUPPCState *env, uint32_t bf,
uint32_t dcmx, ppc_vsr_t *b)
{
uint32_t cc, match, sign = float64_is_neg(b->VsrD(0));
uint32_t exp = (b->VsrD(0) >> 52) & 0x7FF;
int not_sp = (int)not_SP_value(b->VsrD(0));
match = float64_tstdc(b->VsrD(0), dcmx) || (exp > 0 && exp < 0x381);
cc = sign << CRF_LT_BIT | match << CRF_EQ_BIT | not_sp << CRF_SO_BIT;
env->fpscr &= ~FP_FPCC;
env->fpscr |= cc << FPSCR_FPCC;
env->crf[BF(opcode)] = cc;
env->crf[bf] = cc;
}

void helper_xsrqpi(CPUPPCState *env, uint32_t opcode,
Expand Down
6 changes: 3 additions & 3 deletions target/ppc/helper.h
Expand Up @@ -417,9 +417,9 @@ DEF_HELPER_3(xscvuxdsp, void, env, vsr, vsr)
DEF_HELPER_3(xscvsxdsp, void, env, vsr, vsr)
DEF_HELPER_4(xscvudqp, void, env, i32, vsr, vsr)
DEF_HELPER_3(xscvuxddp, void, env, vsr, vsr)
DEF_HELPER_3(xststdcsp, void, env, i32, vsr)
DEF_HELPER_2(xststdcdp, void, env, i32)
DEF_HELPER_2(xststdcqp, void, env, i32)
DEF_HELPER_4(XSTSTDCSP, void, env, i32, i32, vsr)
DEF_HELPER_4(XSTSTDCDP, void, env, i32, i32, vsr)
DEF_HELPER_4(XSTSTDCQP, void, env, i32, i32, vsr)
DEF_HELPER_3(xsrdpi, void, env, vsr, vsr)
DEF_HELPER_3(xsrdpic, void, env, vsr, vsr)
DEF_HELPER_3(xsrdpim, void, env, vsr, vsr)
Expand Down
6 changes: 6 additions & 0 deletions target/ppc/insn32.decode
Expand Up @@ -202,6 +202,9 @@
%xx_uim7 6:1 2:1 16:5
@XX2_uim7 ...... ..... ..... ..... .... . ... . .. &XX2_uim xt=%xx_xt xb=%xx_xb uim=%xx_uim7

&XX2_bf_uim bf xb uim
@XX2_bf_uim ...... bf:3 uim:7 ..... ......... . . &XX2_bf_uim

&XX2_bf_xb bf xb
@XX2_bf_xb ...... bf:3 .. ..... ..... ......... . . &XX2_bf_xb xb=%xx_xb

Expand Down Expand Up @@ -853,6 +856,9 @@ XSCVSPDPN 111100 ..... ----- ..... 101001011 .. @XX2
XVXSIGSP 111100 ..... 01001 ..... 111011011 .. @XX2
XVTSTDCDP 111100 ..... ..... ..... 1111 . 101 ... @XX2_uim7
XVTSTDCSP 111100 ..... ..... ..... 1101 . 101 ... @XX2_uim7
XSTSTDCSP 111100 ... ....... ..... 100101010 . - @XX2_bf_uim xb=%xx_xb
XSTSTDCDP 111100 ... ....... ..... 101101010 . - @XX2_bf_uim xb=%xx_xb
XSTSTDCQP 111111 ... ....... xb:5 1011000100 - @XX2_bf_uim

## VSX Vector Test Least-Significant Bit by Byte Instruction

Expand Down
20 changes: 17 additions & 3 deletions target/ppc/translate/vsx-impl.c.inc
Expand Up @@ -1136,6 +1136,23 @@ static bool do_xvtstdc(DisasContext *ctx, arg_XX2_uim *a, unsigned vece)
TRANS_FLAGS2(VSX, XVTSTDCSP, do_xvtstdc, MO_32)
TRANS_FLAGS2(VSX, XVTSTDCDP, do_xvtstdc, MO_64)

static bool do_XX2_bf_uim(DisasContext *ctx, arg_XX2_bf_uim *a, bool vsr,
void (*gen_helper)(TCGv_env, TCGv_i32, TCGv_i32, TCGv_ptr))
{
TCGv_ptr xb;

REQUIRE_VSX(ctx);
xb = vsr ? gen_vsr_ptr(a->xb) : gen_avr_ptr(a->xb);
gen_helper(cpu_env, tcg_constant_i32(a->bf), tcg_constant_i32(a->uim), xb);
tcg_temp_free_ptr(xb);

return true;
}

TRANS_FLAGS2(ISA300, XSTSTDCSP, do_XX2_bf_uim, true, gen_helper_XSTSTDCSP)
TRANS_FLAGS2(ISA300, XSTSTDCDP, do_XX2_bf_uim, true, gen_helper_XSTSTDCDP)
TRANS_FLAGS2(ISA300, XSTSTDCQP, do_XX2_bf_uim, false, gen_helper_XSTSTDCQP)

bool trans_XSCVSPDPN(DisasContext *ctx, arg_XX2 *a)
{
TCGv_i64 tmp;
Expand Down Expand Up @@ -1182,9 +1199,6 @@ GEN_VSX_HELPER_X2(xssqrtsp, 0x16, 0x00, 0, PPC2_VSX207)
GEN_VSX_HELPER_X2(xsrsqrtesp, 0x14, 0x00, 0, PPC2_VSX207)
GEN_VSX_HELPER_X2(xscvsxdsp, 0x10, 0x13, 0, PPC2_VSX207)
GEN_VSX_HELPER_X2(xscvuxdsp, 0x10, 0x12, 0, PPC2_VSX207)
GEN_VSX_HELPER_X1(xststdcsp, 0x14, 0x12, 0, PPC2_ISA300)
GEN_VSX_HELPER_2(xststdcdp, 0x14, 0x16, 0, PPC2_ISA300)
GEN_VSX_HELPER_2(xststdcqp, 0x04, 0x16, 0, PPC2_ISA300)

GEN_VSX_HELPER_X3(xvadddp, 0x00, 0x0C, 0, PPC2_VSX)
GEN_VSX_HELPER_X3(xvsubdp, 0x00, 0x0D, 0, PPC2_VSX)
Expand Down
4 changes: 0 additions & 4 deletions target/ppc/translate/vsx-ops.c.inc
Expand Up @@ -147,10 +147,6 @@ GEN_HANDLER_E(xsiexpdp, 0x3C, 0x16, 0x1C, 0, PPC_NONE, PPC2_ISA300),
GEN_VSX_XFORM_300(xsiexpqp, 0x4, 0x1B, 0x00000001),
#endif

GEN_XX2FORM(xststdcdp, 0x14, 0x16, PPC2_ISA300),
GEN_XX2FORM(xststdcsp, 0x14, 0x12, PPC2_ISA300),
GEN_VSX_XFORM_300(xststdcqp, 0x04, 0x16, 0x00000001),

GEN_XX3FORM(xviexpsp, 0x00, 0x1B, PPC2_ISA300),
GEN_XX3FORM(xviexpdp, 0x00, 0x1F, PPC2_ISA300),
GEN_XX2FORM_EO(xvxexpdp, 0x16, 0x1D, 0x00, PPC2_ISA300),
Expand Down

0 comments on commit da3c53b

Please sign in to comment.