qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
From: Stafford Horne <shorne@gmail.com>
To: Peter Maydell <peter.maydell@linaro.org>
Cc: QEMU Development <qemu-devel@nongnu.org>,
	Richard Henderson <richard.henderson@linaro.org>,
	Stafford Horne <shorne@gmail.com>
Subject: [Qemu-devel] [PULL v2 07/25] target/openrisc: Link more translation blocks
Date: Tue,  3 Jul 2018 00:10:05 +0900	[thread overview]
Message-ID: <20180702151023.24532-8-shorne@gmail.com> (raw)
In-Reply-To: <20180702151023.24532-1-shorne@gmail.com>

From: Richard Henderson <richard.henderson@linaro.org>

Track direct jumps via dc->jmp_pc_imm.  Use that in
preference to jmp_pc when possible.  Emit goto_tb in
that case, and lookup_and_goto_tb otherwise.

Reviewed-by: Stafford Horne <shorne@gmail.com>
Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
Signed-off-by: Stafford Horne <shorne@gmail.com>
---
 target/openrisc/translate.c | 96 +++++++++++++++++++++----------------
 1 file changed, 55 insertions(+), 41 deletions(-)

diff --git a/target/openrisc/translate.c b/target/openrisc/translate.c
index 22848b17ad..a618d39242 100644
--- a/target/openrisc/translate.c
+++ b/target/openrisc/translate.c
@@ -38,13 +38,16 @@
 
 /* is_jmp field values */
 #define DISAS_EXIT    DISAS_TARGET_0  /* force exit to main loop */
-#define DISAS_UPDATE  DISAS_TARGET_1 /* cpu state was modified dynamically */
+#define DISAS_JUMP    DISAS_TARGET_1  /* exit via jmp_pc/jmp_pc_imm */
 
 typedef struct DisasContext {
     DisasContextBase base;
     uint32_t mem_idx;
     uint32_t tb_flags;
     uint32_t delayed_branch;
+
+    /* If not -1, jmp_pc contains this value and so is a direct jump.  */
+    target_ulong jmp_pc_imm;
 } DisasContext;
 
 /* Include the auto-generated decoder.  */
@@ -160,34 +163,6 @@ static void check_ov64s(DisasContext *dc)
         }                               \
     } while (0)
 
-static inline bool use_goto_tb(DisasContext *dc, target_ulong dest)
-{
-    if (unlikely(dc->base.singlestep_enabled)) {
-        return false;
-    }
-
-#ifndef CONFIG_USER_ONLY
-    return (dc->base.tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK);
-#else
-    return true;
-#endif
-}
-
-static void gen_goto_tb(DisasContext *dc, int n, target_ulong dest)
-{
-    if (use_goto_tb(dc, dest)) {
-        tcg_gen_movi_tl(cpu_pc, dest);
-        tcg_gen_goto_tb(n);
-        tcg_gen_exit_tb(dc->base.tb, n);
-    } else {
-        tcg_gen_movi_tl(cpu_pc, dest);
-        if (dc->base.singlestep_enabled) {
-            gen_exception(dc, EXCP_DEBUG);
-        }
-        tcg_gen_exit_tb(NULL, 0);
-    }
-}
-
 static void gen_ove_cy(DisasContext *dc)
 {
     if (dc->tb_flags & SR_OVE) {
@@ -621,6 +596,7 @@ static bool trans_l_j(DisasContext *dc, arg_l_j *a, uint32_t insn)
     target_ulong tmp_pc = dc->base.pc_next + a->n * 4;
 
     tcg_gen_movi_tl(jmp_pc, tmp_pc);
+    dc->jmp_pc_imm = tmp_pc;
     dc->delayed_branch = 2;
     return true;
 }
@@ -634,6 +610,7 @@ static bool trans_l_jal(DisasContext *dc, arg_l_jal *a, uint32_t insn)
     /* Optimize jal being used to load the PC for PIC.  */
     if (tmp_pc != ret_pc) {
         tcg_gen_movi_tl(jmp_pc, tmp_pc);
+        dc->jmp_pc_imm = tmp_pc;
         dc->delayed_branch = 2;
     }
     return true;
@@ -1267,6 +1244,8 @@ static void openrisc_tr_init_disas_context(DisasContextBase *dcb, CPUState *cs)
     dc->mem_idx = cpu_mmu_index(env, false);
     dc->tb_flags = dc->base.tb->flags;
     dc->delayed_branch = (dc->tb_flags & TB_FLAGS_DFLAG) != 0;
+    dc->jmp_pc_imm = -1;
+
     bound = -(dc->base.pc_first | TARGET_PAGE_MASK) / 4;
     dc->base.max_insns = MIN(dc->base.max_insns, bound);
 }
@@ -1319,37 +1298,72 @@ static void openrisc_tr_translate_insn(DisasContextBase *dcbase, CPUState *cs)
     }
     dc->base.pc_next += 4;
 
-    /* delay slot */
-    if (dc->delayed_branch) {
-        dc->delayed_branch--;
-        if (!dc->delayed_branch) {
-            tcg_gen_mov_tl(cpu_pc, jmp_pc);
-            tcg_gen_discard_tl(jmp_pc);
-            dc->base.is_jmp = DISAS_UPDATE;
-            return;
-        }
+    /* When exiting the delay slot normally, exit via jmp_pc.
+     * For DISAS_NORETURN, we have raised an exception and already exited.
+     * For DISAS_EXIT, we found l.rfe in a delay slot.  There's nothing
+     * in the manual saying this is illegal, but it surely it should.
+     * At least or1ksim overrides pcnext and ignores the branch.
+     */
+    if (dc->delayed_branch
+        && --dc->delayed_branch == 0
+        && dc->base.is_jmp == DISAS_NEXT) {
+        dc->base.is_jmp = DISAS_JUMP;
     }
 }
 
 static void openrisc_tr_tb_stop(DisasContextBase *dcbase, CPUState *cs)
 {
     DisasContext *dc = container_of(dcbase, DisasContext, base);
+    target_ulong jmp_dest;
 
     /* If we have already exited the TB, nothing following has effect.  */
     if (dc->base.is_jmp == DISAS_NORETURN) {
         return;
     }
 
+    /* Adjust the delayed branch state for the next TB.  */
     if ((dc->tb_flags & TB_FLAGS_DFLAG ? 1 : 0) != (dc->delayed_branch != 0)) {
         tcg_gen_movi_i32(cpu_dflag, dc->delayed_branch != 0);
     }
 
-    tcg_gen_movi_tl(cpu_ppc, dc->base.pc_next - 4);
+    /* For DISAS_TOO_MANY, jump to the next insn.  */
+    jmp_dest = dc->base.pc_next;
+    tcg_gen_movi_tl(cpu_ppc, jmp_dest - 4);
+
     switch (dc->base.is_jmp) {
+    case DISAS_JUMP:
+        jmp_dest = dc->jmp_pc_imm;
+        if (jmp_dest == -1) {
+            /* The jump destination is indirect/computed; use jmp_pc.  */
+            tcg_gen_mov_tl(cpu_pc, jmp_pc);
+            tcg_gen_discard_tl(jmp_pc);
+            if (unlikely(dc->base.singlestep_enabled)) {
+                gen_exception(dc, EXCP_DEBUG);
+            } else {
+                tcg_gen_lookup_and_goto_ptr();
+            }
+            break;
+        }
+        /* The jump destination is direct; use jmp_pc_imm.
+           However, we will have stored into jmp_pc as well;
+           we know now that it wasn't needed.  */
+        tcg_gen_discard_tl(jmp_pc);
+        /* fallthru */
+
     case DISAS_TOO_MANY:
-        gen_goto_tb(dc, 0, dc->base.pc_next);
+        if (unlikely(dc->base.singlestep_enabled)) {
+            tcg_gen_movi_tl(cpu_pc, jmp_dest);
+            gen_exception(dc, EXCP_DEBUG);
+        } else if ((dc->base.pc_first ^ jmp_dest) & TARGET_PAGE_MASK) {
+            tcg_gen_movi_tl(cpu_pc, jmp_dest);
+            tcg_gen_lookup_and_goto_ptr();
+        } else {
+            tcg_gen_goto_tb(0);
+            tcg_gen_movi_tl(cpu_pc, jmp_dest);
+            tcg_gen_exit_tb(dc->base.tb, 0);
+        }
         break;
-    case DISAS_UPDATE:
+
     case DISAS_EXIT:
         if (unlikely(dc->base.singlestep_enabled)) {
             gen_exception(dc, EXCP_DEBUG);
-- 
2.17.0

  parent reply	other threads:[~2018-07-02 15:11 UTC|newest]

Thread overview: 35+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2018-07-02 15:09 [Qemu-devel] [PULL v2 00/25] OpenRISC updates for 3.0 Stafford Horne
2018-07-02 15:09 ` [Qemu-devel] [PULL v2 01/25] target/openrisc: Fix mtspr shadow gprs Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 02/25] target/openrisc: Add print_insn_or1k Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 03/25] target/openrisc: Log interrupts Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 04/25] target/openrisc: Remove DISAS_JUMP & DISAS_TB_JUMP Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 05/25] target/openrisc: Use exit_tb instead of CPU_INTERRUPT_EXITTB Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 06/25] target/openrisc: Fix singlestep_enabled Stafford Horne
2018-07-02 15:10 ` Stafford Horne [this message]
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 08/25] target/openrisc: Split out is_user Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 09/25] target/openrisc: Exit the TB after l.mtspr Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 10/25] target/openrisc: Form the spr index from tcg Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 11/25] target/openrisc: Merge tlb allocation into CPUOpenRISCState Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 12/25] target/openrisc: Remove indirect function calls for mmu Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 13/25] target/openrisc: Merge mmu_helper.c into mmu.c Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 14/25] target/openrisc: Reduce tlb to a single dimension Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 15/25] target/openrisc: Fix tlb flushing in mtspr Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 16/25] target/openrisc: Fix cpu_mmu_index Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 17/25] target/openrisc: Use identical sizes for ITLB and DTLB Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 18/25] target/openrisc: Stub out handle_mmu_fault for softmmu Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 19/25] target/openrisc: Increase the TLB size Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 20/25] target/openrisc: Reorg tlb lookup Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 21/25] target/openrisc: Add support in scripts/qemu-binfmt-conf.sh Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 22/25] linux-user: Implement signals for openrisc Stafford Horne
2018-07-03 22:34   ` Philippe Mathieu-Daudé
2018-07-03 23:51     ` Stafford Horne
2018-07-04 20:54       ` Richard Henderson
2018-07-06 22:22         ` Eric Blake
2018-07-06 23:02           ` Stafford Horne
2018-07-07  8:10             ` Laurent Vivier
2018-07-07  7:04       ` Alex Bennée
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 23/25] linux-user: Fix struct sigaltstack " Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 24/25] target/openrisc: Fix delay slot exception flag to match spec Stafford Horne
2018-07-02 15:10 ` [Qemu-devel] [PULL v2 25/25] target/openrisc: Fix writes to interrupt mask register Stafford Horne
2018-07-02 15:36 ` [Qemu-devel] [PULL v2 00/25] OpenRISC updates for 3.0 Peter Maydell
2018-07-03 13:53   ` Stafford Horne

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=20180702151023.24532-8-shorne@gmail.com \
    --to=shorne@gmail.com \
    --cc=peter.maydell@linaro.org \
    --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).