From b75de9504cc52dde7d3808c407e44f94b8c3b19a Mon Sep 17 00:00:00 2001 From: LIU Zhiwei Date: Sun, 7 Mar 2021 12:38:37 -0500 Subject: [PATCH] target/riscv: integer scalar move instruction Backports 9fc08be626a96ae1ac0cffb22f30ae652c1c645a --- qemu/target/riscv/insn32.decode | 1 + qemu/target/riscv/insn_trans/trans_rvv.inc.c | 63 ++++++++++++++++++++ qemu/target/riscv/internals.h | 5 ++ 3 files changed, 69 insertions(+) diff --git a/qemu/target/riscv/insn32.decode b/qemu/target/riscv/insn32.decode index c4496cd0..e06c0ffc 100644 --- a/qemu/target/riscv/insn32.decode +++ b/qemu/target/riscv/insn32.decode @@ -564,6 +564,7 @@ vmsof_m 010110 . ..... 00010 010 ..... 1010111 @r2_vm viota_m 010110 . ..... 10000 010 ..... 1010111 @r2_vm vid_v 010110 . 00000 10001 010 ..... 1010111 @r1_vm vext_x_v 001100 1 ..... ..... 010 ..... 1010111 @r +vmv_s_x 001101 1 00000 ..... 110 ..... 1010111 @r2 vsetvli 0 ........... ..... 111 ..... 1010111 @r2_zimm vsetvl 1000000 ..... ..... 111 ..... 1010111 @r diff --git a/qemu/target/riscv/insn_trans/trans_rvv.inc.c b/qemu/target/riscv/insn_trans/trans_rvv.inc.c index 64e11ab6..f82bc876 100644 --- a/qemu/target/riscv/insn_trans/trans_rvv.inc.c +++ b/qemu/target/riscv/insn_trans/trans_rvv.inc.c @@ -2699,3 +2699,66 @@ static bool trans_vext_x_v(DisasContext *s, arg_r *a) tcg_temp_free_i64(tcg_ctx, tmp); return true; } + +/* Integer Scalar Move Instruction */ + +static void store_element(TCGContext *s, TCGv_i64 val, TCGv_ptr base, + int ofs, int sew) +{ + switch (sew) { + case MO_8: + tcg_gen_st8_i64(s, val, base, ofs); + break; + case MO_16: + tcg_gen_st16_i64(s, val, base, ofs); + break; + case MO_32: + tcg_gen_st32_i64(s, val, base, ofs); + break; + case MO_64: + tcg_gen_st_i64(s, val, base, ofs); + break; + default: + g_assert_not_reached(); + break; + } +} + +/* + * Store vreg[idx] = val. + * The index must be in range of VLMAX. + */ +static void vec_element_storei(DisasContext *s, int vreg, + int idx, TCGv_i64 val) +{ + TCGContext *tcg_ctx = s->uc->tcg_ctx; + store_element(tcg_ctx, val, tcg_ctx->cpu_env, endian_ofs(s, vreg, idx), s->sew); +} + +/* vmv.s.x vd, rs1 # vd[0] = rs1 */ +static bool trans_vmv_s_x(DisasContext *s, arg_vmv_s_x *a) +{ + TCGContext *tcg_ctx = s->uc->tcg_ctx; + + if (vext_check_isa_ill(s)) { + /* This instruction ignores LMUL and vector register groups */ + int maxsz = s->vlen >> 3; + TCGv_i64 t1; + TCGLabel *over = gen_new_label(tcg_ctx); + + tcg_gen_brcondi_tl(tcg_ctx, TCG_COND_EQ, tcg_ctx->cpu_vl_risc, 0, over); + tcg_gen_gvec_dup_imm(tcg_ctx, SEW64, vreg_ofs(s, a->rd), maxsz, maxsz, 0); + if (a->rs1 == 0) { + goto done; + } + + t1 = tcg_temp_new_i64(tcg_ctx); + tcg_gen_extu_tl_i64(tcg_ctx, t1, tcg_ctx->cpu_gpr_risc[a->rs1]); + vec_element_storei(s, a->rd, 0, t1); + tcg_temp_free_i64(tcg_ctx, t1); + done: + gen_set_label(tcg_ctx, over); + return true; + } + return false; +} diff --git a/qemu/target/riscv/internals.h b/qemu/target/riscv/internals.h index 8ea92089..2dcc808f 100644 --- a/qemu/target/riscv/internals.h +++ b/qemu/target/riscv/internals.h @@ -34,4 +34,9 @@ target_ulong fclass_h_risc(uint64_t frs1); target_ulong fclass_s_risc(uint64_t frs1); target_ulong fclass_d_risc(uint64_t frs1); +#define SEW8 0 +#define SEW16 1 +#define SEW32 2 +#define SEW64 3 + #endif