qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8
@ 2013-12-18 20:48 Tom Musta
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06 Tom Musta
                   ` (13 more replies)
  0 siblings, 14 replies; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

The QEMU emulation models for Power7 and Power8 are still missing some
of the base instructions that were introduced in Power ISA 2.06 and
even a few that were introduced prior to that.

This patch series gets these models caught up with respect to the
base 2.06 ISA.  That is, the Book I and Book II instructions for 
the branch, fixed point and floating point units will be completed
with this series.  Decimal floating point is not addressed in this
series, nor are the base ISA 2.07 changes for the Power8 model.

In some cases, existing instructions are re-implemented using common
macros, thus eliminating some redundant code.  The patch series
eliminates almost half as much code as it adds.

Additionally, some bugs in the common floating point library (softfloat)
are fixed.

V2: Addressing comments from Richard Henderson.  Fixed corner case bug
in divweu.

V3: Addressing comments from Peter Maydell.  softloat changes have been
moved back to the VSX stage 3 patch series.

Tom Musta (14):
  target-ppc: Add Flag for Power ISA V2.06
  target-ppc: Add ISA2.06 bpermd Instruction
  target-ppc: Add ISA2.06 divdeu[o] Instructions
  target-ppc: Add ISA2.06 divde[o] Instructions
  target-ppc: Add ISA 2.06 divwe[u][o] Instructions
  target-ppc: Add ISA2.06 lbarx, lharx Instructions
  target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions
  target-ppc: Add ISA2.06 Float to Integer Instructions
  target-ppc: Add ISA 2.06 fcfid[u][s] Instructions
  target-ppc: Fix and enable fri[mnpz]
  target-ppc: Add ISA 2.06 ftdiv Instruction
  target-ppc: Add ISA 2.06 ftsqrt
  target-ppc: Enable frsqrtes on Power7 and Power8
  target-ppc: Add ISA2.06 lfiwzx Instruction

 include/qemu/host-utils.h   |   28 ++++
 target-ppc/cpu.h            |    4 +-
 target-ppc/fpu_helper.c     |  248 +++++++++++++++++++----------------
 target-ppc/helper.h         |   13 ++
 target-ppc/int_helper.c     |   70 ++++++++++
 target-ppc/translate.c      |  309 +++++++++++++++++++++++++++++++++----------
 target-ppc/translate_init.c |   10 +-
 util/host-utils.c           |   75 +++++++++++
 8 files changed, 568 insertions(+), 189 deletions(-)

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

* [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
@ 2013-12-18 20:48 ` Tom Musta
  2013-12-24 15:11   ` Richard Henderson
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction Tom Musta
                   ` (12 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds a flag for base instruction additions to Power ISA
2.06B.  The flag will be used to identify/select basic Book I and
Book II instructions that were newly added in that revision of the
architecture.  The flag will not be used for VSX or Altivec.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/cpu.h            |    4 +++-
 target-ppc/translate_init.c |    6 ++++--
 2 files changed, 7 insertions(+), 3 deletions(-)

diff --git a/target-ppc/cpu.h b/target-ppc/cpu.h
index 0abc848..fe3aace 100644
--- a/target-ppc/cpu.h
+++ b/target-ppc/cpu.h
@@ -1877,9 +1877,11 @@ enum {
     PPC2_ISA205        = 0x0000000000000020ULL,
     /* VSX additions in ISA 2.07                                             */
     PPC2_VSX207        = 0x0000000000000040ULL,
+    /* Book I 2.06B PowerPC specification (base instructions)                */
+    PPC2_ISA206        = 0x0000000000000080ULL,
 
 #define PPC_TCG_INSNS2 (PPC2_BOOKE206 | PPC2_VSX | PPC2_PRCNTL | PPC2_DBRX | \
-                        PPC2_ISA205 | PPC2_VSX207)
+                        PPC2_ISA205 | PPC2_VSX207 | PPC2_ISA206)
 };
 
 /*****************************************************************************/
diff --git a/target-ppc/translate_init.c b/target-ppc/translate_init.c
index e14ab63..491e56c 100644
--- a/target-ppc/translate_init.c
+++ b/target-ppc/translate_init.c
@@ -7234,7 +7234,8 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
                        PPC_64B | PPC_ALTIVEC |
                        PPC_SEGMENT_64B | PPC_SLBI |
                        PPC_POPCNTB | PPC_POPCNTWD;
-    pcc->insns_flags2 = PPC2_VSX | PPC2_DFP | PPC2_DBRX | PPC2_ISA205;
+    pcc->insns_flags2 = PPC2_VSX | PPC2_DFP | PPC2_DBRX | PPC2_ISA205 |
+                        PPC2_ISA206;
     pcc->msr_mask = 0x800000000284FF37ULL;
     pcc->mmu_model = POWERPC_MMU_2_06;
 #if defined(CONFIG_SOFTMMU)
@@ -7270,7 +7271,8 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
                        PPC_64B | PPC_ALTIVEC |
                        PPC_SEGMENT_64B | PPC_SLBI |
                        PPC_POPCNTB | PPC_POPCNTWD;
-    pcc->insns_flags2 = PPC2_VSX | PPC2_VSX207 | PPC2_DFP | PPC2_DBRX;
+    pcc->insns_flags2 = PPC2_VSX | PPC2_VSX207 | PPC2_DFP | PPC2_DBRX |
+                        PPC2_ISA206;
     pcc->msr_mask = 0x800000000284FF36ULL;
     pcc->mmu_model = POWERPC_MMU_2_06;
 #if defined(CONFIG_SOFTMMU)
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06 Tom Musta
@ 2013-12-18 20:48 ` Tom Musta
  2013-12-24 15:17   ` Richard Henderson
  2013-12-28  0:27   ` [Qemu-devel] " Scott Wood
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions Tom Musta
                   ` (11 subsequent siblings)
  13 siblings, 2 replies; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the Bit Permute Doubleword (bpermd) instruction,
which was introduced in Power ISA 2.06 as part of the base 64-bit
architecture.

V2: Addressing stylistic comments from Richard Henderson.

Signed-off-by: Tom Musta <tommusta@gmail.com>
Reviewed-by: Richard Henderson <address@hidden>
---
 target-ppc/helper.h     |    1 +
 target-ppc/int_helper.c |   20 ++++++++++++++++++++
 target-ppc/translate.c  |   10 ++++++++++
 3 files changed, 31 insertions(+), 0 deletions(-)

diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 6250eba..1ec9c65 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -41,6 +41,7 @@ DEF_HELPER_3(sraw, tl, env, tl, tl)
 #if defined(TARGET_PPC64)
 DEF_HELPER_FLAGS_1(cntlzd, TCG_CALL_NO_RWG_SE, tl, tl)
 DEF_HELPER_FLAGS_1(popcntd, TCG_CALL_NO_RWG_SE, tl, tl)
+DEF_HELPER_3(bpermd, i64, env, i64, i64)
 DEF_HELPER_3(srad, tl, env, tl, tl)
 #endif
 
diff --git a/target-ppc/int_helper.c b/target-ppc/int_helper.c
index e50bdd2..abc69a7 100644
--- a/target-ppc/int_helper.c
+++ b/target-ppc/int_helper.c
@@ -53,6 +53,26 @@ target_ulong helper_cntlzd(target_ulong t)
 }
 #endif
 
+#if defined(TARGET_PPC64)
+
+uint64_t helper_bpermd(CPUPPCState *env, uint64_t rs, uint64_t rb)
+{
+    int i;
+    uint64_t ra = 0;
+
+    for (i = 0; i < 8; i++) {
+        int index = (rs >> (i*8)) & 0xFF;
+        if (index < 64) {
+            if (rb & (1ul << (63-index))) {
+                ra |= 1 << i;
+            }
+        }
+    }
+    return ra;
+}
+
+#endif
+
 target_ulong helper_cmpb(target_ulong rs, target_ulong rb)
 {
     target_ulong mask = 0xff;
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 1f7e499..0d39de2 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -1525,6 +1525,15 @@ static void gen_prtyd(DisasContext *ctx)
 #endif
 
 #if defined(TARGET_PPC64)
+/* bpermd */
+static void gen_bpermd(DisasContext *ctx)
+{
+    gen_helper_bpermd(cpu_gpr[rA(ctx->opcode)], cpu_env,
+                      cpu_gpr[rS(ctx->opcode)], cpu_gpr[rB(ctx->opcode)]);
+}
+#endif
+
+#if defined(TARGET_PPC64)
 /* extsw & extsw. */
 GEN_LOGICAL1(extsw, tcg_gen_ext32s_tl, 0x1E, PPC_64B);
 
@@ -9322,6 +9331,7 @@ GEN_HANDLER_E(prtyw, 0x1F, 0x1A, 0x04, 0x0000F801, PPC_NONE, PPC2_ISA205),
 GEN_HANDLER(popcntd, 0x1F, 0x1A, 0x0F, 0x0000F801, PPC_POPCNTWD),
 GEN_HANDLER(cntlzd, 0x1F, 0x1A, 0x01, 0x00000000, PPC_64B),
 GEN_HANDLER_E(prtyd, 0x1F, 0x1A, 0x05, 0x0000F801, PPC_NONE, PPC2_ISA205),
+GEN_HANDLER_E(bpermd, 0x1F, 0x1C, 0x07, 0x00000001, PPC_NONE, PPC2_ISA206),
 #endif
 GEN_HANDLER(rlwimi, 0x14, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
 GEN_HANDLER(rlwinm, 0x15, 0xFF, 0xFF, 0x00000000, PPC_INTEGER),
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06 Tom Musta
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction Tom Musta
@ 2013-12-18 20:48 ` Tom Musta
  2013-12-24 15:20   ` Richard Henderson
  2013-12-28  0:30   ` [Qemu-devel] [Qemu-ppc] " Scott Wood
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 04/14] target-ppc: Add ISA2.06 divde[o] Instructions Tom Musta
                   ` (10 subsequent siblings)
  13 siblings, 2 replies; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the Divide Doubleword Extended Unsigned
instructions.  This instruction requires dividing a 128-bit
value by a 64 bit value.  Since 128 bit integer division is
not supported in TCG, a helper is used, providing a
repeated difference algorithm.

V2: Moved the 128-bit divide routine into host-utils per Richard
Henderson's suggestion.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 include/qemu/host-utils.h |   14 ++++++++++++++
 target-ppc/helper.h       |    1 +
 target-ppc/int_helper.c   |   27 +++++++++++++++++++++++++++
 target-ppc/translate.c    |   20 ++++++++++++++++++++
 util/host-utils.c         |   38 ++++++++++++++++++++++++++++++++++++++
 5 files changed, 100 insertions(+), 0 deletions(-)

diff --git a/include/qemu/host-utils.h b/include/qemu/host-utils.h
index 0f688c1..0ca187d 100644
--- a/include/qemu/host-utils.h
+++ b/include/qemu/host-utils.h
@@ -44,9 +44,23 @@ static inline void muls64(uint64_t *plow, uint64_t *phigh,
     *plow = r;
     *phigh = r >> 64;
 }
+
+static inline int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor)
+{
+    if (divisor == 0) {
+        return 1;
+    } else {
+        __uint128_t dividend = ((__uint128_t)*phigh << 64) | *plow;
+        __uint128_t result = dividend / divisor;
+        *plow = result;
+        *phigh = dividend % divisor;
+        return result > UINT64_MAX;
+    }
+}
 #else
 void muls64(uint64_t *phigh, uint64_t *plow, int64_t a, int64_t b);
 void mulu64(uint64_t *phigh, uint64_t *plow, uint64_t a, uint64_t b);
+int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor);
 #endif
 
 /**
diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 1ec9c65..3eff4df 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -31,6 +31,7 @@ DEF_HELPER_5(lscbx, tl, env, tl, i32, i32, i32)
 
 #if defined(TARGET_PPC64)
 DEF_HELPER_3(mulldo, i64, env, i64, i64)
+DEF_HELPER_4(divdeu, i64, env, i64, i64, i32)
 #endif
 
 DEF_HELPER_FLAGS_1(cntlzw, TCG_CALL_NO_RWG_SE, tl, tl)
diff --git a/target-ppc/int_helper.c b/target-ppc/int_helper.c
index abc69a7..d6dcac9 100644
--- a/target-ppc/int_helper.c
+++ b/target-ppc/int_helper.c
@@ -41,6 +41,33 @@ uint64_t helper_mulldo(CPUPPCState *env, uint64_t arg1, uint64_t arg2)
 }
 #endif
 
+#if defined(TARGET_PPC64)
+
+uint64_t helper_divdeu(CPUPPCState *env, uint64_t ra, uint64_t rb, uint32_t oe)
+{
+    uint64_t rt = 0;
+    int overflow = 0;
+
+    overflow = divu128(&rt, &ra, rb);
+
+    if (unlikely(overflow)) {
+        rt = 0; /* Undefined */
+    }
+
+    if (oe) {
+        if (unlikely(overflow)) {
+            env->so = env->ov = 1;
+        } else {
+            env->ov = 0;
+        }
+    }
+
+    return rt;
+}
+
+#endif
+
+
 target_ulong helper_cntlzw(target_ulong t)
 {
     return clz32(t);
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 0d39de2..7a51c6d 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -1032,6 +1032,23 @@ GEN_INT_ARITH_DIVD(divduo, 0x1E, 0, 1);
 /* divw  divw.  divwo  divwo.   */
 GEN_INT_ARITH_DIVD(divd, 0x0F, 1, 0);
 GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1);
+
+/* divdeu[o][.] */
+#define GEN_DIVDE(name, hlpr, compute_ov)                                     \
+static void gen_##name(DisasContext *ctx)                                     \
+{                                                                             \
+    TCGv_i32 t0 = tcg_const_i32(compute_ov);                                  \
+    gen_helper_##hlpr(cpu_gpr[rD(ctx->opcode)], cpu_env,                      \
+                     cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)], t0); \
+    tcg_temp_free_i32(t0);                                                    \
+    if (unlikely(Rc(ctx->opcode) != 0)) {                                     \
+        gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);                           \
+    }                                                                         \
+}
+
+GEN_DIVDE(divdeu, divdeu, 0);
+GEN_DIVDE(divdeuo, divdeu, 1);
+
 #endif
 
 /* mulhw  mulhw. */
@@ -9594,6 +9611,9 @@ GEN_INT_ARITH_DIVD(divduo, 0x1E, 0, 1),
 GEN_INT_ARITH_DIVD(divd, 0x0F, 1, 0),
 GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1),
 
+GEN_HANDLER_E(divdeu, 0x1F, 0x09, 0x0C, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(divdeuo, 0x1F, 0x09, 0x1C, 0x00000000, PPC_NONE, PPC2_ISA206),
+
 #undef GEN_INT_ARITH_MUL_HELPER
 #define GEN_INT_ARITH_MUL_HELPER(name, opc3)                                  \
 GEN_HANDLER(name, 0x1F, 0x09, opc3, 0x00000000, PPC_64B)
diff --git a/util/host-utils.c b/util/host-utils.c
index f0784d6..b6f7a6e 100644
--- a/util/host-utils.c
+++ b/util/host-utils.c
@@ -86,4 +86,42 @@ void muls64 (uint64_t *plow, uint64_t *phigh, int64_t a, int64_t b)
     }
     *phigh = rh;
 }
+
+/* Unsigned 128x64 division.  Returns 1 if overflow (divide by zero or */
+/* quotient exceeds 64 bits).  Otherwise returns quotient via plow and */
+/* remainder via phigh. */
+int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor)
+{
+    uint64_t dhi = *phigh;
+    uint64_t dlo = *plow;
+    unsigned i;
+    uint64_t carry = 0;
+
+    if (divisor == 0) {
+        return 1;
+    } else if (dhi == 0) {
+        *plow  = dlo / divisor;
+        *phigh = dlo % divisor;
+        return 0;
+    } else if (dhi > divisor) {
+        return 1;
+    } else {
+
+        for (i = 0; i < 64; i++) {
+            carry = dhi >> 63;
+            dhi = (dhi << 1) | (dlo >> 63);
+            if (carry | dhi >= divisor) {
+                dhi -= divisor;
+                carry = 1;
+            } else {
+                carry = 0;
+            }
+            dlo = (dlo << 1) | carry;
+        }
+
+        *plow = dlo;
+        *phigh = dhi;
+        return 0;
+    }
+}
 #endif /* !CONFIG_INT128 */
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 04/14] target-ppc: Add ISA2.06 divde[o] Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (2 preceding siblings ...)
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions Tom Musta
@ 2013-12-18 20:48 ` Tom Musta
  2013-12-24 15:22   ` Richard Henderson
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 05/14] target-ppc: Add ISA 2.06 divwe[u][o] Instructions Tom Musta
                   ` (9 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the Divide Doubleword Extended instructions.
The implementation builds on the unsigned helper provided in
the previous patch.

V2: Updated to use the host-utils 128 bit divide.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 include/qemu/host-utils.h |   14 ++++++++++++++
 target-ppc/helper.h       |    1 +
 target-ppc/int_helper.c   |   23 +++++++++++++++++++++++
 target-ppc/translate.c    |    4 ++++
 util/host-utils.c         |   37 +++++++++++++++++++++++++++++++++++++
 5 files changed, 79 insertions(+), 0 deletions(-)

diff --git a/include/qemu/host-utils.h b/include/qemu/host-utils.h
index 0ca187d..39fe018 100644
--- a/include/qemu/host-utils.h
+++ b/include/qemu/host-utils.h
@@ -57,10 +57,24 @@ static inline int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor)
         return result > UINT64_MAX;
     }
 }
+
+static inline int divs128(int64_t *plow, int64_t *phigh, int64_t divisor)
+{
+    if (divisor == 0) {
+        return 1;
+    } else {
+        __int128_t dividend = ((__int128_t)*phigh << 64) | *plow;
+        __int128_t result = dividend / divisor;
+        *plow = result;
+        *phigh = dividend % divisor;
+        return (result > INT64_MAX) | (result < INT64_MIN);
+    }
+}
 #else
 void muls64(uint64_t *phigh, uint64_t *plow, int64_t a, int64_t b);
 void mulu64(uint64_t *phigh, uint64_t *plow, uint64_t a, uint64_t b);
 int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor);
+int divs128(int64_t *plow, int64_t *phigh, int64_t divisor);
 #endif
 
 /**
diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 3eff4df..4359009 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -32,6 +32,7 @@ DEF_HELPER_5(lscbx, tl, env, tl, i32, i32, i32)
 #if defined(TARGET_PPC64)
 DEF_HELPER_3(mulldo, i64, env, i64, i64)
 DEF_HELPER_4(divdeu, i64, env, i64, i64, i32)
+DEF_HELPER_4(divde, i64, env, i64, i64, i32)
 #endif
 
 DEF_HELPER_FLAGS_1(cntlzw, TCG_CALL_NO_RWG_SE, tl, tl)
diff --git a/target-ppc/int_helper.c b/target-ppc/int_helper.c
index d6dcac9..9b289e7 100644
--- a/target-ppc/int_helper.c
+++ b/target-ppc/int_helper.c
@@ -65,6 +65,29 @@ uint64_t helper_divdeu(CPUPPCState *env, uint64_t ra, uint64_t rb, uint32_t oe)
     return rt;
 }
 
+uint64_t helper_divde(CPUPPCState *env, uint64_t rau, uint64_t rbu, uint32_t oe)
+{
+    int64_t rt = 0;
+    int64_t ra = (int64_t)rau;
+    int64_t rb = (int64_t)rbu;
+    int overflow = divs128(&rt, &ra, rb);
+
+    if (unlikely(overflow)) {
+        rt = 0; /* Undefined */
+    }
+
+    if (oe) {
+
+        if (unlikely(overflow)) {
+            env->so = env->ov = 1;
+        } else {
+            env->ov = 0;
+        }
+    }
+
+    return rt;
+}
+
 #endif
 
 
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 7a51c6d..b274a15 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -1048,6 +1048,8 @@ static void gen_##name(DisasContext *ctx)                                     \
 
 GEN_DIVDE(divdeu, divdeu, 0);
 GEN_DIVDE(divdeuo, divdeu, 1);
+GEN_DIVDE(divde, divde, 0);
+GEN_DIVDE(divdeo, divde, 1);
 
 #endif
 
@@ -9613,6 +9615,8 @@ GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1),
 
 GEN_HANDLER_E(divdeu, 0x1F, 0x09, 0x0C, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_HANDLER_E(divdeuo, 0x1F, 0x09, 0x1C, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(divde, 0x1F, 0x09, 0x0D, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(divdeo, 0x1F, 0x09, 0x1D, 0x00000000, PPC_NONE, PPC2_ISA206),
 
 #undef GEN_INT_ARITH_MUL_HELPER
 #define GEN_INT_ARITH_MUL_HELPER(name, opc3)                                  \
diff --git a/util/host-utils.c b/util/host-utils.c
index b6f7a6e..140e25c 100644
--- a/util/host-utils.c
+++ b/util/host-utils.c
@@ -124,4 +124,41 @@ int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor)
         return 0;
     }
 }
+
+int divs128(int64_t *plow, int64_t *phigh, int64_t divisor)
+{
+    int sgn_dvdnd = *phigh < 0;
+    int sgn_divsr = divisor < 0;
+    int overflow = 0;
+
+    if (sgn_dvdnd) {
+        *plow = ~(*plow);
+        *phigh = ~(*phigh);
+        if (*plow == (int64_t)-1) {
+            *plow = 0;
+            (*phigh)++;
+         } else {
+            (*plow)++;
+         }
+    }
+
+    if (sgn_divsr) {
+        divisor = 0 - divisor;
+    }
+
+    overflow = divu128((uint64_t *)plow, (uint64_t *)phigh, (uint64_t)divisor);
+
+    if (sgn_dvdnd  ^ sgn_divsr) {
+        *plow = 0 - *plow;
+    }
+
+    if (!overflow) {
+        if ((*plow < 0) ^ (sgn_dvdnd ^ sgn_divsr)) {
+            overflow = 1;
+        }
+    }
+
+    return overflow;
+}
+
 #endif /* !CONFIG_INT128 */
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 05/14] target-ppc: Add ISA 2.06 divwe[u][o] Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (3 preceding siblings ...)
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 04/14] target-ppc: Add ISA2.06 divde[o] Instructions Tom Musta
@ 2013-12-18 20:48 ` Tom Musta
  2013-12-24 15:26   ` Richard Henderson
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 06/14] target-ppc: Add ISA2.06 lbarx, lharx Instructions Tom Musta
                   ` (8 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch addes the Signed and Unsigned  Divide Word Extended
instructions which were introduced in Power ISA 2.06.

V2: Eliminating extraneous code in the overflow case per comments
from Richard Henderson.  Fixed corner case bug in divweu (check
for (RA) >= (RB)).

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/translate.c |   70 ++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 70 insertions(+), 0 deletions(-)

diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index b274a15..3344fa9 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -984,6 +984,72 @@ GEN_INT_ARITH_DIVW(divwuo, 0x1E, 0, 1);
 /* divw  divw.  divwo  divwo.   */
 GEN_INT_ARITH_DIVW(divw, 0x0F, 1, 0);
 GEN_INT_ARITH_DIVW(divwo, 0x1F, 1, 1);
+
+#define GEN_DIVWE(op, signed, compute_ov)                                     \
+static void gen_##op(DisasContext *ctx)                                       \
+{                                                                             \
+    /* Need to use local temps because of the branches */                     \
+    TCGv ra = tcg_temp_local_new();                                           \
+    TCGv rb = tcg_temp_local_new();                                           \
+    int lbl_ov = gen_new_label();                                             \
+    int lbl_rc = gen_new_label();                                             \
+                                                                              \
+    if (signed) {                                                             \
+        TCGv tmp0;                                                            \
+        /* divide by zero ? */                                                \
+        tcg_gen_ext32s_i64(rb, cpu_gpr[rB(ctx->opcode)]);                     \
+        tcg_gen_brcondi_i64(TCG_COND_EQ, rb, 0, lbl_ov);                      \
+        tcg_gen_shli_i64(ra, cpu_gpr[rA(ctx->opcode)], 32);                   \
+        /* check for MIN div -1 */                                            \
+        int l3 = gen_new_label();                                             \
+        tcg_gen_brcondi_i64(TCG_COND_NE, rb, -1l, l3);                        \
+        tcg_gen_brcondi_i64(TCG_COND_EQ, ra, INT64_MIN, lbl_ov);              \
+        gen_set_label(l3);                                                    \
+        tcg_gen_div_i64(cpu_gpr[rD(ctx->opcode)], ra, rb);                    \
+        tmp0 = tcg_temp_local_new();                                          \
+        /* does the result fit in 32 bits? */                                 \
+        tcg_gen_ext32s_i64(tmp0, cpu_gpr[rD(ctx->opcode)]);                   \
+        tcg_gen_brcond_i64(TCG_COND_NE, cpu_gpr[rD(ctx->opcode)], tmp0,       \
+                           lbl_ov);                                           \
+        tcg_temp_free(tmp0);                                                  \
+    } else { /* unsigned */                                                   \
+        /* divide by zero ? */                                                \
+        tcg_gen_ext32u_i64(rb, cpu_gpr[rB(ctx->opcode)]);                     \
+        tcg_gen_brcondi_i64(TCG_COND_EQ, rb, 0, lbl_ov);                      \
+        /* is ra[32:63] >= rb[32:63] ? */                                     \
+        tcg_gen_ext32u_i64(ra, cpu_gpr[rA(ctx->opcode)]);                     \
+        tcg_gen_brcond_i64(TCG_COND_GEU, ra, rb, lbl_ov);                     \
+        tcg_gen_shli_i64(ra, cpu_gpr[rA(ctx->opcode)], 32);                   \
+        tcg_gen_divu_i64(cpu_gpr[rD(ctx->opcode)], ra, rb);                   \
+    }                                                                         \
+                                                                              \
+    if (compute_ov) {                                                         \
+        tcg_gen_movi_tl(cpu_ov, 0);                                           \
+    }                                                                         \
+    tcg_gen_br(lbl_rc);                                                       \
+                                                                              \
+    gen_set_label(lbl_ov); /* overflow handling */                            \
+    tcg_gen_movi_i64(cpu_gpr[rD(ctx->opcode)], 0);                            \
+                                                                              \
+    if (compute_ov) {                                                         \
+        tcg_gen_movi_tl(cpu_ov, 1);                                           \
+        tcg_gen_movi_tl(cpu_so, 1);                                           \
+    }                                                                         \
+                                                                              \
+    gen_set_label(lbl_rc);                                                    \
+    if (unlikely(Rc(ctx->opcode) != 0)) {                                     \
+        gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);                           \
+    }                                                                         \
+                                                                              \
+    tcg_temp_free(ra);                                                        \
+    tcg_temp_free(rb);                                                        \
+}
+
+GEN_DIVWE(divweu, 0, 0);
+GEN_DIVWE(divweuo, 0, 1);
+GEN_DIVWE(divwe, 1, 0);
+GEN_DIVWE(divweo, 1, 1);
+
 #if defined(TARGET_PPC64)
 static inline void gen_op_arith_divd(DisasContext *ctx, TCGv ret, TCGv arg1,
                                      TCGv arg2, int sign, int compute_ov)
@@ -9603,6 +9669,10 @@ GEN_INT_ARITH_DIVW(divwu, 0x0E, 0, 0),
 GEN_INT_ARITH_DIVW(divwuo, 0x1E, 0, 1),
 GEN_INT_ARITH_DIVW(divw, 0x0F, 1, 0),
 GEN_INT_ARITH_DIVW(divwo, 0x1F, 1, 1),
+GEN_HANDLER_E(divwe, 0x1F, 0x0B, 0x0D, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(divweo, 0x1F, 0x0B, 0x1D, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(divweu, 0x1F, 0x0B, 0x0C, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(divweuo, 0x1F, 0x0B, 0x1C, 0x00000000, PPC_NONE, PPC2_ISA206),
 
 #if defined(TARGET_PPC64)
 #undef GEN_INT_ARITH_DIVD
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 06/14] target-ppc: Add ISA2.06 lbarx, lharx Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (4 preceding siblings ...)
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 05/14] target-ppc: Add ISA 2.06 divwe[u][o] Instructions Tom Musta
@ 2013-12-18 20:48 ` Tom Musta
  2013-12-24 15:28   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 07/14] target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions Tom Musta
                   ` (7 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:48 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the byte and halfword variations of the Load and
Reserve instructions.   Since there is much commonality among
all forms of Load and Reserve, a common macro is provided and the
existing implementations of lwarx and ldarx are re-implemented using
this macro.

V2: Fixed bug in aligment check for lharx (caught by Richard).

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/translate.c |   50 +++++++++++++++++++++++------------------------
 1 files changed, 24 insertions(+), 26 deletions(-)

diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 3344fa9..c3d0ebe 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -3218,21 +3218,29 @@ static void gen_isync(DisasContext *ctx)
     gen_stop_exception(ctx);
 }
 
-/* lwarx */
-static void gen_lwarx(DisasContext *ctx)
-{
-    TCGv t0;
-    TCGv gpr = cpu_gpr[rD(ctx->opcode)];
-    gen_set_access_type(ctx, ACCESS_RES);
-    t0 = tcg_temp_local_new();
-    gen_addr_reg_index(ctx, t0);
-    gen_check_align(ctx, t0, 0x03);
-    gen_qemu_ld32u(ctx, gpr, t0);
-    tcg_gen_mov_tl(cpu_reserve, t0);
-    tcg_gen_st_tl(gpr, cpu_env, offsetof(CPUPPCState, reserve_val));
-    tcg_temp_free(t0);
+#define LARX(name, len, loadop)                                      \
+static void gen_##name(DisasContext *ctx)                            \
+{                                                                    \
+    TCGv t0;                                                         \
+    TCGv gpr = cpu_gpr[rD(ctx->opcode)];                             \
+    gen_set_access_type(ctx, ACCESS_RES);                            \
+    t0 = tcg_temp_local_new();                                       \
+    gen_addr_reg_index(ctx, t0);                                     \
+    if ((len) > 1) {                                                 \
+        gen_check_align(ctx, t0, (len)-1);                           \
+    }                                                                \
+    gen_qemu_##loadop(ctx, gpr, t0);                                 \
+    tcg_gen_mov_tl(cpu_reserve, t0);                                 \
+    tcg_gen_st_tl(gpr, cpu_env, offsetof(CPUPPCState, reserve_val)); \
+    tcg_temp_free(t0);                                               \
 }
 
+/* lwarx */
+LARX(lbarx, 1, ld8u);
+LARX(lharx, 2, ld16u);
+LARX(lwarx, 4, ld32u);
+
+
 #if defined(CONFIG_USER_ONLY)
 static void gen_conditional_store (DisasContext *ctx, TCGv EA,
                                    int reg, int size)
@@ -3279,19 +3287,7 @@ static void gen_stwcx_(DisasContext *ctx)
 
 #if defined(TARGET_PPC64)
 /* ldarx */
-static void gen_ldarx(DisasContext *ctx)
-{
-    TCGv t0;
-    TCGv gpr = cpu_gpr[rD(ctx->opcode)];
-    gen_set_access_type(ctx, ACCESS_RES);
-    t0 = tcg_temp_local_new();
-    gen_addr_reg_index(ctx, t0);
-    gen_check_align(ctx, t0, 0x07);
-    gen_qemu_ld64(ctx, gpr, t0);
-    tcg_gen_mov_tl(cpu_reserve, t0);
-    tcg_gen_st_tl(gpr, cpu_env, offsetof(CPUPPCState, reserve_val));
-    tcg_temp_free(t0);
-}
+LARX(ldarx, 8, ld64);
 
 /* stdcx. */
 static void gen_stdcx_(DisasContext *ctx)
@@ -9461,6 +9457,8 @@ GEN_HANDLER(stswi, 0x1F, 0x15, 0x16, 0x00000001, PPC_STRING),
 GEN_HANDLER(stswx, 0x1F, 0x15, 0x14, 0x00000001, PPC_STRING),
 GEN_HANDLER(eieio, 0x1F, 0x16, 0x1A, 0x03FFF801, PPC_MEM_EIEIO),
 GEN_HANDLER(isync, 0x13, 0x16, 0x04, 0x03FFF801, PPC_MEM),
+GEN_HANDLER_E(lbarx, 0x1F, 0x14, 0x01, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(lharx, 0x1F, 0x14, 0x03, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_HANDLER(lwarx, 0x1F, 0x14, 0x00, 0x00000000, PPC_RES),
 GEN_HANDLER2(stwcx_, "stwcx.", 0x1F, 0x16, 0x04, 0x00000000, PPC_RES),
 #if defined(TARGET_PPC64)
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 07/14] target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (5 preceding siblings ...)
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 06/14] target-ppc: Add ISA2.06 lbarx, lharx Instructions Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 15:31   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 08/14] target-ppc: Add ISA2.06 Float to Integer Instructions Tom Musta
                   ` (6 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the byte and halfword variants of the Store Conditional
instructions.   A common macro is introduced and the existing implementations
of stwcx. and stdcx. are re-implemented using this macro.

V2: Re-implemented gen_conditional_store() and STCX macro per comments
from Richard.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/translate.c |   88 ++++++++++++++++++++++-------------------------
 1 files changed, 41 insertions(+), 47 deletions(-)

diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index c3d0ebe..27eef84 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -3242,8 +3242,8 @@ LARX(lwarx, 4, ld32u);
 
 
 #if defined(CONFIG_USER_ONLY)
-static void gen_conditional_store (DisasContext *ctx, TCGv EA,
-                                   int reg, int size)
+static void gen_conditional_store(DisasContext *ctx, TCGv EA,
+                                  int reg, int size)
 {
     TCGv t0 = tcg_temp_new();
     uint32_t save_exception = ctx->exception;
@@ -3257,62 +3257,54 @@ static void gen_conditional_store (DisasContext *ctx, TCGv EA,
     gen_exception(ctx, POWERPC_EXCP_STCX);
     ctx->exception = save_exception;
 }
-#endif
-
-/* stwcx. */
-static void gen_stwcx_(DisasContext *ctx)
-{
-    TCGv t0;
-    gen_set_access_type(ctx, ACCESS_RES);
-    t0 = tcg_temp_local_new();
-    gen_addr_reg_index(ctx, t0);
-    gen_check_align(ctx, t0, 0x03);
-#if defined(CONFIG_USER_ONLY)
-    gen_conditional_store(ctx, t0, rS(ctx->opcode), 4);
 #else
-    {
-        int l1;
+static void gen_conditional_store(DisasContext *ctx, TCGv EA,
+                                  int reg, int size)
+{
+    int l1;
 
-        tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
-        l1 = gen_new_label();
-        tcg_gen_brcond_tl(TCG_COND_NE, t0, cpu_reserve, l1);
-        tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
-        gen_qemu_st32(ctx, cpu_gpr[rS(ctx->opcode)], t0);
-        gen_set_label(l1);
-        tcg_gen_movi_tl(cpu_reserve, -1);
+    tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
+    l1 = gen_new_label();
+    tcg_gen_brcond_tl(TCG_COND_NE, EA, cpu_reserve, l1);
+    tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
+    if (size == 8) {
+        gen_qemu_st64(ctx, cpu_gpr[reg], EA);
+    } else if (size == 4) {
+        gen_qemu_st32(ctx, cpu_gpr[reg], EA);
+    } else if (size == 2) {
+        gen_qemu_st16(ctx, cpu_gpr[reg], EA);
+    } else {
+        gen_qemu_st8(ctx, cpu_gpr[reg], EA);
     }
+    gen_set_label(l1);
+    tcg_gen_movi_tl(cpu_reserve, -1);
+}
 #endif
-    tcg_temp_free(t0);
+
+#define STCX(name, len)                                   \
+static void gen_##name(DisasContext *ctx)                 \
+{                                                         \
+    TCGv t0;                                              \
+    gen_set_access_type(ctx, ACCESS_RES);                 \
+    t0 = tcg_temp_local_new();                            \
+    gen_addr_reg_index(ctx, t0);                          \
+    if (len > 1) {                                        \
+        gen_check_align(ctx, t0, (len)-1);                \
+    }                                                     \
+    gen_conditional_store(ctx, t0, rS(ctx->opcode), len); \
+    tcg_temp_free(t0);                                    \
 }
 
+STCX(stbcx_, 1);
+STCX(sthcx_, 2);
+STCX(stwcx_, 4);
+
 #if defined(TARGET_PPC64)
 /* ldarx */
 LARX(ldarx, 8, ld64);
 
 /* stdcx. */
-static void gen_stdcx_(DisasContext *ctx)
-{
-    TCGv t0;
-    gen_set_access_type(ctx, ACCESS_RES);
-    t0 = tcg_temp_local_new();
-    gen_addr_reg_index(ctx, t0);
-    gen_check_align(ctx, t0, 0x07);
-#if defined(CONFIG_USER_ONLY)
-    gen_conditional_store(ctx, t0, rS(ctx->opcode), 8);
-#else
-    {
-        int l1;
-        tcg_gen_trunc_tl_i32(cpu_crf[0], cpu_so);
-        l1 = gen_new_label();
-        tcg_gen_brcond_tl(TCG_COND_NE, t0, cpu_reserve, l1);
-        tcg_gen_ori_i32(cpu_crf[0], cpu_crf[0], 1 << CRF_EQ);
-        gen_qemu_st64(ctx, cpu_gpr[rS(ctx->opcode)], t0);
-        gen_set_label(l1);
-        tcg_gen_movi_tl(cpu_reserve, -1);
-    }
-#endif
-    tcg_temp_free(t0);
-}
+STCX(stdcx_, 8);
 #endif /* defined(TARGET_PPC64) */
 
 /* sync */
@@ -9460,6 +9452,8 @@ GEN_HANDLER(isync, 0x13, 0x16, 0x04, 0x03FFF801, PPC_MEM),
 GEN_HANDLER_E(lbarx, 0x1F, 0x14, 0x01, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_HANDLER_E(lharx, 0x1F, 0x14, 0x03, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_HANDLER(lwarx, 0x1F, 0x14, 0x00, 0x00000000, PPC_RES),
+GEN_HANDLER_E(stbcx_, 0x1F, 0x16, 0x15, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(sthcx_, 0x1F, 0x16, 0x16, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_HANDLER2(stwcx_, "stwcx.", 0x1F, 0x16, 0x04, 0x00000000, PPC_RES),
 #if defined(TARGET_PPC64)
 GEN_HANDLER(ldarx, 0x1F, 0x14, 0x02, 0x00000000, PPC_64B),
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 08/14] target-ppc: Add ISA2.06 Float to Integer Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (6 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 07/14] target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 15:36   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 09/14] target-ppc: Add ISA 2.06 fcfid[u][s] Instructions Tom Musta
                   ` (5 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the four floating point to integer conversion instructions
introduced by Power ISA V2.06:

  - Floating Convert to Integer Word Unsigned (fctiwu)
  - Floating Convert to Integer Word Unsigned with Round Toward
    Zero (fctiwuz)
  - Floating Convert to Integer Doubleword Unsigned (fctidu)
  - Floating Convert to Integer Doubleword Unsigned with Round
    Toward Zero (fctiduz)

A common macro is developed to eliminate repetitive code.  Existing instructions
are also re-implemented to use this macro (fctiw, fctiwz, fctid, fctidz), thus
eliminating copy/paste code.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/fpu_helper.c |  122 +++++++++++++----------------------------------
 target-ppc/helper.h     |    4 ++
 target-ppc/translate.c  |   12 +++++
 3 files changed, 50 insertions(+), 88 deletions(-)

diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c
index 5d35d1c..17e99c3 100644
--- a/target-ppc/fpu_helper.c
+++ b/target-ppc/fpu_helper.c
@@ -600,55 +600,41 @@ uint64_t helper_fdiv(CPUPPCState *env, uint64_t arg1, uint64_t arg2)
     return farg1.ll;
 }
 
-/* fctiw - fctiw. */
-uint64_t helper_fctiw(CPUPPCState *env, uint64_t arg)
-{
-    CPU_DoubleU farg;
-
-    farg.ll = arg;
-
-    if (unlikely(float64_is_signaling_nan(farg.d))) {
-        /* sNaN conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN |
-                                        POWERPC_EXCP_FP_VXCVI, 1);
-    } else if (unlikely(float64_is_quiet_nan(farg.d) ||
-                        float64_is_infinity(farg.d))) {
-        /* qNan / infinity conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);
-    } else {
-        farg.ll = float64_to_int32(farg.d, &env->fp_status);
-        /* XXX: higher bits are not supposed to be significant.
-         *     to make tests easier, return the same as a real PowerPC 750
-         */
-        farg.ll |= 0xFFF80000ULL << 32;
-    }
-    return farg.ll;
-}
-
-/* fctiwz - fctiwz. */
-uint64_t helper_fctiwz(CPUPPCState *env, uint64_t arg)
-{
-    CPU_DoubleU farg;
 
-    farg.ll = arg;
+#define FPU_FCTI(op, cvt, nanval)                                      \
+uint64_t helper_##op(CPUPPCState *env, uint64_t arg)                   \
+{                                                                      \
+    CPU_DoubleU farg;                                                  \
+                                                                       \
+    farg.ll = arg;                                                     \
+    farg.ll = float64_to_##cvt(farg.d, &env->fp_status);               \
+                                                                       \
+    if (unlikely(env->fp_status.float_exception_flags)) {              \
+        if (float64_is_any_nan(arg)) {                                 \
+            fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);      \
+            if (float64_is_signaling_nan(arg)) {                       \
+                fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN, 1); \
+            }                                                          \
+            farg.ll = nanval;                                          \
+        } else if (env->fp_status.float_exception_flags &              \
+                   float_flag_invalid) {                               \
+            fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);      \
+        }                                                              \
+        helper_float_check_status(env);                                \
+    }                                                                  \
+    return farg.ll;                                                    \
+ }
 
-    if (unlikely(float64_is_signaling_nan(farg.d))) {
-        /* sNaN conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN |
-                                        POWERPC_EXCP_FP_VXCVI, 1);
-    } else if (unlikely(float64_is_quiet_nan(farg.d) ||
-                        float64_is_infinity(farg.d))) {
-        /* qNan / infinity conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);
-    } else {
-        farg.ll = float64_to_int32_round_to_zero(farg.d, &env->fp_status);
-        /* XXX: higher bits are not supposed to be significant.
-         *     to make tests easier, return the same as a real PowerPC 750
-         */
-        farg.ll |= 0xFFF80000ULL << 32;
-    }
-    return farg.ll;
-}
+FPU_FCTI(fctiw, int32, 0x80000000)
+FPU_FCTI(fctiwz, int32_round_to_zero, 0x80000000)
+FPU_FCTI(fctiwu, uint32, 0x00000000)
+FPU_FCTI(fctiwuz, uint32_round_to_zero, 0x00000000)
+#if defined(TARGET_PPC64)
+FPU_FCTI(fctid, int64, 0x8000000000000000)
+FPU_FCTI(fctidz, int64_round_to_zero, 0x8000000000000000)
+FPU_FCTI(fctidu, uint64, 0x0000000000000000)
+FPU_FCTI(fctiduz, uint64_round_to_zero, 0x0000000000000000)
+#endif
 
 #if defined(TARGET_PPC64)
 /* fcfid - fcfid. */
@@ -660,47 +646,7 @@ uint64_t helper_fcfid(CPUPPCState *env, uint64_t arg)
     return farg.ll;
 }
 
-/* fctid - fctid. */
-uint64_t helper_fctid(CPUPPCState *env, uint64_t arg)
-{
-    CPU_DoubleU farg;
 
-    farg.ll = arg;
-
-    if (unlikely(float64_is_signaling_nan(farg.d))) {
-        /* sNaN conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN |
-                                        POWERPC_EXCP_FP_VXCVI, 1);
-    } else if (unlikely(float64_is_quiet_nan(farg.d) ||
-                        float64_is_infinity(farg.d))) {
-        /* qNan / infinity conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);
-    } else {
-        farg.ll = float64_to_int64(farg.d, &env->fp_status);
-    }
-    return farg.ll;
-}
-
-/* fctidz - fctidz. */
-uint64_t helper_fctidz(CPUPPCState *env, uint64_t arg)
-{
-    CPU_DoubleU farg;
-
-    farg.ll = arg;
-
-    if (unlikely(float64_is_signaling_nan(farg.d))) {
-        /* sNaN conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN |
-                                        POWERPC_EXCP_FP_VXCVI, 1);
-    } else if (unlikely(float64_is_quiet_nan(farg.d) ||
-                        float64_is_infinity(farg.d))) {
-        /* qNan / infinity conversion */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);
-    } else {
-        farg.ll = float64_to_int64_round_to_zero(farg.d, &env->fp_status);
-    }
-    return farg.ll;
-}
 
 #endif
 
diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 4359009..4518da0 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -64,11 +64,15 @@ DEF_HELPER_4(fcmpo, void, env, i64, i64, i32)
 DEF_HELPER_4(fcmpu, void, env, i64, i64, i32)
 
 DEF_HELPER_2(fctiw, i64, env, i64)
+DEF_HELPER_2(fctiwu, i64, env, i64)
 DEF_HELPER_2(fctiwz, i64, env, i64)
+DEF_HELPER_2(fctiwuz, i64, env, i64)
 #if defined(TARGET_PPC64)
 DEF_HELPER_2(fcfid, i64, env, i64)
 DEF_HELPER_2(fctid, i64, env, i64)
+DEF_HELPER_2(fctidu, i64, env, i64)
 DEF_HELPER_2(fctidz, i64, env, i64)
+DEF_HELPER_2(fctiduz, i64, env, i64)
 #endif
 DEF_HELPER_2(frsp, i64, env, i64)
 DEF_HELPER_2(frin, i64, env, i64)
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 27eef84..5ac00c6 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -2263,8 +2263,12 @@ GEN_FLOAT_ACB(nmsub, 0x1E, 1, PPC_FLOAT);
 /***                     Floating-Point round & convert                    ***/
 /* fctiw */
 GEN_FLOAT_B(ctiw, 0x0E, 0x00, 0, PPC_FLOAT);
+/* fctiwu */
+GEN_FLOAT_B(ctiwu, 0x0E, 0x04, 0, PPC2_ISA206);
 /* fctiwz */
 GEN_FLOAT_B(ctiwz, 0x0F, 0x00, 0, PPC_FLOAT);
+/* fctiwuz */
+GEN_FLOAT_B(ctiwuz, 0x0F, 0x04, 0, PPC2_ISA206);
 /* frsp */
 GEN_FLOAT_B(rsp, 0x0C, 0x00, 1, PPC_FLOAT);
 #if defined(TARGET_PPC64)
@@ -2272,8 +2276,12 @@ GEN_FLOAT_B(rsp, 0x0C, 0x00, 1, PPC_FLOAT);
 GEN_FLOAT_B(cfid, 0x0E, 0x1A, 1, PPC_64B);
 /* fctid */
 GEN_FLOAT_B(ctid, 0x0E, 0x19, 0, PPC_64B);
+/* fctidu */
+GEN_FLOAT_B(ctidu, 0x0E, 0x1D, 0, PPC2_ISA206);
 /* fctidz */
 GEN_FLOAT_B(ctidz, 0x0F, 0x19, 0, PPC_64B);
+/* fctidu */
+GEN_FLOAT_B(ctiduz, 0x0F, 0x1D, 0, PPC2_ISA206);
 #endif
 
 /* frin */
@@ -9788,12 +9796,16 @@ GEN_FLOAT_ACB(msub, 0x1C, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(nmadd, 0x1F, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(nmsub, 0x1E, 1, PPC_FLOAT),
 GEN_FLOAT_B(ctiw, 0x0E, 0x00, 0, PPC_FLOAT),
+GEN_HANDLER_E(fctiwu, 0x3F, 0x0E, 0x04, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctiwz, 0x0F, 0x00, 0, PPC_FLOAT),
+GEN_HANDLER_E(fctiwuz, 0x3F, 0x0F, 0x04, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(rsp, 0x0C, 0x00, 1, PPC_FLOAT),
 #if defined(TARGET_PPC64)
 GEN_FLOAT_B(cfid, 0x0E, 0x1A, 1, PPC_64B),
 GEN_FLOAT_B(ctid, 0x0E, 0x19, 0, PPC_64B),
+GEN_HANDLER_E(fctidu, 0x3F, 0x0E, 0x1D, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctidz, 0x0F, 0x19, 0, PPC_64B),
+GEN_HANDLER_E(fctiduz, 0x3F, 0x0F, 0x1D, 0x00000000, PPC_NONE, PPC2_ISA206),
 #endif
 GEN_FLOAT_B(rin, 0x08, 0x0C, 1, PPC_FLOAT_EXT),
 GEN_FLOAT_B(riz, 0x08, 0x0D, 1, PPC_FLOAT_EXT),
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 09/14] target-ppc: Add ISA 2.06 fcfid[u][s] Instructions
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (7 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 08/14] target-ppc: Add ISA2.06 Float to Integer Instructions Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 15:41   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz] Tom Musta
                   ` (4 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the fcfids, fcfidu and fcfidus instructions which
were introduced in Power ISA 2.06.  A common macro is provided to
eliminated redudant code, and the existing fcfid instruction is
re-implemented to use this macro.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/fpu_helper.c |   23 ++++++++++++++++-------
 target-ppc/helper.h     |    3 +++
 target-ppc/translate.c  |    9 +++++++++
 3 files changed, 28 insertions(+), 7 deletions(-)

diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c
index 17e99c3..18b9bcd 100644
--- a/target-ppc/fpu_helper.c
+++ b/target-ppc/fpu_helper.c
@@ -637,16 +637,25 @@ FPU_FCTI(fctiduz, uint64_round_to_zero, 0x0000000000000000)
 #endif
 
 #if defined(TARGET_PPC64)
-/* fcfid - fcfid. */
-uint64_t helper_fcfid(CPUPPCState *env, uint64_t arg)
-{
-    CPU_DoubleU farg;
-
-    farg.d = int64_to_float64(arg, &env->fp_status);
-    return farg.ll;
-}
-
 
+#define FPU_FCFI(op, cvtr, is_single)                 \
+uint64_t helper_##op(CPUPPCState *env, uint64_t arg)  \
+{                                                     \
+    CPU_DoubleU farg;                                 \
+                                                      \
+    farg.d = cvtr(arg, &env->fp_status);              \
+                                                      \
+    if (is_single) {                                  \
+        farg.d = helper_frsp(env, farg.d);            \
+    }                                                 \
+    helper_float_check_status(env);                   \
+    return farg.ll;                                   \
+}
+
+FPU_FCFI(fcfid, int64_to_float64, 0)
+FPU_FCFI(fcfids, int64_to_float64, 1)
+FPU_FCFI(fcfidu, uint64_to_float64, 0)
+FPU_FCFI(fcfidus, uint64_to_float64, 1)
 
 #endif
 
diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 4518da0..19b2f6b 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -69,6 +69,9 @@ DEF_HELPER_2(fctiwz, i64, env, i64)
 DEF_HELPER_2(fctiwuz, i64, env, i64)
 #if defined(TARGET_PPC64)
 DEF_HELPER_2(fcfid, i64, env, i64)
+DEF_HELPER_2(fcfidu, i64, env, i64)
+DEF_HELPER_2(fcfids, i64, env, i64)
+DEF_HELPER_2(fcfidus, i64, env, i64)
 DEF_HELPER_2(fctid, i64, env, i64)
 DEF_HELPER_2(fctidu, i64, env, i64)
 DEF_HELPER_2(fctidz, i64, env, i64)
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 5ac00c6..9f0c682 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -2274,6 +2274,12 @@ GEN_FLOAT_B(rsp, 0x0C, 0x00, 1, PPC_FLOAT);
 #if defined(TARGET_PPC64)
 /* fcfid */
 GEN_FLOAT_B(cfid, 0x0E, 0x1A, 1, PPC_64B);
+/* fcfids */
+GEN_FLOAT_B(cfids, 0x0E, 0x1A, 0, PPC2_ISA206);
+/* fcfidu */
+GEN_FLOAT_B(cfidu, 0x0E, 0x1E, 0, PPC2_ISA206);
+/* fcfidus */
+GEN_FLOAT_B(cfidus, 0x0E, 0x1E, 0, PPC2_ISA206);
 /* fctid */
 GEN_FLOAT_B(ctid, 0x0E, 0x19, 0, PPC_64B);
 /* fctidu */
@@ -9802,6 +9808,9 @@ GEN_HANDLER_E(fctiwuz, 0x3F, 0x0F, 0x04, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(rsp, 0x0C, 0x00, 1, PPC_FLOAT),
 #if defined(TARGET_PPC64)
 GEN_FLOAT_B(cfid, 0x0E, 0x1A, 1, PPC_64B),
+GEN_HANDLER_E(fcfids, 0x3B, 0x0E, 0x1A, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(fcfidu, 0x3F, 0x0E, 0x1E, 0x00000000, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(fcfidus, 0x3B, 0x0E, 0x1E, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctid, 0x0E, 0x19, 0, PPC_64B),
 GEN_HANDLER_E(fctidu, 0x3F, 0x0E, 0x1D, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctidz, 0x0F, 0x19, 0, PPC_64B),
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz]
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (8 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 09/14] target-ppc: Add ISA 2.06 fcfid[u][s] Instructions Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 16:02   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 11/14] target-ppc: Add ISA 2.06 ftdiv Instruction Tom Musta
                   ` (3 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

The fri* series of instructions was introduced prior to ISA 2.06 and
is supported on Power7 and Power8 hardware.  However, the instruction
is still considered illegal in the P7 and P8 QEMU emulation models.
This patch enables these instructions for the P7 and P8 machines.

Also, the existing helper is modified to correctly handle some of
the boundary cases (NaNs and the inexact flag).

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/fpu_helper.c     |   12 ++++++------
 target-ppc/translate_init.c |    2 ++
 2 files changed, 8 insertions(+), 6 deletions(-)

diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c
index 18b9bcd..981f002 100644
--- a/target-ppc/fpu_helper.c
+++ b/target-ppc/fpu_helper.c
@@ -668,18 +668,18 @@ static inline uint64_t do_fri(CPUPPCState *env, uint64_t arg,
 
     if (unlikely(float64_is_signaling_nan(farg.d))) {
         /* sNaN round */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN |
-                                        POWERPC_EXCP_FP_VXCVI, 1);
-    } else if (unlikely(float64_is_quiet_nan(farg.d) ||
-                        float64_is_infinity(farg.d))) {
-        /* qNan / infinity round */
-        farg.ll = fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXCVI, 1);
+        fload_invalid_op_excp(env, POWERPC_EXCP_FP_VXSNAN, 1);
+        farg.ll = float64_default_nan | 0x0008000000000000ul;
     } else {
         set_float_rounding_mode(rounding_mode, &env->fp_status);
         farg.ll = float64_round_to_int(farg.d, &env->fp_status);
         /* Restore rounding mode from FPSCR */
         fpscr_set_rounding_mode(env);
+
+        /* fri* does not set FPSCR[XX] */
+        env->fp_status.float_exception_flags &= ~float_flag_inexact;
     }
+    helper_float_check_status(env);
     return farg.ll;
 }
 
diff --git a/target-ppc/translate_init.c b/target-ppc/translate_init.c
index 491e56c..7bb9bbc 100644
--- a/target-ppc/translate_init.c
+++ b/target-ppc/translate_init.c
@@ -7228,6 +7228,7 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
                        PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
                        PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
                        PPC_FLOAT_STFIWX |
+                       PPC_FLOAT_EXT |
                        PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
                        PPC_MEM_SYNC | PPC_MEM_EIEIO |
                        PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
@@ -7265,6 +7266,7 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
                        PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
                        PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
                        PPC_FLOAT_STFIWX |
+                       PPC_FLOAT_EXT |
                        PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
                        PPC_MEM_SYNC | PPC_MEM_EIEIO |
                        PPC_MEM_TLBIE | PPC_MEM_TLBSYNC |
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 11/14] target-ppc: Add ISA 2.06 ftdiv Instruction
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (9 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz] Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 16:06   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 12/14] target-ppc: Add ISA 2.06 ftsqrt Tom Musta
                   ` (2 subsequent siblings)
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the Floating Point Test for Divide instruction which
was introduced in Power ISA 2.06.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/fpu_helper.c |   56 ++++++++++++++++++++++++++++++++++++++--------
 target-ppc/helper.h     |    2 +
 target-ppc/translate.c  |   17 ++++++++++++++
 3 files changed, 65 insertions(+), 10 deletions(-)

diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c
index 981f002..82ff0db 100644
--- a/target-ppc/fpu_helper.c
+++ b/target-ppc/fpu_helper.c
@@ -50,6 +50,16 @@ static inline int isden(float64 d)
     return ((u.ll >> 52) & 0x7FF) == 0;
 }
 
+static inline int ppc_float32_get_unbiased_exp(float32 f)
+{
+    return ((f >> 23) & 0xFF) - 127;
+}
+
+static inline int ppc_float64_get_unbiased_exp(float64 f)
+{
+    return ((f >> 52) & 0x7FF) - 1023;
+}
+
 uint32_t helper_compute_fprf(CPUPPCState *env, uint64_t arg, uint32_t set_fprf)
 {
     CPU_DoubleU farg;
@@ -988,6 +998,42 @@ uint64_t helper_fsel(CPUPPCState *env, uint64_t arg1, uint64_t arg2,
     }
 }
 
+void helper_ftdiv(CPUPPCState *env, uint32_t bf, uint64_t fra, uint64_t frb)
+{
+    int fe_flag = 0;
+    int fg_flag = 0;
+
+    if (unlikely(float64_is_infinity(fra) ||
+                 float64_is_infinity(frb) ||
+                 float64_is_zero(frb))) {
+        fe_flag = 1;
+        fg_flag = 1;
+    } else {
+        int e_a = ppc_float64_get_unbiased_exp(fra);
+        int e_b = ppc_float64_get_unbiased_exp(frb);
+
+        if (unlikely(float64_is_any_nan(fra) ||
+                     float64_is_any_nan(frb))) {
+            fe_flag = 1;
+        } else if ((e_b <= -1022) || (e_b >= 1021)) {
+            fe_flag = 1;
+        } else if (!float64_is_zero(fra) &&
+                   (((e_a - e_b) >= 1023) ||
+                    ((e_a - e_b) <= -1021) ||
+                    (e_a <= -970))) {
+            fe_flag = 1;
+        }
+
+        if (unlikely(float64_is_zero_or_denormal(frb))) {
+            /* XB is not zero because of the above check and */
+            /* so must be denormalized.                      */
+            fg_flag = 1;
+        }
+    }
+
+    env->crf[bf] = 0x8 | (fg_flag ? 4 : 0) | (fe_flag ? 2 : 0);
+}
+
 void helper_fcmpu(CPUPPCState *env, uint64_t arg1, uint64_t arg2,
                   uint32_t crfD)
 {
@@ -2016,16 +2062,6 @@ VSX_RSQRTE(xsrsqrtesp, 1, float64, f64, 1, 1)
 VSX_RSQRTE(xvrsqrtedp, 2, float64, f64, 0, 0)
 VSX_RSQRTE(xvrsqrtesp, 4, float32, f32, 0, 0)
 
-static inline int ppc_float32_get_unbiased_exp(float32 f)
-{
-    return ((f >> 23) & 0xFF) - 127;
-}
-
-static inline int ppc_float64_get_unbiased_exp(float64 f)
-{
-    return ((f >> 52) & 0x7FF) - 1023;
-}
-
 /* VSX_TDIV - VSX floating point test for divide
  *   op    - instruction mnemonic
  *   nels  - number of elements (1, 2 or 4)
diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 19b2f6b..5f5d3f6 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -97,6 +97,8 @@ DEF_HELPER_2(fres, i64, env, i64)
 DEF_HELPER_2(frsqrte, i64, env, i64)
 DEF_HELPER_4(fsel, i64, env, i64, i64, i64)
 
+DEF_HELPER_4(ftdiv, void, env, i32, i64, i64)
+
 #define dh_alias_avr ptr
 #define dh_ctype_avr ppc_avr_t *
 #define dh_is_signed_avr dh_is_signed_ptr
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 9f0c682..403e274 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -2299,6 +2299,22 @@ GEN_FLOAT_B(rip, 0x08, 0x0E, 1, PPC_FLOAT_EXT);
 /* frim */
 GEN_FLOAT_B(rim, 0x08, 0x0F, 1, PPC_FLOAT_EXT);
 
+static void gen_ftdiv(DisasContext *ctx)
+{
+    TCGv_i32 bf;
+    if (unlikely(!ctx->fpu_enabled)) {
+        gen_exception(ctx, POWERPC_EXCP_FPU);
+        return;
+    }
+    /* NIP cannot be restored if the memory exception comes from an helper */
+    gen_update_nip(ctx, ctx->nip - 4);
+    bf = tcg_const_i32(crfD(ctx->opcode));
+    gen_helper_ftdiv(cpu_env, bf, cpu_fpr[rA(ctx->opcode)],
+                     cpu_fpr[rB(ctx->opcode)]);
+}
+
+
+
 /***                         Floating-Point compare                        ***/
 
 /* fcmpo */
@@ -9801,6 +9817,7 @@ GEN_FLOAT_ACB(madd, 0x1D, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(msub, 0x1C, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(nmadd, 0x1F, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(nmsub, 0x1E, 1, PPC_FLOAT),
+GEN_HANDLER_E(ftdiv, 0x3F, 0x00, 0x04, 1, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctiw, 0x0E, 0x00, 0, PPC_FLOAT),
 GEN_HANDLER_E(fctiwu, 0x3F, 0x0E, 0x04, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctiwz, 0x0F, 0x00, 0, PPC_FLOAT),
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 12/14] target-ppc: Add ISA 2.06 ftsqrt
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (10 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 11/14] target-ppc: Add ISA 2.06 ftdiv Instruction Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 16:07   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 13/14] target-ppc: Enable frsqrtes on Power7 and Power8 Tom Musta
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 14/14] target-ppc: Add ISA2.06 lfiwzx Instruction Tom Musta
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the Floating Point Test for Square Root instruction
which was introduced in Power ISA 2.06.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/fpu_helper.c |   31 +++++++++++++++++++++++++++++++
 target-ppc/helper.h     |    1 +
 target-ppc/translate.c  |   14 ++++++++++++++
 3 files changed, 46 insertions(+), 0 deletions(-)

diff --git a/target-ppc/fpu_helper.c b/target-ppc/fpu_helper.c
index 82ff0db..d5eb4ef 100644
--- a/target-ppc/fpu_helper.c
+++ b/target-ppc/fpu_helper.c
@@ -1034,6 +1034,37 @@ void helper_ftdiv(CPUPPCState *env, uint32_t bf, uint64_t fra, uint64_t frb)
     env->crf[bf] = 0x8 | (fg_flag ? 4 : 0) | (fe_flag ? 2 : 0);
 }
 
+void helper_ftsqrt(CPUPPCState *env, uint32_t bf, uint64_t frb)
+{
+    int fe_flag = 0;
+    int fg_flag = 0;
+
+    if (unlikely(float64_is_infinity(frb) || float64_is_zero(frb))) {
+        fe_flag = 1;
+        fg_flag = 1;
+    } else {
+        int e_b = ppc_float64_get_unbiased_exp(frb);
+
+        if (unlikely(float64_is_any_nan(frb))) {
+            fe_flag = 1;
+        } else if (unlikely(float64_is_zero(frb))) {
+            fe_flag = 1;
+        } else if (unlikely(float64_is_neg(frb))) {
+            fe_flag = 1;
+        } else if (!float64_is_zero(frb) && (e_b <= (-1022+52))) {
+            fe_flag = 1;
+        }
+
+        if (unlikely(float64_is_zero_or_denormal(frb))) {
+            /* XB is not zero because of the above check and */
+            /* therefore must be denormalized.               */
+            fg_flag = 1;
+        }
+    }
+
+    env->crf[bf] = 0x8 | (fg_flag ? 4 : 0) | (fe_flag ? 2 : 0);
+}
+
 void helper_fcmpu(CPUPPCState *env, uint64_t arg1, uint64_t arg2,
                   uint32_t crfD)
 {
diff --git a/target-ppc/helper.h b/target-ppc/helper.h
index 5f5d3f6..ccf5711 100644
--- a/target-ppc/helper.h
+++ b/target-ppc/helper.h
@@ -98,6 +98,7 @@ DEF_HELPER_2(frsqrte, i64, env, i64)
 DEF_HELPER_4(fsel, i64, env, i64, i64, i64)
 
 DEF_HELPER_4(ftdiv, void, env, i32, i64, i64)
+DEF_HELPER_3(ftsqrt, void, env, i32, i64)
 
 #define dh_alias_avr ptr
 #define dh_ctype_avr ppc_avr_t *
diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 403e274..0833606 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -2313,6 +2313,19 @@ static void gen_ftdiv(DisasContext *ctx)
                      cpu_fpr[rB(ctx->opcode)]);
 }
 
+static void gen_ftsqrt(DisasContext *ctx)
+{
+    TCGv_i32 bf;
+    if (unlikely(!ctx->fpu_enabled)) {
+        gen_exception(ctx, POWERPC_EXCP_FPU);
+        return;
+    }
+    /* NIP cannot be restored if the memory exception comes from an helper */
+    gen_update_nip(ctx, ctx->nip - 4);
+    bf = tcg_const_i32(crfD(ctx->opcode));
+    gen_helper_ftsqrt(cpu_env, bf, cpu_fpr[rB(ctx->opcode)]);
+}
+
 
 
 /***                         Floating-Point compare                        ***/
@@ -9818,6 +9831,7 @@ GEN_FLOAT_ACB(msub, 0x1C, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(nmadd, 0x1F, 1, PPC_FLOAT),
 GEN_FLOAT_ACB(nmsub, 0x1E, 1, PPC_FLOAT),
 GEN_HANDLER_E(ftdiv, 0x3F, 0x00, 0x04, 1, PPC_NONE, PPC2_ISA206),
+GEN_HANDLER_E(ftsqrt, 0x3F, 0x00, 0x05, 1, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctiw, 0x0E, 0x00, 0, PPC_FLOAT),
 GEN_HANDLER_E(fctiwu, 0x3F, 0x0E, 0x04, 0x00000000, PPC_NONE, PPC2_ISA206),
 GEN_FLOAT_B(ctiwz, 0x0F, 0x00, 0, PPC_FLOAT),
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 13/14] target-ppc: Enable frsqrtes on Power7 and Power8
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (11 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 12/14] target-ppc: Add ISA 2.06 ftsqrt Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 16:07   ` Richard Henderson
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 14/14] target-ppc: Add ISA2.06 lfiwzx Instruction Tom Musta
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

The frsqrtes instruction was introduced prior to ISA 2.06 and is
support on both the Power7 and Power8 processors.  However, this
instruction is handled as illegal in the current QEMU emulation
machines.  This patch enables the existing implemention of frsqrtes
in the P7 and P8 machines.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/translate_init.c |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/target-ppc/translate_init.c b/target-ppc/translate_init.c
index 7bb9bbc..ec65bf4 100644
--- a/target-ppc/translate_init.c
+++ b/target-ppc/translate_init.c
@@ -7227,6 +7227,7 @@ POWERPC_FAMILY(POWER7)(ObjectClass *oc, void *data)
     pcc->insns_flags = PPC_INSNS_BASE | PPC_ISEL | PPC_STRING | PPC_MFTB |
                        PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
                        PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
+                       PPC_FLOAT_FRSQRTES |
                        PPC_FLOAT_STFIWX |
                        PPC_FLOAT_EXT |
                        PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
@@ -7265,6 +7266,7 @@ POWERPC_FAMILY(POWER8)(ObjectClass *oc, void *data)
     pcc->insns_flags = PPC_INSNS_BASE | PPC_STRING | PPC_MFTB |
                        PPC_FLOAT | PPC_FLOAT_FSEL | PPC_FLOAT_FRES |
                        PPC_FLOAT_FSQRT | PPC_FLOAT_FRSQRTE |
+                       PPC_FLOAT_FRSQRTES |
                        PPC_FLOAT_STFIWX |
                        PPC_FLOAT_EXT |
                        PPC_CACHE | PPC_CACHE_ICBI | PPC_CACHE_DCBZ |
-- 
1.7.1

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

* [Qemu-devel] [V3 PATCH 14/14] target-ppc: Add ISA2.06 lfiwzx Instruction
  2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
                   ` (12 preceding siblings ...)
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 13/14] target-ppc: Enable frsqrtes on Power7 and Power8 Tom Musta
@ 2013-12-18 20:49 ` Tom Musta
  2013-12-24 16:09   ` Richard Henderson
  13 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2013-12-18 20:49 UTC (permalink / raw)
  To: qemu-devel; +Cc: Tom Musta, qemu-ppc

This patch adds the Load Floating Point as Integer Word and
Zero Indexed (lfiwzx) instruction which was introduced in
Power ISA 2.06.

Signed-off-by: Tom Musta <tommusta@gmail.com>
---
 target-ppc/translate.c |   15 +++++++++++++++
 1 files changed, 15 insertions(+), 0 deletions(-)

diff --git a/target-ppc/translate.c b/target-ppc/translate.c
index 0833606..cf1fb1b 100644
--- a/target-ppc/translate.c
+++ b/target-ppc/translate.c
@@ -3524,6 +3524,20 @@ static void gen_lfiwax(DisasContext *ctx)
     tcg_temp_free(t0);
 }
 
+/* lfiwzx */
+static void gen_lfiwzx(DisasContext *ctx)
+{
+    TCGv EA;
+    if (unlikely(!ctx->fpu_enabled)) {
+        gen_exception(ctx, POWERPC_EXCP_FPU);
+        return;
+    }
+    gen_set_access_type(ctx, ACCESS_FLOAT);
+    EA = tcg_temp_new();
+    gen_addr_reg_index(ctx, EA);
+    gen_qemu_ld32u(ctx, cpu_fpr[rD(ctx->opcode)], EA);
+    tcg_temp_free(EA);
+}
 /***                         Floating-point store                          ***/
 #define GEN_STF(name, stop, opc, type)                                        \
 static void glue(gen_, name)(DisasContext *ctx)                                       \
@@ -9937,6 +9951,7 @@ GEN_LDXF(name, ldop, 0x17, op | 0x00, type)
 GEN_LDFS(lfd, ld64, 0x12, PPC_FLOAT)
 GEN_LDFS(lfs, ld32fs, 0x10, PPC_FLOAT)
 GEN_HANDLER_E(lfiwax, 0x1f, 0x17, 0x1a, 0x00000001, PPC_NONE, PPC2_ISA205),
+GEN_HANDLER_E(lfiwzx, 0x1f, 0x17, 0x1b, 0x00000001, PPC_NONE, PPC2_ISA206),
 GEN_HANDLER_E(lfdp, 0x39, 0xFF, 0xFF, 0x00200003, PPC_NONE, PPC2_ISA205),
 GEN_HANDLER_E(lfdpx, 0x1F, 0x17, 0x18, 0x00200001, PPC_NONE, PPC2_ISA205),
 
-- 
1.7.1

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

* Re: [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06 Tom Musta
@ 2013-12-24 15:11   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:11 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:48 PM, Tom Musta wrote:
> This patch adds a flag for base instruction additions to Power ISA
> 2.06B.  The flag will be used to identify/select basic Book I and
> Book II instructions that were newly added in that revision of the
> architecture.  The flag will not be used for VSX or Altivec.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/cpu.h            |    4 +++-
>  target-ppc/translate_init.c |    6 ++++--
>  2 files changed, 7 insertions(+), 3 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction Tom Musta
@ 2013-12-24 15:17   ` Richard Henderson
  2013-12-28  0:23     ` Scott Wood
  2013-12-28  0:27   ` [Qemu-devel] " Scott Wood
  1 sibling, 1 reply; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:17 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:48 PM, Tom Musta wrote:
> +DEF_HELPER_3(bpermd, i64, env, i64, i64)

Should be DEF_HELPER_FLAGS_2(bpermd, TCG_CALL_NO_RWG_SE, i64, i64, i64)

> +uint64_t helper_bpermd(CPUPPCState *env, uint64_t rs, uint64_t rb)
> +{
> +    int i;
> +    uint64_t ra = 0;
> +
> +    for (i = 0; i < 8; i++) {
> +        int index = (rs >> (i*8)) & 0xFF;
> +        if (index < 64) {
> +            if (rb & (1ul << (63-index))) {
> +                ra |= 1 << i;
> +            }
> +        }
> +    }
> +    return ra;
> +}
> +

You don't need env as an argument; it's unused.

Why is all of this specific to ppc64?  Can't you run an ISA2.06B machine in
32-bit mode?


r~

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

* Re: [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions Tom Musta
@ 2013-12-24 15:20   ` Richard Henderson
  2013-12-28  0:30   ` [Qemu-devel] [Qemu-ppc] " Scott Wood
  1 sibling, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:20 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:48 PM, Tom Musta wrote:
> This patch adds the Divide Doubleword Extended Unsigned
> instructions.  This instruction requires dividing a 128-bit
> value by a 64 bit value.  Since 128 bit integer division is
> not supported in TCG, a helper is used, providing a
> repeated difference algorithm.
> 
> V2: Moved the 128-bit divide routine into host-utils per Richard
> Henderson's suggestion.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  include/qemu/host-utils.h |   14 ++++++++++++++
>  target-ppc/helper.h       |    1 +
>  target-ppc/int_helper.c   |   27 +++++++++++++++++++++++++++
>  target-ppc/translate.c    |   20 ++++++++++++++++++++
>  util/host-utils.c         |   38 ++++++++++++++++++++++++++++++++++++++
>  5 files changed, 100 insertions(+), 0 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 04/14] target-ppc: Add ISA2.06 divde[o] Instructions
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 04/14] target-ppc: Add ISA2.06 divde[o] Instructions Tom Musta
@ 2013-12-24 15:22   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:22 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:48 PM, Tom Musta wrote:
> +        *plow = result;
> +        *phigh = dividend % divisor;
> +        return (result > INT64_MAX) | (result < INT64_MIN);

Probably better as

  return result != *plow;

Otherwise,

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 05/14] target-ppc: Add ISA 2.06 divwe[u][o] Instructions
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 05/14] target-ppc: Add ISA 2.06 divwe[u][o] Instructions Tom Musta
@ 2013-12-24 15:26   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:26 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:48 PM, Tom Musta wrote:
> +        tcg_gen_div_i64(cpu_gpr[rD(ctx->opcode)], ra, rb);                    \
> +        tmp0 = tcg_temp_local_new();                                          \
> +        /* does the result fit in 32 bits? */                                 \
> +        tcg_gen_ext32s_i64(tmp0, cpu_gpr[rD(ctx->opcode)]);                   \
> +        tcg_gen_brcond_i64(TCG_COND_NE, cpu_gpr[rD(ctx->opcode)], tmp0,       \
> +                           lbl_ov);                                           \
> +        tcg_temp_free(tmp0);                                                  \

tmp0 does not need to be a local temp, as it's not used across basic blocks.

I do wonder if this wouldn't be better as a helper, what with all of the
branches.  TCG essentially won't optimize any of this.


r~

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

* Re: [Qemu-devel] [V3 PATCH 06/14] target-ppc: Add ISA2.06 lbarx, lharx Instructions
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 06/14] target-ppc: Add ISA2.06 lbarx, lharx Instructions Tom Musta
@ 2013-12-24 15:28   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:28 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:48 PM, Tom Musta wrote:
> This patch adds the byte and halfword variations of the Load and
> Reserve instructions.   Since there is much commonality among
> all forms of Load and Reserve, a common macro is provided and the
> existing implementations of lwarx and ldarx are re-implemented using
> this macro.
> 
> V2: Fixed bug in aligment check for lharx (caught by Richard).
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/translate.c |   50 +++++++++++++++++++++++------------------------
>  1 files changed, 24 insertions(+), 26 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 07/14] target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 07/14] target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions Tom Musta
@ 2013-12-24 15:31   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:31 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> This patch adds the byte and halfword variants of the Store Conditional
> instructions.   A common macro is introduced and the existing implementations
> of stwcx. and stdcx. are re-implemented using this macro.
> 
> V2: Re-implemented gen_conditional_store() and STCX macro per comments
> from Richard.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/translate.c |   88 ++++++++++++++++++++++-------------------------
>  1 files changed, 41 insertions(+), 47 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 08/14] target-ppc: Add ISA2.06 Float to Integer Instructions
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 08/14] target-ppc: Add ISA2.06 Float to Integer Instructions Tom Musta
@ 2013-12-24 15:36   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:36 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> This patch adds the four floating point to integer conversion instructions
> introduced by Power ISA V2.06:
> 
>   - Floating Convert to Integer Word Unsigned (fctiwu)
>   - Floating Convert to Integer Word Unsigned with Round Toward
>     Zero (fctiwuz)
>   - Floating Convert to Integer Doubleword Unsigned (fctidu)
>   - Floating Convert to Integer Doubleword Unsigned with Round
>     Toward Zero (fctiduz)
> 
> A common macro is developed to eliminate repetitive code.  Existing instructions
> are also re-implemented to use this macro (fctiw, fctiwz, fctid, fctidz), thus
> eliminating copy/paste code.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/fpu_helper.c |  122 +++++++++++++----------------------------------
>  target-ppc/helper.h     |    4 ++
>  target-ppc/translate.c  |   12 +++++
>  3 files changed, 50 insertions(+), 88 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 09/14] target-ppc: Add ISA 2.06 fcfid[u][s] Instructions
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 09/14] target-ppc: Add ISA 2.06 fcfid[u][s] Instructions Tom Musta
@ 2013-12-24 15:41   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 15:41 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> +#define FPU_FCFI(op, cvtr, is_single)                 \
> +uint64_t helper_##op(CPUPPCState *env, uint64_t arg)  \
> +{                                                     \
> +    CPU_DoubleU farg;                                 \
> +                                                      \
> +    farg.d = cvtr(arg, &env->fp_status);              \
> +                                                      \
> +    if (is_single) {                                  \
> +        farg.d = helper_frsp(env, farg.d);            \
> +    }                                                 \
> +    helper_float_check_status(env);                   \
> +    return farg.ll;                                   \
> +}

This formulation will lead to double-rounding errors for some int64 inputs.
You should convert to single-precision directly, then convert to double.


r~

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

* Re: [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz]
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz] Tom Musta
@ 2013-12-24 16:02   ` Richard Henderson
  2014-01-06 20:06     ` Tom Musta
  0 siblings, 1 reply; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 16:02 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> The fri* series of instructions was introduced prior to ISA 2.06 and
> is supported on Power7 and Power8 hardware.  However, the instruction
> is still considered illegal in the P7 and P8 QEMU emulation models.
> This patch enables these instructions for the P7 and P8 machines.
> 
> Also, the existing helper is modified to correctly handle some of
> the boundary cases (NaNs and the inexact flag).
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/fpu_helper.c     |   12 ++++++------
>  target-ppc/translate_init.c |    2 ++
>  2 files changed, 8 insertions(+), 6 deletions(-)

Probably should be separate patches, but whatever.

> +        farg.ll = float64_default_nan | 0x0008000000000000ul;

That doesn't match what I see here:

  FRT <-  (FRB)
  FRT12 <- 1

i.e.

  farg.ll |= 1ull << (63 - 12);

i.e. mostly preserve the SNAN input.

I'll also note that frin can't properly be implemented with
float_round_nearest_even because it doesn't round to even.


r~

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

* Re: [Qemu-devel] [V3 PATCH 11/14] target-ppc: Add ISA 2.06 ftdiv Instruction
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 11/14] target-ppc: Add ISA 2.06 ftdiv Instruction Tom Musta
@ 2013-12-24 16:06   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 16:06 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> +    env->crf[bf] = 0x8 | (fg_flag ? 4 : 0) | (fe_flag ? 2 : 0);
> +}

You should return that value instead of assigning it.  Then you need neither
the env nor bf arguments, and the whole function can be TCG_CALL_NO_RWG_SE.

> +static void gen_ftdiv(DisasContext *ctx)
> +{
> +    TCGv_i32 bf;
> +    if (unlikely(!ctx->fpu_enabled)) {
> +        gen_exception(ctx, POWERPC_EXCP_FPU);
> +        return;
> +    }
> +    /* NIP cannot be restored if the memory exception comes from an helper */
> +    gen_update_nip(ctx, ctx->nip - 4);
> +    bf = tcg_const_i32(crfD(ctx->opcode));
> +    gen_helper_ftdiv(cpu_env, bf, cpu_fpr[rA(ctx->opcode)],
> +                     cpu_fpr[rB(ctx->opcode)]);
> +}

What memory exception?

Assign the result to cpu_crf[bf] here.



r~

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

* Re: [Qemu-devel] [V3 PATCH 12/14] target-ppc: Add ISA 2.06 ftsqrt
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 12/14] target-ppc: Add ISA 2.06 ftsqrt Tom Musta
@ 2013-12-24 16:07   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 16:07 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> +static void gen_ftsqrt(DisasContext *ctx)
> +{
> +    TCGv_i32 bf;
> +    if (unlikely(!ctx->fpu_enabled)) {
> +        gen_exception(ctx, POWERPC_EXCP_FPU);
> +        return;
> +    }
> +    /* NIP cannot be restored if the memory exception comes from an helper */
> +    gen_update_nip(ctx, ctx->nip - 4);
> +    bf = tcg_const_i32(crfD(ctx->opcode));
> +    gen_helper_ftsqrt(cpu_env, bf, cpu_fpr[rB(ctx->opcode)]);
> +}

Similar comments as for fdivt.


r~

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

* Re: [Qemu-devel] [V3 PATCH 13/14] target-ppc: Enable frsqrtes on Power7 and Power8
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 13/14] target-ppc: Enable frsqrtes on Power7 and Power8 Tom Musta
@ 2013-12-24 16:07   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 16:07 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> The frsqrtes instruction was introduced prior to ISA 2.06 and is
> support on both the Power7 and Power8 processors.  However, this
> instruction is handled as illegal in the current QEMU emulation
> machines.  This patch enables the existing implemention of frsqrtes
> in the P7 and P8 machines.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/translate_init.c |    2 ++
>  1 files changed, 2 insertions(+), 0 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 14/14] target-ppc: Add ISA2.06 lfiwzx Instruction
  2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 14/14] target-ppc: Add ISA2.06 lfiwzx Instruction Tom Musta
@ 2013-12-24 16:09   ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-24 16:09 UTC (permalink / raw)
  To: Tom Musta, qemu-devel; +Cc: qemu-ppc

On 12/18/2013 12:49 PM, Tom Musta wrote:
> This patch adds the Load Floating Point as Integer Word and
> Zero Indexed (lfiwzx) instruction which was introduced in
> Power ISA 2.06.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  target-ppc/translate.c |   15 +++++++++++++++
>  1 files changed, 15 insertions(+), 0 deletions(-)

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


r~

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

* Re: [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-24 15:17   ` Richard Henderson
@ 2013-12-28  0:23     ` Scott Wood
  2013-12-30 14:48       ` Richard Henderson
  0 siblings, 1 reply; 38+ messages in thread
From: Scott Wood @ 2013-12-28  0:23 UTC (permalink / raw)
  To: Richard Henderson; +Cc: Tom Musta, qemu-ppc, qemu-devel

On Tue, 2013-12-24 at 07:17 -0800, Richard Henderson wrote:
> On 12/18/2013 12:48 PM, Tom Musta wrote:
> > +DEF_HELPER_3(bpermd, i64, env, i64, i64)
> 
> Should be DEF_HELPER_FLAGS_2(bpermd, TCG_CALL_NO_RWG_SE, i64, i64, i64)
> 
> > +uint64_t helper_bpermd(CPUPPCState *env, uint64_t rs, uint64_t rb)
> > +{
> > +    int i;
> > +    uint64_t ra = 0;
> > +
> > +    for (i = 0; i < 8; i++) {
> > +        int index = (rs >> (i*8)) & 0xFF;
> > +        if (index < 64) {
> > +            if (rb & (1ul << (63-index))) {
> > +                ra |= 1 << i;
> > +            }
> > +        }
> > +    }
> > +    return ra;
> > +}
> > +
> 
> You don't need env as an argument; it's unused.
> 
> Why is all of this specific to ppc64?  Can't you run an ISA2.06B machine in
> 32-bit mode?

bpermd is a 64-bit instruction.  32-bit implementations do not have it.

-Scott

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

* Re: [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction Tom Musta
  2013-12-24 15:17   ` Richard Henderson
@ 2013-12-28  0:27   ` Scott Wood
  1 sibling, 0 replies; 38+ messages in thread
From: Scott Wood @ 2013-12-28  0:27 UTC (permalink / raw)
  To: Tom Musta; +Cc: qemu-ppc, qemu-devel

On Wed, 2013-12-18 at 14:48 -0600, Tom Musta wrote:
> This patch adds the Bit Permute Doubleword (bpermd) instruction,
> which was introduced in Power ISA 2.06 as part of the base 64-bit
> architecture.

Technically it's "Category: Embedded.Phased-in, Server" rather than
"Category: Base".  e5500 does have it, though, so if IBM's 64-bit booke
chips also have it, it might as well be Base.

> V2: Addressing stylistic comments from Richard Henderson.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> Reviewed-by: Richard Henderson <address@hidden>
> ---
>  target-ppc/helper.h     |    1 +
>  target-ppc/int_helper.c |   20 ++++++++++++++++++++
>  target-ppc/translate.c  |   10 ++++++++++
>  3 files changed, 31 insertions(+), 0 deletions(-)
> 
> diff --git a/target-ppc/helper.h b/target-ppc/helper.h
> index 6250eba..1ec9c65 100644
> --- a/target-ppc/helper.h
> +++ b/target-ppc/helper.h
> @@ -41,6 +41,7 @@ DEF_HELPER_3(sraw, tl, env, tl, tl)
>  #if defined(TARGET_PPC64)
>  DEF_HELPER_FLAGS_1(cntlzd, TCG_CALL_NO_RWG_SE, tl, tl)
>  DEF_HELPER_FLAGS_1(popcntd, TCG_CALL_NO_RWG_SE, tl, tl)
> +DEF_HELPER_3(bpermd, i64, env, i64, i64)
>  DEF_HELPER_3(srad, tl, env, tl, tl)
>  #endif
>  
> diff --git a/target-ppc/int_helper.c b/target-ppc/int_helper.c
> index e50bdd2..abc69a7 100644
> --- a/target-ppc/int_helper.c
> +++ b/target-ppc/int_helper.c
> @@ -53,6 +53,26 @@ target_ulong helper_cntlzd(target_ulong t)
>  }
>  #endif
>  
> +#if defined(TARGET_PPC64)
> +
> +uint64_t helper_bpermd(CPUPPCState *env, uint64_t rs, uint64_t rb)
> +{
> +    int i;
> +    uint64_t ra = 0;
> +
> +    for (i = 0; i < 8; i++) {
> +        int index = (rs >> (i*8)) & 0xFF;
> +        if (index < 64) {
> +            if (rb & (1ul << (63-index))) {

1ull

Don't assume that the host is 64-bit

-Scott

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

* Re: [Qemu-devel] [Qemu-ppc] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions
  2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions Tom Musta
  2013-12-24 15:20   ` Richard Henderson
@ 2013-12-28  0:30   ` Scott Wood
  2014-01-03 19:24     ` Tom Musta
  1 sibling, 1 reply; 38+ messages in thread
From: Scott Wood @ 2013-12-28  0:30 UTC (permalink / raw)
  To: Tom Musta; +Cc: qemu-ppc, qemu-devel

On Wed, 2013-12-18 at 14:48 -0600, Tom Musta wrote:
> This patch adds the Divide Doubleword Extended Unsigned
> instructions.  This instruction requires dividing a 128-bit
> value by a 64 bit value.  Since 128 bit integer division is
> not supported in TCG, a helper is used, providing a
> repeated difference algorithm.
> 
> V2: Moved the 128-bit divide routine into host-utils per Richard
> Henderson's suggestion.
> 
> Signed-off-by: Tom Musta <tommusta@gmail.com>
> ---
>  include/qemu/host-utils.h |   14 ++++++++++++++
>  target-ppc/helper.h       |    1 +
>  target-ppc/int_helper.c   |   27 +++++++++++++++++++++++++++
>  target-ppc/translate.c    |   20 ++++++++++++++++++++
>  util/host-utils.c         |   38 ++++++++++++++++++++++++++++++++++++++
>  5 files changed, 100 insertions(+), 0 deletions(-)
> 
> diff --git a/include/qemu/host-utils.h b/include/qemu/host-utils.h
> index 0f688c1..0ca187d 100644
> --- a/include/qemu/host-utils.h
> +++ b/include/qemu/host-utils.h
> @@ -44,9 +44,23 @@ static inline void muls64(uint64_t *plow, uint64_t *phigh,
>      *plow = r;
>      *phigh = r >> 64;
>  }
> +
> +static inline int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor)
> +{
> +    if (divisor == 0) {
> +        return 1;
> +    } else {
> +        __uint128_t dividend = ((__uint128_t)*phigh << 64) | *plow;
> +        __uint128_t result = dividend / divisor;
> +        *plow = result;
> +        *phigh = dividend % divisor;
> +        return result > UINT64_MAX;
> +    }
> +}
>  #else
>  void muls64(uint64_t *phigh, uint64_t *plow, int64_t a, int64_t b);
>  void mulu64(uint64_t *phigh, uint64_t *plow, uint64_t a, uint64_t b);
> +int divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor);
>  #endif
>  
>  /**
> diff --git a/target-ppc/helper.h b/target-ppc/helper.h
> index 1ec9c65..3eff4df 100644
> --- a/target-ppc/helper.h
> +++ b/target-ppc/helper.h
> @@ -31,6 +31,7 @@ DEF_HELPER_5(lscbx, tl, env, tl, i32, i32, i32)
>  
>  #if defined(TARGET_PPC64)
>  DEF_HELPER_3(mulldo, i64, env, i64, i64)
> +DEF_HELPER_4(divdeu, i64, env, i64, i64, i32)
>  #endif
>  
>  DEF_HELPER_FLAGS_1(cntlzw, TCG_CALL_NO_RWG_SE, tl, tl)
> diff --git a/target-ppc/int_helper.c b/target-ppc/int_helper.c
> index abc69a7..d6dcac9 100644
> --- a/target-ppc/int_helper.c
> +++ b/target-ppc/int_helper.c
> @@ -41,6 +41,33 @@ uint64_t helper_mulldo(CPUPPCState *env, uint64_t arg1, uint64_t arg2)
>  }
>  #endif
>  
> +#if defined(TARGET_PPC64)
> +
> +uint64_t helper_divdeu(CPUPPCState *env, uint64_t ra, uint64_t rb, uint32_t oe)
> +{
> +    uint64_t rt = 0;
> +    int overflow = 0;
> +
> +    overflow = divu128(&rt, &ra, rb);
> +
> +    if (unlikely(overflow)) {
> +        rt = 0; /* Undefined */
> +    }
> +
> +    if (oe) {
> +        if (unlikely(overflow)) {
> +            env->so = env->ov = 1;
> +        } else {
> +            env->ov = 0;
> +        }
> +    }
> +
> +    return rt;
> +}
> +
> +#endif
> +
> +
>  target_ulong helper_cntlzw(target_ulong t)
>  {
>      return clz32(t);
> diff --git a/target-ppc/translate.c b/target-ppc/translate.c
> index 0d39de2..7a51c6d 100644
> --- a/target-ppc/translate.c
> +++ b/target-ppc/translate.c
> @@ -1032,6 +1032,23 @@ GEN_INT_ARITH_DIVD(divduo, 0x1E, 0, 1);
>  /* divw  divw.  divwo  divwo.   */
>  GEN_INT_ARITH_DIVD(divd, 0x0F, 1, 0);
>  GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1);
> +
> +/* divdeu[o][.] */
> +#define GEN_DIVDE(name, hlpr, compute_ov)                                     \
> +static void gen_##name(DisasContext *ctx)                                     \
> +{                                                                             \
> +    TCGv_i32 t0 = tcg_const_i32(compute_ov);                                  \
> +    gen_helper_##hlpr(cpu_gpr[rD(ctx->opcode)], cpu_env,                      \
> +                     cpu_gpr[rA(ctx->opcode)], cpu_gpr[rB(ctx->opcode)], t0); \
> +    tcg_temp_free_i32(t0);                                                    \
> +    if (unlikely(Rc(ctx->opcode) != 0)) {                                     \
> +        gen_set_Rc0(ctx, cpu_gpr[rD(ctx->opcode)]);                           \
> +    }                                                                         \
> +}
> +
> +GEN_DIVDE(divdeu, divdeu, 0);
> +GEN_DIVDE(divdeuo, divdeu, 1);
> +
>  #endif
>  
>  /* mulhw  mulhw. */
> @@ -9594,6 +9611,9 @@ GEN_INT_ARITH_DIVD(divduo, 0x1E, 0, 1),
>  GEN_INT_ARITH_DIVD(divd, 0x0F, 1, 0),
>  GEN_INT_ARITH_DIVD(divdo, 0x1F, 1, 1),
>  
> +GEN_HANDLER_E(divdeu, 0x1F, 0x09, 0x0C, 0x00000000, PPC_NONE, PPC2_ISA206),
> +GEN_HANDLER_E(divdeuo, 0x1F, 0x09, 0x1C, 0x00000000, PPC_NONE, PPC2_ISA206),

These instructions are phased-in on embedded, and unlike bpermd are not
present on e5500/e6500 which are 64-bit ISA 2.06 implementations.
Wasn't the conclusion in a previous thread to use separate flags for
these instruction groups?

-Scott

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

* Re: [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-28  0:23     ` Scott Wood
@ 2013-12-30 14:48       ` Richard Henderson
  2013-12-30 15:43         ` [Qemu-devel] [Qemu-ppc] " Alexander Graf
  0 siblings, 1 reply; 38+ messages in thread
From: Richard Henderson @ 2013-12-30 14:48 UTC (permalink / raw)
  To: Scott Wood; +Cc: Tom Musta, qemu-ppc, qemu-devel

On 12/27/2013 04:23 PM, Scott Wood wrote:
> On Tue, 2013-12-24 at 07:17 -0800, Richard Henderson wrote:
>> On 12/18/2013 12:48 PM, Tom Musta wrote:
>>> +DEF_HELPER_3(bpermd, i64, env, i64, i64)
>>
>> Should be DEF_HELPER_FLAGS_2(bpermd, TCG_CALL_NO_RWG_SE, i64, i64, i64)
>>
>>> +uint64_t helper_bpermd(CPUPPCState *env, uint64_t rs, uint64_t rb)
>>> +{
>>> +    int i;
>>> +    uint64_t ra = 0;
>>> +
>>> +    for (i = 0; i < 8; i++) {
>>> +        int index = (rs >> (i*8)) & 0xFF;
>>> +        if (index < 64) {
>>> +            if (rb & (1ul << (63-index))) {
>>> +                ra |= 1 << i;
>>> +            }
>>> +        }
>>> +    }
>>> +    return ra;
>>> +}
>>> +
>>
>> You don't need env as an argument; it's unused.
>>
>> Why is all of this specific to ppc64?  Can't you run an ISA2.06B machine in
>> 32-bit mode?
> 
> bpermd is a 64-bit instruction.  32-bit implementations do not have it.

What has that got to do with running a 64-bit chip in 32-bit mode?


r~

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

* Re: [Qemu-devel] [Qemu-ppc] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-30 14:48       ` Richard Henderson
@ 2013-12-30 15:43         ` Alexander Graf
  2013-12-30 16:23           ` Richard Henderson
  0 siblings, 1 reply; 38+ messages in thread
From: Alexander Graf @ 2013-12-30 15:43 UTC (permalink / raw)
  To: Richard Henderson
  Cc: Scott Wood, Tom Musta, qemu-ppc@nongnu.org, qemu-devel@nongnu.org



> Am 30.12.2013 um 15:48 schrieb Richard Henderson <rth@twiddle.net>:
> 
>> On 12/27/2013 04:23 PM, Scott Wood wrote:
>>> On Tue, 2013-12-24 at 07:17 -0800, Richard Henderson wrote:
>>>> On 12/18/2013 12:48 PM, Tom Musta wrote:
>>>> +DEF_HELPER_3(bpermd, i64, env, i64, i64)
>>> 
>>> Should be DEF_HELPER_FLAGS_2(bpermd, TCG_CALL_NO_RWG_SE, i64, i64, i64)
>>> 
>>>> +uint64_t helper_bpermd(CPUPPCState *env, uint64_t rs, uint64_t rb)
>>>> +{
>>>> +    int i;
>>>> +    uint64_t ra = 0;
>>>> +
>>>> +    for (i = 0; i < 8; i++) {
>>>> +        int index = (rs >> (i*8)) & 0xFF;
>>>> +        if (index < 64) {
>>>> +            if (rb & (1ul << (63-index))) {
>>>> +                ra |= 1 << i;
>>>> +            }
>>>> +        }
>>>> +    }
>>>> +    return ra;
>>>> +}
>>>> +
>>> 
>>> You don't need env as an argument; it's unused.
>>> 
>>> Why is all of this specific to ppc64?  Can't you run an ISA2.06B machine in
>>> 32-bit mode?
>> 
>> bpermd is a 64-bit instruction.  32-bit implementations do not have it.
> 
> What has that got to do with running a 64-bit chip in 32-bit mode?

Yes you can, but we only expose 64bit capable cpus with TARGET_PPC64 defined. You couldn't select them with the 32bit target.

There is even a special linux user target that loads 32bit binaries with the 64bit emulator and 32bit syscall wrapper.

Or are you referring to something else than the #ifdef TARGET_PPC64?

Alex

> 
> 
> r~
> 
> 

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

* Re: [Qemu-devel] [Qemu-ppc] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction
  2013-12-30 15:43         ` [Qemu-devel] [Qemu-ppc] " Alexander Graf
@ 2013-12-30 16:23           ` Richard Henderson
  0 siblings, 0 replies; 38+ messages in thread
From: Richard Henderson @ 2013-12-30 16:23 UTC (permalink / raw)
  To: Alexander Graf
  Cc: Scott Wood, Tom Musta, qemu-ppc@nongnu.org, qemu-devel@nongnu.org

On 12/30/2013 07:43 AM, Alexander Graf wrote:
> Yes you can, but we only expose 64bit capable cpus with TARGET_PPC64 defined. You couldn't select them with the 32bit target.

Ah, well.  That answers my question then, really.


r~

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

* Re: [Qemu-devel] [Qemu-ppc] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions
  2013-12-28  0:30   ` [Qemu-devel] [Qemu-ppc] " Scott Wood
@ 2014-01-03 19:24     ` Tom Musta
  2014-01-03 19:43       ` Scott Wood
  0 siblings, 1 reply; 38+ messages in thread
From: Tom Musta @ 2014-01-03 19:24 UTC (permalink / raw)
  To: Scott Wood; +Cc: qemu-ppc, qemu-devel

On 12/27/2013 6:30 PM, Scott Wood wrote:
> These instructions are phased-in on embedded, and unlike bpermd are not
> present on e5500/e6500 which are 64-bit ISA 2.06 implementations.
> Wasn't the conclusion in a previous thread to use separate flags for
> these instruction groups?
> 
> -Scott

Scott:

Yes ... but those comments were made *after* this revision was published
(http://lists.nongnu.org/archive/html/qemu-devel/2013-12/msg03681.html).

I have yet to produce V4 of this series which will include the new and
separate flags.

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

* Re: [Qemu-devel] [Qemu-ppc] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions
  2014-01-03 19:24     ` Tom Musta
@ 2014-01-03 19:43       ` Scott Wood
  0 siblings, 0 replies; 38+ messages in thread
From: Scott Wood @ 2014-01-03 19:43 UTC (permalink / raw)
  To: Tom Musta; +Cc: qemu-ppc, qemu-devel

On Fri, 2014-01-03 at 13:24 -0600, Tom Musta wrote:
> On 12/27/2013 6:30 PM, Scott Wood wrote:
> > These instructions are phased-in on embedded, and unlike bpermd are not
> > present on e5500/e6500 which are 64-bit ISA 2.06 implementations.
> > Wasn't the conclusion in a previous thread to use separate flags for
> > these instruction groups?
> > 
> > -Scott
> 
> Scott:
> 
> Yes ... but those comments were made *after* this revision was published
> (http://lists.nongnu.org/archive/html/qemu-devel/2013-12/msg03681.html).
> 
> I have yet to produce V4 of this series which will include the new and
> separate flags.

Oops... for some reason I thought the patchset was newer.  Sorry about
that.

-Scott

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

* Re: [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz]
  2013-12-24 16:02   ` Richard Henderson
@ 2014-01-06 20:06     ` Tom Musta
  0 siblings, 0 replies; 38+ messages in thread
From: Tom Musta @ 2014-01-06 20:06 UTC (permalink / raw)
  To: Richard Henderson, qemu-devel; +Cc: qemu-ppc

On 12/24/2013 10:02 AM, Richard Henderson wrote:
> I'll also note that frin can't properly be implemented with
> float_round_nearest_even because it doesn't round to even.

Good catch.  I should be able to use Peter's ties away rounding
mode patches.

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

end of thread, other threads:[~2014-01-06 20:07 UTC | newest]

Thread overview: 38+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2013-12-18 20:48 [Qemu-devel] [V3 PATCH 00/14] target-ppc: Base ISA V2.06 for Power7/Power8 Tom Musta
2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 01/14] target-ppc: Add Flag for Power ISA V2.06 Tom Musta
2013-12-24 15:11   ` Richard Henderson
2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 02/14] target-ppc: Add ISA2.06 bpermd Instruction Tom Musta
2013-12-24 15:17   ` Richard Henderson
2013-12-28  0:23     ` Scott Wood
2013-12-30 14:48       ` Richard Henderson
2013-12-30 15:43         ` [Qemu-devel] [Qemu-ppc] " Alexander Graf
2013-12-30 16:23           ` Richard Henderson
2013-12-28  0:27   ` [Qemu-devel] " Scott Wood
2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 03/14] target-ppc: Add ISA2.06 divdeu[o] Instructions Tom Musta
2013-12-24 15:20   ` Richard Henderson
2013-12-28  0:30   ` [Qemu-devel] [Qemu-ppc] " Scott Wood
2014-01-03 19:24     ` Tom Musta
2014-01-03 19:43       ` Scott Wood
2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 04/14] target-ppc: Add ISA2.06 divde[o] Instructions Tom Musta
2013-12-24 15:22   ` Richard Henderson
2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 05/14] target-ppc: Add ISA 2.06 divwe[u][o] Instructions Tom Musta
2013-12-24 15:26   ` Richard Henderson
2013-12-18 20:48 ` [Qemu-devel] [V3 PATCH 06/14] target-ppc: Add ISA2.06 lbarx, lharx Instructions Tom Musta
2013-12-24 15:28   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 07/14] target-ppc: Add ISA 2.06 stbcx. and sthcx. Instructions Tom Musta
2013-12-24 15:31   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 08/14] target-ppc: Add ISA2.06 Float to Integer Instructions Tom Musta
2013-12-24 15:36   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 09/14] target-ppc: Add ISA 2.06 fcfid[u][s] Instructions Tom Musta
2013-12-24 15:41   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 10/14] target-ppc: Fix and enable fri[mnpz] Tom Musta
2013-12-24 16:02   ` Richard Henderson
2014-01-06 20:06     ` Tom Musta
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 11/14] target-ppc: Add ISA 2.06 ftdiv Instruction Tom Musta
2013-12-24 16:06   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 12/14] target-ppc: Add ISA 2.06 ftsqrt Tom Musta
2013-12-24 16:07   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 13/14] target-ppc: Enable frsqrtes on Power7 and Power8 Tom Musta
2013-12-24 16:07   ` Richard Henderson
2013-12-18 20:49 ` [Qemu-devel] [V3 PATCH 14/14] target-ppc: Add ISA2.06 lfiwzx Instruction Tom Musta
2013-12-24 16:09   ` Richard Henderson

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).