summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
author Aaron Giles <aaron@aarongiles.com>2007-12-31 02:00:41 +0000
committer Aaron Giles <aaron@aarongiles.com>2007-12-31 02:00:41 +0000
commit3f6e8e1abfc478371e1e6f1a9cd317fbf5460424 (patch)
treea4cfa1cd073753a3dababb18243fc42b93bdd53d
parent625c8308b9b3eb661f712a53f3b9a359af0ff276 (diff)
(From Samuele Zannoli)
The attached patch is some more progress in the sh4 core, expecially in the fpu. Now there should be all the minimum needed to run the naomi bios ...
-rw-r--r--src/emu/cpu/sh4/sh4.c711
-rw-r--r--src/emu/cpu/sh4/sh4dasm.c2
2 files changed, 602 insertions, 111 deletions
diff --git a/src/emu/cpu/sh4/sh4.c b/src/emu/cpu/sh4/sh4.c
index aacc951245e..61e26701aed 100644
--- a/src/emu/cpu/sh4/sh4.c
+++ b/src/emu/cpu/sh4/sh4.c
@@ -25,9 +25,12 @@
#include "debugger.h"
#include "sh4.h"
#include "sh4regs.h"
+#include <math.h>
/* speed up delay loops, bail out of tight loops */
#define BUSY_LOOP_HACKS 0
+/* work only as described in the datasheet */
+#define DATASHEET_STRICT 0
#define VERBOSE 0
@@ -41,6 +44,19 @@
#define NMIPRI() EXPPRI(3,0,16,SH4_INTC_NMI)
#define INTPRI(p,n) EXPPRI(4,2,p,n)
+#define FP_RS(r) sh4.fr[(r)] // binary representation of single precision floating point register r
+#define FP_RFS(r) *( (float *)(sh4.fr+(r)) ) // single precision floating point register r
+#define FP_RFD(r) *( (double *)(sh4.fr+(r)) ) // double precision floating point register r
+#define FP_XS(r) sh4.xf[(r)] // binary representation of extended single precision floating point register r
+#define FP_XFS(r) *( (float *)(sh4.xf+(r)) ) // single precision extended floating point register r
+#define FP_XFD(r) *( (double *)(sh4.xf+(r)) ) // double precision extended floating point register r
+#ifdef LSB_FIRST
+#define FP_RS2(r) sh4.fr[(r) ^ sh4.fpu_pr]
+#define FP_RFS2(r) *( (float *)(sh4.fr+((r) ^ sh4.fpu_pr)) )
+#define FP_XS2(r) sh4.xf[(r) ^ sh4.fpu_pr]
+#define FP_XFS2(r) *( (float *)(sh4.xf+((r) ^ sh4.fpu_pr)) )
+#endif
+
typedef struct
{
UINT32 ppc;
@@ -84,6 +100,7 @@ typedef struct
int is_slave, cpu_number;
int cpu_clock, bus_clock, pm_clock;
+ int fpu_sz, fpu_pr;
void (*ftcsr_read_callback)(UINT32 data);
} SH4;
@@ -270,6 +287,37 @@ int s;
}
}
+static void sh4_swap_fp_registers(void)
+{
+int s;
+UINT32 z;
+
+ for (s = 0;s <= 15;s++)
+ {
+ z = sh4.fr[s];
+ sh4.fr[s] = sh4.xf[s];
+ sh4.xf[s] = z;
+ }
+}
+
+#ifdef LSB_FIRST
+static void sh4_swap_fp_couples(void)
+{
+int s;
+UINT32 z;
+
+ for (s = 0;s <= 15;s = s+2)
+ {
+ z = sh4.fr[s];
+ sh4.fr[s] = sh4.fr[s + 1];
+ sh4.fr[s + 1] = z;
+ z = sh4.xf[s];
+ sh4.xf[s] = sh4.xf[s + 1];
+ sh4.xf[s + 1] = z;
+ }
+}
+#endif
+
#ifdef MAME_DEBUG
static void sh4_syncronize_register_bank(int to)
{
@@ -415,19 +463,6 @@ int a,irq,z;
sh4_exception(message, irq);
}
-static void sh4_swap_fp_registers(void)
-{
-int s;
-UINT32 z;
-
- for (s = 0;s <= 15;s++)
- {
- z = sh4.fr[s];
- sh4.fr[s] = sh4.xf[s];
- sh4.xf[s] = z;
- }
-}
-
/* code cycles t-bit
* 0011 nnnn mmmm 1100 1 -
* ADD Rm,Rn
@@ -2174,6 +2209,12 @@ UINT32 s;
sh4.r[m] += 4;
if ((s & FR) != (sh4.fpscr & FR))
sh4_swap_fp_registers();
+#ifdef LSB_FIRST
+ if ((s & PR) != (sh4.fpscr & PR))
+ sh4_swap_fp_couples();
+#endif
+ sh4.fpu_sz = (sh4.fpscr & SZ) ? 1 : 0;
+ sh4.fpu_pr = (sh4.fpscr & PR) ? 1 : 0;
}
/* LDC.L @Rm+,DBR */
@@ -2223,6 +2264,12 @@ UINT32 s;
sh4.fpscr = sh4.r[m] & 0x003FFFFF;
if ((s & FR) != (sh4.fpscr & FR))
sh4_swap_fp_registers();
+#ifdef LSB_FIRST
+ if ((s & PR) != (sh4.fpscr & PR))
+ sh4_swap_fp_couples();
+#endif
+ sh4.fpu_sz = (sh4.fpscr & SZ) ? 1 : 0;
+ sh4.fpu_pr = (sh4.fpscr & PR) ? 1 : 0;
}
/* LDC Rm,DBR */
@@ -2290,11 +2337,11 @@ UINT32 addr,dest,sq;
else
dest |= (sh4.m[QACR1] & 0x1C) << 24;
addr = addr & 0xFFFFFFE0;
- for (a = 0;a < 8;a++)
+ for (a = 0;a < 4;a++)
{
- program_write_dword_64le(dest, program_read_dword_64le(addr));
- addr += 4;
- dest += 4;
+ program_write_qword_64le(dest, program_read_qword_64le(addr));
+ addr += 8;
+ dest += 8;
}
}
}
@@ -2774,20 +2821,24 @@ INLINE void op1110(UINT16 opcode)
MOVI(opcode & 0xff, Rn);
}
+/* FMOV.S @Rm+,FRn PR=0 SZ=0 1111nnnnmmmm1001 */
/* FMOV @Rm+,DRn PR=0 SZ=1 1111nnn0mmmm1001 */
/* FMOV @Rm+,XDn PR=1 1111nnn1mmmm1001 */
-/* FMOV.S @Rm+,FRn PR=0 SZ=0 1111nnnnmmmm1001 */
INLINE void FMOVMRIFR(UINT32 m,UINT32 n)
{
- if (sh4.fpscr & PR) { /* PR = 1 */
+ if (sh4.fpu_pr) { /* PR = 1 */
n = n & 14;
sh4.ea = sh4.r[m];
+ sh4.r[m] += 8;
+#ifdef LSB_FIRST
+ sh4.xf[n+1] = RL( sh4.ea );
+ sh4.xf[n] = RL( sh4.ea+4 );
+#else
sh4.xf[n] = RL( sh4.ea );
- sh4.r[m] += 4;
- sh4.xf[n+1] = RL( sh4.r[m] );
- sh4.r[m] += 4;
+ sh4.xf[n+1] = RL( sh4.ea+4 );
+#endif
} else { /* PR = 0 */
- if (sh4.fpscr & SZ) { /* SZ = 1 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
n = n & 14;
sh4.ea = sh4.r[m];
sh4.fr[n] = RL( sh4.ea );
@@ -2802,18 +2853,23 @@ INLINE void FMOVMRIFR(UINT32 m,UINT32 n)
}
}
-/* FMOV XDm,@Rn PR=1 1111nnnnmmm11010 */
/* FMOV.S FRm,@Rn PR=0 SZ=0 1111nnnnmmmm1010 */
/* FMOV DRm,@Rn PR=0 SZ=1 1111nnnnmmm01010 */
+/* FMOV XDm,@Rn PR=1 1111nnnnmmm11010 */
INLINE void FMOVFRMR(UINT32 m,UINT32 n)
{
- if (sh4.fpscr & PR) { /* PR = 1 */
+ if (sh4.fpu_pr) { /* PR = 1 */
m= m & 14;
sh4.ea = sh4.r[n];
+#ifdef LSB_FIRST
+ WL( sh4.ea,sh4.xf[m+1] );
+ WL( sh4.ea+4,sh4.xf[m] );
+#else
WL( sh4.ea,sh4.xf[m] );
WL( sh4.ea+4,sh4.xf[m+1] );
+#endif
} else { /* PR = 0 */
- if (sh4.fpscr & SZ) { /* SZ = 1 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
m= m & 14;
sh4.ea = sh4.r[n];
WL( sh4.ea,sh4.fr[m] );
@@ -2825,19 +2881,24 @@ INLINE void FMOVFRMR(UINT32 m,UINT32 n)
}
}
-/* FMOV XDm,@-Rn PR=1 1111nnnnmmm11011 */
/* FMOV.S FRm,@-Rn PR=0 SZ=0 1111nnnnmmmm1011 */
/* FMOV DRm,@-Rn PR=0 SZ=1 1111nnnnmmm01011 */
+/* FMOV XDm,@-Rn PR=1 1111nnnnmmm11011 */
INLINE void FMOVFRMDR(UINT32 m,UINT32 n)
{
- if (sh4.fpscr & PR) { /* PR = 1 */
+ if (sh4.fpu_pr) { /* PR = 1 */
m= m & 14;
sh4.r[n] -= 8;
sh4.ea = sh4.r[n];
+#ifdef LSB_FIRST
+ WL( sh4.ea,sh4.xf[m+1] );
+ WL( sh4.ea+4,sh4.xf[m] );
+#else
WL( sh4.ea,sh4.xf[m] );
WL( sh4.ea+4,sh4.xf[m+1] );
+#endif
} else { /* PR = 0 */
- if (sh4.fpscr & SZ) { /* SZ = 1 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
m= m & 14;
sh4.r[n] -= 8;
sh4.ea = sh4.r[n];
@@ -2851,30 +2912,23 @@ INLINE void FMOVFRMDR(UINT32 m,UINT32 n)
}
}
-/* FLDI1 FRn 1111nnnn10011101 */
-INLINE void FLDI1(UINT32 n)
-{
- sh4.fr[n] = 0x3F800000;
-}
-
-/* FLDI0 FRn 1111nnnn10001101 */
-INLINE void FLDI0(UINT32 n)
-{
- sh4.fr[n] = 0;
-}
-
-/* FMOV XDm,@(R0,Rn) PR=1 1111nnnnmmm10111 */
/* FMOV.S FRm,@(R0,Rn) PR=0 SZ=0 1111nnnnmmmm0111 */
/* FMOV DRm,@(R0,Rn) PR=0 SZ=1 1111nnnnmmm00111 */
+/* FMOV XDm,@(R0,Rn) PR=1 1111nnnnmmm10111 */
INLINE void FMOVFRS0(UINT32 m,UINT32 n)
{
- if (sh4.fpscr & PR) { /* PR = 1 */
+ if (sh4.fpu_pr) { /* PR = 1 */
m= m & 14;
sh4.ea = sh4.r[0] + sh4.r[n];
+#ifdef LSB_FIRST
+ WL( sh4.ea,sh4.xf[m+1] );
+ WL( sh4.ea+4,sh4.xf[m] );
+#else
WL( sh4.ea,sh4.xf[m] );
WL( sh4.ea+4,sh4.xf[m+1] );
+#endif
} else { /* PR = 0 */
- if (sh4.fpscr & SZ) { /* SZ = 1 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
m= m & 14;
sh4.ea = sh4.r[0] + sh4.r[n];
WL( sh4.ea,sh4.fr[m] );
@@ -2886,18 +2940,23 @@ INLINE void FMOVFRS0(UINT32 m,UINT32 n)
}
}
-/* FMOV @(R0,Rm),XDn PR=1 1111nnn1mmmm0110 */
/* FMOV.S @(R0,Rm),FRn PR=0 SZ=0 1111nnnnmmmm0110 */
/* FMOV @(R0,Rm),DRn PR=0 SZ=1 1111nnn0mmmm0110 */
+/* FMOV @(R0,Rm),XDn PR=1 1111nnn1mmmm0110 */
INLINE void FMOVS0FR(UINT32 m,UINT32 n)
{
- if (sh4.fpscr & PR) { /* PR = 1 */
+ if (sh4.fpu_pr) { /* PR = 1 */
n= n & 14;
sh4.ea = sh4.r[0] + sh4.r[m];
+#ifdef LSB_FIRST
+ sh4.xf[n+1] = RL( sh4.ea );
+ sh4.xf[n] = RL( sh4.ea+4 );
+#else
sh4.xf[n] = RL( sh4.ea );
sh4.xf[n+1] = RL( sh4.ea+4 );
+#endif
} else { /* PR = 0 */
- if (sh4.fpscr & SZ) { /* SZ = 1 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
n= n & 14;
sh4.ea = sh4.r[0] + sh4.r[m];
sh4.fr[n] = RL( sh4.ea );
@@ -2909,18 +2968,26 @@ INLINE void FMOVS0FR(UINT32 m,UINT32 n)
}
}
-/* FMOV @Rm,XDn PR=1 1111nnn1mmmm1000 */
/* FMOV.S @Rm,FRn PR=0 SZ=0 1111nnnnmmmm1000 */
/* FMOV @Rm,DRn PR=0 SZ=1 1111nnn0mmmm1000 */
+/* FMOV @Rm,XDn PR=0 SZ=1 1111nnn1mmmm1000 */
+/* FMOV @Rm,XDn PR=1 1111nnn1mmmm1000 */
+/* FMOV @Rm,DRn PR=1 1111nnn0mmmm1000 */
INLINE void FMOVMRFR(UINT32 m,UINT32 n)
{
- if (sh4.fpscr & PR) { /* PR = 1 */
+#if DATASHEET_STRICT
+ if (sh4.fpu_pr) { /* PR = 1 */
n= n & 14;
sh4.ea = sh4.r[m];
+#ifdef LSB_FIRST
+ sh4.xf[n+1] = RL( sh4.ea );
+ sh4.xf[n] = RL( sh4.ea+4 );
+#else
sh4.xf[n] = RL( sh4.ea );
sh4.xf[n+1] = RL( sh4.ea+4 );
+#endif
} else { /* PR = 0 */
- if (sh4.fpscr & SZ) { /* SZ = 1 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
n= n & 14;
sh4.ea = sh4.r[m];
sh4.fr[n] = RL( sh4.ea );
@@ -2930,6 +2997,126 @@ INLINE void FMOVMRFR(UINT32 m,UINT32 n)
sh4.fr[n] = RL( sh4.ea );
}
}
+#else
+ if (sh4.fpu_pr) { /* PR = 1 */
+ if (n & 1) {
+ n= n & 14;
+ sh4.ea = sh4.r[m];
+#ifdef LSB_FIRST
+ sh4.xf[n+1] = RL( sh4.ea );
+ sh4.xf[n] = RL( sh4.ea+4 );
+#else
+ sh4.xf[n] = RL( sh4.ea );
+ sh4.xf[n+1] = RL( sh4.ea+4 );
+#endif
+ } else {
+ n= n & 14;
+ sh4.ea = sh4.r[m];
+#ifdef LSB_FIRST
+ sh4.fr[n+1] = RL( sh4.ea );
+ sh4.fr[n] = RL( sh4.ea+4 );
+#else
+ sh4.fr[n] = RL( sh4.ea );
+ sh4.fr[n+1] = RL( sh4.ea+4 );
+#endif
+ }
+ } else { /* PR = 0 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
+ if (n & 1) {
+ n= n & 14;
+ sh4.ea = sh4.r[m];
+ sh4.xf[n] = RL( sh4.ea );
+ sh4.xf[n+1] = RL( sh4.ea+4 );
+ } else {
+ n= n & 14;
+ sh4.ea = sh4.r[m];
+ sh4.fr[n] = RL( sh4.ea );
+ sh4.fr[n+1] = RL( sh4.ea+4 );
+ }
+ } else { /* SZ = 0 */
+ sh4.ea = sh4.r[m];
+ sh4.fr[n] = RL( sh4.ea );
+ }
+ }
+#endif
+}
+
+/* FMOV FRm,FRn PR=0 SZ=0 FRm -> FRn 1111nnnnmmmm1100 */
+/* FMOV DRm,DRn PR=0 SZ=1 DRm -> DRn 1111nnn0mmm01100 */
+/* FMOV XDm,DRn PR=1 XDm -> DRn 1111nnn0mmm11100 */
+/* FMOV DRm,XDn PR=1 DRm -> XDn 1111nnn1mmm01100 */
+/* FMOV XDm,XDn PR=1 XDm -> XDn 1111nnn1mmm11100 */
+INLINE void FMOVFR(UINT32 m,UINT32 n)
+{
+#if DATASHEET_STRICT
+ if (sh4.fpu_pr) { /* PR = 1 */
+ if (m & 1)
+ if (n & 1) {
+ sh4.xf[n & 14] = sh4.xf[m & 14];
+ sh4.xf[n | 1] = sh4.xf[m | 1];
+ } else {
+ sh4.fr[n] = sh4.xf[m & 14];
+ sh4.fr[n | 1] = sh4.xf[m | 1];
+ }
+ else {
+ sh4.xf[n & 14] = sh4.fr[m];
+ sh4.xf[n | 1] = sh4.fr[m|1]; // (a&14)+1 -> a|1
+ }
+ } else { /* PR = 0 */
+ if (sh4.fpu_sz) { /* SZ = 1 */
+ sh4.fr[n] = sh4.fr[m];
+ sh4.fr[n+1] = sh4.fr[m+1];
+ } else { /* SZ = 0 */
+ sh4.fr[n] = sh4.fr[m];
+ }
+ }
+#else
+ if (sh4.fpu_sz == 0) /* SZ = 0 */
+ sh4.fr[n] = sh4.fr[m];
+ else { /* SZ = 1 or PR = 1 */
+ if (m & 1)
+ if (n & 1) {
+ sh4.xf[n & 14] = sh4.xf[m & 14];
+ sh4.xf[n | 1] = sh4.xf[m | 1];
+ } else {
+ sh4.fr[n] = sh4.xf[m & 14];
+ sh4.fr[n | 1] = sh4.xf[m | 1];
+ }
+ else {
+ if (n & 1) {
+ sh4.xf[n & 14] = sh4.fr[m];
+ sh4.xf[n | 1] = sh4.fr[m | 1]; // (a&14)+1 -> a|1
+ } else {
+ sh4.fr[n] = sh4.fr[m & 14];
+ sh4.fr[n | 1] = sh4.fr[m | 1];
+ }
+ }
+ }
+#endif
+}
+
+/* FLDI1 FRn 1111nnnn10011101 */
+INLINE void FLDI1(UINT32 n)
+{
+ sh4.fr[n] = 0x3F800000;
+}
+
+/* FLDI0 FRn 1111nnnn10001101 */
+INLINE void FLDI0(UINT32 n)
+{
+ sh4.fr[n] = 0;
+}
+
+/* FLDS FRm,FPUL 1111mmmm00011101 */
+INLINE void FLDS(UINT32 m)
+{
+ sh4.fpul = sh4.fr[m];
+}
+
+/* FSTS FPUL,FRn 1111nnnn00001101 */
+INLINE void FSTS(UINT32 n)
+{
+ sh4.fr[n] = sh4.fpul;
}
/* FRCHG 1111101111111101 */
@@ -2943,6 +3130,240 @@ INLINE void FRCHG(void)
INLINE void FSCHG(void)
{
sh4.fpscr ^= SZ;
+ sh4.fpu_sz = (sh4.fpscr & SZ) ? 1 : 0;
+}
+
+/* FTRC FRm,FPUL PR=0 1111mmmm00111101 */
+/* FTRC DRm,FPUL PR=1 1111mmm000111101 */
+INLINE void FTRC(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ sh4.fpul = (INT32)FP_RFD(n);
+ } else { /* PR = 0 */
+ /* read sh4.fr[n] as float -> truncate -> fpul(32) */
+ sh4.fpul = (INT32)FP_RFS(n);
+ }
+}
+
+/* FLOAT FPUL,FRn PR=0 1111nnnn00101101 */
+/* FLOAT FPUL,DRn PR=1 1111nnn000101101 */
+INLINE void FLOAT(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ FP_RFD(n) = (double)(INT32)sh4.fpul;
+ } else { /* PR = 0 */
+ FP_RFS(n) = (float)(INT32)sh4.fpul;
+ }
+}
+
+/* FNEG FRn PR=0 1111nnnn01001101 */
+/* FNEG DRn PR=1 1111nnn001001101 */
+INLINE void FNEG(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+#ifdef LSB_FIRST
+ n = n | 1; // n & 14 + 1
+ sh4.fr[n] = sh4.fr[n] ^ 0x80000000;
+#else
+ n = n & 14;
+ sh4.fr[n] = sh4.fr[n] ^ 0x80000000;
+#endif
+ } else { /* PR = 0 */
+ sh4.fr[n] = sh4.fr[n] ^ 0x80000000;
+ }
+}
+
+
+/* FABS FRn PR=0 1111nnnn01011101 */
+/* FABS DRn PR=1 1111nnn001011101 */
+INLINE void FABS(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+#ifdef LSB_FIRST
+ n = n | 1; // n & 14 + 1
+ sh4.fr[n] = sh4.fr[n] & 0x7fffffff;
+#else
+ n = n & 14;
+ sh4.fr[n] = sh4.fr[n] & 0x7fffffff;
+#endif
+ } else { /* PR = 0 */
+ sh4.fr[n] = sh4.fr[n] & 0x7fffffff;
+ }
+}
+
+/* FCMP/EQ FRm,FRn PR=0 1111nnnnmmmm0100 */
+/* FCMP/EQ DRm,DRn PR=1 1111nnn0mmm00100 */
+INLINE void FCMP_EQ(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ m = m & 14;
+ if (FP_RFD(n) == FP_RFD(m))
+ sh4.sr |= T;
+ else
+ sh4.sr &= ~T;
+ } else { /* PR = 0 */
+ if (FP_RFS(n) == FP_RFS(m))
+ sh4.sr |= T;
+ else
+ sh4.sr &= ~T;
+ }
+}
+
+/* FCMP/GT FRm,FRn PR=0 1111nnnnmmmm0101 */
+/* FCMP/GT DRm,DRn PR=1 1111nnn0mmm00101 */
+INLINE void FCMP_GT(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ m = m & 14;
+ if (FP_RFD(n) > FP_RFD(m))
+ sh4.sr |= T;
+ else
+ sh4.sr &= ~T;
+ } else { /* PR = 0 */
+ if (FP_RFS(n) > FP_RFS(m))
+ sh4.sr |= T;
+ else
+ sh4.sr &= ~T;
+ }
+}
+
+/* FCNVDS DRm,FPUL PR=1 1111mmm010111101 */
+INLINE void FCNVDS(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+#ifdef LSB_FIRST
+ if (sh4.fpscr & RM)
+ sh4.fr[n] &= 0xe0000000; /* round toward zero*/
+#else
+ if (sh4.fpscr & RM)
+ sh4.fr[n | 1] &= 0xe0000000; /* round toward zero*/
+#endif
+ *((float *)&sh4.fpul) = (float)FP_RFD(n);
+ }
+}
+
+/* FCNVSD FPUL, DRn PR=1 1111nnn010101101 */
+INLINE void FCNVSD(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ FP_RFD(n) = *((float *)&sh4.fpul);
+ }
+}
+
+/* FADD FRm,FRn PR=0 1111nnnnmmmm0000 */
+/* FADD DRm,DRn PR=1 1111nnn0mmm00000 */
+INLINE void FADD(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ m = m & 14;
+ FP_RFD(n) = FP_RFD(n) + FP_RFD(m);
+ } else { /* PR = 0 */
+ FP_RFS(n) = FP_RFS(n) + FP_RFS(m);
+ }
+}
+
+/* FSUB FRm,FRn PR=0 1111nnnnmmmm0001 */
+/* FSUB DRm,DRn PR=1 1111nnn0mmm00001 */
+INLINE void FSUB(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ m = m & 14;
+ FP_RFD(n) = FP_RFD(n) - FP_RFD(m);
+ } else { /* PR = 0 */
+ FP_RFS(n) = FP_RFS(n) - FP_RFS(m);
+ }
+}
+
+
+/* FMUL FRm,FRn PR=0 1111nnnnmmmm0010 */
+/* FMUL DRm,DRn PR=1 1111nnn0mmm00010 */
+INLINE void FMUL(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ m = m & 14;
+ FP_RFD(n) = FP_RFD(n) * FP_RFD(m);
+ } else { /* PR = 0 */
+ FP_RFS(n) = FP_RFS(n) * FP_RFS(m);
+ }
+}
+
+/* FDIV FRm,FRn PR=0 1111nnnnmmmm0011 */
+/* FDIV DRm,DRn PR=1 1111nnn0mmm00011 */
+INLINE void FDIV(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ m = m & 14;
+ if (FP_RFD(m) == 0)
+ return;
+ FP_RFD(n) = FP_RFD(n) / FP_RFD(m);
+ } else { /* PR = 0 */
+ if (FP_RFS(m) == 0)
+ return;
+ FP_RFS(n) = FP_RFS(n) / FP_RFS(m);
+ }
+}
+
+/* FMAC FR0,FRm,FRn PR=0 1111nnnnmmmm1110 */
+INLINE void FMAC(UINT32 m,UINT32 n)
+{
+ if (sh4.fpu_pr == 0) { /* PR = 0 */
+ FP_RFS(n) = (FP_RFS(0) * FP_RFS(m)) + FP_RFS(n);
+ }
+}
+
+/* FSQRT FRn PR=0 1111nnnn01101101 */
+/* FSQRT DRn PR=1 1111nnnn01101101 */
+INLINE void FSQRT(UINT32 n)
+{
+ if (sh4.fpu_pr) { /* PR = 1 */
+ n = n & 14;
+ if (FP_RFD(n) < 0)
+ return;
+ FP_RFD(n) = sqrt(FP_RFD(n));
+ } else { /* PR = 0 */
+ if (FP_RFS(n) < 0)
+ return;
+ FP_RFS(n) = sqrt(FP_RFS(n));
+ }
+}
+
+/* FIPR FVm,FVn PR=0 1111nnmm11101101 */
+INLINE void FIPR(UINT32 n)
+{
+UINT32 m;
+float ml[4];
+int a;
+
+ m = (n & 3) << 2;
+ n = n & 12;
+ for (a = 0;a < 4;a++)
+ ml[a] = FP_RFS(n+a) * FP_RFS(m+a);
+ FP_RFS(n+3) = ml[0] + ml[1] + ml[2] + ml[3];
+}
+
+/* FTRV XMTRX,FVn PR=0 1111nn0111111101 */
+INLINE void FTRV(UINT32 n)
+{
+int i,j;
+float sum[4];
+
+ n = n & 12;
+ for (i = 0;i < 4;i++) {
+ sum[i] = 0;
+ for (j=0;j < 4;j++)
+ sum[i] += FP_XFS((j << 2) + i)*FP_RFS(n + i);
+ FP_RFS(n + i) = sum[i];
+ }
}
INLINE void op1111(UINT16 opcode)
@@ -2950,22 +3371,22 @@ INLINE void op1111(UINT16 opcode)
switch (opcode & 0xf)
{
case 0:
- TODO();
+ FADD(Rm,Rn);
break;
case 1:
- TODO();
+ FSUB(Rm,Rn);
break;
case 2:
- TODO();
+ FMUL(Rm,Rn);
break;
case 3:
- TODO();
+ FDIV(Rm,Rn);
break;
case 4:
- TODO();
+ FCMP_EQ(Rm,Rn);
break;
case 5:
- TODO();
+ FCMP_GT(Rm,Rn);
break;
case 6:
FMOVS0FR(Rm,Rn);
@@ -2986,31 +3407,31 @@ INLINE void op1111(UINT16 opcode)
FMOVFRMDR(Rm,Rn);
break;
case 12:
- TODO();
+ FMOVFR(Rm,Rn);
break;
case 13:
switch (opcode & 0xF0)
{
case 0x00:
- TODO();
+ FSTS(Rn);
break;
case 0x10:
- TODO();
+ FLDS(Rn);
break;
case 0x20:
- TODO();
+ FLOAT(Rn);
break;
case 0x30:
- TODO();
+ FTRC(Rn);
break;
case 0x40:
- TODO();
+ FNEG(Rn);
break;
case 0x50:
- TODO();
+ FABS(Rn);
break;
case 0x60:
- TODO();
+ FSQRT(Rn);
break;
case 0x80:
FLDI0(Rn);
@@ -3019,13 +3440,13 @@ INLINE void op1111(UINT16 opcode)
FLDI1(Rn);
break;
case 0xA0:
- TODO();
+ FCNVSD(Rn);
break;
case 0xB0:
- TODO();
+ FCNVDS(Rn);
break;
case 0xE0:
- TODO();
+ FIPR(Rn);
break;
case 0xF0:
if (opcode == 0xF3FD)
@@ -3033,12 +3454,12 @@ INLINE void op1111(UINT16 opcode)
else if (opcode == 0xFBFD)
FRCHG();
else if ((opcode & 0x300) == 0x100)
- TODO();
+ FTRV(Rn);
break;
}
break;
case 14:
- TODO();
+ FMAC(Rm,Rn);
break;
}
}
@@ -3113,6 +3534,8 @@ static void sh4_reset(void)
sh4.r[15] = RL(4);
sh4.sr = 0x700000f0;
sh4.fpscr = 0x00040001;
+ sh4.fpu_sz = (sh4.fpscr & SZ) ? 1 : 0;
+ sh4.fpu_pr = (sh4.fpscr & PR) ? 1 : 0;
sh4.fpul = 0;
sh4.dbr = 0;
change_pc(sh4.pc & AM);
@@ -3221,9 +3644,7 @@ UINT32 ticks;
INLINE attotime sh4_scale_up_mame_time(attotime _time1, UINT32 factor1)
{
- if (factor1 == 0)
- return attotime_zero;
- return attotime_mul(_time1, factor1 + 1);
+ return attotime_add(attotime_mul(_time1, factor1), _time1);
}
static UINT32 compute_ticks_timer(emu_timer *timer, int hertz, int divisor)
@@ -3499,7 +3920,7 @@ static int sh4_dma_transfer(int channel, int timermode, UINT32 chcr, UINT32 *sar
switch(size)
{
- case 1:
+ case 1: // 8 bit
for(;count > 0; count --)
{
if(incs == 2)
@@ -3513,7 +3934,7 @@ static int sh4_dma_transfer(int channel, int timermode, UINT32 chcr, UINT32 *sar
dst ++;
}
break;
- case 2:
+ case 2: // 16 bit
src &= ~1;
dst &= ~1;
for(;count > 0; count --)
@@ -3529,7 +3950,7 @@ static int sh4_dma_transfer(int channel, int timermode, UINT32 chcr, UINT32 *sar
dst += 2;
}
break;
- case 8:
+ case 8: // 64 bit
src &= ~7;
dst &= ~7;
for(;count > 0; count --)
@@ -3546,7 +3967,7 @@ static int sh4_dma_transfer(int channel, int timermode, UINT32 chcr, UINT32 *sar
}
break;
- case 4:
+ case 4: // 32 bit
src &= ~3;
dst &= ~3;
for(;count > 0; count --)
@@ -4307,7 +4728,7 @@ UINT32 pos,len,siz;
} else {
if ((s->direction) == 0) {
len = s->length;
- p32bits = (UINT32 *)(s->buffer);
+ p32bits = (UINT32 *)(s->buffer);
for (pos = 0;pos < len;pos++) {
*p32bits = program_read_dword_64le(s->source);
p32bits++;
@@ -4315,7 +4736,7 @@ UINT32 pos,len,siz;
}
} else {
len = s->length;
- p32bits = (UINT32 *)(s->buffer);
+ p32bits = (UINT32 *)(s->buffer);
for (pos = 0;pos < len;pos++) {
program_write_dword_64le(s->destination, *p32bits);
p32bits++;
@@ -4394,6 +4815,40 @@ static void sh4_set_info(UINT32 state, cpuinfo *info)
case CPUINFO_STR_REGISTER + SH4_SGR: sh4.sgr = info->i; break;
case CPUINFO_STR_REGISTER + SH4_FPSCR: sh4.fpscr = info->i; break;
case CPUINFO_STR_REGISTER + SH4_FPUL: sh4.fpul = info->i; break;
+#ifdef LSB_FIRST
+ case CPUINFO_STR_REGISTER + SH4_FR0: sh4.fr[ 0 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR1: sh4.fr[ 1 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR2: sh4.fr[ 2 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR3: sh4.fr[ 3 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR4: sh4.fr[ 4 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR5: sh4.fr[ 5 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR6: sh4.fr[ 6 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR7: sh4.fr[ 7 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR8: sh4.fr[ 8 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR9: sh4.fr[ 9 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR10: sh4.fr[10 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR11: sh4.fr[11 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR12: sh4.fr[12 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR13: sh4.fr[13 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR14: sh4.fr[14 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_FR15: sh4.fr[15 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF0: sh4.xf[ 0 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF1: sh4.xf[ 1 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF2: sh4.xf[ 2 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF3: sh4.xf[ 3 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF4: sh4.xf[ 4 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF5: sh4.xf[ 5 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF6: sh4.xf[ 6 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF7: sh4.xf[ 7 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF8: sh4.xf[ 8 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF9: sh4.xf[ 9 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF10: sh4.xf[10 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF11: sh4.xf[11 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF12: sh4.xf[12 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF13: sh4.xf[13 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF14: sh4.xf[14 ^ sh4.fpu_pr] = info->i; break;
+ case CPUINFO_STR_REGISTER + SH4_XF15: sh4.xf[15 ^ sh4.fpu_pr] = info->i; break;
+#else
case CPUINFO_STR_REGISTER + SH4_FR0: sh4.fr[ 0] = info->i; break;
case CPUINFO_STR_REGISTER + SH4_FR1: sh4.fr[ 1] = info->i; break;
case CPUINFO_STR_REGISTER + SH4_FR2: sh4.fr[ 2] = info->i; break;
@@ -4426,6 +4881,7 @@ static void sh4_set_info(UINT32 state, cpuinfo *info)
case CPUINFO_STR_REGISTER + SH4_XF13: sh4.xf[13] = info->i; break;
case CPUINFO_STR_REGISTER + SH4_XF14: sh4.xf[14] = info->i; break;
case CPUINFO_STR_REGISTER + SH4_XF15: sh4.xf[15] = info->i; break;
+#endif
case CPUINFO_INT_SH4_IRLn_INPUT: sh4_set_irln_input(cpu_getactivecpu(), info->i); break;
case CPUINFO_INT_SH4_FRT_INPUT: sh4_set_frt_input(cpu_getactivecpu(), info->i); break;
@@ -4599,38 +5055,73 @@ void sh4_get_info(UINT32 state, cpuinfo *info)
case CPUINFO_STR_REGISTER + SH4_SGR: sprintf(info->s, "SGR :%08X", sh4.sgr); break;
case CPUINFO_STR_REGISTER + SH4_FPSCR: sprintf(info->s, "FPSCR :%08X", sh4.fpscr); break;
case CPUINFO_STR_REGISTER + SH4_FPUL: sprintf(info->s, "FPUL :%08X", sh4.fpul); break;
- case CPUINFO_STR_REGISTER + SH4_FR0: sprintf(info->s, "FR0 :%08X", sh4.fr[ 0]); break;
- case CPUINFO_STR_REGISTER + SH4_FR1: sprintf(info->s, "FR1 :%08X", sh4.fr[ 1]); break;
- case CPUINFO_STR_REGISTER + SH4_FR2: sprintf(info->s, "FR2 :%08X", sh4.fr[ 2]); break;
- case CPUINFO_STR_REGISTER + SH4_FR3: sprintf(info->s, "FR3 :%08X", sh4.fr[ 3]); break;
- case CPUINFO_STR_REGISTER + SH4_FR4: sprintf(info->s, "FR4 :%08X", sh4.fr[ 4]); break;
- case CPUINFO_STR_REGISTER + SH4_FR5: sprintf(info->s, "FR5 :%08X", sh4.fr[ 5]); break;
- case CPUINFO_STR_REGISTER + SH4_FR6: sprintf(info->s, "FR6 :%08X", sh4.fr[ 6]); break;
- case CPUINFO_STR_REGISTER + SH4_FR7: sprintf(info->s, "FR7 :%08X", sh4.fr[ 7]); break;
- case CPUINFO_STR_REGISTER + SH4_FR8: sprintf(info->s, "FR8 :%08X", sh4.fr[ 8]); break;
- case CPUINFO_STR_REGISTER + SH4_FR9: sprintf(info->s, "FR9 :%08X", sh4.fr[ 9]); break;
- case CPUINFO_STR_REGISTER + SH4_FR10: sprintf(info->s, "FR10 :%08X", sh4.fr[10]); break;
- case CPUINFO_STR_REGISTER + SH4_FR11: sprintf(info->s, "FR11 :%08X", sh4.fr[11]); break;
- case CPUINFO_STR_REGISTER + SH4_FR12: sprintf(info->s, "FR12 :%08X", sh4.fr[12]); break;
- case CPUINFO_STR_REGISTER + SH4_FR13: sprintf(info->s, "FR13 :%08X", sh4.fr[13]); break;
- case CPUINFO_STR_REGISTER + SH4_FR14: sprintf(info->s, "FR14 :%08X", sh4.fr[14]); break;
- case CPUINFO_STR_REGISTER + SH4_FR15: sprintf(info->s, "FR15 :%08X", sh4.fr[15]); break;
- case CPUINFO_STR_REGISTER + SH4_XF0: sprintf(info->s, "XF0 :%08X", sh4.xf[ 0]); break;
- case CPUINFO_STR_REGISTER + SH4_XF1: sprintf(info->s, "XF1 :%08X", sh4.xf[ 1]); break;
- case CPUINFO_STR_REGISTER + SH4_XF2: sprintf(info->s, "XF2 :%08X", sh4.xf[ 2]); break;
- case CPUINFO_STR_REGISTER + SH4_XF3: sprintf(info->s, "XF3 :%08X", sh4.xf[ 3]); break;
- case CPUINFO_STR_REGISTER + SH4_XF4: sprintf(info->s, "XF4 :%08X", sh4.xf[ 4]); break;
- case CPUINFO_STR_REGISTER + SH4_XF5: sprintf(info->s, "XF5 :%08X", sh4.xf[ 5]); break;
- case CPUINFO_STR_REGISTER + SH4_XF6: sprintf(info->s, "XF6 :%08X", sh4.xf[ 6]); break;
- case CPUINFO_STR_REGISTER + SH4_XF7: sprintf(info->s, "XF7 :%08X", sh4.xf[ 7]); break;
- case CPUINFO_STR_REGISTER + SH4_XF8: sprintf(info->s, "XF8 :%08X", sh4.xf[ 8]); break;
- case CPUINFO_STR_REGISTER + SH4_XF9: sprintf(info->s, "XF9 :%08X", sh4.xf[ 9]); break;
- case CPUINFO_STR_REGISTER + SH4_XF10: sprintf(info->s, "XF10 :%08X", sh4.xf[10]); break;
- case CPUINFO_STR_REGISTER + SH4_XF11: sprintf(info->s, "XF11 :%08X", sh4.xf[11]); break;
- case CPUINFO_STR_REGISTER + SH4_XF12: sprintf(info->s, "XF12 :%08X", sh4.xf[12]); break;
- case CPUINFO_STR_REGISTER + SH4_XF13: sprintf(info->s, "XF13 :%08X", sh4.xf[13]); break;
- case CPUINFO_STR_REGISTER + SH4_XF14: sprintf(info->s, "XF14 :%08X", sh4.xf[14]); break;
- case CPUINFO_STR_REGISTER + SH4_XF15: sprintf(info->s, "XF15 :%08X", sh4.xf[15]); break;
+#ifdef LSB_FIRST
+ case CPUINFO_STR_REGISTER + SH4_FR0: sprintf(info->s, "FR0 :%08X %01.4e", FP_RS2( 0),(double)FP_RFS2( 0)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR1: sprintf(info->s, "FR1 :%08X %01.2e", FP_RS2( 1),(double)FP_RFS2( 1)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR2: sprintf(info->s, "FR2 :%08X %01.2e", FP_RS2( 2),(double)FP_RFS2( 2)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR3: sprintf(info->s, "FR3 :%08X %01.2e", FP_RS2( 3),(double)FP_RFS2( 3)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR4: sprintf(info->s, "FR4 :%08X %01.2e", FP_RS2( 4),(double)FP_RFS2( 4)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR5: sprintf(info->s, "FR5 :%08X %01.2e", FP_RS2( 5),(double)FP_RFS2( 5)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR6: sprintf(info->s, "FR6 :%08X %01.2e", FP_RS2( 6),(double)FP_RFS2( 6)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR7: sprintf(info->s, "FR7 :%08X %01.2e", FP_RS2( 7),(double)FP_RFS2( 7)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR8: sprintf(info->s, "FR8 :%08X %01.2e", FP_RS2( 8),(double)FP_RFS2( 8)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR9: sprintf(info->s, "FR9 :%08X %01.2e", FP_RS2( 9),(double)FP_RFS2( 9)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR10: sprintf(info->s, "FR10 :%08X %01.2e", FP_RS2(10),(double)FP_RFS2(10)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR11: sprintf(info->s, "FR11 :%08X %01.2e", FP_RS2(11),(double)FP_RFS2(11)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR12: sprintf(info->s, "FR12 :%08X %01.2e", FP_RS2(12),(double)FP_RFS2(12)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR13: sprintf(info->s, "FR13 :%08X %01.2e", FP_RS2(13),(double)FP_RFS2(13)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR14: sprintf(info->s, "FR14 :%08X %01.2e", FP_RS2(14),(double)FP_RFS2(14)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR15: sprintf(info->s, "FR15 :%08X %01.2e", FP_RS2(15),(double)FP_RFS2(15)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF0: sprintf(info->s, "XF0 :%08X %01.2e", FP_XS2( 0),(double)FP_XFS2( 0)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF1: sprintf(info->s, "XF1 :%08X %01.2e", FP_XS2( 1),(double)FP_XFS2( 1)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF2: sprintf(info->s, "XF2 :%08X %01.2e", FP_XS2( 2),(double)FP_XFS2( 2)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF3: sprintf(info->s, "XF3 :%08X %01.2e", FP_XS2( 3),(double)FP_XFS2( 3)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF4: sprintf(info->s, "XF4 :%08X %01.2e", FP_XS2( 4),(double)FP_XFS2( 4)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF5: sprintf(info->s, "XF5 :%08X %01.2e", FP_XS2( 5),(double)FP_XFS2( 5)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF6: sprintf(info->s, "XF6 :%08X %01.2e", FP_XS2( 6),(double)FP_XFS2( 6)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF7: sprintf(info->s, "XF7 :%08X %01.2e", FP_XS2( 7),(double)FP_XFS2( 7)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF8: sprintf(info->s, "XF8 :%08X %01.2e", FP_XS2( 8),(double)FP_XFS2( 8)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF9: sprintf(info->s, "XF9 :%08X %01.2e", FP_XS2( 9),(double)FP_XFS2( 9)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF10: sprintf(info->s, "XF10 :%08X %01.2e", FP_XS2(10),(double)FP_XFS2(10)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF11: sprintf(info->s, "XF11 :%08X %01.2e", FP_XS2(11),(double)FP_XFS2(11)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF12: sprintf(info->s, "XF12 :%08X %01.2e", FP_XS2(12),(double)FP_XFS2(12)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF13: sprintf(info->s, "XF13 :%08X %01.2e", FP_XS2(13),(double)FP_XFS2(13)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF14: sprintf(info->s, "XF14 :%08X %01.2e", FP_XS2(14),(double)FP_XFS2(14)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF15: sprintf(info->s, "XF15 :%08X %01.2e", FP_XS2(15),(double)FP_XFS2(15)); break;
+#else
+ case CPUINFO_STR_REGISTER + SH4_FR0: sprintf(info->s, "FR0 :%08X %01.4e", FP_RS( 0),(double)FP_RFS( 0)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR1: sprintf(info->s, "FR1 :%08X %01.2e", FP_RS( 1),(double)FP_RFS( 1)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR2: sprintf(info->s, "FR2 :%08X %01.2e", FP_RS( 2),(double)FP_RFS( 2)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR3: sprintf(info->s, "FR3 :%08X %01.2e", FP_RS( 3),(double)FP_RFS( 3)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR4: sprintf(info->s, "FR4 :%08X %01.2e", FP_RS( 4),(double)FP_RFS( 4)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR5: sprintf(info->s, "FR5 :%08X %01.2e", FP_RS( 5),(double)FP_RFS( 5)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR6: sprintf(info->s, "FR6 :%08X %01.2e", FP_RS( 6),(double)FP_RFS( 6)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR7: sprintf(info->s, "FR7 :%08X %01.2e", FP_RS( 7),(double)FP_RFS( 7)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR8: sprintf(info->s, "FR8 :%08X %01.2e", FP_RS( 8),(double)FP_RFS( 8)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR9: sprintf(info->s, "FR9 :%08X %01.2e", FP_RS( 9),(double)FP_RFS( 9)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR10: sprintf(info->s, "FR10 :%08X %01.2e", FP_RS(10),(double)FP_RFS(10)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR11: sprintf(info->s, "FR11 :%08X %01.2e", FP_RS(11),(double)FP_RFS(11)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR12: sprintf(info->s, "FR12 :%08X %01.2e", FP_RS(12),(double)FP_RFS(12)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR13: sprintf(info->s, "FR13 :%08X %01.2e", FP_RS(13),(double)FP_RFS(13)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR14: sprintf(info->s, "FR14 :%08X %01.2e", FP_RS(14),(double)FP_RFS(14)); break;
+ case CPUINFO_STR_REGISTER + SH4_FR15: sprintf(info->s, "FR15 :%08X %01.2e", FP_RS(15),(double)FP_RFS(15)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF0: sprintf(info->s, "XF0 :%08X %01.2e", FP_XS( 0),(double)FP_XFS( 0)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF1: sprintf(info->s, "XF1 :%08X %01.2e", FP_XS( 1),(double)FP_XFS( 1)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF2: sprintf(info->s, "XF2 :%08X %01.2e", FP_XS( 2),(double)FP_XFS( 2)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF3: sprintf(info->s, "XF3 :%08X %01.2e", FP_XS( 3),(double)FP_XFS( 3)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF4: sprintf(info->s, "XF4 :%08X %01.2e", FP_XS( 4),(double)FP_XFS( 4)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF5: sprintf(info->s, "XF5 :%08X %01.2e", FP_XS( 5),(double)FP_XFS( 5)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF6: sprintf(info->s, "XF6 :%08X %01.2e", FP_XS( 6),(double)FP_XFS( 6)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF7: sprintf(info->s, "XF7 :%08X %01.2e", FP_XS( 7),(double)FP_XFS( 7)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF8: sprintf(info->s, "XF8 :%08X %01.2e", FP_XS( 8),(double)FP_XFS( 8)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF9: sprintf(info->s, "XF9 :%08X %01.2e", FP_XS( 9),(double)FP_XFS( 9)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF10: sprintf(info->s, "XF10 :%08X %01.2e", FP_XS(10),(double)FP_XFS(10)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF11: sprintf(info->s, "XF11 :%08X %01.2e", FP_XS(11),(double)FP_XFS(11)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF12: sprintf(info->s, "XF12 :%08X %01.2e", FP_XS(12),(double)FP_XFS(12)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF13: sprintf(info->s, "XF13 :%08X %01.2e", FP_XS(13),(double)FP_XFS(13)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF14: sprintf(info->s, "XF14 :%08X %01.2e", FP_XS(14),(double)FP_XFS(14)); break;
+ case CPUINFO_STR_REGISTER + SH4_XF15: sprintf(info->s, "XF15 :%08X %01.2e", FP_XS(15),(double)FP_XFS(15)); break;
+#endif
case CPUINFO_PTR_SH4_FTCSR_READ_CALLBACK: info->f = (genf*)sh4.ftcsr_read_callback; break;
}
diff --git a/src/emu/cpu/sh4/sh4dasm.c b/src/emu/cpu/sh4/sh4dasm.c
index 6a33d45f101..1b8ece6dee7 100644
--- a/src/emu/cpu/sh4/sh4dasm.c
+++ b/src/emu/cpu/sh4/sh4dasm.c
@@ -543,7 +543,7 @@ static UINT32 op1000(char *buffer, UINT32 pc, UINT16 opcode)
sprintf(buffer, "MOV.B @($%02X,%s),R0", (opcode & 15), regname[Rm]);
break;
case 5:
- sprintf(buffer, "MOV.W @($%02X,%s),R0", (opcode & 15), regname[Rm]);
+ sprintf(buffer, "MOV.W @($%02X,%s),R0", (opcode & 15) * 2, regname[Rm]);
break;
case 8:
sprintf(buffer, "CMP/EQ #$%02X,R0", (opcode & 0xff));