On Wed, Oct 1, 2025 at 7:49 PM Djordje Todorovic
<[email protected]> wrote:
>
> Add MIPS P8700 ldp, lwp, sdp, swp instructions.
>
> Signed-off-by: Chao-ying Fu <[email protected]>
> Signed-off-by: Djordje Todorovic <[email protected]>
> Acked-by: Daniel Henrique Barboza <[email protected]>

Acked-by: Alistair Francis <[email protected]>

Alistair

> ---
>  target/riscv/cpu.c                        |  3 +
>  target/riscv/cpu_cfg.h                    |  2 +-
>  target/riscv/cpu_cfg_fields.h.inc         |  1 +
>  target/riscv/insn_trans/trans_xmips.c.inc | 88 +++++++++++++++++++++++
>  target/riscv/xmips.decode                 | 23 ++++++
>  5 files changed, 116 insertions(+), 1 deletion(-)
>
> diff --git a/target/riscv/cpu.c b/target/riscv/cpu.c
> index 87f9eb7ac4..964b995269 100644
> --- a/target/riscv/cpu.c
> +++ b/target/riscv/cpu.c
> @@ -249,6 +249,7 @@ const RISCVIsaExtData isa_edata_arr[] = {
>      ISA_EXT_DATA_ENTRY(svvptc, PRIV_VERSION_1_13_0, ext_svvptc),
>      ISA_EXT_DATA_ENTRY(xmipscbop, PRIV_VERSION_1_12_0, ext_xmipscbop),
>      ISA_EXT_DATA_ENTRY(xmipscmov, PRIV_VERSION_1_12_0, ext_xmipscmov),
> +    ISA_EXT_DATA_ENTRY(xmipslsp, PRIV_VERSION_1_12_0, ext_xmipslsp),
>      ISA_EXT_DATA_ENTRY(xtheadba, PRIV_VERSION_1_11_0, ext_xtheadba),
>      ISA_EXT_DATA_ENTRY(xtheadbb, PRIV_VERSION_1_11_0, ext_xtheadbb),
>      ISA_EXT_DATA_ENTRY(xtheadbs, PRIV_VERSION_1_11_0, ext_xtheadbs),
> @@ -1383,6 +1384,7 @@ const RISCVCPUMultiExtConfig riscv_cpu_vendor_exts[] = {
>      MULTI_EXT_CFG_BOOL("xventanacondops", ext_XVentanaCondOps, false),
>      MULTI_EXT_CFG_BOOL("xmipscbop", ext_xmipscbop, false),
>      MULTI_EXT_CFG_BOOL("xmipscmov", ext_xmipscmov, false),
> +    MULTI_EXT_CFG_BOOL("xmipslsp", ext_xmipslsp, false),
>
>      { },
>  };
> @@ -3297,6 +3299,7 @@ static const TypeInfo riscv_cpu_type_infos[] = {
>          .cfg.pmp = true,
>          .cfg.ext_zba = true,
>          .cfg.ext_zbb = true,
> +        .cfg.ext_xmipslsp = true,
>          .cfg.ext_xmipscbop = true,
>          .cfg.ext_xmipscmov = true,
>          .cfg.marchid = 0x8000000000000201,
> diff --git a/target/riscv/cpu_cfg.h b/target/riscv/cpu_cfg.h
> index e4d5039c49..cd1cba797c 100644
> --- a/target/riscv/cpu_cfg.h
> +++ b/target/riscv/cpu_cfg.h
> @@ -38,7 +38,7 @@ static inline bool always_true_p(const RISCVCPUConfig *cfg 
> __attribute__((__unus
>
>  static inline bool has_xmips_p(const RISCVCPUConfig *cfg)
>  {
> -    return cfg->ext_xmipscbop || cfg->ext_xmipscmov;
> +    return cfg->ext_xmipscbop || cfg->ext_xmipscmov || cfg->ext_xmipslsp;
>  }
>
>  static inline bool has_xthead_p(const RISCVCPUConfig *cfg)
> diff --git a/target/riscv/cpu_cfg_fields.h.inc 
> b/target/riscv/cpu_cfg_fields.h.inc
> index dd3ee7ba2b..7c624ab677 100644
> --- a/target/riscv/cpu_cfg_fields.h.inc
> +++ b/target/riscv/cpu_cfg_fields.h.inc
> @@ -149,6 +149,7 @@ BOOL_FIELD(ext_xtheadsync)
>  BOOL_FIELD(ext_XVentanaCondOps)
>  BOOL_FIELD(ext_xmipscbop)
>  BOOL_FIELD(ext_xmipscmov)
> +BOOL_FIELD(ext_xmipslsp)
>
>  BOOL_FIELD(mmu)
>  BOOL_FIELD(pmp)
> diff --git a/target/riscv/insn_trans/trans_xmips.c.inc 
> b/target/riscv/insn_trans/trans_xmips.c.inc
> index bfe9046153..9a72f3392f 100644
> --- a/target/riscv/insn_trans/trans_xmips.c.inc
> +++ b/target/riscv/insn_trans/trans_xmips.c.inc
> @@ -21,6 +21,12 @@
>      }                                            \
>  } while (0)
>
> +#define REQUIRE_XMIPSLSP(ctx) do {               \
> +    if (!ctx->cfg_ptr->ext_xmipslsp) {           \
> +        return false;                            \
> +    }                                            \
> +} while (0)
> +
>  /* Conditional move by MIPS. */
>  static bool trans_ccmov(DisasContext *ctx, arg_ccmov *a)
>  {
> @@ -38,6 +44,88 @@ static bool trans_ccmov(DisasContext *ctx, arg_ccmov *a)
>      return true;
>  }
>
> +/* Load Doubleword Pair. */
> +static bool trans_ldp(DisasContext *ctx, arg_ldp *a)
> +{
> +    REQUIRE_XMIPSLSP(ctx);
> +    REQUIRE_64_OR_128BIT(ctx);
> +
> +    TCGv src = get_gpr(ctx, a->rs1, EXT_NONE);
> +    TCGv dest0 = dest_gpr(ctx, a->rd);
> +    TCGv dest1 = dest_gpr(ctx, a->rs3);
> +    TCGv addr = tcg_temp_new();
> +
> +    tcg_gen_addi_tl(addr, src, a->imm_y);
> +    tcg_gen_qemu_ld_tl(dest0, addr, ctx->mem_idx, MO_TESQ);
> +    gen_set_gpr(ctx, a->rd, dest0);
> +
> +    tcg_gen_addi_tl(addr, addr, 8);
> +    tcg_gen_qemu_ld_tl(dest1, addr, ctx->mem_idx, MO_TESQ);
> +    gen_set_gpr(ctx, a->rs3, dest1);
> +
> +    return true;
> +}
> +
> +/* Load Word Pair. */
> +static bool trans_lwp(DisasContext *ctx, arg_lwp *a)
> +{
> +    REQUIRE_XMIPSLSP(ctx);
> +
> +    TCGv src = get_gpr(ctx, a->rs1, EXT_NONE);
> +    TCGv dest0 = dest_gpr(ctx, a->rd);
> +    TCGv dest1 = dest_gpr(ctx, a->rs3);
> +    TCGv addr = tcg_temp_new();
> +
> +    tcg_gen_addi_tl(addr, src, a->imm_x);
> +    tcg_gen_qemu_ld_tl(dest0, addr, ctx->mem_idx, MO_TESL);
> +    gen_set_gpr(ctx, a->rd, dest0);
> +
> +    tcg_gen_addi_tl(addr, addr, 4);
> +    tcg_gen_qemu_ld_tl(dest1, addr, ctx->mem_idx, MO_TESL);
> +    gen_set_gpr(ctx, a->rs3, dest1);
> +
> +    return true;
> +}
> +
> +/* Store Doubleword Pair. */
> +static bool trans_sdp(DisasContext *ctx, arg_sdp *a)
> +{
> +    REQUIRE_XMIPSLSP(ctx);
> +    REQUIRE_64_OR_128BIT(ctx);
> +
> +    TCGv src = get_gpr(ctx, a->rs1, EXT_NONE);
> +    TCGv data0 = get_gpr(ctx, a->rs2, EXT_NONE);
> +    TCGv data1 = get_gpr(ctx, a->rs3, EXT_NONE);
> +    TCGv addr = tcg_temp_new();
> +
> +    tcg_gen_addi_tl(addr, src, a->imm_w);
> +    tcg_gen_qemu_st_tl(data0, addr, ctx->mem_idx, MO_TEUQ);
> +
> +    tcg_gen_addi_tl(addr, addr, 8);
> +    tcg_gen_qemu_st_tl(data1, addr, ctx->mem_idx, MO_TEUQ);
> +
> +    return true;
> +}
> +
> +/* Store Word Pair. */
> +static bool trans_swp(DisasContext *ctx, arg_swp *a)
> +{
> +    REQUIRE_XMIPSLSP(ctx);
> +
> +    TCGv src = get_gpr(ctx, a->rs1, EXT_NONE);
> +    TCGv data0 = get_gpr(ctx, a->rs2, EXT_NONE);
> +    TCGv data1 = get_gpr(ctx, a->rs3, EXT_NONE);
> +    TCGv addr = tcg_temp_new();
> +
> +    tcg_gen_addi_tl(addr, src, a->imm_v);
> +    tcg_gen_qemu_st_tl(data0, addr, ctx->mem_idx, MO_TESL);
> +
> +    tcg_gen_addi_tl(addr, addr, 4);
> +    tcg_gen_qemu_st_tl(data1, addr, ctx->mem_idx, MO_TESL);
> +
> +    return true;
> +}
> +
>  /* Move data from memory into cache. */
>  static bool trans_pref(DisasContext *ctx, arg_pref *a)
>  {
> diff --git a/target/riscv/xmips.decode b/target/riscv/xmips.decode
> index 4215813b32..3174f17aa4 100644
> --- a/target/riscv/xmips.decode
> +++ b/target/riscv/xmips.decode
> @@ -8,5 +8,28 @@
>  # Reference: MIPS P8700 instructions
>  #            (https://mips.com/products/hardware/p8700/)
>
> +# Fields
> +%rs3       27:5
> +%rs2       20:5
> +%rs1       15:5
> +%rd        7:5
> +%imm_9     20:9
> +%imm_hint  7:5
> +%imm_v     25:2 9:3               !function=ex_shift_2
> +%imm_w     25:2 10:2              !function=ex_shift_3
> +%imm_x     22:5                   !function=ex_shift_2
> +%imm_y     23:4                   !function=ex_shift_3
> +
> +# Formats
> +@r4_immv ..... .. ..... ..... ... ... .. ....... %rs2 %rs3 %imm_v %rs1
> +@r4_immw ..... .. ..... ..... ... .. ... ....... %rs2 %rs3 %imm_w %rs1
> +@r4_immx ..... .....  .. ..... ... ..... ....... %rs3 %imm_x %rs1 %rd
> +@r4_immy ..... ....  ... ..... ... ..... ....... %rs3 %imm_y %rs1 %rd
> +
> +# *** RV64 MIPS Extension ***
>  ccmov          rs3:5 11 rs2:5 rs1:5 011 rd:5 0001011
>  pref        000 imm_9:9 rs1:5 000 imm_hint:5 0001011
> +ldp         ..... .... 000 ..... 100 .....  0001011 @r4_immy
> +lwp         ..... ..... 01 ..... 100 .....  0001011 @r4_immx
> +sdp         ..... .. ..... ..... 101 ..  0000001011 @r4_immw
> +swp         ..... .. ..... ..... 101 ...  010001011 @r4_immv
> --
> 2.34.1

Reply via email to