]> git.proxmox.com Git - qemu.git/commitdiff
ppc fixes (Jocelyn Mayer)
authorbellard <bellard@c046a42c-6fe2-441c-8c8c-71466251a162>
Tue, 15 Feb 2005 23:06:19 +0000 (23:06 +0000)
committerbellard <bellard@c046a42c-6fe2-441c-8c8c-71466251a162>
Tue, 15 Feb 2005 23:06:19 +0000 (23:06 +0000)
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@1297 c046a42c-6fe2-441c-8c8c-71466251a162

target-ppc/cpu.h
target-ppc/helper.c
target-ppc/op.c
target-ppc/op_helper.c
target-ppc/translate.c

index 123cb3f91b17f77acd56fb346e9740621aa7d7e2..1776a3577a945ad6f137a60b383f4c65a94efda7 100644 (file)
@@ -24,8 +24,6 @@
 
 #include "cpu-defs.h"
 
-//#define USE_OPEN_FIRMWARE
-
 #include "config.h"
 #include <setjmp.h>
 
index 21e89008f4e42ed91c4bf55d29cd3b5ac462a6ef..a9424dfa707d3ddccc56d04930f1b40053060be2 100644 (file)
  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  */
 #include "exec.h"
-#if defined (USE_OPEN_FIRMWARE)
-#include <time.h>
-#include "of.h"
-#endif
 
 //#define DEBUG_MMU
 //#define DEBUG_BATS
@@ -688,18 +684,6 @@ void do_interrupt (CPUState *env)
     }
     /* Generate informations in save/restore registers */
     switch (excp) {
-    case EXCP_OFCALL:
-#if defined (USE_OPEN_FIRMWARE)
-        env->gpr[3] = OF_client_entry((void *)env->gpr[3]);
-#endif
-        return;
-    case EXCP_RTASCALL:
-#if defined (USE_OPEN_FIRMWARE)
-        printf("RTAS call !\n");
-        env->gpr[3] = RTAS_entry((void *)env->gpr[3]);
-        printf("RTAS call done\n");
-#endif
-        return;
     case EXCP_NONE:
         /* Do nothing */
 #if defined (DEBUG_EXCEPTIONS)
index c6c0989ce9f49175a54c8cda40f5342923df242a..5accc55064c1caa5a81b2fd0bb6198a35fb839ba 100644 (file)
@@ -697,9 +697,9 @@ PPC_OP(addzeo)
 PPC_OP(divw)
 {
     if ((Ts0 == INT32_MIN && Ts1 == -1) || Ts1 == 0) {
-        Ts0 = (-1) * (T0 >> 31);
+        T0 = (int32_t)((-1) * (T0 >> 31));
     } else {
-        Ts0 /= Ts1;
+        T0 = (Ts0 / Ts1);
     }
     RETURN();
 }
@@ -712,7 +712,7 @@ PPC_OP(divwo)
         T0 = (-1) * (T0 >> 31);
     } else {
         xer_ov = 0;
-        Ts0 /= Ts1;
+        T0 = (Ts0 / Ts1);
     }
     RETURN();
 }
@@ -744,7 +744,7 @@ PPC_OP(divwuo)
 /* multiply high word */
 PPC_OP(mulhw)
 {
-    Ts0 = ((int64_t)Ts0 * (int64_t)Ts1) >> 32;
+    T0 = ((int64_t)Ts0 * (int64_t)Ts1) >> 32;
     RETURN();
 }
 
@@ -758,7 +758,7 @@ PPC_OP(mulhwu)
 /* multiply low immediate */
 PPC_OP(mulli)
 {
-    Ts0 *= SPARAM(1);
+    T0 = (Ts0 * SPARAM(1));
     RETURN();
 }
 
@@ -779,7 +779,7 @@ PPC_OP(mullwo)
     } else {
         xer_ov = 0;
     }
-    Ts0 = res;
+    T0 = (int32_t)res;
     RETURN();
 }
 
@@ -787,7 +787,7 @@ PPC_OP(mullwo)
 PPC_OP(neg)
 {
     if (T0 != 0x80000000) {
-        Ts0 = -Ts0;
+        T0 = -Ts0;
     }
     RETURN();
 }
@@ -799,7 +799,7 @@ PPC_OP(nego)
         xer_so = 1;
     } else {
         xer_ov = 0;
-        Ts0 = -Ts0;
+        T0 = -Ts0;
     }
     RETURN();
 }
@@ -1047,14 +1047,14 @@ PPC_OP(eqv)
 /* extend sign byte */
 PPC_OP(extsb)
 {
-    Ts0 = (int8_t)(Ts0);
+    T0 = (int32_t)((int8_t)(Ts0));
     RETURN();
 }
 
 /* extend sign half word */
 PPC_OP(extsh)
 {
-    Ts0 = (int16_t)(Ts0);
+    T0 = (int32_t)((int16_t)(Ts0));
     RETURN();
 }
 
@@ -1175,8 +1175,8 @@ PPC_OP(sraw)
 /* shift right algebraic word immediate */
 PPC_OP(srawi)
 {
-    Ts1 = Ts0;
-    Ts0 = Ts0 >> PARAM(1);
+    T1 = T0;
+    T0 = (Ts0 >> PARAM(1));
     if (Ts1 < 0 && (Ts1 & PARAM(2)) != 0) {
         xer_ca = 1;
     } else {
@@ -1207,7 +1207,7 @@ PPC_OP(fadd)
 /* fadds - fadds. */
 PPC_OP(fadds)
 {
-    FTS0 += FTS1;
+    FT0 = FTS0 + FTS1;
     RETURN();
 }
 
@@ -1221,7 +1221,7 @@ PPC_OP(fsub)
 /* fsubs - fsubs. */
 PPC_OP(fsubs)
 {
-    FTS0 -= FTS1;
+    FT0 = FTS0 - FTS1;
     RETURN();
 }
 
@@ -1235,7 +1235,7 @@ PPC_OP(fmul)
 /* fmuls - fmuls. */
 PPC_OP(fmuls)
 {
-    FTS0 *= FTS1;
+    FT0 = FTS0 * FTS1;
     RETURN();
 }
 
@@ -1249,7 +1249,7 @@ PPC_OP(fdiv)
 /* fdivs - fdivs. */
 PPC_OP(fdivs)
 {
-    FTS0 /= FTS1;
+    FT0 = FTS0 / FTS1;
     RETURN();
 }
 
@@ -1299,7 +1299,7 @@ PPC_OP(fmadd)
 /* fmadds - fmadds. */
 PPC_OP(fmadds)
 {
-    FTS0 = (FTS0 * FTS1) + FTS2;
+    FT0 = (FTS0 * FTS1) + FTS2;
     RETURN();
 }
 
@@ -1313,7 +1313,7 @@ PPC_OP(fmsub)
 /* fmsubs - fmsubs. */
 PPC_OP(fmsubs)
 {
-    FTS0 = (FTS0 * FTS1) - FTS2;
+    FT0 = (FTS0 * FTS1) - FTS2;
     RETURN();
 }
 
@@ -1349,7 +1349,7 @@ PPC_OP(fnmsubs)
 /* frsp - frsp. */
 PPC_OP(frsp)
 {
-    FTS0 = FT0;
+    FT0 = (float)FT0;
     RETURN();
 }
 
index 433f6b12845e0f3c25e1d7d12e3c454a63688a74..20aba8b6ebd2b2ac30b6672adf8ac06bda92fe05 100644 (file)
@@ -188,10 +188,17 @@ void do_load_fpscr (void)
     } u;
     int i;
 
-    u.s.u[0] = 0;
-    u.s.u[1] = 0;
+#ifdef WORDS_BIGENDIAN
+#define WORD0 0
+#define WORD1 1
+#else
+#define WORD0 1
+#define WORD1 0
+#endif
+    u.s.u[WORD0] = 0;
+    u.s.u[WORD1] = 0;
     for (i = 0; i < 8; i++)
-        u.s.u[1] |= env->fpscr[i] << (4 * i);
+        u.s.u[WORD1] |= env->fpscr[i] << (4 * i);
     FT0 = u.d;
 }
 
@@ -210,10 +217,10 @@ void do_store_fpscr (uint32_t mask)
 
     u.d = FT0;
     if (mask & 0x80)
-        env->fpscr[0] = (env->fpscr[0] & 0x9) | ((u.s.u[1] >> 28) & ~0x9);
+        env->fpscr[0] = (env->fpscr[0] & 0x9) | ((u.s.u[WORD1] >> 28) & ~0x9);
     for (i = 1; i < 7; i++) {
         if (mask & (1 << (7 - i)))
-            env->fpscr[i] = (u.s.u[1] >> (4 * (7 - i))) & 0xF;
+            env->fpscr[i] = (u.s.u[WORD1] >> (4 * (7 - i))) & 0xF;
     }
     /* TODO: update FEX & VX */
     /* Set rounding mode */
index 4de116f18504f0d5038a18923024e2779053f020..bb3bbbb544aa9b5f63169c093811f03c2567410f 100644 (file)
@@ -134,12 +134,13 @@ typedef struct DisasContext {
     target_ulong nip;
     uint32_t opcode;
     uint32_t exception;
-    /* Execution mode */
+    /* Routine used to access memory */
+    int mem_idx;
+    /* Translation flags */
 #if !defined(CONFIG_USER_ONLY)
     int supervisor;
 #endif
-    /* Routine used to access memory */
-    int mem_idx;
+    int fpu_enabled;
 } DisasContext;
 
 typedef struct opc_handler_t {
@@ -330,19 +331,6 @@ GEN_HANDLER(stop, 0x06, 0x00, 0xFF, 0x03FFFFC1, PPC_COMMON)
     RET_EXCP(ctx, EXCP_HLT, 0);
 }
 
-/* Special opcode to call open-firmware */
-GEN_HANDLER(of_enter, 0x06, 0x01, 0xFF, 0x03FFFFC1, PPC_COMMON)
-{
-    RET_EXCP(ctx, EXCP_OFCALL, 0);
-}
-
-/* Special opcode to call RTAS */
-GEN_HANDLER(rtas_enter, 0x06, 0x02, 0xFF, 0x03FFFFC1, PPC_COMMON)
-{
-    printf("RTAS entry point !\n");
-    RET_EXCP(ctx, EXCP_RTASCALL, 0);
-}
-
 static opc_handler_t invalid_handler = {
     .inval   = 0xFFFFFFFF,
     .type    = PPC_NONE,
@@ -764,6 +752,10 @@ __GEN_LOGICAL2(srw, 0x18, 0x10);
 #define _GEN_FLOAT_ACB(name, op1, op2)                                        \
 GEN_HANDLER(f##name, op1, op2, 0xFF, 0x00000000, PPC_FLOAT)                   \
 {                                                                             \
+    if (!ctx->fpu_enabled) {                                                  \
+        RET_EXCP(ctx, EXCP_NO_FP, 0);                                         \
+        return;                                                               \
+    }                                                                         \
     gen_op_reset_scrfx();                                                     \
     gen_op_load_fpr_FT0(rA(ctx->opcode));                                     \
     gen_op_load_fpr_FT1(rC(ctx->opcode));                                     \
@@ -781,6 +773,10 @@ _GEN_FLOAT_ACB(name##s, 0x3B, op2);
 #define _GEN_FLOAT_AB(name, op1, op2, inval)                                  \
 GEN_HANDLER(f##name, op1, op2, 0xFF, inval, PPC_FLOAT)                        \
 {                                                                             \
+    if (!ctx->fpu_enabled) {                                                  \
+        RET_EXCP(ctx, EXCP_NO_FP, 0);                                         \
+        return;                                                               \
+    }                                                                         \
     gen_op_reset_scrfx();                                                     \
     gen_op_load_fpr_FT0(rA(ctx->opcode));                                     \
     gen_op_load_fpr_FT1(rB(ctx->opcode));                                     \
@@ -796,6 +792,10 @@ _GEN_FLOAT_AB(name##s, 0x3B, op2, inval);
 #define _GEN_FLOAT_AC(name, op1, op2, inval)                                  \
 GEN_HANDLER(f##name, op1, op2, 0xFF, inval, PPC_FLOAT)                        \
 {                                                                             \
+    if (!ctx->fpu_enabled) {                                                  \
+        RET_EXCP(ctx, EXCP_NO_FP, 0);                                         \
+        return;                                                               \
+    }                                                                         \
     gen_op_reset_scrfx();                                                     \
     gen_op_load_fpr_FT0(rA(ctx->opcode));                                     \
     gen_op_load_fpr_FT1(rC(ctx->opcode));                                     \
@@ -811,6 +811,10 @@ _GEN_FLOAT_AC(name##s, 0x3B, op2, inval);
 #define GEN_FLOAT_B(name, op2, op3)                                           \
 GEN_HANDLER(f##name, 0x3F, op2, op3, 0x001F0000, PPC_FLOAT)                   \
 {                                                                             \
+    if (!ctx->fpu_enabled) {                                                  \
+        RET_EXCP(ctx, EXCP_NO_FP, 0);                                         \
+        return;                                                               \
+    }                                                                         \
     gen_op_reset_scrfx();                                                     \
     gen_op_load_fpr_FT0(rB(ctx->opcode));                                     \
     gen_op_f##name();                                                         \
@@ -822,6 +826,10 @@ GEN_HANDLER(f##name, 0x3F, op2, op3, 0x001F0000, PPC_FLOAT)                   \
 #define GEN_FLOAT_BS(name, op2)                                               \
 GEN_HANDLER(f##name, 0x3F, op2, 0xFF, 0x001F07C0, PPC_FLOAT)                  \
 {                                                                             \
+    if (!ctx->fpu_enabled) {                                                  \
+        RET_EXCP(ctx, EXCP_NO_FP, 0);                                         \
+        return;                                                               \
+    }                                                                         \
     gen_op_reset_scrfx();                                                     \
     gen_op_load_fpr_FT0(rB(ctx->opcode));                                     \
     gen_op_f##name();                                                         \
@@ -853,6 +861,10 @@ GEN_FLOAT_BS(sqrt, 0x16);
 
 GEN_HANDLER(fsqrts, 0x3B, 0x16, 0xFF, 0x001F07C0, PPC_FLOAT_OPT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_reset_scrfx();
     gen_op_load_fpr_FT0(rB(ctx->opcode));
     gen_op_fsqrts();
@@ -883,6 +895,10 @@ GEN_FLOAT_B(rsp, 0x0C, 0x00);
 /* fcmpo */
 GEN_HANDLER(fcmpo, 0x3F, 0x00, 0x00, 0x00600001, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_reset_scrfx();
     gen_op_load_fpr_FT0(rA(ctx->opcode));
     gen_op_load_fpr_FT1(rB(ctx->opcode));
@@ -893,6 +909,10 @@ GEN_HANDLER(fcmpo, 0x3F, 0x00, 0x00, 0x00600001, PPC_FLOAT)
 /* fcmpu */
 GEN_HANDLER(fcmpu, 0x3F, 0x00, 0x01, 0x00600001, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_reset_scrfx();
     gen_op_load_fpr_FT0(rA(ctx->opcode));
     gen_op_load_fpr_FT1(rB(ctx->opcode));
@@ -907,6 +927,10 @@ GEN_FLOAT_B(abs, 0x08, 0x08);
 /* fmr  - fmr. */
 GEN_HANDLER(fmr, 0x3F, 0x08, 0x02, 0x001F0000, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_reset_scrfx();
     gen_op_load_fpr_FT0(rB(ctx->opcode));
     gen_op_store_FT0_fpr(rD(ctx->opcode));
@@ -923,6 +947,10 @@ GEN_FLOAT_B(neg, 0x08, 0x01);
 /* mcrfs */
 GEN_HANDLER(mcrfs, 0x3F, 0x00, 0x02, 0x0063F801, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_load_fpscr_T0(crfS(ctx->opcode));
     gen_op_store_T0_crf(crfD(ctx->opcode));
     gen_op_clear_fpscr(crfS(ctx->opcode));
@@ -931,6 +959,10 @@ GEN_HANDLER(mcrfs, 0x3F, 0x00, 0x02, 0x0063F801, PPC_FLOAT)
 /* mffs */
 GEN_HANDLER(mffs, 0x3F, 0x07, 0x12, 0x001FF800, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_load_fpscr();
     gen_op_store_FT0_fpr(rD(ctx->opcode));
     if (Rc(ctx->opcode))
@@ -942,6 +974,10 @@ GEN_HANDLER(mtfsb0, 0x3F, 0x06, 0x02, 0x001FF800, PPC_FLOAT)
 {
     uint8_t crb;
     
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     crb = crbD(ctx->opcode) >> 2;
     gen_op_load_fpscr_T0(crb);
     gen_op_andi_(~(1 << (crbD(ctx->opcode) & 0x03)));
@@ -955,6 +991,10 @@ GEN_HANDLER(mtfsb1, 0x3F, 0x06, 0x01, 0x001FF800, PPC_FLOAT)
 {
     uint8_t crb;
     
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     crb = crbD(ctx->opcode) >> 2;
     gen_op_load_fpscr_T0(crb);
     gen_op_ori(1 << (crbD(ctx->opcode) & 0x03));
@@ -966,6 +1006,10 @@ GEN_HANDLER(mtfsb1, 0x3F, 0x06, 0x01, 0x001FF800, PPC_FLOAT)
 /* mtfsf */
 GEN_HANDLER(mtfsf, 0x3F, 0x07, 0x16, 0x02010000, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_load_fpr_FT0(rB(ctx->opcode));
     gen_op_store_fpscr(FM(ctx->opcode));
     if (Rc(ctx->opcode))
@@ -975,6 +1019,10 @@ GEN_HANDLER(mtfsf, 0x3F, 0x07, 0x16, 0x02010000, PPC_FLOAT)
 /* mtfsfi */
 GEN_HANDLER(mtfsfi, 0x3F, 0x06, 0x04, 0x006f0800, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     gen_op_store_T0_fpscri(crbD(ctx->opcode) >> 2, FPIMM(ctx->opcode));
     if (Rc(ctx->opcode))
         gen_op_set_Rc1();
@@ -1525,6 +1573,10 @@ GEN_STFS(fs, 0x14);
 /* stfiwx */
 GEN_HANDLER(stfiwx, 0x1F, 0x17, 0x1E, 0x00000001, PPC_FLOAT)
 {
+    if (!ctx->fpu_enabled) {
+        RET_EXCP(ctx, EXCP_NO_FP, 0);
+        return;
+    }
     RET_INVAL(ctx);
 }
 
@@ -2978,10 +3030,6 @@ void cpu_dump_state(CPUState *env, FILE *f,
     cpu_fprintf(f, "reservation 0x%08x\n", env->reserve);
 }
 
-#if !defined(CONFIG_USER_ONLY) && defined (USE_OPENFIRMWARE)
-int setup_machine (CPUPPCState *env, uint32_t mid);
-#endif
-
 CPUPPCState *cpu_ppc_init(void)
 {
     CPUPPCState *env;
@@ -2991,14 +3039,10 @@ CPUPPCState *cpu_ppc_init(void)
     env = qemu_mallocz(sizeof(CPUPPCState));
     if (!env)
         return NULL;
-#if !defined(CONFIG_USER_ONLY) && defined (USE_OPEN_FIRMWARE)
-    setup_machine(env, 0);
-#else
 //    env->spr[PVR] = 0; /* Basic PPC */
     env->spr[PVR] = 0x00080100; /* G3 CPU */
 //    env->spr[PVR] = 0x00083100; /* MPC755 (G3 embedded) */
 //    env->spr[PVR] = 0x00070100; /* IBM 750FX */
-#endif
     tlb_flush(env, 1);
 #if defined (DO_SINGLE_STEP)
     /* Single step trace mode */
@@ -3053,8 +3097,9 @@ int gen_intermediate_code_internal (CPUState *env, TranslationBlock *tb,
     ctx.mem_idx = 0;
 #else
     ctx.supervisor = 1 - msr_pr;
-    ctx.mem_idx = (1 - msr_pr);
+    ctx.mem_idx = 1 - msr_pr;
 #endif
+    ctx.fpu_enabled = msr_fp;
 #if defined (DO_SINGLE_STEP)
     /* Single step trace mode */
     msr_se = 1;