On Sun, Oct 17, 2021 at 3:29 AM Richard Henderson <richard.hender...@linaro.org> wrote: > > The count zeros instructions require a separate implementation > for RV32 when TARGET_LONG_BITS == 64. > > Reviewed-by: LIU Zhiwei <zhiwei_...@c-sky.com> > Signed-off-by: Richard Henderson <richard.hender...@linaro.org>
Reviewed-by: Alistair Francis <alistair.fran...@wdc.com> Alistair > --- > target/riscv/translate.c | 16 ++++++++++++ > target/riscv/insn_trans/trans_rvb.c.inc | 33 ++++++++++++------------- > 2 files changed, 32 insertions(+), 17 deletions(-) > > diff --git a/target/riscv/translate.c b/target/riscv/translate.c > index 8f5f39d143..7286791c0f 100644 > --- a/target/riscv/translate.c > +++ b/target/riscv/translate.c > @@ -511,6 +511,22 @@ static bool gen_unary(DisasContext *ctx, arg_r2 *a, > DisasExtend ext, > return true; > } > > +static bool gen_unary_per_ol(DisasContext *ctx, arg_r2 *a, DisasExtend ext, > + void (*f_tl)(TCGv, TCGv), > + void (*f_32)(TCGv, TCGv)) > +{ > + int olen = get_olen(ctx); > + > + if (olen != TARGET_LONG_BITS) { > + if (olen == 32) { > + f_tl = f_32; > + } else { > + g_assert_not_reached(); > + } > + } > + return gen_unary(ctx, a, ext, f_tl); > +} > + > static uint32_t opcode_at(DisasContextBase *dcbase, target_ulong pc) > { > DisasContext *ctx = container_of(dcbase, DisasContext, base); > diff --git a/target/riscv/insn_trans/trans_rvb.c.inc > b/target/riscv/insn_trans/trans_rvb.c.inc > index c62eea433a..0c2120428d 100644 > --- a/target/riscv/insn_trans/trans_rvb.c.inc > +++ b/target/riscv/insn_trans/trans_rvb.c.inc > @@ -47,10 +47,18 @@ static void gen_clz(TCGv ret, TCGv arg1) > tcg_gen_clzi_tl(ret, arg1, TARGET_LONG_BITS); > } > > +static void gen_clzw(TCGv ret, TCGv arg1) > +{ > + TCGv t = tcg_temp_new(); > + tcg_gen_shli_tl(t, arg1, 32); > + tcg_gen_clzi_tl(ret, t, 32); > + tcg_temp_free(t); > +} > + > static bool trans_clz(DisasContext *ctx, arg_clz *a) > { > REQUIRE_ZBB(ctx); > - return gen_unary(ctx, a, EXT_ZERO, gen_clz); > + return gen_unary_per_ol(ctx, a, EXT_NONE, gen_clz, gen_clzw); > } > > static void gen_ctz(TCGv ret, TCGv arg1) > @@ -58,10 +66,15 @@ static void gen_ctz(TCGv ret, TCGv arg1) > tcg_gen_ctzi_tl(ret, arg1, TARGET_LONG_BITS); > } > > +static void gen_ctzw(TCGv ret, TCGv arg1) > +{ > + tcg_gen_ctzi_tl(ret, arg1, 32); > +} > + > static bool trans_ctz(DisasContext *ctx, arg_ctz *a) > { > REQUIRE_ZBB(ctx); > - return gen_unary(ctx, a, EXT_ZERO, gen_ctz); > + return gen_unary_per_ol(ctx, a, EXT_ZERO, gen_ctz, gen_ctzw); > } > > static bool trans_cpop(DisasContext *ctx, arg_cpop *a) > @@ -314,14 +327,6 @@ static bool trans_zext_h_64(DisasContext *ctx, > arg_zext_h_64 *a) > return gen_unary(ctx, a, EXT_NONE, tcg_gen_ext16u_tl); > } > > -static void gen_clzw(TCGv ret, TCGv arg1) > -{ > - TCGv t = tcg_temp_new(); > - tcg_gen_shli_tl(t, arg1, 32); > - tcg_gen_clzi_tl(ret, t, 32); > - tcg_temp_free(t); > -} > - > static bool trans_clzw(DisasContext *ctx, arg_clzw *a) > { > REQUIRE_64BIT(ctx); > @@ -329,17 +334,11 @@ static bool trans_clzw(DisasContext *ctx, arg_clzw *a) > return gen_unary(ctx, a, EXT_NONE, gen_clzw); > } > > -static void gen_ctzw(TCGv ret, TCGv arg1) > -{ > - tcg_gen_ori_tl(ret, arg1, (target_ulong)MAKE_64BIT_MASK(32, 32)); > - tcg_gen_ctzi_tl(ret, ret, 64); > -} > - > static bool trans_ctzw(DisasContext *ctx, arg_ctzw *a) > { > REQUIRE_64BIT(ctx); > REQUIRE_ZBB(ctx); > - return gen_unary(ctx, a, EXT_NONE, gen_ctzw); > + return gen_unary(ctx, a, EXT_ZERO, gen_ctzw); > } > > static bool trans_cpopw(DisasContext *ctx, arg_cpopw *a) > -- > 2.25.1 > >