All of lore.kernel.org
 help / color / mirror / Atom feed
* [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions
@ 2014-09-27 14:58 Bastian Koppelmann
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes Bastian Koppelmann
                   ` (4 more replies)
  0 siblings, 5 replies; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-27 14:58 UTC (permalink / raw)
  To: qemu-devel; +Cc: peter.maydell, rth

Hi guys,

here is the next round of TriCore patches. The first patch addresses a clang issue mentioned by Peter Maydell and
some bugfixes. And the other four add instructions of the ABS, ABSB, B, BIT and BO opcode format.

Thanks,

Bastian

Bastian Koppelmann (5):
  target-tricore: Cleanup and Bugfixes
  target-tricore: Add instructions of ABS, ABSB opcode format
  target-tricore: Add instructions of B opcode format
  target-tricore: Add instructions of BIT opcode format
  target-tricore: Add instructions of BO opcode format

 target-tricore/helper.h          |   46 ++
 target-tricore/op_helper.c       |  575 ++++++++++++++++-
 target-tricore/translate.c       | 1261 ++++++++++++++++++++++++++++++++++++++
 target-tricore/tricore-opcodes.h |    4 +-
 4 files changed, 1859 insertions(+), 27 deletions(-)

--
2.1.1

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

* [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes
  2014-09-27 14:58 [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions Bastian Koppelmann
@ 2014-09-27 14:58 ` Bastian Koppelmann
  2014-09-28  6:18   ` Richard Henderson
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 2/5] target-tricore: Add instructions of ABS, ABSB opcode format Bastian Koppelmann
                   ` (3 subsequent siblings)
  4 siblings, 1 reply; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-27 14:58 UTC (permalink / raw)
  To: qemu-devel; +Cc: peter.maydell, rth

Move FCX loading of save_context_ to caller functions, for STLCX, STUCX insn to use those functions.
Move FCX storing of restore_context_ to caller functions, for LDLCX, LDUCX insn to use those functions.
Remove do_raise_exception function, which caused clang to emit a warning.
Fix: save_context_lower now saves a[11] instead of PSW.
Fix: MASK_OP_ABSB_BPOS starting at wrong offset.

Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>
---
 target-tricore/op_helper.c       | 47 ++++++++++++++++++----------------------
 target-tricore/tricore-opcodes.h |  2 +-
 2 files changed, 22 insertions(+), 27 deletions(-)

diff --git a/target-tricore/op_helper.c b/target-tricore/op_helper.c
index 6376f07..f2a5cbc 100644
--- a/target-tricore/op_helper.c
+++ b/target-tricore/op_helper.c
@@ -114,10 +114,8 @@ static bool cdc_zero(target_ulong *psw)
     return count == 0;
 }
 
-static void save_context_upper(CPUTriCoreState *env, int ea,
-                               target_ulong *new_FCX)
+static void save_context_upper(CPUTriCoreState *env, int ea)
 {
-    *new_FCX = cpu_ldl_data(env, ea);
     cpu_stl_data(env, ea, env->PCXI);
     cpu_stl_data(env, ea+4, env->PSW);
     cpu_stl_data(env, ea+8, env->gpr_a[10]);
@@ -134,15 +132,12 @@ static void save_context_upper(CPUTriCoreState *env, int ea,
     cpu_stl_data(env, ea+52, env->gpr_d[13]);
     cpu_stl_data(env, ea+56, env->gpr_d[14]);
     cpu_stl_data(env, ea+60, env->gpr_d[15]);
-
 }
 
-static void save_context_lower(CPUTriCoreState *env, int ea,
-                               target_ulong *new_FCX)
+static void save_context_lower(CPUTriCoreState *env, int ea)
 {
-    *new_FCX = cpu_ldl_data(env, ea);
     cpu_stl_data(env, ea, env->PCXI);
-    cpu_stl_data(env, ea+4, env->PSW);
+    cpu_stl_data(env, ea+4, env->gpr_a[11]);
     cpu_stl_data(env, ea+8, env->gpr_a[2]);
     cpu_stl_data(env, ea+12, env->gpr_a[3]);
     cpu_stl_data(env, ea+16, env->gpr_d[0]);
@@ -178,7 +173,6 @@ static void restore_context_upper(CPUTriCoreState *env, int ea,
     env->gpr_d[13] = cpu_ldl_data(env, ea+52);
     env->gpr_d[14] = cpu_ldl_data(env, ea+56);
     env->gpr_d[15] = cpu_ldl_data(env, ea+60);
-    cpu_stl_data(env, ea, env->FCX);
 }
 
 void helper_call(CPUTriCoreState *env, uint32_t next_pc)
@@ -206,11 +200,12 @@ void helper_call(CPUTriCoreState *env, uint32_t next_pc)
     /* EA = {FCX.FCXS, 6'b0, FCX.FCXO, 6'b0}; */
     ea = ((env->FCX & MASK_FCX_FCXS) << 12) +
          ((env->FCX & MASK_FCX_FCXO) << 6);
-    /* new_FCX = M(EA, word);
-       M(EA, 16 * word) = {PCXI, PSW, A[10], A[11], D[8], D[9], D[10], D[11],
-                          A[12], A[13], A[14], A[15], D[12], D[13], D[14],
-                          D[15]}; */
-    save_context_upper(env, ea, &new_FCX);
+    /* new_FCX = M(EA, word); */
+    new_FCX = cpu_ldl_data(env, ea);
+    /* M(EA, 16 * word) = {PCXI, PSW, A[10], A[11], D[8], D[9], D[10], D[11],
+                           A[12], A[13], A[14], A[15], D[12], D[13], D[14],
+                           D[15]}; */
+    save_context_upper(env, ea);
 
     /* PCXI.PCPN = ICR.CCPN; */
     env->PCXI = (env->PCXI & 0xffffff) +
@@ -263,9 +258,10 @@ void helper_ret(CPUTriCoreState *env)
     ea = ((env->PCXI & MASK_PCXI_PCXS) << 12) +
          ((env->PCXI & MASK_PCXI_PCXO) << 6);
     /* {new_PCXI, new_PSW, A[10], A[11], D[8], D[9], D[10], D[11], A[12],
-        A[13], A[14], A[15], D[12], D[13], D[14], D[15]} = M(EA, 16 * word);
-        M(EA, word) = FCX; */
+        A[13], A[14], A[15], D[12], D[13], D[14], D[15]} = M(EA, 16 * word); */
     restore_context_upper(env, ea, &new_PCXI, &new_PSW);
+    /* M(EA, word) = FCX; */
+    cpu_stl_data(env, ea, env->FCX);
     /* FCX[19: 0] = PCXI[19: 0]; */
     env->FCX = (env->FCX & 0xfff00000) + (env->PCXI & 0x000fffff);
     /* PCXI = new_PCXI; */
@@ -293,7 +289,12 @@ void helper_bisr(CPUTriCoreState *env, uint32_t const9)
     tmp_FCX = env->FCX;
     ea = ((env->FCX & 0xf0000) << 12) + ((env->FCX & 0xffff) << 6);
 
-    save_context_lower(env, ea, &new_FCX);
+    /* new_FCX = M(EA, word); */
+    new_FCX = cpu_ldl_data(env, ea);
+    /* M(EA, 16 * word) = {PCXI, A[11], A[2], A[3], D[0], D[1], D[2], D[3], A[4]
+                           , A[5], A[6], A[7], D[4], D[5], D[6], D[7]}; */
+    save_context_lower(env, ea);
+
 
     /* PCXI.PCPN = ICR.CCPN */
     env->PCXI = (env->PCXI & 0xffffff) +
@@ -343,9 +344,10 @@ void helper_rfe(CPUTriCoreState *env)
     ea = ((env->PCXI & MASK_PCXI_PCXS) << 12) +
          ((env->PCXI & MASK_PCXI_PCXO) << 6);
     /*{new_PCXI, PSW, A[10], A[11], D[8], D[9], D[10], D[11], A[12],
-      A[13], A[14], A[15], D[12], D[13], D[14], D[15]} = M(EA, 16 * word);
-      M(EA, word) = FCX;*/
+      A[13], A[14], A[15], D[12], D[13], D[14], D[15]} = M(EA, 16 * word); */
     restore_context_upper(env, ea, &new_PCXI, &new_PSW);
+    /* M(EA, word) = FCX;*/
+    cpu_stl_data(env, ea, env->FCX);
     /* FCX[19: 0] = PCXI[19: 0]; */
     env->FCX = (env->FCX & 0xfff00000) + (env->PCXI & 0x000fffff);
     /* PCXI = new_PCXI; */
@@ -371,13 +373,6 @@ static inline void QEMU_NORETURN do_raise_exception_err(CPUTriCoreState *env,
     cpu_loop_exit(cs);
 }
 
-static inline void QEMU_NORETURN do_raise_exception(CPUTriCoreState *env,
-                                                    uint32_t exception,
-                                                    uintptr_t pc)
-{
-    do_raise_exception_err(env, exception, 0, pc);
-}
-
 void tlb_fill(CPUState *cs, target_ulong addr, int is_write, int mmu_idx,
               uintptr_t retaddr)
 {
diff --git a/target-tricore/tricore-opcodes.h b/target-tricore/tricore-opcodes.h
index 9c6ec01..342414f 100644
--- a/target-tricore/tricore-opcodes.h
+++ b/target-tricore/tricore-opcodes.h
@@ -89,7 +89,7 @@
 #define MASK_OP_ABSB_OFF18(op) MASK_OP_ABS_OFF18(op)
 #define MASK_OP_ABSB_OP2(op)   MASK_BITS_SHIFT(op, 26, 27)
 #define MASK_OP_ABSB_B(op)     MASK_BITS_SHIFT(op, 11, 11)
-#define MASK_OP_ABSB_BPOS(op)  MASK_BITS_SHIFT(op, 7, 10)
+#define MASK_OP_ABSB_BPOS(op)  MASK_BITS_SHIFT(op, 8, 10)
 
 /* B Format   */
 #define MASK_OP_B_DISP24(op)   (MASK_BITS_SHIFT(op, 16, 31) + \
-- 
2.1.1

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

* [Qemu-devel] [PATCH 2/5] target-tricore: Add instructions of ABS, ABSB opcode format
  2014-09-27 14:58 [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions Bastian Koppelmann
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes Bastian Koppelmann
@ 2014-09-27 14:58 ` Bastian Koppelmann
  2014-09-28  1:30   ` Richard Henderson
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 3/5] target-tricore: Add instructions of B " Bastian Koppelmann
                   ` (2 subsequent siblings)
  4 siblings, 1 reply; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-27 14:58 UTC (permalink / raw)
  To: qemu-devel; +Cc: peter.maydell, rth

Add instructions of ABS, ABSB opcode format.
Add microcode generator functions for ld/st of two 32bit reg as one 64bit value.
Add microcode generator functions for ldmst and swap.
Add helper ldlcx, lducx, stlcx and stucx.

Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>
---
 target-tricore/helper.h    |   4 +
 target-tricore/op_helper.c |  45 +++++++
 target-tricore/translate.c | 303 +++++++++++++++++++++++++++++++++++++++++++++
 3 files changed, 352 insertions(+)

diff --git a/target-tricore/helper.h b/target-tricore/helper.h
index 7b7d74b..fbabbd5 100644
--- a/target-tricore/helper.h
+++ b/target-tricore/helper.h
@@ -23,3 +23,7 @@ DEF_HELPER_2(call, void, env, i32)
 DEF_HELPER_1(ret, void, env)
 DEF_HELPER_2(bisr, void, env, i32)
 DEF_HELPER_1(rfe, void, env)
+DEF_HELPER_2(ldlcx, void, env, i32)
+DEF_HELPER_2(lducx, void, env, i32)
+DEF_HELPER_2(stlcx, void, env, i32)
+DEF_HELPER_2(stucx, void, env, i32)
diff --git a/target-tricore/op_helper.c b/target-tricore/op_helper.c
index f2a5cbc..7a33afd 100644
--- a/target-tricore/op_helper.c
+++ b/target-tricore/op_helper.c
@@ -175,6 +175,27 @@ static void restore_context_upper(CPUTriCoreState *env, int ea,
     env->gpr_d[15] = cpu_ldl_data(env, ea+60);
 }
 
+static void restore_context_lower(CPUTriCoreState *env, int ea,
+                                  target_ulong *ra, target_ulong *pcxi)
+{
+    *pcxi = cpu_ldl_data(env, ea);
+    *ra = cpu_ldl_data(env, ea+4);
+    env->gpr_a[2] = cpu_ldl_data(env, ea+8);
+    env->gpr_a[3] = cpu_ldl_data(env, ea+12);
+    env->gpr_d[0]  = cpu_ldl_data(env, ea+16);
+    env->gpr_d[1]  = cpu_ldl_data(env, ea+20);
+    env->gpr_d[2] = cpu_ldl_data(env, ea+24);
+    env->gpr_d[3] = cpu_ldl_data(env, ea+28);
+    env->gpr_a[4] = cpu_ldl_data(env, ea+32);
+    env->gpr_a[5] = cpu_ldl_data(env, ea+36);
+    env->gpr_a[6] = cpu_ldl_data(env, ea+40);
+    env->gpr_a[7] = cpu_ldl_data(env, ea+44);
+    env->gpr_d[4] = cpu_ldl_data(env, ea+48);
+    env->gpr_d[5] = cpu_ldl_data(env, ea+52);
+    env->gpr_d[6] = cpu_ldl_data(env, ea+56);
+    env->gpr_d[7] = cpu_ldl_data(env, ea+60);
+}
+
 void helper_call(CPUTriCoreState *env, uint32_t next_pc)
 {
     target_ulong tmp_FCX;
@@ -356,6 +377,30 @@ void helper_rfe(CPUTriCoreState *env)
     psw_write(env, new_PSW);
 }
 
+void helper_ldlcx(CPUTriCoreState *env, uint32_t ea)
+{
+    uint32_t dummy;
+    /* insn doesn't load PCXI and RA */
+    restore_context_lower(env, ea, &dummy, &dummy);
+}
+
+void helper_lducx(CPUTriCoreState *env, uint32_t ea)
+{
+    uint32_t dummy;
+    /* insn doesn't load PCXI and PSW */
+    restore_context_upper(env, ea, &dummy, &dummy);
+}
+
+void helper_stlcx(CPUTriCoreState *env, uint32_t ea)
+{
+    save_context_lower(env, ea);
+}
+
+void helper_stucx(CPUTriCoreState *env, uint32_t ea)
+{
+    save_context_upper(env, ea);
+}
+
 static inline void QEMU_NORETURN do_raise_exception_err(CPUTriCoreState *env,
                                                         uint32_t exception,
                                                         int error_code,
diff --git a/target-tricore/translate.c b/target-tricore/translate.c
index 4f654de..3ec5ca7 100644
--- a/target-tricore/translate.c
+++ b/target-tricore/translate.c
@@ -115,6 +115,8 @@ void tricore_cpu_dump_state(CPUState *cs, FILE *f,
     tcg_temp_free_i32(helper_tmp);                                \
     } while (0)
 
+#define EA_ABS_FORMAT(con) (((con & 0x3C000) << 14) + (con & 0x3FFF))
+
 /* Functions for load/save to/from memory */
 
 static inline void gen_offset_ld(DisasContext *ctx, TCGv r1, TCGv r2,
@@ -135,6 +137,64 @@ static inline void gen_offset_st(DisasContext *ctx, TCGv r1, TCGv r2,
     tcg_temp_free(temp);
 }
 
+static void gen_st_2regs_64(TCGv rh, TCGv rl, TCGv address, DisasContext *ctx)
+{
+    TCGv_i64 temp = tcg_temp_new_i64();
+
+    tcg_gen_concat_i32_i64(temp, rl, rh);
+    tcg_gen_qemu_st_i64(temp, address, ctx->mem_idx, MO_LEQ);
+
+    tcg_temp_free_i64(temp);
+}
+
+static void gen_ld_2regs_64(TCGv rh, TCGv rl, TCGv address, DisasContext *ctx)
+{
+    TCGv_i64 temp = tcg_temp_new_i64();
+
+    tcg_gen_qemu_ld_i64(temp, address, ctx->mem_idx, MO_LEQ);
+    /* write back to two 32 bit regs */
+    tcg_gen_trunc_i64_i32(rl, temp);
+    tcg_gen_shri_i64(temp, temp, 32);
+    tcg_gen_trunc_i64_i32(rh, temp);
+
+    tcg_temp_free_i64(temp);
+}
+
+/* M(EA, word) = (M(EA, word) & ~E[a][63:32]) | (E[a][31:0] & E[a][63:32]); */
+static void gen_ldmst(DisasContext *ctx, int ereg, TCGv ea)
+{
+    TCGv temp = tcg_temp_new();
+    TCGv temp2 = tcg_temp_new();
+
+    /* temp = (M(EA, word) */
+    tcg_gen_qemu_ld_tl(temp, ea, ctx->mem_idx, MO_LEUL);
+    /* temp = temp & ~E[a][63:32]) */
+    tcg_gen_andc_tl(temp, temp, cpu_gpr_d[ereg+1]);
+    /* temp2 = (E[a][31:0] & E[a][63:32]); */
+    tcg_gen_and_tl(temp2, cpu_gpr_d[ereg], cpu_gpr_d[ereg+1]);
+    /* temp = temp | temp2; */
+    tcg_gen_or_tl(temp, temp, temp2);
+    /* M(EA, word) = temp; */
+    tcg_gen_qemu_st_tl(temp, ea, ctx->mem_idx, MO_LEUL);
+
+    tcg_temp_free(temp);
+    tcg_temp_free(temp2);
+}
+
+/* tmp = M(EA, word);
+   M(EA, word) = D[a];
+   D[a] = tmp[31:0];*/
+static void gen_swap(DisasContext *ctx, int reg, TCGv ea)
+{
+    TCGv temp = tcg_temp_new();
+
+    tcg_gen_qemu_ld_tl(temp, ea, ctx->mem_idx, MO_LEUL);
+    tcg_gen_qemu_st_tl(cpu_gpr_d[reg], ea, ctx->mem_idx, MO_LEUL);
+    tcg_gen_mov_tl(cpu_gpr_d[reg], temp);
+
+    tcg_temp_free(temp);
+}
+
 /* Functions for arithmetic instructions  */
 
 static inline void gen_add_d(TCGv ret, TCGv r1, TCGv r2)
@@ -1099,8 +1159,251 @@ static void decode_16Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
     }
 }
 
+/*
+ * 32 bit instructions
+ */
+
+/* ABS-format */
+static void decode_abs_ldw(CPUTriCoreState *env, DisasContext *ctx)
+{
+    int32_t op2;
+    int32_t r1;
+    uint32_t address;
+    TCGv temp;
+
+    r1 = MASK_OP_ABS_S1D(ctx->opcode);
+    address = MASK_OP_ABS_OFF18(ctx->opcode);
+    op2 = MASK_OP_ABS_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(EA_ABS_FORMAT(address));
+
+    switch (op2) {
+    case OPC2_32_ABS_LD_A:
+        tcg_gen_qemu_ld_tl(cpu_gpr_a[r1], temp, ctx->mem_idx, MO_LESL);
+        break;
+    case OPC2_32_ABS_LD_D:
+        gen_ld_2regs_64(cpu_gpr_d[r1+1], cpu_gpr_d[r1], temp, ctx);
+        break;
+    case OPC2_32_ABS_LD_DA:
+        gen_ld_2regs_64(cpu_gpr_a[r1+1], cpu_gpr_a[r1], temp, ctx);
+        break;
+    case OPC2_32_ABS_LD_W:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_LESL);
+        break;
+    }
+
+    tcg_temp_free(temp);
+}
+
+static void decode_abs_ldb(CPUTriCoreState *env, DisasContext *ctx)
+{
+    int32_t op2;
+    int32_t r1;
+    uint32_t address;
+    TCGv temp;
+
+    r1 = MASK_OP_ABS_S1D(ctx->opcode);
+    address = MASK_OP_ABS_OFF18(ctx->opcode);
+    op2 = MASK_OP_ABS_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(EA_ABS_FORMAT(address));
+
+    switch (op2) {
+    case OPC2_32_ABS_LD_B:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_SB);
+        break;
+    case OPC2_32_ABS_LD_BU:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_UB);
+        break;
+    case OPC2_32_ABS_LD_H:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_LESW);
+        break;
+    case OPC2_32_ABS_LD_HU:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_LEUW);
+        break;
+    }
+
+    tcg_temp_free(temp);
+}
+
+static void decode_abs_ldst_swap(CPUTriCoreState *env, DisasContext *ctx)
+{
+    int32_t op2;
+    int32_t r1;
+    uint32_t address;
+    TCGv temp;
+
+    r1 = MASK_OP_ABS_S1D(ctx->opcode);
+    address = MASK_OP_ABS_OFF18(ctx->opcode);
+    op2 = MASK_OP_ABS_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(EA_ABS_FORMAT(address));
+
+    switch (op2) {
+    case OPC2_32_ABS_LDMST:
+        gen_ldmst(ctx, r1, temp);
+        break;
+    case OPC2_32_ABS_SWAP_W:
+        gen_swap(ctx, r1, temp);
+        break;
+    }
+
+    tcg_temp_free(temp);
+}
+
+static void decode_abs_ldst_context(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+    int32_t off18;
+
+    off18 = MASK_OP_ABS_OFF18(ctx->opcode);
+    op2   = MASK_OP_ABS_OP2(ctx->opcode);
+
+    switch (op2) {
+    case OPC2_32_ABS_LDLCX:
+        gen_helper_1arg(ldlcx, EA_ABS_FORMAT(off18));
+        break;
+    case OPC2_32_ABS_LDUCX:
+        gen_helper_1arg(lducx, EA_ABS_FORMAT(off18));
+        break;
+    case OPC2_32_ABS_STLCX:
+        gen_helper_1arg(stlcx, EA_ABS_FORMAT(off18));
+        break;
+    case OPC2_32_ABS_STUCX:
+        gen_helper_1arg(stucx, EA_ABS_FORMAT(off18));
+        break;
+    }
+}
+
+static void decode_abs_store(CPUTriCoreState *env, DisasContext *ctx)
+{
+    int32_t op2;
+    int32_t r1;
+    uint32_t address;
+    TCGv temp;
+
+    r1 = MASK_OP_ABS_S1D(ctx->opcode);
+    address = MASK_OP_ABS_OFF18(ctx->opcode);
+    op2 = MASK_OP_ABS_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(EA_ABS_FORMAT(address));
+
+    switch (op2) {
+    case OPC2_32_ABS_ST_A:
+        tcg_gen_qemu_st_tl(cpu_gpr_a[r1], temp, ctx->mem_idx, MO_LESL);
+        break;
+    case OPC2_32_ABS_ST_D:
+        gen_st_2regs_64(cpu_gpr_d[r1+1], cpu_gpr_d[r1], temp, ctx);
+        break;
+    case OPC2_32_ABS_ST_DA:
+        gen_st_2regs_64(cpu_gpr_a[r1+1], cpu_gpr_a[r1], temp, ctx);
+        break;
+    case OPC2_32_ABS_ST_W:
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_LESL);
+        break;
+
+    }
+    tcg_temp_free(temp);
+}
+
+static void decode_abs_storeb_h(CPUTriCoreState *env, DisasContext *ctx)
+{
+    int32_t op2;
+    int32_t r1;
+    uint32_t address;
+    TCGv temp;
+
+    r1 = MASK_OP_ABS_S1D(ctx->opcode);
+    address = MASK_OP_ABS_OFF18(ctx->opcode);
+    op2 = MASK_OP_ABS_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(EA_ABS_FORMAT(address));
+
+    switch (op2) {
+    case OPC2_32_ABS_ST_B:
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_UB);
+        break;
+    case OPC2_32_ABS_ST_H:
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_LEUW);
+        break;
+    }
+    tcg_temp_free(temp);
+}
+
 static void decode_32Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
 {
+    int op1;
+    int32_t r1;
+    int32_t address;
+    TCGv temp, temp2;
+
+    op1 = MASK_OP_MAJOR(ctx->opcode);
+
+    switch (op1) {
+/* ABS-format */
+    case OPCM_32_ABS_LDW:
+        decode_abs_ldw(env, ctx);
+        break;
+    case OPCM_32_ABS_LDB:
+        decode_abs_ldb(env, ctx);
+        break;
+    case OPCM_32_ABS_LDMST_SWAP:
+        decode_abs_ldst_swap(env, ctx);
+        break;
+    case OPCM_32_ABS_LDST_CONTEXT:
+        decode_abs_ldst_context(env, ctx);
+        break;
+    case OPCM_32_ABS_STORE:
+        decode_abs_store(env, ctx);
+        break;
+    case OPCM_32_ABS_STOREB_H:
+        decode_abs_storeb_h(env, ctx);
+        break;
+    case OPC1_32_ABS_STOREQ:
+        address = MASK_OP_ABS_OFF18(ctx->opcode);
+        r1 = MASK_OP_ABS_S1D(ctx->opcode);
+        temp = tcg_const_i32(EA_ABS_FORMAT(address));
+        temp2 = tcg_temp_new();
+
+        tcg_gen_shri_tl(temp2, cpu_gpr_d[r1], 16);
+        tcg_gen_qemu_st_tl(temp2, temp, ctx->mem_idx, MO_LEUW);
+
+        tcg_temp_free(temp2);
+        tcg_temp_free(temp);
+        break;
+    case OPC1_32_ABS_LD_Q:
+        address = MASK_OP_ABS_OFF18(ctx->opcode);
+        r1 = MASK_OP_ABS_S1D(ctx->opcode);
+        temp = tcg_const_i32(EA_ABS_FORMAT(address));
+
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], temp, ctx->mem_idx, MO_LEUW);
+        tcg_gen_shli_tl(cpu_gpr_d[r1], cpu_gpr_d[r1], 16);
+
+        tcg_temp_free(temp);
+        break;
+    case OPC1_32_ABS_LEA:
+        address = MASK_OP_ABS_OFF18(ctx->opcode);
+        r1 = MASK_OP_ABS_S1D(ctx->opcode);
+        tcg_gen_movi_tl(cpu_gpr_a[r1], EA_ABS_FORMAT(address));
+        break;
+/* ABSB-format */
+    case OPC1_32_ABSB_ST_T:
+        address = MASK_OP_ABS_OFF18(ctx->opcode);
+        int8_t b = MASK_OP_ABSB_B(ctx->opcode);
+        int32_t bpos = MASK_OP_ABSB_BPOS(ctx->opcode);
+
+        temp = tcg_const_i32(EA_ABS_FORMAT(address));
+        temp2 = tcg_temp_new();
+
+        tcg_gen_qemu_ld_tl(temp2, temp, ctx->mem_idx, MO_UB);
+        tcg_gen_andi_tl(temp2, temp2, ~(0x1u << bpos));
+        tcg_gen_ori_tl(temp2, temp2, (b << bpos));
+        tcg_gen_qemu_st_tl(temp2, temp, ctx->mem_idx, MO_UB);
+
+        tcg_temp_free(temp);
+        tcg_temp_free(temp2);
+        break;
+    }
 }
 
 static void decode_opc(CPUTriCoreState *env, DisasContext *ctx, int *is_branch)
-- 
2.1.1

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

* [Qemu-devel] [PATCH 3/5] target-tricore: Add instructions of B opcode format
  2014-09-27 14:58 [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions Bastian Koppelmann
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes Bastian Koppelmann
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 2/5] target-tricore: Add instructions of ABS, ABSB opcode format Bastian Koppelmann
@ 2014-09-27 14:58 ` Bastian Koppelmann
  2014-09-28  1:35   ` Richard Henderson
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT " Bastian Koppelmann
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 5/5] target-tricore: Add instructions of BO " Bastian Koppelmann
  4 siblings, 1 reply; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-27 14:58 UTC (permalink / raw)
  To: qemu-devel; +Cc: peter.maydell, rth

Add instructions of B opcode format.

Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>
---
 target-tricore/translate.c | 27 +++++++++++++++++++++++++++
 1 file changed, 27 insertions(+)

diff --git a/target-tricore/translate.c b/target-tricore/translate.c
index 3ec5ca7..871c3cd 100644
--- a/target-tricore/translate.c
+++ b/target-tricore/translate.c
@@ -116,6 +116,8 @@ void tricore_cpu_dump_state(CPUState *cs, FILE *f,
     } while (0)
 
 #define EA_ABS_FORMAT(con) (((con & 0x3C000) << 14) + (con & 0x3FFF))
+#define EA_B_FORMAT(con) (((offset & 0xf00000) << 8) | \
+                         ((offset & 0x0fffff) << 1))
 
 /* Functions for load/save to/from memory */
 
@@ -494,6 +496,7 @@ static void gen_compute_branch(DisasContext *ctx, uint32_t opc, int r1,
     case OPC1_32_B_J:
         gen_goto_tb(ctx, 0, ctx->pc + offset * 2);
         break;
+    case OPC1_32_B_CALL:
     case OPC1_16_SB_CALL:
         gen_helper_1arg(call, ctx->next_pc);
         gen_goto_tb(ctx, 0, ctx->pc + offset * 2);
@@ -569,6 +572,20 @@ static void gen_compute_branch(DisasContext *ctx, uint32_t opc, int r1,
         gen_helper_ret(cpu_env);
         tcg_gen_exit_tb(0);
         break;
+/* B-format */
+    case OPC1_32_B_CALLA:
+        gen_helper_1arg(call, ctx->next_pc);
+        gen_goto_tb(ctx, 0, EA_B_FORMAT(offset));
+        break;
+    case OPC1_32_B_JLA:
+        tcg_gen_movi_tl(cpu_gpr_a[11], ctx->next_pc);
+    case OPC1_32_B_JA:
+        gen_goto_tb(ctx, 0, EA_B_FORMAT(offset));
+        break;
+    case OPC1_32_B_JL:
+        tcg_gen_movi_tl(cpu_gpr_a[11], ctx->next_pc);
+        gen_goto_tb(ctx, 0, ctx->pc + offset * 2);
+        break;
     default:
         printf("Branch Error at %x\n", ctx->pc);
     }
@@ -1403,6 +1420,16 @@ static void decode_32Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
         tcg_temp_free(temp);
         tcg_temp_free(temp2);
         break;
+/* B-format */
+    case OPC1_32_B_CALL:
+    case OPC1_32_B_CALLA:
+    case OPC1_32_B_J:
+    case OPC1_32_B_JA:
+    case OPC1_32_B_JL:
+    case OPC1_32_B_JLA:
+        address = MASK_OP_B_DISP24(ctx->opcode);
+        gen_compute_branch(ctx, op1, 0, 0, 0, address);
+        break;
     }
 }
 
-- 
2.1.1

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

* [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT opcode format
  2014-09-27 14:58 [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions Bastian Koppelmann
                   ` (2 preceding siblings ...)
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 3/5] target-tricore: Add instructions of B " Bastian Koppelmann
@ 2014-09-27 14:58 ` Bastian Koppelmann
  2014-09-28  5:22   ` Richard Henderson
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 5/5] target-tricore: Add instructions of BO " Bastian Koppelmann
  4 siblings, 1 reply; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-27 14:58 UTC (permalink / raw)
  To: qemu-devel; +Cc: peter.maydell, rth

Add instructions of BIT opcode format.
Add microcode generator functions gen_bit_1/2op to do 1/2 bit operations on the last bit.

Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>
---
 target-tricore/translate.c | 349 +++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 349 insertions(+)

diff --git a/target-tricore/translate.c b/target-tricore/translate.c
index 871c3cd..34375a9 100644
--- a/target-tricore/translate.c
+++ b/target-tricore/translate.c
@@ -427,6 +427,56 @@ static inline void gen_subs(TCGv ret, TCGv r1, TCGv r2)
     gen_helper_sub_ssov(ret, cpu_env, r1, r2);
 }
 
+/* D[c] = D[c][0] op1 (D[a][pos1] op2 D[b][pos2]);*/
+static inline void gen_bit_2op(TCGv ret, TCGv r1, TCGv r2, TCGv r3,
+                               int pos1, int pos2,
+                               void(*op1)(TCGv, TCGv, TCGv),
+                               void(*op2)(TCGv, TCGv, TCGv))
+{
+    TCGv temp1, temp2, temp3;
+
+    temp1 = tcg_temp_new();
+    temp2 = tcg_temp_new();
+    temp3 = tcg_temp_new();
+
+    tcg_gen_andi_tl(temp3, r3, 0x1);
+
+    tcg_gen_andi_tl(temp2, r2 , (0x1u << pos2));
+    tcg_gen_shri_tl(temp2, temp2, pos2);
+
+    tcg_gen_andi_tl(temp1, r1, (0x1u << pos1));
+    tcg_gen_shri_tl(temp1, temp1, pos1);
+
+    (*op1)(temp1, temp1, temp2);
+    (*op2)(ret , temp3, temp1);
+
+    tcg_temp_free(temp1);
+    tcg_temp_free(temp2);
+    tcg_temp_free(temp3);
+}
+
+/* result = D[a][pos1] op1 D[b][pos2]; */
+static inline void gen_bit_1op(TCGv ret, TCGv r1, TCGv r2,
+                               int pos1, int pos2,
+                               void(*op1)(TCGv, TCGv, TCGv))
+{
+    TCGv temp1, temp2;
+
+    temp1 = tcg_temp_new();
+    temp2 = tcg_temp_new();
+
+    tcg_gen_andi_tl(temp2, r2, (0x1u << pos2));
+    tcg_gen_shri_tl(temp2, temp2, pos2);
+
+    tcg_gen_andi_tl(temp1, r1, (0x1u << pos1));
+    tcg_gen_shri_tl(temp1, temp1, pos1);
+
+    (*op1)(ret, temp1, temp2);
+
+    tcg_temp_free(temp1);
+    tcg_temp_free(temp2);
+}
+
 /* helpers for generating program flow micro-ops */
 
 static inline void gen_save_pc(target_ulong pc)
@@ -1347,6 +1397,283 @@ static void decode_abs_storeb_h(CPUTriCoreState *env, DisasContext *ctx)
     tcg_temp_free(temp);
 }
 
+/* Bit-format */
+
+static void decode_bit_andacc(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+    int r1, r2, r3;
+    int pos1, pos2;
+    TCGv temp;
+
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+
+    temp = tcg_temp_new();
+
+    switch (op2) {
+    case OPC2_32_BIT_AND_AND_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_and_tl, &tcg_gen_and_tl);
+        break;
+    case OPC2_32_BIT_AND_ANDN_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_andc_tl, &tcg_gen_and_tl);
+        break;
+    case OPC2_32_BIT_AND_NOR_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_or_tl, &tcg_gen_andc_tl);
+        break;
+    case OPC2_32_BIT_AND_OR_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_or_tl, &tcg_gen_and_tl);
+        break;
+    }
+    tcg_gen_andi_tl(temp, temp, 0x1);
+    tcg_gen_andi_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 0xfffffffe);
+    tcg_gen_add_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], temp);
+    tcg_temp_free(temp);
+}
+
+static void decode_bit_logical_t(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+    int r1, r2, r3;
+    int pos1, pos2;
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+
+    switch (op2) {
+    case OPC2_32_BIT_AND_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_and_tl);
+        break;
+    case OPC2_32_BIT_ANDN_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_andc_tl);
+        break;
+    case OPC2_32_BIT_NOR_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_nor_tl);
+        tcg_gen_andi_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 0x1);
+        break;
+    case OPC2_32_BIT_OR_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_or_tl);
+        break;
+    }
+}
+
+static void decode_bit_insert(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+    int r1, r2, r3;
+    int pos1, pos2;
+    TCGv temp, temp2;
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+
+    /* D[c] = {D[a][31:(pos1+1)], D[b][pos2], D[a][(pos1-1):0]}; */
+
+    temp = tcg_temp_new();
+    temp2 = tcg_temp_new();
+
+    /* temp2 = {D[a][31:(pos1+1)], 0} */
+    tcg_gen_andi_tl(temp2, cpu_gpr_d[r1],
+                   ((1 << (31 - pos1)) - 1) << (pos1 + 1));
+    /* temp = D[b][pos2] */;
+    tcg_gen_andi_tl(temp, cpu_gpr_d[r2], (1 << pos2));
+
+    if (op2 == OPC2_32_BIT_INSN_T) {
+        tcg_gen_not_tl(temp, temp);
+        tcg_gen_andi_tl(temp, temp, 1 << pos2);
+    }
+    /* temp2 = {D[a][31:(pos1+1)], D[b][pos2], 0} */
+    tcg_gen_shri_tl(temp, temp, pos2);
+    tcg_gen_shli_tl(temp, temp, pos1);
+    tcg_gen_add_tl(temp2, temp2, temp);
+
+    tcg_gen_andi_tl(temp, cpu_gpr_d[r1], (1 << pos1) - 1);
+    tcg_gen_add_tl(cpu_gpr_d[r3], temp2, temp);
+
+    tcg_temp_free(temp);
+    tcg_temp_free(temp2);
+}
+
+static void decode_bit_logical_t2(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+
+    int r1, r2, r3;
+    int pos1, pos2;
+
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+
+    switch (op2) {
+    case OPC2_32_BIT_NAND_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_nand_tl);
+        tcg_gen_andi_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 0x1);
+        break;
+    case OPC2_32_BIT_ORN_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_orc_tl);
+        tcg_gen_andi_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 0x1);
+        break;
+    case OPC2_32_BIT_XNOR_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_xor_tl);
+        tcg_gen_not_tl(cpu_gpr_d[r3], cpu_gpr_d[r3]);
+        tcg_gen_andi_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 0x1);
+        break;
+    case OPC2_32_BIT_XOR_T:
+        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_xor_tl);
+        break;
+    }
+}
+
+static void decode_bit_orand(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+
+    int r1, r2, r3;
+    int pos1, pos2;
+    TCGv temp;
+
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+
+    temp = tcg_temp_new();
+
+    switch (op2) {
+    case OPC2_32_BIT_OR_AND_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_and_tl, &tcg_gen_or_tl);
+        break;
+    case OPC2_32_BIT_OR_ANDN_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_andc_tl, &tcg_gen_or_tl);
+        break;
+    case OPC2_32_BIT_OR_NOR_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_or_tl, &tcg_gen_orc_tl);
+        break;
+    case OPC2_32_BIT_OR_OR_T:
+        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
+                    pos1, pos2, &tcg_gen_or_tl, &tcg_gen_or_tl);
+        break;
+    }
+    tcg_gen_andi_tl(temp, temp, 0x1);
+    tcg_gen_andi_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 0xfffffffe);
+    tcg_gen_add_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], temp);
+    tcg_temp_free(temp);
+}
+
+static void decode_bit_sh_logic1(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+    int r1, r2, r3;
+    int pos1, pos2;
+    TCGv temp;
+
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+
+    temp = tcg_temp_new();
+
+    switch (op2) {
+    case OPC2_32_BIT_SH_AND_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_and_tl);
+        break;
+    case OPC2_32_BIT_SH_ANDN_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_andc_tl);
+        break;
+    case OPC2_32_BIT_SH_NOR_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_nor_tl);
+        tcg_gen_andi_tl(temp, temp, 0x1);
+        break;
+    case OPC2_32_BIT_SH_OR_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_or_tl);
+        break;
+    }
+    tcg_gen_shli_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 1);
+    tcg_gen_add_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], temp);
+    tcg_temp_free(temp);
+}
+
+static void decode_bit_sh_logic2(CPUTriCoreState *env, DisasContext *ctx)
+{
+    uint32_t op2;
+    int r1, r2, r3;
+    int pos1, pos2;
+    TCGv temp;
+
+    op2 = MASK_OP_BIT_OP2(ctx->opcode);
+    r1 = MASK_OP_BIT_S1(ctx->opcode);
+    r2 = MASK_OP_BIT_S2(ctx->opcode);
+    r3 = MASK_OP_BIT_D(ctx->opcode);
+    pos1 = MASK_OP_BIT_POS1(ctx->opcode);
+    pos2 = MASK_OP_BIT_POS2(ctx->opcode);
+
+    temp = tcg_temp_new();
+
+    switch (op2) {
+    case OPC2_32_BIT_SH_NAND_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1] , cpu_gpr_d[r2] ,
+                    pos1, pos2, &tcg_gen_nand_tl);
+        tcg_gen_andi_tl(temp, temp, 0x1);
+        break;
+    case OPC2_32_BIT_SH_ORN_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_orc_tl);
+        tcg_gen_andi_tl(temp, temp, 0x1);
+        break;
+    case OPC2_32_BIT_SH_XNOR_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_xor_tl);
+        tcg_gen_not_tl(temp, temp);
+        tcg_gen_andi_tl(temp, temp, 0x1);
+        break;
+    case OPC2_32_BIT_SH_XOR_T:
+        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
+                    pos1, pos2, &tcg_gen_xor_tl);
+        break;
+    }
+    tcg_gen_shli_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], 1);
+    tcg_gen_add_tl(cpu_gpr_d[r3], cpu_gpr_d[r3], temp);
+    tcg_temp_free(temp);
+}
+
 static void decode_32Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
 {
     int op1;
@@ -1430,6 +1757,28 @@ static void decode_32Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
         address = MASK_OP_B_DISP24(ctx->opcode);
         gen_compute_branch(ctx, op1, 0, 0, 0, address);
         break;
+/* Bit-format */
+    case OPCM_32_BIT_ANDACC:
+        decode_bit_andacc(env, ctx);
+        break;
+    case OPCM_32_BIT_LOGICAL_T1:
+        decode_bit_logical_t(env, ctx);
+        break;
+    case OPCM_32_BIT_INSERT:
+        decode_bit_insert(env, ctx);
+        break;
+    case OPCM_32_BIT_LOGICAL_T2:
+        decode_bit_logical_t2(env, ctx);
+        break;
+    case OPCM_32_BIT_ORAND:
+        decode_bit_orand(env, ctx);
+        break;
+    case OPCM_32_BIT_SH_LOGIC1:
+        decode_bit_sh_logic1(env, ctx);
+        break;
+    case OPCM_32_BIT_SH_LOGIC2:
+        decode_bit_sh_logic2(env, ctx);
+        break;
     }
 }
 
-- 
2.1.1

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

* [Qemu-devel] [PATCH 5/5] target-tricore: Add instructions of BO opcode format
  2014-09-27 14:58 [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions Bastian Koppelmann
                   ` (3 preceding siblings ...)
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT " Bastian Koppelmann
@ 2014-09-27 14:58 ` Bastian Koppelmann
  2014-09-28  6:17   ` Richard Henderson
  4 siblings, 1 reply; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-27 14:58 UTC (permalink / raw)
  To: qemu-devel; +Cc: peter.maydell, rth

Add instructions of BO opcode format.
Add microcode generator functions gen_swap, gen_ldmst.
Add helper for loading/storing byte, halfword, upper halfword word, dword in circular and bit reverse addr mode
Add sign extended bitmask for BO_OFF10 field.

Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>
---
 target-tricore/helper.h          |  42 +++
 target-tricore/op_helper.c       | 483 ++++++++++++++++++++++++++++++++
 target-tricore/translate.c       | 582 +++++++++++++++++++++++++++++++++++++++
 target-tricore/tricore-opcodes.h |   2 +
 4 files changed, 1109 insertions(+)

diff --git a/target-tricore/helper.h b/target-tricore/helper.h
index fbabbd5..ee8c9a7 100644
--- a/target-tricore/helper.h
+++ b/target-tricore/helper.h
@@ -27,3 +27,45 @@ DEF_HELPER_2(ldlcx, void, env, i32)
 DEF_HELPER_2(lducx, void, env, i32)
 DEF_HELPER_2(stlcx, void, env, i32)
 DEF_HELPER_2(stucx, void, env, i32)
+/* ld circ */
+DEF_HELPER_4(ld_b_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_bu_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_h_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_hu_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_q_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ldmst_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_a_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_w_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_d_circ, void, env, i32, i32, int)
+DEF_HELPER_4(ld_da_circ, void, env, i32, i32, int)
+/* st circ */
+DEF_HELPER_4(st_a_circ, void, env, i32, i32, int)
+DEF_HELPER_4(st_b_circ, void, env, i32, i32, int)
+DEF_HELPER_4(st_d_circ, void, env, i32, i32, int)
+DEF_HELPER_4(st_da_circ, void, env, i32, i32, int)
+DEF_HELPER_4(st_h_circ, void, env, i32, i32, int)
+DEF_HELPER_4(st_q_circ, void, env, i32, i32, int)
+DEF_HELPER_4(st_w_circ, void, env, i32, i32, int)
+DEF_HELPER_4(swap_circ, void, env, i32, i32, int)
+DEF_HELPER_3(empty_circ, void, env, i32, int)
+/* ld br */
+DEF_HELPER_3(ld_b_br, void, env, i32, i32)
+DEF_HELPER_3(ld_bu_br, void, env, i32, i32)
+DEF_HELPER_3(ld_h_br, void, env, i32, i32)
+DEF_HELPER_3(ld_hu_br, void, env, i32, i32)
+DEF_HELPER_3(ld_q_br, void, env, i32, i32)
+DEF_HELPER_3(ldmst_br, void, env, i32, i32)
+DEF_HELPER_3(ld_a_br, void, env, i32, i32)
+DEF_HELPER_3(ld_w_br, void, env, i32, i32)
+DEF_HELPER_3(ld_d_br, void, env, i32, i32)
+DEF_HELPER_3(ld_da_br, void, env, i32, i32)
+/* st br */
+DEF_HELPER_3(st_a_br, void, env, i32, i32)
+DEF_HELPER_3(st_b_br, void, env, i32, i32)
+DEF_HELPER_3(st_d_br, void, env, i32, i32)
+DEF_HELPER_3(st_da_br, void, env, i32, i32)
+DEF_HELPER_3(st_h_br, void, env, i32, i32)
+DEF_HELPER_3(st_q_br, void, env, i32, i32)
+DEF_HELPER_3(st_w_br, void, env, i32, i32)
+DEF_HELPER_3(swap_br, void, env, i32, i32)
+DEF_HELPER_2(empty_br, void, env, i32)
diff --git a/target-tricore/op_helper.c b/target-tricore/op_helper.c
index 7a33afd..c965a46 100644
--- a/target-tricore/op_helper.c
+++ b/target-tricore/op_helper.c
@@ -20,6 +20,489 @@
 #include "exec/helper-proto.h"
 #include "exec/cpu_ldst.h"
 
+/* Addressing mode helper */
+
+#define CIRC_BR_DEFINES(reg)                                       \
+    uint32_t index = env->gpr_a[reg+1] & 0xffff;                   \
+    uint32_t length_incr = (env->gpr_a[reg+1] & 0xffff0000) >> 16; \
+
+static uint16_t reverse16(uint16_t val)
+{
+    uint8_t high = (uint8_t)(val >> 8);
+    uint8_t low  = (uint8_t)(val & 0xff);
+
+    uint16_t rh, rl;
+
+    rl = (uint16_t)((high * 0x0202020202ULL & 0x010884422010ULL) % 1023);
+    rh = (uint16_t)((low * 0x0202020202ULL & 0x010884422010ULL) % 1023);
+
+    return (rh << 8) | rl;
+}
+
+#define BR_CALC_INDEX(reg, index, incr) do {                           \
+    int32_t new_index = reverse16(reverse16(index) + reverse16(incr)); \
+    env->gpr_a[reg+1] = (incr << 16) | new_index;                      \
+} while (0)
+
+#define CIRC_CALC_INDEX(reg, off, len) do {         \
+    int32_t new_index = index + off;                \
+    if (new_index < 0) {                            \
+        new_index = new_index + len;                \
+    } else {                                        \
+        new_index = new_index % len;                \
+    }                                               \
+    env->gpr_a[reg+1] = (len << 16) | new_index; \
+} while (0)
+
+void helper_ld_b_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldsb_data(env, ea);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_bu_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2,
+                       int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldub_data(env, ea);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_h_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldsw_data(env, ea);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_hu_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2,
+                       int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_lduw_data(env, ea);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_q_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_lduw_data(env, ea) << 16;
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ldmst_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2,
+                       int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    /* M(EA, word) = (M(EA, word) & ~E[a][63:32]) | (E[a][31:0] & E[a][63:32]);
+     */
+    uint32_t data = (cpu_ldl_data(env, ea) & ~(env->gpr_d[r1+1])) |
+                     (env->gpr_d[r1] & env->gpr_d[r1+1]);
+    cpu_stl_data(env, ea, data);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_a_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_a[r1] = cpu_ldl_data(env, ea);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_w_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    uint32_t ea2 = env->gpr_a[r2] + (index + 2 % length_incr);
+
+    uint32_t hw_ea2 = cpu_lduw_data(env, ea2) << 16;
+    uint32_t lw_ea0 = cpu_lduw_data(env, ea0);
+
+    env->gpr_d[r1] = hw_ea2 | lw_ea0;
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_d_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    uint32_t ea2 = env->gpr_a[r2] + (index + 2 % length_incr);
+    uint32_t ea4 = env->gpr_a[r2] + (index + 4 % length_incr);
+    uint32_t ea6 = env->gpr_a[r2] + (index + 6 % length_incr);
+
+
+    uint32_t hw_ea6 = cpu_lduw_data(env, ea6) << 16;
+    uint32_t lw_ea4 = cpu_lduw_data(env, ea4);
+    uint32_t hw_ea2 = cpu_lduw_data(env, ea2) << 16;
+    uint32_t lw_ea0 = cpu_lduw_data(env, ea0);
+
+    env->gpr_d[r1] = hw_ea6 | lw_ea4;
+    env->gpr_d[r1+1] = hw_ea2 | lw_ea0;
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_ld_da_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2,
+                       int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    uint32_t ea4 = env->gpr_a[r2] + (index + 4 % length_incr);
+
+    env->gpr_a[r1] = cpu_lduw_data(env, ea4);
+    env->gpr_a[r1+1] = cpu_lduw_data(env, ea0);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_a_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    cpu_stb_data(env, ea0, env->gpr_a[r1]);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_b_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    cpu_stb_data(env, ea0, env->gpr_d[r1]);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_d_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    uint32_t ea2 = env->gpr_a[r2] + (index + 2 % length_incr);
+    uint32_t ea4 = env->gpr_a[r2] + (index + 4 % length_incr);
+    uint32_t ea6 = env->gpr_a[r2] + (index + 6 % length_incr);
+
+    cpu_stw_data(env, ea0, env->gpr_d[r1]);
+    cpu_stw_data(env, ea2, env->gpr_d[r1] >> 16);
+    cpu_stw_data(env, ea4, env->gpr_d[r1+1]);
+    cpu_stw_data(env, ea6, env->gpr_d[r1+1]  >> 16);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_da_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2,
+                       int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    uint32_t ea4 = env->gpr_a[r2] + (index + 4 % length_incr);
+
+    cpu_stl_data(env, ea0, env->gpr_d[r1]);
+    cpu_stl_data(env, ea4, env->gpr_d[r1+1]);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_h_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    cpu_stw_data(env, ea0, env->gpr_d[r1]);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_q_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    cpu_stw_data(env, ea0, env->gpr_d[r1] >> 16);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_st_w_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+    uint32_t ea2 = env->gpr_a[r2] + (index + 2 % length_incr);
+
+    cpu_stw_data(env, ea0, env->gpr_d[r1]);
+    cpu_stw_data(env, ea2, env->gpr_d[r1] >> 16);
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+void helper_swap_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea0 = env->gpr_a[r2] + index;
+
+    uint32_t tmp = cpu_ldl_data(env, ea0);
+    cpu_stl_data(env, ea0, env->gpr_d[r1]);
+    env->gpr_d[r1] = tmp;
+
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+/* for cache reads/writes */
+void helper_empty_circ(CPUTriCoreState *env, uint32_t r2, int off10)
+{
+    CIRC_BR_DEFINES(r2)
+    CIRC_CALC_INDEX(r2, off10, length_incr);
+}
+
+/*
+ * Bit reverse helpers
+ */
+
+void helper_ld_b_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldsb_data(env, ea);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_bu_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldub_data(env, ea);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_h_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldsw_data(env, ea);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_hu_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_lduw_data(env, ea);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_q_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_lduw_data(env, ea) << 16;
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ldmst_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+/* M(EA, word) = (M(EA, word) & ~E[a][63:32]) | (E[a][31:0] & E[a][63:32]); */
+    uint32_t data = (cpu_ldl_data(env, ea) & ~(env->gpr_d[r1+1])) |
+                     (env->gpr_d[r1] & env->gpr_d[r1+1]);
+    cpu_stl_data(env, ea, data);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_a_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_a[r1] = cpu_ldl_data(env, ea);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_w_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    env->gpr_d[r1] = cpu_ldl_data(env, ea);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_d_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    uint64_t data = cpu_ldq_data(env, ea);
+
+    env->gpr_d[r1] = (uint32_t)data;
+    env->gpr_d[r1+1] = (uint32_t)(data >> 32);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_ld_da_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    uint64_t data = cpu_ldq_data(env, ea);
+
+    env->gpr_a[r1] = (uint32_t)data;
+    env->gpr_a[r1+1] = (uint32_t)(data >> 32);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_a_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    cpu_stl_data(env, ea, env->gpr_a[r1]);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_b_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    cpu_stb_data(env, ea, env->gpr_a[r1]);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_d_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    uint64_t data = ((uint64_t)(env->gpr_d[r1+1]) << 32) | (env->gpr_d[r1]);
+    cpu_stq_data(env, ea, data);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_da_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    uint64_t data = ((uint64_t)(env->gpr_a[r1+1]) << 32) | (env->gpr_a[r1]);
+    cpu_stq_data(env, ea, data);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_h_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    cpu_stw_data(env, ea, env->gpr_d[r1]);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_q_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    cpu_stw_data(env, ea, env->gpr_d[r1] >> 16);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_st_w_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+
+    uint32_t ea = env->gpr_a[r2] + index;
+    cpu_stl_data(env, ea, env->gpr_d[r1]);
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+void helper_swap_br(CPUTriCoreState *env, uint32_t r1, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+    uint32_t ea = env->gpr_a[r2] + index;
+
+    uint32_t tmp = cpu_ldl_data(env, ea);
+    cpu_stl_data(env, ea, env->gpr_d[r1]);
+    env->gpr_d[r1] = tmp;
+
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
+/* for cache reads/writes */
+void helper_empty_br(CPUTriCoreState *env, uint32_t r2)
+{
+    CIRC_BR_DEFINES(r2)
+    BR_CALC_INDEX(r2, index, length_incr);
+}
+
 #define SSOV(env, ret, arg, len) do {               \
     int64_t max_pos = INT##len ##_MAX;              \
     int64_t max_neg = INT##len ##_MIN;              \
diff --git a/target-tricore/translate.c b/target-tricore/translate.c
index 34375a9..2bb7309 100644
--- a/target-tricore/translate.c
+++ b/target-tricore/translate.c
@@ -149,6 +149,15 @@ static void gen_st_2regs_64(TCGv rh, TCGv rl, TCGv address, DisasContext *ctx)
     tcg_temp_free_i64(temp);
 }
 
+static void gen_offset_st_2regs(TCGv rh, TCGv rl, TCGv base, int16_t con,
+                                DisasContext *ctx)
+{
+    TCGv temp = tcg_temp_new();
+    tcg_gen_addi_tl(temp, base, con);
+    gen_st_2regs_64(rh, rl, temp, ctx);
+    tcg_temp_free(temp);
+}
+
 static void gen_ld_2regs_64(TCGv rh, TCGv rl, TCGv address, DisasContext *ctx)
 {
     TCGv_i64 temp = tcg_temp_new_i64();
@@ -162,6 +171,15 @@ static void gen_ld_2regs_64(TCGv rh, TCGv rl, TCGv address, DisasContext *ctx)
     tcg_temp_free_i64(temp);
 }
 
+static void gen_offset_ld_2regs(TCGv rh, TCGv rl, TCGv base, int16_t con,
+                                DisasContext *ctx)
+{
+    TCGv temp = tcg_temp_new();
+    tcg_gen_addi_tl(temp, base, con);
+    gen_ld_2regs_64(rh, rl, temp, ctx);
+    tcg_temp_free(temp);
+}
+
 /* M(EA, word) = (M(EA, word) & ~E[a][63:32]) | (E[a][31:0] & E[a][63:32]); */
 static void gen_ldmst(DisasContext *ctx, int ereg, TCGv ea)
 {
@@ -1674,6 +1692,551 @@ static void decode_bit_sh_logic2(CPUTriCoreState *env, DisasContext *ctx)
     tcg_temp_free(temp);
 }
 
+/* BO-format */
+
+
+static void decode_bo_addrmode_post_pre_base(CPUTriCoreState *env,
+                                             DisasContext *ctx)
+{
+    uint32_t op2;
+    uint32_t off10;
+    int32_t r1, r2;
+    TCGv temp;
+
+    r1 = MASK_OP_BO_S1D(ctx->opcode);
+    r2  = MASK_OP_BO_S2(ctx->opcode);
+    off10 = MASK_OP_BO_OFF10_SEXT(ctx->opcode);
+    op2 = MASK_OP_BO_OP2(ctx->opcode);
+
+    switch (op2) {
+    case OPC2_32_BO_CACHEA_WI_SHORTOFF:
+    case OPC2_32_BO_CACHEA_W_SHORTOFF:
+    case OPC2_32_BO_CACHEA_I_SHORTOFF:
+        /* instruction to access the cache */
+        break;
+    case OPC2_32_BO_CACHEA_WI_POSTINC:
+    case OPC2_32_BO_CACHEA_W_POSTINC:
+    case OPC2_32_BO_CACHEA_I_POSTINC:
+        /* instruction to access the cache, but we still need to handle
+           the addressing mode */
+        tcg_gen_addi_tl(cpu_gpr_d[r2], cpu_gpr_d[r2], off10);
+        break;
+    case OPC2_32_BO_CACHEA_WI_PREINC:
+    case OPC2_32_BO_CACHEA_W_PREINC:
+    case OPC2_32_BO_CACHEA_I_PREINC:
+        /* instruction to access the cache, but we still need to handle
+           the addressing mode */
+        tcg_gen_addi_tl(cpu_gpr_d[r2], cpu_gpr_d[r2], off10);
+        break;
+    case OPC2_32_BO_CACHEI_WI_SHORTOFF:
+    case OPC2_32_BO_CACHEI_W_SHORTOFF:
+        /* TODO: Raise illegal opcode trap,
+                 if tricore_feature(TRICORE_FEATURE_13) */
+        break;
+    case OPC2_32_BO_CACHEI_W_POSTINC:
+    case OPC2_32_BO_CACHEI_WI_POSTINC:
+        if (!tricore_feature(env, TRICORE_FEATURE_13)) {
+            tcg_gen_addi_tl(cpu_gpr_d[r2], cpu_gpr_d[r2], off10);
+        } /* TODO: else raise illegal opcode trap */
+        break;
+    case OPC2_32_BO_CACHEI_W_PREINC:
+    case OPC2_32_BO_CACHEI_WI_PREINC:
+        if (!tricore_feature(env, TRICORE_FEATURE_13)) {
+            tcg_gen_addi_tl(cpu_gpr_d[r2], cpu_gpr_d[r2], off10);
+        } /* TODO: else raise illegal opcode trap */
+        break;
+    case OPC2_32_BO_ST_A_SHORTOFF:
+        gen_offset_st(ctx, cpu_gpr_a[r1], cpu_gpr_a[r2], off10, MO_LESL);
+        break;
+    case OPC2_32_BO_ST_A_POSTINC:
+        tcg_gen_qemu_st_tl(cpu_gpr_a[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LESL);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_ST_A_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_st_tl(cpu_gpr_a[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LESL);
+        break;
+    case OPC2_32_BO_ST_B_SHORTOFF:
+        gen_offset_st(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_UB);
+        break;
+    case OPC2_32_BO_ST_B_POSTINC:
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_UB);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_ST_B_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_UB);
+        break;
+    case OPC2_32_BO_ST_D_SHORTOFF:
+        gen_offset_st_2regs(cpu_gpr_d[r1+1], cpu_gpr_d[r1], cpu_gpr_a[r2],
+                            off10, ctx);
+        break;
+    case OPC2_32_BO_ST_D_POSTINC:
+        gen_st_2regs_64(cpu_gpr_d[r1+1], cpu_gpr_d[r1], cpu_gpr_a[r2], ctx);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_ST_D_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        gen_st_2regs_64(cpu_gpr_d[r1+1], cpu_gpr_d[r1], cpu_gpr_a[r2], ctx);
+        break;
+    case OPC2_32_BO_ST_DA_SHORTOFF:
+        gen_offset_st_2regs(cpu_gpr_a[r1+1], cpu_gpr_a[r1], cpu_gpr_a[r2],
+                            off10, ctx);
+        break;
+    case OPC2_32_BO_ST_DA_POSTINC:
+        gen_st_2regs_64(cpu_gpr_a[r1+1], cpu_gpr_a[r1], cpu_gpr_a[r2], ctx);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_ST_DA_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        gen_st_2regs_64(cpu_gpr_a[r1+1], cpu_gpr_a[r1], cpu_gpr_a[r2], ctx);
+        break;
+    case OPC2_32_BO_ST_H_SHORTOFF:
+        gen_offset_st(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_LEUW);
+        break;
+    case OPC2_32_BO_ST_H_POSTINC:
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUW);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_ST_H_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUW);
+        break;
+    case OPC2_32_BO_ST_Q_SHORTOFF:
+        temp = tcg_temp_new();
+        tcg_gen_shri_tl(temp, cpu_gpr_d[r1], 16);
+        gen_offset_st(ctx, temp, cpu_gpr_a[r2], off10, MO_LEUW);
+        tcg_temp_free(temp);
+        break;
+    case OPC2_32_BO_ST_Q_POSTINC:
+        temp = tcg_temp_new();
+        tcg_gen_shri_tl(temp, cpu_gpr_d[r1], 16);
+        gen_offset_st(ctx, temp, cpu_gpr_a[r2], off10, MO_LEUW);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_temp_free(temp);
+        break;
+    case OPC2_32_BO_ST_Q_PREINC:
+        temp = tcg_temp_new();
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_shri_tl(temp, cpu_gpr_d[r1], 16);
+        gen_offset_st(ctx, temp, cpu_gpr_a[r2], off10, MO_LEUW);
+        tcg_temp_free(temp);
+        break;
+    case OPC2_32_BO_ST_W_SHORTOFF:
+        gen_offset_st(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_LEUL);
+        break;
+    case OPC2_32_BO_ST_W_POSTINC:
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUL);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_ST_W_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_st_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUL);
+        break;
+    }
+}
+
+static void decode_bo_addrmode_bitreverse_circular(CPUTriCoreState *env,
+                                                   DisasContext *ctx)
+{
+    uint32_t op2;
+    uint32_t off10;
+    int32_t r1, r2;
+    TCGv temp, temp2, temp3;
+
+    r1 = MASK_OP_BO_S1D(ctx->opcode);
+    r2  = MASK_OP_BO_S2(ctx->opcode);
+    off10 = MASK_OP_BO_OFF10_SEXT(ctx->opcode);
+    op2 = MASK_OP_BO_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(r1);
+    temp2 = tcg_const_i32(r2);
+    temp3 = tcg_const_i32(off10);
+
+    switch (op2) {
+    case OPC2_32_BO_CACHEA_WI_BR:
+    case OPC2_32_BO_CACHEA_W_BR:
+    case OPC2_32_BO_CACHEA_I_BR:
+        gen_helper_empty_br(cpu_env, temp2);
+        break;
+    case OPC2_32_BO_CACHEA_WI_CIRC:
+    case OPC2_32_BO_CACHEA_W_CIRC:
+    case OPC2_32_BO_CACHEA_I_CIRC:
+        gen_helper_empty_circ(cpu_env, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_A_BR:
+        gen_helper_st_a_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_A_CIRC:
+        gen_helper_st_a_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_B_BR:
+        gen_helper_st_b_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_B_CIRC:
+        gen_helper_st_b_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_D_BR:
+        gen_helper_st_d_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_D_CIRC:
+        gen_helper_st_d_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_DA_BR:
+        gen_helper_st_da_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_DA_CIRC:
+        gen_helper_st_da_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_H_BR:
+        gen_helper_st_h_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_H_CIRC:
+        gen_helper_st_h_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_Q_BR:
+        gen_helper_st_q_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_Q_CIRC:
+        gen_helper_st_q_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_ST_W_BR:
+        gen_helper_st_w_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_ST_W_CIRC:
+        gen_helper_st_w_circ(cpu_env, temp, temp2, temp3);
+        break;
+    }
+    tcg_temp_free(temp);
+    tcg_temp_free(temp2);
+    tcg_temp_free(temp3);
+}
+
+static void decode_bo_addrmode_ld_post_pre_base(CPUTriCoreState *env,
+                                                DisasContext *ctx)
+{
+    uint32_t op2;
+    uint32_t off10;
+    int32_t r1, r2;
+
+    r1 = MASK_OP_BO_S1D(ctx->opcode);
+    r2  = MASK_OP_BO_S2(ctx->opcode);
+    off10 = MASK_OP_BO_OFF10_SEXT(ctx->opcode);
+    op2 = MASK_OP_BO_OP2(ctx->opcode);
+
+    switch (op2) {
+    case OPC2_32_BO_LD_A_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_a[r1], cpu_gpr_a[r2], off10, MO_LEUL);
+        break;
+    case OPC2_32_BO_LD_A_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_a[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUL);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_A_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_ld_tl(cpu_gpr_a[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUL);
+        break;
+    case OPC2_32_BO_LD_B_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_SB);
+        break;
+    case OPC2_32_BO_LD_B_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_SB);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_B_PREINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_SB);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_BU_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_UB);
+        break;
+    case OPC2_32_BO_LD_BU_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_UB);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_BU_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_SB);
+        break;
+    case OPC2_32_BO_LD_D_SHORTOFF:
+        gen_offset_ld_2regs(cpu_gpr_d[r1+1], cpu_gpr_d[r1], cpu_gpr_a[r2],
+                            off10, ctx);
+        break;
+    case OPC2_32_BO_LD_D_POSTINC:
+        gen_ld_2regs_64(cpu_gpr_d[r1+1], cpu_gpr_d[r1], cpu_gpr_a[r2], ctx);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_D_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        gen_ld_2regs_64(cpu_gpr_d[r1+1], cpu_gpr_d[r1], cpu_gpr_a[r2], ctx);
+        break;
+    case OPC2_32_BO_LD_DA_SHORTOFF:
+        gen_offset_ld_2regs(cpu_gpr_a[r1+1], cpu_gpr_a[r1], cpu_gpr_a[r2],
+                            off10, ctx);
+        break;
+    case OPC2_32_BO_LD_DA_POSTINC:
+        gen_ld_2regs_64(cpu_gpr_a[r1+1], cpu_gpr_a[r1], cpu_gpr_a[r2], ctx);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_DA_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        gen_ld_2regs_64(cpu_gpr_a[r1+1], cpu_gpr_a[r1], cpu_gpr_a[r2], ctx);
+        break;
+    case OPC2_32_BO_LD_H_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_LESW);
+        break;
+    case OPC2_32_BO_LD_H_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LESW);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_H_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LESW);
+        break;
+    case OPC2_32_BO_LD_HU_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_LEUW);
+        break;
+    case OPC2_32_BO_LD_HU_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUW);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_HU_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUW);
+        break;
+    case OPC2_32_BO_LD_Q_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_LEUW);
+        tcg_gen_shli_tl(cpu_gpr_d[r1], cpu_gpr_d[r1], 16);
+        break;
+    case OPC2_32_BO_LD_Q_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUW);
+        tcg_gen_shli_tl(cpu_gpr_d[r1], cpu_gpr_d[r1], 16);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_Q_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUW);
+        tcg_gen_shli_tl(cpu_gpr_d[r1], cpu_gpr_d[r1], 16);
+        break;
+    case OPC2_32_BO_LD_W_SHORTOFF:
+        gen_offset_ld(ctx, cpu_gpr_d[r1], cpu_gpr_a[r2], off10, MO_LEUL);
+        break;
+    case OPC2_32_BO_LD_W_POSTINC:
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUL);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LD_W_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        tcg_gen_qemu_ld_tl(cpu_gpr_d[r1], cpu_gpr_a[r2], ctx->mem_idx,
+                           MO_LEUL);
+        break;
+    }
+}
+
+static void decode_bo_addrmode_ld_bitreverse_circular(CPUTriCoreState *env,
+                                                DisasContext *ctx)
+{
+    uint32_t op2;
+    uint32_t off10;
+    int r1, r2;
+
+    TCGv temp, temp2, temp3;
+
+    r1 = MASK_OP_BO_S1D(ctx->opcode);
+    r2 = MASK_OP_BO_S2(ctx->opcode);
+    off10 = MASK_OP_BO_OFF10_SEXT(ctx->opcode);
+    op2 = MASK_OP_BO_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(r1);
+    temp2 = tcg_const_i32(r2);
+    temp3 = tcg_const_i32(off10);
+
+    switch (op2) {
+    case OPC2_32_BO_LD_A_BR:
+        gen_helper_ld_a_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_A_CIRC:
+        gen_helper_ld_a_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_B_BR:
+        gen_helper_ld_b_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_B_CIRC:
+        gen_helper_ld_b_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_BU_BR:
+        gen_helper_ld_bu_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_BU_CIRC:
+        gen_helper_ld_bu_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_D_BR:
+        gen_helper_ld_d_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_D_CIRC:
+        gen_helper_ld_d_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_DA_BR:
+        gen_helper_ld_da_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_DA_CIRC:
+        gen_helper_ld_da_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_H_BR:
+        gen_helper_ld_h_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_H_CIRC:
+        gen_helper_ld_h_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_HU_BR:
+        gen_helper_ld_hu_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_HU_CIRC:
+        gen_helper_ld_hu_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_Q_BR:
+        gen_helper_ld_q_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_Q_CIRC:
+        gen_helper_ld_q_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_LD_W_BR:
+        gen_helper_ld_w_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LD_W_CIRC:
+        gen_helper_ld_w_circ(cpu_env, temp, temp2, temp3);
+        break;
+    }
+    tcg_temp_free(temp);
+    tcg_temp_free(temp2);
+    tcg_temp_free(temp3);
+}
+
+static void decode_bo_addrmode_stctx_post_pre_base(CPUTriCoreState *env,
+                                                   DisasContext *ctx)
+{
+    uint32_t op2;
+    uint32_t off10;
+    int r1, r2;
+
+    TCGv temp, temp2;
+
+    r1 = MASK_OP_BO_S1D(ctx->opcode);
+    r2 = MASK_OP_BO_S2(ctx->opcode);
+    off10 = MASK_OP_BO_OFF10_SEXT(ctx->opcode);
+    op2 = MASK_OP_BO_OP2(ctx->opcode);
+
+
+    temp = tcg_temp_new();
+    temp2 = tcg_temp_new();
+
+    switch (op2) {
+    case OPC2_32_BO_LDLCX_SHORTOFF:
+        tcg_gen_addi_tl(temp, cpu_gpr_a[r2], off10);
+        gen_helper_ldlcx(cpu_env, temp);
+        break;
+    case OPC2_32_BO_LDMST_SHORTOFF:
+        tcg_gen_addi_tl(temp, cpu_gpr_a[r2], off10);
+        gen_ldmst(ctx, r1, temp);
+        break;
+    case OPC2_32_BO_LDMST_POSTINC:
+        gen_ldmst(ctx, r1, cpu_gpr_a[r2]);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_LDMST_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        gen_ldmst(ctx, r1, cpu_gpr_a[r2]);
+        break;
+    case OPC2_32_BO_LDUCX_SHORTOFF:
+        tcg_gen_addi_tl(temp, cpu_gpr_a[r2], off10);
+        gen_helper_lducx(cpu_env, temp);
+        break;
+    case OPC2_32_BO_LEA_SHORTOFF:
+        tcg_gen_addi_tl(cpu_gpr_a[r1], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_STLCX_SHORTOFF:
+        tcg_gen_addi_tl(temp, cpu_gpr_a[r2], off10);
+        gen_helper_stlcx(cpu_env, temp);
+        break;
+    case OPC2_32_BO_STUCX_SHORTOFF:
+        tcg_gen_addi_tl(temp, cpu_gpr_a[r2], off10);
+        gen_helper_stucx(cpu_env, temp);
+        break;
+    case OPC2_32_BO_SWAP_W_SHORTOFF:
+        tcg_gen_addi_tl(temp, cpu_gpr_a[r2], off10);
+        gen_swap(ctx, r1, temp);
+        break;
+    case OPC2_32_BO_SWAP_W_POSTINC:
+        gen_swap(ctx, r1, cpu_gpr_a[r2]);
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        break;
+    case OPC2_32_BO_SWAP_W_PREINC:
+        tcg_gen_addi_tl(cpu_gpr_a[r2], cpu_gpr_a[r2], off10);
+        gen_swap(ctx, r1, cpu_gpr_a[r2]);
+        break;
+    }
+    tcg_temp_free(temp);
+    tcg_temp_free(temp2);
+}
+
+static void decode_bo_addrmode_ldmst_bitreverse_circular(CPUTriCoreState *env,
+                                                         DisasContext *ctx)
+{
+    uint32_t op2;
+    uint32_t off10;
+    int r1, r2;
+
+    TCGv temp, temp2, temp3;
+
+    r1 = MASK_OP_BO_S1D(ctx->opcode);
+    r2 = MASK_OP_BO_S2(ctx->opcode);
+    off10 = MASK_OP_BO_OFF10_SEXT(ctx->opcode);
+    op2 = MASK_OP_BO_OP2(ctx->opcode);
+
+    temp = tcg_const_i32(r1);
+    temp2 = tcg_const_i32(r2);
+    temp3 = tcg_const_i32(off10);
+
+    switch (op2) {
+    case OPC2_32_BO_LDMST_BR:
+        gen_helper_ldmst_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_LDMST_CIRC:
+        gen_helper_ldmst_circ(cpu_env, temp, temp2, temp3);
+        break;
+    case OPC2_32_BO_SWAP_W_BR:
+        gen_helper_swap_br(cpu_env, temp, temp2);
+        break;
+    case OPC2_32_BO_SWAP_W_CIRC:
+        gen_helper_swap_circ(cpu_env, temp, temp2, temp3);
+        break;
+    }
+    tcg_temp_free(temp);
+    tcg_temp_free(temp2);
+    tcg_temp_free(temp3);
+}
+
 static void decode_32Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
 {
     int op1;
@@ -1779,6 +2342,25 @@ static void decode_32Bit_opc(CPUTriCoreState *env, DisasContext *ctx)
     case OPCM_32_BIT_SH_LOGIC2:
         decode_bit_sh_logic2(env, ctx);
         break;
+    /* BO Format */
+    case OPCM_32_BO_ADDRMODE_POST_PRE_BASE:
+        decode_bo_addrmode_post_pre_base(env, ctx);
+        break;
+    case OPCM_32_BO_ADDRMODE_BITREVERSE_CIRCULAR:
+        decode_bo_addrmode_bitreverse_circular(env, ctx);
+        break;
+    case OPCM_32_BO_ADDRMODE_LD_POST_PRE_BASE:
+        decode_bo_addrmode_ld_post_pre_base(env, ctx);
+        break;
+    case OPCM_32_BO_ADDRMODE_LD_BITREVERSE_CIRCULAR:
+        decode_bo_addrmode_ld_bitreverse_circular(env, ctx);
+        break;
+    case OPCM_32_BO_ADDRMODE_STCTX_POST_PRE_BASE:
+        decode_bo_addrmode_stctx_post_pre_base(env, ctx);
+        break;
+    case OPCM_32_BO_ADDRMODE_LDMST_BITREVERSE_CIRCULAR:
+        decode_bo_addrmode_ldmst_bitreverse_circular(env, ctx);
+        break;
     }
 }
 
diff --git a/target-tricore/tricore-opcodes.h b/target-tricore/tricore-opcodes.h
index 342414f..7e6f33b 100644
--- a/target-tricore/tricore-opcodes.h
+++ b/target-tricore/tricore-opcodes.h
@@ -105,6 +105,8 @@
 /* BO Format */
 #define MASK_OP_BO_OFF10(op)   (MASK_BITS_SHIFT(op, 16, 21) + \
                                (MASK_BITS_SHIFT(op, 28, 31) << 6))
+#define MASK_OP_BO_OFF10_SEXT(op)   (MASK_BITS_SHIFT_SEXT(op, 16, 21) + \
+                                    (MASK_BITS_SHIFT_SEXT(op, 28, 31) << 6))
 #define MASK_OP_BO_OP2(op)     MASK_BITS_SHIFT(op, 22, 27)
 #define MASK_OP_BO_S2(op)      MASK_BITS_SHIFT(op, 12, 15)
 #define MASK_OP_BO_S1D(op)     MASK_BITS_SHIFT(op, 8, 11)
-- 
2.1.1

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

* Re: [Qemu-devel] [PATCH 2/5] target-tricore: Add instructions of ABS, ABSB opcode format
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 2/5] target-tricore: Add instructions of ABS, ABSB opcode format Bastian Koppelmann
@ 2014-09-28  1:30   ` Richard Henderson
  0 siblings, 0 replies; 13+ messages in thread
From: Richard Henderson @ 2014-09-28  1:30 UTC (permalink / raw)
  To: Bastian Koppelmann, qemu-devel; +Cc: peter.maydell

On 09/27/2014 07:58 AM, Bastian Koppelmann wrote:
 +    env->gpr_a[2] = cpu_ldl_data(env, ea+8);
> +    env->gpr_a[3] = cpu_ldl_data(env, ea+12);
> +    env->gpr_d[0]  = cpu_ldl_data(env, ea+16);
> +    env->gpr_d[1]  = cpu_ldl_data(env, ea+20);
> +    env->gpr_d[2] = cpu_ldl_data(env, ea+24);

Watch the extra spaces.

> +static void gen_ld_2regs_64(TCGv rh, TCGv rl, TCGv address, DisasContext *ctx)
> +{
> +    TCGv_i64 temp = tcg_temp_new_i64();
> +
> +    tcg_gen_qemu_ld_i64(temp, address, ctx->mem_idx, MO_LEQ);
> +    /* write back to two 32 bit regs */
> +    tcg_gen_trunc_i64_i32(rl, temp);
> +    tcg_gen_shri_i64(temp, temp, 32);
> +    tcg_gen_trunc_i64_i32(rh, temp);

tcg_gen_extr_i64_i32(rl, rh, temp)

> +/* ABSB-format */
> +    case OPC1_32_ABSB_ST_T:
> +        address = MASK_OP_ABS_OFF18(ctx->opcode);
> +        int8_t b = MASK_OP_ABSB_B(ctx->opcode);
> +        int32_t bpos = MASK_OP_ABSB_BPOS(ctx->opcode);

You're not supposed to be relying on c99 mixed code and declarations.


r~

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

* Re: [Qemu-devel] [PATCH 3/5] target-tricore: Add instructions of B opcode format
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 3/5] target-tricore: Add instructions of B " Bastian Koppelmann
@ 2014-09-28  1:35   ` Richard Henderson
  0 siblings, 0 replies; 13+ messages in thread
From: Richard Henderson @ 2014-09-28  1:35 UTC (permalink / raw)
  To: Bastian Koppelmann, qemu-devel; +Cc: peter.maydell

On 09/27/2014 07:58 AM, Bastian Koppelmann wrote:
> Add instructions of B opcode format.
> 
> Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>
> ---
>  target-tricore/translate.c | 27 +++++++++++++++++++++++++++
>  1 file changed, 27 insertions(+)

Reviewed-by: Richard Henderson <rth@twiddle.net>

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

* Re: [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT opcode format
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT " Bastian Koppelmann
@ 2014-09-28  5:22   ` Richard Henderson
  2014-09-28 12:05     ` Bastian Koppelmann
  0 siblings, 1 reply; 13+ messages in thread
From: Richard Henderson @ 2014-09-28  5:22 UTC (permalink / raw)
  To: Bastian Koppelmann, qemu-devel; +Cc: peter.maydell

On 09/27/2014 07:58 AM, Bastian Koppelmann wrote:
> +/* D[c] = D[c][0] op1 (D[a][pos1] op2 D[b][pos2]);*/
> +static inline void gen_bit_2op(TCGv ret, TCGv r1, TCGv r2, TCGv r3,
> +                               int pos1, int pos2,
> +                               void(*op1)(TCGv, TCGv, TCGv),
> +                               void(*op2)(TCGv, TCGv, TCGv))
> +{
> +    TCGv temp1, temp2, temp3;
> +
> +    temp1 = tcg_temp_new();
> +    temp2 = tcg_temp_new();
> +    temp3 = tcg_temp_new();
> +
> +    tcg_gen_andi_tl(temp3, r3, 0x1);
> +
> +    tcg_gen_andi_tl(temp2, r2 , (0x1u << pos2));
> +    tcg_gen_shri_tl(temp2, temp2, pos2);
> +
> +    tcg_gen_andi_tl(temp1, r1, (0x1u << pos1));
> +    tcg_gen_shri_tl(temp1, temp1, pos1);
> +
> +    (*op1)(temp1, temp1, temp2);
> +    (*op2)(ret , temp3, temp1);

This incorrectly clobbers bits 1:31 of ret.  You want

  shri tmp1, r2, pos2
  shri tmp1, r1, pos1
  op1(tmp1, tmp1, tmp2)
  op2(tmp1, r3, tmp1)
  deposit ret, ret, tmp1, 0, 1


> +    TCGv temp1, temp2;
> +
> +    temp1 = tcg_temp_new();
> +    temp2 = tcg_temp_new();
> +
> +    tcg_gen_andi_tl(temp2, r2, (0x1u << pos2));
> +    tcg_gen_shri_tl(temp2, temp2, pos2);
> +
> +    tcg_gen_andi_tl(temp1, r1, (0x1u << pos1));
> +    tcg_gen_shri_tl(temp1, temp1, pos1);
> +
> +    (*op1)(ret, temp1, temp2);

This one, though, does get to set the whole register.  That said,
I think you should *not* mask the two inputs, but instead mask the one output.
 That saves one operation, and allows NOR to not need a special case.

> +    case OPC2_32_BIT_AND_NOR_T:
> +        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
> +                    pos1, pos2, &tcg_gen_or_tl, &tcg_gen_andc_tl);
> +        break;

Without trying to take into account the properties of the tcg backend, this
seems less than ideal.  Yes, it's correct, but so is

	tcg_gen_nor_tl, tcg_gen_and_tl

which matches the name of the instruction.

If the tcg backend is sparc or ppc, it's more efficient too, since nor is
actually present in the isa.  But of course, arm and even haswell x86 have andc
but don't have nor.  This is stuff that a normal compiler optimizer could sort
out, but we don't have that for tcg.

I'd be willing to accept something conditionalized on TCG_TARGET_HAS_nor_i32,
if you like, but otherwise just match the instruction.

> +static void decode_bit_insert(CPUTriCoreState *env, DisasContext *ctx)

It's probably better to implement this with one right-shift and one deposit.
Certainly would be easier to read and follow.

> +    case OPC2_32_BIT_XNOR_T:
> +        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
> +                    pos1, pos2, &tcg_gen_xor_tl);

tcg_gen_eqv_tl

> +    case OPC2_32_BIT_OR_NOR_T:
> +        gen_bit_2op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2], cpu_gpr_d[r3],
> +                    pos1, pos2, &tcg_gen_or_tl, &tcg_gen_orc_tl);
> +        break;

Again, probably better with nor + or, or conditionalization.

> +    case OPC2_32_BIT_SH_XNOR_T:
> +        gen_bit_1op(temp, cpu_gpr_d[r1], cpu_gpr_d[r2],
> +                    pos1, pos2, &tcg_gen_xor_tl);
> +        tcg_gen_not_tl(temp, temp);

Again, eqv.


r~

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

* Re: [Qemu-devel] [PATCH 5/5] target-tricore: Add instructions of BO opcode format
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 5/5] target-tricore: Add instructions of BO " Bastian Koppelmann
@ 2014-09-28  6:17   ` Richard Henderson
  0 siblings, 0 replies; 13+ messages in thread
From: Richard Henderson @ 2014-09-28  6:17 UTC (permalink / raw)
  To: Bastian Koppelmann, qemu-devel; +Cc: peter.maydell

On 09/27/2014 07:58 AM, Bastian Koppelmann wrote:
> +/* ld circ */
> +DEF_HELPER_4(ld_b_circ, void, env, i32, i32, int)

Avoid, whenever possible, performing memory operations within helpers.  Doing
that complicates the generation of correct code for exact exceptions from the
memory operation.  I'm not saying it can't be done, but what you're doing right
now certainly isn't correct, and it's easier to do the memory operation with
tcg ops.

So now we need to find an efficient way to do this.  In both cases, I think one
helper each for bit-reverse and circular modes should suffice.

E.g.

	tcg_gen_ext16u_tl(temp, A[b+1])
	tcg_gen_add_tl(ea, A[b], temp)
	tcg_gen_qemu_ld_tl(ret, ea, mmu_idx, MO_UB)
	gen_helper_br_update(A[b+1], A[b+1])

and then

uint32_t helper_br_update(uint32_t reg)
{
    uint32_t index = reg & 0xffff;
    uint32_t incr = reg >> 16;
    uint32_t new_index = reverse16(reverse16(index) + reverse16(incr));
    return reg - index + new_index;
}

uint32_t helper_circ_update(uint32_t reg, uint32_t off)
{
    uint32_t index = reg & 0xffff;
    uint32_t length = reg >> 16;
    int32_t new_index = index + off;
    if (new_index < 0) {
        new_index += length;
    } else {
        new_index %= length;
    }
    return reg - index + new_index;
}


> +void helper_ld_w_circ(CPUTriCoreState *env, uint32_t r1, uint32_t r2, int off10)
> +{
> +    CIRC_BR_DEFINES(r2)
> +
> +    uint32_t ea0 = env->gpr_a[r2] + index;
> +    uint32_t ea2 = env->gpr_a[r2] + (index + 2 % length_incr);
> +
> +    uint32_t hw_ea2 = cpu_lduw_data(env, ea2) << 16;
> +    uint32_t lw_ea0 = cpu_lduw_data(env, ea0);
> +
> +    env->gpr_d[r1] = hw_ea2 | lw_ea0;
> +
> +    CIRC_CALC_INDEX(r2, off10, length_incr);
> +}

I know that the volume 2 pseudo code for LD.W says two halfword loads, but the
volume 1 text, section 2.5.5 says that the buffer end must be aligned to the
size of the access.  As I read it, two memory operations should not be required.


r~

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

* Re: [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes
  2014-09-27 14:58 ` [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes Bastian Koppelmann
@ 2014-09-28  6:18   ` Richard Henderson
  0 siblings, 0 replies; 13+ messages in thread
From: Richard Henderson @ 2014-09-28  6:18 UTC (permalink / raw)
  To: Bastian Koppelmann, qemu-devel; +Cc: peter.maydell

On 09/27/2014 07:58 AM, Bastian Koppelmann wrote:
> Move FCX loading of save_context_ to caller functions, for STLCX, STUCX insn to use those functions.
> Move FCX storing of restore_context_ to caller functions, for LDLCX, LDUCX insn to use those functions.
> Remove do_raise_exception function, which caused clang to emit a warning.
> Fix: save_context_lower now saves a[11] instead of PSW.
> Fix: MASK_OP_ABSB_BPOS starting at wrong offset.
> 
> Signed-off-by: Bastian Koppelmann <kbastian@mail.uni-paderborn.de>

Reviewed-by: Richard Henderson <rth@twiddle.net>


r~

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

* Re: [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT opcode format
  2014-09-28  5:22   ` Richard Henderson
@ 2014-09-28 12:05     ` Bastian Koppelmann
  2014-09-28 13:27       ` Peter Maydell
  0 siblings, 1 reply; 13+ messages in thread
From: Bastian Koppelmann @ 2014-09-28 12:05 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: peter.maydell


On 09/28/2014 06:22 AM, Richard Henderson wrote:
>> +    case OPC2_32_BIT_XNOR_T:
>> +        gen_bit_1op(cpu_gpr_d[r3], cpu_gpr_d[r1], cpu_gpr_d[r2],
>> +                    pos1, pos2, &tcg_gen_xor_tl);
> tcg_gen_eqv_tl
>
I often don't use the optimal tcg-frontend operation, since the 
documentation I mostly use is 
http://wiki.qemu.org/Documentation/TCG/frontend-ops, which is outdated. 
That said, I'm willing to update the documentation to include all the 
latest tcg-ops. Richard, would you be willing to review those changes?

Thanks,

Bastian

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

* Re: [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT opcode format
  2014-09-28 12:05     ` Bastian Koppelmann
@ 2014-09-28 13:27       ` Peter Maydell
  0 siblings, 0 replies; 13+ messages in thread
From: Peter Maydell @ 2014-09-28 13:27 UTC (permalink / raw)
  To: Bastian Koppelmann; +Cc: QEMU Developers, Richard Henderson

On 28 September 2014 13:05, Bastian Koppelmann
<kbastian@mail.uni-paderborn.de> wrote:
> I often don't use the optimal tcg-frontend operation, since the
> documentation I mostly use is
> http://wiki.qemu.org/Documentation/TCG/frontend-ops, which is outdated.

Probably better to read (and update if necessary) tcg/README.

-- PMM

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

end of thread, other threads:[~2014-09-28 13:27 UTC | newest]

Thread overview: 13+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2014-09-27 14:58 [Qemu-devel] [PATCH 0/5] Add TriCore ABS, ABSB, B, BIT, BO instructions Bastian Koppelmann
2014-09-27 14:58 ` [Qemu-devel] [PATCH 1/5] target-tricore: Cleanup and Bugfixes Bastian Koppelmann
2014-09-28  6:18   ` Richard Henderson
2014-09-27 14:58 ` [Qemu-devel] [PATCH 2/5] target-tricore: Add instructions of ABS, ABSB opcode format Bastian Koppelmann
2014-09-28  1:30   ` Richard Henderson
2014-09-27 14:58 ` [Qemu-devel] [PATCH 3/5] target-tricore: Add instructions of B " Bastian Koppelmann
2014-09-28  1:35   ` Richard Henderson
2014-09-27 14:58 ` [Qemu-devel] [PATCH 4/5] target-tricore: Add instructions of BIT " Bastian Koppelmann
2014-09-28  5:22   ` Richard Henderson
2014-09-28 12:05     ` Bastian Koppelmann
2014-09-28 13:27       ` Peter Maydell
2014-09-27 14:58 ` [Qemu-devel] [PATCH 5/5] target-tricore: Add instructions of BO " Bastian Koppelmann
2014-09-28  6:17   ` Richard Henderson

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.