All of lore.kernel.org
 help / color / mirror / Atom feed
* [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-05  2:52 ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:52 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

This patch set implements UXL field in mstatus register. Programmer can change
UXLEN by writting to this field. So that you can run a 32 bit program
on a 64 bit CPU.

This patch set depends on one patch set by Richard Henderson
https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.

LIU Zhiwei (13):
  target/riscv: Add UXL to tb flags
  target/riscv: Support UXL32 for branch instructions
  target/riscv: Support UXL32 on 64-bit cpu for load/store
  target/riscv: Support UXL32 for slit/sltiu
  target/riscv: Support UXL32 for shift instruction
  target/riscv: Fix div instructions
  target/riscv: Support UXL32 for RVM
  target/riscv: Support UXL32 for vector instructions
  target/riscv: Support UXL32 for atomic instructions
  target/riscv: Support UXL32 for float instructions
  target/riscv: Fix srow
  target/riscv: Support UXL32 for RVB
  target/riscv: Changing the width of U-mode CSR

 target/riscv/cpu.h                      |  18 +++
 target/riscv/csr.c                      |  42 +++++-
 target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
 target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
 target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
 target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
 target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
 target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
 target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
 target/riscv/translate.c                | 186 ++++++++++++++++++++----
 target/riscv/vector_helper.c            |  54 +++++--
 11 files changed, 414 insertions(+), 111 deletions(-)

-- 
2.17.1



^ permalink raw reply	[flat|nested] 82+ messages in thread

* [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-05  2:52 ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:52 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

This patch set implements UXL field in mstatus register. Programmer can change
UXLEN by writting to this field. So that you can run a 32 bit program
on a 64 bit CPU.

This patch set depends on one patch set by Richard Henderson
https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.

LIU Zhiwei (13):
  target/riscv: Add UXL to tb flags
  target/riscv: Support UXL32 for branch instructions
  target/riscv: Support UXL32 on 64-bit cpu for load/store
  target/riscv: Support UXL32 for slit/sltiu
  target/riscv: Support UXL32 for shift instruction
  target/riscv: Fix div instructions
  target/riscv: Support UXL32 for RVM
  target/riscv: Support UXL32 for vector instructions
  target/riscv: Support UXL32 for atomic instructions
  target/riscv: Support UXL32 for float instructions
  target/riscv: Fix srow
  target/riscv: Support UXL32 for RVB
  target/riscv: Changing the width of U-mode CSR

 target/riscv/cpu.h                      |  18 +++
 target/riscv/csr.c                      |  42 +++++-
 target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
 target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
 target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
 target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
 target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
 target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
 target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
 target/riscv/translate.c                | 186 ++++++++++++++++++++----
 target/riscv/vector_helper.c            |  54 +++++--
 11 files changed, 414 insertions(+), 111 deletions(-)

-- 
2.17.1



^ permalink raw reply	[flat|nested] 82+ messages in thread

* [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

For 32-bit applications run on 64-bit cpu, it may share some code
with other 64-bit applictions. Thus we should distinguish the translated
cache of the share code with a tb flag.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/cpu.h       | 15 +++++++++++++++
 target/riscv/translate.c |  3 +++
 2 files changed, 18 insertions(+)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index bf1c899c00..2b3ba21a78 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
 FIELD(TB_FLAGS, VILL, 8, 1)
 /* Is a Hypervisor instruction load/store allowed? */
 FIELD(TB_FLAGS, HLSX, 9, 1)
+FIELD(TB_FLAGS, UXL, 10, 2)
 
 bool riscv_cpu_is_32bit(CPURISCVState *env);
 
+static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
+{
+#ifndef CONFIG_USER_ONLY
+    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
+           !riscv_cpu_is_32bit(env) &&
+           (env->priv == PRV_U);
+#endif
+    return false;
+}
+
 /*
  * A simplification for VLMAX
  * = (1 << LMUL) * VLEN / (8 * (1 << SEW))
@@ -451,6 +462,10 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
             flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
         }
     }
+    if (riscv_cpu_is_uxl32(env)) {
+        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
+                           get_field(env->mstatus, MSTATUS64_UXL));
+    }
 #endif
 
     *pflags = flags;
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 076f28b9c1..ac4a545da8 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -67,6 +67,8 @@ typedef struct DisasContext {
     CPUState *cs;
     TCGv zero;
     TCGv sink;
+    /* UXLEN is 32 bit for 64-bit CPU */
+    bool uxl32;
 } DisasContext;
 
 static inline bool has_ext(DisasContext *ctx, uint32_t ext)
@@ -912,6 +914,7 @@ static void riscv_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
     ctx->mlen = 1 << (ctx->sew  + 3 - ctx->lmul);
     ctx->vl_eq_vlmax = FIELD_EX32(tb_flags, TB_FLAGS, VL_EQ_VLMAX);
     ctx->cs = cs;
+    ctx->uxl32 = FIELD_EX32(tb_flags, TB_FLAGS, UXL) == 1;
 }
 
 static void riscv_tr_tb_start(DisasContextBase *dcbase, CPUState *cpu)
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

For 32-bit applications run on 64-bit cpu, it may share some code
with other 64-bit applictions. Thus we should distinguish the translated
cache of the share code with a tb flag.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/cpu.h       | 15 +++++++++++++++
 target/riscv/translate.c |  3 +++
 2 files changed, 18 insertions(+)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index bf1c899c00..2b3ba21a78 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
 FIELD(TB_FLAGS, VILL, 8, 1)
 /* Is a Hypervisor instruction load/store allowed? */
 FIELD(TB_FLAGS, HLSX, 9, 1)
+FIELD(TB_FLAGS, UXL, 10, 2)
 
 bool riscv_cpu_is_32bit(CPURISCVState *env);
 
+static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
+{
+#ifndef CONFIG_USER_ONLY
+    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
+           !riscv_cpu_is_32bit(env) &&
+           (env->priv == PRV_U);
+#endif
+    return false;
+}
+
 /*
  * A simplification for VLMAX
  * = (1 << LMUL) * VLEN / (8 * (1 << SEW))
@@ -451,6 +462,10 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
             flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
         }
     }
+    if (riscv_cpu_is_uxl32(env)) {
+        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
+                           get_field(env->mstatus, MSTATUS64_UXL));
+    }
 #endif
 
     *pflags = flags;
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 076f28b9c1..ac4a545da8 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -67,6 +67,8 @@ typedef struct DisasContext {
     CPUState *cs;
     TCGv zero;
     TCGv sink;
+    /* UXLEN is 32 bit for 64-bit CPU */
+    bool uxl32;
 } DisasContext;
 
 static inline bool has_ext(DisasContext *ctx, uint32_t ext)
@@ -912,6 +914,7 @@ static void riscv_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
     ctx->mlen = 1 << (ctx->sew  + 3 - ctx->lmul);
     ctx->vl_eq_vlmax = FIELD_EX32(tb_flags, TB_FLAGS, VL_EQ_VLMAX);
     ctx->cs = cs;
+    ctx->uxl32 = FIELD_EX32(tb_flags, TB_FLAGS, UXL) == 1;
 }
 
 static void riscv_tr_tb_start(DisasContextBase *dcbase, CPUState *cpu)
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

When UXLEN is 32 on 64-bit CPU, only use the LSB 32 bits of source
registers and sign-extend or zero-extend it according to different
operations.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc | 38 ++++++++++++++++++++-----
 target/riscv/translate.c                | 22 ++++++++++++++
 2 files changed, 53 insertions(+), 7 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 3705aad380..ea41d1de2d 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -84,11 +84,11 @@ static bool trans_jalr(DisasContext *ctx, arg_jalr *a)
     return true;
 }
 
-static bool gen_branch(DisasContext *ctx, arg_b *a, TCGCond cond)
+static bool gen_branch_internal(DisasContext *ctx, arg_b *a,
+                                TCGCond cond,
+                                TCGv src1, TCGv src2)
 {
     TCGLabel *l = gen_new_label();
-    TCGv src1 = gpr_src(ctx, a->rs1);
-    TCGv src2 = gpr_src(ctx, a->rs2);
 
     tcg_gen_brcond_tl(cond, src1, src2, l);
     gen_goto_tb(ctx, 1, ctx->pc_succ_insn);
@@ -106,6 +106,30 @@ static bool gen_branch(DisasContext *ctx, arg_b *a, TCGCond cond)
     return true;
 }
 
+static bool gen_branch_s(DisasContext *ctx, arg_b *a, TCGCond cond)
+{
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = gpr_src_s(ctx, a->rs2);
+
+    return gen_branch_internal(ctx, a, cond, src1, src2);
+}
+
+static bool gen_branch_u(DisasContext *ctx, arg_b *a, TCGCond cond)
+{
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
+
+    return gen_branch_internal(ctx, a, cond, src1, src2);
+}
+
+static bool gen_branch(DisasContext *ctx, arg_b *a, TCGCond cond)
+{
+    TCGv src1 = gpr_src(ctx, a->rs1);
+    TCGv src2 = gpr_src(ctx, a->rs2);
+
+    return gen_branch_internal(ctx, a, cond, src1, src2);
+}
+
 static bool trans_beq(DisasContext *ctx, arg_beq *a)
 {
     return gen_branch(ctx, a, TCG_COND_EQ);
@@ -118,22 +142,22 @@ static bool trans_bne(DisasContext *ctx, arg_bne *a)
 
 static bool trans_blt(DisasContext *ctx, arg_blt *a)
 {
-    return gen_branch(ctx, a, TCG_COND_LT);
+    return gen_branch_s(ctx, a, TCG_COND_LT);
 }
 
 static bool trans_bge(DisasContext *ctx, arg_bge *a)
 {
-    return gen_branch(ctx, a, TCG_COND_GE);
+    return gen_branch_s(ctx, a, TCG_COND_GE);
 }
 
 static bool trans_bltu(DisasContext *ctx, arg_bltu *a)
 {
-    return gen_branch(ctx, a, TCG_COND_LTU);
+    return gen_branch_u(ctx, a, TCG_COND_LTU);
 }
 
 static bool trans_bgeu(DisasContext *ctx, arg_bgeu *a)
 {
-    return gen_branch(ctx, a, TCG_COND_GEU);
+    return gen_branch_u(ctx, a, TCG_COND_GEU);
 }
 
 static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index ac4a545da8..d334a9db86 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -176,6 +176,28 @@ static void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
     }
 }
 
+static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
+{
+    if (reg_num == 0) {
+        return ctx->zero;
+    }
+    if (ctx->uxl32) {
+        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
+    }
+    return cpu_gpr[reg_num];
+}
+
+static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
+{
+    if (reg_num == 0) {
+        return ctx->zero;
+    }
+    if (ctx->uxl32) {
+        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
+    }
+    return cpu_gpr[reg_num];
+}
+
 /* Wrapper for getting reg values - need to check of reg is zero since
  * cpu_gpr[0] is not actually allocated
  */
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

When UXLEN is 32 on 64-bit CPU, only use the LSB 32 bits of source
registers and sign-extend or zero-extend it according to different
operations.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc | 38 ++++++++++++++++++++-----
 target/riscv/translate.c                | 22 ++++++++++++++
 2 files changed, 53 insertions(+), 7 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 3705aad380..ea41d1de2d 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -84,11 +84,11 @@ static bool trans_jalr(DisasContext *ctx, arg_jalr *a)
     return true;
 }
 
-static bool gen_branch(DisasContext *ctx, arg_b *a, TCGCond cond)
+static bool gen_branch_internal(DisasContext *ctx, arg_b *a,
+                                TCGCond cond,
+                                TCGv src1, TCGv src2)
 {
     TCGLabel *l = gen_new_label();
-    TCGv src1 = gpr_src(ctx, a->rs1);
-    TCGv src2 = gpr_src(ctx, a->rs2);
 
     tcg_gen_brcond_tl(cond, src1, src2, l);
     gen_goto_tb(ctx, 1, ctx->pc_succ_insn);
@@ -106,6 +106,30 @@ static bool gen_branch(DisasContext *ctx, arg_b *a, TCGCond cond)
     return true;
 }
 
+static bool gen_branch_s(DisasContext *ctx, arg_b *a, TCGCond cond)
+{
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = gpr_src_s(ctx, a->rs2);
+
+    return gen_branch_internal(ctx, a, cond, src1, src2);
+}
+
+static bool gen_branch_u(DisasContext *ctx, arg_b *a, TCGCond cond)
+{
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
+
+    return gen_branch_internal(ctx, a, cond, src1, src2);
+}
+
+static bool gen_branch(DisasContext *ctx, arg_b *a, TCGCond cond)
+{
+    TCGv src1 = gpr_src(ctx, a->rs1);
+    TCGv src2 = gpr_src(ctx, a->rs2);
+
+    return gen_branch_internal(ctx, a, cond, src1, src2);
+}
+
 static bool trans_beq(DisasContext *ctx, arg_beq *a)
 {
     return gen_branch(ctx, a, TCG_COND_EQ);
@@ -118,22 +142,22 @@ static bool trans_bne(DisasContext *ctx, arg_bne *a)
 
 static bool trans_blt(DisasContext *ctx, arg_blt *a)
 {
-    return gen_branch(ctx, a, TCG_COND_LT);
+    return gen_branch_s(ctx, a, TCG_COND_LT);
 }
 
 static bool trans_bge(DisasContext *ctx, arg_bge *a)
 {
-    return gen_branch(ctx, a, TCG_COND_GE);
+    return gen_branch_s(ctx, a, TCG_COND_GE);
 }
 
 static bool trans_bltu(DisasContext *ctx, arg_bltu *a)
 {
-    return gen_branch(ctx, a, TCG_COND_LTU);
+    return gen_branch_u(ctx, a, TCG_COND_LTU);
 }
 
 static bool trans_bgeu(DisasContext *ctx, arg_bgeu *a)
 {
-    return gen_branch(ctx, a, TCG_COND_GEU);
+    return gen_branch_u(ctx, a, TCG_COND_GEU);
 }
 
 static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index ac4a545da8..d334a9db86 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -176,6 +176,28 @@ static void gen_goto_tb(DisasContext *ctx, int n, target_ulong dest)
     }
 }
 
+static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
+{
+    if (reg_num == 0) {
+        return ctx->zero;
+    }
+    if (ctx->uxl32) {
+        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
+    }
+    return cpu_gpr[reg_num];
+}
+
+static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
+{
+    if (reg_num == 0) {
+        return ctx->zero;
+    }
+    if (ctx->uxl32) {
+        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
+    }
+    return cpu_gpr[reg_num];
+}
+
 /* Wrapper for getting reg values - need to check of reg is zero since
  * cpu_gpr[0] is not actually allocated
  */
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Get the LSB 32 bits and zero-extend as the base address.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index ea41d1de2d..6823a6b3e0 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -163,7 +163,7 @@ static bool trans_bgeu(DisasContext *ctx, arg_bgeu *a)
 static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
@@ -207,7 +207,7 @@ static bool trans_lhu(DisasContext *ctx, arg_lhu *a)
 
 static bool gen_store(DisasContext *ctx, arg_sb *a, MemOp memop)
 {
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv data = gpr_src(ctx, a->rs2);
     TCGv temp = NULL;
 
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Get the LSB 32 bits and zero-extend as the base address.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index ea41d1de2d..6823a6b3e0 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -163,7 +163,7 @@ static bool trans_bgeu(DisasContext *ctx, arg_bgeu *a)
 static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
@@ -207,7 +207,7 @@ static bool trans_lhu(DisasContext *ctx, arg_lhu *a)
 
 static bool gen_store(DisasContext *ctx, arg_sb *a, MemOp memop)
 {
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv data = gpr_src(ctx, a->rs2);
     TCGv temp = NULL;
 
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

For slitu, the imm is sign-extend before unsigned compare. Thus we
should only use the LSB 32 bits of the imm for UXL32.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc |  8 ++---
 target/riscv/translate.c                | 44 +++++++++++++++++++++++++
 2 files changed, 48 insertions(+), 4 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 6823a6b3e0..6201c07795 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -276,12 +276,12 @@ static void gen_sltu(TCGv ret, TCGv s1, TCGv s2)
 
 static bool trans_slti(DisasContext *ctx, arg_slti *a)
 {
-    return gen_arith_imm_tl(ctx, a, &gen_slt);
+    return gen_arith_simm_tl(ctx, a, &gen_slt);
 }
 
 static bool trans_sltiu(DisasContext *ctx, arg_sltiu *a)
 {
-    return gen_arith_imm_tl(ctx, a, &gen_sltu);
+    return gen_arith_uimm_tl(ctx, a, &gen_sltu);
 }
 
 static bool trans_xori(DisasContext *ctx, arg_xori *a)
@@ -328,12 +328,12 @@ static bool trans_sll(DisasContext *ctx, arg_sll *a)
 
 static bool trans_slt(DisasContext *ctx, arg_slt *a)
 {
-    return gen_arith(ctx, a, &gen_slt);
+    return gen_arith_s(ctx, a, &gen_slt);
 }
 
 static bool trans_sltu(DisasContext *ctx, arg_sltu *a)
 {
-    return gen_arith(ctx, a, &gen_sltu);
+    return gen_arith_u(ctx, a, &gen_sltu);
 }
 
 static bool trans_xor(DisasContext *ctx, arg_xor *a)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index d334a9db86..912e5f1061 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -494,6 +494,28 @@ static bool gen_arith_imm_tl(DisasContext *ctx, arg_i *a,
     return true;
 }
 
+static bool gen_arith_simm_tl(DisasContext *ctx, arg_i *a,
+                              void (*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = tcg_constant_tl(a->imm);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
+static bool gen_arith_uimm_tl(DisasContext *ctx, arg_i *a,
+                              void (*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = tcg_constant_tl(ctx->uxl32 ? a->imm & UINT32_MAX : a->imm);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
 static void gen_addw(TCGv ret, TCGv arg1, TCGv arg2)
 {
     tcg_gen_add_tl(ret, arg1, arg2);
@@ -779,6 +801,28 @@ static bool gen_arith(DisasContext *ctx, arg_r *a,
     return true;
 }
 
+static bool gen_arith_u(DisasContext *ctx, arg_r *a,
+                        void(*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
+static bool gen_arith_s(DisasContext *ctx, arg_r *a,
+                        void(*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = gpr_src_s(ctx, a->rs2);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
 static bool gen_shift(DisasContext *ctx, arg_r *a,
                         void(*func)(TCGv, TCGv, TCGv))
 {
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

For slitu, the imm is sign-extend before unsigned compare. Thus we
should only use the LSB 32 bits of the imm for UXL32.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc |  8 ++---
 target/riscv/translate.c                | 44 +++++++++++++++++++++++++
 2 files changed, 48 insertions(+), 4 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 6823a6b3e0..6201c07795 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -276,12 +276,12 @@ static void gen_sltu(TCGv ret, TCGv s1, TCGv s2)
 
 static bool trans_slti(DisasContext *ctx, arg_slti *a)
 {
-    return gen_arith_imm_tl(ctx, a, &gen_slt);
+    return gen_arith_simm_tl(ctx, a, &gen_slt);
 }
 
 static bool trans_sltiu(DisasContext *ctx, arg_sltiu *a)
 {
-    return gen_arith_imm_tl(ctx, a, &gen_sltu);
+    return gen_arith_uimm_tl(ctx, a, &gen_sltu);
 }
 
 static bool trans_xori(DisasContext *ctx, arg_xori *a)
@@ -328,12 +328,12 @@ static bool trans_sll(DisasContext *ctx, arg_sll *a)
 
 static bool trans_slt(DisasContext *ctx, arg_slt *a)
 {
-    return gen_arith(ctx, a, &gen_slt);
+    return gen_arith_s(ctx, a, &gen_slt);
 }
 
 static bool trans_sltu(DisasContext *ctx, arg_sltu *a)
 {
-    return gen_arith(ctx, a, &gen_sltu);
+    return gen_arith_u(ctx, a, &gen_sltu);
 }
 
 static bool trans_xor(DisasContext *ctx, arg_xor *a)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index d334a9db86..912e5f1061 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -494,6 +494,28 @@ static bool gen_arith_imm_tl(DisasContext *ctx, arg_i *a,
     return true;
 }
 
+static bool gen_arith_simm_tl(DisasContext *ctx, arg_i *a,
+                              void (*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = tcg_constant_tl(a->imm);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
+static bool gen_arith_uimm_tl(DisasContext *ctx, arg_i *a,
+                              void (*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = tcg_constant_tl(ctx->uxl32 ? a->imm & UINT32_MAX : a->imm);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
 static void gen_addw(TCGv ret, TCGv arg1, TCGv arg2)
 {
     tcg_gen_add_tl(ret, arg1, arg2);
@@ -779,6 +801,28 @@ static bool gen_arith(DisasContext *ctx, arg_r *a,
     return true;
 }
 
+static bool gen_arith_u(DisasContext *ctx, arg_r *a,
+                        void(*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
+static bool gen_arith_s(DisasContext *ctx, arg_r *a,
+                        void(*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = gpr_src_s(ctx, a->rs2);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
 static bool gen_shift(DisasContext *ctx, arg_r *a,
                         void(*func)(TCGv, TCGv, TCGv))
 {
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Reuse 32-bit right shift instructions.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 6201c07795..698a28731e 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -303,11 +303,17 @@ static bool trans_slli(DisasContext *ctx, arg_slli *a)
 
 static bool trans_srli(DisasContext *ctx, arg_srli *a)
 {
+    if (ctx->uxl32) {
+        return trans_srliw(ctx, a);
+    }
     return gen_shifti(ctx, a, tcg_gen_shr_tl);
 }
 
 static bool trans_srai(DisasContext *ctx, arg_srai *a)
 {
+    if (ctx->uxl32) {
+        return trans_sraiw(ctx, a);
+    }
     return gen_shifti(ctx, a, tcg_gen_sar_tl);
 }
 
@@ -343,11 +349,17 @@ static bool trans_xor(DisasContext *ctx, arg_xor *a)
 
 static bool trans_srl(DisasContext *ctx, arg_srl *a)
 {
+    if (ctx->uxl32) {
+        return trans_srlw(ctx, a);
+    }
     return gen_shift(ctx, a, &tcg_gen_shr_tl);
 }
 
 static bool trans_sra(DisasContext *ctx, arg_sra *a)
 {
+    if (ctx->uxl32) {
+        return trans_sraw(ctx, a);
+    }
     return gen_shift(ctx, a, &tcg_gen_sar_tl);
 }
 
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Reuse 32-bit right shift instructions.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvi.c.inc | 12 ++++++++++++
 1 file changed, 12 insertions(+)

diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
index 6201c07795..698a28731e 100644
--- a/target/riscv/insn_trans/trans_rvi.c.inc
+++ b/target/riscv/insn_trans/trans_rvi.c.inc
@@ -303,11 +303,17 @@ static bool trans_slli(DisasContext *ctx, arg_slli *a)
 
 static bool trans_srli(DisasContext *ctx, arg_srli *a)
 {
+    if (ctx->uxl32) {
+        return trans_srliw(ctx, a);
+    }
     return gen_shifti(ctx, a, tcg_gen_shr_tl);
 }
 
 static bool trans_srai(DisasContext *ctx, arg_srai *a)
 {
+    if (ctx->uxl32) {
+        return trans_sraiw(ctx, a);
+    }
     return gen_shifti(ctx, a, tcg_gen_sar_tl);
 }
 
@@ -343,11 +349,17 @@ static bool trans_xor(DisasContext *ctx, arg_xor *a)
 
 static bool trans_srl(DisasContext *ctx, arg_srl *a)
 {
+    if (ctx->uxl32) {
+        return trans_srlw(ctx, a);
+    }
     return gen_shift(ctx, a, &tcg_gen_shr_tl);
 }
 
 static bool trans_sra(DisasContext *ctx, arg_sra *a)
 {
+    if (ctx->uxl32) {
+        return trans_sraw(ctx, a);
+    }
     return gen_shift(ctx, a, &tcg_gen_sar_tl);
 }
 
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 06/13] target/riscv: Fix div instructions
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Don't overwrite global source register after
https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00058.html.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/translate.c | 46 +++++++++++++++++++++++-----------------
 1 file changed, 26 insertions(+), 20 deletions(-)

diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 912e5f1061..2892eaa9a7 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -265,7 +265,7 @@ static void gen_mulhsu(TCGv ret, TCGv arg1, TCGv arg2)
 
 static void gen_div(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, cond2, zeroreg, resultopt1;
+    TCGv cond1, cond2, zeroreg, resultopt1, t1, t2;
     /*
      * Handle by altering args to tcg_gen_div to produce req'd results:
      * For overflow: want source1 in source1 and 1 in source2
@@ -275,6 +275,8 @@ static void gen_div(TCGv ret, TCGv source1, TCGv source2)
     cond2 = tcg_temp_new();
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_movi_tl(resultopt1, (target_ulong)-1);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)(~0L));
@@ -283,49 +285,52 @@ static void gen_div(TCGv ret, TCGv source1, TCGv source2)
     tcg_gen_and_tl(cond1, cond1, cond2); /* cond1 = overflow */
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, 0); /* cond2 = div 0 */
     /* if div by zero, set source1 to -1, otherwise don't change */
-    tcg_gen_movcond_tl(TCG_COND_EQ, source1, cond2, zeroreg, source1,
-            resultopt1);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t1, cond2, zeroreg, source1, resultopt1);
     /* if overflow or div by zero, set source2 to 1, else don't change */
     tcg_gen_or_tl(cond1, cond1, cond2);
     tcg_gen_movi_tl(resultopt1, (target_ulong)1);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond1, zeroreg, source2,
-            resultopt1);
-    tcg_gen_div_tl(ret, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond1, zeroreg, source2, resultopt1);
+    tcg_gen_div_tl(ret, t1, t2);
 
     tcg_temp_free(cond1);
     tcg_temp_free(cond2);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t1);
+    tcg_temp_free(t2);
 }
 
 static void gen_divu(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, zeroreg, resultopt1;
+    TCGv cond1, zeroreg, resultopt1, t1, t2;
     cond1 = tcg_temp_new();
 
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0);
     tcg_gen_movi_tl(resultopt1, (target_ulong)-1);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source1, cond1, zeroreg, source1,
-            resultopt1);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t1, cond1, zeroreg, source1, resultopt1);
     tcg_gen_movi_tl(resultopt1, (target_ulong)1);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond1, zeroreg, source2,
-            resultopt1);
-    tcg_gen_divu_tl(ret, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond1, zeroreg, source2, resultopt1);
+    tcg_gen_divu_tl(ret, t1, t2);
 
     tcg_temp_free(cond1);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t1);
+    tcg_temp_free(t2);
 }
 
 static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, cond2, zeroreg, resultopt1;
+    TCGv cond1, cond2, zeroreg, resultopt1, t2;
 
     cond1 = tcg_temp_new();
     cond2 = tcg_temp_new();
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_movi_tl(resultopt1, 1L);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)-1);
@@ -335,9 +340,8 @@ static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0); /* cond2 = div 0 */
     /* if overflow or div by zero, set source2 to 1, else don't change */
     tcg_gen_or_tl(cond2, cond1, cond2);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond2, zeroreg, source2,
-            resultopt1);
-    tcg_gen_rem_tl(resultopt1, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond2, zeroreg, source2, resultopt1);
+    tcg_gen_rem_tl(resultopt1, source1, t2);
     /* if div by zero, just return the original dividend */
     tcg_gen_movcond_tl(TCG_COND_EQ, ret, cond1, zeroreg, resultopt1,
             source1);
@@ -345,26 +349,28 @@ static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
     tcg_temp_free(cond1);
     tcg_temp_free(cond2);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t2);
 }
 
 static void gen_remu(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, zeroreg, resultopt1;
+    TCGv cond1, zeroreg, resultopt1, t2;
     cond1 = tcg_temp_new();
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_movi_tl(resultopt1, (target_ulong)1);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond1, zeroreg, source2,
-            resultopt1);
-    tcg_gen_remu_tl(resultopt1, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond1, zeroreg, source2, resultopt1);
+    tcg_gen_remu_tl(resultopt1, source1, t2);
     /* if div by zero, just return the original dividend */
     tcg_gen_movcond_tl(TCG_COND_EQ, ret, cond1, zeroreg, resultopt1,
             source1);
 
     tcg_temp_free(cond1);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t2);
 }
 
 static void gen_jal(DisasContext *ctx, int rd, target_ulong imm)
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 06/13] target/riscv: Fix div instructions
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Don't overwrite global source register after
https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00058.html.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/translate.c | 46 +++++++++++++++++++++++-----------------
 1 file changed, 26 insertions(+), 20 deletions(-)

diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 912e5f1061..2892eaa9a7 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -265,7 +265,7 @@ static void gen_mulhsu(TCGv ret, TCGv arg1, TCGv arg2)
 
 static void gen_div(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, cond2, zeroreg, resultopt1;
+    TCGv cond1, cond2, zeroreg, resultopt1, t1, t2;
     /*
      * Handle by altering args to tcg_gen_div to produce req'd results:
      * For overflow: want source1 in source1 and 1 in source2
@@ -275,6 +275,8 @@ static void gen_div(TCGv ret, TCGv source1, TCGv source2)
     cond2 = tcg_temp_new();
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_movi_tl(resultopt1, (target_ulong)-1);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)(~0L));
@@ -283,49 +285,52 @@ static void gen_div(TCGv ret, TCGv source1, TCGv source2)
     tcg_gen_and_tl(cond1, cond1, cond2); /* cond1 = overflow */
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, 0); /* cond2 = div 0 */
     /* if div by zero, set source1 to -1, otherwise don't change */
-    tcg_gen_movcond_tl(TCG_COND_EQ, source1, cond2, zeroreg, source1,
-            resultopt1);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t1, cond2, zeroreg, source1, resultopt1);
     /* if overflow or div by zero, set source2 to 1, else don't change */
     tcg_gen_or_tl(cond1, cond1, cond2);
     tcg_gen_movi_tl(resultopt1, (target_ulong)1);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond1, zeroreg, source2,
-            resultopt1);
-    tcg_gen_div_tl(ret, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond1, zeroreg, source2, resultopt1);
+    tcg_gen_div_tl(ret, t1, t2);
 
     tcg_temp_free(cond1);
     tcg_temp_free(cond2);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t1);
+    tcg_temp_free(t2);
 }
 
 static void gen_divu(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, zeroreg, resultopt1;
+    TCGv cond1, zeroreg, resultopt1, t1, t2;
     cond1 = tcg_temp_new();
 
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0);
     tcg_gen_movi_tl(resultopt1, (target_ulong)-1);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source1, cond1, zeroreg, source1,
-            resultopt1);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t1, cond1, zeroreg, source1, resultopt1);
     tcg_gen_movi_tl(resultopt1, (target_ulong)1);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond1, zeroreg, source2,
-            resultopt1);
-    tcg_gen_divu_tl(ret, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond1, zeroreg, source2, resultopt1);
+    tcg_gen_divu_tl(ret, t1, t2);
 
     tcg_temp_free(cond1);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t1);
+    tcg_temp_free(t2);
 }
 
 static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, cond2, zeroreg, resultopt1;
+    TCGv cond1, cond2, zeroreg, resultopt1, t2;
 
     cond1 = tcg_temp_new();
     cond2 = tcg_temp_new();
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_movi_tl(resultopt1, 1L);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)-1);
@@ -335,9 +340,8 @@ static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0); /* cond2 = div 0 */
     /* if overflow or div by zero, set source2 to 1, else don't change */
     tcg_gen_or_tl(cond2, cond1, cond2);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond2, zeroreg, source2,
-            resultopt1);
-    tcg_gen_rem_tl(resultopt1, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond2, zeroreg, source2, resultopt1);
+    tcg_gen_rem_tl(resultopt1, source1, t2);
     /* if div by zero, just return the original dividend */
     tcg_gen_movcond_tl(TCG_COND_EQ, ret, cond1, zeroreg, resultopt1,
             source1);
@@ -345,26 +349,28 @@ static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
     tcg_temp_free(cond1);
     tcg_temp_free(cond2);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t2);
 }
 
 static void gen_remu(TCGv ret, TCGv source1, TCGv source2)
 {
-    TCGv cond1, zeroreg, resultopt1;
+    TCGv cond1, zeroreg, resultopt1, t2;
     cond1 = tcg_temp_new();
     zeroreg = tcg_constant_tl(0);
     resultopt1 = tcg_temp_new();
+    t2 = tcg_temp_new();
 
     tcg_gen_movi_tl(resultopt1, (target_ulong)1);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0);
-    tcg_gen_movcond_tl(TCG_COND_EQ, source2, cond1, zeroreg, source2,
-            resultopt1);
-    tcg_gen_remu_tl(resultopt1, source1, source2);
+    tcg_gen_movcond_tl(TCG_COND_EQ, t2, cond1, zeroreg, source2, resultopt1);
+    tcg_gen_remu_tl(resultopt1, source1, t2);
     /* if div by zero, just return the original dividend */
     tcg_gen_movcond_tl(TCG_COND_EQ, ret, cond1, zeroreg, resultopt1,
             source1);
 
     tcg_temp_free(cond1);
     tcg_temp_free(resultopt1);
+    tcg_temp_free(t2);
 }
 
 static void gen_jal(DisasContext *ctx, int rd, target_ulong imm)
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 07/13] target/riscv: Support UXL32 for RVM
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvm.c.inc | 24 ++++++++---
 target/riscv/translate.c                | 56 +++++++++++++++++++------
 2 files changed, 62 insertions(+), 18 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvm.c.inc b/target/riscv/insn_trans/trans_rvm.c.inc
index 34220b824d..121d592351 100644
--- a/target/riscv/insn_trans/trans_rvm.c.inc
+++ b/target/riscv/insn_trans/trans_rvm.c.inc
@@ -28,43 +28,55 @@ static bool trans_mul(DisasContext *ctx, arg_mul *a)
 static bool trans_mulh(DisasContext *ctx, arg_mulh *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, gen_mulh);
+    return gen_arith_s(ctx, a, gen_mulh);
 }
 
 static bool trans_mulhsu(DisasContext *ctx, arg_mulhsu *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_mulhsu);
+    return gen_arith_su(ctx, a, &gen_mulhsu);
 }
 
 static bool trans_mulhu(DisasContext *ctx, arg_mulhu *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, gen_mulhu);
+    return gen_arith_u(ctx, a, gen_mulhu);
 }
 
 static bool trans_div(DisasContext *ctx, arg_div *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_div);
+    if (ctx->uxl32) {
+        return trans_divw(ctx, a);
+    }
+    return gen_arith_div(ctx, a, &gen_div);
 }
 
 static bool trans_divu(DisasContext *ctx, arg_divu *a)
 {
     REQUIRE_EXT(ctx, RVM);
+    if (ctx->uxl32) {
+        return trans_divuw(ctx, a);
+    }
     return gen_arith(ctx, a, &gen_divu);
 }
 
 static bool trans_rem(DisasContext *ctx, arg_rem *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_rem);
+    if (ctx->uxl32) {
+        return trans_remw(ctx, a);
+    }
+    return gen_arith_div(ctx, a, &gen_rem);
 }
 
 static bool trans_remu(DisasContext *ctx, arg_remu *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_remu);
+    if (ctx->uxl32) {
+        return trans_remuw(ctx, a);
+    }
+    return gen_arith_u(ctx, a, &gen_remu);
 }
 
 static bool trans_mulw(DisasContext *ctx, arg_mulw *a)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 2892eaa9a7..160a2df629 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -254,16 +254,14 @@ static void gen_mulhsu(TCGv ret, TCGv arg1, TCGv arg2)
     TCGv rh = tcg_temp_new();
 
     tcg_gen_mulu2_tl(rl, rh, arg1, arg2);
-    /* fix up for one negative */
-    tcg_gen_sari_tl(rl, arg1, TARGET_LONG_BITS - 1);
-    tcg_gen_and_tl(rl, rl, arg2);
-    tcg_gen_sub_tl(ret, rh, rl);
+    tcg_gen_sub_tl(rl, rh, arg2);
+    tcg_gen_movcond_tl(TCG_COND_LT, ret, arg1, tcg_constant_tl(0), rl, rh);
 
     tcg_temp_free(rl);
     tcg_temp_free(rh);
 }
 
-static void gen_div(TCGv ret, TCGv source1, TCGv source2)
+static void gen_div(DisasContext *ctx, TCGv ret, TCGv source1, TCGv source2)
 {
     TCGv cond1, cond2, zeroreg, resultopt1, t1, t2;
     /*
@@ -280,8 +278,14 @@ static void gen_div(TCGv ret, TCGv source1, TCGv source2)
 
     tcg_gen_movi_tl(resultopt1, (target_ulong)-1);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)(~0L));
-    tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
-                        ((target_ulong)1) << (TARGET_LONG_BITS - 1));
+
+    if (ctx->uxl32) {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1, INT32_MIN);
+    } else {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
+                            ((target_ulong)1) << (TARGET_LONG_BITS - 1));
+    }
+
     tcg_gen_and_tl(cond1, cond1, cond2); /* cond1 = overflow */
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, 0); /* cond2 = div 0 */
     /* if div by zero, set source1 to -1, otherwise don't change */
@@ -322,7 +326,7 @@ static void gen_divu(TCGv ret, TCGv source1, TCGv source2)
     tcg_temp_free(t2);
 }
 
-static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
+static void gen_rem(DisasContext *ctx, TCGv ret, TCGv source1, TCGv source2)
 {
     TCGv cond1, cond2, zeroreg, resultopt1, t2;
 
@@ -334,8 +338,14 @@ static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
 
     tcg_gen_movi_tl(resultopt1, 1L);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)-1);
-    tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
-                        (target_ulong)1 << (TARGET_LONG_BITS - 1));
+
+    if (ctx->uxl32) {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1, INT32_MIN);
+    } else {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
+                            ((target_long)1) << (TARGET_LONG_BITS - 1));
+    }
+
     tcg_gen_and_tl(cond2, cond1, cond2); /* cond1 = overflow */
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0); /* cond2 = div 0 */
     /* if overflow or div by zero, set source2 to 1, else don't change */
@@ -541,7 +551,7 @@ static void gen_mulw(TCGv ret, TCGv arg1, TCGv arg2)
 }
 
 static bool gen_arith_div_w(DisasContext *ctx, arg_r *a,
-                            void(*func)(TCGv, TCGv, TCGv))
+                            void(*func)(DisasContext *, TCGv, TCGv, TCGv))
 {
     TCGv dest = gpr_dst(ctx, a->rd);
     TCGv src1 = gpr_src(ctx, a->rs1);
@@ -552,7 +562,7 @@ static bool gen_arith_div_w(DisasContext *ctx, arg_r *a,
     tcg_gen_ext32s_tl(ext1, src1);
     tcg_gen_ext32s_tl(ext2, src2);
 
-    (*func)(dest, ext1, ext2);
+    (*func)(ctx, dest, ext1, ext2);
     tcg_temp_free(ext1);
     tcg_temp_free(ext2);
 
@@ -829,6 +839,28 @@ static bool gen_arith_s(DisasContext *ctx, arg_r *a,
     return true;
 }
 
+static bool gen_arith_su(DisasContext *ctx, arg_r *a,
+                         void(*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
+static bool gen_arith_div(DisasContext *ctx, arg_r *a,
+                          void(*func)(DisasContext *, TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = gpr_src_s(ctx, a->rs2);
+
+    (*func)(ctx, dest, src1, src2);
+    return true;
+}
+
 static bool gen_shift(DisasContext *ctx, arg_r *a,
                         void(*func)(TCGv, TCGv, TCGv))
 {
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 07/13] target/riscv: Support UXL32 for RVM
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvm.c.inc | 24 ++++++++---
 target/riscv/translate.c                | 56 +++++++++++++++++++------
 2 files changed, 62 insertions(+), 18 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvm.c.inc b/target/riscv/insn_trans/trans_rvm.c.inc
index 34220b824d..121d592351 100644
--- a/target/riscv/insn_trans/trans_rvm.c.inc
+++ b/target/riscv/insn_trans/trans_rvm.c.inc
@@ -28,43 +28,55 @@ static bool trans_mul(DisasContext *ctx, arg_mul *a)
 static bool trans_mulh(DisasContext *ctx, arg_mulh *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, gen_mulh);
+    return gen_arith_s(ctx, a, gen_mulh);
 }
 
 static bool trans_mulhsu(DisasContext *ctx, arg_mulhsu *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_mulhsu);
+    return gen_arith_su(ctx, a, &gen_mulhsu);
 }
 
 static bool trans_mulhu(DisasContext *ctx, arg_mulhu *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, gen_mulhu);
+    return gen_arith_u(ctx, a, gen_mulhu);
 }
 
 static bool trans_div(DisasContext *ctx, arg_div *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_div);
+    if (ctx->uxl32) {
+        return trans_divw(ctx, a);
+    }
+    return gen_arith_div(ctx, a, &gen_div);
 }
 
 static bool trans_divu(DisasContext *ctx, arg_divu *a)
 {
     REQUIRE_EXT(ctx, RVM);
+    if (ctx->uxl32) {
+        return trans_divuw(ctx, a);
+    }
     return gen_arith(ctx, a, &gen_divu);
 }
 
 static bool trans_rem(DisasContext *ctx, arg_rem *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_rem);
+    if (ctx->uxl32) {
+        return trans_remw(ctx, a);
+    }
+    return gen_arith_div(ctx, a, &gen_rem);
 }
 
 static bool trans_remu(DisasContext *ctx, arg_remu *a)
 {
     REQUIRE_EXT(ctx, RVM);
-    return gen_arith(ctx, a, &gen_remu);
+    if (ctx->uxl32) {
+        return trans_remuw(ctx, a);
+    }
+    return gen_arith_u(ctx, a, &gen_remu);
 }
 
 static bool trans_mulw(DisasContext *ctx, arg_mulw *a)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 2892eaa9a7..160a2df629 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -254,16 +254,14 @@ static void gen_mulhsu(TCGv ret, TCGv arg1, TCGv arg2)
     TCGv rh = tcg_temp_new();
 
     tcg_gen_mulu2_tl(rl, rh, arg1, arg2);
-    /* fix up for one negative */
-    tcg_gen_sari_tl(rl, arg1, TARGET_LONG_BITS - 1);
-    tcg_gen_and_tl(rl, rl, arg2);
-    tcg_gen_sub_tl(ret, rh, rl);
+    tcg_gen_sub_tl(rl, rh, arg2);
+    tcg_gen_movcond_tl(TCG_COND_LT, ret, arg1, tcg_constant_tl(0), rl, rh);
 
     tcg_temp_free(rl);
     tcg_temp_free(rh);
 }
 
-static void gen_div(TCGv ret, TCGv source1, TCGv source2)
+static void gen_div(DisasContext *ctx, TCGv ret, TCGv source1, TCGv source2)
 {
     TCGv cond1, cond2, zeroreg, resultopt1, t1, t2;
     /*
@@ -280,8 +278,14 @@ static void gen_div(TCGv ret, TCGv source1, TCGv source2)
 
     tcg_gen_movi_tl(resultopt1, (target_ulong)-1);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)(~0L));
-    tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
-                        ((target_ulong)1) << (TARGET_LONG_BITS - 1));
+
+    if (ctx->uxl32) {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1, INT32_MIN);
+    } else {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
+                            ((target_ulong)1) << (TARGET_LONG_BITS - 1));
+    }
+
     tcg_gen_and_tl(cond1, cond1, cond2); /* cond1 = overflow */
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, 0); /* cond2 = div 0 */
     /* if div by zero, set source1 to -1, otherwise don't change */
@@ -322,7 +326,7 @@ static void gen_divu(TCGv ret, TCGv source1, TCGv source2)
     tcg_temp_free(t2);
 }
 
-static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
+static void gen_rem(DisasContext *ctx, TCGv ret, TCGv source1, TCGv source2)
 {
     TCGv cond1, cond2, zeroreg, resultopt1, t2;
 
@@ -334,8 +338,14 @@ static void gen_rem(TCGv ret, TCGv source1, TCGv source2)
 
     tcg_gen_movi_tl(resultopt1, 1L);
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond2, source2, (target_ulong)-1);
-    tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
-                        (target_ulong)1 << (TARGET_LONG_BITS - 1));
+
+    if (ctx->uxl32) {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1, INT32_MIN);
+    } else {
+        tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source1,
+                            ((target_long)1) << (TARGET_LONG_BITS - 1));
+    }
+
     tcg_gen_and_tl(cond2, cond1, cond2); /* cond1 = overflow */
     tcg_gen_setcondi_tl(TCG_COND_EQ, cond1, source2, 0); /* cond2 = div 0 */
     /* if overflow or div by zero, set source2 to 1, else don't change */
@@ -541,7 +551,7 @@ static void gen_mulw(TCGv ret, TCGv arg1, TCGv arg2)
 }
 
 static bool gen_arith_div_w(DisasContext *ctx, arg_r *a,
-                            void(*func)(TCGv, TCGv, TCGv))
+                            void(*func)(DisasContext *, TCGv, TCGv, TCGv))
 {
     TCGv dest = gpr_dst(ctx, a->rd);
     TCGv src1 = gpr_src(ctx, a->rs1);
@@ -552,7 +562,7 @@ static bool gen_arith_div_w(DisasContext *ctx, arg_r *a,
     tcg_gen_ext32s_tl(ext1, src1);
     tcg_gen_ext32s_tl(ext2, src2);
 
-    (*func)(dest, ext1, ext2);
+    (*func)(ctx, dest, ext1, ext2);
     tcg_temp_free(ext1);
     tcg_temp_free(ext2);
 
@@ -829,6 +839,28 @@ static bool gen_arith_s(DisasContext *ctx, arg_r *a,
     return true;
 }
 
+static bool gen_arith_su(DisasContext *ctx, arg_r *a,
+                         void(*func)(TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
+
+    (*func)(dest, src1, src2);
+    return true;
+}
+
+static bool gen_arith_div(DisasContext *ctx, arg_r *a,
+                          void(*func)(DisasContext *, TCGv, TCGv, TCGv))
+{
+    TCGv dest = gpr_dst(ctx, a->rd);
+    TCGv src1 = gpr_src_s(ctx, a->rs1);
+    TCGv src2 = gpr_src_s(ctx, a->rs2);
+
+    (*func)(ctx, dest, src1, src2);
+    return true;
+}
+
 static bool gen_shift(DisasContext *ctx, arg_r *a,
                         void(*func)(TCGv, TCGv, TCGv))
 {
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 08/13] target/riscv: Support UXL32 for vector instructions
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

For integer operations, the scalar can be taken from the scalar x register
specified by rs1. If XLEN<SEW, the value from the x register is sign-extended
to SEW bits.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/cpu.h                      |  3 ++
 target/riscv/insn_trans/trans_rvv.c.inc | 44 ++++++++++++--------
 target/riscv/vector_helper.c            | 54 +++++++++++++++++--------
 3 files changed, 68 insertions(+), 33 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 2b3ba21a78..9c96a1e818 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -111,6 +111,9 @@ FIELD(VTYPE, VEDIV, 5, 2)
 FIELD(VTYPE, RESERVED, 7, sizeof(target_ulong) * 8 - 9)
 FIELD(VTYPE, VILL, sizeof(target_ulong) * 8 - 1, 1)
 
+FIELD(VTYPE, RESERVED_UXL32, 7, 23)
+FIELD(VTYPE, VILL_UXL32, 31, 1)
+
 struct CPURISCVState {
     target_ulong gpr[32];
     uint64_t fpr[32]; /* assume both F and D extensions */
diff --git a/target/riscv/insn_trans/trans_rvv.c.inc b/target/riscv/insn_trans/trans_rvv.c.inc
index 84a45fac38..732b8ab460 100644
--- a/target/riscv/insn_trans/trans_rvv.c.inc
+++ b/target/riscv/insn_trans/trans_rvv.c.inc
@@ -35,7 +35,7 @@ static bool trans_vsetvl(DisasContext *ctx, arg_vsetvl *a)
         /* As the mask is at least one bit, RV_VLEN_MAX is >= VLMAX */
         s1 = tcg_constant_tl(RV_VLEN_MAX);
     } else {
-        s1 = gpr_src(ctx, a->rs1);
+        s1 = gpr_src_u(ctx, a->rs1);
     }
     gen_helper_vsetvl(dst, cpu_env, s1, s2);
 
@@ -61,7 +61,7 @@ static bool trans_vsetvli(DisasContext *ctx, arg_vsetvli *a)
         /* As the mask is at least one bit, RV_VLEN_MAX is >= VLMAX */
         s1 = tcg_constant_tl(RV_VLEN_MAX);
     } else {
-        s1 = gpr_src(ctx, a->rs1);
+        s1 = gpr_src_u(ctx, a->rs1);
     }
     gen_helper_vsetvl(dst, cpu_env, s1, s2);
 
@@ -163,7 +163,7 @@ static bool ldst_us_trans(uint32_t vd, uint32_t rs1, uint32_t data,
 
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
 
     /*
      * As simd_desc supports at most 256 bytes, and in this implementation,
@@ -318,8 +318,8 @@ static bool ldst_stride_trans(uint32_t vd, uint32_t rs1, uint32_t rs2,
 
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
-    stride = gpr_src(s, rs2);
+    base = gpr_src_u(s, rs1);
+    stride = gpr_src_s(s, rs2);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -442,7 +442,7 @@ static bool ldst_index_trans(uint32_t vd, uint32_t rs1, uint32_t vs2,
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
     index = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -571,7 +571,7 @@ static bool ldff_trans(uint32_t vd, uint32_t rs1, uint32_t data,
 
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -645,7 +645,7 @@ static bool amo_trans(uint32_t vd, uint32_t rs1, uint32_t vs2,
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
     index = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -731,12 +731,13 @@ static bool amo_op(DisasContext *s, arg_rwdvm *a, uint8_t seq)
  */
 static bool amo_check(DisasContext *s, arg_rwdvm* a)
 {
-    return (!s->vill && has_ext(s, RVA) &&
-            (!a->wd || vext_check_overlap_mask(s, a->rd, a->vm, false)) &&
-            vext_check_reg(s, a->rd, false) &&
-            vext_check_reg(s, a->rs2, false) &&
-            ((1 << s->sew) <= sizeof(target_ulong)) &&
-            ((1 << s->sew) >= 4));
+    return !s->vill && has_ext(s, RVA) &&
+           (!a->wd || vext_check_overlap_mask(s, a->rd, a->vm, false)) &&
+           vext_check_reg(s, a->rd, false) &&
+           vext_check_reg(s, a->rs2, false) &&
+           (s->uxl32 ? ((1 << s->sew) == 4) :
+                       (((1 << s->sew) <= sizeof(target_ulong)) &&
+                        ((1 << s->sew) >= 4)));
 }
 
 static bool amo_check64(DisasContext *s, arg_rwdvm* a)
@@ -840,7 +841,7 @@ static bool opivx_trans(uint32_t vd, uint32_t rs1, uint32_t vs2, uint32_t vm,
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
     src2 = tcg_temp_new_ptr();
-    src1 = gpr_src(s, rs1);
+    src1 = gpr_src_s(s, rs1);
 
     data = FIELD_DP32(data, VDATA, MLEN, s->mlen);
     data = FIELD_DP32(data, VDATA, VM, vm);
@@ -882,7 +883,7 @@ do_opivx_gvec(DisasContext *s, arg_rmrr *a, GVecGen2sFn *gvec_fn,
     if (a->vm && s->vl_eq_vlmax) {
         TCGv_i64 src1 = tcg_temp_new_i64();
 
-        tcg_gen_ext_tl_i64(src1, gpr_src(s, a->rs1));
+        tcg_gen_ext_tl_i64(src1, gpr_src_s(s, a->rs1));
         gvec_fn(s->sew, vreg_ofs(s, a->rd), vreg_ofs(s, a->rs2),
                 src1, MAXSZ(s), MAXSZ(s));
 
@@ -1635,7 +1636,7 @@ static bool trans_vmv_v_x(DisasContext *s, arg_vmv_v_x *a)
         TCGLabel *over = gen_new_label();
         tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over);
 
-        s1 = gpr_src(s, a->rs1);
+        s1 = gpr_src_s(s, a->rs1);
 
         if (s->vl_eq_vlmax) {
             tcg_gen_gvec_dup_tl(s->sew, vreg_ofs(s, a->rd),
@@ -2609,6 +2610,9 @@ static bool trans_vext_x_v(DisasContext *s, arg_r *a)
     } else {
         /* This instruction ignores LMUL and vector register groups */
         int vlmax = s->vlen >> (3 + s->sew);
+        if (s->uxl32) {
+            tcg_gen_ext32u_tl(cpu_gpr[a->rs1], cpu_gpr[a->rs1]);
+        }
         vec_element_loadx(s, tmp, a->rs2, cpu_gpr[a->rs1], vlmax);
     }
 
@@ -2667,6 +2671,9 @@ static bool trans_vmv_s_x(DisasContext *s, arg_vmv_s_x *a)
         }
 
         t1 = tcg_temp_new_i64();
+        if (s->uxl32) {
+            tcg_gen_ext32u_tl(cpu_gpr[a->rs1], cpu_gpr[a->rs1]);
+        }
         tcg_gen_extu_tl_i64(t1, cpu_gpr[a->rs1]);
         vec_element_storei(s, a->rd, 0, t1);
         tcg_temp_free_i64(t1);
@@ -2780,6 +2787,9 @@ static bool trans_vrgather_vx(DisasContext *s, arg_rmrr *a)
         if (a->rs1 == 0) {
             vec_element_loadi(s, dest, a->rs2, 0);
         } else {
+            if (unlikely(s->uxl32)) {
+                tcg_gen_ext32u_tl(cpu_gpr[a->rs1], cpu_gpr[a->rs1]);
+            }
             vec_element_loadx(s, dest, a->rs2, cpu_gpr[a->rs1], vlmax);
         }
 
diff --git a/target/riscv/vector_helper.c b/target/riscv/vector_helper.c
index 12c31aa4b4..4babd1b6aa 100644
--- a/target/riscv/vector_helper.c
+++ b/target/riscv/vector_helper.c
@@ -35,10 +35,19 @@ target_ulong HELPER(vsetvl)(CPURISCVState *env, target_ulong s1,
     uint8_t ediv = FIELD_EX64(s2, VTYPE, VEDIV);
     bool vill = FIELD_EX64(s2, VTYPE, VILL);
     target_ulong reserved = FIELD_EX64(s2, VTYPE, RESERVED);
+    bool uxl32 = riscv_cpu_is_uxl32(env);
 
+    if (uxl32) {
+        vill = FIELD_EX64(s2, VTYPE, VILL_UXL32);
+        reserved = FIELD_EX64(s2, VTYPE, RESERVED_UXL32);
+    }
     if ((sew > cpu->cfg.elen) || vill || (ediv != 0) || (reserved != 0)) {
         /* only set vill bit. */
-        env->vtype = FIELD_DP64(0, VTYPE, VILL, 1);
+        if (uxl32) {
+            env->vtype = FIELD_DP64(0, VTYPE, VILL_UXL32, 1);
+        } else {
+            env->vtype = FIELD_DP64(0, VTYPE, VILL, 1);
+        }
         env->vl = 0;
         env->vstart = 0;
         return 0;
@@ -479,14 +488,18 @@ GEN_VEXT_ST_US(vse_v_d, int64_t, int64_t, ste_d)
 /*
  *** index: access vector element from indexed memory
  */
-typedef target_ulong vext_get_index_addr(target_ulong base,
-        uint32_t idx, void *vs2);
+typedef target_ulong vext_get_index_addr(bool uxl32, target_ulong base,
+                                         uint32_t idx, void *vs2);
 
-#define GEN_VEXT_GET_INDEX_ADDR(NAME, ETYPE, H)        \
-static target_ulong NAME(target_ulong base,            \
-                         uint32_t idx, void *vs2)      \
-{                                                      \
-    return (base + *((ETYPE *)vs2 + H(idx)));          \
+#define GEN_VEXT_GET_INDEX_ADDR(NAME, ETYPE, H)                 \
+static target_ulong NAME(bool uxl32, target_ulong base,         \
+                         uint32_t idx, void *vs2)               \
+{                                                               \
+    if (uxl32) {                                                \
+        return base + (int32_t)(*((ETYPE *)vs2 + H(idx)));      \
+    } else {                                                    \
+        return base + *((ETYPE *)vs2 + H(idx));                 \
+    }                                                           \
 }
 
 GEN_VEXT_GET_INDEX_ADDR(idx_b, int8_t,  H1)
@@ -508,13 +521,14 @@ vext_ldst_index(void *vd, void *v0, target_ulong base,
     uint32_t vm = vext_vm(desc);
     uint32_t mlen = vext_mlen(desc);
     uint32_t vlmax = vext_maxsz(desc) / esz;
+    bool uxl32 = riscv_cpu_is_uxl32(env);
 
     /* probe every access*/
     for (i = 0; i < env->vl; i++) {
         if (!vm && !vext_elem_mask(v0, mlen, i)) {
             continue;
         }
-        probe_pages(env, get_index_addr(base, i, vs2), nf * msz, ra,
+        probe_pages(env, get_index_addr(uxl32, base, i, vs2), nf * msz, ra,
                     access_type);
     }
     /* load bytes from guest memory */
@@ -524,7 +538,7 @@ vext_ldst_index(void *vd, void *v0, target_ulong base,
             continue;
         }
         while (k < nf) {
-            abi_ptr addr = get_index_addr(base, i, vs2) + k * msz;
+            abi_ptr addr = get_index_addr(uxl32, base, i, vs2) + k * msz;
             ldst_elem(env, addr, i + k * vlmax, vd, ra);
             k++;
         }
@@ -784,19 +798,22 @@ vext_amo_noatomic(void *vs3, void *v0, target_ulong base,
     uint32_t vm = vext_vm(desc);
     uint32_t mlen = vext_mlen(desc);
     uint32_t vlmax = vext_maxsz(desc) / esz;
+    bool uxl32 = riscv_cpu_is_uxl32(env);
 
     for (i = 0; i < env->vl; i++) {
         if (!vm && !vext_elem_mask(v0, mlen, i)) {
             continue;
         }
-        probe_pages(env, get_index_addr(base, i, vs2), msz, ra, MMU_DATA_LOAD);
-        probe_pages(env, get_index_addr(base, i, vs2), msz, ra, MMU_DATA_STORE);
+        probe_pages(env, get_index_addr(uxl32, base, i, vs2), msz, ra,
+                    MMU_DATA_LOAD);
+        probe_pages(env, get_index_addr(uxl32, base, i, vs2), msz, ra,
+                    MMU_DATA_STORE);
     }
     for (i = 0; i < env->vl; i++) {
         if (!vm && !vext_elem_mask(v0, mlen, i)) {
             continue;
         }
-        addr = get_index_addr(base, i, vs2);
+        addr = get_index_addr(uxl32, base, i, vs2);
         noatomic_op(vs3, addr, wd, i, env, ra);
     }
     clear_elem(vs3, env->vl, env->vl * esz, vlmax * esz);
@@ -4682,7 +4699,8 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vlmax = env_archcpu(env)->cfg.vlen / mlen;                   \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
-    target_ulong offset = s1, i;                                          \
+    target_ulong offset, i;                                               \
+    offset = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;              \
                                                                           \
     for (i = offset; i < vl; i++) {                                       \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
@@ -4707,7 +4725,8 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vlmax = env_archcpu(env)->cfg.vlen / mlen;                   \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
-    target_ulong offset = s1, i;                                          \
+    target_ulong offset, i;                                               \
+    offset = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;              \
                                                                           \
     for (i = 0; i < vl; ++i) {                                            \
         target_ulong j = i + offset;                                      \
@@ -4734,6 +4753,7 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
     uint32_t i;                                                           \
+    s1 = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;                  \
                                                                           \
     for (i = 0; i < vl; i++) {                                            \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
@@ -4763,6 +4783,7 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
     uint32_t i;                                                           \
+    s1 = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;                  \
                                                                           \
     for (i = 0; i < vl; i++) {                                            \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
@@ -4823,8 +4844,9 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vlmax = env_archcpu(env)->cfg.vlen / mlen;                   \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
-    uint64_t index = s1;                                                  \
+    uint64_t index;                                                       \
     uint32_t i;                                                           \
+    index = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;               \
                                                                           \
     for (i = 0; i < vl; i++) {                                            \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 08/13] target/riscv: Support UXL32 for vector instructions
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

For integer operations, the scalar can be taken from the scalar x register
specified by rs1. If XLEN<SEW, the value from the x register is sign-extended
to SEW bits.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/cpu.h                      |  3 ++
 target/riscv/insn_trans/trans_rvv.c.inc | 44 ++++++++++++--------
 target/riscv/vector_helper.c            | 54 +++++++++++++++++--------
 3 files changed, 68 insertions(+), 33 deletions(-)

diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
index 2b3ba21a78..9c96a1e818 100644
--- a/target/riscv/cpu.h
+++ b/target/riscv/cpu.h
@@ -111,6 +111,9 @@ FIELD(VTYPE, VEDIV, 5, 2)
 FIELD(VTYPE, RESERVED, 7, sizeof(target_ulong) * 8 - 9)
 FIELD(VTYPE, VILL, sizeof(target_ulong) * 8 - 1, 1)
 
+FIELD(VTYPE, RESERVED_UXL32, 7, 23)
+FIELD(VTYPE, VILL_UXL32, 31, 1)
+
 struct CPURISCVState {
     target_ulong gpr[32];
     uint64_t fpr[32]; /* assume both F and D extensions */
diff --git a/target/riscv/insn_trans/trans_rvv.c.inc b/target/riscv/insn_trans/trans_rvv.c.inc
index 84a45fac38..732b8ab460 100644
--- a/target/riscv/insn_trans/trans_rvv.c.inc
+++ b/target/riscv/insn_trans/trans_rvv.c.inc
@@ -35,7 +35,7 @@ static bool trans_vsetvl(DisasContext *ctx, arg_vsetvl *a)
         /* As the mask is at least one bit, RV_VLEN_MAX is >= VLMAX */
         s1 = tcg_constant_tl(RV_VLEN_MAX);
     } else {
-        s1 = gpr_src(ctx, a->rs1);
+        s1 = gpr_src_u(ctx, a->rs1);
     }
     gen_helper_vsetvl(dst, cpu_env, s1, s2);
 
@@ -61,7 +61,7 @@ static bool trans_vsetvli(DisasContext *ctx, arg_vsetvli *a)
         /* As the mask is at least one bit, RV_VLEN_MAX is >= VLMAX */
         s1 = tcg_constant_tl(RV_VLEN_MAX);
     } else {
-        s1 = gpr_src(ctx, a->rs1);
+        s1 = gpr_src_u(ctx, a->rs1);
     }
     gen_helper_vsetvl(dst, cpu_env, s1, s2);
 
@@ -163,7 +163,7 @@ static bool ldst_us_trans(uint32_t vd, uint32_t rs1, uint32_t data,
 
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
 
     /*
      * As simd_desc supports at most 256 bytes, and in this implementation,
@@ -318,8 +318,8 @@ static bool ldst_stride_trans(uint32_t vd, uint32_t rs1, uint32_t rs2,
 
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
-    stride = gpr_src(s, rs2);
+    base = gpr_src_u(s, rs1);
+    stride = gpr_src_s(s, rs2);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -442,7 +442,7 @@ static bool ldst_index_trans(uint32_t vd, uint32_t rs1, uint32_t vs2,
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
     index = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -571,7 +571,7 @@ static bool ldff_trans(uint32_t vd, uint32_t rs1, uint32_t data,
 
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -645,7 +645,7 @@ static bool amo_trans(uint32_t vd, uint32_t rs1, uint32_t vs2,
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
     index = tcg_temp_new_ptr();
-    base = gpr_src(s, rs1);
+    base = gpr_src_u(s, rs1);
     desc = tcg_constant_i32(simd_desc(s->vlen / 8, s->vlen / 8, data));
 
     tcg_gen_addi_ptr(dest, cpu_env, vreg_ofs(s, vd));
@@ -731,12 +731,13 @@ static bool amo_op(DisasContext *s, arg_rwdvm *a, uint8_t seq)
  */
 static bool amo_check(DisasContext *s, arg_rwdvm* a)
 {
-    return (!s->vill && has_ext(s, RVA) &&
-            (!a->wd || vext_check_overlap_mask(s, a->rd, a->vm, false)) &&
-            vext_check_reg(s, a->rd, false) &&
-            vext_check_reg(s, a->rs2, false) &&
-            ((1 << s->sew) <= sizeof(target_ulong)) &&
-            ((1 << s->sew) >= 4));
+    return !s->vill && has_ext(s, RVA) &&
+           (!a->wd || vext_check_overlap_mask(s, a->rd, a->vm, false)) &&
+           vext_check_reg(s, a->rd, false) &&
+           vext_check_reg(s, a->rs2, false) &&
+           (s->uxl32 ? ((1 << s->sew) == 4) :
+                       (((1 << s->sew) <= sizeof(target_ulong)) &&
+                        ((1 << s->sew) >= 4)));
 }
 
 static bool amo_check64(DisasContext *s, arg_rwdvm* a)
@@ -840,7 +841,7 @@ static bool opivx_trans(uint32_t vd, uint32_t rs1, uint32_t vs2, uint32_t vm,
     dest = tcg_temp_new_ptr();
     mask = tcg_temp_new_ptr();
     src2 = tcg_temp_new_ptr();
-    src1 = gpr_src(s, rs1);
+    src1 = gpr_src_s(s, rs1);
 
     data = FIELD_DP32(data, VDATA, MLEN, s->mlen);
     data = FIELD_DP32(data, VDATA, VM, vm);
@@ -882,7 +883,7 @@ do_opivx_gvec(DisasContext *s, arg_rmrr *a, GVecGen2sFn *gvec_fn,
     if (a->vm && s->vl_eq_vlmax) {
         TCGv_i64 src1 = tcg_temp_new_i64();
 
-        tcg_gen_ext_tl_i64(src1, gpr_src(s, a->rs1));
+        tcg_gen_ext_tl_i64(src1, gpr_src_s(s, a->rs1));
         gvec_fn(s->sew, vreg_ofs(s, a->rd), vreg_ofs(s, a->rs2),
                 src1, MAXSZ(s), MAXSZ(s));
 
@@ -1635,7 +1636,7 @@ static bool trans_vmv_v_x(DisasContext *s, arg_vmv_v_x *a)
         TCGLabel *over = gen_new_label();
         tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over);
 
-        s1 = gpr_src(s, a->rs1);
+        s1 = gpr_src_s(s, a->rs1);
 
         if (s->vl_eq_vlmax) {
             tcg_gen_gvec_dup_tl(s->sew, vreg_ofs(s, a->rd),
@@ -2609,6 +2610,9 @@ static bool trans_vext_x_v(DisasContext *s, arg_r *a)
     } else {
         /* This instruction ignores LMUL and vector register groups */
         int vlmax = s->vlen >> (3 + s->sew);
+        if (s->uxl32) {
+            tcg_gen_ext32u_tl(cpu_gpr[a->rs1], cpu_gpr[a->rs1]);
+        }
         vec_element_loadx(s, tmp, a->rs2, cpu_gpr[a->rs1], vlmax);
     }
 
@@ -2667,6 +2671,9 @@ static bool trans_vmv_s_x(DisasContext *s, arg_vmv_s_x *a)
         }
 
         t1 = tcg_temp_new_i64();
+        if (s->uxl32) {
+            tcg_gen_ext32u_tl(cpu_gpr[a->rs1], cpu_gpr[a->rs1]);
+        }
         tcg_gen_extu_tl_i64(t1, cpu_gpr[a->rs1]);
         vec_element_storei(s, a->rd, 0, t1);
         tcg_temp_free_i64(t1);
@@ -2780,6 +2787,9 @@ static bool trans_vrgather_vx(DisasContext *s, arg_rmrr *a)
         if (a->rs1 == 0) {
             vec_element_loadi(s, dest, a->rs2, 0);
         } else {
+            if (unlikely(s->uxl32)) {
+                tcg_gen_ext32u_tl(cpu_gpr[a->rs1], cpu_gpr[a->rs1]);
+            }
             vec_element_loadx(s, dest, a->rs2, cpu_gpr[a->rs1], vlmax);
         }
 
diff --git a/target/riscv/vector_helper.c b/target/riscv/vector_helper.c
index 12c31aa4b4..4babd1b6aa 100644
--- a/target/riscv/vector_helper.c
+++ b/target/riscv/vector_helper.c
@@ -35,10 +35,19 @@ target_ulong HELPER(vsetvl)(CPURISCVState *env, target_ulong s1,
     uint8_t ediv = FIELD_EX64(s2, VTYPE, VEDIV);
     bool vill = FIELD_EX64(s2, VTYPE, VILL);
     target_ulong reserved = FIELD_EX64(s2, VTYPE, RESERVED);
+    bool uxl32 = riscv_cpu_is_uxl32(env);
 
+    if (uxl32) {
+        vill = FIELD_EX64(s2, VTYPE, VILL_UXL32);
+        reserved = FIELD_EX64(s2, VTYPE, RESERVED_UXL32);
+    }
     if ((sew > cpu->cfg.elen) || vill || (ediv != 0) || (reserved != 0)) {
         /* only set vill bit. */
-        env->vtype = FIELD_DP64(0, VTYPE, VILL, 1);
+        if (uxl32) {
+            env->vtype = FIELD_DP64(0, VTYPE, VILL_UXL32, 1);
+        } else {
+            env->vtype = FIELD_DP64(0, VTYPE, VILL, 1);
+        }
         env->vl = 0;
         env->vstart = 0;
         return 0;
@@ -479,14 +488,18 @@ GEN_VEXT_ST_US(vse_v_d, int64_t, int64_t, ste_d)
 /*
  *** index: access vector element from indexed memory
  */
-typedef target_ulong vext_get_index_addr(target_ulong base,
-        uint32_t idx, void *vs2);
+typedef target_ulong vext_get_index_addr(bool uxl32, target_ulong base,
+                                         uint32_t idx, void *vs2);
 
-#define GEN_VEXT_GET_INDEX_ADDR(NAME, ETYPE, H)        \
-static target_ulong NAME(target_ulong base,            \
-                         uint32_t idx, void *vs2)      \
-{                                                      \
-    return (base + *((ETYPE *)vs2 + H(idx)));          \
+#define GEN_VEXT_GET_INDEX_ADDR(NAME, ETYPE, H)                 \
+static target_ulong NAME(bool uxl32, target_ulong base,         \
+                         uint32_t idx, void *vs2)               \
+{                                                               \
+    if (uxl32) {                                                \
+        return base + (int32_t)(*((ETYPE *)vs2 + H(idx)));      \
+    } else {                                                    \
+        return base + *((ETYPE *)vs2 + H(idx));                 \
+    }                                                           \
 }
 
 GEN_VEXT_GET_INDEX_ADDR(idx_b, int8_t,  H1)
@@ -508,13 +521,14 @@ vext_ldst_index(void *vd, void *v0, target_ulong base,
     uint32_t vm = vext_vm(desc);
     uint32_t mlen = vext_mlen(desc);
     uint32_t vlmax = vext_maxsz(desc) / esz;
+    bool uxl32 = riscv_cpu_is_uxl32(env);
 
     /* probe every access*/
     for (i = 0; i < env->vl; i++) {
         if (!vm && !vext_elem_mask(v0, mlen, i)) {
             continue;
         }
-        probe_pages(env, get_index_addr(base, i, vs2), nf * msz, ra,
+        probe_pages(env, get_index_addr(uxl32, base, i, vs2), nf * msz, ra,
                     access_type);
     }
     /* load bytes from guest memory */
@@ -524,7 +538,7 @@ vext_ldst_index(void *vd, void *v0, target_ulong base,
             continue;
         }
         while (k < nf) {
-            abi_ptr addr = get_index_addr(base, i, vs2) + k * msz;
+            abi_ptr addr = get_index_addr(uxl32, base, i, vs2) + k * msz;
             ldst_elem(env, addr, i + k * vlmax, vd, ra);
             k++;
         }
@@ -784,19 +798,22 @@ vext_amo_noatomic(void *vs3, void *v0, target_ulong base,
     uint32_t vm = vext_vm(desc);
     uint32_t mlen = vext_mlen(desc);
     uint32_t vlmax = vext_maxsz(desc) / esz;
+    bool uxl32 = riscv_cpu_is_uxl32(env);
 
     for (i = 0; i < env->vl; i++) {
         if (!vm && !vext_elem_mask(v0, mlen, i)) {
             continue;
         }
-        probe_pages(env, get_index_addr(base, i, vs2), msz, ra, MMU_DATA_LOAD);
-        probe_pages(env, get_index_addr(base, i, vs2), msz, ra, MMU_DATA_STORE);
+        probe_pages(env, get_index_addr(uxl32, base, i, vs2), msz, ra,
+                    MMU_DATA_LOAD);
+        probe_pages(env, get_index_addr(uxl32, base, i, vs2), msz, ra,
+                    MMU_DATA_STORE);
     }
     for (i = 0; i < env->vl; i++) {
         if (!vm && !vext_elem_mask(v0, mlen, i)) {
             continue;
         }
-        addr = get_index_addr(base, i, vs2);
+        addr = get_index_addr(uxl32, base, i, vs2);
         noatomic_op(vs3, addr, wd, i, env, ra);
     }
     clear_elem(vs3, env->vl, env->vl * esz, vlmax * esz);
@@ -4682,7 +4699,8 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vlmax = env_archcpu(env)->cfg.vlen / mlen;                   \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
-    target_ulong offset = s1, i;                                          \
+    target_ulong offset, i;                                               \
+    offset = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;              \
                                                                           \
     for (i = offset; i < vl; i++) {                                       \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
@@ -4707,7 +4725,8 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vlmax = env_archcpu(env)->cfg.vlen / mlen;                   \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
-    target_ulong offset = s1, i;                                          \
+    target_ulong offset, i;                                               \
+    offset = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;              \
                                                                           \
     for (i = 0; i < vl; ++i) {                                            \
         target_ulong j = i + offset;                                      \
@@ -4734,6 +4753,7 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
     uint32_t i;                                                           \
+    s1 = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;                  \
                                                                           \
     for (i = 0; i < vl; i++) {                                            \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
@@ -4763,6 +4783,7 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
     uint32_t i;                                                           \
+    s1 = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;                  \
                                                                           \
     for (i = 0; i < vl; i++) {                                            \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
@@ -4823,8 +4844,9 @@ void HELPER(NAME)(void *vd, void *v0, target_ulong s1, void *vs2,         \
     uint32_t vlmax = env_archcpu(env)->cfg.vlen / mlen;                   \
     uint32_t vm = vext_vm(desc);                                          \
     uint32_t vl = env->vl;                                                \
-    uint64_t index = s1;                                                  \
+    uint64_t index;                                                       \
     uint32_t i;                                                           \
+    index = riscv_cpu_is_uxl32(env) ? s1 & UINT32_MAX : s1;               \
                                                                           \
     for (i = 0; i < vl; i++) {                                            \
         if (!vm && !vext_elem_mask(v0, mlen, i)) {                        \
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 09/13] target/riscv: Support UXL32 for atomic instructions
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Only load or store 32 bits data for atomic instructions when UXL32.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rva.c.inc | 36 ++++++++++++++++++++-----
 1 file changed, 30 insertions(+), 6 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rva.c.inc b/target/riscv/insn_trans/trans_rva.c.inc
index 5bb5bbd09c..07c94416e5 100644
--- a/target/riscv/insn_trans/trans_rva.c.inc
+++ b/target/riscv/insn_trans/trans_rva.c.inc
@@ -20,12 +20,19 @@
 
 static bool gen_lr(DisasContext *ctx, arg_atomic *a, MemOp mop)
 {
-    TCGv src1 = gpr_src(ctx, a->rs1);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
 
     /* Put addr in load_res, data in load_val.  */
     if (a->rl) {
         tcg_gen_mb(TCG_MO_ALL | TCG_BAR_STRL);
     }
+    if (ctx->uxl32) {
+        TCGv_i32 val = tcg_temp_new_i32();
+        tcg_gen_qemu_ld_i32(val, src1, ctx->mem_idx, mop);
+        tcg_gen_extu_i32_tl(load_val, val);
+    } else {
+        tcg_gen_qemu_ld_tl(load_val, src1, ctx->mem_idx, mop);
+    }
     tcg_gen_qemu_ld_tl(load_val, src1, ctx->mem_idx, mop);
     if (a->aq) {
         tcg_gen_mb(TCG_MO_ALL | TCG_BAR_LDAQ);
@@ -39,8 +46,8 @@ static bool gen_lr(DisasContext *ctx, arg_atomic *a, MemOp mop)
 static bool gen_sc(DisasContext *ctx, arg_atomic *a, MemOp mop)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-    TCGv src1 = gpr_src(ctx, a->rs1);
-    TCGv src2 = gpr_src(ctx, a->rs2);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
     TCGLabel *l1 = gen_new_label();
     TCGLabel *l2 = gen_new_label();
 
@@ -50,8 +57,25 @@ static bool gen_sc(DisasContext *ctx, arg_atomic *a, MemOp mop)
      * Note that the TCG atomic primitives are SC,
      * so we can ignore AQ/RL along this path.
      */
-    tcg_gen_atomic_cmpxchg_tl(dest, load_res, load_val, src2,
-                              ctx->mem_idx, mop);
+    if (ctx->uxl32) {
+        TCGv_i32 retv, cmpv, newv;
+        retv = tcg_temp_new_i32();
+        cmpv = tcg_temp_new_i32();
+        newv = tcg_temp_new_i32();
+        tcg_gen_trunc_tl_i32(cmpv, load_val);
+        tcg_gen_trunc_tl_i32(newv, src2);
+
+        tcg_gen_atomic_cmpxchg_i32(retv, load_res, cmpv, newv,
+                                   ctx->mem_idx, mop);
+
+        tcg_gen_extu_i32_tl(dest, retv);
+        tcg_temp_free_i32(retv);
+        tcg_temp_free_i32(cmpv);
+        tcg_temp_free_i32(newv);
+    } else {
+        tcg_gen_atomic_cmpxchg_tl(dest, load_res, load_val, src2,
+                                  ctx->mem_idx, mop);
+    }
     tcg_gen_setcond_tl(TCG_COND_NE, dest, dest, load_val);
     tcg_gen_br(l2);
 
@@ -78,7 +102,7 @@ static bool gen_amo(DisasContext *ctx, arg_atomic *a,
                     MemOp mop)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-    TCGv src1 = gpr_src(ctx, a->rs1);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
     TCGv src2 = gpr_src(ctx, a->rs2);
 
     (*func)(dest, src1, src2, ctx->mem_idx, mop);
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 09/13] target/riscv: Support UXL32 for atomic instructions
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Only load or store 32 bits data for atomic instructions when UXL32.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rva.c.inc | 36 ++++++++++++++++++++-----
 1 file changed, 30 insertions(+), 6 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rva.c.inc b/target/riscv/insn_trans/trans_rva.c.inc
index 5bb5bbd09c..07c94416e5 100644
--- a/target/riscv/insn_trans/trans_rva.c.inc
+++ b/target/riscv/insn_trans/trans_rva.c.inc
@@ -20,12 +20,19 @@
 
 static bool gen_lr(DisasContext *ctx, arg_atomic *a, MemOp mop)
 {
-    TCGv src1 = gpr_src(ctx, a->rs1);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
 
     /* Put addr in load_res, data in load_val.  */
     if (a->rl) {
         tcg_gen_mb(TCG_MO_ALL | TCG_BAR_STRL);
     }
+    if (ctx->uxl32) {
+        TCGv_i32 val = tcg_temp_new_i32();
+        tcg_gen_qemu_ld_i32(val, src1, ctx->mem_idx, mop);
+        tcg_gen_extu_i32_tl(load_val, val);
+    } else {
+        tcg_gen_qemu_ld_tl(load_val, src1, ctx->mem_idx, mop);
+    }
     tcg_gen_qemu_ld_tl(load_val, src1, ctx->mem_idx, mop);
     if (a->aq) {
         tcg_gen_mb(TCG_MO_ALL | TCG_BAR_LDAQ);
@@ -39,8 +46,8 @@ static bool gen_lr(DisasContext *ctx, arg_atomic *a, MemOp mop)
 static bool gen_sc(DisasContext *ctx, arg_atomic *a, MemOp mop)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-    TCGv src1 = gpr_src(ctx, a->rs1);
-    TCGv src2 = gpr_src(ctx, a->rs2);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
+    TCGv src2 = gpr_src_u(ctx, a->rs2);
     TCGLabel *l1 = gen_new_label();
     TCGLabel *l2 = gen_new_label();
 
@@ -50,8 +57,25 @@ static bool gen_sc(DisasContext *ctx, arg_atomic *a, MemOp mop)
      * Note that the TCG atomic primitives are SC,
      * so we can ignore AQ/RL along this path.
      */
-    tcg_gen_atomic_cmpxchg_tl(dest, load_res, load_val, src2,
-                              ctx->mem_idx, mop);
+    if (ctx->uxl32) {
+        TCGv_i32 retv, cmpv, newv;
+        retv = tcg_temp_new_i32();
+        cmpv = tcg_temp_new_i32();
+        newv = tcg_temp_new_i32();
+        tcg_gen_trunc_tl_i32(cmpv, load_val);
+        tcg_gen_trunc_tl_i32(newv, src2);
+
+        tcg_gen_atomic_cmpxchg_i32(retv, load_res, cmpv, newv,
+                                   ctx->mem_idx, mop);
+
+        tcg_gen_extu_i32_tl(dest, retv);
+        tcg_temp_free_i32(retv);
+        tcg_temp_free_i32(cmpv);
+        tcg_temp_free_i32(newv);
+    } else {
+        tcg_gen_atomic_cmpxchg_tl(dest, load_res, load_val, src2,
+                                  ctx->mem_idx, mop);
+    }
     tcg_gen_setcond_tl(TCG_COND_NE, dest, dest, load_val);
     tcg_gen_br(l2);
 
@@ -78,7 +102,7 @@ static bool gen_amo(DisasContext *ctx, arg_atomic *a,
                     MemOp mop)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-    TCGv src1 = gpr_src(ctx, a->rs1);
+    TCGv src1 = gpr_src_u(ctx, a->rs1);
     TCGv src2 = gpr_src(ctx, a->rs2);
 
     (*func)(dest, src1, src2, ctx->mem_idx, mop);
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 10/13] target/riscv: Support UXL32 for float instructions
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvd.c.inc | 4 ++--
 target/riscv/insn_trans/trans_rvf.c.inc | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvd.c.inc b/target/riscv/insn_trans/trans_rvd.c.inc
index 9bb15fdc12..fb033ccd97 100644
--- a/target/riscv/insn_trans/trans_rvd.c.inc
+++ b/target/riscv/insn_trans/trans_rvd.c.inc
@@ -23,7 +23,7 @@ static bool trans_fld(DisasContext *ctx, arg_fld *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVD);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
@@ -46,7 +46,7 @@ static bool trans_fsd(DisasContext *ctx, arg_fsd *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVD);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
diff --git a/target/riscv/insn_trans/trans_rvf.c.inc b/target/riscv/insn_trans/trans_rvf.c.inc
index ff8e942199..4576072124 100644
--- a/target/riscv/insn_trans/trans_rvf.c.inc
+++ b/target/riscv/insn_trans/trans_rvf.c.inc
@@ -28,7 +28,7 @@ static bool trans_flw(DisasContext *ctx, arg_flw *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVF);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
@@ -53,7 +53,7 @@ static bool trans_fsw(DisasContext *ctx, arg_fsw *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVF);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 10/13] target/riscv: Support UXL32 for float instructions
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvd.c.inc | 4 ++--
 target/riscv/insn_trans/trans_rvf.c.inc | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvd.c.inc b/target/riscv/insn_trans/trans_rvd.c.inc
index 9bb15fdc12..fb033ccd97 100644
--- a/target/riscv/insn_trans/trans_rvd.c.inc
+++ b/target/riscv/insn_trans/trans_rvd.c.inc
@@ -23,7 +23,7 @@ static bool trans_fld(DisasContext *ctx, arg_fld *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVD);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
@@ -46,7 +46,7 @@ static bool trans_fsd(DisasContext *ctx, arg_fsd *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVD);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
diff --git a/target/riscv/insn_trans/trans_rvf.c.inc b/target/riscv/insn_trans/trans_rvf.c.inc
index ff8e942199..4576072124 100644
--- a/target/riscv/insn_trans/trans_rvf.c.inc
+++ b/target/riscv/insn_trans/trans_rvf.c.inc
@@ -28,7 +28,7 @@ static bool trans_flw(DisasContext *ctx, arg_flw *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVF);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
@@ -53,7 +53,7 @@ static bool trans_fsw(DisasContext *ctx, arg_fsw *a)
     REQUIRE_FPU;
     REQUIRE_EXT(ctx, RVF);
 
-    TCGv addr = gpr_src(ctx, a->rs1);
+    TCGv addr = gpr_src_u(ctx, a->rs1);
     TCGv temp = NULL;
 
     if (a->imm) {
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 11/13] target/riscv: Fix srow
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Always fill MSB 32 bits with 1s in source register before calling
gen_sro. Otherwise it may not only shift in 1s.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvb.c.inc | 4 ++--
 target/riscv/translate.c                | 7 +++++++
 2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvb.c.inc b/target/riscv/insn_trans/trans_rvb.c.inc
index 58921f3224..0bae0a2bbf 100644
--- a/target/riscv/insn_trans/trans_rvb.c.inc
+++ b/target/riscv/insn_trans/trans_rvb.c.inc
@@ -339,14 +339,14 @@ static bool trans_srow(DisasContext *ctx, arg_srow *a)
 {
     REQUIRE_64BIT(ctx);
     REQUIRE_EXT(ctx, RVB);
-    return gen_shiftw(ctx, a, gen_sro);
+    return gen_shiftw(ctx, a, gen_srow);
 }
 
 static bool trans_sroiw(DisasContext *ctx, arg_sroiw *a)
 {
     REQUIRE_64BIT(ctx);
     REQUIRE_EXT(ctx, RVB);
-    return gen_shiftiw(ctx, a, gen_sro);
+    return gen_shiftiw(ctx, a, gen_srow);
 }
 
 static bool trans_rorw(DisasContext *ctx, arg_rorw *a)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 160a2df629..5ee0feac4b 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -669,6 +669,13 @@ static void gen_sro(TCGv ret, TCGv arg1, TCGv arg2)
     tcg_gen_not_tl(ret, ret);
 }
 
+static void gen_srow(TCGv ret, TCGv arg1, TCGv arg2)
+{
+    TCGv ones = tcg_constant_tl(UINT32_MAX);
+    tcg_gen_deposit_tl(arg1, arg1, ones, 32, 32);
+    gen_sro(ret, arg1, arg2);
+}
+
 static bool gen_grevi(DisasContext *ctx, arg_grevi *a)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 11/13] target/riscv: Fix srow
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Always fill MSB 32 bits with 1s in source register before calling
gen_sro. Otherwise it may not only shift in 1s.

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvb.c.inc | 4 ++--
 target/riscv/translate.c                | 7 +++++++
 2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvb.c.inc b/target/riscv/insn_trans/trans_rvb.c.inc
index 58921f3224..0bae0a2bbf 100644
--- a/target/riscv/insn_trans/trans_rvb.c.inc
+++ b/target/riscv/insn_trans/trans_rvb.c.inc
@@ -339,14 +339,14 @@ static bool trans_srow(DisasContext *ctx, arg_srow *a)
 {
     REQUIRE_64BIT(ctx);
     REQUIRE_EXT(ctx, RVB);
-    return gen_shiftw(ctx, a, gen_sro);
+    return gen_shiftw(ctx, a, gen_srow);
 }
 
 static bool trans_sroiw(DisasContext *ctx, arg_sroiw *a)
 {
     REQUIRE_64BIT(ctx);
     REQUIRE_EXT(ctx, RVB);
-    return gen_shiftiw(ctx, a, gen_sro);
+    return gen_shiftiw(ctx, a, gen_srow);
 }
 
 static bool trans_rorw(DisasContext *ctx, arg_rorw *a)
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 160a2df629..5ee0feac4b 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -669,6 +669,13 @@ static void gen_sro(TCGv ret, TCGv arg1, TCGv arg2)
     tcg_gen_not_tl(ret, ret);
 }
 
+static void gen_srow(TCGv ret, TCGv arg1, TCGv arg2)
+{
+    TCGv ones = tcg_constant_tl(UINT32_MAX);
+    tcg_gen_deposit_tl(arg1, arg1, ones, 32, 32);
+    gen_sro(ret, arg1, arg2);
+}
+
 static bool gen_grevi(DisasContext *ctx, arg_grevi *a)
 {
     TCGv dest = gpr_dst(ctx, a->rd);
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 12/13] target/riscv: Support UXL32 for RVB
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvb.c.inc | 47 +++++++++++++++++++------
 target/riscv/translate.c                |  8 +++++
 2 files changed, 45 insertions(+), 10 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvb.c.inc b/target/riscv/insn_trans/trans_rvb.c.inc
index 0bae0a2bbf..5de24c3a24 100644
--- a/target/riscv/insn_trans/trans_rvb.c.inc
+++ b/target/riscv/insn_trans/trans_rvb.c.inc
@@ -20,19 +20,19 @@
 static bool trans_clz(DisasContext *ctx, arg_clz *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_unary(ctx, a, gen_clz);
+    return gen_unary(ctx, a, ctx->uxl32 ? gen_clzw : gen_clz);
 }
 
 static bool trans_ctz(DisasContext *ctx, arg_ctz *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_unary(ctx, a, gen_ctz);
+    return gen_unary(ctx, a, ctx->uxl32 ? gen_ctzw : gen_ctz);
 }
 
 static bool trans_cpop(DisasContext *ctx, arg_cpop *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_unary(ctx, a, tcg_gen_ctpop_tl);
+    return gen_unary(ctx, a, ctx->uxl32 ? gen_cpopw : tcg_gen_ctpop_tl);
 }
 
 static bool trans_andn(DisasContext *ctx, arg_andn *a)
@@ -56,43 +56,43 @@ static bool trans_xnor(DisasContext *ctx, arg_xnor *a)
 static bool trans_pack(DisasContext *ctx, arg_pack *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, gen_pack);
+    return gen_arith(ctx, a, ctx->uxl32 ? gen_packw : gen_pack);
 }
 
 static bool trans_packu(DisasContext *ctx, arg_packu *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, gen_packu);
+    return gen_arith(ctx, a, ctx->uxl32 ? gen_packuw : gen_packu);
 }
 
 static bool trans_packh(DisasContext *ctx, arg_packh *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, gen_packh);
+    return gen_arith(ctx, a, ctx->uxl32 ? gen_packhw : gen_packh);
 }
 
 static bool trans_min(DisasContext *ctx, arg_min *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_smin_tl);
+    return gen_arith_s(ctx, a, tcg_gen_smin_tl);
 }
 
 static bool trans_max(DisasContext *ctx, arg_max *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_smax_tl);
+    return gen_arith_s(ctx, a, tcg_gen_smax_tl);
 }
 
 static bool trans_minu(DisasContext *ctx, arg_minu *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_umin_tl);
+    return gen_arith_u(ctx, a, tcg_gen_umin_tl);
 }
 
 static bool trans_maxu(DisasContext *ctx, arg_maxu *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_umax_tl);
+    return gen_arith_u(ctx, a, tcg_gen_umax_tl);
 }
 
 static bool trans_sext_b(DisasContext *ctx, arg_sext_b *a)
@@ -170,36 +170,54 @@ static bool trans_sloi(DisasContext *ctx, arg_sloi *a)
 static bool trans_sro(DisasContext *ctx, arg_sro *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_srow(ctx, a);
+    }
     return gen_shift(ctx, a, gen_sro);
 }
 
 static bool trans_sroi(DisasContext *ctx, arg_sroi *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_sroiw(ctx, a);
+    }
     return gen_shifti(ctx, a, gen_sro);
 }
 
 static bool trans_ror(DisasContext *ctx, arg_ror *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_rorw(ctx, a);
+    }
     return gen_shift(ctx, a, tcg_gen_rotr_tl);
 }
 
 static bool trans_rori(DisasContext *ctx, arg_rori *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_roriw(ctx, a);
+    }
     return gen_shifti(ctx, a, tcg_gen_rotr_tl);
 }
 
 static bool trans_rol(DisasContext *ctx, arg_rol *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_rolw(ctx, a);
+    }
     return gen_shift(ctx, a, tcg_gen_rotl_tl);
 }
 
 static bool trans_grev(DisasContext *ctx, arg_grev *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_grevw(ctx, a);
+    }
     return gen_shift(ctx, a, gen_helper_grev);
 }
 
@@ -207,6 +225,9 @@ static bool trans_grevi(DisasContext *ctx, arg_grevi *a)
 {
     REQUIRE_EXT(ctx, RVB);
 
+    if (ctx->uxl32) {
+        return trans_grevi(ctx, a);
+    }
     if (a->shamt >= TARGET_LONG_BITS) {
         return false;
     }
@@ -217,12 +238,18 @@ static bool trans_grevi(DisasContext *ctx, arg_grevi *a)
 static bool trans_gorc(DisasContext *ctx, arg_gorc *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_gorcw(ctx, a);
+    }
     return gen_shift(ctx, a, gen_helper_gorc);
 }
 
 static bool trans_gorci(DisasContext *ctx, arg_gorci *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_gorciw(ctx, a);
+    }
     return gen_shifti(ctx, a, gen_helper_gorc);
 }
 
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 5ee0feac4b..f4b2f75812 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -742,6 +742,14 @@ static void gen_packuw(TCGv ret, TCGv arg1, TCGv arg2)
     tcg_temp_free(t);
 }
 
+static void gen_packhw(TCGv ret, TCGv arg1, TCGv arg2)
+{
+    TCGv t = tcg_temp_new();
+    tcg_gen_ext8u_tl(t, arg2);
+    tcg_gen_deposit_tl(ret, arg1, t, 8, 24);
+    tcg_temp_free(t);
+}
+
 static void gen_rorw(TCGv ret, TCGv arg1, TCGv arg2)
 {
     TCGv_i32 t1 = tcg_temp_new_i32();
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 12/13] target/riscv: Support UXL32 for RVB
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/insn_trans/trans_rvb.c.inc | 47 +++++++++++++++++++------
 target/riscv/translate.c                |  8 +++++
 2 files changed, 45 insertions(+), 10 deletions(-)

diff --git a/target/riscv/insn_trans/trans_rvb.c.inc b/target/riscv/insn_trans/trans_rvb.c.inc
index 0bae0a2bbf..5de24c3a24 100644
--- a/target/riscv/insn_trans/trans_rvb.c.inc
+++ b/target/riscv/insn_trans/trans_rvb.c.inc
@@ -20,19 +20,19 @@
 static bool trans_clz(DisasContext *ctx, arg_clz *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_unary(ctx, a, gen_clz);
+    return gen_unary(ctx, a, ctx->uxl32 ? gen_clzw : gen_clz);
 }
 
 static bool trans_ctz(DisasContext *ctx, arg_ctz *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_unary(ctx, a, gen_ctz);
+    return gen_unary(ctx, a, ctx->uxl32 ? gen_ctzw : gen_ctz);
 }
 
 static bool trans_cpop(DisasContext *ctx, arg_cpop *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_unary(ctx, a, tcg_gen_ctpop_tl);
+    return gen_unary(ctx, a, ctx->uxl32 ? gen_cpopw : tcg_gen_ctpop_tl);
 }
 
 static bool trans_andn(DisasContext *ctx, arg_andn *a)
@@ -56,43 +56,43 @@ static bool trans_xnor(DisasContext *ctx, arg_xnor *a)
 static bool trans_pack(DisasContext *ctx, arg_pack *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, gen_pack);
+    return gen_arith(ctx, a, ctx->uxl32 ? gen_packw : gen_pack);
 }
 
 static bool trans_packu(DisasContext *ctx, arg_packu *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, gen_packu);
+    return gen_arith(ctx, a, ctx->uxl32 ? gen_packuw : gen_packu);
 }
 
 static bool trans_packh(DisasContext *ctx, arg_packh *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, gen_packh);
+    return gen_arith(ctx, a, ctx->uxl32 ? gen_packhw : gen_packh);
 }
 
 static bool trans_min(DisasContext *ctx, arg_min *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_smin_tl);
+    return gen_arith_s(ctx, a, tcg_gen_smin_tl);
 }
 
 static bool trans_max(DisasContext *ctx, arg_max *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_smax_tl);
+    return gen_arith_s(ctx, a, tcg_gen_smax_tl);
 }
 
 static bool trans_minu(DisasContext *ctx, arg_minu *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_umin_tl);
+    return gen_arith_u(ctx, a, tcg_gen_umin_tl);
 }
 
 static bool trans_maxu(DisasContext *ctx, arg_maxu *a)
 {
     REQUIRE_EXT(ctx, RVB);
-    return gen_arith(ctx, a, tcg_gen_umax_tl);
+    return gen_arith_u(ctx, a, tcg_gen_umax_tl);
 }
 
 static bool trans_sext_b(DisasContext *ctx, arg_sext_b *a)
@@ -170,36 +170,54 @@ static bool trans_sloi(DisasContext *ctx, arg_sloi *a)
 static bool trans_sro(DisasContext *ctx, arg_sro *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_srow(ctx, a);
+    }
     return gen_shift(ctx, a, gen_sro);
 }
 
 static bool trans_sroi(DisasContext *ctx, arg_sroi *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_sroiw(ctx, a);
+    }
     return gen_shifti(ctx, a, gen_sro);
 }
 
 static bool trans_ror(DisasContext *ctx, arg_ror *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_rorw(ctx, a);
+    }
     return gen_shift(ctx, a, tcg_gen_rotr_tl);
 }
 
 static bool trans_rori(DisasContext *ctx, arg_rori *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_roriw(ctx, a);
+    }
     return gen_shifti(ctx, a, tcg_gen_rotr_tl);
 }
 
 static bool trans_rol(DisasContext *ctx, arg_rol *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_rolw(ctx, a);
+    }
     return gen_shift(ctx, a, tcg_gen_rotl_tl);
 }
 
 static bool trans_grev(DisasContext *ctx, arg_grev *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_grevw(ctx, a);
+    }
     return gen_shift(ctx, a, gen_helper_grev);
 }
 
@@ -207,6 +225,9 @@ static bool trans_grevi(DisasContext *ctx, arg_grevi *a)
 {
     REQUIRE_EXT(ctx, RVB);
 
+    if (ctx->uxl32) {
+        return trans_grevi(ctx, a);
+    }
     if (a->shamt >= TARGET_LONG_BITS) {
         return false;
     }
@@ -217,12 +238,18 @@ static bool trans_grevi(DisasContext *ctx, arg_grevi *a)
 static bool trans_gorc(DisasContext *ctx, arg_gorc *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_gorcw(ctx, a);
+    }
     return gen_shift(ctx, a, gen_helper_gorc);
 }
 
 static bool trans_gorci(DisasContext *ctx, arg_gorci *a)
 {
     REQUIRE_EXT(ctx, RVB);
+    if (ctx->uxl32) {
+        return trans_gorciw(ctx, a);
+    }
     return gen_shifti(ctx, a, gen_helper_gorc);
 }
 
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index 5ee0feac4b..f4b2f75812 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -742,6 +742,14 @@ static void gen_packuw(TCGv ret, TCGv arg1, TCGv arg2)
     tcg_temp_free(t);
 }
 
+static void gen_packhw(TCGv ret, TCGv arg1, TCGv arg2)
+{
+    TCGv t = tcg_temp_new();
+    tcg_gen_ext8u_tl(t, arg2);
+    tcg_gen_deposit_tl(ret, arg1, t, 8, 24);
+    tcg_temp_free(t);
+}
+
 static void gen_rorw(TCGv ret, TCGv arg1, TCGv arg2)
 {
     TCGv_i32 t1 = tcg_temp_new_i32();
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 13/13] target/riscv: Changing the width of U-mode CSR
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  2:53   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: palmer, richard.henderson, bin.meng, Alistair.Francis, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/csr.c | 42 +++++++++++++++++++++++++++++++++++++-----
 1 file changed, 37 insertions(+), 5 deletions(-)

diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 9a4ed18ac5..dc9807c0ff 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -297,7 +297,7 @@ static RISCVException read_vxrm(CPURISCVState *env, int csrno,
 static RISCVException write_vxrm(CPURISCVState *env, int csrno,
                                  target_ulong val)
 {
-    env->vxrm = val;
+    env->vxrm = riscv_cpu_is_uxl32(env) ? val & UINT32_MAX : val;
     return RISCV_EXCP_NONE;
 }
 
@@ -311,7 +311,7 @@ static RISCVException read_vxsat(CPURISCVState *env, int csrno,
 static RISCVException write_vxsat(CPURISCVState *env, int csrno,
                                   target_ulong val)
 {
-    env->vxsat = val;
+    env->vxsat = riscv_cpu_is_uxl32(env) ? val & UINT32_MAX : val;
     return RISCV_EXCP_NONE;
 }
 
@@ -325,7 +325,7 @@ static RISCVException read_vstart(CPURISCVState *env, int csrno,
 static RISCVException write_vstart(CPURISCVState *env, int csrno,
                                    target_ulong val)
 {
-    env->vstart = val;
+    env->vstart = riscv_cpu_is_uxl32(env) ? val & UINT32_MAX : val;
     return RISCV_EXCP_NONE;
 }
 
@@ -493,6 +493,36 @@ static int validate_vm(CPURISCVState *env, target_ulong vm)
     }
 }
 
+static void uxl32_switch(CPURISCVState *env, target_ulong val)
+{
+    uint32_t old = get_field(env->mstatus, MSTATUS64_UXL);
+    uint32_t new = get_field(val, MSTATUS64_UXL);
+
+    if (old == new) {
+        return;
+    }
+
+    /*
+     * For the read-only bits of the previous-width CSR, the bits at the
+     * same positions in the temporary register are set to zeros.
+     */
+    if (env->misa & RVV) {
+        env->vl = 0;
+        env->vtype = 0;
+    }
+
+    /*
+     * If the new width W is narrower than the previous width, the
+     * least-significant W bits of the temporary register are retained and
+     * the more-significant bits are discarded.
+     */
+    if ((old == 2) && (new == 1)) {
+        if (env->misa & RVV) {
+            env->vtype &= UINT32_MAX;
+        }
+    }
+}
+
 static RISCVException write_mstatus(CPURISCVState *env, int csrno,
                                     target_ulong val)
 {
@@ -502,13 +532,13 @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
 
     /* flush tlb on mstatus fields that affect VM */
     if ((val ^ mstatus) & (MSTATUS_MXR | MSTATUS_MPP | MSTATUS_MPV |
-            MSTATUS_MPRV | MSTATUS_SUM)) {
+            MSTATUS_MPRV | MSTATUS_SUM | MSTATUS64_UXL)) {
         tlb_flush(env_cpu(env));
     }
     mask = MSTATUS_SIE | MSTATUS_SPIE | MSTATUS_MIE | MSTATUS_MPIE |
         MSTATUS_SPP | MSTATUS_FS | MSTATUS_MPRV | MSTATUS_SUM |
         MSTATUS_MPP | MSTATUS_MXR | MSTATUS_TVM | MSTATUS_TSR |
-        MSTATUS_TW;
+        MSTATUS_TW | MSTATUS64_UXL;
 
     if (!riscv_cpu_is_32bit(env)) {
         /*
@@ -518,6 +548,8 @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
         mask |= MSTATUS_MPV | MSTATUS_GVA;
     }
 
+    uxl32_switch(env, val);
+
     mstatus = (mstatus & ~mask) | (val & mask);
 
     dirty = ((mstatus & MSTATUS_FS) == MSTATUS_FS) |
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* [RFC PATCH 13/13] target/riscv: Changing the width of U-mode CSR
@ 2021-08-05  2:53   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  2:53 UTC (permalink / raw)
  To: qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng, richard.henderson, LIU Zhiwei

Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
---
 target/riscv/csr.c | 42 +++++++++++++++++++++++++++++++++++++-----
 1 file changed, 37 insertions(+), 5 deletions(-)

diff --git a/target/riscv/csr.c b/target/riscv/csr.c
index 9a4ed18ac5..dc9807c0ff 100644
--- a/target/riscv/csr.c
+++ b/target/riscv/csr.c
@@ -297,7 +297,7 @@ static RISCVException read_vxrm(CPURISCVState *env, int csrno,
 static RISCVException write_vxrm(CPURISCVState *env, int csrno,
                                  target_ulong val)
 {
-    env->vxrm = val;
+    env->vxrm = riscv_cpu_is_uxl32(env) ? val & UINT32_MAX : val;
     return RISCV_EXCP_NONE;
 }
 
@@ -311,7 +311,7 @@ static RISCVException read_vxsat(CPURISCVState *env, int csrno,
 static RISCVException write_vxsat(CPURISCVState *env, int csrno,
                                   target_ulong val)
 {
-    env->vxsat = val;
+    env->vxsat = riscv_cpu_is_uxl32(env) ? val & UINT32_MAX : val;
     return RISCV_EXCP_NONE;
 }
 
@@ -325,7 +325,7 @@ static RISCVException read_vstart(CPURISCVState *env, int csrno,
 static RISCVException write_vstart(CPURISCVState *env, int csrno,
                                    target_ulong val)
 {
-    env->vstart = val;
+    env->vstart = riscv_cpu_is_uxl32(env) ? val & UINT32_MAX : val;
     return RISCV_EXCP_NONE;
 }
 
@@ -493,6 +493,36 @@ static int validate_vm(CPURISCVState *env, target_ulong vm)
     }
 }
 
+static void uxl32_switch(CPURISCVState *env, target_ulong val)
+{
+    uint32_t old = get_field(env->mstatus, MSTATUS64_UXL);
+    uint32_t new = get_field(val, MSTATUS64_UXL);
+
+    if (old == new) {
+        return;
+    }
+
+    /*
+     * For the read-only bits of the previous-width CSR, the bits at the
+     * same positions in the temporary register are set to zeros.
+     */
+    if (env->misa & RVV) {
+        env->vl = 0;
+        env->vtype = 0;
+    }
+
+    /*
+     * If the new width W is narrower than the previous width, the
+     * least-significant W bits of the temporary register are retained and
+     * the more-significant bits are discarded.
+     */
+    if ((old == 2) && (new == 1)) {
+        if (env->misa & RVV) {
+            env->vtype &= UINT32_MAX;
+        }
+    }
+}
+
 static RISCVException write_mstatus(CPURISCVState *env, int csrno,
                                     target_ulong val)
 {
@@ -502,13 +532,13 @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
 
     /* flush tlb on mstatus fields that affect VM */
     if ((val ^ mstatus) & (MSTATUS_MXR | MSTATUS_MPP | MSTATUS_MPV |
-            MSTATUS_MPRV | MSTATUS_SUM)) {
+            MSTATUS_MPRV | MSTATUS_SUM | MSTATUS64_UXL)) {
         tlb_flush(env_cpu(env));
     }
     mask = MSTATUS_SIE | MSTATUS_SPIE | MSTATUS_MIE | MSTATUS_MPIE |
         MSTATUS_SPP | MSTATUS_FS | MSTATUS_MPRV | MSTATUS_SUM |
         MSTATUS_MPP | MSTATUS_MXR | MSTATUS_TVM | MSTATUS_TSR |
-        MSTATUS_TW;
+        MSTATUS_TW | MSTATUS64_UXL;
 
     if (!riscv_cpu_is_32bit(env)) {
         /*
@@ -518,6 +548,8 @@ static RISCVException write_mstatus(CPURISCVState *env, int csrno,
         mask |= MSTATUS_MPV | MSTATUS_GVA;
     }
 
+    uxl32_switch(env, val);
+
     mstatus = (mstatus & ~mask) | (val & mask);
 
     dirty = ((mstatus & MSTATUS_FS) == MSTATUS_FS) |
-- 
2.17.1



^ permalink raw reply related	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05  6:00     ` Alistair Francis
  -1 siblings, 0 replies; 82+ messages in thread
From: Alistair Francis @ 2021-08-05  6:00 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis

On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
> For 32-bit applications run on 64-bit cpu, it may share some code
> with other 64-bit applictions. Thus we should distinguish the translated
> cache of the share code with a tb flag.
>
> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  target/riscv/cpu.h       | 15 +++++++++++++++
>  target/riscv/translate.c |  3 +++
>  2 files changed, 18 insertions(+)
>
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index bf1c899c00..2b3ba21a78 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
>  FIELD(TB_FLAGS, VILL, 8, 1)
>  /* Is a Hypervisor instruction load/store allowed? */
>  FIELD(TB_FLAGS, HLSX, 9, 1)
> +FIELD(TB_FLAGS, UXL, 10, 2)
>
>  bool riscv_cpu_is_32bit(CPURISCVState *env);
>
> +static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
> +{
> +#ifndef CONFIG_USER_ONLY
> +    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
> +           !riscv_cpu_is_32bit(env) &&
> +           (env->priv == PRV_U);
> +#endif
> +    return false;
> +}
> +
>  /*
>   * A simplification for VLMAX
>   * = (1 << LMUL) * VLEN / (8 * (1 << SEW))
> @@ -451,6 +462,10 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
>              flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
>          }
>      }
> +    if (riscv_cpu_is_uxl32(env)) {
> +        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
> +                           get_field(env->mstatus, MSTATUS64_UXL));
> +    }
>  #endif
>
>      *pflags = flags;
> diff --git a/target/riscv/translate.c b/target/riscv/translate.c
> index 076f28b9c1..ac4a545da8 100644
> --- a/target/riscv/translate.c
> +++ b/target/riscv/translate.c
> @@ -67,6 +67,8 @@ typedef struct DisasContext {
>      CPUState *cs;
>      TCGv zero;
>      TCGv sink;
> +    /* UXLEN is 32 bit for 64-bit CPU */
> +    bool uxl32;
>  } DisasContext;
>
>  static inline bool has_ext(DisasContext *ctx, uint32_t ext)
> @@ -912,6 +914,7 @@ static void riscv_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
>      ctx->mlen = 1 << (ctx->sew  + 3 - ctx->lmul);
>      ctx->vl_eq_vlmax = FIELD_EX32(tb_flags, TB_FLAGS, VL_EQ_VLMAX);
>      ctx->cs = cs;
> +    ctx->uxl32 = FIELD_EX32(tb_flags, TB_FLAGS, UXL) == 1;
>  }
>
>  static void riscv_tr_tb_start(DisasContextBase *dcbase, CPUState *cpu)
> --
> 2.17.1
>
>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
@ 2021-08-05  6:00     ` Alistair Francis
  0 siblings, 0 replies; 82+ messages in thread
From: Alistair Francis @ 2021-08-05  6:00 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: qemu-devel@nongnu.org Developers, open list:RISC-V,
	Palmer Dabbelt, Richard Henderson, Bin Meng, Alistair Francis

On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
> For 32-bit applications run on 64-bit cpu, it may share some code
> with other 64-bit applictions. Thus we should distinguish the translated
> cache of the share code with a tb flag.
>
> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>

Reviewed-by: Alistair Francis <alistair.francis@wdc.com>

Alistair

> ---
>  target/riscv/cpu.h       | 15 +++++++++++++++
>  target/riscv/translate.c |  3 +++
>  2 files changed, 18 insertions(+)
>
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index bf1c899c00..2b3ba21a78 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
>  FIELD(TB_FLAGS, VILL, 8, 1)
>  /* Is a Hypervisor instruction load/store allowed? */
>  FIELD(TB_FLAGS, HLSX, 9, 1)
> +FIELD(TB_FLAGS, UXL, 10, 2)
>
>  bool riscv_cpu_is_32bit(CPURISCVState *env);
>
> +static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
> +{
> +#ifndef CONFIG_USER_ONLY
> +    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
> +           !riscv_cpu_is_32bit(env) &&
> +           (env->priv == PRV_U);
> +#endif
> +    return false;
> +}
> +
>  /*
>   * A simplification for VLMAX
>   * = (1 << LMUL) * VLEN / (8 * (1 << SEW))
> @@ -451,6 +462,10 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
>              flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
>          }
>      }
> +    if (riscv_cpu_is_uxl32(env)) {
> +        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
> +                           get_field(env->mstatus, MSTATUS64_UXL));
> +    }
>  #endif
>
>      *pflags = flags;
> diff --git a/target/riscv/translate.c b/target/riscv/translate.c
> index 076f28b9c1..ac4a545da8 100644
> --- a/target/riscv/translate.c
> +++ b/target/riscv/translate.c
> @@ -67,6 +67,8 @@ typedef struct DisasContext {
>      CPUState *cs;
>      TCGv zero;
>      TCGv sink;
> +    /* UXLEN is 32 bit for 64-bit CPU */
> +    bool uxl32;
>  } DisasContext;
>
>  static inline bool has_ext(DisasContext *ctx, uint32_t ext)
> @@ -912,6 +914,7 @@ static void riscv_tr_init_disas_context(DisasContextBase *dcbase, CPUState *cs)
>      ctx->mlen = 1 << (ctx->sew  + 3 - ctx->lmul);
>      ctx->vl_eq_vlmax = FIELD_EX32(tb_flags, TB_FLAGS, VL_EQ_VLMAX);
>      ctx->cs = cs;
> +    ctx->uxl32 = FIELD_EX32(tb_flags, TB_FLAGS, UXL) == 1;
>  }
>
>  static void riscv_tr_tb_start(DisasContextBase *dcbase, CPUState *cpu)
> --
> 2.17.1
>
>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
  2021-08-05  2:52 ` LIU Zhiwei
@ 2021-08-05  6:01   ` Alistair Francis
  -1 siblings, 0 replies; 82+ messages in thread
From: Alistair Francis @ 2021-08-05  6:01 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis

On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
> This patch set implements UXL field in mstatus register. Programmer can change
> UXLEN by writting to this field. So that you can run a 32 bit program
> on a 64 bit CPU.

Awesome! Do you have any steps for building a rootFS to test this?

Alistair

>
> This patch set depends on one patch set by Richard Henderson
> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
>
> LIU Zhiwei (13):
>   target/riscv: Add UXL to tb flags
>   target/riscv: Support UXL32 for branch instructions
>   target/riscv: Support UXL32 on 64-bit cpu for load/store
>   target/riscv: Support UXL32 for slit/sltiu
>   target/riscv: Support UXL32 for shift instruction
>   target/riscv: Fix div instructions
>   target/riscv: Support UXL32 for RVM
>   target/riscv: Support UXL32 for vector instructions
>   target/riscv: Support UXL32 for atomic instructions
>   target/riscv: Support UXL32 for float instructions
>   target/riscv: Fix srow
>   target/riscv: Support UXL32 for RVB
>   target/riscv: Changing the width of U-mode CSR
>
>  target/riscv/cpu.h                      |  18 +++
>  target/riscv/csr.c                      |  42 +++++-
>  target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
>  target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
>  target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
>  target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
>  target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
>  target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
>  target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
>  target/riscv/translate.c                | 186 ++++++++++++++++++++----
>  target/riscv/vector_helper.c            |  54 +++++--
>  11 files changed, 414 insertions(+), 111 deletions(-)
>
> --
> 2.17.1
>
>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-05  6:01   ` Alistair Francis
  0 siblings, 0 replies; 82+ messages in thread
From: Alistair Francis @ 2021-08-05  6:01 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: qemu-devel@nongnu.org Developers, open list:RISC-V,
	Palmer Dabbelt, Richard Henderson, Bin Meng, Alistair Francis

On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
> This patch set implements UXL field in mstatus register. Programmer can change
> UXLEN by writting to this field. So that you can run a 32 bit program
> on a 64 bit CPU.

Awesome! Do you have any steps for building a rootFS to test this?

Alistair

>
> This patch set depends on one patch set by Richard Henderson
> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
>
> LIU Zhiwei (13):
>   target/riscv: Add UXL to tb flags
>   target/riscv: Support UXL32 for branch instructions
>   target/riscv: Support UXL32 on 64-bit cpu for load/store
>   target/riscv: Support UXL32 for slit/sltiu
>   target/riscv: Support UXL32 for shift instruction
>   target/riscv: Fix div instructions
>   target/riscv: Support UXL32 for RVM
>   target/riscv: Support UXL32 for vector instructions
>   target/riscv: Support UXL32 for atomic instructions
>   target/riscv: Support UXL32 for float instructions
>   target/riscv: Fix srow
>   target/riscv: Support UXL32 for RVB
>   target/riscv: Changing the width of U-mode CSR
>
>  target/riscv/cpu.h                      |  18 +++
>  target/riscv/csr.c                      |  42 +++++-
>  target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
>  target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
>  target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
>  target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
>  target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
>  target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
>  target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
>  target/riscv/translate.c                | 186 ++++++++++++++++++++----
>  target/riscv/vector_helper.c            |  54 +++++--
>  11 files changed, 414 insertions(+), 111 deletions(-)
>
> --
> 2.17.1
>
>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
  2021-08-05  6:01   ` Alistair Francis
@ 2021-08-05  7:14     ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  7:14 UTC (permalink / raw)
  To: Alistair Francis
  Cc: open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis


On 2021/8/5 下午2:01, Alistair Francis wrote:
> On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>> This patch set implements UXL field in mstatus register. Programmer can change
>> UXLEN by writting to this field. So that you can run a 32 bit program
>> on a 64 bit CPU.
> Awesome! Do you have any steps for building a rootFS to test this?

Not yet.  It depends on Linux support which  will not start until  
October.  Maybe as a rough test,
we can run the 32 glibc test cases on qemu-riscv64 with an option 
uxl32=true(not implement yet).

Zhiwei

>
> Alistair
>
>> This patch set depends on one patch set by Richard Henderson
>> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
>>
>> LIU Zhiwei (13):
>>    target/riscv: Add UXL to tb flags
>>    target/riscv: Support UXL32 for branch instructions
>>    target/riscv: Support UXL32 on 64-bit cpu for load/store
>>    target/riscv: Support UXL32 for slit/sltiu
>>    target/riscv: Support UXL32 for shift instruction
>>    target/riscv: Fix div instructions
>>    target/riscv: Support UXL32 for RVM
>>    target/riscv: Support UXL32 for vector instructions
>>    target/riscv: Support UXL32 for atomic instructions
>>    target/riscv: Support UXL32 for float instructions
>>    target/riscv: Fix srow
>>    target/riscv: Support UXL32 for RVB
>>    target/riscv: Changing the width of U-mode CSR
>>
>>   target/riscv/cpu.h                      |  18 +++
>>   target/riscv/csr.c                      |  42 +++++-
>>   target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
>>   target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
>>   target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
>>   target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
>>   target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
>>   target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
>>   target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
>>   target/riscv/translate.c                | 186 ++++++++++++++++++++----
>>   target/riscv/vector_helper.c            |  54 +++++--
>>   11 files changed, 414 insertions(+), 111 deletions(-)
>>
>> --
>> 2.17.1
>>
>>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-05  7:14     ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  7:14 UTC (permalink / raw)
  To: Alistair Francis
  Cc: qemu-devel@nongnu.org Developers, open list:RISC-V,
	Palmer Dabbelt, Richard Henderson, Bin Meng, Alistair Francis


On 2021/8/5 下午2:01, Alistair Francis wrote:
> On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>> This patch set implements UXL field in mstatus register. Programmer can change
>> UXLEN by writting to this field. So that you can run a 32 bit program
>> on a 64 bit CPU.
> Awesome! Do you have any steps for building a rootFS to test this?

Not yet.  It depends on Linux support which  will not start until  
October.  Maybe as a rough test,
we can run the 32 glibc test cases on qemu-riscv64 with an option 
uxl32=true(not implement yet).

Zhiwei

>
> Alistair
>
>> This patch set depends on one patch set by Richard Henderson
>> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
>>
>> LIU Zhiwei (13):
>>    target/riscv: Add UXL to tb flags
>>    target/riscv: Support UXL32 for branch instructions
>>    target/riscv: Support UXL32 on 64-bit cpu for load/store
>>    target/riscv: Support UXL32 for slit/sltiu
>>    target/riscv: Support UXL32 for shift instruction
>>    target/riscv: Fix div instructions
>>    target/riscv: Support UXL32 for RVM
>>    target/riscv: Support UXL32 for vector instructions
>>    target/riscv: Support UXL32 for atomic instructions
>>    target/riscv: Support UXL32 for float instructions
>>    target/riscv: Fix srow
>>    target/riscv: Support UXL32 for RVB
>>    target/riscv: Changing the width of U-mode CSR
>>
>>   target/riscv/cpu.h                      |  18 +++
>>   target/riscv/csr.c                      |  42 +++++-
>>   target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
>>   target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
>>   target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
>>   target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
>>   target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
>>   target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
>>   target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
>>   target/riscv/translate.c                | 186 ++++++++++++++++++++----
>>   target/riscv/vector_helper.c            |  54 +++++--
>>   11 files changed, 414 insertions(+), 111 deletions(-)
>>
>> --
>> 2.17.1
>>
>>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
  2021-08-05  7:14     ` LIU Zhiwei
@ 2021-08-05  7:20       ` Bin Meng
  -1 siblings, 0 replies; 82+ messages in thread
From: Bin Meng @ 2021-08-05  7:20 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: Alistair Francis, open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis

On Thu, Aug 5, 2021 at 3:16 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
>
> On 2021/8/5 下午2:01, Alistair Francis wrote:
> > On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
> >> This patch set implements UXL field in mstatus register. Programmer can change
> >> UXLEN by writting to this field. So that you can run a 32 bit program
> >> on a 64 bit CPU.
> > Awesome! Do you have any steps for building a rootFS to test this?
>
> Not yet.  It depends on Linux support which  will not start until
> October.  Maybe as a rough test,
> we can run the 32 glibc test cases on qemu-riscv64 with an option
> uxl32=true(not implement yet).

That's my understanding as well. Currently there is no software stack
that supports mode switch, e.g.: OpenSBI boots in 64-bit but loading a
32-bit payload to execute.

Do you plan to support SXL as well?

Regards,
Bin


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-05  7:20       ` Bin Meng
  0 siblings, 0 replies; 82+ messages in thread
From: Bin Meng @ 2021-08-05  7:20 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: Alistair Francis, open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis

On Thu, Aug 5, 2021 at 3:16 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
>
> On 2021/8/5 下午2:01, Alistair Francis wrote:
> > On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
> >> This patch set implements UXL field in mstatus register. Programmer can change
> >> UXLEN by writting to this field. So that you can run a 32 bit program
> >> on a 64 bit CPU.
> > Awesome! Do you have any steps for building a rootFS to test this?
>
> Not yet.  It depends on Linux support which  will not start until
> October.  Maybe as a rough test,
> we can run the 32 glibc test cases on qemu-riscv64 with an option
> uxl32=true(not implement yet).

That's my understanding as well. Currently there is no software stack
that supports mode switch, e.g.: OpenSBI boots in 64-bit but loading a
32-bit payload to execute.

Do you plan to support SXL as well?

Regards,
Bin


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
  2021-08-05  7:20       ` Bin Meng
@ 2021-08-05  8:10         ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  8:10 UTC (permalink / raw)
  To: Bin Meng
  Cc: Alistair Francis, open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis


On 2021/8/5 下午3:20, Bin Meng wrote:
> On Thu, Aug 5, 2021 at 3:16 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>
>> On 2021/8/5 下午2:01, Alistair Francis wrote:
>>> On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>>> This patch set implements UXL field in mstatus register. Programmer can change
>>>> UXLEN by writting to this field. So that you can run a 32 bit program
>>>> on a 64 bit CPU.
>>> Awesome! Do you have any steps for building a rootFS to test this?
>> Not yet.  It depends on Linux support which  will not start until
>> October.  Maybe as a rough test,
>> we can run the 32 glibc test cases on qemu-riscv64 with an option
>> uxl32=true(not implement yet).
> That's my understanding as well. Currently there is no software stack
> that supports mode switch, e.g.: OpenSBI boots in 64-bit but loading a
> 32-bit payload to execute.
>
> Do you plan to support SXL as well?

Sorry, SXL is not  planned.   If I have enough time later,  I will have 
a try.

Zhiwei

>
> Regards,
> Bin


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-05  8:10         ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-05  8:10 UTC (permalink / raw)
  To: Bin Meng
  Cc: Alistair Francis, open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis


On 2021/8/5 下午3:20, Bin Meng wrote:
> On Thu, Aug 5, 2021 at 3:16 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>
>> On 2021/8/5 下午2:01, Alistair Francis wrote:
>>> On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>>> This patch set implements UXL field in mstatus register. Programmer can change
>>>> UXLEN by writting to this field. So that you can run a 32 bit program
>>>> on a 64 bit CPU.
>>> Awesome! Do you have any steps for building a rootFS to test this?
>> Not yet.  It depends on Linux support which  will not start until
>> October.  Maybe as a rough test,
>> we can run the 32 glibc test cases on qemu-riscv64 with an option
>> uxl32=true(not implement yet).
> That's my understanding as well. Currently there is no software stack
> that supports mode switch, e.g.: OpenSBI boots in 64-bit but loading a
> 32-bit payload to execute.
>
> Do you plan to support SXL as well?

Sorry, SXL is not  planned.   If I have enough time later,  I will have 
a try.

Zhiwei

>
> Regards,
> Bin


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05 19:01     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:01 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> For 32-bit applications run on 64-bit cpu, it may share some code
> with other 64-bit applictions. Thus we should distinguish the translated
> cache of the share code with a tb flag.
> 
> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
> ---
>   target/riscv/cpu.h       | 15 +++++++++++++++
>   target/riscv/translate.c |  3 +++
>   2 files changed, 18 insertions(+)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index bf1c899c00..2b3ba21a78 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
>   FIELD(TB_FLAGS, VILL, 8, 1)
>   /* Is a Hypervisor instruction load/store allowed? */
>   FIELD(TB_FLAGS, HLSX, 9, 1)
> +FIELD(TB_FLAGS, UXL, 10, 2)

Are you intending to reserve space for RV128 here?
Otherwise this could be a single bit.

Also, you probably don't want to name it "UXL", since it should indicate the current 
operating XLEN, taking MXL, SXL and UXL into account.

Perhaps just name the field XLEN32, and make it a single bit?

> +static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
> +{
> +#ifndef CONFIG_USER_ONLY
> +    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
> +           !riscv_cpu_is_32bit(env) &&
> +           (env->priv == PRV_U);
> +#endif
> +    return false;
> +}

Again, naming could be better?
It seems trivial to handle all of the fields here.  Perhaps


static inline bool riscv_cpu_is_xlen32(env)
{
#if defined(TARGET_RISCV32)
     return true;
#elif defined(CONFIG_USER_ONLY)
     return false;
#else
     /* When emulating a 32-bit-only cpu, use RV32. */
     if (riscv_cpu_is_32bit(env)) {
         return true;
     }
     /*
      * If MXL has been reduced to RV32, MSTATUSH doesn't have UXL/SXL,
      * therefore, XLEN cannot be widened back to RV64 for lower privs.
      */
     if (get_field(env->misa, MISA64_MXL) == 1) {
         return true;
     }
     switch (env->priv) {
     case PRV_M:
         return false;
     case PRV_U:
         return get_field(env->mstatus, MSTATUS64_UXL) == 1;
     default: /* PRV_S & PRV_H */
         return get_field(env->mstatus, MSTATUS64_SXL) == 1;
     }
#endif
}


> @@ -451,6 +462,10 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
>               flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
>           }
>       }
> +    if (riscv_cpu_is_uxl32(env)) {
> +        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
> +                           get_field(env->mstatus, MSTATUS64_UXL));

   flags = FIELD_DP32(flags, TB_FLAGS, XLEN32,
                      riscv_cpu_is_xlen32(env));


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
@ 2021-08-05 19:01     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:01 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> For 32-bit applications run on 64-bit cpu, it may share some code
> with other 64-bit applictions. Thus we should distinguish the translated
> cache of the share code with a tb flag.
> 
> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
> ---
>   target/riscv/cpu.h       | 15 +++++++++++++++
>   target/riscv/translate.c |  3 +++
>   2 files changed, 18 insertions(+)
> 
> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
> index bf1c899c00..2b3ba21a78 100644
> --- a/target/riscv/cpu.h
> +++ b/target/riscv/cpu.h
> @@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
>   FIELD(TB_FLAGS, VILL, 8, 1)
>   /* Is a Hypervisor instruction load/store allowed? */
>   FIELD(TB_FLAGS, HLSX, 9, 1)
> +FIELD(TB_FLAGS, UXL, 10, 2)

Are you intending to reserve space for RV128 here?
Otherwise this could be a single bit.

Also, you probably don't want to name it "UXL", since it should indicate the current 
operating XLEN, taking MXL, SXL and UXL into account.

Perhaps just name the field XLEN32, and make it a single bit?

> +static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
> +{
> +#ifndef CONFIG_USER_ONLY
> +    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
> +           !riscv_cpu_is_32bit(env) &&
> +           (env->priv == PRV_U);
> +#endif
> +    return false;
> +}

Again, naming could be better?
It seems trivial to handle all of the fields here.  Perhaps


static inline bool riscv_cpu_is_xlen32(env)
{
#if defined(TARGET_RISCV32)
     return true;
#elif defined(CONFIG_USER_ONLY)
     return false;
#else
     /* When emulating a 32-bit-only cpu, use RV32. */
     if (riscv_cpu_is_32bit(env)) {
         return true;
     }
     /*
      * If MXL has been reduced to RV32, MSTATUSH doesn't have UXL/SXL,
      * therefore, XLEN cannot be widened back to RV64 for lower privs.
      */
     if (get_field(env->misa, MISA64_MXL) == 1) {
         return true;
     }
     switch (env->priv) {
     case PRV_M:
         return false;
     case PRV_U:
         return get_field(env->mstatus, MSTATUS64_UXL) == 1;
     default: /* PRV_S & PRV_H */
         return get_field(env->mstatus, MSTATUS64_SXL) == 1;
     }
#endif
}


> @@ -451,6 +462,10 @@ static inline void cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
>               flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
>           }
>       }
> +    if (riscv_cpu_is_uxl32(env)) {
> +        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
> +                           get_field(env->mstatus, MSTATUS64_UXL));

   flags = FIELD_DP32(flags, TB_FLAGS, XLEN32,
                      riscv_cpu_is_xlen32(env));


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05 19:06     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:06 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
> +{
> +    if (reg_num == 0) {
> +        return ctx->zero;
> +    }
> +    if (ctx->uxl32) {
> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
> +    }
> +    return cpu_gpr[reg_num];
> +}
> +
> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
> +{
> +    if (reg_num == 0) {
> +        return ctx->zero;
> +    }
> +    if (ctx->uxl32) {
> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
> +    }
> +    return cpu_gpr[reg_num];
> +}

This is bad: you cannot modify the source registers like this.

These incorrect modifications will be visible to the kernel on transition back to S-mode.

> 
> +static bool gen_branch_u(DisasContext *ctx, arg_b *a, TCGCond cond)
> +{
> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
> +    TCGv src2 = gpr_src_u(ctx, a->rs2);
> +
> +    return gen_branch_internal(ctx, a, cond, src1, src2);
> +}

This is unnecessary.  Unsigned comparisons work just fine with sign-extended values.  It 
will be simpler to keep all values sign-extended.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-05 19:06     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:06 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
> +{
> +    if (reg_num == 0) {
> +        return ctx->zero;
> +    }
> +    if (ctx->uxl32) {
> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
> +    }
> +    return cpu_gpr[reg_num];
> +}
> +
> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
> +{
> +    if (reg_num == 0) {
> +        return ctx->zero;
> +    }
> +    if (ctx->uxl32) {
> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
> +    }
> +    return cpu_gpr[reg_num];
> +}

This is bad: you cannot modify the source registers like this.

These incorrect modifications will be visible to the kernel on transition back to S-mode.

> 
> +static bool gen_branch_u(DisasContext *ctx, arg_b *a, TCGCond cond)
> +{
> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
> +    TCGv src2 = gpr_src_u(ctx, a->rs2);
> +
> +    return gen_branch_internal(ctx, a, cond, src1, src2);
> +}

This is unnecessary.  Unsigned comparisons work just fine with sign-extended values.  It 
will be simpler to keep all values sign-extended.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05 19:08     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:08 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> Get the LSB 32 bits and zero-extend as the base address.
> 
> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
> ---
>   target/riscv/insn_trans/trans_rvi.c.inc | 4 ++--
>   1 file changed, 2 insertions(+), 2 deletions(-)
> 
> diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
> index ea41d1de2d..6823a6b3e0 100644
> --- a/target/riscv/insn_trans/trans_rvi.c.inc
> +++ b/target/riscv/insn_trans/trans_rvi.c.inc
> @@ -163,7 +163,7 @@ static bool trans_bgeu(DisasContext *ctx, arg_bgeu *a)
>   static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
>   {
>       TCGv dest = gpr_dst(ctx, a->rd);
> -    TCGv addr = gpr_src(ctx, a->rs1);
> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>       TCGv temp = NULL;
>   
>       if (a->imm) {
> @@ -207,7 +207,7 @@ static bool trans_lhu(DisasContext *ctx, arg_lhu *a)
>   
>   static bool gen_store(DisasContext *ctx, arg_sb *a, MemOp memop)
>   {
> -    TCGv addr = gpr_src(ctx, a->rs1);
> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>       TCGv data = gpr_src(ctx, a->rs2);
>       TCGv temp = NULL;

This is incorrect.  The zero-extension should happen after the addition of the immediate 
offset.

r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store
@ 2021-08-05 19:08     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:08 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> Get the LSB 32 bits and zero-extend as the base address.
> 
> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
> ---
>   target/riscv/insn_trans/trans_rvi.c.inc | 4 ++--
>   1 file changed, 2 insertions(+), 2 deletions(-)
> 
> diff --git a/target/riscv/insn_trans/trans_rvi.c.inc b/target/riscv/insn_trans/trans_rvi.c.inc
> index ea41d1de2d..6823a6b3e0 100644
> --- a/target/riscv/insn_trans/trans_rvi.c.inc
> +++ b/target/riscv/insn_trans/trans_rvi.c.inc
> @@ -163,7 +163,7 @@ static bool trans_bgeu(DisasContext *ctx, arg_bgeu *a)
>   static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
>   {
>       TCGv dest = gpr_dst(ctx, a->rd);
> -    TCGv addr = gpr_src(ctx, a->rs1);
> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>       TCGv temp = NULL;
>   
>       if (a->imm) {
> @@ -207,7 +207,7 @@ static bool trans_lhu(DisasContext *ctx, arg_lhu *a)
>   
>   static bool gen_store(DisasContext *ctx, arg_sb *a, MemOp memop)
>   {
> -    TCGv addr = gpr_src(ctx, a->rs1);
> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>       TCGv data = gpr_src(ctx, a->rs2);
>       TCGv temp = NULL;

This is incorrect.  The zero-extension should happen after the addition of the immediate 
offset.

r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05 19:09     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:09 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> +static bool gen_arith_simm_tl(DisasContext *ctx, arg_i *a,
> +                              void (*func)(TCGv, TCGv, TCGv))
> +{
> +    TCGv dest = gpr_dst(ctx, a->rd);
> +    TCGv src1 = gpr_src_s(ctx, a->rs1);
> +    TCGv src2 = tcg_constant_tl(a->imm);
> +
> +    (*func)(dest, src1, src2);
> +    return true;
> +}
> +
> +static bool gen_arith_uimm_tl(DisasContext *ctx, arg_i *a,
> +                              void (*func)(TCGv, TCGv, TCGv))
> +{
> +    TCGv dest = gpr_dst(ctx, a->rd);
> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
> +    TCGv src2 = tcg_constant_tl(ctx->uxl32 ? a->imm & UINT32_MAX : a->imm);
> +
> +    (*func)(dest, src1, src2);
> +    return true;
> +}

Again, unsigned comparisions work fine with sign-extended inputs.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu
@ 2021-08-05 19:09     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 19:09 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> +static bool gen_arith_simm_tl(DisasContext *ctx, arg_i *a,
> +                              void (*func)(TCGv, TCGv, TCGv))
> +{
> +    TCGv dest = gpr_dst(ctx, a->rd);
> +    TCGv src1 = gpr_src_s(ctx, a->rs1);
> +    TCGv src2 = tcg_constant_tl(a->imm);
> +
> +    (*func)(dest, src1, src2);
> +    return true;
> +}
> +
> +static bool gen_arith_uimm_tl(DisasContext *ctx, arg_i *a,
> +                              void (*func)(TCGv, TCGv, TCGv))
> +{
> +    TCGv dest = gpr_dst(ctx, a->rd);
> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
> +    TCGv src2 = tcg_constant_tl(ctx->uxl32 ? a->imm & UINT32_MAX : a->imm);
> +
> +    (*func)(dest, src1, src2);
> +    return true;
> +}

Again, unsigned comparisions work fine with sign-extended inputs.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05 22:17     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 22:17 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>   static bool trans_srli(DisasContext *ctx, arg_srli *a)
>   {
> +    if (ctx->uxl32) {
> +        return trans_srliw(ctx, a);
> +    }
>       return gen_shifti(ctx, a, tcg_gen_shr_tl);
>   }

First, trans_srliw begins with REQUIRE_64BIT, which *should* fail when RV32 is in effect. 
  This means there's a missing change to is_32bit().

Second, the current decode for srli allows 7 bits of shift, while srilw only allows 5.  As 
a consequence, gen_shifti contains a check for TARGET_LONG_BITS and trans_srliw does not 
contain a check at all.  We need to diagnose an out-of-range shift for RV32 somewhere.

I recommend extending the gen_shift* family of helpers.

static bool gen_shifti_imm(DisasContext *ctx, arg_shift *a, int width,
                            void (*func)(TCGv, TCGv, target_long))
{
     TCGv dest, src1;

     if (a->shamt >= width) {
         return false;
     }
     dest = gpr_dst(ctx, a->rd);
     src1 = gpr_src(ctx, a->rs1);
     func(dest, src1, a->shamt);
     return true;
}

static bool gen_shifti(DisasContext *ctx, arg_shift *a, int width,
                        void (*func)(TCGv, TCGv, TCGv))
{...}

static void gen_srliw(TCGv dest, TCGv src1, target_long shamt)
{
     tcg_gen_extract_tl(dest, src1, shamt, 32 - shamt);
     tcg_gen_ext32s_tl(dest, dest);
}

static bool trans_srliw(DisasContext *ctx, arg_shift *a)
{
     REQUIRE_64BIT(ctx);
     return gen_shifti_imm(ctx, a, 32, gen_srliw);
}

static bool trans_srli(DisasContext *ctx, arg_shift *a)
{
     int xlen = is_32bit(ctx) ? 32 : 64;
     return gen_shifti_imm(ctx, a, xlen,
                           xlen == TARGET_LONG_BITS
                           ? tcg_gen_shri_tl : gen_srliw);
}

etc.  Perhaps that is_32bit() check above could be consolidated into some macro/inline.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction
@ 2021-08-05 22:17     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 22:17 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>   static bool trans_srli(DisasContext *ctx, arg_srli *a)
>   {
> +    if (ctx->uxl32) {
> +        return trans_srliw(ctx, a);
> +    }
>       return gen_shifti(ctx, a, tcg_gen_shr_tl);
>   }

First, trans_srliw begins with REQUIRE_64BIT, which *should* fail when RV32 is in effect. 
  This means there's a missing change to is_32bit().

Second, the current decode for srli allows 7 bits of shift, while srilw only allows 5.  As 
a consequence, gen_shifti contains a check for TARGET_LONG_BITS and trans_srliw does not 
contain a check at all.  We need to diagnose an out-of-range shift for RV32 somewhere.

I recommend extending the gen_shift* family of helpers.

static bool gen_shifti_imm(DisasContext *ctx, arg_shift *a, int width,
                            void (*func)(TCGv, TCGv, target_long))
{
     TCGv dest, src1;

     if (a->shamt >= width) {
         return false;
     }
     dest = gpr_dst(ctx, a->rd);
     src1 = gpr_src(ctx, a->rs1);
     func(dest, src1, a->shamt);
     return true;
}

static bool gen_shifti(DisasContext *ctx, arg_shift *a, int width,
                        void (*func)(TCGv, TCGv, TCGv))
{...}

static void gen_srliw(TCGv dest, TCGv src1, target_long shamt)
{
     tcg_gen_extract_tl(dest, src1, shamt, 32 - shamt);
     tcg_gen_ext32s_tl(dest, dest);
}

static bool trans_srliw(DisasContext *ctx, arg_shift *a)
{
     REQUIRE_64BIT(ctx);
     return gen_shifti_imm(ctx, a, 32, gen_srliw);
}

static bool trans_srli(DisasContext *ctx, arg_shift *a)
{
     int xlen = is_32bit(ctx) ? 32 : 64;
     return gen_shifti_imm(ctx, a, xlen,
                           xlen == TARGET_LONG_BITS
                           ? tcg_gen_shri_tl : gen_srliw);
}

etc.  Perhaps that is_32bit() check above could be consolidated into some macro/inline.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 06/13] target/riscv: Fix div instructions
  2021-08-05  2:53   ` LIU Zhiwei
@ 2021-08-05 22:18     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 22:18 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> Don't overwrite global source register after
> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00058.html.
> 
> Signed-off-by: LIU Zhiwei<zhiwei_liu@c-sky.com>
> ---
>   target/riscv/translate.c | 46 +++++++++++++++++++++++-----------------
>   1 file changed, 26 insertions(+), 20 deletions(-)

FWIW, I have a cleanup to these routines that does more than add temps.  I've been slow to 
re-post the series; sorry about that.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 06/13] target/riscv: Fix div instructions
@ 2021-08-05 22:18     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-05 22:18 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/4/21 4:53 PM, LIU Zhiwei wrote:
> Don't overwrite global source register after
> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00058.html.
> 
> Signed-off-by: LIU Zhiwei<zhiwei_liu@c-sky.com>
> ---
>   target/riscv/translate.c | 46 +++++++++++++++++++++++-----------------
>   1 file changed, 26 insertions(+), 20 deletions(-)

FWIW, I have a cleanup to these routines that does more than add temps.  I've been slow to 
re-post the series; sorry about that.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
  2021-08-05 19:01     ` Richard Henderson
@ 2021-08-06  2:49       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-06  2:49 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis

[-- Attachment #1: Type: text/plain, Size: 3772 bytes --]


On 2021/8/6 上午3:01, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> For 32-bit applications run on 64-bit cpu, it may share some code
>> with other 64-bit applictions. Thus we should distinguish the translated
>> cache of the share code with a tb flag.
>>
>> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
>> ---
>>   target/riscv/cpu.h       | 15 +++++++++++++++
>>   target/riscv/translate.c |  3 +++
>>   2 files changed, 18 insertions(+)
>>
>> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
>> index bf1c899c00..2b3ba21a78 100644
>> --- a/target/riscv/cpu.h
>> +++ b/target/riscv/cpu.h
>> @@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
>>   FIELD(TB_FLAGS, VILL, 8, 1)
>>   /* Is a Hypervisor instruction load/store allowed? */
>>   FIELD(TB_FLAGS, HLSX, 9, 1)
>> +FIELD(TB_FLAGS, UXL, 10, 2)
>
> Are you intending to reserve space for RV128 here?
> Otherwise this could be a single bit.
>
Yes.
> Also, you probably don't want to name it "UXL", since it should 
> indicate the current operating XLEN, taking MXL, SXL and UXL into 
> account.
>
Hi Richard,

I don't have the ambitious to define a XLEN32 at least for this patch 
set. I think it is much more difficult.

The only purpose of this patch set is that we can run 32-bit application 
on  a 64 bit Linux from qemu-system-riscv64.

So  I didn't change the default behavior of every instruction except when

 1. Current CPU is 64 bit CPU, i.s. TARGET_LONG_BITS is 64.
 2. Current privileged is U-mode.
 3. UXL is 1.

I know that Alistair has done a lot to support 32-bit CPU on 
qemu-system-riscv64. But We are doing different things,
and it maybe a little confusing.

I still do not find a good to combine them. In my opinion, some code in 
this patch set can be reused for SXL32.
If you have any advice, please let me know.

Best Regards,
Zhiwei

> Perhaps just name the field XLEN32, and make it a single bit?
>
>> +static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
>> +{
>> +#ifndef CONFIG_USER_ONLY
>> +    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
>> +           !riscv_cpu_is_32bit(env) &&
>> +           (env->priv == PRV_U);
>> +#endif
>> +    return false;
>> +}
>
> Again, naming could be better?
> It seems trivial to handle all of the fields here.  Perhaps
>
>
> static inline bool riscv_cpu_is_xlen32(env)
> {
> #if defined(TARGET_RISCV32)
>     return true;
> #elif defined(CONFIG_USER_ONLY)
>     return false;
> #else
>     /* When emulating a 32-bit-only cpu, use RV32. */
>     if (riscv_cpu_is_32bit(env)) {
>         return true;
>     }
>     /*
>      * If MXL has been reduced to RV32, MSTATUSH doesn't have UXL/SXL,
>      * therefore, XLEN cannot be widened back to RV64 for lower privs.
>      */
>     if (get_field(env->misa, MISA64_MXL) == 1) {
>         return true;
>     }
>     switch (env->priv) {
>     case PRV_M:
>         return false;
>     case PRV_U:
>         return get_field(env->mstatus, MSTATUS64_UXL) == 1;
>     default: /* PRV_S & PRV_H */
>         return get_field(env->mstatus, MSTATUS64_SXL) == 1;
>     }
> #endif
> }
>
>
>> @@ -451,6 +462,10 @@ static inline void 
>> cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
>>               flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
>>           }
>>       }
>> +    if (riscv_cpu_is_uxl32(env)) {
>> +        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
>> +                           get_field(env->mstatus, MSTATUS64_UXL));
>
>   flags = FIELD_DP32(flags, TB_FLAGS, XLEN32,
>                      riscv_cpu_is_xlen32(env));
>
>
> r~

[-- Attachment #2: Type: text/html, Size: 6122 bytes --]

^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 01/13] target/riscv: Add UXL to tb flags
@ 2021-08-06  2:49       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-06  2:49 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng

[-- Attachment #1: Type: text/plain, Size: 3772 bytes --]


On 2021/8/6 上午3:01, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> For 32-bit applications run on 64-bit cpu, it may share some code
>> with other 64-bit applictions. Thus we should distinguish the translated
>> cache of the share code with a tb flag.
>>
>> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
>> ---
>>   target/riscv/cpu.h       | 15 +++++++++++++++
>>   target/riscv/translate.c |  3 +++
>>   2 files changed, 18 insertions(+)
>>
>> diff --git a/target/riscv/cpu.h b/target/riscv/cpu.h
>> index bf1c899c00..2b3ba21a78 100644
>> --- a/target/riscv/cpu.h
>> +++ b/target/riscv/cpu.h
>> @@ -394,9 +394,20 @@ FIELD(TB_FLAGS, SEW, 5, 3)
>>   FIELD(TB_FLAGS, VILL, 8, 1)
>>   /* Is a Hypervisor instruction load/store allowed? */
>>   FIELD(TB_FLAGS, HLSX, 9, 1)
>> +FIELD(TB_FLAGS, UXL, 10, 2)
>
> Are you intending to reserve space for RV128 here?
> Otherwise this could be a single bit.
>
Yes.
> Also, you probably don't want to name it "UXL", since it should 
> indicate the current operating XLEN, taking MXL, SXL and UXL into 
> account.
>
Hi Richard,

I don't have the ambitious to define a XLEN32 at least for this patch 
set. I think it is much more difficult.

The only purpose of this patch set is that we can run 32-bit application 
on  a 64 bit Linux from qemu-system-riscv64.

So  I didn't change the default behavior of every instruction except when

 1. Current CPU is 64 bit CPU, i.s. TARGET_LONG_BITS is 64.
 2. Current privileged is U-mode.
 3. UXL is 1.

I know that Alistair has done a lot to support 32-bit CPU on 
qemu-system-riscv64. But We are doing different things,
and it maybe a little confusing.

I still do not find a good to combine them. In my opinion, some code in 
this patch set can be reused for SXL32.
If you have any advice, please let me know.

Best Regards,
Zhiwei

> Perhaps just name the field XLEN32, and make it a single bit?
>
>> +static inline bool riscv_cpu_is_uxl32(CPURISCVState *env)
>> +{
>> +#ifndef CONFIG_USER_ONLY
>> +    return (get_field(env->mstatus, MSTATUS64_UXL) == 1) &&
>> +           !riscv_cpu_is_32bit(env) &&
>> +           (env->priv == PRV_U);
>> +#endif
>> +    return false;
>> +}
>
> Again, naming could be better?
> It seems trivial to handle all of the fields here.  Perhaps
>
>
> static inline bool riscv_cpu_is_xlen32(env)
> {
> #if defined(TARGET_RISCV32)
>     return true;
> #elif defined(CONFIG_USER_ONLY)
>     return false;
> #else
>     /* When emulating a 32-bit-only cpu, use RV32. */
>     if (riscv_cpu_is_32bit(env)) {
>         return true;
>     }
>     /*
>      * If MXL has been reduced to RV32, MSTATUSH doesn't have UXL/SXL,
>      * therefore, XLEN cannot be widened back to RV64 for lower privs.
>      */
>     if (get_field(env->misa, MISA64_MXL) == 1) {
>         return true;
>     }
>     switch (env->priv) {
>     case PRV_M:
>         return false;
>     case PRV_U:
>         return get_field(env->mstatus, MSTATUS64_UXL) == 1;
>     default: /* PRV_S & PRV_H */
>         return get_field(env->mstatus, MSTATUS64_SXL) == 1;
>     }
> #endif
> }
>
>
>> @@ -451,6 +462,10 @@ static inline void 
>> cpu_get_tb_cpu_state(CPURISCVState *env, target_ulong *pc,
>>               flags = FIELD_DP32(flags, TB_FLAGS, HLSX, 1);
>>           }
>>       }
>> +    if (riscv_cpu_is_uxl32(env)) {
>> +        flags = FIELD_DP32(flags, TB_FLAGS, UXL,
>> +                           get_field(env->mstatus, MSTATUS64_UXL));
>
>   flags = FIELD_DP32(flags, TB_FLAGS, XLEN32,
>                      riscv_cpu_is_xlen32(env));
>
>
> r~

[-- Attachment #2: Type: text/html, Size: 6122 bytes --]

^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
  2021-08-05  7:14     ` LIU Zhiwei
@ 2021-08-06 10:05       ` Alistair Francis
  -1 siblings, 0 replies; 82+ messages in thread
From: Alistair Francis @ 2021-08-06 10:05 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis

On Thu, Aug 5, 2021 at 5:15 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
>
> On 2021/8/5 下午2:01, Alistair Francis wrote:
> > On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
> >> This patch set implements UXL field in mstatus register. Programmer can change
> >> UXLEN by writting to this field. So that you can run a 32 bit program
> >> on a 64 bit CPU.
> > Awesome! Do you have any steps for building a rootFS to test this?
>
> Not yet.  It depends on Linux support which  will not start until
> October.  Maybe as a rough test,
> we can run the 32 glibc test cases on qemu-riscv64 with an option
> uxl32=true(not implement yet).

Hmmm... That's a pain. We really need some way to test this (and
ensure no future breakages occur). But I see the problem of no
software support until this exists.

It sounds like you or a colleague is planning on adding Linux support.
Maybe we will have to wait until that at least exists before this can
go upstream. We could at least review this before hand though, so
thanks for sending the series.

A 32-bit glibc test on qemu-riscv64 would probably also be enough, at
least as a start.

Alistair

>
> Zhiwei
>
> >
> > Alistair
> >
> >> This patch set depends on one patch set by Richard Henderson
> >> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
> >>
> >> LIU Zhiwei (13):
> >>    target/riscv: Add UXL to tb flags
> >>    target/riscv: Support UXL32 for branch instructions
> >>    target/riscv: Support UXL32 on 64-bit cpu for load/store
> >>    target/riscv: Support UXL32 for slit/sltiu
> >>    target/riscv: Support UXL32 for shift instruction
> >>    target/riscv: Fix div instructions
> >>    target/riscv: Support UXL32 for RVM
> >>    target/riscv: Support UXL32 for vector instructions
> >>    target/riscv: Support UXL32 for atomic instructions
> >>    target/riscv: Support UXL32 for float instructions
> >>    target/riscv: Fix srow
> >>    target/riscv: Support UXL32 for RVB
> >>    target/riscv: Changing the width of U-mode CSR
> >>
> >>   target/riscv/cpu.h                      |  18 +++
> >>   target/riscv/csr.c                      |  42 +++++-
> >>   target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
> >>   target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
> >>   target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
> >>   target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
> >>   target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
> >>   target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
> >>   target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
> >>   target/riscv/translate.c                | 186 ++++++++++++++++++++----
> >>   target/riscv/vector_helper.c            |  54 +++++--
> >>   11 files changed, 414 insertions(+), 111 deletions(-)
> >>
> >> --
> >> 2.17.1
> >>
> >>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-06 10:05       ` Alistair Francis
  0 siblings, 0 replies; 82+ messages in thread
From: Alistair Francis @ 2021-08-06 10:05 UTC (permalink / raw)
  To: LIU Zhiwei
  Cc: qemu-devel@nongnu.org Developers, open list:RISC-V,
	Palmer Dabbelt, Richard Henderson, Bin Meng, Alistair Francis

On Thu, Aug 5, 2021 at 5:15 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>
>
> On 2021/8/5 下午2:01, Alistair Francis wrote:
> > On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
> >> This patch set implements UXL field in mstatus register. Programmer can change
> >> UXLEN by writting to this field. So that you can run a 32 bit program
> >> on a 64 bit CPU.
> > Awesome! Do you have any steps for building a rootFS to test this?
>
> Not yet.  It depends on Linux support which  will not start until
> October.  Maybe as a rough test,
> we can run the 32 glibc test cases on qemu-riscv64 with an option
> uxl32=true(not implement yet).

Hmmm... That's a pain. We really need some way to test this (and
ensure no future breakages occur). But I see the problem of no
software support until this exists.

It sounds like you or a colleague is planning on adding Linux support.
Maybe we will have to wait until that at least exists before this can
go upstream. We could at least review this before hand though, so
thanks for sending the series.

A 32-bit glibc test on qemu-riscv64 would probably also be enough, at
least as a start.

Alistair

>
> Zhiwei
>
> >
> > Alistair
> >
> >> This patch set depends on one patch set by Richard Henderson
> >> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
> >>
> >> LIU Zhiwei (13):
> >>    target/riscv: Add UXL to tb flags
> >>    target/riscv: Support UXL32 for branch instructions
> >>    target/riscv: Support UXL32 on 64-bit cpu for load/store
> >>    target/riscv: Support UXL32 for slit/sltiu
> >>    target/riscv: Support UXL32 for shift instruction
> >>    target/riscv: Fix div instructions
> >>    target/riscv: Support UXL32 for RVM
> >>    target/riscv: Support UXL32 for vector instructions
> >>    target/riscv: Support UXL32 for atomic instructions
> >>    target/riscv: Support UXL32 for float instructions
> >>    target/riscv: Fix srow
> >>    target/riscv: Support UXL32 for RVB
> >>    target/riscv: Changing the width of U-mode CSR
> >>
> >>   target/riscv/cpu.h                      |  18 +++
> >>   target/riscv/csr.c                      |  42 +++++-
> >>   target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
> >>   target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
> >>   target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
> >>   target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
> >>   target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
> >>   target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
> >>   target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
> >>   target/riscv/translate.c                | 186 ++++++++++++++++++++----
> >>   target/riscv/vector_helper.c            |  54 +++++--
> >>   11 files changed, 414 insertions(+), 111 deletions(-)
> >>
> >> --
> >> 2.17.1
> >>
> >>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
  2021-08-06 10:05       ` Alistair Francis
@ 2021-08-09  1:25         ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  1:25 UTC (permalink / raw)
  To: Alistair Francis
  Cc: open list:RISC-V, Bin Meng, Richard Henderson,
	qemu-devel@nongnu.org Developers, Palmer Dabbelt,
	Alistair Francis


On 2021/8/6 下午6:05, Alistair Francis wrote:
> On Thu, Aug 5, 2021 at 5:15 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>
>> On 2021/8/5 下午2:01, Alistair Francis wrote:
>>> On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>>> This patch set implements UXL field in mstatus register. Programmer can change
>>>> UXLEN by writting to this field. So that you can run a 32 bit program
>>>> on a 64 bit CPU.
>>> Awesome! Do you have any steps for building a rootFS to test this?
>> Not yet.  It depends on Linux support which  will not start until
>> October.  Maybe as a rough test,
>> we can run the 32 glibc test cases on qemu-riscv64 with an option
>> uxl32=true(not implement yet).
> Hmmm... That's a pain. We really need some way to test this (and
> ensure no future breakages occur). But I see the problem of no
> software support until this exists.
>
> It sounds like you or a colleague is planning on adding Linux support.
> Maybe we will have to wait until that at least exists before this can
> go upstream. We could at least review this before hand though

Enough for me. Thanks. I will also think more about Richard's advice, 
maybe we can merge 32bit cpu and UXL32 into one in the future.

Zhiwei

> , so
> thanks for sending the series.
>
> A 32-bit glibc test on qemu-riscv64 would probably also be enough, at
> least as a start.
>
> Alistair
>
>> Zhiwei
>>
>>> Alistair
>>>
>>>> This patch set depends on one patch set by Richard Henderson
>>>> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
>>>>
>>>> LIU Zhiwei (13):
>>>>     target/riscv: Add UXL to tb flags
>>>>     target/riscv: Support UXL32 for branch instructions
>>>>     target/riscv: Support UXL32 on 64-bit cpu for load/store
>>>>     target/riscv: Support UXL32 for slit/sltiu
>>>>     target/riscv: Support UXL32 for shift instruction
>>>>     target/riscv: Fix div instructions
>>>>     target/riscv: Support UXL32 for RVM
>>>>     target/riscv: Support UXL32 for vector instructions
>>>>     target/riscv: Support UXL32 for atomic instructions
>>>>     target/riscv: Support UXL32 for float instructions
>>>>     target/riscv: Fix srow
>>>>     target/riscv: Support UXL32 for RVB
>>>>     target/riscv: Changing the width of U-mode CSR
>>>>
>>>>    target/riscv/cpu.h                      |  18 +++
>>>>    target/riscv/csr.c                      |  42 +++++-
>>>>    target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
>>>>    target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
>>>>    target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
>>>>    target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
>>>>    target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
>>>>    target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
>>>>    target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
>>>>    target/riscv/translate.c                | 186 ++++++++++++++++++++----
>>>>    target/riscv/vector_helper.c            |  54 +++++--
>>>>    11 files changed, 414 insertions(+), 111 deletions(-)
>>>>
>>>> --
>>>> 2.17.1
>>>>
>>>>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 00/13] Support UXL field in mstatus
@ 2021-08-09  1:25         ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  1:25 UTC (permalink / raw)
  To: Alistair Francis
  Cc: qemu-devel@nongnu.org Developers, open list:RISC-V,
	Palmer Dabbelt, Richard Henderson, Bin Meng, Alistair Francis


On 2021/8/6 下午6:05, Alistair Francis wrote:
> On Thu, Aug 5, 2021 at 5:15 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>
>> On 2021/8/5 下午2:01, Alistair Francis wrote:
>>> On Thu, Aug 5, 2021 at 12:55 PM LIU Zhiwei <zhiwei_liu@c-sky.com> wrote:
>>>> This patch set implements UXL field in mstatus register. Programmer can change
>>>> UXLEN by writting to this field. So that you can run a 32 bit program
>>>> on a 64 bit CPU.
>>> Awesome! Do you have any steps for building a rootFS to test this?
>> Not yet.  It depends on Linux support which  will not start until
>> October.  Maybe as a rough test,
>> we can run the 32 glibc test cases on qemu-riscv64 with an option
>> uxl32=true(not implement yet).
> Hmmm... That's a pain. We really need some way to test this (and
> ensure no future breakages occur). But I see the problem of no
> software support until this exists.
>
> It sounds like you or a colleague is planning on adding Linux support.
> Maybe we will have to wait until that at least exists before this can
> go upstream. We could at least review this before hand though

Enough for me. Thanks. I will also think more about Richard's advice, 
maybe we can merge 32bit cpu and UXL32 into one in the future.

Zhiwei

> , so
> thanks for sending the series.
>
> A 32-bit glibc test on qemu-riscv64 would probably also be enough, at
> least as a start.
>
> Alistair
>
>> Zhiwei
>>
>>> Alistair
>>>
>>>> This patch set depends on one patch set by Richard Henderson
>>>> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00059.html.
>>>>
>>>> LIU Zhiwei (13):
>>>>     target/riscv: Add UXL to tb flags
>>>>     target/riscv: Support UXL32 for branch instructions
>>>>     target/riscv: Support UXL32 on 64-bit cpu for load/store
>>>>     target/riscv: Support UXL32 for slit/sltiu
>>>>     target/riscv: Support UXL32 for shift instruction
>>>>     target/riscv: Fix div instructions
>>>>     target/riscv: Support UXL32 for RVM
>>>>     target/riscv: Support UXL32 for vector instructions
>>>>     target/riscv: Support UXL32 for atomic instructions
>>>>     target/riscv: Support UXL32 for float instructions
>>>>     target/riscv: Fix srow
>>>>     target/riscv: Support UXL32 for RVB
>>>>     target/riscv: Changing the width of U-mode CSR
>>>>
>>>>    target/riscv/cpu.h                      |  18 +++
>>>>    target/riscv/csr.c                      |  42 +++++-
>>>>    target/riscv/insn_trans/trans_rva.c.inc |  36 ++++-
>>>>    target/riscv/insn_trans/trans_rvb.c.inc |  51 +++++--
>>>>    target/riscv/insn_trans/trans_rvd.c.inc |   4 +-
>>>>    target/riscv/insn_trans/trans_rvf.c.inc |   4 +-
>>>>    target/riscv/insn_trans/trans_rvi.c.inc |  62 ++++++--
>>>>    target/riscv/insn_trans/trans_rvm.c.inc |  24 ++-
>>>>    target/riscv/insn_trans/trans_rvv.c.inc |  44 +++---
>>>>    target/riscv/translate.c                | 186 ++++++++++++++++++++----
>>>>    target/riscv/vector_helper.c            |  54 +++++--
>>>>    11 files changed, 414 insertions(+), 111 deletions(-)
>>>>
>>>> --
>>>> 2.17.1
>>>>
>>>>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-05 19:06     ` Richard Henderson
@ 2021-08-09  1:45       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  1:45 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/6 上午3:06, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
>> +{
>> +    if (reg_num == 0) {
>> +        return ctx->zero;
>> +    }
>> +    if (ctx->uxl32) {
>> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>> +    }
>> +    return cpu_gpr[reg_num];
>> +}
>> +
>> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
>> +{
>> +    if (reg_num == 0) {
>> +        return ctx->zero;
>> +    }
>> +    if (ctx->uxl32) {
>> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>> +    }
>> +    return cpu_gpr[reg_num];
>> +}
>
> This is bad: you cannot modify the source registers like this.

In my opinion, when uxl32, the only meaningful part is the low 32 bits, 
and it doesn't matter to modify the high parts.

>
> These incorrect modifications will be visible to the kernel on 
> transition back to S-mode.

When transition back to S-mode, I think the kernel will save the U-mode 
registers to memory.

Thanks,
Zhiwei

>
>>
>> +static bool gen_branch_u(DisasContext *ctx, arg_b *a, TCGCond cond)
>> +{
>> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
>> +    TCGv src2 = gpr_src_u(ctx, a->rs2);
>> +
>> +    return gen_branch_internal(ctx, a, cond, src1, src2);
>> +}
>
> This is unnecessary.  Unsigned comparisons work just fine with 
> sign-extended values.  It will be simpler to keep all values 
> sign-extended.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-09  1:45       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  1:45 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/6 上午3:06, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
>> +{
>> +    if (reg_num == 0) {
>> +        return ctx->zero;
>> +    }
>> +    if (ctx->uxl32) {
>> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>> +    }
>> +    return cpu_gpr[reg_num];
>> +}
>> +
>> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
>> +{
>> +    if (reg_num == 0) {
>> +        return ctx->zero;
>> +    }
>> +    if (ctx->uxl32) {
>> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>> +    }
>> +    return cpu_gpr[reg_num];
>> +}
>
> This is bad: you cannot modify the source registers like this.

In my opinion, when uxl32, the only meaningful part is the low 32 bits, 
and it doesn't matter to modify the high parts.

>
> These incorrect modifications will be visible to the kernel on 
> transition back to S-mode.

When transition back to S-mode, I think the kernel will save the U-mode 
registers to memory.

Thanks,
Zhiwei

>
>>
>> +static bool gen_branch_u(DisasContext *ctx, arg_b *a, TCGCond cond)
>> +{
>> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
>> +    TCGv src2 = gpr_src_u(ctx, a->rs2);
>> +
>> +    return gen_branch_internal(ctx, a, cond, src1, src2);
>> +}
>
> This is unnecessary.  Unsigned comparisons work just fine with 
> sign-extended values.  It will be simpler to keep all values 
> sign-extended.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store
  2021-08-05 19:08     ` Richard Henderson
@ 2021-08-09  1:50       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  1:50 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/6 上午3:08, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> Get the LSB 32 bits and zero-extend as the base address.
>>
>> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
>> ---
>>   target/riscv/insn_trans/trans_rvi.c.inc | 4 ++--
>>   1 file changed, 2 insertions(+), 2 deletions(-)
>>
>> diff --git a/target/riscv/insn_trans/trans_rvi.c.inc 
>> b/target/riscv/insn_trans/trans_rvi.c.inc
>> index ea41d1de2d..6823a6b3e0 100644
>> --- a/target/riscv/insn_trans/trans_rvi.c.inc
>> +++ b/target/riscv/insn_trans/trans_rvi.c.inc
>> @@ -163,7 +163,7 @@ static bool trans_bgeu(DisasContext *ctx, 
>> arg_bgeu *a)
>>   static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
>>   {
>>       TCGv dest = gpr_dst(ctx, a->rd);
>> -    TCGv addr = gpr_src(ctx, a->rs1);
>> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>>       TCGv temp = NULL;
>>         if (a->imm) {
>> @@ -207,7 +207,7 @@ static bool trans_lhu(DisasContext *ctx, arg_lhu *a)
>>     static bool gen_store(DisasContext *ctx, arg_sb *a, MemOp memop)
>>   {
>> -    TCGv addr = gpr_src(ctx, a->rs1);
>> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>>       TCGv data = gpr_src(ctx, a->rs2);
>>       TCGv temp = NULL;
>
> This is incorrect.  The zero-extension should happen after the 
> addition of the immediate offset.

Thanks. I think you are right. I mistook the immediate will be signed to 
target_ulong.

Zhiwei

>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store
@ 2021-08-09  1:50       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  1:50 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/6 上午3:08, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> Get the LSB 32 bits and zero-extend as the base address.
>>
>> Signed-off-by: LIU Zhiwei <zhiwei_liu@c-sky.com>
>> ---
>>   target/riscv/insn_trans/trans_rvi.c.inc | 4 ++--
>>   1 file changed, 2 insertions(+), 2 deletions(-)
>>
>> diff --git a/target/riscv/insn_trans/trans_rvi.c.inc 
>> b/target/riscv/insn_trans/trans_rvi.c.inc
>> index ea41d1de2d..6823a6b3e0 100644
>> --- a/target/riscv/insn_trans/trans_rvi.c.inc
>> +++ b/target/riscv/insn_trans/trans_rvi.c.inc
>> @@ -163,7 +163,7 @@ static bool trans_bgeu(DisasContext *ctx, 
>> arg_bgeu *a)
>>   static bool gen_load(DisasContext *ctx, arg_lb *a, MemOp memop)
>>   {
>>       TCGv dest = gpr_dst(ctx, a->rd);
>> -    TCGv addr = gpr_src(ctx, a->rs1);
>> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>>       TCGv temp = NULL;
>>         if (a->imm) {
>> @@ -207,7 +207,7 @@ static bool trans_lhu(DisasContext *ctx, arg_lhu *a)
>>     static bool gen_store(DisasContext *ctx, arg_sb *a, MemOp memop)
>>   {
>> -    TCGv addr = gpr_src(ctx, a->rs1);
>> +    TCGv addr = gpr_src_u(ctx, a->rs1);
>>       TCGv data = gpr_src(ctx, a->rs2);
>>       TCGv temp = NULL;
>
> This is incorrect.  The zero-extension should happen after the 
> addition of the immediate offset.

Thanks. I think you are right. I mistook the immediate will be signed to 
target_ulong.

Zhiwei

>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu
  2021-08-05 19:09     ` Richard Henderson
@ 2021-08-09  7:28       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  7:28 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/6 上午3:09, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> +static bool gen_arith_simm_tl(DisasContext *ctx, arg_i *a,
>> +                              void (*func)(TCGv, TCGv, TCGv))
>> +{
>> +    TCGv dest = gpr_dst(ctx, a->rd);
>> +    TCGv src1 = gpr_src_s(ctx, a->rs1);
>> +    TCGv src2 = tcg_constant_tl(a->imm);
>> +
>> +    (*func)(dest, src1, src2);
>> +    return true;
>> +}
>> +
>> +static bool gen_arith_uimm_tl(DisasContext *ctx, arg_i *a,
>> +                              void (*func)(TCGv, TCGv, TCGv))
>> +{
>> +    TCGv dest = gpr_dst(ctx, a->rd);
>> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
>> +    TCGv src2 = tcg_constant_tl(ctx->uxl32 ? a->imm & UINT32_MAX : 
>> a->imm);
>> +
>> +    (*func)(dest, src1, src2);
>> +    return true;
>> +}
>
> Again, unsigned comparisions work fine with sign-extended inputs.
>
Thanks. Fix it in next patch set.

Zhiwei

>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu
@ 2021-08-09  7:28       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  7:28 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/6 上午3:09, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> +static bool gen_arith_simm_tl(DisasContext *ctx, arg_i *a,
>> +                              void (*func)(TCGv, TCGv, TCGv))
>> +{
>> +    TCGv dest = gpr_dst(ctx, a->rd);
>> +    TCGv src1 = gpr_src_s(ctx, a->rs1);
>> +    TCGv src2 = tcg_constant_tl(a->imm);
>> +
>> +    (*func)(dest, src1, src2);
>> +    return true;
>> +}
>> +
>> +static bool gen_arith_uimm_tl(DisasContext *ctx, arg_i *a,
>> +                              void (*func)(TCGv, TCGv, TCGv))
>> +{
>> +    TCGv dest = gpr_dst(ctx, a->rd);
>> +    TCGv src1 = gpr_src_u(ctx, a->rs1);
>> +    TCGv src2 = tcg_constant_tl(ctx->uxl32 ? a->imm & UINT32_MAX : 
>> a->imm);
>> +
>> +    (*func)(dest, src1, src2);
>> +    return true;
>> +}
>
> Again, unsigned comparisions work fine with sign-extended inputs.
>
Thanks. Fix it in next patch set.

Zhiwei

>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction
  2021-08-05 22:17     ` Richard Henderson
@ 2021-08-09  7:51       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  7:51 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/6 上午6:17, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>>   static bool trans_srli(DisasContext *ctx, arg_srli *a)
>>   {
>> +    if (ctx->uxl32) {
>> +        return trans_srliw(ctx, a);
>> +    }
>>       return gen_shifti(ctx, a, tcg_gen_shr_tl);
>>   }
>
> First, trans_srliw begins with REQUIRE_64BIT, which *should* fail when 
> RV32 is in effect.  This means there's a missing change to is_32bit().

As I have replied in another patch, ctx->uxl32 already indicats 64 bit 
CPU.  Anyway, I will think more about how to merge is_32bit() and uxl32 
in next patch set.

>
> Second, the current decode for srli allows 7 bits of shift, while 
> srilw only allows 5.  As a consequence, gen_shifti contains a check 
> for TARGET_LONG_BITS and trans_srliw does not contain a check at all.  
> We need to diagnose an out-of-range shift for RV32 somewhere.
>
Yes, it's not proper directly use *w here.  Fix it in next patch set.

Zhiwei

> I recommend extending the gen_shift* family of helpers.
>
> static bool gen_shifti_imm(DisasContext *ctx, arg_shift *a, int width,
>                            void (*func)(TCGv, TCGv, target_long))
> {
>     TCGv dest, src1;
>
>     if (a->shamt >= width) {
>         return false;
>     }
>     dest = gpr_dst(ctx, a->rd);
>     src1 = gpr_src(ctx, a->rs1);
>     func(dest, src1, a->shamt);
>     return true;
> }
>
> static bool gen_shifti(DisasContext *ctx, arg_shift *a, int width,
>                        void (*func)(TCGv, TCGv, TCGv))
> {...}
>
> static void gen_srliw(TCGv dest, TCGv src1, target_long shamt)
> {
>     tcg_gen_extract_tl(dest, src1, shamt, 32 - shamt);
>     tcg_gen_ext32s_tl(dest, dest);
> }
>
> static bool trans_srliw(DisasContext *ctx, arg_shift *a)
> {
>     REQUIRE_64BIT(ctx);
>     return gen_shifti_imm(ctx, a, 32, gen_srliw);
> }
>
> static bool trans_srli(DisasContext *ctx, arg_shift *a)
> {
>     int xlen = is_32bit(ctx) ? 32 : 64;
>     return gen_shifti_imm(ctx, a, xlen,
>                           xlen == TARGET_LONG_BITS
>                           ? tcg_gen_shri_tl : gen_srliw);
> }
>
> etc.  Perhaps that is_32bit() check above could be consolidated into 
> some macro/inline.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction
@ 2021-08-09  7:51       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  7:51 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/6 上午6:17, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>>   static bool trans_srli(DisasContext *ctx, arg_srli *a)
>>   {
>> +    if (ctx->uxl32) {
>> +        return trans_srliw(ctx, a);
>> +    }
>>       return gen_shifti(ctx, a, tcg_gen_shr_tl);
>>   }
>
> First, trans_srliw begins with REQUIRE_64BIT, which *should* fail when 
> RV32 is in effect.  This means there's a missing change to is_32bit().

As I have replied in another patch, ctx->uxl32 already indicats 64 bit 
CPU.  Anyway, I will think more about how to merge is_32bit() and uxl32 
in next patch set.

>
> Second, the current decode for srli allows 7 bits of shift, while 
> srilw only allows 5.  As a consequence, gen_shifti contains a check 
> for TARGET_LONG_BITS and trans_srliw does not contain a check at all.  
> We need to diagnose an out-of-range shift for RV32 somewhere.
>
Yes, it's not proper directly use *w here.  Fix it in next patch set.

Zhiwei

> I recommend extending the gen_shift* family of helpers.
>
> static bool gen_shifti_imm(DisasContext *ctx, arg_shift *a, int width,
>                            void (*func)(TCGv, TCGv, target_long))
> {
>     TCGv dest, src1;
>
>     if (a->shamt >= width) {
>         return false;
>     }
>     dest = gpr_dst(ctx, a->rd);
>     src1 = gpr_src(ctx, a->rs1);
>     func(dest, src1, a->shamt);
>     return true;
> }
>
> static bool gen_shifti(DisasContext *ctx, arg_shift *a, int width,
>                        void (*func)(TCGv, TCGv, TCGv))
> {...}
>
> static void gen_srliw(TCGv dest, TCGv src1, target_long shamt)
> {
>     tcg_gen_extract_tl(dest, src1, shamt, 32 - shamt);
>     tcg_gen_ext32s_tl(dest, dest);
> }
>
> static bool trans_srliw(DisasContext *ctx, arg_shift *a)
> {
>     REQUIRE_64BIT(ctx);
>     return gen_shifti_imm(ctx, a, 32, gen_srliw);
> }
>
> static bool trans_srli(DisasContext *ctx, arg_shift *a)
> {
>     int xlen = is_32bit(ctx) ? 32 : 64;
>     return gen_shifti_imm(ctx, a, xlen,
>                           xlen == TARGET_LONG_BITS
>                           ? tcg_gen_shri_tl : gen_srliw);
> }
>
> etc.  Perhaps that is_32bit() check above could be consolidated into 
> some macro/inline.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 06/13] target/riscv: Fix div instructions
  2021-08-05 22:18     ` Richard Henderson
@ 2021-08-09  7:53       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  7:53 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/6 上午6:18, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> Don't overwrite global source register after
>> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00058.html.
>>
>> Signed-off-by: LIU Zhiwei<zhiwei_liu@c-sky.com>
>> ---
>>   target/riscv/translate.c | 46 +++++++++++++++++++++++-----------------
>>   1 file changed, 26 insertions(+), 20 deletions(-)
>
> FWIW, I have a cleanup to these routines that does more than add 
> temps.  I've been slow to re-post the series; sorry about that.
>
Look forward to your next patch set. I will send my next patch set based 
on your new post.

Thanks,
Zhiwei

> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 06/13] target/riscv: Fix div instructions
@ 2021-08-09  7:53       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-09  7:53 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/6 上午6:18, Richard Henderson wrote:
> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>> Don't overwrite global source register after
>> https://lists.gnu.org/archive/html/qemu-riscv/2021-07/msg00058.html.
>>
>> Signed-off-by: LIU Zhiwei<zhiwei_liu@c-sky.com>
>> ---
>>   target/riscv/translate.c | 46 +++++++++++++++++++++++-----------------
>>   1 file changed, 26 insertions(+), 20 deletions(-)
>
> FWIW, I have a cleanup to these routines that does more than add 
> temps.  I've been slow to re-post the series; sorry about that.
>
Look forward to your next patch set. I will send my next patch set based 
on your new post.

Thanks,
Zhiwei

> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-09  1:45       ` LIU Zhiwei
@ 2021-08-09 19:34         ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-09 19:34 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/8/21 3:45 PM, LIU Zhiwei wrote:
> 
> On 2021/8/6 上午3:06, Richard Henderson wrote:
>> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>>> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
>>> +{
>>> +    if (reg_num == 0) {
>>> +        return ctx->zero;
>>> +    }
>>> +    if (ctx->uxl32) {
>>> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>> +    }
>>> +    return cpu_gpr[reg_num];
>>> +}
>>> +
>>> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
>>> +{
>>> +    if (reg_num == 0) {
>>> +        return ctx->zero;
>>> +    }
>>> +    if (ctx->uxl32) {
>>> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>> +    }
>>> +    return cpu_gpr[reg_num];
>>> +}
>>
>> This is bad: you cannot modify the source registers like this.
> 
> In my opinion, when uxl32, the only meaningful part is the low 32 bits, and it doesn't 
> matter to modify the high parts.

Then why does the architecture manual specify that when registers are modified the value 
written sign-extended?  This effect should be visible...

> 
>>
>> These incorrect modifications will be visible to the kernel on transition back to S-mode.
> 
> When transition back to S-mode, I think the kernel will save the U-mode registers to memory.

... here.  Once we're in S-mode, we have SXLEN, and if SXLEN > UXLEN, the high part of the 
register will be visible.  It really must be either (1) sign-extended because U-mode wrote 
to the register or (2) unmodified from the last time S-mode wrote to the register.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-09 19:34         ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-09 19:34 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/8/21 3:45 PM, LIU Zhiwei wrote:
> 
> On 2021/8/6 上午3:06, Richard Henderson wrote:
>> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>>> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
>>> +{
>>> +    if (reg_num == 0) {
>>> +        return ctx->zero;
>>> +    }
>>> +    if (ctx->uxl32) {
>>> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>> +    }
>>> +    return cpu_gpr[reg_num];
>>> +}
>>> +
>>> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
>>> +{
>>> +    if (reg_num == 0) {
>>> +        return ctx->zero;
>>> +    }
>>> +    if (ctx->uxl32) {
>>> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>> +    }
>>> +    return cpu_gpr[reg_num];
>>> +}
>>
>> This is bad: you cannot modify the source registers like this.
> 
> In my opinion, when uxl32, the only meaningful part is the low 32 bits, and it doesn't 
> matter to modify the high parts.

Then why does the architecture manual specify that when registers are modified the value 
written sign-extended?  This effect should be visible...

> 
>>
>> These incorrect modifications will be visible to the kernel on transition back to S-mode.
> 
> When transition back to S-mode, I think the kernel will save the U-mode registers to memory.

... here.  Once we're in S-mode, we have SXLEN, and if SXLEN > UXLEN, the high part of the 
register will be visible.  It really must be either (1) sign-extended because U-mode wrote 
to the register or (2) unmodified from the last time S-mode wrote to the register.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-09 19:34         ` Richard Henderson
@ 2021-08-11 14:57           ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-11 14:57 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/10 上午3:34, Richard Henderson wrote:
> On 8/8/21 3:45 PM, LIU Zhiwei wrote:
>>
>> On 2021/8/6 上午3:06, Richard Henderson wrote:
>>> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>>>> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
>>>> +{
>>>> +    if (reg_num == 0) {
>>>> +        return ctx->zero;
>>>> +    }
>>>> +    if (ctx->uxl32) {
>>>> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>>> +    }
>>>> +    return cpu_gpr[reg_num];
>>>> +}
>>>> +
>>>> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
>>>> +{
>>>> +    if (reg_num == 0) {
>>>> +        return ctx->zero;
>>>> +    }
>>>> +    if (ctx->uxl32) {
>>>> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>>> +    }
>>>> +    return cpu_gpr[reg_num];
>>>> +}
>>>
>>> This is bad: you cannot modify the source registers like this.
>>
>> In my opinion, when uxl32, the only meaningful part is the low 32 
>> bits, and it doesn't matter to modify the high parts.
>
> Then why does the architecture manual specify that when registers are 
> modified the value written sign-extended?  This effect should be 
> visible...
>
Hi Richard,

I  still don't know why the value written sign-extended.  If that's the 
the rule of final specification, I will try to obey it although our 
Linux will not depend on the high part.

Thanks,
Zhiwei

>>
>>>
>>> These incorrect modifications will be visible to the kernel on 
>>> transition back to S-mode.
>>
>> When transition back to S-mode, I think the kernel will save the 
>> U-mode registers to memory.
>
> ... here.  Once we're in S-mode, we have SXLEN, and if SXLEN > UXLEN, 
> the high part of the register will be visible.  It really must be 
> either (1) sign-extended because U-mode wrote to the register or (2) 
> unmodified from the last time S-mode wrote to the register.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-11 14:57           ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-11 14:57 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/10 上午3:34, Richard Henderson wrote:
> On 8/8/21 3:45 PM, LIU Zhiwei wrote:
>>
>> On 2021/8/6 上午3:06, Richard Henderson wrote:
>>> On 8/4/21 4:53 PM, LIU Zhiwei wrote:
>>>> +static TCGv gpr_src_u(DisasContext *ctx, int reg_num)
>>>> +{
>>>> +    if (reg_num == 0) {
>>>> +        return ctx->zero;
>>>> +    }
>>>> +    if (ctx->uxl32) {
>>>> +        tcg_gen_ext32u_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>>> +    }
>>>> +    return cpu_gpr[reg_num];
>>>> +}
>>>> +
>>>> +static TCGv gpr_src_s(DisasContext *ctx, int reg_num)
>>>> +{
>>>> +    if (reg_num == 0) {
>>>> +        return ctx->zero;
>>>> +    }
>>>> +    if (ctx->uxl32) {
>>>> +        tcg_gen_ext32s_tl(cpu_gpr[reg_num], cpu_gpr[reg_num]);
>>>> +    }
>>>> +    return cpu_gpr[reg_num];
>>>> +}
>>>
>>> This is bad: you cannot modify the source registers like this.
>>
>> In my opinion, when uxl32, the only meaningful part is the low 32 
>> bits, and it doesn't matter to modify the high parts.
>
> Then why does the architecture manual specify that when registers are 
> modified the value written sign-extended?  This effect should be 
> visible...
>
Hi Richard,

I  still don't know why the value written sign-extended.  If that's the 
the rule of final specification, I will try to obey it although our 
Linux will not depend on the high part.

Thanks,
Zhiwei

>>
>>>
>>> These incorrect modifications will be visible to the kernel on 
>>> transition back to S-mode.
>>
>> When transition back to S-mode, I think the kernel will save the 
>> U-mode registers to memory.
>
> ... here.  Once we're in S-mode, we have SXLEN, and if SXLEN > UXLEN, 
> the high part of the register will be visible.  It really must be 
> either (1) sign-extended because U-mode wrote to the register or (2) 
> unmodified from the last time S-mode wrote to the register.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-11 14:57           ` LIU Zhiwei
@ 2021-08-11 17:56             ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-11 17:56 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/11/21 4:57 AM, LIU Zhiwei wrote:
> I  still don't know why the value written sign-extended.  If that's the the rule of final 
> specification, I will try to obey it although our Linux will not depend on the high part.

The text that I'm looking at is

https://github.com/riscv/riscv-isa-manual/releases/download/Ratified-IMFDQC-and-Priv-v1.11/riscv-privileged-20190608.pdf

3.1.6.2 Base ISA Control in mstatus Register

In the fifth paragraph, the requirement for sign-extension is detailed.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-11 17:56             ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-11 17:56 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/11/21 4:57 AM, LIU Zhiwei wrote:
> I  still don't know why the value written sign-extended.  If that's the the rule of final 
> specification, I will try to obey it although our Linux will not depend on the high part.

The text that I'm looking at is

https://github.com/riscv/riscv-isa-manual/releases/download/Ratified-IMFDQC-and-Priv-v1.11/riscv-privileged-20190608.pdf

3.1.6.2 Base ISA Control in mstatus Register

In the fifth paragraph, the requirement for sign-extension is detailed.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-11 17:56             ` Richard Henderson
@ 2021-08-11 22:40               ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-11 22:40 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis

[-- Attachment #1: Type: text/plain, Size: 1254 bytes --]


On 2021/8/12 上午1:56, Richard Henderson wrote:
> On 8/11/21 4:57 AM, LIU Zhiwei wrote:
>> I  still don't know why the value written sign-extended.  If that's 
>> the the rule of final specification, I will try to obey it although 
>> our Linux will not depend on the high part.
>
> The text that I'm looking at is
>
> https://github.com/riscv/riscv-isa-manual/releases/download/Ratified-IMFDQC-and-Priv-v1.11/riscv-privileged-20190608.pdf 
>
>
> 3.1.6.2 Base ISA Control in mstatus Register
>
> In the fifth paragraph, the requirement for sign-extension is detailed.
>
Thanks. I have already seen this rule.

/"Whenever XLEN in any mode is set to a value less than the widest 
supported XLEN, all operations////must ignore source operand register bits above the configured XLEN, and 
must sign-extend results////to fill the entire widest supported XLEN in the destination register.//" /

I still don't know why the specification has this constraint. It just 
requires that fill hardware registers with defined sign-extension value.
But it doesn't give the real benefit of this constraint.

If the software doesn't use the high part, who cares the really value in 
high part? Do you know the benefit?  Thanks again.

Best Regards,
Zhiwei//

>
> r~

[-- Attachment #2: Type: text/html, Size: 2200 bytes --]

^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-11 22:40               ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-11 22:40 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng

[-- Attachment #1: Type: text/plain, Size: 1254 bytes --]


On 2021/8/12 上午1:56, Richard Henderson wrote:
> On 8/11/21 4:57 AM, LIU Zhiwei wrote:
>> I  still don't know why the value written sign-extended.  If that's 
>> the the rule of final specification, I will try to obey it although 
>> our Linux will not depend on the high part.
>
> The text that I'm looking at is
>
> https://github.com/riscv/riscv-isa-manual/releases/download/Ratified-IMFDQC-and-Priv-v1.11/riscv-privileged-20190608.pdf 
>
>
> 3.1.6.2 Base ISA Control in mstatus Register
>
> In the fifth paragraph, the requirement for sign-extension is detailed.
>
Thanks. I have already seen this rule.

/"Whenever XLEN in any mode is set to a value less than the widest 
supported XLEN, all operations////must ignore source operand register bits above the configured XLEN, and 
must sign-extend results////to fill the entire widest supported XLEN in the destination register.//" /

I still don't know why the specification has this constraint. It just 
requires that fill hardware registers with defined sign-extension value.
But it doesn't give the real benefit of this constraint.

If the software doesn't use the high part, who cares the really value in 
high part? Do you know the benefit?  Thanks again.

Best Regards,
Zhiwei//

>
> r~

[-- Attachment #2: Type: text/html, Size: 2200 bytes --]

^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-11 22:40               ` LIU Zhiwei
@ 2021-08-12  4:42                 ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-12  4:42 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/11/21 12:40 PM, LIU Zhiwei wrote:
> If the software doesn't use the high part, who cares the really value in high part? Do you 
> know the benefit?  Thanks again.

I do not.

I simply presume that they already have the hardware, in the form of the addw instruction, 
etc.

The mistake, I think, was changing the definition of "add" in the first place, which 
required the addition of a different opcode "addw", which is then undefined for RV32. 
They should simply have had "addw" and "addq" as different opcodes that didn't change 
behaviour.  Etc.

But what's done is done.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-12  4:42                 ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-12  4:42 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/11/21 12:40 PM, LIU Zhiwei wrote:
> If the software doesn't use the high part, who cares the really value in high part? Do you 
> know the benefit?  Thanks again.

I do not.

I simply presume that they already have the hardware, in the form of the addw instruction, 
etc.

The mistake, I think, was changing the definition of "add" in the first place, which 
required the addition of a different opcode "addw", which is then undefined for RV32. 
They should simply have had "addw" and "addq" as different opcodes that didn't change 
behaviour.  Etc.

But what's done is done.


r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-12  4:42                 ` Richard Henderson
@ 2021-08-12  5:03                   ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-12  5:03 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/12 下午12:42, Richard Henderson wrote:
> On 8/11/21 12:40 PM, LIU Zhiwei wrote:
>> If the software doesn't use the high part, who cares the really value 
>> in high part? Do you know the benefit?  Thanks again.
>
> I do not.
>
> I simply presume that they already have the hardware, in the form of 
> the addw instruction, etc.
>
> The mistake, I think, was changing the definition of "add" in the 
> first place, which required the addition of a different opcode "addw", 
> which is then undefined for RV32. 

Sorry, I don't get "the mistake" here. Do you think the specification is 
not right.
Or the QEMU implementation of this patch set is not right?
Currently I don't know there is  a 64-bit hardware which has done with 
UXL32.

> They should simply have had "addw" and "addq" as different opcodes 
> that didn't change behaviour.  Etc.

I don't get  this statement. Is it related to UXL32?

Best Regards,
Zhiwei

>
> But what's done is done.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-12  5:03                   ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-12  5:03 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/12 下午12:42, Richard Henderson wrote:
> On 8/11/21 12:40 PM, LIU Zhiwei wrote:
>> If the software doesn't use the high part, who cares the really value 
>> in high part? Do you know the benefit?  Thanks again.
>
> I do not.
>
> I simply presume that they already have the hardware, in the form of 
> the addw instruction, etc.
>
> The mistake, I think, was changing the definition of "add" in the 
> first place, which required the addition of a different opcode "addw", 
> which is then undefined for RV32. 

Sorry, I don't get "the mistake" here. Do you think the specification is 
not right.
Or the QEMU implementation of this patch set is not right?
Currently I don't know there is  a 64-bit hardware which has done with 
UXL32.

> They should simply have had "addw" and "addq" as different opcodes 
> that didn't change behaviour.  Etc.

I don't get  this statement. Is it related to UXL32?

Best Regards,
Zhiwei

>
> But what's done is done.
>
>
> r~


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-12  5:03                   ` LIU Zhiwei
@ 2021-08-12  6:12                     ` Richard Henderson
  -1 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-12  6:12 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: palmer, bin.meng, Alistair.Francis

On 8/11/21 7:03 PM, LIU Zhiwei wrote:
> 
> On 2021/8/12 下午12:42, Richard Henderson wrote:
>> On 8/11/21 12:40 PM, LIU Zhiwei wrote:
>>> If the software doesn't use the high part, who cares the really value in high part? Do 
>>> you know the benefit?  Thanks again.
>>
>> I do not.
>>
>> I simply presume that they already have the hardware, in the form of the addw 
>> instruction, etc.
>>
>> The mistake, I think, was changing the definition of "add" in the first place, which 
>> required the addition of a different opcode "addw", which is then undefined for RV32. 
> 
> Sorry, I don't get "the mistake" here. Do you think the specification is not right.

I was critiquing the development of the risc-v specification, in that there are 
complications in the current specification that could have been foreseen and avoided with 
different choices years ago.


>> They should simply have had "addw" and "addq" as different opcodes that didn't change 
>> behaviour.  Etc.
> 
> I don't get  this statement. Is it related to UXL32?

No.  I was just musing.  It's not important.


r~



^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-12  6:12                     ` Richard Henderson
  0 siblings, 0 replies; 82+ messages in thread
From: Richard Henderson @ 2021-08-12  6:12 UTC (permalink / raw)
  To: LIU Zhiwei, qemu-devel, qemu-riscv; +Cc: Alistair.Francis, palmer, bin.meng

On 8/11/21 7:03 PM, LIU Zhiwei wrote:
> 
> On 2021/8/12 下午12:42, Richard Henderson wrote:
>> On 8/11/21 12:40 PM, LIU Zhiwei wrote:
>>> If the software doesn't use the high part, who cares the really value in high part? Do 
>>> you know the benefit?  Thanks again.
>>
>> I do not.
>>
>> I simply presume that they already have the hardware, in the form of the addw 
>> instruction, etc.
>>
>> The mistake, I think, was changing the definition of "add" in the first place, which 
>> required the addition of a different opcode "addw", which is then undefined for RV32. 
> 
> Sorry, I don't get "the mistake" here. Do you think the specification is not right.

I was critiquing the development of the risc-v specification, in that there are 
complications in the current specification that could have been foreseen and avoided with 
different choices years ago.


>> They should simply have had "addw" and "addq" as different opcodes that didn't change 
>> behaviour.  Etc.
> 
> I don't get  this statement. Is it related to UXL32?

No.  I was just musing.  It's not important.


r~



^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
  2021-08-12  6:12                     ` Richard Henderson
@ 2021-08-12  7:20                       ` LIU Zhiwei
  -1 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-12  7:20 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: palmer, bin.meng, Alistair.Francis


On 2021/8/12 下午2:12, Richard Henderson wrote:
> On 8/11/21 7:03 PM, LIU Zhiwei wrote:
>>
>> On 2021/8/12 下午12:42, Richard Henderson wrote:
>>> On 8/11/21 12:40 PM, LIU Zhiwei wrote:
>>>> If the software doesn't use the high part, who cares the really 
>>>> value in high part? Do you know the benefit?  Thanks again.
>>>
>>> I do not.
>>>
>>> I simply presume that they already have the hardware, in the form of 
>>> the addw instruction, etc.
>>>
>>> The mistake, I think, was changing the definition of "add" in the 
>>> first place, which required the addition of a different opcode 
>>> "addw", which is then undefined for RV32. 
>>
>> Sorry, I don't get "the mistake" here. Do you think the specification 
>> is not right.
>
> I was critiquing the development of the risc-v specification, in that 
> there are complications in the current specification that could have 
> been foreseen and avoided with different choices years ago.
>
>
>>> They should simply have had "addw" and "addq" as different opcodes 
>>> that didn't change behaviour. Etc.
>>
>> I don't get  this statement. Is it related to UXL32?
>
> No.  I was just musing.  It's not important.
>
>
Although I don't know what really you mean, I think "addw" and "addq" 
will be better than current "addw" and "add".
At least we can avoid adjust almost every instruction like "add" for UXL32.

Best Regards,
Zhiwei

> r~
>


^ permalink raw reply	[flat|nested] 82+ messages in thread

* Re: [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions
@ 2021-08-12  7:20                       ` LIU Zhiwei
  0 siblings, 0 replies; 82+ messages in thread
From: LIU Zhiwei @ 2021-08-12  7:20 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel, qemu-riscv
  Cc: Alistair.Francis, palmer, bin.meng


On 2021/8/12 下午2:12, Richard Henderson wrote:
> On 8/11/21 7:03 PM, LIU Zhiwei wrote:
>>
>> On 2021/8/12 下午12:42, Richard Henderson wrote:
>>> On 8/11/21 12:40 PM, LIU Zhiwei wrote:
>>>> If the software doesn't use the high part, who cares the really 
>>>> value in high part? Do you know the benefit?  Thanks again.
>>>
>>> I do not.
>>>
>>> I simply presume that they already have the hardware, in the form of 
>>> the addw instruction, etc.
>>>
>>> The mistake, I think, was changing the definition of "add" in the 
>>> first place, which required the addition of a different opcode 
>>> "addw", which is then undefined for RV32. 
>>
>> Sorry, I don't get "the mistake" here. Do you think the specification 
>> is not right.
>
> I was critiquing the development of the risc-v specification, in that 
> there are complications in the current specification that could have 
> been foreseen and avoided with different choices years ago.
>
>
>>> They should simply have had "addw" and "addq" as different opcodes 
>>> that didn't change behaviour. Etc.
>>
>> I don't get  this statement. Is it related to UXL32?
>
> No.  I was just musing.  It's not important.
>
>
Although I don't know what really you mean, I think "addw" and "addq" 
will be better than current "addw" and "add".
At least we can avoid adjust almost every instruction like "add" for UXL32.

Best Regards,
Zhiwei

> r~
>


^ permalink raw reply	[flat|nested] 82+ messages in thread

end of thread, other threads:[~2021-08-12  7:21 UTC | newest]

Thread overview: 82+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-08-05  2:52 [RFC PATCH 00/13] Support UXL field in mstatus LIU Zhiwei
2021-08-05  2:52 ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 01/13] target/riscv: Add UXL to tb flags LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  6:00   ` Alistair Francis
2021-08-05  6:00     ` Alistair Francis
2021-08-05 19:01   ` Richard Henderson
2021-08-05 19:01     ` Richard Henderson
2021-08-06  2:49     ` LIU Zhiwei
2021-08-06  2:49       ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 02/13] target/riscv: Support UXL32 for branch instructions LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05 19:06   ` Richard Henderson
2021-08-05 19:06     ` Richard Henderson
2021-08-09  1:45     ` LIU Zhiwei
2021-08-09  1:45       ` LIU Zhiwei
2021-08-09 19:34       ` Richard Henderson
2021-08-09 19:34         ` Richard Henderson
2021-08-11 14:57         ` LIU Zhiwei
2021-08-11 14:57           ` LIU Zhiwei
2021-08-11 17:56           ` Richard Henderson
2021-08-11 17:56             ` Richard Henderson
2021-08-11 22:40             ` LIU Zhiwei
2021-08-11 22:40               ` LIU Zhiwei
2021-08-12  4:42               ` Richard Henderson
2021-08-12  4:42                 ` Richard Henderson
2021-08-12  5:03                 ` LIU Zhiwei
2021-08-12  5:03                   ` LIU Zhiwei
2021-08-12  6:12                   ` Richard Henderson
2021-08-12  6:12                     ` Richard Henderson
2021-08-12  7:20                     ` LIU Zhiwei
2021-08-12  7:20                       ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 03/13] target/riscv: Support UXL32 on 64-bit cpu for load/store LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05 19:08   ` Richard Henderson
2021-08-05 19:08     ` Richard Henderson
2021-08-09  1:50     ` LIU Zhiwei
2021-08-09  1:50       ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 04/13] target/riscv: Support UXL32 for slit/sltiu LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05 19:09   ` Richard Henderson
2021-08-05 19:09     ` Richard Henderson
2021-08-09  7:28     ` LIU Zhiwei
2021-08-09  7:28       ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 05/13] target/riscv: Support UXL32 for shift instruction LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05 22:17   ` Richard Henderson
2021-08-05 22:17     ` Richard Henderson
2021-08-09  7:51     ` LIU Zhiwei
2021-08-09  7:51       ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 06/13] target/riscv: Fix div instructions LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05 22:18   ` Richard Henderson
2021-08-05 22:18     ` Richard Henderson
2021-08-09  7:53     ` LIU Zhiwei
2021-08-09  7:53       ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 07/13] target/riscv: Support UXL32 for RVM LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 08/13] target/riscv: Support UXL32 for vector instructions LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 09/13] target/riscv: Support UXL32 for atomic instructions LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 10/13] target/riscv: Support UXL32 for float instructions LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 11/13] target/riscv: Fix srow LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 12/13] target/riscv: Support UXL32 for RVB LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  2:53 ` [RFC PATCH 13/13] target/riscv: Changing the width of U-mode CSR LIU Zhiwei
2021-08-05  2:53   ` LIU Zhiwei
2021-08-05  6:01 ` [RFC PATCH 00/13] Support UXL field in mstatus Alistair Francis
2021-08-05  6:01   ` Alistair Francis
2021-08-05  7:14   ` LIU Zhiwei
2021-08-05  7:14     ` LIU Zhiwei
2021-08-05  7:20     ` Bin Meng
2021-08-05  7:20       ` Bin Meng
2021-08-05  8:10       ` LIU Zhiwei
2021-08-05  8:10         ` LIU Zhiwei
2021-08-06 10:05     ` Alistair Francis
2021-08-06 10:05       ` Alistair Francis
2021-08-09  1:25       ` LIU Zhiwei
2021-08-09  1:25         ` LIU Zhiwei

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.