Merge pull request #7 from skidau/HLE-BIOS-SndDriver-PhantasyStarColl
HLE BIOS functions for sound driver
This commit is contained in:
commit
06ffccc3f9
|
@ -2342,6 +2342,28 @@ void CPUSoftwareInterrupt(int comment)
|
||||||
else
|
else
|
||||||
soundResume();
|
soundResume();
|
||||||
break;
|
break;
|
||||||
|
case 0x1A:
|
||||||
|
BIOS_SndDriverInit();
|
||||||
|
SWITicks = 252000;
|
||||||
|
break;
|
||||||
|
case 0x1B:
|
||||||
|
BIOS_SndDriverMode();
|
||||||
|
SWITicks = 280000;
|
||||||
|
break;
|
||||||
|
case 0x1C:
|
||||||
|
BIOS_SndDriverMain();
|
||||||
|
SWITicks = 11050;//avg
|
||||||
|
break;
|
||||||
|
case 0x1D:
|
||||||
|
BIOS_SndDriverVSync();
|
||||||
|
SWITicks = 44;
|
||||||
|
break;
|
||||||
|
case 0x1E:
|
||||||
|
BIOS_SndChannelClear();
|
||||||
|
break;
|
||||||
|
case 0x28:
|
||||||
|
BIOS_SndDriverVSyncOff();
|
||||||
|
break;
|
||||||
case 0x1F:
|
case 0x1F:
|
||||||
BIOS_MidiKey2Freq();
|
BIOS_MidiKey2Freq();
|
||||||
break;
|
break;
|
||||||
|
|
703
src/gba/bios.cpp
703
src/gba/bios.cpp
|
@ -1108,6 +1108,709 @@ void BIOS_Sqrt()
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#define ADBITS_MASK 0x3FU
|
||||||
|
u32 const base1 = 0x040000C0;
|
||||||
|
u32 const base2 = 0x04000080;
|
||||||
|
|
||||||
|
static bool BIOS_SndDriver_ba4(u32 r0, u32 r4r12) // 0xba4
|
||||||
|
{
|
||||||
|
if (r4r12)
|
||||||
|
{
|
||||||
|
r4r12 = r4r12 & ~0xFE000000;
|
||||||
|
r4r12 += r0;
|
||||||
|
if (!((r0 & 0x0E000000) && (r4r12 & 0x0E000000)))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void BIOS_SndDriver_b4c(u32 r0, u32 r1, u32 r2) // 0xb4c
|
||||||
|
{
|
||||||
|
// @r4
|
||||||
|
u32 r4 = 4 * r2 & 0x7FFFFF;
|
||||||
|
bool ok = BIOS_SndDriver_ba4(r0, r4); // aka b9c
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
int v3; // r4@1
|
||||||
|
int v4; // r0@1
|
||||||
|
int v5; // r1@1
|
||||||
|
int v6; // r2@1
|
||||||
|
char v7; // zf@1
|
||||||
|
signed int v8; // r5@2
|
||||||
|
int v9; // r5@4
|
||||||
|
int v10; // r3@6
|
||||||
|
int v11; // r3@10
|
||||||
|
unsigned int v12; // r4@11
|
||||||
|
unsigned short v13; // r3@13
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// 0b56
|
||||||
|
if ( !ok )
|
||||||
|
{
|
||||||
|
u32 r5 = 0; //v8
|
||||||
|
if ( r2 >= (1<<(27-1)) ) //v6
|
||||||
|
{
|
||||||
|
r5 = r1 + r4;
|
||||||
|
if ( r2 >= (1<<(25-1)) )
|
||||||
|
{
|
||||||
|
u32 r3 = CPUReadMemory(r0);
|
||||||
|
while ( r1 < r5 )
|
||||||
|
{
|
||||||
|
CPUWriteMemory(r1, r3);
|
||||||
|
r1 += 4;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else // @todo 0b6e
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
while ( v5 < v9 )
|
||||||
|
{
|
||||||
|
v11 = *(_DWORD *)v4;
|
||||||
|
v4 += 4;
|
||||||
|
*(_DWORD *)v5 = v11;
|
||||||
|
v5 += 4;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else // @todo 0b78
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
v12 = (unsigned int)v3 >> 1;
|
||||||
|
if ( __CFSHR__(v6, 25) )
|
||||||
|
{
|
||||||
|
v13 = *(_WORD *)v4;
|
||||||
|
while ( v8 < (signed int)v12 )
|
||||||
|
{
|
||||||
|
*(_WORD *)(v5 + v8) = v13;
|
||||||
|
v8 += 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
while ( v8 < (signed int)v12 )
|
||||||
|
{
|
||||||
|
*(_WORD *)(v5 + v8) = *(_WORD *)(v4 + v8);
|
||||||
|
v8 += 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// 0x0b96
|
||||||
|
}
|
||||||
|
|
||||||
|
static s32 BIOS_SndDriver_3e4(u32 const r0a, u32 const r1a) // 0x3e4
|
||||||
|
{
|
||||||
|
s32 r0 = r1a;
|
||||||
|
s32 r1 = r0a;
|
||||||
|
u32 v5 = r0 & 0x80000000;
|
||||||
|
s32 r12;
|
||||||
|
s32 r2;
|
||||||
|
bool gtr;
|
||||||
|
|
||||||
|
if ( (r1 & 0x80000000 & 0x80000000) != 0 )
|
||||||
|
r1 = -r1;
|
||||||
|
r12 = r0; //v5 ^ (r0 >> 32);
|
||||||
|
if ( r0 < 0 )
|
||||||
|
r0 = -r0;
|
||||||
|
r2 = r1;
|
||||||
|
|
||||||
|
do
|
||||||
|
{
|
||||||
|
gtr = (r2 >= r0 >> 1);
|
||||||
|
if ( r2 <= r0 >> 1 )
|
||||||
|
r2 *= 2;
|
||||||
|
} while ( !gtr );
|
||||||
|
|
||||||
|
while ( 1 )
|
||||||
|
{
|
||||||
|
v5 += (r0 >= (u32)r2) + v5;
|
||||||
|
if ( r0 >= (u32)r2 )
|
||||||
|
r0 -= r2;
|
||||||
|
if ( r2 == r1 )
|
||||||
|
break;
|
||||||
|
r2 = (u32)r2 >> 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( !(r12 << 1) )
|
||||||
|
return -v5;
|
||||||
|
else
|
||||||
|
return v5;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void BIOS_SndDriverSub1(u32 p1) // 0x170a
|
||||||
|
{
|
||||||
|
u8 local1 = (p1 & 0x000F0000) >> 16; // param is r0
|
||||||
|
u32 const puser1 = CPUReadMemory(0x3007FF0); // 7FC0 + 0x30
|
||||||
|
|
||||||
|
// Store something
|
||||||
|
CPUWriteByte(puser1+8, local1);
|
||||||
|
|
||||||
|
u32 r0 = (0x31e8 + (local1 << 1)) - 0x20;
|
||||||
|
|
||||||
|
// @todo read from bios region
|
||||||
|
if (r0 == 0x31D0)
|
||||||
|
{
|
||||||
|
r0 = 0xE0;
|
||||||
|
}
|
||||||
|
else if (r0 == 0x31E0)
|
||||||
|
{
|
||||||
|
r0 = 0x2C0;
|
||||||
|
}
|
||||||
|
else r0 = CPUReadHalfWord(r0+0x1E);
|
||||||
|
CPUWriteMemory(puser1+0x10, r0);
|
||||||
|
|
||||||
|
u32 r1 = 0x630;
|
||||||
|
u32 const r4 = r0;
|
||||||
|
|
||||||
|
// 0x172c
|
||||||
|
r0 = BIOS_SndDriver_3e4(r0, r1);
|
||||||
|
CPUWriteByte(puser1+0xB, r0);
|
||||||
|
|
||||||
|
u32 x = 0x91d1b * r4;
|
||||||
|
r1 = x + 0x1388;
|
||||||
|
r0 = 0x1388 << 1;
|
||||||
|
r0 = BIOS_SndDriver_3e4(r0, r1);
|
||||||
|
CPUWriteMemory(puser1+0x14, r0);
|
||||||
|
|
||||||
|
r1 = 1 << 24;
|
||||||
|
r0 = BIOS_SndDriver_3e4(r0, r1) + 1;
|
||||||
|
r0 /= 2;
|
||||||
|
CPUWriteMemory(puser1+0x18, r0);
|
||||||
|
|
||||||
|
// 0x1750
|
||||||
|
u32 r4basesnd = 0x4000100;
|
||||||
|
r0 = r4;
|
||||||
|
r1 = 0x44940;
|
||||||
|
CPUWriteHalfWord(r4basesnd+2, 0);
|
||||||
|
r0 = BIOS_SndDriver_3e4(r0, r1);
|
||||||
|
r0 = (1<<16)-r0;
|
||||||
|
CPUWriteHalfWord(r4basesnd+0, r0);
|
||||||
|
|
||||||
|
// sub 0x18c8 is unrolled here
|
||||||
|
r1 = 0x5b << 9;
|
||||||
|
CPUWriteHalfWord(base1+6 , r1);
|
||||||
|
CPUWriteHalfWord(base1+12 , r1);
|
||||||
|
|
||||||
|
// 0x176a, @todo busy loop here
|
||||||
|
r0 = 0x4000000;
|
||||||
|
//do
|
||||||
|
{
|
||||||
|
r1 = CPUReadByte(r0+6);
|
||||||
|
} //while (r1 != 0x9F);
|
||||||
|
|
||||||
|
CPUWriteHalfWord(r4basesnd+2, 0x80);
|
||||||
|
}
|
||||||
|
|
||||||
|
void BIOS_SndDriverInit() // 0x166a
|
||||||
|
{
|
||||||
|
#ifdef GBA_LOGGING
|
||||||
|
if(systemVerbose & VERBOSE_SWI) {
|
||||||
|
log("SndDriverInit: WaveData=%08x mk=%08x fp=%08x\n",
|
||||||
|
reg[0].I,
|
||||||
|
reg[1].I,
|
||||||
|
reg[2].I);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
// 7FC0 + 0x30
|
||||||
|
u32 const puser1 = 0x3007FF0;
|
||||||
|
u32 const user1 = reg[0].I;
|
||||||
|
|
||||||
|
u32 base3 = 0x040000BC;
|
||||||
|
//u32 base4 = 0x03007FF0;
|
||||||
|
|
||||||
|
CPUWriteHalfWord(base1+6 , 0);
|
||||||
|
CPUWriteHalfWord(base1+12, 0);
|
||||||
|
|
||||||
|
CPUWriteHalfWord(base2+4, 0x8F);
|
||||||
|
CPUWriteHalfWord(base2+2, 0xA90E);
|
||||||
|
|
||||||
|
u16 val9 = CPUReadHalfWord(base2+9);
|
||||||
|
CPUWriteHalfWord(base2+9, val9&ADBITS_MASK); // DA?
|
||||||
|
|
||||||
|
CPUWriteMemory(base3+0, (user1 + 0x350)); //0x350, 640int
|
||||||
|
CPUWriteMemory(base1+0, 0x40000A0);
|
||||||
|
CPUWriteMemory(base1+8, 2224); //0x980
|
||||||
|
CPUWriteMemory(base1+12, 0x40000A4);
|
||||||
|
CPUWriteMemory(puser1, user1);
|
||||||
|
|
||||||
|
u32 const r2 = 0x050003EC;
|
||||||
|
u32 const sp = reg[13].I; // 0x03003c98;
|
||||||
|
CPUWriteMemory(sp, 0);
|
||||||
|
BIOS_SndDriver_b4c(sp, user1, r2);
|
||||||
|
|
||||||
|
// 0x16b0
|
||||||
|
CPUWriteByte(user1+0x6, 0x8);
|
||||||
|
CPUWriteByte(user1+0x7, 0xF);
|
||||||
|
CPUWriteMemory(user1+0x38, 0x2425);
|
||||||
|
CPUWriteMemory(user1+0x28, 0x1709);
|
||||||
|
CPUWriteMemory(user1+0x2C, 0x1709);
|
||||||
|
CPUWriteMemory(user1+0x30, 0x1709);
|
||||||
|
CPUWriteMemory(user1+0x3C, 0x1709);
|
||||||
|
CPUWriteMemory(user1+0x34, 0x3738);
|
||||||
|
|
||||||
|
BIOS_SndDriverSub1(0x40000);
|
||||||
|
|
||||||
|
CPUWriteMemory(user1, 0x68736D53); // this ret is common among funcs
|
||||||
|
}
|
||||||
|
|
||||||
|
void BIOS_SndDriverMode() //0x179c
|
||||||
|
{
|
||||||
|
u32 input = reg[0].I;
|
||||||
|
u32 const puser1 = CPUReadMemory(0x3007FF0); // 7FC0 + 0x30
|
||||||
|
u32 user1 = CPUReadMemory(puser1);
|
||||||
|
|
||||||
|
if ( user1 == 0x68736D53 )
|
||||||
|
{
|
||||||
|
CPUWriteMemory(puser1, (++user1)); // this guard is common for funcs, unify
|
||||||
|
|
||||||
|
// reverb values at bits 0...7
|
||||||
|
u8 revb = (input & 0xFF);
|
||||||
|
if ( revb )
|
||||||
|
{
|
||||||
|
revb>>=1; // shift out the 7th enable bit
|
||||||
|
CPUWriteByte(puser1+5, revb);
|
||||||
|
}
|
||||||
|
// direct sound multi channels at bits 8...11
|
||||||
|
u8 chc = (input & 0xF00)>>8;
|
||||||
|
if ( chc > 0 )
|
||||||
|
{
|
||||||
|
CPUWriteByte(puser1+6, chc);
|
||||||
|
u32 puser2 = puser1 + 7 + 0x49;
|
||||||
|
int count=12;
|
||||||
|
while (count--)
|
||||||
|
{
|
||||||
|
CPUWriteByte(puser2, 0);
|
||||||
|
puser2+=0x40;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// direct sound master volume at bits 12...15
|
||||||
|
u8 chv = (input & 0xF000)>>12;
|
||||||
|
if ( chv > 0 )
|
||||||
|
{
|
||||||
|
CPUWriteByte(puser1+7, chv);
|
||||||
|
}
|
||||||
|
// DA converter bits at bits 20...23
|
||||||
|
u32 dab = (input & 0x00B00000);
|
||||||
|
if ( dab )
|
||||||
|
{
|
||||||
|
dab &= 0x00300000;
|
||||||
|
dab >>= 0xE;
|
||||||
|
u8 adv = CPUReadByte(puser1+9) & ADBITS_MASK; // @todo verify offset
|
||||||
|
dab |= adv;
|
||||||
|
CPUWriteByte(puser1+9, dab);
|
||||||
|
}
|
||||||
|
// Playback frequency at bits 16...19
|
||||||
|
u32 pbf = (input & 0x000F0000);
|
||||||
|
if ( pbf )
|
||||||
|
{
|
||||||
|
// Modifies puser1/user1
|
||||||
|
BIOS_SndDriverVSyncOff();
|
||||||
|
|
||||||
|
// another sub at 180c
|
||||||
|
BIOS_SndDriverSub1(pbf);
|
||||||
|
}
|
||||||
|
CPUWriteMemory(puser1, (--user1));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void BIOS_SndDriverMain() // 0x1dc4 -> 0x08004024 phantasy star
|
||||||
|
{
|
||||||
|
//// Usually addr 0x2010928
|
||||||
|
u32 const puser1 = CPUReadMemory(0x3007FF0); // 7FC0 + 0x30, //@+sp14
|
||||||
|
u32 user1 = CPUReadMemory(puser1);
|
||||||
|
|
||||||
|
if ( user1 != 0x68736D53 )
|
||||||
|
return;
|
||||||
|
|
||||||
|
// main
|
||||||
|
CPUWriteMemory(puser1, (++user1)); // this guard is common for funcs, unify
|
||||||
|
|
||||||
|
int const user2 = CPUReadMemory(puser1 + 0x20);
|
||||||
|
if ( user2 )
|
||||||
|
{
|
||||||
|
int const par1 = CPUReadMemory(puser1 + 0x24);
|
||||||
|
// Call 0x2102 sub_16A8 - -> param r1
|
||||||
|
}
|
||||||
|
|
||||||
|
int const userfunc = CPUReadMemory(puser1 + 0x28);
|
||||||
|
switch (userfunc)
|
||||||
|
{
|
||||||
|
case 0x1709: //phantasy star
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
u32 const v2 = CPUReadMemory(puser1 + 0x10); //r8
|
||||||
|
u8 const user4 = CPUReadByte(puser1+4) - 1;
|
||||||
|
u32 user41 = 0;
|
||||||
|
|
||||||
|
if ( user4 > 0 )
|
||||||
|
{
|
||||||
|
user41 = CPUReadByte(puser1 + 0x0B);
|
||||||
|
user41 -= user4;
|
||||||
|
user41 *= v2;
|
||||||
|
}
|
||||||
|
|
||||||
|
u32 r5;
|
||||||
|
u32 const r5c = puser1 + 0x350 + user41; //r5 @sp+8
|
||||||
|
int user6 = r5c + 0x630; //r6
|
||||||
|
int user5 = CPUReadByte(puser1 + 0x5); //r3
|
||||||
|
|
||||||
|
if ( user5 )
|
||||||
|
{
|
||||||
|
// @todo 0x1e1a
|
||||||
|
}
|
||||||
|
else // 0x1e74
|
||||||
|
{
|
||||||
|
r5 = r5c;
|
||||||
|
int count = v2>>4; //r1...v13
|
||||||
|
if ( !(v2 >> 3) )
|
||||||
|
{
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
}
|
||||||
|
if ( !(v2 >> 1) ) //0x1e7c
|
||||||
|
{
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
}
|
||||||
|
do // 0x1e8e
|
||||||
|
{
|
||||||
|
// @todo optimize this memset
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
|
||||||
|
CPUWriteMemory(r5, 0);
|
||||||
|
CPUWriteMemory(user6, 0);
|
||||||
|
r5+=4; user6+=4;
|
||||||
|
|
||||||
|
count -= 1;
|
||||||
|
} while (count > 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
//0x1ea2
|
||||||
|
u32 r4 = puser1; // apparenty ch ptr?
|
||||||
|
int r9 = CPUReadMemory(r4+0x14);
|
||||||
|
int r12 = CPUReadMemory(r4+0x18);
|
||||||
|
u32 i = CPUReadByte(r4+0x6);
|
||||||
|
|
||||||
|
for (r4+=0x10; i > 0; i-- )
|
||||||
|
{
|
||||||
|
r4+=0x40;
|
||||||
|
/*lbl_0x1eb0:*/
|
||||||
|
u32 r3 = CPUReadMemory(r4+0x24);
|
||||||
|
u8 r6 = CPUReadByte(r4);
|
||||||
|
|
||||||
|
if ( (r6 & 0xC7) == 0 ) // 0x1ebc
|
||||||
|
continue; //goto lbl_20e4;
|
||||||
|
if ( (r6 & 0x80) && ((r6 & 0x40) == 0) ) // 0x1ec4
|
||||||
|
{
|
||||||
|
r6 = 0x3;
|
||||||
|
CPUWriteByte(r4, r6);
|
||||||
|
CPUWriteMemory(r4+0x28, r3+0x10);
|
||||||
|
|
||||||
|
int r0t1 = CPUReadMemory(r3+0xC);
|
||||||
|
CPUWriteMemory(r4+0x18, r0t1);
|
||||||
|
|
||||||
|
r5=0;
|
||||||
|
CPUWriteByte(r4+0x9, 0);
|
||||||
|
CPUWriteMemory(r4+0x1c, 0);
|
||||||
|
|
||||||
|
u8 r2a = CPUReadByte(r3+0x3); // seems to be LABEL_20e4
|
||||||
|
if ((r2a & 0xC0)) // 1ee4
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
goto lbl_0x1f46;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//lbl_0x1eee:
|
||||||
|
r5 = CPUReadByte(r4+0x9); //
|
||||||
|
if ( (r6 & 0x4) != 0) // @todo 0x1ef4
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( (r6 & 0x40) != 0) // @todo 0x1f08
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( (r6 & 0x03) == 2) // 0x1f2a
|
||||||
|
{
|
||||||
|
u8 mul1 = CPUReadByte(r4+0x5);
|
||||||
|
r5*=mul1;
|
||||||
|
r5>>=8;
|
||||||
|
|
||||||
|
u8 cmp1 = CPUReadByte(r4+0x6);
|
||||||
|
if (r5 <= cmp1)
|
||||||
|
{
|
||||||
|
r5=cmp1;
|
||||||
|
// @todo beq @ 0x1f3a -> ??
|
||||||
|
r6--;
|
||||||
|
CPUWriteByte(r4, r6);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if ( (r6 & 0x03) == 3) // 0x1f44
|
||||||
|
{
|
||||||
|
lbl_0x1f46: //@todo check if there is really another path to here
|
||||||
|
u8 add1 = CPUReadByte(r4+0x4);
|
||||||
|
r5+=add1;
|
||||||
|
|
||||||
|
if (r5>=0xff)
|
||||||
|
{
|
||||||
|
r6--;
|
||||||
|
r5=0xff;
|
||||||
|
CPUWriteByte(r4, r6);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
{
|
||||||
|
//lbl_0x1f54:
|
||||||
|
CPUWriteByte(r4+0x9, r5);
|
||||||
|
|
||||||
|
u32 user0 = CPUReadByte(puser1+0x7); // @sp+10
|
||||||
|
user0++;
|
||||||
|
user0*=r5;
|
||||||
|
r5=user0>>4;
|
||||||
|
|
||||||
|
user0 = CPUReadByte(r4+0x2);
|
||||||
|
user0*=r5;
|
||||||
|
user0>>=8;
|
||||||
|
CPUWriteByte(r4+0xA, user0);
|
||||||
|
|
||||||
|
user0 = CPUReadByte(r4+0x3);
|
||||||
|
user0*=r5;
|
||||||
|
user0>>=8;
|
||||||
|
CPUWriteByte(r4+0xB, user0);
|
||||||
|
|
||||||
|
user0 = r6&0x10;
|
||||||
|
if ( user0 != 0) // @todo 0x1f76
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
r5 = r5c; // @todo below r5 is used and updated
|
||||||
|
u32 r2 = CPUReadMemory(r4+0x18);
|
||||||
|
r3 = CPUReadMemory(r4+0x28);
|
||||||
|
|
||||||
|
u32 r8 = v2;
|
||||||
|
|
||||||
|
u8 r10 = CPUReadByte(r4+0xA);
|
||||||
|
u8 r11 = CPUReadByte(r4+0xB);
|
||||||
|
u8 r0a = CPUReadByte(r4+0x1);
|
||||||
|
if ((r0a & 8)) //@todo 0x1fa8
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
u32 r7 = CPUReadMemory(r4+0x1c);
|
||||||
|
u32 r14 = CPUReadMemory(r4+0x20);
|
||||||
|
|
||||||
|
lbl_0x2004:// LABEL_52:
|
||||||
|
while ( r7 >= 4 * r9 )
|
||||||
|
{
|
||||||
|
if ( r2 <= 4 )// @todo 0x2008, no phant
|
||||||
|
goto lbl_204c;
|
||||||
|
r2 -= 4;
|
||||||
|
r3 += 4;
|
||||||
|
r7 -= 4 * r9;
|
||||||
|
}
|
||||||
|
if ( r7 >= 2 * r9 )
|
||||||
|
{
|
||||||
|
if ( r2 <= 2 ) // @todo 0x2008, no phant
|
||||||
|
goto lbl_204c;
|
||||||
|
r2 -= 2;
|
||||||
|
r3 += 2;
|
||||||
|
r7 -= 2 * r9;
|
||||||
|
}
|
||||||
|
if ( r7 < r9 )
|
||||||
|
goto lbl_207c;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
lbl_204c: // LABEL_59:
|
||||||
|
--r2;
|
||||||
|
if ( r2 )
|
||||||
|
{
|
||||||
|
++r3;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
r2 = user0; //0x2054
|
||||||
|
if ( r2 )
|
||||||
|
{
|
||||||
|
r3 = CPUReadMemory(reg[13].I+0xC); // @todo stack pull 0x205c
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
CPUWriteByte(r4, r2);
|
||||||
|
goto lbl_20e4;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
r7 -= r9;
|
||||||
|
} while ( r7 >= r9 );
|
||||||
|
lbl_207c:
|
||||||
|
while ( 1 )
|
||||||
|
{
|
||||||
|
s32 r0a = CPUReadByte(r3);
|
||||||
|
s32 r1a = CPUReadByte(r3+0x1);
|
||||||
|
|
||||||
|
r1a-=r0a;
|
||||||
|
s32 r6a = r1a*(s32)r7;
|
||||||
|
r1a = r6a * r12; // 208c
|
||||||
|
r6a = (r0a + ((s8)(r1a>>23)));
|
||||||
|
|
||||||
|
r1a = r6a * (s32)r11;
|
||||||
|
|
||||||
|
r0a = CPUReadByte(r5 + 0x630);
|
||||||
|
r0a = (r0a + ((s8)(r1a>>8)));
|
||||||
|
CPUWriteByte(r5 + 0x630, r0a);
|
||||||
|
r1a = r6a * (s32)r10;
|
||||||
|
r0a = CPUReadByte(r5);
|
||||||
|
r0a = (r0a + ((s8)(r1a>>8)));
|
||||||
|
CPUWriteByte(r5++, r0a); //ptr inc +1 not +4
|
||||||
|
|
||||||
|
r7+=r14;
|
||||||
|
--r8;
|
||||||
|
if ( !r8 )
|
||||||
|
break;
|
||||||
|
if ( r7 >= r9 )
|
||||||
|
goto lbl_0x2004;
|
||||||
|
}
|
||||||
|
|
||||||
|
CPUWriteMemory(r4+0x1c, r7);
|
||||||
|
//lbl_20cc:
|
||||||
|
CPUWriteMemory(r4+0x18, r2);
|
||||||
|
CPUWriteMemory(r4+0x28, r3);
|
||||||
|
}
|
||||||
|
lbl_20e4:
|
||||||
|
(void)r5;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 0x20EE
|
||||||
|
CPUWriteMemory(puser1, 0x68736D53); // this guard is common for funcs, unify
|
||||||
|
}
|
||||||
|
|
||||||
|
// fully implemented @ 0x210c
|
||||||
|
void BIOS_SndDriverVSync()
|
||||||
|
{
|
||||||
|
u32 const puser1 = CPUReadMemory(0x3007FF0); // @todo some sound area, make it common.
|
||||||
|
u32 const user1 = CPUReadMemory(puser1);
|
||||||
|
|
||||||
|
if ( user1 == 0x68736D53 )
|
||||||
|
{
|
||||||
|
u8 v1 = CPUReadByte(puser1+4);
|
||||||
|
s8 v1i = v1-1;
|
||||||
|
CPUWriteByte(puser1+4, v1i);
|
||||||
|
if ( v1 <= 1 )
|
||||||
|
{
|
||||||
|
u8 v2 = CPUReadByte(puser1+0xB); //11
|
||||||
|
u32 base2 = 0x040000D2;
|
||||||
|
CPUWriteByte(puser1+4, v2);
|
||||||
|
|
||||||
|
CPUWriteHalfWord(base1+0x6 , 0);
|
||||||
|
CPUWriteHalfWord(base2, 0);
|
||||||
|
CPUWriteHalfWord(base1+0x6 , 0xB600);
|
||||||
|
CPUWriteHalfWord(base2, 0xB600); //-18944
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void BIOS_SndDriverVSyncOff() // 0x1878
|
||||||
|
{
|
||||||
|
u32 const puser1 = CPUReadMemory(0x3007FF0); // 7FC0 + 0x30
|
||||||
|
u32 user1 = CPUReadMemory(puser1);
|
||||||
|
|
||||||
|
if ( user1 == 0x68736D53 || user1 == 0x68736D54 )
|
||||||
|
{
|
||||||
|
CPUWriteMemory(puser1, (++user1)); // this guard is common for funcs, unify
|
||||||
|
|
||||||
|
CPUWriteHalfWord(base1+0x6 , 0);
|
||||||
|
CPUWriteHalfWord(base1+0x12 , 0);
|
||||||
|
CPUWriteByte(puser1+4, 0);
|
||||||
|
|
||||||
|
u32 r1 = puser1+0x350;
|
||||||
|
u32 r2 = 0x05000318;
|
||||||
|
u32 sp = reg[13].I; //0x03003c94;
|
||||||
|
|
||||||
|
CPUWriteMemory(sp, 0);
|
||||||
|
BIOS_SndDriver_b4c(sp, r1, r2);
|
||||||
|
|
||||||
|
user1 = CPUReadMemory(puser1); // 0x18aa
|
||||||
|
CPUWriteMemory(puser1, (--user1)); // this ret is common among funcs
|
||||||
|
}
|
||||||
|
//0x18b0
|
||||||
|
}
|
||||||
|
|
||||||
|
// This functions is verified but lacks proper register settings before calling user func
|
||||||
|
// it might be that user func modifies or uses those?
|
||||||
|
// r7 should be puser1, r6 should be flags, ....
|
||||||
|
void BIOS_SndChannelClear() //0x1824
|
||||||
|
{
|
||||||
|
u32 const puser1 = CPUReadMemory(0x3007FF0); // 7FC0 + 0x30
|
||||||
|
u32 user1 = CPUReadMemory(puser1);
|
||||||
|
|
||||||
|
if ( user1 == 0x68736D53 )
|
||||||
|
{
|
||||||
|
CPUWriteMemory(puser1, (++user1));
|
||||||
|
u32 puser2 = puser1 + 0x7 + 0x49;
|
||||||
|
|
||||||
|
int count=12;
|
||||||
|
while (count--)
|
||||||
|
{
|
||||||
|
CPUWriteByte(puser2, 0);
|
||||||
|
puser2+=0x40;
|
||||||
|
}
|
||||||
|
|
||||||
|
reg[4].I = CPUReadMemory(puser1 + 0x1c); //r5 -> some user thing
|
||||||
|
if ( reg[4].I != 0 )
|
||||||
|
{
|
||||||
|
reg[3].I = 1; // r4 -> channel counter?
|
||||||
|
int puser4 = puser1 + 0x2c;
|
||||||
|
//reg[0].I = reg[3].I = 1; // r0 & r4 => 1
|
||||||
|
|
||||||
|
while (reg[3].I <= 4)
|
||||||
|
{
|
||||||
|
// @todo does user func modify these?
|
||||||
|
reg[0].I = reg[3].I << 24;
|
||||||
|
reg[0].I >>= 24;
|
||||||
|
|
||||||
|
// Get ptr to user func
|
||||||
|
reg[1].I = CPUReadMemory(puser4);
|
||||||
|
|
||||||
|
// @todo here we jump where r1 points; user func?
|
||||||
|
// @todo might modify r6 also?
|
||||||
|
|
||||||
|
// After call routines
|
||||||
|
reg[3].I += 1; // r4 -> channel counter?
|
||||||
|
reg[4].I += 0x40;// r5 -> some user thing
|
||||||
|
}
|
||||||
|
CPUWriteByte(reg[4].I, 0); // terminating record?
|
||||||
|
}
|
||||||
|
CPUWriteMemory(puser1, 0x68736D53);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void BIOS_MidiKey2Freq()
|
void BIOS_MidiKey2Freq()
|
||||||
{
|
{
|
||||||
#ifdef GBA_LOGGING
|
#ifdef GBA_LOGGING
|
||||||
|
|
|
@ -25,5 +25,11 @@ extern void BIOS_SoftReset();
|
||||||
extern void BIOS_Sqrt();
|
extern void BIOS_Sqrt();
|
||||||
extern void BIOS_MidiKey2Freq();
|
extern void BIOS_MidiKey2Freq();
|
||||||
extern void BIOS_SndDriverJmpTableCopy();
|
extern void BIOS_SndDriverJmpTableCopy();
|
||||||
|
extern void BIOS_SndDriverInit();
|
||||||
|
extern void BIOS_SndDriverMode();
|
||||||
|
extern void BIOS_SndDriverMain();
|
||||||
|
extern void BIOS_SndDriverVSync();
|
||||||
|
extern void BIOS_SndDriverVSyncOff();
|
||||||
|
extern void BIOS_SndChannelClear();
|
||||||
|
|
||||||
#endif // BIOS_H
|
#endif // BIOS_H
|
||||||
|
|
Loading…
Reference in New Issue