From: Alistair Francis <alistair.francis@opensource.wdc.com>
To: qemu-devel@nongnu.org
Cc: alistair23@gmail.com,
Richard Henderson <richard.henderson@linaro.org>,
Daniel Henrique Barboza <dbarboza@ventanamicro.com>,
Alistair Francis <alistair.francis@wdc.com>
Subject: [PULL 35/37] target/riscv: Introduce helper_set_rounding_mode_chkfrm
Date: Fri, 20 Jan 2023 17:39:11 +1000 [thread overview]
Message-ID: <20230120073913.1028407-36-alistair.francis@opensource.wdc.com> (raw)
In-Reply-To: <20230120073913.1028407-1-alistair.francis@opensource.wdc.com>
From: Richard Henderson <richard.henderson@linaro.org>
The new helper always validates the contents of FRM, even
if the new rounding mode is not DYN. This is required by
the vector unit.
Track whether we've validated FRM separately from whether
we've updated fp_status with a given rounding mode, so that
we can elide calls correctly.
This partially reverts d6c4d3f2a69 which attempted the to do
the same thing, but with two calls to gen_set_rm(), which is
both inefficient and tickles an assertion in decode_save_opc.
Resolves: https://gitlab.com/qemu-project/qemu/-/issues/1441
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Reviewed-by: Daniel Henrique Barboza <dbarboza@ventanamicro.com>
Acked-by: Alistair Francis <alistair.francis@wdc.com>
Message-Id: <20230115160657.3169274-2-richard.henderson@linaro.org>
Signed-off-by: Alistair Francis <alistair.francis@wdc.com>
---
target/riscv/helper.h | 1 +
target/riscv/fpu_helper.c | 37 +++++++++++++++++++++++++
target/riscv/translate.c | 19 +++++++++++++
target/riscv/insn_trans/trans_rvv.c.inc | 24 +++-------------
4 files changed, 61 insertions(+), 20 deletions(-)
diff --git a/target/riscv/helper.h b/target/riscv/helper.h
index 227c7122ef..9792ab5086 100644
--- a/target/riscv/helper.h
+++ b/target/riscv/helper.h
@@ -3,6 +3,7 @@ DEF_HELPER_2(raise_exception, noreturn, env, i32)
/* Floating Point - rounding mode */
DEF_HELPER_FLAGS_2(set_rounding_mode, TCG_CALL_NO_WG, void, env, i32)
+DEF_HELPER_FLAGS_2(set_rounding_mode_chkfrm, TCG_CALL_NO_WG, void, env, i32)
DEF_HELPER_FLAGS_1(set_rod_rounding_mode, TCG_CALL_NO_WG, void, env)
/* Floating Point - fused */
diff --git a/target/riscv/fpu_helper.c b/target/riscv/fpu_helper.c
index 5699c9517f..96817df8ef 100644
--- a/target/riscv/fpu_helper.c
+++ b/target/riscv/fpu_helper.c
@@ -81,6 +81,43 @@ void helper_set_rounding_mode(CPURISCVState *env, uint32_t rm)
set_float_rounding_mode(softrm, &env->fp_status);
}
+void helper_set_rounding_mode_chkfrm(CPURISCVState *env, uint32_t rm)
+{
+ int softrm;
+
+ /* Always validate frm, even if rm != DYN. */
+ if (unlikely(env->frm >= 5)) {
+ riscv_raise_exception(env, RISCV_EXCP_ILLEGAL_INST, GETPC());
+ }
+ if (rm == RISCV_FRM_DYN) {
+ rm = env->frm;
+ }
+ switch (rm) {
+ case RISCV_FRM_RNE:
+ softrm = float_round_nearest_even;
+ break;
+ case RISCV_FRM_RTZ:
+ softrm = float_round_to_zero;
+ break;
+ case RISCV_FRM_RDN:
+ softrm = float_round_down;
+ break;
+ case RISCV_FRM_RUP:
+ softrm = float_round_up;
+ break;
+ case RISCV_FRM_RMM:
+ softrm = float_round_ties_away;
+ break;
+ case RISCV_FRM_ROD:
+ softrm = float_round_to_odd;
+ break;
+ default:
+ g_assert_not_reached();
+ }
+
+ set_float_rounding_mode(softrm, &env->fp_status);
+}
+
void helper_set_rod_rounding_mode(CPURISCVState *env)
{
set_float_rounding_mode(float_round_to_odd, &env->fp_status);
diff --git a/target/riscv/translate.c b/target/riscv/translate.c
index df38db7553..493c3815e1 100644
--- a/target/riscv/translate.c
+++ b/target/riscv/translate.c
@@ -114,6 +114,8 @@ typedef struct DisasContext {
bool pm_base_enabled;
/* Use icount trigger for native debug */
bool itrigger;
+ /* FRM is known to contain a valid value. */
+ bool frm_valid;
/* TCG of the current insn_start */
TCGOp *insn_start;
} DisasContext;
@@ -674,12 +676,29 @@ static void gen_set_rm(DisasContext *ctx, int rm)
gen_helper_set_rod_rounding_mode(cpu_env);
return;
}
+ if (rm == RISCV_FRM_DYN) {
+ /* The helper will return only if frm valid. */
+ ctx->frm_valid = true;
+ }
/* The helper may raise ILLEGAL_INSN -- record binv for unwind. */
decode_save_opc(ctx);
gen_helper_set_rounding_mode(cpu_env, tcg_constant_i32(rm));
}
+static void gen_set_rm_chkfrm(DisasContext *ctx, int rm)
+{
+ if (ctx->frm == rm && ctx->frm_valid) {
+ return;
+ }
+ ctx->frm = rm;
+ ctx->frm_valid = true;
+
+ /* The helper may raise ILLEGAL_INSN -- record binv for unwind. */
+ decode_save_opc(ctx);
+ gen_helper_set_rounding_mode_chkfrm(cpu_env, tcg_constant_i32(rm));
+}
+
static int ex_plus_1(DisasContext *ctx, int nf)
{
return nf + 1;
diff --git a/target/riscv/insn_trans/trans_rvv.c.inc b/target/riscv/insn_trans/trans_rvv.c.inc
index d455acedbf..bbb5c3a7b5 100644
--- a/target/riscv/insn_trans/trans_rvv.c.inc
+++ b/target/riscv/insn_trans/trans_rvv.c.inc
@@ -2679,13 +2679,9 @@ static bool do_opfv(DisasContext *s, arg_rmr *a,
int rm)
{
if (checkfn(s, a)) {
- if (rm != RISCV_FRM_DYN) {
- gen_set_rm(s, RISCV_FRM_DYN);
- }
-
uint32_t data = 0;
TCGLabel *over = gen_new_label();
- gen_set_rm(s, rm);
+ gen_set_rm_chkfrm(s, rm);
tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over);
tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over);
@@ -2882,17 +2878,13 @@ static bool opffv_widen_check(DisasContext *s, arg_rmr *a)
static bool trans_##NAME(DisasContext *s, arg_rmr *a) \
{ \
if (CHECK(s, a)) { \
- if (FRM != RISCV_FRM_DYN) { \
- gen_set_rm(s, RISCV_FRM_DYN); \
- } \
- \
uint32_t data = 0; \
static gen_helper_gvec_3_ptr * const fns[2] = { \
gen_helper_##HELPER##_h, \
gen_helper_##HELPER##_w, \
}; \
TCGLabel *over = gen_new_label(); \
- gen_set_rm(s, FRM); \
+ gen_set_rm_chkfrm(s, FRM); \
tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over); \
tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over); \
\
@@ -3005,17 +2997,13 @@ static bool opffv_narrow_check(DisasContext *s, arg_rmr *a)
static bool trans_##NAME(DisasContext *s, arg_rmr *a) \
{ \
if (CHECK(s, a)) { \
- if (FRM != RISCV_FRM_DYN) { \
- gen_set_rm(s, RISCV_FRM_DYN); \
- } \
- \
uint32_t data = 0; \
static gen_helper_gvec_3_ptr * const fns[2] = { \
gen_helper_##HELPER##_h, \
gen_helper_##HELPER##_w, \
}; \
TCGLabel *over = gen_new_label(); \
- gen_set_rm(s, FRM); \
+ gen_set_rm_chkfrm(s, FRM); \
tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over); \
tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over); \
\
@@ -3060,10 +3048,6 @@ static bool opxfv_narrow_check(DisasContext *s, arg_rmr *a)
static bool trans_##NAME(DisasContext *s, arg_rmr *a) \
{ \
if (opxfv_narrow_check(s, a)) { \
- if (FRM != RISCV_FRM_DYN) { \
- gen_set_rm(s, RISCV_FRM_DYN); \
- } \
- \
uint32_t data = 0; \
static gen_helper_gvec_3_ptr * const fns[3] = { \
gen_helper_##HELPER##_b, \
@@ -3071,7 +3055,7 @@ static bool trans_##NAME(DisasContext *s, arg_rmr *a) \
gen_helper_##HELPER##_w, \
}; \
TCGLabel *over = gen_new_label(); \
- gen_set_rm(s, FRM); \
+ gen_set_rm_chkfrm(s, FRM); \
tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_vl, 0, over); \
tcg_gen_brcond_tl(TCG_COND_GEU, cpu_vstart, cpu_vl, over); \
\
--
2.39.0
next prev parent reply other threads:[~2023-01-20 7:44 UTC|newest]
Thread overview: 39+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-01-20 7:38 [PULL 00/37] riscv-to-apply queue Alistair Francis
2023-01-20 7:38 ` [PULL 01/37] hw/char: riscv_htif: Avoid using magic numbers Alistair Francis
2023-01-20 7:38 ` [PULL 02/37] hw/char: riscv_htif: Drop {to, from}host_size in HTIFState Alistair Francis
2023-01-20 7:38 ` [PULL 03/37] hw/char: riscv_htif: Drop useless assignment of memory region Alistair Francis
2023-01-20 7:38 ` [PULL 04/37] hw/char: riscv_htif: Use conventional 's' for HTIFState Alistair Francis
2023-01-20 7:38 ` [PULL 05/37] hw/char: riscv_htif: Move registers from CPUArchState to HTIFState Alistair Francis
2023-01-20 7:38 ` [PULL 06/37] hw/char: riscv_htif: Remove forward declarations for non-existent variables Alistair Francis
2023-01-20 7:38 ` [PULL 07/37] hw/char: riscv_htif: Support console output via proxy syscall Alistair Francis
2023-01-20 7:38 ` [PULL 08/37] hw/riscv: spike: Remove the out-of-date comments Alistair Francis
2023-01-20 7:38 ` [PULL 09/37] hw/riscv/boot.c: make riscv_find_firmware() static Alistair Francis
2023-01-20 7:38 ` [PULL 10/37] hw/riscv/boot.c: introduce riscv_default_firmware_name() Alistair Francis
2023-01-20 7:38 ` [PULL 11/37] hw/riscv/boot.c: Introduce riscv_find_firmware() Alistair Francis
2023-01-20 7:38 ` [PULL 12/37] hw/riscv: spike: Decouple create_fdt() dependency to ELF loading Alistair Francis
2023-01-20 7:38 ` [PULL 13/37] target/riscv/cpu.c: Fix elen check Alistair Francis
2023-01-20 7:38 ` [PULL 14/37] tests/avocado: add RISC-V OpenSBI boot test Alistair Francis
2023-01-20 7:38 ` [PULL 15/37] hw/riscv/spike: use 'fdt' from MachineState Alistair Francis
2023-01-20 7:38 ` [PULL 16/37] hw/riscv/sifive_u: " Alistair Francis
2023-01-20 7:38 ` [PULL 17/37] hw/riscv/boot.c: exit early if filename is NULL in load functions Alistair Francis
2023-01-20 7:38 ` [PULL 18/37] hw/riscv/spike.c: load initrd right after riscv_load_kernel() Alistair Francis
2023-01-20 7:38 ` [PULL 19/37] hw/riscv: write initrd 'chosen' FDT inside riscv_load_initrd() Alistair Francis
2023-01-20 7:38 ` [PULL 20/37] hw/riscv: write bootargs 'chosen' FDT after riscv_load_kernel() Alistair Francis
2023-01-20 7:38 ` [PULL 21/37] hw/riscv/boot.c: use MachineState in riscv_load_initrd() Alistair Francis
2023-01-20 7:38 ` [PULL 22/37] hw/riscv/boot.c: use MachineState in riscv_load_kernel() Alistair Francis
2023-01-20 7:38 ` [PULL 23/37] target/riscv/cpu: set cpu->cfg in register_cpu_props() Alistair Francis
2023-01-20 7:39 ` [PULL 24/37] target/riscv/cpu.c: do not skip misa logic in riscv_cpu_realize() Alistair Francis
2023-01-20 7:39 ` [PULL 25/37] target/riscv: Use TARGET_FMT_lx for env->mhartid Alistair Francis
2023-01-20 7:39 ` [PULL 26/37] hw/riscv/spike.c: simplify create_fdt() Alistair Francis
2023-01-20 7:39 ` [PULL 27/37] hw/riscv/virt.c: " Alistair Francis
2023-01-20 7:39 ` [PULL 28/37] hw/riscv/sifive_u.c: " Alistair Francis
2023-01-20 7:39 ` [PULL 29/37] hw/riscv/virt.c: remove 'is_32_bit' param from create_fdt_socket_cpus() Alistair Francis
2023-01-20 7:39 ` [PULL 30/37] hw/riscv: use MachineState::fdt in riscv_socket_fdt_write_id() Alistair Francis
2023-01-20 7:39 ` [PULL 31/37] hw/riscv: use ms->fdt in riscv_socket_fdt_write_distance_matrix() Alistair Francis
2023-01-20 7:39 ` [PULL 32/37] target/riscv: Fix up masking of vsip/vsie accesses Alistair Francis
2023-01-20 7:39 ` [PULL 33/37] target/riscv: Trap on writes to stimecmp from VS when hvictl.VTI=1 Alistair Francis
2023-01-20 7:39 ` [PULL 34/37] tcg/riscv: Use tcg_pcrel_diff in tcg_out_ldst Alistair Francis
2023-01-20 7:39 ` Alistair Francis [this message]
2023-01-20 7:39 ` [PULL 36/37] target/riscv: Remove helper_set_rod_rounding_mode Alistair Francis
2023-01-20 7:39 ` [PULL 37/37] hw/riscv/virt.c: move create_fw_cfg() back to virt_machine_init() Alistair Francis
2023-01-21 13:01 ` [PULL 00/37] riscv-to-apply queue Peter Maydell
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20230120073913.1028407-36-alistair.francis@opensource.wdc.com \
--to=alistair.francis@opensource.wdc.com \
--cc=alistair.francis@wdc.com \
--cc=alistair23@gmail.com \
--cc=dbarboza@ventanamicro.com \
--cc=qemu-devel@nongnu.org \
--cc=richard.henderson@linaro.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).