aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJoão Silva2017-02-12 02:40:43 +0000
committerJoão Silva2017-02-12 02:40:43 +0000
commitae5fb3ae9006d90c32cba9efad3dd1645972117a (patch)
treecddb693fc5c982294a48c086c655d02c180c596d
parent3777d1fcf4232cde426f46b7ee5c374fd949b1b0 (diff)
downloadsnesemu-ae5fb3ae9006d90c32cba9efad3dd1645972117a.tar.gz
snesemu-ae5fb3ae9006d90c32cba9efad3dd1645972117a.tar.bz2
snesemu-ae5fb3ae9006d90c32cba9efad3dd1645972117a.zip
Integer-only C4 from snes9x2002. Integer-only, finalized DSP1 from snes9x 1.50. Integer-only libretro.c and seta010.c.
-rw-r--r--libretro.c16
-rw-r--r--source/c4.c211
-rw-r--r--source/c4.h6
-rw-r--r--source/c4emu.c369
-rw-r--r--source/dsp1.c4
-rw-r--r--source/dsp1emu.c453
-rw-r--r--source/globals.c61
-rw-r--r--source/port.h33
-rw-r--r--source/seta010.c84
9 files changed, 605 insertions, 632 deletions
diff --git a/libretro.c b/libretro.c
index 53c652e..f2056b9 100644
--- a/libretro.c
+++ b/libretro.c
@@ -43,8 +43,8 @@ char slash = '\\';
char slash = '/';
#endif
-static float samples_per_frame = 0.0;
-static float samplerate = (((SNES_CLOCK_SPEED * 6) / (32 * ONE_APU_CYCLE)));
+static int32_t samples_per_frame = 0;
+static int32_t samplerate = (((SNES_CLOCK_SPEED * 6) / (32 * ONE_APU_CYCLE)));
#ifdef PERF_TEST
#define RETRO_PERFORMANCE_INIT(name) \
@@ -400,7 +400,7 @@ static void check_variables(void)
#define FRAMESKIP
#endif
-static float samples_to_play = 0.0;
+static int32_t samples_to_play = 0;
void retro_run(void)
{
bool updated = false;
@@ -427,13 +427,13 @@ void retro_run(void)
if (samples_to_play > 512)
{
- S9xMixSamples(audio_buf, ((int32_t)samples_to_play) * 2);
- audio_batch_cb(audio_buf, (int32_t)samples_to_play);
- samples_to_play -= (int32_t)samples_to_play;
+ S9xMixSamples(audio_buf, samples_to_play * 2);
+ audio_batch_cb(audio_buf, samples_to_play);
+ samples_to_play = 0;
}
#endif
-#ifdef NO_VIDEO_OUTPUT
+#ifdef NO_VIDEO_OUTPUT
return;
#endif
@@ -767,7 +767,7 @@ void retro_cheat_set(unsigned index, bool enabled, const char* code)
Cheat.c[index].saved = false; // it'll be saved next time cheats run anyways
- Settings.ApplyCheats=true;
+ Settings.ApplyCheats = true;
S9xApplyCheats();
#endif
}
diff --git a/source/c4.c b/source/c4.c
index 65d4c01..9519cc3 100644
--- a/source/c4.c
+++ b/source/c4.c
@@ -3,7 +3,7 @@
#include <math.h>
#include <stdlib.h>
#include "c4.h"
-#include "memmap.h"
+#include "port.h"
int16_t C4WFXVal;
int16_t C4WFYVal;
@@ -13,70 +13,174 @@ int16_t C4WFY2Val;
int16_t C4WFDist;
int16_t C4WFScale;
-static double tanval;
-static double c4x, c4y, c4z;
-static double c4x2, c4y2, c4z2;
+int32_t tanval;
+static int32_t c4x, c4y, c4z;
+static int32_t c4x2, c4y2, c4z2;
+
+const int16_t C4MulTable[256] =
+{
+ 0x0000, 0x0003, 0x0006, 0x0009, 0x000c, 0x000f, 0x0012, 0x0015,
+ 0x0019, 0x001c, 0x001f, 0x0022, 0x0025, 0x0028, 0x002b, 0x002f,
+ 0x0032, 0x0035, 0x0038, 0x003b, 0x003e, 0x0041, 0x0045, 0x0048,
+ 0x004b, 0x004e, 0x0051, 0x0054, 0x0057, 0x005b, 0x005e, 0x0061,
+ 0x0064, 0x0067, 0x006a, 0x006d, 0x0071, 0x0074, 0x0077, 0x007a,
+ 0x007d, 0x0080, 0x0083, 0x0087, 0x008a, 0x008d, 0x0090, 0x0093,
+ 0x0096, 0x0099, 0x009d, 0x00a0, 0x00a3, 0x00a6, 0x00a9, 0x00ac,
+ 0x00af, 0x00b3, 0x00b6, 0x00b9, 0x00bc, 0x00bf, 0x00c2, 0x00c5,
+ 0x00c9, 0x00cc, 0x00cf, 0x00d2, 0x00d5, 0x00d8, 0x00db, 0x00df,
+ 0x00e2, 0x00e5, 0x00e8, 0x00eb, 0x00ee, 0x00f1, 0x00f5, 0x00f8,
+ 0x00fb, 0x00fe, 0x0101, 0x0104, 0x0107, 0x010b, 0x010e, 0x0111,
+ 0x0114, 0x0117, 0x011a, 0x011d, 0x0121, 0x0124, 0x0127, 0x012a,
+ 0x012d, 0x0130, 0x0133, 0x0137, 0x013a, 0x013d, 0x0140, 0x0143,
+ 0x0146, 0x0149, 0x014d, 0x0150, 0x0153, 0x0156, 0x0159, 0x015c,
+ 0x015f, 0x0163, 0x0166, 0x0169, 0x016c, 0x016f, 0x0172, 0x0175,
+ 0x0178, 0x017c, 0x017f, 0x0182, 0x0185, 0x0188, 0x018b, 0x018e,
+ 0x0192, 0x0195, 0x0198, 0x019b, 0x019e, 0x01a1, 0x01a4, 0x01a8,
+ 0x01ab, 0x01ae, 0x01b1, 0x01b4, 0x01b7, 0x01ba, 0x01be, 0x01c1,
+ 0x01c4, 0x01c7, 0x01ca, 0x01cd, 0x01d0, 0x01d4, 0x01d7, 0x01da,
+ 0x01dd, 0x01e0, 0x01e3, 0x01e6, 0x01ea, 0x01ed, 0x01f0, 0x01f3,
+ 0x01f6, 0x01f9, 0x01fc, 0x0200, 0x0203, 0x0206, 0x0209, 0x020c,
+ 0x020f, 0x0212, 0x0216, 0x0219, 0x021c, 0x021f, 0x0222, 0x0225,
+ 0x0228, 0x022c, 0x022f, 0x0232, 0x0235, 0x0238, 0x023b, 0x023e,
+ 0x0242, 0x0245, 0x0248, 0x024b, 0x024e, 0x0251, 0x0254, 0x0258,
+ 0x025b, 0x025e, 0x0261, 0x0264, 0x0267, 0x026a, 0x026e, 0x0271,
+ 0x0274, 0x0277, 0x027a, 0x027d, 0x0280, 0x0284, 0x0287, 0x028a,
+ 0x028d, 0x0290, 0x0293, 0x0296, 0x029a, 0x029d, 0x02a0, 0x02a3,
+ 0x02a6, 0x02a9, 0x02ac, 0x02b0, 0x02b3, 0x02b6, 0x02b9, 0x02bc,
+ 0x02bf, 0x02c2, 0x02c6, 0x02c9, 0x02cc, 0x02cf, 0x02d2, 0x02d5,
+ 0x02d8, 0x02db, 0x02df, 0x02e2, 0x02e5, 0x02e8, 0x02eb, 0x02ee,
+ 0x02f1, 0x02f5, 0x02f8, 0x02fb, 0x02fe, 0x0301, 0x0304, 0x0307,
+ 0x030b, 0x030e, 0x0311, 0x0314, 0x0317, 0x031a, 0x031d, 0x0321
+};
+
+int16_t C4_Sin(int16_t Angle)
+{
+ if (Angle < 0)
+ {
+ if (Angle == -32768)
+ return 0;
+ return -C4_Sin(-Angle);
+ }
+ int16_t AngleS7 = Angle >> 7;
+ int32_t S = C4SinTable[AngleS7] + (C4MulTable[Angle & 0xff] * C4SinTable[0x80 + AngleS7] >> 15);
+ if (S > 32767)
+ S = 32767;
+ return (int16_t) S;
+}
+
+int16_t C4_Cos(int16_t Angle)
+{
+ if (Angle < 0)
+ {
+ if (Angle == -32768)
+ return -32768;
+ Angle = -Angle;
+ }
+ int16_t AngleS7 = Angle >> 7;
+ int32_t S = C4SinTable[0x80 + AngleS7] - (C4MulTable[Angle & 0xff] * C4SinTable[AngleS7] >> 15);
+ if (S < -32768)
+ S = -32767;
+ return (int16_t) S;
+}
+
+const int16_t atantbl[256] = {
+ 0, 1, 1, 2, 3, 3, 4, 4, 5, 6, 6, 7, 8, 8, 9, 10,
+ 10, 11, 11, 12, 13, 13, 14, 15, 15, 16, 16, 17, 18, 18, 19, 20,
+ 20, 21, 21, 22, 23, 23, 24, 25, 25, 26, 26, 27, 28, 28, 29, 29,
+ 30, 31, 31, 32, 33, 33, 34, 34, 35, 36, 36, 37, 37, 38, 39, 39,
+ 40, 40, 41, 42, 42, 43, 43, 44, 44, 45, 46, 46, 47, 47, 48, 49,
+ 49, 50, 50, 51, 51, 52, 53, 53, 54, 54, 55, 55, 56, 57, 57, 58,
+ 58, 59, 59, 60, 60, 61, 62, 62, 63, 63, 64, 64, 65, 65, 66, 66,
+ 67, 67, 68, 69, 69, 70, 70, 71, 71, 72, 72, 73, 73, 74, 74, 75,
+ 75, 76, 76, 77, 77, 78, 78, 79, 79, 80, 80, 81, 81, 82, 82, 83,
+ 83, 84, 84, 85, 85, 86, 86, 86, 87, 87, 88, 88, 89, 89, 90, 90,
+ 91, 91, 92, 92, 92, 93, 93, 94, 94, 95, 95, 96, 96, 96, 97, 97,
+ 98, 98, 99, 99, 99, 100, 100, 101, 101, 101, 102, 102, 103, 103, 104, 104,
+ 104, 105, 105, 106, 106, 106, 107, 107, 108, 108, 108, 109, 109, 109, 110, 110,
+ 111, 111, 111, 112, 112, 113, 113, 113, 114, 114, 114, 115, 115, 115, 116, 116,
+ 117, 117, 117, 118, 118, 118, 119, 119, 119, 120, 120, 120, 121, 121, 121, 122,
+ 122, 122, 123, 123, 123, 124, 124, 124, 125, 125, 125, 126, 126, 126, 127, 127
+};
+
+int16_t _atan2(int16_t x, int16_t y)
+{
+ if (x == 0)
+ return 0;
+
+ int32_t x1 = ABS(x), y1 = ABS(y);
+ int32_t absAtan;
+
+ if (x1 > y1)
+ absAtan = atantbl[(unsigned char)((y1 << 8) / x1)];
+ else
+ absAtan = atantbl[(unsigned char)((x1 << 8) / y1)];
+
+ if ((x >= 0) ^ (y >= 0))
+ return -absAtan;
+
+ return absAtan;
+}
void C4TransfWireFrame()
{
- c4x = (double) C4WFXVal;
- c4y = (double) C4WFYVal;
- c4z = (double) C4WFZVal - 0x95;
+ c4x = C4WFXVal;
+ c4y = C4WFYVal;
+ c4z = C4WFZVal - 0x95;
// Rotate X
- tanval = -(double) C4WFX2Val * 3.14159265 * 2 / 128;
- c4y2 = c4y * cos(tanval) - c4z * sin(tanval);
- c4z2 = c4y * sin(tanval) + c4z * cos(tanval);
+ tanval = -C4WFX2Val << 9;
+ c4y2 = (c4y * C4_Cos(tanval) - c4z * C4_Sin(tanval)) >> 15;
+ c4z2 = (c4y * C4_Sin(tanval) + c4z * C4_Cos(tanval)) >> 15;
// Rotate Y
- tanval = -(double)C4WFY2Val * 3.14159265 * 2 / 128;
- c4x2 = c4x * cos(tanval) + c4z2 * sin(tanval);
- c4z = c4x * - sin(tanval) + c4z2 * cos(tanval);
+ tanval = -C4WFY2Val << 9;
+ c4x2 = (c4x * C4_Cos(tanval) + c4z2 * C4_Sin(tanval)) >> 15;
+ c4z = (c4x * -C4_Sin(tanval) + c4z2 * C4_Cos(tanval)) >> 15;
// Rotate Z
- tanval = -(double) C4WFDist * 3.14159265 * 2 / 128;
- c4x = c4x2 * cos(tanval) - c4y2 * sin(tanval);
- c4y = c4x2 * sin(tanval) + c4y2 * cos(tanval);
+ tanval = -C4WFDist << 9;
+ c4x = (c4x2 * C4_Cos(tanval) - c4y2 * C4_Sin(tanval)) >> 15;
+ c4y = (c4x2 * C4_Sin(tanval) + c4y2 * C4_Cos(tanval)) >> 15;
// Scale
- C4WFXVal = (int16_t)(c4x * (double)C4WFScale / (0x90 * (c4z + 0x95)) * 0x95);
- C4WFYVal = (int16_t)(c4y * (double)C4WFScale / (0x90 * (c4z + 0x95)) * 0x95);
+ C4WFXVal = (int16_t)(((int32_t)c4x * C4WFScale * 0x95) / (0x90 * (c4z + 0x95)));
+ C4WFYVal = (int16_t)(((int32_t)c4y * C4WFScale * 0x95) / (0x90 * (c4z + 0x95)));
}
void C4TransfWireFrame2()
{
- c4x = (double)C4WFXVal;
- c4y = (double)C4WFYVal;
- c4z = (double)C4WFZVal;
+ c4x = C4WFXVal;
+ c4y = C4WFYVal;
+ c4z = C4WFZVal;
// Rotate X
- tanval = -(double) C4WFX2Val * 3.14159265 * 2 / 128;
- c4y2 = c4y * cos(tanval) - c4z * sin(tanval);
- c4z2 = c4y * sin(tanval) + c4z * cos(tanval);
+ tanval = -C4WFX2Val << 9;
+ c4y2 = (c4y * C4_Cos(tanval) - c4z * C4_Sin(tanval)) >> 15;
+ c4z2 = (c4y * C4_Sin(tanval) + c4z * C4_Cos(tanval)) >> 15;
// Rotate Y
- tanval = -(double) C4WFY2Val * 3.14159265 * 2 / 128;
- c4x2 = c4x * cos(tanval) + c4z2 * sin(tanval);
- c4z = c4x * -sin(tanval) + c4z2 * cos(tanval);
+ tanval = -C4WFY2Val << 9;
+ c4x2 = (c4x * C4_Cos(tanval) + c4z2 * C4_Sin(tanval)) >> 15;
+ c4z = (c4x * -C4_Sin(tanval) + c4z2 * C4_Cos(tanval)) >> 15;
// Rotate Z
- tanval = -(double)C4WFDist * 3.14159265 * 2 / 128;
- c4x = c4x2 * cos(tanval) - c4y2 * sin(tanval);
- c4y = c4x2 * sin(tanval) + c4y2 * cos(tanval);
+ tanval = -C4WFDist << 9;
+ c4x = (c4x2 * C4_Cos(tanval) - c4y2 * C4_Sin(tanval)) >> 15;
+ c4y = (c4x2 * C4_Sin(tanval) + c4y2 * C4_Cos(tanval)) >> 15;
// Scale
- C4WFXVal = (int16_t)(c4x * (double)C4WFScale / 0x100);
- C4WFYVal = (int16_t)(c4y * (double)C4WFScale / 0x100);
+ C4WFXVal = (int16_t)(((int32_t)c4x * C4WFScale) / 0x100);
+ C4WFYVal = (int16_t)(((int32_t)c4y * C4WFScale) / 0x100);
}
void C4CalcWireFrame()
{
C4WFXVal = C4WFX2Val - C4WFXVal;
C4WFYVal = C4WFY2Val - C4WFYVal;
- if (abs(C4WFXVal) > abs(C4WFYVal))
+ if (ABS(C4WFXVal) > ABS(C4WFYVal))
{
- C4WFDist = abs(C4WFXVal) + 1;
- C4WFYVal = (int16_t)(256 * (double) C4WFYVal / abs(C4WFXVal));
+ C4WFDist = ABS(C4WFXVal) + 1;
+ C4WFYVal = (int16_t)(((int32_t)C4WFYVal << 8) / ABS(C4WFXVal));
if (C4WFXVal < 0)
C4WFXVal = -256;
else
@@ -86,8 +190,8 @@ void C4CalcWireFrame()
{
if (C4WFYVal != 0)
{
- C4WFDist = abs(C4WFYVal) + 1;
- C4WFXVal = (int16_t)(256 * (double)C4WFXVal / abs(C4WFYVal));
+ C4WFDist = ABS(C4WFYVal) + 1;
+ C4WFXVal = (int16_t)(((int32_t)C4WFXVal << 8) / ABS(C4WFYVal));
if (C4WFYVal < 0)
C4WFYVal = -256;
else
@@ -103,36 +207,3 @@ int16_t C41FYVal;
int16_t C41FAngleRes;
int16_t C41FDist;
int16_t C41FDistVal;
-
-void C4Op1F()
-{
- if (C41FXVal == 0)
- {
- if (C41FYVal > 0)
- C41FAngleRes = 0x80;
- else
- C41FAngleRes = 0x180;
- }
- else
- {
- tanval = (double) C41FYVal / C41FXVal;
- C41FAngleRes = (int16_t)(atan(tanval) / (3.141592675 * 2) * 512);
- if (C41FXVal < 0)
- C41FAngleRes += 0x100;
- C41FAngleRes &= 0x1FF;
- }
-}
-
-void C4Op15()
-{
- tanval = sqrt((double) C41FYVal * C41FYVal + (double) C41FXVal * C41FXVal);
- C41FDist = (int16_t) tanval;
-}
-
-void C4Op0D()
-{
- tanval = sqrt((double) C41FYVal * C41FYVal + (double) C41FXVal * C41FXVal);
- tanval = C41FDistVal / tanval;
- C41FYVal = (int16_t)(C41FYVal * tanval * 0.99);
- C41FXVal = (int16_t)(C41FXVal * tanval * 0.98);
-}
diff --git a/source/c4.h b/source/c4.h
index 590ead0..7ab3964 100644
--- a/source/c4.h
+++ b/source/c4.h
@@ -23,9 +23,9 @@ extern int16_t C41FAngleRes;
extern int16_t C41FDist;
extern int16_t C41FDistVal;
-void C4Op1F();
-void C4Op15();
-void C4Op0D();
+extern int32_t tanval;
+
+int16_t _atan2(int16_t x, int16_t y);
extern int16_t C4CosTable[];
extern int16_t C4SinTable[];
diff --git a/source/c4emu.c b/source/c4emu.c
index a6baecf..0cfb3aa 100644
--- a/source/c4emu.c
+++ b/source/c4emu.c
@@ -12,11 +12,13 @@
void S9xInitC4()
{
- memset(Memory.C4RAM, 0, 0x2000);
+ Memory.C4RAM = &Memory.FillRAM [0x6000];
}
uint8_t S9xGetC4(uint16_t Address)
{
+ if (Address == 0x7f5e)
+ return 0;
return (Memory.C4RAM [Address - 0x6000]);
}
@@ -37,15 +39,12 @@ static uint8_t C4TestPattern [12 * 4] =
};
-static void C4ConvOAM(void)
+static void C4ConvOAM()
{
uint8_t* i;
uint8_t* OAMptr = Memory.C4RAM + (Memory.C4RAM[0x626] << 2);
for (i = Memory.C4RAM + 0x1fd; i > OAMptr; i -= 4)
- {
- // Clear OAM-to-be
- *i = 0xe0;
- }
+ *i = 0xe0; // Clear OAM-to-be
uint16_t globalX, globalY;
uint8_t* OAMptr2;
@@ -67,7 +66,8 @@ static void C4ConvOAM(void)
uint8_t* srcptr = Memory.C4RAM + 0x220;
for (i = Memory.C4RAM[0x0620]; i > 0 && SprCount > 0; i--, srcptr += 16)
{
- if ((srcptr[4] & 0x30) != prio) continue;
+ if ((srcptr[4] & 0x30) != prio)
+ continue;
SprX = READ_WORD(srcptr) - globalX;
SprY = READ_WORD(srcptr + 2) - globalY;
SprName = srcptr[5];
@@ -97,12 +97,15 @@ static void C4ConvOAM(void)
OAMptr[2] = SprName + sprptr[3];
OAMptr[3] = SprAttr ^ (sprptr[0] & 0xc0); // XXX: Carry from SprName addition?
*OAMptr2 &= ~(3 << offset);
- if (X & 0x100) *OAMptr2 |= 1 << offset;
- if (sprptr[0] & 0x20) *OAMptr2 |= 2 << offset;
+ if (X & 0x100)
+ *OAMptr2 |= 1 << offset;
+ if (sprptr[0] & 0x20)
+ *OAMptr2 |= 2 << offset;
OAMptr += 4;
SprCount--;
offset = (offset + 2) & 6;
- if (offset == 0) OAMptr2++;
+ if (offset == 0)
+ OAMptr2++;
}
}
}
@@ -114,17 +117,19 @@ static void C4ConvOAM(void)
OAMptr[2] = SprName;
OAMptr[3] = SprAttr;
*OAMptr2 &= ~(3 << offset);
- if (SprX & 0x100) *OAMptr2 |= 3 << offset;
- else *OAMptr2 |= 2 << offset;
+ if (SprX & 0x100)
+ *OAMptr2 |= 3 << offset;
+ else
+ *OAMptr2 |= 2 << offset;
OAMptr += 4;
SprCount--;
offset = (offset + 2) & 6;
- if (offset == 0) OAMptr2++;
+ if (offset == 0)
+ OAMptr2++;
}
}
}
}
- // XXX: Copy to OAM? I doubt it.
}
static void C4DoScaleRotate(int32_t row_padding)
@@ -133,9 +138,11 @@ static void C4DoScaleRotate(int32_t row_padding)
// Calculate matrix
int32_t XScale = READ_WORD(Memory.C4RAM + 0x1f8f);
- if (XScale & 0x8000) XScale = 0x7fff;
+ if (XScale & 0x8000)
+ XScale = 0x7fff;
int32_t YScale = READ_WORD(Memory.C4RAM + 0x1f92);
- if (YScale & 0x8000) YScale = 0x7fff;
+ if (YScale & 0x8000)
+ YScale = 0x7fff;
if (READ_WORD(Memory.C4RAM + 0x1f80) == 0)
{
@@ -173,14 +180,10 @@ static void C4DoScaleRotate(int32_t row_padding)
}
else
{
- A = (int16_t)SAR16(C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * XScale,
- 15);
- B = (int16_t)(-SAR16(C4SinTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] *
- YScale, 15));
- C = (int16_t)SAR16(C4SinTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * XScale,
- 15);
- D = (int16_t)SAR16(C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * YScale,
- 15);
+ A = (int16_t) SAR16(C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * XScale, 15);
+ B = (int16_t)(-SAR16(C4SinTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * YScale, 15));
+ C = (int16_t) SAR16(C4SinTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * XScale, 15);
+ D = (int16_t) SAR16(C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * YScale, 15);
}
// Calculate Pixel Resolution
@@ -218,14 +221,19 @@ static void C4DoScaleRotate(int32_t row_padding)
{
uint32_t addr = (Y >> 12) * w + (X >> 12);
byte = Memory.C4RAM[0x600 + (addr >> 1)];
- if (addr & 1) byte >>= 4;
+ if (addr & 1)
+ byte >>= 4;
}
// De-bitplanify
- if (byte & 1) Memory.C4RAM[outidx] |= bit;
- if (byte & 2) Memory.C4RAM[outidx + 1] |= bit;
- if (byte & 4) Memory.C4RAM[outidx + 16] |= bit;
- if (byte & 8) Memory.C4RAM[outidx + 17] |= bit;
+ if (byte & 1)
+ Memory.C4RAM[outidx] |= bit;
+ if (byte & 2)
+ Memory.C4RAM[outidx + 1] |= bit;
+ if (byte & 4)
+ Memory.C4RAM[outidx + 16] |= bit;
+ if (byte & 8)
+ Memory.C4RAM[outidx + 17] |= bit;
bit >>= 1;
if (bit == 0)
@@ -247,8 +255,7 @@ static void C4DoScaleRotate(int32_t row_padding)
}
}
-static void C4DrawLine(int32_t X1, int32_t Y1, int16_t Z1,
- int32_t X2, int32_t Y2, int16_t Z2, uint8_t Color)
+static void C4DrawLine(int32_t X1, int32_t Y1, int16_t Z1, int32_t X2, int32_t Y2, int16_t Z2, uint8_t Color)
{
// Transform coordinates
C4WFXVal = (int16_t)X1;
@@ -270,8 +277,8 @@ static void C4DrawLine(int32_t X1, int32_t Y1, int16_t Z1,
Y2 = (C4WFYVal + 48) << 8;
// get line info
- C4WFXVal = (int16_t)(X1 >> 8);
- C4WFYVal = (int16_t)(Y1 >> 8);
+ C4WFXVal = (int16_t)(X1 >> 8);
+ C4WFYVal = (int16_t)(Y1 >> 8);
C4WFX2Val = (int16_t)(X2 >> 8);
C4WFY2Val = (int16_t)(Y2 >> 8);
C4CalcWireFrame();
@@ -285,20 +292,21 @@ static void C4DrawLine(int32_t X1, int32_t Y1, int16_t Z1,
//.loop
if (X1 > 0xff && Y1 > 0xff && X1 < 0x6000 && Y1 < 0x6000)
{
- uint16_t addr = (((Y1 >> 8) >> 3) << 8) - (((Y1 >> 8) >> 3) << 6) + (((
- X1 >> 8) >> 3) << 4) + ((Y1 >> 8) & 7) * 2;
+ uint16_t addr = (((Y1 >> 8) >> 3) << 8) - (((Y1 >> 8) >> 3) << 6) + (((X1 >> 8) >> 3) << 4) + ((Y1 >> 8) & 7) * 2;
uint8_t bit = 0x80 >> ((X1 >> 8) & 7);
Memory.C4RAM[addr + 0x300] &= ~bit;
Memory.C4RAM[addr + 0x301] &= ~bit;
- if (Color & 1) Memory.C4RAM[addr + 0x300] |= bit;
- if (Color & 2) Memory.C4RAM[addr + 0x301] |= bit;
+ if (Color & 1)
+ Memory.C4RAM[addr + 0x300] |= bit;
+ if (Color & 2)
+ Memory.C4RAM[addr + 0x301] |= bit;
}
X1 += X2;
Y1 += Y2;
}
}
-static void C4DrawWireFrame(void)
+static void C4DrawWireFrame()
{
uint8_t* line = S9xGetMemPointer(READ_3WORD(Memory.C4RAM + 0x1f80));
uint8_t* point1, *point2;
@@ -312,15 +320,13 @@ static void C4DrawWireFrame(void)
if (line[0] == 0xff && line[1] == 0xff)
{
uint8_t* tmp = line - 5;
- while (line[2] == 0xff && line[3] == 0xff) tmp -= 5;
- point1 = S9xGetMemPointer((Memory.C4RAM[0x1f82] << 16) |
- (tmp[2] << 8) | tmp[3]);
+ while (line[2] == 0xff && line[3] == 0xff)
+ tmp -= 5;
+ point1 = S9xGetMemPointer((Memory.C4RAM[0x1f82] << 16) | (tmp[2] << 8) | tmp[3]);
}
else
- point1 = S9xGetMemPointer((Memory.C4RAM[0x1f82] << 16) |
- (line[0] << 8) | line[1]);
- point2 = S9xGetMemPointer((Memory.C4RAM[0x1f82] << 16) |
- (line[2] << 8) | line[3]);
+ point1 = S9xGetMemPointer((Memory.C4RAM[0x1f82] << 16) | (line[0] << 8) | line[1]);
+ point2 = S9xGetMemPointer((Memory.C4RAM[0x1f82] << 16) | (line[2] << 8) | line[3]);
X1 = (point1[0] << 8) | point1[1];
Y1 = (point1[2] << 8) | point1[3];
@@ -333,7 +339,7 @@ static void C4DrawWireFrame(void)
}
}
-static void C4TransformLines(void)
+static void C4TransformLines()
{
C4WFX2Val = Memory.C4RAM[0x1f83];
C4WFY2Val = Memory.C4RAM[0x1f86];
@@ -366,19 +372,17 @@ static void C4TransformLines(void)
ptr = Memory.C4RAM + 0xb02;
uint8_t* ptr2 = Memory.C4RAM;
+
+ for (i = READ_WORD(Memory.C4RAM + 0xb00); i > 0; i--, ptr += 2, ptr2 += 8)
{
- int32_t i;
- for (i = READ_WORD(Memory.C4RAM + 0xb00); i > 0; i--, ptr += 2, ptr2 += 8)
- {
- C4WFXVal = READ_WORD(Memory.C4RAM + (ptr[0] << 4) + 1);
- C4WFYVal = READ_WORD(Memory.C4RAM + (ptr[0] << 4) + 5);
- C4WFX2Val = READ_WORD(Memory.C4RAM + (ptr[1] << 4) + 1);
- C4WFY2Val = READ_WORD(Memory.C4RAM + (ptr[1] << 4) + 5);
- C4CalcWireFrame();
- WRITE_WORD(ptr2 + 0x600, C4WFDist ? C4WFDist : 1);
- WRITE_WORD(ptr2 + 0x602, C4WFXVal);
- WRITE_WORD(ptr2 + 0x605, C4WFYVal);
- }
+ C4WFXVal = READ_WORD(Memory.C4RAM + (ptr[0] << 4) + 1);
+ C4WFYVal = READ_WORD(Memory.C4RAM + (ptr[0] << 4) + 5);
+ C4WFX2Val = READ_WORD(Memory.C4RAM + (ptr[1] << 4) + 1);
+ C4WFY2Val = READ_WORD(Memory.C4RAM + (ptr[1] << 4) + 5);
+ C4CalcWireFrame();
+ WRITE_WORD(ptr2 + 0x600, C4WFDist ? C4WFDist : 1);
+ WRITE_WORD(ptr2 + 0x602, C4WFXVal);
+ WRITE_WORD(ptr2 + 0x605, C4WFYVal);
}
}
static void C4BitPlaneWave()
@@ -479,12 +483,17 @@ static void C4SprDisintegrate()
uint8_t pixel = (j & 1) ? (*src >> 4) : *src;
int32_t idx = (y >> 11) * width * 4 + (x >> 11) * 32 + ((y >> 8) & 7) * 2;
uint8_t mask = 0x80 >> ((x >> 8) & 7);
- if (pixel & 1) Memory.C4RAM[idx] |= mask;
- if (pixel & 2) Memory.C4RAM[idx + 1] |= mask;
- if (pixel & 4) Memory.C4RAM[idx + 16] |= mask;
- if (pixel & 8) Memory.C4RAM[idx + 17] |= mask;
+ if (pixel & 1)
+ Memory.C4RAM[idx] |= mask;
+ if (pixel & 2)
+ Memory.C4RAM[idx + 1] |= mask;
+ if (pixel & 4)
+ Memory.C4RAM[idx + 16] |= mask;
+ if (pixel & 8)
+ Memory.C4RAM[idx + 17] |= mask;
}
- if (j & 1) src++;
+ if (j & 1)
+ src++;
}
}
}
@@ -496,31 +505,24 @@ static void S9xC4ProcessSprites()
case 0x00: // Build OAM
C4ConvOAM();
break;
-
case 0x03: // Scale/Rotate
C4DoScaleRotate(0);
break;
-
case 0x05: // Transform Lines
C4TransformLines();
break;
-
case 0x07: // Scale/Rotate
C4DoScaleRotate(64);
break;
-
case 0x08: // Draw wireframe
C4DrawWireFrame();
break;
-
case 0x0b: // Disintegrate
C4SprDisintegrate();
break;
-
case 0x0c: // Wave
C4BitPlaneWave();
break;
-
default:
break;
}
@@ -541,76 +543,75 @@ void S9xSetC4(uint8_t byte, uint16_t Address)
case 0x00: // Sprite
S9xC4ProcessSprites();
break;
-
case 0x01: // Draw wireframe
memset(Memory.C4RAM + 0x300, 0, 16 * 12 * 3 * 4);
C4DrawWireFrame();
break;
-
case 0x05: // Propulsion (?)
{
int32_t tmp = 0x10000;
if (READ_WORD(Memory.C4RAM + 0x1f83))
- tmp = SAR32((tmp / READ_WORD(Memory.C4RAM + 0x1f83)) * READ_WORD(
- Memory.C4RAM + 0x1f81), 8);
+ tmp = SAR32((tmp / READ_WORD(Memory.C4RAM + 0x1f83)) * READ_WORD(Memory.C4RAM + 0x1f81), 8);
WRITE_WORD(Memory.C4RAM + 0x1f80, (uint16_t)tmp);
+ break;
}
- break;
-
case 0x0d: // Set vector length
C41FXVal = READ_WORD(Memory.C4RAM + 0x1f80);
C41FYVal = READ_WORD(Memory.C4RAM + 0x1f83);
C41FDistVal = READ_WORD(Memory.C4RAM + 0x1f86);
- C4Op0D();
+ tanval = C41FDistVal / _isqrt((int32_t) C41FYVal * C41FYVal + (int32_t) C41FXVal * C41FXVal);
+ C41FYVal = (int16_t)(((int32_t)C41FYVal * tanval * 99) / 100);
+ C41FXVal = (int16_t)(((int32_t)C41FXVal * tanval * 98) / 100);
WRITE_WORD(Memory.C4RAM + 0x1f89, C41FXVal);
WRITE_WORD(Memory.C4RAM + 0x1f8c, C41FYVal);
break;
-
case 0x10: // Polar to rectangluar
{
- int32_t tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) *
- C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 16);
+ int32_t tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) * C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 16);
WRITE_3WORD(Memory.C4RAM + 0x1f86, tmp);
- tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) * C4SinTable[READ_WORD(
- Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 16);
+ tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) * C4SinTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 16);
WRITE_3WORD(Memory.C4RAM + 0x1f89, (tmp - SAR32(tmp, 6)));
+ break;
}
- break;
-
case 0x13: // Polar to rectangluar
{
- int32_t tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) *
- C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 8);
+ int32_t tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) * C4CosTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 8);
WRITE_3WORD(Memory.C4RAM + 0x1f86, tmp);
- tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) * C4SinTable[READ_WORD(
- Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 8);
+ tmp = SAR32((int32_t)READ_WORD(Memory.C4RAM + 0x1f83) * C4SinTable[READ_WORD(Memory.C4RAM + 0x1f80) & 0x1ff] * 2, 8);
WRITE_3WORD(Memory.C4RAM + 0x1f89, tmp);
+ break;
}
- break;
-
case 0x15: // Pythagorean
C41FXVal = READ_WORD(Memory.C4RAM + 0x1f80);
C41FYVal = READ_WORD(Memory.C4RAM + 0x1f83);
- C41FDist = (int16_t)sqrt((double)C41FXVal * C41FXVal + (double)C41FYVal *
- C41FYVal);
+ C41FDist = (int16_t)_isqrt((int32_t) C41FXVal * C41FXVal + (int32_t) C41FYVal * C41FYVal);
WRITE_WORD(Memory.C4RAM + 0x1f80, C41FDist);
break;
-
case 0x1f: // atan
C41FXVal = READ_WORD(Memory.C4RAM + 0x1f80);
C41FYVal = READ_WORD(Memory.C4RAM + 0x1f83);
- C4Op1F();
+ if (C41FXVal == 0)
+ {
+ if (C41FYVal > 0)
+ C41FAngleRes = 0x80;
+ else
+ C41FAngleRes = 0x180;
+ }
+ else
+ {
+ C41FAngleRes = (int16_t)(_atan2(C41FYVal, C41FXVal) / 2);
+ if (C41FXVal < 0)
+ C41FAngleRes += 0x100;
+ C41FAngleRes &= 0x1FF;
+ }
WRITE_WORD(Memory.C4RAM + 0x1f86, C41FAngleRes);
break;
-
case 0x22: // Trapezoid
{
int16_t angle1 = READ_WORD(Memory.C4RAM + 0x1f8c) & 0x1ff;
int16_t angle2 = READ_WORD(Memory.C4RAM + 0x1f8f) & 0x1ff;
- int32_t tan1 = (C4CosTable[angle1] != 0) ? ((((int32_t)C4SinTable[angle1]) << 16) /
- C4CosTable[angle1]) : 0x80000000;
- int32_t tan2 = (C4CosTable[angle2] != 0) ? ((((int32_t)C4SinTable[angle2]) << 16) /
- C4CosTable[angle2]) : 0x80000000;
+ int32_t tan1 = (C4CosTable[angle1] != 0) ? ((((int32_t)C4SinTable[angle1]) << 16) / C4CosTable[angle1]) : 0x80000000;
+ int32_t tan2 = (C4CosTable[angle2] != 0) ? ((((int32_t)C4SinTable[angle2]) << 16) / C4CosTable[angle2]) : 0x80000000;
int16_t y = READ_WORD(Memory.C4RAM + 0x1f83) - READ_WORD(Memory.C4RAM + 0x1f89);
int16_t left, right;
int32_t j;
@@ -618,13 +619,8 @@ void S9xSetC4(uint8_t byte, uint16_t Address)
{
if (y >= 0)
{
- left = SAR32((int32_t)tan1 * y, 16) -
- READ_WORD(Memory.C4RAM + 0x1f80) +
- READ_WORD(Memory.C4RAM + 0x1f86);
- right = SAR32((int32_t)tan2 * y, 16) -
- READ_WORD(Memory.C4RAM + 0x1f80) +
- READ_WORD(Memory.C4RAM + 0x1f86) +
- READ_WORD(Memory.C4RAM + 0x1f93);
+ left = SAR32((int32_t)tan1 * y, 16) - READ_WORD(Memory.C4RAM + 0x1f80) + READ_WORD(Memory.C4RAM + 0x1f86);
+ right = SAR32((int32_t)tan2 * y, 16) - READ_WORD(Memory.C4RAM + 0x1f80) + READ_WORD(Memory.C4RAM + 0x1f86) + READ_WORD(Memory.C4RAM + 0x1f93);
if (left < 0 && right < 0)
{
@@ -654,18 +650,16 @@ void S9xSetC4(uint8_t byte, uint16_t Address)
Memory.C4RAM[j + 0x900] = (uint8_t)right;
y++;
}
+ break;
}
- break;
-
case 0x25: // Multiply
{
int32_t foo = READ_3WORD(Memory.C4RAM + 0x1f80);
int32_t bar = READ_3WORD(Memory.C4RAM + 0x1f83);
foo *= bar;
WRITE_3WORD(Memory.C4RAM + 0x1f80, foo);
+ break;
}
- break;
-
case 0x2d: // Transform Coords
C4WFXVal = READ_WORD(Memory.C4RAM + 0x1f81);
C4WFYVal = READ_WORD(Memory.C4RAM + 0x1f84);
@@ -678,88 +672,79 @@ void S9xSetC4(uint8_t byte, uint16_t Address)
WRITE_WORD(Memory.C4RAM + 0x1f80, C4WFXVal);
WRITE_WORD(Memory.C4RAM + 0x1f83, C4WFYVal);
break;
-
case 0x40: // Sum
{
int32_t i;
uint16_t sum = 0;
for (i = 0; i < 0x800; sum += Memory.C4RAM[i++]);
WRITE_WORD(Memory.C4RAM + 0x1f80, sum);
+ break;
}
- break;
-
case 0x54: // Square
{
int64_t a = SAR64((int64_t)READ_3WORD(Memory.C4RAM + 0x1f80) << 40, 40);
a *= a;
WRITE_3WORD(Memory.C4RAM + 0x1f83, a);
WRITE_3WORD(Memory.C4RAM + 0x1f86, (a >> 24));
+ break;
}
- break;
-
case 0x5c: // Immediate Reg
for (i = 0; i < 12 * 4; i++)
Memory.C4RAM [i] = C4TestPattern [i];
break;
-
case 0x89: // Immediate ROM
Memory.C4RAM [0x1f80] = 0x36;
Memory.C4RAM [0x1f81] = 0x43;
Memory.C4RAM [0x1f82] = 0x05;
break;
-
default:
break;
}
}
}
else if (Address == 0x7f47)
- {
// memmove required: Can overlap arbitrarily [Neb]
- memmove(Memory.C4RAM + (READ_WORD(Memory.C4RAM + 0x1f45) & 0x1fff),
- S9xGetMemPointer(READ_3WORD(Memory.C4RAM + 0x1f40)),
- READ_WORD(Memory.C4RAM + 0x1f43));
- }
+ memmove(Memory.C4RAM + (READ_WORD(Memory.C4RAM + 0x1f45) & 0x1fff), S9xGetMemPointer(READ_3WORD(Memory.C4RAM + 0x1f40)), READ_WORD(Memory.C4RAM + 0x1f43));
}
int16_t C4SinTable[512] =
{
- 0, 402, 804, 1206, 1607, 2009, 2410, 2811,
- 3211, 3611, 4011, 4409, 4808, 5205, 5602, 5997,
- 6392, 6786, 7179, 7571, 7961, 8351, 8739, 9126,
- 9512, 9896, 10278, 10659, 11039, 11416, 11793, 12167,
- 12539, 12910, 13278, 13645, 14010, 14372, 14732, 15090,
- 15446, 15800, 16151, 16499, 16846, 17189, 17530, 17869,
- 18204, 18537, 18868, 19195, 19519, 19841, 20159, 20475,
- 20787, 21097, 21403, 21706, 22005, 22301, 22594, 22884,
- 23170, 23453, 23732, 24007, 24279, 24547, 24812, 25073,
- 25330, 25583, 25832, 26077, 26319, 26557, 26790, 27020,
- 27245, 27466, 27684, 27897, 28106, 28310, 28511, 28707,
- 28898, 29086, 29269, 29447, 29621, 29791, 29956, 30117,
- 30273, 30425, 30572, 30714, 30852, 30985, 31114, 31237,
- 31357, 31471, 31581, 31685, 31785, 31881, 31971, 32057,
- 32138, 32214, 32285, 32351, 32413, 32469, 32521, 32568,
- 32610, 32647, 32679, 32706, 32728, 32745, 32758, 32765,
- 32767, 32765, 32758, 32745, 32728, 32706, 32679, 32647,
- 32610, 32568, 32521, 32469, 32413, 32351, 32285, 32214,
- 32138, 32057, 31971, 31881, 31785, 31685, 31581, 31471,
- 31357, 31237, 31114, 30985, 30852, 30714, 30572, 30425,
- 30273, 30117, 29956, 29791, 29621, 29447, 29269, 29086,
- 28898, 28707, 28511, 28310, 28106, 27897, 27684, 27466,
- 27245, 27020, 26790, 26557, 26319, 26077, 25832, 25583,
- 25330, 25073, 24812, 24547, 24279, 24007, 23732, 23453,
- 23170, 22884, 22594, 22301, 22005, 21706, 21403, 21097,
- 20787, 20475, 20159, 19841, 19519, 19195, 18868, 18537,
- 18204, 17869, 17530, 17189, 16846, 16499, 16151, 15800,
- 15446, 15090, 14732, 14372, 14010, 13645, 13278, 12910,
- 12539, 12167, 11793, 11416, 11039, 10659, 10278, 9896,
- 9512, 9126, 8739, 8351, 7961, 7571, 7179, 6786,
- 6392, 5997, 5602, 5205, 4808, 4409, 4011, 3611,
- 3211, 2811, 2410, 2009, 1607, 1206, 804, 402,
- 0, -402, -804, -1206, -1607, -2009, -2410, -2811,
+ 0, 402, 804, 1206, 1607, 2009, 2410, 2811,
+ 3211, 3611, 4011, 4409, 4808, 5205, 5602, 5997,
+ 6392, 6786, 7179, 7571, 7961, 8351, 8739, 9126,
+ 9512, 9896, 10278, 10659, 11039, 11416, 11793, 12167,
+ 12539, 12910, 13278, 13645, 14010, 14372, 14732, 15090,
+ 15446, 15800, 16151, 16499, 16846, 17189, 17530, 17869,
+ 18204, 18537, 18868, 19195, 19519, 19841, 20159, 20475,
+ 20787, 21097, 21403, 21706, 22005, 22301, 22594, 22884,
+ 23170, 23453, 23732, 24007, 24279, 24547, 24812, 25073,
+ 25330, 25583, 25832, 26077, 26319, 26557, 26790, 27020,
+ 27245, 27466, 27684, 27897, 28106, 28310, 28511, 28707,
+ 28898, 29086, 29269, 29447, 29621, 29791, 29956, 30117,
+ 30273, 30425, 30572, 30714, 30852, 30985, 31114, 31237,
+ 31357, 31471, 31581, 31685, 31785, 31881, 31971, 32057,
+ 32138, 32214, 32285, 32351, 32413, 32469, 32521, 32568,
+ 32610, 32647, 32679, 32706, 32728, 32745, 32758, 32765,
+ 32767, 32765, 32758, 32745, 32728, 32706, 32679, 32647,
+ 32610, 32568, 32521, 32469, 32413, 32351, 32285, 32214,
+ 32138, 32057, 31971, 31881, 31785, 31685, 31581, 31471,
+ 31357, 31237, 31114, 30985, 30852, 30714, 30572, 30425,
+ 30273, 30117, 29956, 29791, 29621, 29447, 29269, 29086,
+ 28898, 28707, 28511, 28310, 28106, 27897, 27684, 27466,
+ 27245, 27020, 26790, 26557, 26319, 26077, 25832, 25583,
+ 25330, 25073, 24812, 24547, 24279, 24007, 23732, 23453,
+ 23170, 22884, 22594, 22301, 22005, 21706, 21403, 21097,
+ 20787, 20475, 20159, 19841, 19519, 19195, 18868, 18537,
+ 18204, 17869, 17530, 17189, 16846, 16499, 16151, 15800,
+ 15446, 15090, 14732, 14372, 14010, 13645, 13278, 12910,
+ 12539, 12167, 11793, 11416, 11039, 10659, 10278, 9896,
+ 9512, 9126, 8739, 8351, 7961, 7571, 7179, 6786,
+ 6392, 5997, 5602, 5205, 4808, 4409, 4011, 3611,
+ 3211, 2811, 2410, 2009, 1607, 1206, 804, 402,
+ 0, -402, -804, -1206, -1607, -2009, -2410, -2811,
-3211, -3611, -4011, -4409, -4808, -5205, -5602, -5997,
-6392, -6786, -7179, -7571, -7961, -8351, -8739, -9126,
- -9512, -9896, -10278, -10659, -11039, -11416, -11793, -12167,
+ -9512, -9896, -10278, -10659, -11039, -11416, -11793, -12167,
-12539, -12910, -13278, -13645, -14010, -14372, -14732, -15090,
-15446, -15800, -16151, -16499, -16846, -17189, -17530, -17869,
-18204, -18537, -18868, -19195, -19519, -19841, -20159, -20475,
@@ -792,26 +777,26 @@ int16_t C4SinTable[512] =
int16_t C4CosTable[512] =
{
- 32767, 32765, 32758, 32745, 32728, 32706, 32679, 32647,
- 32610, 32568, 32521, 32469, 32413, 32351, 32285, 32214,
- 32138, 32057, 31971, 31881, 31785, 31685, 31581, 31471,
- 31357, 31237, 31114, 30985, 30852, 30714, 30572, 30425,
- 30273, 30117, 29956, 29791, 29621, 29447, 29269, 29086,
- 28898, 28707, 28511, 28310, 28106, 27897, 27684, 27466,
- 27245, 27020, 26790, 26557, 26319, 26077, 25832, 25583,
- 25330, 25073, 24812, 24547, 24279, 24007, 23732, 23453,
- 23170, 22884, 22594, 22301, 22005, 21706, 21403, 21097,
- 20787, 20475, 20159, 19841, 19519, 19195, 18868, 18537,
- 18204, 17869, 17530, 17189, 16846, 16499, 16151, 15800,
- 15446, 15090, 14732, 14372, 14010, 13645, 13278, 12910,
- 12539, 12167, 11793, 11416, 11039, 10659, 10278, 9896,
- 9512, 9126, 8739, 8351, 7961, 7571, 7179, 6786,
- 6392, 5997, 5602, 5205, 4808, 4409, 4011, 3611,
- 3211, 2811, 2410, 2009, 1607, 1206, 804, 402,
- 0, -402, -804, -1206, -1607, -2009, -2410, -2811,
+ 32767, 32765, 32758, 32745, 32728, 32706, 32679, 32647,
+ 32610, 32568, 32521, 32469, 32413, 32351, 32285, 32214,
+ 32138, 32057, 31971, 31881, 31785, 31685, 31581, 31471,
+ 31357, 31237, 31114, 30985, 30852, 30714, 30572, 30425,
+ 30273, 30117, 29956, 29791, 29621, 29447, 29269, 29086,
+ 28898, 28707, 28511, 28310, 28106, 27897, 27684, 27466,
+ 27245, 27020, 26790, 26557, 26319, 26077, 25832, 25583,
+ 25330, 25073, 24812, 24547, 24279, 24007, 23732, 23453,
+ 23170, 22884, 22594, 22301, 22005, 21706, 21403, 21097,
+ 20787, 20475, 20159, 19841, 19519, 19195, 18868, 18537,
+ 18204, 17869, 17530, 17189, 16846, 16499, 16151, 15800,
+ 15446, 15090, 14732, 14372, 14010, 13645, 13278, 12910,
+ 12539, 12167, 11793, 11416, 11039, 10659, 10278, 9896,
+ 9512, 9126, 8739, 8351, 7961, 7571, 7179, 6786,
+ 6392, 5997, 5602, 5205, 4808, 4409, 4011, 3611,
+ 3211, 2811, 2410, 2009, 1607, 1206, 804, 402,
+ 0, -402, -804, -1206, -1607, -2009, -2410, -2811,
-3211, -3611, -4011, -4409, -4808, -5205, -5602, -5997,
-6392, -6786, -7179, -7571, -7961, -8351, -8739, -9126,
- -9512, -9896, -10278, -10659, -11039, -11416, -11793, -12167,
+ -9512, -9896, -10278, -10659, -11039, -11416, -11793, -12167,
-12539, -12910, -13278, -13645, -14010, -14372, -14732, -15090,
-15446, -15800, -16151, -16499, -16846, -17189, -17530, -17869,
-18204, -18537, -18868, -19195, -19519, -19841, -20159, -20475,
@@ -836,24 +821,24 @@ int16_t C4CosTable[512] =
-20787, -20475, -20159, -19841, -19519, -19195, -18868, -18537,
-18204, -17869, -17530, -17189, -16846, -16499, -16151, -15800,
-15446, -15090, -14732, -14372, -14010, -13645, -13278, -12910,
- -12539, -12167, -11793, -11416, -11039, -10659, -10278, -9896,
+ -12539, -12167, -11793, -11416, -11039, -10659, -10278, -9896,
-9512, -9126, -8739, -8351, -7961, -7571, -7179, -6786,
-6392, -5997, -5602, -5205, -4808, -4409, -4011, -3611,
- -3211, -2811, -2410, -2009, -1607, -1206, -804, -402,
- 0, 402, 804, 1206, 1607, 2009, 2410, 2811,
- 3211, 3611, 4011, 4409, 4808, 5205, 5602, 5997,
- 6392, 6786, 7179, 7571, 7961, 8351, 8739, 9126,
- 9512, 9896, 10278, 10659, 11039, 11416, 11793, 12167,
- 12539, 12910, 13278, 13645, 14010, 14372, 14732, 15090,
- 15446, 15800, 16151, 16499, 16846, 17189, 17530, 17869,
- 18204, 18537, 18868, 19195, 19519, 19841, 20159, 20475,
- 20787, 21097, 21403, 21706, 22005, 22301, 22594, 22884,
- 23170, 23453, 23732, 24007, 24279, 24547, 24812, 25073,
- 25330, 25583, 25832, 26077, 26319, 26557, 26790, 27020,
- 27245, 27466, 27684, 27897, 28106, 28310, 28511, 28707,
- 28898, 29086, 29269, 29447, 29621, 29791, 29956, 30117,
- 30273, 30425, 30572, 30714, 30852, 30985, 31114, 31237,
- 31357, 31471, 31581, 31685, 31785, 31881, 31971, 32057,
- 32138, 32214, 32285, 32351, 32413, 32469, 32521, 32568,
- 32610, 32647, 32679, 32706, 32728, 32745, 32758, 32765
+ -3211, -2811, -2410, -2009, -1607, -1206, -804, -402,
+ 0, 402, 804, 1206, 1607, 2009, 2410, 2811,
+ 3211, 3611, 4011, 4409, 4808, 5205, 5602, 5997,
+ 6392, 6786, 7179, 7571, 7961, 8351, 8739, 9126,
+ 9512, 9896, 10278, 10659, 11039, 11416, 11793, 12167,
+ 12539, 12910, 13278, 13645, 14010, 14372, 14732, 15090,
+ 15446, 15800, 16151, 16499, 16846, 17189, 17530, 17869,
+ 18204, 18537, 18868, 19195, 19519, 19841, 20159, 20475,
+ 20787, 21097, 21403, 21706, 22005, 22301, 22594, 22884,
+ 23170, 23453, 23732, 24007, 24279, 24547, 24812, 25073,
+ 25330, 25583, 25832, 26077, 26319, 26557, 26790, 27020,
+ 27245, 27466, 27684, 27897, 28106, 28310, 28511, 28707,
+ 28898, 29086, 29269, 29447, 29621, 29791, 29956, 30117,
+ 30273, 30425, 30572, 30714, 30852, 30985, 31114, 31237,
+ 31357, 31471, 31581, 31685, 31785, 31881, 31971, 32057,
+ 32138, 32214, 32285, 32351, 32413, 32469, 32521, 32568,
+ 32610, 32647, 32679, 32706, 32728, 32745, 32758, 32765
};
diff --git a/source/dsp1.c b/source/dsp1.c
index 5d4d522..9e7f05b 100644
--- a/source/dsp1.c
+++ b/source/dsp1.c
@@ -356,8 +356,8 @@ void DSP1SetByte(uint8_t byte, uint16_t address)
DSP1.output [1] = (uint8_t)((Op06H >> 8) & 0xFF);
DSP1.output [2] = (uint8_t)(Op06V & 0xFF);
DSP1.output [3] = (uint8_t)((Op06V >> 8) & 0xFF);
- DSP1.output [4] = (uint8_t)(Op06S & 0xFF);
- DSP1.output [5] = (uint8_t)((Op06S >> 8) & 0xFF);
+ DSP1.output [4] = (uint8_t)(Op06M & 0xFF);
+ DSP1.output [5] = (uint8_t)((Op06M >> 8) & 0xFF);
break;
case 0x1e:
case 0x2e:
diff --git a/source/dsp1emu.c b/source/dsp1emu.c
index a2767b0..3e34795 100644
--- a/source/dsp1emu.c
+++ b/source/dsp1emu.c
@@ -6,9 +6,6 @@
#include <string.h>
#include <stdlib.h>
-#define __OPT__
-#define __OPT06__
-
const uint16_t DSP1ROM[1024] =
{
0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000, 0x0000,
@@ -142,46 +139,9 @@ const uint16_t DSP1ROM[1024] =
};
/***************************************************************************\
-* Math tables *
-\***************************************************************************/
-
-#define INCR 2048
-#define Angle(x) (((x)/(65536/INCR)) & (INCR-1))
-#define Cos(x) ((double) CosTable2[x])
-#define Sin(x) ((double) SinTable2[x])
-#ifdef PI
-#undef PI
-#endif
-#define PI 3.1415926535897932384626433832795
-double CosTable2[INCR];
-double SinTable2[INCR];
-
-
-double Atan(double x)
-{
- if ((x >= 1) || (x <= 1))
- return (x / (1 + 0.28 * x * x));
- else
- return (PI / 2 - Atan(1 / x));
-}
-
-/***************************************************************************\
* DSP1 code *
\***************************************************************************/
-void InitDSP(void)
-{
-#ifdef __OPT__
- uint32_t i;
- for (i = 0; i < INCR; i++)
- {
- CosTable2[i] = (cos((double)(2 * PI * i / INCR)));
- SinTable2[i] = (sin((double)(2 * PI * i / INCR)));
- }
-#endif
-}
-
-
int16_t Op00Multiplicand;
int16_t Op00Multiplier;
int16_t Op00Result;
@@ -189,7 +149,6 @@ int16_t Op00Result;
void DSPOp00()
{
Op00Result = Op00Multiplicand * Op00Multiplier >> 15;
-
}
int16_t Op20Multiplicand;
@@ -200,7 +159,6 @@ void DSPOp20()
{
Op20Result = Op20Multiplicand * Op20Multiplier >> 15;
Op20Result++;
-
}
int16_t Op10Coefficient;
@@ -208,8 +166,7 @@ int16_t Op10Exponent;
int16_t Op10CoefficientR;
int16_t Op10ExponentR;
-void DSP1_Inverse(int16_t Coefficient, int16_t Exponent, int16_t* iCoefficient,
- int16_t* iExponent)
+void DSP1_Inverse(int16_t Coefficient, int16_t Exponent, int16_t* iCoefficient, int16_t* iExponent)
{
// Step One: Division by Zero
if (Coefficient == 0x0000)
@@ -308,22 +265,22 @@ const int16_t DSP1_MulTable[256] =
const int16_t DSP1_SinTable[256] =
{
- 0x0000, 0x0324, 0x0647, 0x096a, 0x0c8b, 0x0fab, 0x12c8, 0x15e2,
- 0x18f8, 0x1c0b, 0x1f19, 0x2223, 0x2528, 0x2826, 0x2b1f, 0x2e11,
- 0x30fb, 0x33de, 0x36ba, 0x398c, 0x3c56, 0x3f17, 0x41ce, 0x447a,
- 0x471c, 0x49b4, 0x4c3f, 0x4ebf, 0x5133, 0x539b, 0x55f5, 0x5842,
- 0x5a82, 0x5cb4, 0x5ed7, 0x60ec, 0x62f2, 0x64e8, 0x66cf, 0x68a6,
- 0x6a6d, 0x6c24, 0x6dca, 0x6f5f, 0x70e2, 0x7255, 0x73b5, 0x7504,
- 0x7641, 0x776c, 0x7884, 0x798a, 0x7a7d, 0x7b5d, 0x7c29, 0x7ce3,
- 0x7d8a, 0x7e1d, 0x7e9d, 0x7f09, 0x7f62, 0x7fa7, 0x7fd8, 0x7ff6,
- 0x7fff, 0x7ff6, 0x7fd8, 0x7fa7, 0x7f62, 0x7f09, 0x7e9d, 0x7e1d,
- 0x7d8a, 0x7ce3, 0x7c29, 0x7b5d, 0x7a7d, 0x798a, 0x7884, 0x776c,
- 0x7641, 0x7504, 0x73b5, 0x7255, 0x70e2, 0x6f5f, 0x6dca, 0x6c24,
- 0x6a6d, 0x68a6, 0x66cf, 0x64e8, 0x62f2, 0x60ec, 0x5ed7, 0x5cb4,
- 0x5a82, 0x5842, 0x55f5, 0x539b, 0x5133, 0x4ebf, 0x4c3f, 0x49b4,
- 0x471c, 0x447a, 0x41ce, 0x3f17, 0x3c56, 0x398c, 0x36ba, 0x33de,
- 0x30fb, 0x2e11, 0x2b1f, 0x2826, 0x2528, 0x2223, 0x1f19, 0x1c0b,
- 0x18f8, 0x15e2, 0x12c8, 0x0fab, 0x0c8b, 0x096a, 0x0647, 0x0324,
+ 0x0000, 0x0324, 0x0647, 0x096a, 0x0c8b, 0x0fab, 0x12c8, 0x15e2,
+ 0x18f8, 0x1c0b, 0x1f19, 0x2223, 0x2528, 0x2826, 0x2b1f, 0x2e11,
+ 0x30fb, 0x33de, 0x36ba, 0x398c, 0x3c56, 0x3f17, 0x41ce, 0x447a,
+ 0x471c, 0x49b4, 0x4c3f, 0x4ebf, 0x5133, 0x539b, 0x55f5, 0x5842,
+ 0x5a82, 0x5cb4, 0x5ed7, 0x60ec, 0x62f2, 0x64e8, 0x66cf, 0x68a6,
+ 0x6a6d, 0x6c24, 0x6dca, 0x6f5f, 0x70e2, 0x7255, 0x73b5, 0x7504,
+ 0x7641, 0x776c, 0x7884, 0x798a, 0x7a7d, 0x7b5d, 0x7c29, 0x7ce3,
+ 0x7d8a, 0x7e1d, 0x7e9d, 0x7f09, 0x7f62, 0x7fa7, 0x7fd8, 0x7ff6,
+ 0x7fff, 0x7ff6, 0x7fd8, 0x7fa7, 0x7f62, 0x7f09, 0x7e9d, 0x7e1d,
+ 0x7d8a, 0x7ce3, 0x7c29, 0x7b5d, 0x7a7d, 0x798a, 0x7884, 0x776c,
+ 0x7641, 0x7504, 0x73b5, 0x7255, 0x70e2, 0x6f5f, 0x6dca, 0x6c24,
+ 0x6a6d, 0x68a6, 0x66cf, 0x64e8, 0x62f2, 0x60ec, 0x5ed7, 0x5cb4,
+ 0x5a82, 0x5842, 0x55f5, 0x539b, 0x5133, 0x4ebf, 0x4c3f, 0x49b4,
+ 0x471c, 0x447a, 0x41ce, 0x3f17, 0x3c56, 0x398c, 0x36ba, 0x33de,
+ 0x30fb, 0x2e11, 0x2b1f, 0x2826, 0x2528, 0x2223, 0x1f19, 0x1c0b,
+ 0x18f8, 0x15e2, 0x12c8, 0x0fab, 0x0c8b, 0x096a, 0x0647, 0x0324,
-0x0000, -0x0324, -0x0647, -0x096a, -0x0c8b, -0x0fab, -0x12c8, -0x15e2,
-0x18f8, -0x1c0b, -0x1f19, -0x2223, -0x2528, -0x2826, -0x2b1f, -0x2e11,
-0x30fb, -0x33de, -0x36ba, -0x398c, -0x3c56, -0x3f17, -0x41ce, -0x447a,
@@ -349,8 +306,7 @@ int16_t DSP1_Sin(int16_t Angle)
if (Angle == -32768) return 0;
return -DSP1_Sin(-Angle);
}
- int32_t S = DSP1_SinTable[Angle >> 8] + (DSP1_MulTable[Angle & 0xff] *
- DSP1_SinTable[0x40 + (Angle >> 8)] >> 15);
+ int32_t S = DSP1_SinTable[Angle >> 8] + (DSP1_MulTable[Angle & 0xff] * DSP1_SinTable[0x40 + (Angle >> 8)] >> 15);
if (S > 32767) S = 32767;
return (int16_t) S;
}
@@ -362,8 +318,7 @@ int16_t DSP1_Cos(int16_t Angle)
if (Angle == -32768) return -32768;
Angle = -Angle;
}
- int32_t S = DSP1_SinTable[0x40 + (Angle >> 8)] - (DSP1_MulTable[Angle & 0xff] *
- DSP1_SinTable[Angle >> 8] >> 15);
+ int32_t S = DSP1_SinTable[0x40 + (Angle >> 8)] - (DSP1_MulTable[Angle & 0xff] * DSP1_SinTable[Angle >> 8] >> 15);
if (S < -32768) S = -32767;
return (int16_t) S;
}
@@ -502,50 +457,75 @@ int16_t SecAZS_E1;
int16_t SecAZS_C2;
int16_t SecAZS_E2;
+int16_t Nx, Ny, Nz;
+int16_t Gx, Gy, Gz;
+int16_t C_Les, E_Les, G_Les;
+
const int16_t MaxAZS_Exp[16] =
{
0x38b4, 0x38b7, 0x38ba, 0x38be, 0x38c0, 0x38c4, 0x38c7, 0x38ca,
0x38ce, 0x38d0, 0x38d4, 0x38d7, 0x38da, 0x38dd, 0x38e0, 0x38e4
};
-void DSP1_Parameter(int16_t Fx, int16_t Fy, int16_t Fz, int16_t Lfe, int16_t Les,
- int16_t Aas, int16_t Azs, int16_t* Vof, int16_t* Vva, int16_t* Cx, int16_t* Cy)
+void DSP1_Parameter(int16_t Fx, int16_t Fy, int16_t Fz, int16_t Lfe, int16_t Les, int16_t Aas, int16_t Azs, int16_t* Vof, int16_t* Vva, int16_t* Cx, int16_t* Cy)
{
- int16_t CSec, C, E;
+ int16_t CSec, C, E, MaxAZS, Aux;
+ int16_t LfeNx, LfeNy, LfeNz;
+ int16_t LesNx, LesNy, LesNz;
+ int16_t CentreZ;
// Copy Zenith angle for clipping
int16_t AZS = Azs;
- // Store Sin and Cos of Azimuth and Zenith angles
+ // Store Sine and Cosine of Azimuth and Zenith angle
SinAas = DSP1_Sin(Aas);
CosAas = DSP1_Cos(Aas);
SinAzs = DSP1_Sin(Azs);
CosAzs = DSP1_Cos(Azs);
+ Nx = SinAzs * -SinAas >> 15;
+ Ny = SinAzs * CosAas >> 15;
+ Nz = CosAzs * 0x7fff >> 15;
+
+ LfeNx = Lfe * Nx >> 15;
+ LfeNy = Lfe * Ny >> 15;
+ LfeNz = Lfe * Nz >> 15;
+
// Center of Projection
- CentreX = Fx + (Lfe * (SinAzs * -SinAas >> 15) >> 15);
- CentreY = Fy + (Lfe * (SinAzs * CosAas >> 15) >> 15);
+ CentreX = Fx + LfeNx;
+ CentreY = Fy + LfeNy;
+ CentreZ = Fz + LfeNz;
+
+ LesNx = Les * Nx >> 15;
+ LesNy = Les * Ny >> 15;
+ LesNz = Les * Nz >> 15;
+
+ Gx = CentreX - LesNx;
+ Gy = CentreY - LesNy;
+ Gz = CentreZ - LesNz;
+
+ E_Les=0;
+ DSP1_Normalize(Les, &C_Les, &E_Les);
+ G_Les = Les;
E = 0;
- DSP1_Normalize(Fz + (Lfe * (CosAzs * 0x7fff >> 15) >> 15), &C, &E);
+ DSP1_Normalize(CentreZ, &C, &E);
VPlane_C = C;
VPlane_E = E;
// Determine clip boundary and clip Zenith angle if necessary
- int16_t MaxAZS = MaxAZS_Exp[-E];
+ MaxAZS = MaxAZS_Exp[-E];
if (AZS < 0)
{
MaxAZS = -MaxAZS;
if (AZS < MaxAZS + 1) AZS = MaxAZS + 1;
}
- else
- {
- if (AZS > MaxAZS) AZS = MaxAZS;
- }
+ else if (AZS > MaxAZS)
+ AZS = MaxAZS;
- // Store Sin and Cos of clipped Zenith angle
+ // Store Sine and Cosine of clipped Zenith angle
SinAZS = DSP1_Sin(AZS);
CosAZS = DSP1_Cos(AZS);
@@ -570,7 +550,7 @@ void DSP1_Parameter(int16_t Fx, int16_t Fy, int16_t Fz, int16_t Lfe, int16_t Les
C = Azs - MaxAZS;
if (C >= 0) C--;
- int16_t Aux = ~(C << 2);
+ Aux = ~(C << 2);
C = Aux * DSP1ROM[0x0328] >> 15;
C = (C * Aux >> 15) + DSP1ROM[0x0327];
@@ -595,7 +575,7 @@ void DSP1_Parameter(int16_t Fx, int16_t Fy, int16_t Fz, int16_t Lfe, int16_t Les
*Vva = DSP1_Truncate(-C, E);
- // Store Sec of clipped Zenith angle
+ // Store Secant of clipped Zenith angle
DSP1_Inverse(CosAZS, 0, &SecAZS_C2, &SecAZS_E2);
}
@@ -638,8 +618,7 @@ int16_t Op02CY;
void DSPOp02()
{
- DSP1_Parameter(Op02FX, Op02FY, Op02FZ, Op02LFE, Op02LES, Op02AAS, Op02AZS,
- &Op02VOF, &Op02VVA, &Op02CX, &Op02CY);
+ DSP1_Parameter(Op02FX, Op02FY, Op02FZ, Op02LFE, Op02LES, Op02AAS, Op02AZS, &Op02VOF, &Op02VVA, &Op02CX, &Op02CY);
}
int16_t Op0AVS;
@@ -654,115 +633,96 @@ void DSPOp0A()
Op0AVS++;
}
+int16_t DSP1_ShiftR(int16_t C, int16_t E)
+{
+ return (C * DSP1ROM[0x0031 + E] >> 15);
+}
+
+void DSP1_Project(int16_t X, int16_t Y, int16_t Z, int16_t *H, int16_t *V, int16_t *M)
+{
+ int32_t aux, aux4;
+ int16_t E, E2, E3, E4, E5, refE, E6, E7;
+ int16_t C2, C4, C6, C8, C9, C10, C11, C12, C16, C17, C18, C19, C20, C21, C22, C23, C24, C25, C26;
+ int16_t Px, Py, Pz;
+
+ E4 = E3 = E2 = E = E5 = 0;
+
+ DSP1_NormalizeDouble((int32_t) X - Gx, &Px, &E4);
+ DSP1_NormalizeDouble((int32_t) Y - Gy, &Py, &E);
+ DSP1_NormalizeDouble((int32_t) Z - Gz, &Pz, &E3);
+ Px>>=1;
+ E4--; // to avoid overflows when calculating the scalar products
+ Py>>=1;
+ E--;
+ Pz>>=1;
+ E3--;
+
+ refE = MIN(E, E3);
+ refE = MIN(refE, E4);
+
+ Px = DSP1_ShiftR(Px, E4 - refE); // normalize them to the same exponent
+ Py = DSP1_ShiftR(Py, E - refE);
+ Pz = DSP1_ShiftR(Pz, E3 - refE);
+
+ C11 = -(Px * Nx >> 15);
+ C8 = -(Py * Ny >> 15);
+ C9 = -(Pz * Nz >> 15);
+ C12 = C11 + C8 + C9; // this cannot overflow!
+
+ aux4 = C12; // de-normalization with 32-bit arithmetic
+ refE = 16 - refE; // refE can be up to 3
+ if (refE >= 0)
+ aux4 <<= refE;
+ else
+ aux4 >>= -refE;
+ if (aux4 == -1)
+ aux4 = 0; // why?
+ aux4>>=1;
+
+ aux = ((int16_t) G_Les) + aux4; // Les - the scalar product of P with the normal vector of the screen
+ DSP1_NormalizeDouble(aux, &C10, &E2);
+ E2 = 15 - E2;
+
+ DSP1_Inverse(C10, 0, &C4, &E4);
+ C2 = C4 * C_Les >> 15; // scale factor
+
+ // H
+ E7 = 0;
+ C16 = (Px * (CosAas * 0x7fff >> 15) >> 15);
+ C20 = (Py * (SinAas * 0x7fff >> 15) >> 15);
+ C17 = C16 + C20; // scalar product of P with the normalized horizontal vector of the screen...
+
+ C18 = C17 * C2 >> 15; // ... multiplied by the scale factor
+ DSP1_Normalize(C18, &C19, &E7);
+ *H = DSP1_Truncate(C19, E_Les - E2 + refE + E7);
+
+ // V
+ E6 = 0;
+ C21 = Px * (CosAzs * -SinAas >> 15) >> 15;
+ C22 = Py * (CosAzs * CosAas >> 15) >> 15;
+ C23 = Pz * (-SinAzs * 0x7fff >> 15) >> 15;
+ C24 = C21 + C22 + C23; // scalar product of P with the normalized vertical vector of the screen...
+
+ C26 = C24 * C2 >> 15; // ... multiplied by the scale factor
+ DSP1_Normalize(C26, &C25, &E6);
+ *V = DSP1_Truncate(C25, E_Les - E2 + refE + E6);
+
+ // M
+ DSP1_Normalize(C2, &C6, &E4);
+ *M = DSP1_Truncate(C6, E4 + E_Les - E2 - 7); // M is the scale factor divided by 2^7
+}
+
int16_t Op06X;
int16_t Op06Y;
int16_t Op06Z;
int16_t Op06H;
int16_t Op06V;
-uint16_t Op06S;
-
-double ObjPX;
-double ObjPY;
-double ObjPZ;
-double ObjPX1;
-double ObjPY1;
-double ObjPZ1;
-double ObjPX2;
-double ObjPY2;
-double ObjPZ2;
-double DivideOp06;
-int32_t Temp;
-int32_t tanval2;
-
-#ifdef __OPT06__
-void DSPOp06()
-{
- ObjPX = Op06X - Op02FX;
- ObjPY = Op06Y - Op02FY;
- ObjPZ = Op06Z - Op02FZ;
-
- // rotate around Z
- tanval2 = Angle(-Op02AAS + 32768);
- ObjPX1 = (ObjPX * Cos(tanval2) + ObjPY * -Sin(tanval2));
- ObjPY1 = (ObjPX * Sin(tanval2) + ObjPY * Cos(tanval2));
- ObjPZ1 = ObjPZ;
-
- // rotate around X
- tanval2 = Angle(-Op02AZS);
- ObjPX2 = ObjPX1;
- ObjPY2 = (ObjPY1 * Cos(tanval2) + ObjPZ1 * -Sin(tanval2));
- ObjPZ2 = (ObjPY1 * Sin(tanval2) + ObjPZ1 * Cos(tanval2));
-
- ObjPZ2 = ObjPZ2 - Op02LFE;
-
- if (ObjPZ2 < 0)
- {
- double d;
- Op06H = (int16_t)(-ObjPX2 * Op02LES / -(ObjPZ2));
- Op06V = (int16_t)(-ObjPY2 * Op02LES / -(ObjPZ2));
- d = (double)Op02LES;
- d *= 256.0;
- d /= (-ObjPZ2);
- if (d > 65535.0)
- d = 65535.0;
- else if (d < 0.0)
- d = 0.0;
- Op06S = (uint16_t)d;
- }
- else
- {
- Op06H = 0;
- Op06V = 14 * 16;
- Op06S = 0xFFFF;
- }
-
-
-}
-#else
+int16_t Op06M;
void DSPOp06()
{
- ObjPX = Op06X - Op02FX;
- ObjPY = Op06Y - Op02FY;
- ObjPZ = Op06Z - Op02FZ;
-
- // rotate around Z
- tanval = (-Op02AAS + 32768) / 65536.0 * 6.2832;
- ObjPX1 = (ObjPX * cos(tanval) + ObjPY * -sin(tanval));
- ObjPY1 = (ObjPX * sin(tanval) + ObjPY * cos(tanval));
- ObjPZ1 = ObjPZ;
-
- // rotate around X
- tanval = (-Op02AZS) / 65536.0 * 6.2832;
- ObjPX2 = ObjPX1;
- ObjPY2 = (ObjPY1 * cos(tanval) + ObjPZ1 * -sin(tanval));
- ObjPZ2 = (ObjPY1 * sin(tanval) + ObjPZ1 * cos(tanval));
-
- ObjPZ2 = ObjPZ2 - Op02LFE;
-
- if (ObjPZ2 < 0)
- {
- Op06H = (int16_t)(-ObjPX2 * Op02LES / -(ObjPZ2));
- Op06V = (int16_t)(-ObjPY2 * Op02LES / -(ObjPZ2));
- double d = (double)Op02LES;
- d *= 256.0;
- d /= (-ObjPZ2);
- if (d > 65535.0)
- d = 65535.0;
- else if (d < 0.0)
- d = 0.0;
- Op06S = (uint16_t)d;
- }
- else
- {
- Op06H = 0;
- Op06V = 14 * 16;
- Op06S = 0xFFFF;
- }
-
+ DSP1_Project(Op06X, Op06Y, Op06Z, &Op06H, &Op06V, &Op06M);
}
-#endif
-
int16_t matrixC[3][3];
int16_t matrixB[3][3];
@@ -796,16 +756,12 @@ void DSPOp01()
matrixA[0][1] = -((Op01m * SinAz >> 15) * CosAy >> 15);
matrixA[0][2] = Op01m * SinAy >> 15;
- matrixA[1][0] = ((Op01m * SinAz >> 15) * CosAx >> 15) + (((
- Op01m * CosAz >> 15) * SinAx >> 15) * SinAy >> 15);
- matrixA[1][1] = ((Op01m * CosAz >> 15) * CosAx >> 15) - (((
- Op01m * SinAz >> 15) * SinAx >> 15) * SinAy >> 15);
+ matrixA[1][0] = ((Op01m * SinAz >> 15) * CosAx >> 15) + (((Op01m * CosAz >> 15) * SinAx >> 15) * SinAy >> 15);
+ matrixA[1][1] = ((Op01m * CosAz >> 15) * CosAx >> 15) - (((Op01m * SinAz >> 15) * SinAx >> 15) * SinAy >> 15);
matrixA[1][2] = -((Op01m * SinAx >> 15) * CosAy >> 15);
- matrixA[2][0] = ((Op01m * SinAz >> 15) * SinAx >> 15) - (((
- Op01m * CosAz >> 15) * CosAx >> 15) * SinAy >> 15);
- matrixA[2][1] = ((Op01m * CosAz >> 15) * SinAx >> 15) + (((
- Op01m * SinAz >> 15) * CosAx >> 15) * SinAy >> 15);
+ matrixA[2][0] = ((Op01m * SinAz >> 15) * SinAx >> 15) - (((Op01m * CosAz >> 15) * CosAx >> 15) * SinAy >> 15);
+ matrixA[2][1] = ((Op01m * CosAz >> 15) * SinAx >> 15) + (((Op01m * SinAz >> 15) * CosAx >> 15) * SinAy >> 15);
matrixA[2][2] = (Op01m * CosAx >> 15) * CosAy >> 15;
}
@@ -824,16 +780,12 @@ void DSPOp11()
matrixB[0][1] = -((Op11m * SinAz >> 15) * CosAy >> 15);
matrixB[0][2] = Op11m * SinAy >> 15;
- matrixB[1][0] = ((Op11m * SinAz >> 15) * CosAx >> 15) + (((
- Op11m * CosAz >> 15) * SinAx >> 15) * SinAy >> 15);
- matrixB[1][1] = ((Op11m * CosAz >> 15) * CosAx >> 15) - (((
- Op11m * SinAz >> 15) * SinAx >> 15) * SinAy >> 15);
+ matrixB[1][0] = ((Op11m * SinAz >> 15) * CosAx >> 15) + (((Op11m * CosAz >> 15) * SinAx >> 15) * SinAy >> 15);
+ matrixB[1][1] = ((Op11m * CosAz >> 15) * CosAx >> 15) - (((Op11m * SinAz >> 15) * SinAx >> 15) * SinAy >> 15);
matrixB[1][2] = -((Op11m * SinAx >> 15) * CosAy >> 15);
- matrixB[2][0] = ((Op11m * SinAz >> 15) * SinAx >> 15) - (((
- Op11m * CosAz >> 15) * CosAx >> 15) * SinAy >> 15);
- matrixB[2][1] = ((Op11m * CosAz >> 15) * SinAx >> 15) + (((
- Op11m * SinAz >> 15) * CosAx >> 15) * SinAy >> 15);
+ matrixB[2][0] = ((Op11m * SinAz >> 15) * SinAx >> 15) - (((Op11m * CosAz >> 15) * CosAx >> 15) * SinAy >> 15);
+ matrixB[2][1] = ((Op11m * CosAz >> 15) * SinAx >> 15) + (((Op11m * SinAz >> 15) * CosAx >> 15) * SinAy >> 15);
matrixB[2][2] = (Op11m * CosAx >> 15) * CosAy >> 15;
}
@@ -852,16 +804,12 @@ void DSPOp21()
matrixC[0][1] = -((Op21m * SinAz >> 15) * CosAy >> 15);
matrixC[0][2] = Op21m * SinAy >> 15;
- matrixC[1][0] = ((Op21m * SinAz >> 15) * CosAx >> 15) + (((
- Op21m * CosAz >> 15) * SinAx >> 15) * SinAy >> 15);
- matrixC[1][1] = ((Op21m * CosAz >> 15) * CosAx >> 15) - (((
- Op21m * SinAz >> 15) * SinAx >> 15) * SinAy >> 15);
+ matrixC[1][0] = ((Op21m * SinAz >> 15) * CosAx >> 15) + (((Op21m * CosAz >> 15) * SinAx >> 15) * SinAy >> 15);
+ matrixC[1][1] = ((Op21m * CosAz >> 15) * CosAx >> 15) - (((Op21m * SinAz >> 15) * SinAx >> 15) * SinAy >> 15);
matrixC[1][2] = -((Op21m * SinAx >> 15) * CosAy >> 15);
- matrixC[2][0] = ((Op21m * SinAz >> 15) * SinAx >> 15) - (((
- Op21m * CosAz >> 15) * CosAx >> 15) * SinAy >> 15);
- matrixC[2][1] = ((Op21m * CosAz >> 15) * SinAx >> 15) + (((
- Op21m * SinAz >> 15) * CosAx >> 15) * SinAy >> 15);
+ matrixC[2][0] = ((Op21m * SinAz >> 15) * SinAx >> 15) - (((Op21m * CosAz >> 15) * CosAx >> 15) * SinAy >> 15);
+ matrixC[2][1] = ((Op21m * CosAz >> 15) * SinAx >> 15) + (((Op21m * SinAz >> 15) * CosAx >> 15) * SinAy >> 15);
matrixC[2][2] = (Op21m * CosAx >> 15) * CosAy >> 15;
}
@@ -886,35 +834,23 @@ int16_t Op2DU;
void DSPOp0D()
{
- Op0DF = (Op0DX * matrixA[0][0] >> 15) + (Op0DY * matrixA[0][1] >> 15) +
- (Op0DZ * matrixA[0][2] >> 15);
- Op0DL = (Op0DX * matrixA[1][0] >> 15) + (Op0DY * matrixA[1][1] >> 15) +
- (Op0DZ * matrixA[1][2] >> 15);
- Op0DU = (Op0DX * matrixA[2][0] >> 15) + (Op0DY * matrixA[2][1] >> 15) +
- (Op0DZ * matrixA[2][2] >> 15);
-
+ Op0DF = (Op0DX * matrixA[0][0] >> 15) + (Op0DY * matrixA[0][1] >> 15) + (Op0DZ * matrixA[0][2] >> 15);
+ Op0DL = (Op0DX * matrixA[1][0] >> 15) + (Op0DY * matrixA[1][1] >> 15) + (Op0DZ * matrixA[1][2] >> 15);
+ Op0DU = (Op0DX * matrixA[2][0] >> 15) + (Op0DY * matrixA[2][1] >> 15) + (Op0DZ * matrixA[2][2] >> 15);
}
void DSPOp1D()
{
- Op1DF = (Op1DX * matrixB[0][0] >> 15) + (Op1DY * matrixB[0][1] >> 15) +
- (Op1DZ * matrixB[0][2] >> 15);
- Op1DL = (Op1DX * matrixB[1][0] >> 15) + (Op1DY * matrixB[1][1] >> 15) +
- (Op1DZ * matrixB[1][2] >> 15);
- Op1DU = (Op1DX * matrixB[2][0] >> 15) + (Op1DY * matrixB[2][1] >> 15) +
- (Op1DZ * matrixB[2][2] >> 15);
-
+ Op1DF = (Op1DX * matrixB[0][0] >> 15) + (Op1DY * matrixB[0][1] >> 15) + (Op1DZ * matrixB[0][2] >> 15);
+ Op1DL = (Op1DX * matrixB[1][0] >> 15) + (Op1DY * matrixB[1][1] >> 15) + (Op1DZ * matrixB[1][2] >> 15);
+ Op1DU = (Op1DX * matrixB[2][0] >> 15) + (Op1DY * matrixB[2][1] >> 15) + (Op1DZ * matrixB[2][2] >> 15);
}
void DSPOp2D()
{
- Op2DF = (Op2DX * matrixC[0][0] >> 15) + (Op2DY * matrixC[0][1] >> 15) +
- (Op2DZ * matrixC[0][2] >> 15);
- Op2DL = (Op2DX * matrixC[1][0] >> 15) + (Op2DY * matrixC[1][1] >> 15) +
- (Op2DZ * matrixC[1][2] >> 15);
- Op2DU = (Op2DX * matrixC[2][0] >> 15) + (Op2DY * matrixC[2][1] >> 15) +
- (Op2DZ * matrixC[2][2] >> 15);
-
+ Op2DF = (Op2DX * matrixC[0][0] >> 15) + (Op2DY * matrixC[0][1] >> 15) + (Op2DZ * matrixC[0][2] >> 15);
+ Op2DL = (Op2DX * matrixC[1][0] >> 15) + (Op2DY * matrixC[1][1] >> 15) + (Op2DZ * matrixC[1][2] >> 15);
+ Op2DU = (Op2DX * matrixC[2][0] >> 15) + (Op2DY * matrixC[2][1] >> 15) + (Op2DZ * matrixC[2][2] >> 15);
}
int16_t Op03F;
@@ -938,35 +874,23 @@ int16_t Op23Z;
void DSPOp03()
{
- Op03X = (Op03F * matrixA[0][0] >> 15) + (Op03L * matrixA[1][0] >> 15) +
- (Op03U * matrixA[2][0] >> 15);
- Op03Y = (Op03F * matrixA[0][1] >> 15) + (Op03L * matrixA[1][1] >> 15) +
- (Op03U * matrixA[2][1] >> 15);
- Op03Z = (Op03F * matrixA[0][2] >> 15) + (Op03L * matrixA[1][2] >> 15) +
- (Op03U * matrixA[2][2] >> 15);
-
+ Op03X = (Op03F * matrixA[0][0] >> 15) + (Op03L * matrixA[1][0] >> 15) + (Op03U * matrixA[2][0] >> 15);
+ Op03Y = (Op03F * matrixA[0][1] >> 15) + (Op03L * matrixA[1][1] >> 15) + (Op03U * matrixA[2][1] >> 15);
+ Op03Z = (Op03F * matrixA[0][2] >> 15) + (Op03L * matrixA[1][2] >> 15) + (Op03U * matrixA[2][2] >> 15);
}
void DSPOp13()
{
- Op13X = (Op13F * matrixB[0][0] >> 15) + (Op13L * matrixB[1][0] >> 15) +
- (Op13U * matrixB[2][0] >> 15);
- Op13Y = (Op13F * matrixB[0][1] >> 15) + (Op13L * matrixB[1][1] >> 15) +
- (Op13U * matrixB[2][1] >> 15);
- Op13Z = (Op13F * matrixB[0][2] >> 15) + (Op13L * matrixB[1][2] >> 15) +
- (Op13U * matrixB[2][2] >> 15);
-
+ Op13X = (Op13F * matrixB[0][0] >> 15) + (Op13L * matrixB[1][0] >> 15) + (Op13U * matrixB[2][0] >> 15);
+ Op13Y = (Op13F * matrixB[0][1] >> 15) + (Op13L * matrixB[1][1] >> 15) + (Op13U * matrixB[2][1] >> 15);
+ Op13Z = (Op13F * matrixB[0][2] >> 15) + (Op13L * matrixB[1][2] >> 15) + (Op13U * matrixB[2][2] >> 15);
}
void DSPOp23()
{
- Op23X = (Op23F * matrixC[0][0] >> 15) + (Op23L * matrixC[1][0] >> 15) +
- (Op23U * matrixC[2][0] >> 15);
- Op23Y = (Op23F * matrixC[0][1] >> 15) + (Op23L * matrixC[1][1] >> 15) +
- (Op23U * matrixC[2][1] >> 15);
- Op23Z = (Op23F * matrixC[0][2] >> 15) + (Op23L * matrixC[1][2] >> 15) +
- (Op23U * matrixC[2][2] >> 15);
-
+ Op23X = (Op23F * matrixC[0][0] >> 15) + (Op23L * matrixC[1][0] >> 15) + (Op23U * matrixC[2][0] >> 15);
+ Op23Y = (Op23F * matrixC[0][1] >> 15) + (Op23L * matrixC[1][1] >> 15) + (Op23U * matrixC[2][1] >> 15);
+ Op23Z = (Op23F * matrixC[0][2] >> 15) + (Op23L * matrixC[1][2] >> 15) + (Op23U * matrixC[2][2] >> 15);
}
int16_t Op14Zr;
@@ -986,8 +910,7 @@ void DSPOp14()
DSP1_Inverse(DSP1_Cos(Op14Xr), 0, &CSec, &ESec);
// Rotation Around Z
- DSP1_NormalizeDouble(Op14U * DSP1_Cos(Op14Yr) - Op14F * DSP1_Sin(Op14Yr), &C,
- &E);
+ DSP1_NormalizeDouble(Op14U * DSP1_Cos(Op14Yr) - Op14F * DSP1_Sin(Op14Yr), &C, &E);
E = ESec - E;
@@ -996,12 +919,10 @@ void DSPOp14()
Op14Zrr = Op14Zr + DSP1_Truncate(C, E);
// Rotation Around X
- Op14Xrr = Op14Xr + (Op14U * DSP1_Sin(Op14Yr) >> 15) + (Op14F * DSP1_Cos(
- Op14Yr) >> 15);
+ Op14Xrr = Op14Xr + (Op14U * DSP1_Sin(Op14Yr) >> 15) + (Op14F * DSP1_Cos(Op14Yr) >> 15);
// Rotation Around Y
- DSP1_NormalizeDouble(Op14U * DSP1_Cos(Op14Yr) + Op14F * DSP1_Sin(Op14Yr), &C,
- &E);
+ DSP1_NormalizeDouble(Op14U * DSP1_Cos(Op14Yr) + Op14F * DSP1_Sin(Op14Yr), &C, &E);
E = ESec - E;
@@ -1068,23 +989,17 @@ int16_t Op2BS;
void DSPOp0B()
{
- Op0BS = (Op0BX * matrixA[0][0] + Op0BY * matrixA[0][1] + Op0BZ * matrixA[0][2])
- >> 15;
-
+ Op0BS = (Op0BX * matrixA[0][0] + Op0BY * matrixA[0][1] + Op0BZ * matrixA[0][2]) >> 15;
}
void DSPOp1B()
{
- Op1BS = (Op1BX * matrixB[0][0] + Op1BY * matrixB[0][1] + Op1BZ * matrixB[0][2])
- >> 15;
-
+ Op1BS = (Op1BX * matrixB[0][0] + Op1BY * matrixB[0][1] + Op1BZ * matrixB[0][2]) >> 15;
}
void DSPOp2B()
{
- Op2BS = (Op2BX * matrixC[0][0] + Op2BY * matrixC[0][1] + Op2BZ * matrixC[0][2])
- >> 15;
-
+ Op2BS = (Op2BX * matrixC[0][0] + Op2BY * matrixC[0][1] + Op2BZ * matrixC[0][2]) >> 15;
}
int16_t Op08X, Op08Y, Op08Z, Op08Ll, Op08Lh;
@@ -1094,7 +1009,6 @@ void DSPOp08()
int32_t Op08Size = (Op08X * Op08X + Op08Y * Op08Y + Op08Z * Op08Z) << 1;
Op08Ll = Op08Size & 0xffff;
Op08Lh = (Op08Size >> 16) & 0xffff;
-
}
int16_t Op18X, Op18Y, Op18Z, Op18R, Op18D;
@@ -1102,7 +1016,6 @@ int16_t Op18X, Op18Y, Op18Z, Op18R, Op18D;
void DSPOp18()
{
Op18D = (Op18X * Op18X + Op18Y * Op18Y + Op18Z * Op18Z - Op18R * Op18R) >> 15;
-
}
int16_t Op38X, Op38Y, Op38Z, Op38R, Op38D;
@@ -1111,7 +1024,6 @@ void DSPOp38()
{
Op38D = (Op38X * Op38X + Op38Y * Op38Y + Op38Z * Op38Z - Op38R * Op38R) >> 15;
Op38D++;
-
}
int16_t Op28X;
@@ -1126,19 +1038,18 @@ void DSPOp28()
if (Radius == 0) Op28R = 0;
else
{
- int16_t C, E;
+ int16_t C, E, Pos, Node1, Node2;
DSP1_NormalizeDouble(Radius, &C, &E);
if (E & 1) C = C * 0x4000 >> 15;
- int16_t Pos = C * 0x0040 >> 15;
+ Pos = C * 0x0040 >> 15;
- int16_t Node1 = DSP1ROM[0x00d5 + Pos];
- int16_t Node2 = DSP1ROM[0x00d6 + Pos];
+ Node1 = DSP1ROM[0x00d5 + Pos];
+ Node2 = DSP1ROM[0x00d6 + Pos];
Op28R = ((Node2 - Node1) * (C & 0x1ff) >> 9) + Node1;
Op28R >>= (E >> 1);
}
-
}
int16_t Op1CX, Op1CY, Op1CZ;
@@ -1169,7 +1080,6 @@ void DSPOp1C()
Op1CZ1 = (Op1CZBR * DSP1_Cos(Op1CX) >> 15) - (Op1CYBR * DSP1_Sin(Op1CX) >> 15);
Op1CYAR = Op1CY1;
Op1CZAR = Op1CZ1;
-
}
uint16_t Op0FRamsize;
@@ -1178,7 +1088,6 @@ uint16_t Op0FPass;
void DSPOp0F()
{
Op0FPass = 0x0000;
-
}
int16_t Op2FUnknown;
diff --git a/source/globals.c b/source/globals.c
index eecb297..b99e488 100644
--- a/source/globals.c
+++ b/source/globals.c
@@ -205,27 +205,26 @@ uint8_t APUROM [64] =
0xF4, 0xC4, 0xF4, 0xDD, 0x5D, 0xD0, 0xDB, 0x1F, 0x00, 0x00, 0xC0, 0xFF
};
-
// Raw SPC700 instruction cycle lengths
uint16_t S9xAPUCycleLengths [256] =
{
/* 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, a, b, c, d, e, f, */
- /* 00 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 6, 8,
- /* 10 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 4, 6,
- /* 20 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 5, 4,
- /* 30 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 3, 8,
- /* 40 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 6, 6,
- /* 50 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 4, 5, 2, 2, 4, 3,
- /* 60 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 5, 5,
- /* 70 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 6,
- /* 80 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 2, 4, 5,
+ /* 00 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 6, 8,
+ /* 10 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 4, 6,
+ /* 20 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 5, 4,
+ /* 30 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 3, 8,
+ /* 40 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 6, 6,
+ /* 50 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 4, 5, 2, 2, 4, 3,
+ /* 60 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 5, 5,
+ /* 70 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 6,
+ /* 80 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 2, 4, 5,
/* 90 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 12, 5,
- /* a0 */ 3, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 2, 4, 4,
- /* b0 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 4,
- /* c0 */ 3, 8, 4, 5, 4, 5, 4, 7, 2, 5, 6, 4, 5, 2, 4, 9,
- /* d0 */ 2, 8, 4, 5, 5, 6, 6, 7, 4, 5, 4, 5, 2, 2, 6, 3,
- /* e0 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 4, 5, 3, 4, 3, 4, 3,
- /* f0 */ 2, 8, 4, 5, 4, 5, 5, 6, 3, 4, 5, 4, 2, 2, 4, 3
+ /* a0 */ 3, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 2, 4, 4,
+ /* b0 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 4,
+ /* c0 */ 3, 8, 4, 5, 4, 5, 4, 7, 2, 5, 6, 4, 5, 2, 4, 9,
+ /* d0 */ 2, 8, 4, 5, 5, 6, 6, 7, 4, 5, 4, 5, 2, 2, 6, 3,
+ /* e0 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 4, 5, 3, 4, 3, 4, 3,
+ /* f0 */ 2, 8, 4, 5, 4, 5, 5, 6, 3, 4, 5, 4, 2, 2, 4, 3
};
// Actual data used by CPU emulation, will be scaled by APUReset routine
@@ -233,20 +232,20 @@ uint16_t S9xAPUCycleLengths [256] =
uint16_t S9xAPUCycles [256] =
{
/* 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, a, b, c, d, e, f, */
- /* 00 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 6, 8,
- /* 10 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 4, 6,
- /* 20 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 5, 4,
- /* 30 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 3, 8,
- /* 40 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 6, 6,
- /* 50 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 4, 5, 2, 2, 4, 3,
- /* 60 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 5, 5,
- /* 70 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 6,
- /* 80 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 2, 4, 5,
+ /* 00 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 6, 8,
+ /* 10 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 4, 6,
+ /* 20 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 4, 5, 4,
+ /* 30 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 6, 5, 2, 2, 3, 8,
+ /* 40 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 6, 6,
+ /* 50 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 4, 5, 2, 2, 4, 3,
+ /* 60 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 4, 5, 5,
+ /* 70 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 6,
+ /* 80 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 6, 5, 4, 5, 2, 4, 5,
/* 90 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 12, 5,
- /* a0 */ 3, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 2, 4, 4,
- /* b0 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 4,
- /* c0 */ 3, 8, 4, 5, 4, 5, 4, 7, 2, 5, 6, 4, 5, 2, 4, 9,
- /* d0 */ 2, 8, 4, 5, 5, 6, 6, 7, 4, 5, 4, 5, 2, 2, 6, 3,
- /* e0 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 4, 5, 3, 4, 3, 4, 3,
- /* f0 */ 2, 8, 4, 5, 4, 5, 5, 6, 3, 4, 5, 4, 2, 2, 4, 3
+ /* a0 */ 3, 8, 4, 5, 3, 4, 3, 6, 2, 6, 4, 4, 5, 2, 4, 4,
+ /* b0 */ 2, 8, 4, 5, 4, 5, 5, 6, 5, 5, 5, 5, 2, 2, 3, 4,
+ /* c0 */ 3, 8, 4, 5, 4, 5, 4, 7, 2, 5, 6, 4, 5, 2, 4, 9,
+ /* d0 */ 2, 8, 4, 5, 5, 6, 6, 7, 4, 5, 4, 5, 2, 2, 6, 3,
+ /* e0 */ 2, 8, 4, 5, 3, 4, 3, 6, 2, 4, 5, 3, 4, 3, 4, 3,
+ /* f0 */ 2, 8, 4, 5, 4, 5, 5, 6, 3, 4, 5, 4, 2, 2, 4, 3
};
diff --git a/source/port.h b/source/port.h
index bbe28c3..622027f 100644
--- a/source/port.h
+++ b/source/port.h
@@ -30,10 +30,8 @@
#define _MAX_EXT PATH_MAX
#define _MAX_PATH PATH_MAX
-void _makepath(char* path, const char* drive, const char* dir,
- const char* fname, const char* ext);
-void _splitpath(const char* path, char* drive, char* dir, char* fname,
- char* ext);
+void _makepath(char* path, const char* drive, const char* dir, const char* fname, const char* ext);
+void _splitpath(const char* path, char* drive, char* dir, char* fname, char* ext);
#else /* __WIN32__ */
#define strcasecmp stricmp
#define strncasecmp strnicmp
@@ -57,4 +55,31 @@ void _splitpath(const char* path, char* drive, char* dir, char* fname,
#define MIN(A,B) ((A) < (B) ? (A) : (B))
#define MAX(A,B) ((A) > (B) ? (A) : (B))
+/* Integer square root by Halleck's method, with Legalize's speedup */
+static inline int32_t _isqrt(int32_t val)
+{
+ int32_t squaredbit, remainder, root;
+
+ if (val < 1)
+ return 0;
+
+ squaredbit = 1 << 30;
+ remainder = val;
+ root = 0;
+
+ while (squaredbit > 0)
+ {
+ if (remainder >= (squaredbit | root))
+ {
+ remainder -= (squaredbit | root);
+ root >>= 1;
+ root |= squaredbit;
+ } else
+ root >>= 1;
+ squaredbit >>= 2;
+ }
+
+ return root;
+}
+
#endif
diff --git a/source/seta010.c b/source/seta010.c
index 0e64248..89ae4f8 100644
--- a/source/seta010.c
+++ b/source/seta010.c
@@ -30,12 +30,6 @@ const int16_t ST010_M7Scale[176] =
0x002d, 0x002c, 0x002c, 0x002c, 0x002c, 0x002b, 0x002b, 0x002b
};
-// H-DMA hack
-bool seta_hack;
-
-//temporary Op04 requirement
-#include <math.h>
-
ST010_Regs ST010;
uint8_t S9xGetST010(uint32_t Address)
@@ -52,23 +46,23 @@ uint8_t S9xGetST010(uint32_t Address)
const int16_t ST010_SinTable[256] =
{
- 0x0000, 0x0324, 0x0648, 0x096a, 0x0c8c, 0x0fab, 0x12c8, 0x15e2,
- 0x18f9, 0x1c0b, 0x1f1a, 0x2223, 0x2528, 0x2826, 0x2b1f, 0x2e11,
- 0x30fb, 0x33df, 0x36ba, 0x398c, 0x3c56, 0x3f17, 0x41ce, 0x447a,
- 0x471c, 0x49b4, 0x4c3f, 0x4ebf, 0x5133, 0x539b, 0x55f5, 0x5842,
- 0x5a82, 0x5cb3, 0x5ed7, 0x60eb, 0x62f1, 0x64e8, 0x66cf, 0x68a6,
- 0x6a6d, 0x6c23, 0x6dc9, 0x6f5e, 0x70e2, 0x7254, 0x73b5, 0x7504,
- 0x7641, 0x776b, 0x7884, 0x7989, 0x7a7c, 0x7b5c, 0x7c29, 0x7ce3,
- 0x7d89, 0x7e1d, 0x7e9c, 0x7f09, 0x7f61, 0x7fa6, 0x7fd8, 0x7ff5,
- 0x7fff, 0x7ff5, 0x7fd8, 0x7fa6, 0x7f61, 0x7f09, 0x7e9c, 0x7e1d,
- 0x7d89, 0x7ce3, 0x7c29, 0x7b5c, 0x7a7c, 0x7989, 0x7884, 0x776b,
- 0x7641, 0x7504, 0x73b5, 0x7254, 0x70e2, 0x6f5e, 0x6dc9, 0x6c23,
- 0x6a6d, 0x68a6, 0x66cf, 0x64e8, 0x62f1, 0x60eb, 0x5ed7, 0x5cb3,
- 0x5a82, 0x5842, 0x55f5, 0x539b, 0x5133, 0x4ebf, 0x4c3f, 0x49b4,
- 0x471c, 0x447a, 0x41ce, 0x3f17, 0x3c56, 0x398c, 0x36ba, 0x33df,
- 0x30fb, 0x2e11, 0x2b1f, 0x2826, 0x2528, 0x2223, 0x1f1a, 0x1c0b,
- 0x18f8, 0x15e2, 0x12c8, 0x0fab, 0x0c8c, 0x096a, 0x0648, 0x0324,
- 0x0000, -0x0324, -0x0648, -0x096b, -0x0c8c, -0x0fab, -0x12c8, -0x15e2,
+ 0x0000, 0x0324, 0x0648, 0x096a, 0x0c8c, 0x0fab, 0x12c8, 0x15e2,
+ 0x18f9, 0x1c0b, 0x1f1a, 0x2223, 0x2528, 0x2826, 0x2b1f, 0x2e11,
+ 0x30fb, 0x33df, 0x36ba, 0x398c, 0x3c56, 0x3f17, 0x41ce, 0x447a,
+ 0x471c, 0x49b4, 0x4c3f, 0x4ebf, 0x5133, 0x539b, 0x55f5, 0x5842,
+ 0x5a82, 0x5cb3, 0x5ed7, 0x60eb, 0x62f1, 0x64e8, 0x66cf, 0x68a6,
+ 0x6a6d, 0x6c23, 0x6dc9, 0x6f5e, 0x70e2, 0x7254, 0x73b5, 0x7504,
+ 0x7641, 0x776b, 0x7884, 0x7989, 0x7a7c, 0x7b5c, 0x7c29, 0x7ce3,
+ 0x7d89, 0x7e1d, 0x7e9c, 0x7f09, 0x7f61, 0x7fa6, 0x7fd8, 0x7ff5,
+ 0x7fff, 0x7ff5, 0x7fd8, 0x7fa6, 0x7f61, 0x7f09, 0x7e9c, 0x7e1d,
+ 0x7d89, 0x7ce3, 0x7c29, 0x7b5c, 0x7a7c, 0x7989, 0x7884, 0x776b,
+ 0x7641, 0x7504, 0x73b5, 0x7254, 0x70e2, 0x6f5e, 0x6dc9, 0x6c23,
+ 0x6a6d, 0x68a6, 0x66cf, 0x64e8, 0x62f1, 0x60eb, 0x5ed7, 0x5cb3,
+ 0x5a82, 0x5842, 0x55f5, 0x539b, 0x5133, 0x4ebf, 0x4c3f, 0x49b4,
+ 0x471c, 0x447a, 0x41ce, 0x3f17, 0x3c56, 0x398c, 0x36ba, 0x33df,
+ 0x30fb, 0x2e11, 0x2b1f, 0x2826, 0x2528, 0x2223, 0x1f1a, 0x1c0b,
+ 0x18f8, 0x15e2, 0x12c8, 0x0fab, 0x0c8c, 0x096a, 0x0648, 0x0324,
+ 0x0000, -0x0324, -0x0648, -0x096b, -0x0c8c, -0x0fab, -0x12c8, -0x15e2,
-0x18f9, -0x1c0b, -0x1f1a, -0x2223, -0x2528, -0x2826, -0x2b1f, -0x2e11,
-0x30fb, -0x33df, -0x36ba, -0x398d, -0x3c56, -0x3f17, -0x41ce, -0x447a,
-0x471c, -0x49b4, -0x4c3f, -0x4ebf, -0x5133, -0x539b, -0x55f5, -0x5842,
@@ -228,8 +222,7 @@ int16_t ST010_Cos(int16_t Theta)
return ST010_SinTable[((Theta + 0x4000) >> 8) & 0xff];
}
-void ST010_OP01(int16_t x0, int16_t y0, int16_t* x1, int16_t* y1, int16_t* Quadrant,
- int16_t* Theta)
+void ST010_OP01(int16_t x0, int16_t y0, int16_t* x1, int16_t* y1, int16_t* Quadrant, int16_t* Theta)
{
if ((x0 < 0) && (y0 < 0))
{
@@ -258,8 +251,10 @@ void ST010_OP01(int16_t x0, int16_t y0, int16_t* x1, int16_t* y1, int16_t* Quadr
while ((*x1 > 0x1f) || (*y1 > 0x1f))
{
- if (*x1 > 1) *x1 >>= 1;
- if (*y1 > 1) *y1 >>= 1;
+ if (*x1 > 1)
+ *x1 >>= 1;
+ if (*y1 > 1)
+ *y1 >>= 1;
}
if (*y1 == 0) *Quadrant += 0x4000;
@@ -346,8 +341,7 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
{
#if defined(FAST_LSB_WORD_ACCESS) && !defined(ANDROID)
/* TODO - FIXME */
- ST010_SortDrivers(*(int16_t*)&Memory.SRAM[0x0024], (uint16_t*)(Memory.SRAM + 0x0040),
- (uint16_t*)(Memory.SRAM + 0x0080));
+ ST010_SortDrivers(*(int16_t*)&Memory.SRAM[0x0024], (uint16_t*)(Memory.SRAM + 0x0040), (uint16_t*)(Memory.SRAM + 0x0080));
#else
uint16_t Places[32];
uint16_t Positions = ST010_WORD(0x0024);
@@ -391,13 +385,11 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
#if defined(FAST_LSB_WORD_ACCESS) && !defined(ANDROID)
/* TODO - FIXME */
ST010_Scale(*(int16_t*)&Memory.SRAM[0x0004], *(int16_t*)&Memory.SRAM[0x0000],
- *(int16_t*)&Memory.SRAM[0x0002],
- (int32_t*)&Memory.SRAM[0x0010], (int32_t*)&Memory.SRAM[0x0014]);
+ *(int16_t*)&Memory.SRAM[0x0002], (int32_t*)&Memory.SRAM[0x0010], (int32_t*)&Memory.SRAM[0x0014]);
#else
int32_t x1, y1;
- ST010_Scale(ST010_WORD(0x0004), ST010_WORD(0x0000), ST010_WORD(0x0002), &x1,
- &y1);
+ ST010_Scale(ST010_WORD(0x0004), ST010_WORD(0x0000), ST010_WORD(0x0002), &x1, &y1);
Memory.SRAM[0x0010] = (uint8_t)(x1);
Memory.SRAM[0x0011] = (uint8_t)(x1 >> 8);
@@ -423,8 +415,7 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
{
#if defined(FAST_LSB_WORD_ACCESS) && !defined(ANDROID)
/* TODO - FIXME */
- ST010_Multiply(*(int16_t*)&Memory.SRAM[0x0000], *(int16_t*)&Memory.SRAM[0x0002],
- (int32_t*)&Memory.SRAM[0x0010]);
+ ST010_Multiply(*(int16_t*)&Memory.SRAM[0x0000], *(int16_t*)&Memory.SRAM[0x0002], (int32_t*)&Memory.SRAM[0x0010]);
#else
int32_t Product;
@@ -501,13 +492,11 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
#if defined(FAST_LSB_WORD_ACCESS) && !defined(ANDROID)
/* TODO - FIXME */
ST010_Rotate(*(int16_t*)&Memory.SRAM[0x0004], *(int16_t*)&Memory.SRAM[0x0000],
- *(int16_t*)&Memory.SRAM[0x0002],
- (int16_t*)&Memory.SRAM[0x0010], (int16_t*)&Memory.SRAM[0x0012]);
+ *(int16_t*)&Memory.SRAM[0x0002], (int16_t*)&Memory.SRAM[0x0010], (int16_t*)&Memory.SRAM[0x0012]);
#else
int16_t x1, y1;
- ST010_Rotate(ST010_WORD(0x0004), ST010_WORD(0x0000), ST010_WORD(0x0002), &x1,
- &y1);
+ ST010_Rotate(ST010_WORD(0x0004), ST010_WORD(0x0000), ST010_WORD(0x0002), &x1, &y1);
Memory.SRAM[0x0010] = (uint8_t)(x1);
Memory.SRAM[0x0011] = (uint8_t)(x1 >> 8);
@@ -562,7 +551,7 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
x = Memory.SRAM[0] | (Memory.SRAM[1] << 8);
y = Memory.SRAM[2] | (Memory.SRAM[3] << 8);
#endif
- square = (int16_t)sqrt((double)(y * y + x * x));
+ square = (int16_t)_isqrt((int32_t) x * x + (int32_t) y * y);
#if defined(FAST_LSB_WORD_ACCESS) && !defined(ANDROID)
/* TODO - FIXME */
@@ -624,7 +613,7 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
ST010_OP01(dy, dx, &a1, &b1, &c1, (int16_t*)&o1);
// check for wrapping
- if (abs(o1 - rot) > 0x8000)
+ if (ABS(o1 - rot) > 0x8000)
{
o1 += 0x8000;
rot += 0x8000;
@@ -636,12 +625,12 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
old_speed = speed;
// special case
- if (abs(o1 - rot) == 0x8000)
+ if (ABS(o1 - rot) == 0x8000)
speed = 0x100;
// slow down for sharp curves
- else if (abs(o1 - rot) >= 0x1000)
+ else if (ABS(o1 - rot) >= 0x1000)
{
- uint32_t slow = abs(o1 - rot);
+ uint32_t slow = ABS(o1 - rot);
slow >>= 4; // scaling
speed -= slow;
}
@@ -657,7 +646,7 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
}
// prevent negative/positive overflow
- if (abs(old_speed - speed) > 0x8000)
+ if (ABS(old_speed - speed) > 0x8000)
{
if (old_speed < speed) speed = 0;
else speed = 0xff00;
@@ -717,13 +706,8 @@ void S9xSetST010(uint32_t Address, uint8_t Byte)
Memory.SRAM[0x00D5] = (uint8_t)(speed >> 8);
Memory.SRAM[0x00DC] = (uint8_t)(flags);
Memory.SRAM[0x00DD] = (uint8_t)(flags >> 8);
-
break;
}
-
- default:
- printf("Unknown Op\n");
- break;
}
// lower signal: op processed