Added several important variables to the VIFdma savestate, relating to it's SSE unpacker; which should make the gifdone savestate hack obsolete (it broke savestates for most FMVs and some games). Seeing how important the unpacker tables are, it's a miracle VIFdma ever recovered from a savestate without them ;)

Fixed a bug in the memorycard hotswapper.  It wasn't reloading the cards correctly after changes.

Improved the new INTC hack slightly, and changed its description since it's not quite as universally awesome as Pseudonym and I had hoped when we worked on it last night. -_-

Added __fastcall and __forceinline to some of the VIF's unpack functions, where appropriate (very small speedup).

Removed some code I added to the MULT/DIV instructions, since it wasn't needed afterall, and fixed some typos in vtlb's API.

git-svn-id: http://pcsx2.googlecode.com/svn/trunk@538 96395faa-99c1-11dd-bbfe-3dabce05a288
This commit is contained in:
Jake.Stine 2009-02-19 22:48:05 +00:00
parent 23336fe987
commit 243e4fba9f
20 changed files with 442 additions and 212 deletions

View File

@ -813,12 +813,10 @@ void gsDynamicSkipEnable()
frameLimitReset();
}
extern unsigned int gifdone;
void SaveState::gsFreeze()
{
FreezeMem(PS2MEM_GS, 0x2000);
Freeze(CSRw);
if(((DMACh*)&PS2MEM_HW[0xA000])->chcr & 0x100)gifdone = 0;
mtgsFreeze();
}

View File

@ -376,6 +376,7 @@ extern mem32_t __fastcall hwRead32_page_00(u32 mem);
extern mem32_t __fastcall hwRead32_page_01(u32 mem);
extern mem32_t __fastcall hwRead32_page_02(u32 mem);
extern mem32_t __fastcall hwRead32_page_0F(u32 mem);
extern mem32_t __fastcall hwRead32_page_0F_INTC_HACK(u32 mem);
extern mem32_t __fastcall hwRead32_generic(u32 mem);
extern void __fastcall hwRead64_page_00(u32 mem, mem64_t* result );

View File

@ -34,6 +34,19 @@
using namespace R5900;
static __forceinline void IntCHackCheck()
{
if( !CHECK_INTC_STAT_HACK ) return;
cpuRegs.cycle = g_nextBranchCycle;
// Threshold method, might fix games that have problems with the simple
// implementation above (none known that break yet)
/*if( ( g_nextBranchCycle - cpuRegs.cycle ) > 500 )
cpuRegs.cycle += 498;
else
cpuRegs.cycle = g_nextBranchCycle - 2;*/
}
/////////////////////////////////////////////////////////////////////////
// Hardware READ 8 bit
@ -186,7 +199,8 @@ mem32_t __fastcall hwRead32_page_01(u32 mem)
}
// Reads hardware registers for page 15 (0x0F).
mem32_t __fastcall hwRead32_page_0F(u32 mem)
// This is used internally to produce two inline versions, one with INTC_HACK, and one without.
static __forceinline mem32_t __hwRead32_page_0F( u32 mem, bool intchack )
{
// *Performance Warning* This function is called -A-LOT. Be weary when making changes. It
// could impact FPS significantly.
@ -196,8 +210,7 @@ mem32_t __fastcall hwRead32_page_0F(u32 mem)
switch( mem )
{
case 0xf000:
if( CHECK_INTC_STAT_HACK )
cpuRegs.cycle = g_nextBranchCycle;
if( intchack ) IntCHackCheck();
// This one is checked alot, so leave it commented out unless you love 600 meg logfiles.
//HW_LOG("INTC_STAT Read 32bit %x\n", psHu32(0xf010));
break;
@ -247,6 +260,16 @@ mem32_t __fastcall hwRead32_page_0F(u32 mem)
return *((u32*)&PS2MEM_HW[mem]);
}
mem32_t __fastcall hwRead32_page_0F(u32 mem)
{
return __hwRead32_page_0F( mem, false );
}
mem32_t __fastcall hwRead32_page_0F_INTC_HACK(u32 mem)
{
return __hwRead32_page_0F( mem, true );
}
mem32_t __fastcall hwRead32_page_02(u32 mem)
{
return ipuRead32( mem );
@ -327,8 +350,7 @@ void __fastcall hwRead64_page_02(u32 mem, mem64_t* result )
void __fastcall hwRead64_generic(u32 mem, mem64_t* result )
{
if( mem == INTC_STAT && CHECK_INTC_STAT_HACK )
cpuRegs.cycle = g_nextBranchCycle;
if( mem == INTC_STAT ) IntCHackCheck();
*result = psHu64(mem);
HW_LOG("Unknown Hardware Read 64 at %x\n",mem);

View File

@ -106,17 +106,6 @@ namespace OpcodeImpl {
void MULTU1() {
u64 tempu = (u64)cpuRegs.GPR.r[_Rs_].UL[0] * (u64)cpuRegs.GPR.r[_Rt_].UL[0];
// The EE says that results are "undefined" if the source operands are not correctly
// sign extended into the full 64 bits. Since this is InterpreterLand, let's put a
// check in and issue a message if it ever happens.
// Could be a clue to something else someday.
if( cpuRegs.GPR.r[_Rs_].SL[0] != cpuRegs.GPR.r[_Rs_].SD[0] )
DevCon::Notice( "MULTU1 > Non-extended sign bit on Rs: %8.8x", params cpuRegs.GPR.r[_Rs_].SL[0] );
if( cpuRegs.GPR.r[_Rt_].SL[0] != cpuRegs.GPR.r[_Rt_].SD[0] )
DevCon::Notice( "MULTU1 > Non-extended sign bit on Rt: %8.8x", params cpuRegs.GPR.r[_Rt_].SL[0] );
// According to docs, sign-extend into 64 bits even though it's an unsigned mult.
cpuRegs.LO.UD[1] = (s32)(tempu & 0xffffffff);
cpuRegs.HI.UD[1] = (s32)(tempu >> 32);
@ -134,14 +123,6 @@ namespace OpcodeImpl {
void DIVU1() {
if (cpuRegs.GPR.r[_Rt_].UL[0] != 0) {
// See MULTU above for notes on the following sanity check
if( cpuRegs.GPR.r[_Rs_].SL[0] != cpuRegs.GPR.r[_Rs_].SD[0] )
DevCon::Notice( "DIVU1 > Non-extended sign bit on Rs: %8.8x", params cpuRegs.GPR.r[_Rs_].SL[0] );
if( cpuRegs.GPR.r[_Rt_].SL[0] != cpuRegs.GPR.r[_Rt_].SD[0] )
DevCon::Notice( "DIVU1 > Non-extended sign bit on Rt: %8.8x", params cpuRegs.GPR.r[_Rt_].SL[0] );
// note: DIVU has no sign extension when assigning back to 64 bits
cpuRegs.LO.UD[1] = cpuRegs.GPR.r[_Rs_].UL[0] / cpuRegs.GPR.r[_Rt_].UL[0];
cpuRegs.HI.UD[1] = cpuRegs.GPR.r[_Rs_].UL[0] % cpuRegs.GPR.r[_Rt_].UL[0];

View File

@ -754,8 +754,10 @@ void memReset()
_ext_memWrite8<1>, _ext_memWrite16<1>, hwWrite32_page_0E, hwWrite64_page_0E, hwWrite128_generic
);
vtlbMemR32FP* page0F( CHECK_INTC_STAT_HACK ? hwRead32_page_0F_INTC_HACK : hwRead32_page_0F );
hw_by_page[0xf] = vtlb_RegisterHandler(
_ext_memRead8<1>, _ext_memRead16<1>, hwRead32_page_0F, hwRead64_generic, hwRead128_generic,
_ext_memRead8<1>, _ext_memRead16<1>, page0F, hwRead64_generic, hwRead128_generic,
_ext_memWrite8<1>, _ext_memWrite16<1>, hwWrite32_page_0F, hwWrite64_generic, hwWrite128_generic
);

View File

@ -42,11 +42,16 @@ void MemoryCard::Init()
void MemoryCard::Shutdown()
{
for( int i=0; i<2; i++ )
{
if(cardfile[0] == NULL) continue;
fclose( cardfile[i] );
cardfile[0] = NULL;
}
Unload( i );
}
void MemoryCard::Unload( uint mcd )
{
jASSUME( mcd < 2 );
if(cardfile[mcd] == NULL) return;
fclose( cardfile[mcd] );
cardfile[mcd] = NULL;
}
bool MemoryCard::IsPresent( uint mcd )

View File

@ -34,6 +34,8 @@ protected:
public:
static void Init();
static void Shutdown();
static void Unload( uint mcd );
static bool IsPresent( uint mcdId );
static void Read( uint mcdId, u8 *data, u32 adr, int size );
static void Save( uint mcdId, const u8 *data, u32 adr, int size );

View File

@ -153,14 +153,6 @@ void DIV() {
void DIVU() {
if (cpuRegs.GPR.r[_Rt_].UL[0] != 0) {
// See MULTU below for notes on the following sanity check
if( cpuRegs.GPR.r[_Rs_].SL[0] != cpuRegs.GPR.r[_Rs_].SD[0] )
DevCon::Notice( "DIVU > Non-extended sign bit on Rs: %8.8x", params cpuRegs.GPR.r[_Rs_].SL[0] );
if( cpuRegs.GPR.r[_Rt_].SL[0] != cpuRegs.GPR.r[_Rt_].SD[0] )
DevCon::Notice( "DIVU > Non-extended sign bit on Rt: %8.8x", params cpuRegs.GPR.r[_Rt_].SL[0] );
// note: DIVU has no sign extension when assigning back to 64 bits
cpuRegs.LO.SD[0] = cpuRegs.GPR.r[_Rs_].UL[0] / cpuRegs.GPR.r[_Rt_].UL[0];
cpuRegs.HI.SD[0] = cpuRegs.GPR.r[_Rs_].UL[0] % cpuRegs.GPR.r[_Rt_].UL[0];
@ -180,17 +172,6 @@ void MULT() { //different in ps2...
void MULTU() { //different in ps2..
u64 res = (u64)cpuRegs.GPR.r[_Rs_].UL[0] * (u64)cpuRegs.GPR.r[_Rt_].UL[0];
// The EE says that results are "undefined" if the source operands are not correctly
// sign extended into the full 64 bits. Since this is InterpreterLand, let's put a
// check in and issue a message if it ever happens.
// Could be a clue to something else someday.
if( cpuRegs.GPR.r[_Rs_].SL[0] != cpuRegs.GPR.r[_Rs_].SD[0] )
DevCon::Notice( "MULTU > Non-extended sign bit on Rs: %8.8x", params cpuRegs.GPR.r[_Rs_].SL[0] );
if( cpuRegs.GPR.r[_Rt_].SL[0] != cpuRegs.GPR.r[_Rt_].SD[0] )
DevCon::Notice( "MULTU > Non-extended sign bit on Rt: %8.8x", params cpuRegs.GPR.r[_Rt_].SL[0] );
// According to docs, sign-extend into 64 bits even though it's an unsigned mult.
cpuRegs.LO.UD[0] = (s32)(res & 0xffffffff);
cpuRegs.HI.UD[0] = (s32)(res >> 32);

View File

@ -113,11 +113,10 @@ void SaveState::FreezeAll()
Freeze(g_psxNextBranchCycle);
Freeze(s_iLastCOP0Cycle);
if( m_version >= 0x7a30000e )
Freeze(s_iLastPERFCycle);
Freeze(s_iLastPERFCycle);
Freeze(g_psxWriteOk);
//hope didn't forgot any cpu....
rcntFreeze();

View File

@ -29,7 +29,7 @@
// Savestate Versioning!
// If you make changes to the savestate version, please increment the value below.
static const u32 g_SaveVersion = 0x8b400003;
static const u32 g_SaveVersion = 0x8b400004;
// this function is meant to be sued in the place of GSfreeze, and provides a safe layer
// between the GS saving function and the MTGS's needs. :)

View File

@ -554,6 +554,11 @@ void sioEjectCard( uint mcdId )
{
jASSUME( mcdId < 2 );
m_PostSavestateCards[mcdId] = 64;
// Reload the new memory card:
MemoryCard::Unload( mcdId );
MemoryCard::Init();
}
void SaveState::sioFreeze()

View File

@ -42,7 +42,7 @@ static int n;
__forceinline static int _limit( int a, int max )
{
return ( a > max ? max : a );
return ( a > max ) ? max : a;
}
#define _UNPACKpart( offnum, func ) \
@ -58,7 +58,16 @@ __forceinline static int _limit( int a, int max )
_vifRegs->offset++; \
}
static void writeX( u32 *dest, u32 data ) {
// Forceinline macro that is enabled for RELEASE/PUBLIC builds ONLY.
// This is useful because forceinline can make certain types of debugging problematic since
// functions that look like they should be called won't breakpoint since their code is inlined.
#ifdef PCSX2_DEVBUILD
# define __pub_inline
#else
# define __pub_inline __forceinline
#endif
static __pub_inline void writeX( u32 *dest, u32 data ) {
if (_vifRegs->code & 0x10000000) {
switch ( _vif->cl ) {
case 0: n = (_vifRegs->mask) & 0x3; break;
@ -97,7 +106,7 @@ static void writeX( u32 *dest, u32 data ) {
// VIF_LOG("writeX %8.8x : Mode %d, r0 = %x, data %8.8x\n", *dest,_vifRegs->mode,_vifRegs->r0,data);
}
static void writeY( u32 *dest, u32 data ) {
static __pub_inline void writeY( u32 *dest, u32 data ) {
if (_vifRegs->code & 0x10000000) {
switch ( _vif->cl ) {
case 0: n = (_vifRegs->mask >> 2) & 0x3; break;
@ -136,7 +145,7 @@ static void writeY( u32 *dest, u32 data ) {
// VIF_LOG("writeY %8.8x : Mode %d, r1 = %x, data %8.8x\n", *dest,_vifRegs->mode,_vifRegs->r1,data);
}
static void writeZ( u32 *dest, u32 data ) {
static __pub_inline void writeZ( u32 *dest, u32 data ) {
if (_vifRegs->code & 0x10000000) {
switch ( _vif->cl ) {
case 0: n = (_vifRegs->mask >> 4) & 0x3; break;
@ -175,7 +184,7 @@ static void writeZ( u32 *dest, u32 data ) {
// VIF_LOG("writeZ %8.8x : Mode %d, r2 = %x, data %8.8x\n", *dest,_vifRegs->mode,_vifRegs->r2,data);
}
static void writeW( u32 *dest, u32 data ) {
static __pub_inline void writeW( u32 *dest, u32 data ) {
if (_vifRegs->code & 0x10000000) {
switch ( _vif->cl ) {
case 0: n = (_vifRegs->mask >> 6) & 0x3; break;
@ -214,7 +223,7 @@ static void writeW( u32 *dest, u32 data ) {
// VIF_LOG("writeW %8.8x : Mode %d, r3 = %x, data %8.8x\n", *dest,_vifRegs->mode,_vifRegs->r3,data);
}
void UNPACK_S_32(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_S_32(u32 *dest, u32 *data, int size) {
_UNPACKpart(0, writeX(dest++, *data) );
_UNPACKpart(1, writeY(dest++, *data) );
_UNPACKpart(2, writeZ(dest++, *data) );
@ -222,7 +231,7 @@ void UNPACK_S_32(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_S_16s( u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_S_16s( u32 *dest, u32 *data, int size) {
s16 *sdata = (s16*)data;
_UNPACKpart(0, writeX(dest++, *sdata) );
_UNPACKpart(1, writeY(dest++, *sdata) );
@ -231,8 +240,8 @@ void UNPACK_S_16s( u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_S_16u( u32 *dest, u32 *data, int size) {
u16 *sdata = (u16*)data;
void __fastcall UNPACK_S_16u( u32 *dest, u32 *data, int size) {
const u16 *sdata = (u16*)data;
_UNPACKpart(0, writeX(dest++, *sdata) );
_UNPACKpart(1, writeY(dest++, *sdata) );
_UNPACKpart(2, writeZ(dest++, *sdata) );
@ -240,7 +249,7 @@ void UNPACK_S_16u( u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_S_8s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_S_8s(u32 *dest, u32 *data, int size) {
s8 *cdata = (s8*)data;
_UNPACKpart(0, writeX(dest++, *cdata) );
_UNPACKpart(1, writeY(dest++, *cdata) );
@ -249,7 +258,7 @@ void UNPACK_S_8s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_S_8u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_S_8u(u32 *dest, u32 *data, int size) {
u8 *cdata = (u8*)data;
_UNPACKpart(0, writeX(dest++, *cdata) );
_UNPACKpart(1, writeY(dest++, *cdata) );
@ -258,7 +267,7 @@ void UNPACK_S_8u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V2_32( u32 *dest, u32 *data, int size ) {
void __fastcall UNPACK_V2_32( u32 *dest, u32 *data, int size ) {
_UNPACKpart(0, writeX(dest++, *data++));
_UNPACKpart(1, writeY(dest++, *data--));
_UNPACKpart_nosize(2, writeZ(dest++, *data));
@ -267,7 +276,7 @@ void UNPACK_V2_32( u32 *dest, u32 *data, int size ) {
}
void UNPACK_V2_16s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V2_16s(u32 *dest, u32 *data, int size) {
s16 *sdata = (s16*)data;
_UNPACKpart(0, writeX(dest++, *sdata++));
_UNPACKpart(1, writeY(dest++, *sdata--));
@ -276,7 +285,7 @@ void UNPACK_V2_16s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V2_16u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V2_16u(u32 *dest, u32 *data, int size) {
u16 *sdata = (u16*)data;
_UNPACKpart(0, writeX(dest++, *sdata++));
_UNPACKpart(1, writeY(dest++, *sdata--));
@ -285,7 +294,7 @@ void UNPACK_V2_16u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V2_8s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V2_8s(u32 *dest, u32 *data, int size) {
s8 *cdata = (s8*)data;
_UNPACKpart(0, writeX(dest++, *cdata++));
_UNPACKpart(1, writeY(dest++, *cdata--));
@ -294,7 +303,7 @@ void UNPACK_V2_8s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V2_8u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V2_8u(u32 *dest, u32 *data, int size) {
u8 *cdata = (u8*)data;
_UNPACKpart(0, writeX(dest++, *cdata++));
_UNPACKpart(1, writeY(dest++, *cdata--));
@ -303,7 +312,7 @@ void UNPACK_V2_8u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V3_32(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V3_32(u32 *dest, u32 *data, int size) {
_UNPACKpart(0, writeX(dest++, *data++); );
_UNPACKpart(1, writeY(dest++, *data++); );
_UNPACKpart(2, writeZ(dest++, *data++); );
@ -311,7 +320,7 @@ void UNPACK_V3_32(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V3_16s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V3_16s(u32 *dest, u32 *data, int size) {
s16 *sdata = (s16*)data;
_UNPACKpart(0, writeX(dest++, *sdata++));
_UNPACKpart(1, writeY(dest++, *sdata++));
@ -320,7 +329,7 @@ void UNPACK_V3_16s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V3_16u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V3_16u(u32 *dest, u32 *data, int size) {
u16 *sdata = (u16*)data;
_UNPACKpart(0, writeX(dest++, *sdata++));
_UNPACKpart(1, writeY(dest++, *sdata++));
@ -329,7 +338,7 @@ void UNPACK_V3_16u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V3_8s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V3_8s(u32 *dest, u32 *data, int size) {
s8 *cdata = (s8*)data;
_UNPACKpart(0, writeX(dest++, *cdata++));
_UNPACKpart(1, writeY(dest++, *cdata++));
@ -338,7 +347,7 @@ void UNPACK_V3_8s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V3_8u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V3_8u(u32 *dest, u32 *data, int size) {
u8 *cdata = (u8*)data;
_UNPACKpart(0, writeX(dest++, *cdata++));
_UNPACKpart(1, writeY(dest++, *cdata++));
@ -347,7 +356,7 @@ void UNPACK_V3_8u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V4_32( u32 *dest, u32 *data , int size) {
void __fastcall UNPACK_V4_32( u32 *dest, u32 *data , int size) {
_UNPACKpart(0, writeX(dest++, *data++) );
_UNPACKpart(1, writeY(dest++, *data++) );
_UNPACKpart(2, writeZ(dest++, *data++) );
@ -355,7 +364,7 @@ void UNPACK_V4_32( u32 *dest, u32 *data , int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V4_16s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V4_16s(u32 *dest, u32 *data, int size) {
s16 *sdata = (s16*)data;
_UNPACKpart(0, writeX(dest++, *sdata++) );
_UNPACKpart(1, writeY(dest++, *sdata++) );
@ -364,7 +373,7 @@ void UNPACK_V4_16s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V4_16u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V4_16u(u32 *dest, u32 *data, int size) {
u16 *sdata = (u16*)data;
_UNPACKpart(0, writeX(dest++, *sdata++) );
_UNPACKpart(1, writeY(dest++, *sdata++) );
@ -373,7 +382,7 @@ void UNPACK_V4_16u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V4_8s(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V4_8s(u32 *dest, u32 *data, int size) {
s8 *cdata = (s8*)data;
_UNPACKpart(0, writeX(dest++, *cdata++) );
_UNPACKpart(1, writeY(dest++, *cdata++) );
@ -382,7 +391,7 @@ void UNPACK_V4_8s(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V4_8u(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V4_8u(u32 *dest, u32 *data, int size) {
u8 *cdata = (u8*)data;
_UNPACKpart(0, writeX(dest++, *cdata++) );
_UNPACKpart(1, writeY(dest++, *cdata++) );
@ -391,7 +400,7 @@ void UNPACK_V4_8u(u32 *dest, u32 *data, int size) {
if (_vifRegs->offset == 4) _vifRegs->offset = 0;
}
void UNPACK_V4_5(u32 *dest, u32 *data, int size) {
void __fastcall UNPACK_V4_5(u32 *dest, u32 *data, int size) {
_UNPACKpart(0, writeX(dest++, (*data & 0x001f) << 3); );
_UNPACKpart(1, writeY(dest++, (*data & 0x03e0) >> 2); );

View File

@ -96,7 +96,7 @@ int VIF0transfer(u32 *data, int size, int istag);
int VIF1transfer(u32 *data, int size, int istag);
void vifMFIFOInterrupt();
void SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask);
void __fastcall SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask);
#define XMM_R0 xmm0
#define XMM_R1 xmm1

View File

@ -68,12 +68,12 @@ static const unsigned int VIF1dmanum = 1;
int g_vifCycles = 0;
int path3hack = 0;
typedef void (*UNPACKFUNCTYPE)( u32 *dest, u32 *data, int size );
typedef void (__fastcall *UNPACKFUNCTYPE)( u32 *dest, u32 *data, int size );
typedef int (*UNPACKPARTFUNCTYPESSE)( u32 *dest, u32 *data, int size );
extern void (*Vif1CMDTLB[82])();
extern void (*Vif0CMDTLB[75])();
extern int (*Vif1TransTLB[128])(u32 *data);
extern int (*Vif0TransTLB[128])(u32 *data);
extern int (__fastcall *Vif1TransTLB[128])(u32 *data);
extern int (__fastcall *Vif0TransTLB[128])(u32 *data);
struct VIFUnpackFuncTable {
UNPACKFUNCTYPE funcU;
@ -395,24 +395,29 @@ static void VIFunpack(u32 *data, vifCode *v, int size, const unsigned int VIFdma
#ifdef _DEBUG
memsize = size;
#endif
if( _vifRegs->offset > 0) {
if( _vifRegs->offset > 0)
{
int destinc, unpacksize;
VIFUNPACK_LOG("aligning packet size = %d offset %d addr %x\n", size, vifRegs->offset, vif->tag.addr);
// SSE doesn't handle such small data
if (v->size != (size>>2))ProcessMemSkip(size, unpackType, VIFdmanum);
if (v->size != (size>>2))
ProcessMemSkip(size, unpackType, VIFdmanum);
if(vifRegs->offset < (u32)ft->qsize){
if(((u32)size/(u32)ft->dsize) < ((u32)ft->qsize - vifRegs->offset)){
if(vifRegs->offset < (u32)ft->qsize)
{
if(((u32)size/(u32)ft->dsize) < ((u32)ft->qsize - vifRegs->offset))
{
SysPrintf("wasnt enough left size/dsize = %x left to write %x\n", (size/ft->dsize), (ft->qsize - vifRegs->offset));
}
unpacksize = min(((u32)size/(u32)ft->dsize), ((u32)ft->qsize - vifRegs->offset));
}
else {
unpacksize = 0;
SysPrintf("Unpack align offset = 0\n");
}
unpacksize = min(((u32)size/(u32)ft->dsize), ((u32)ft->qsize - vifRegs->offset));
}
else
{
unpacksize = 0;
SysPrintf("Unpack align offset = 0\n");
}
destinc = (4 - ft->qsize) + unpacksize;
func(dest, (u32*)cdata, unpacksize);
@ -434,7 +439,9 @@ static void VIFunpack(u32 *data, vifCode *v, int size, const unsigned int VIFdma
}
VIFUNPACK_LOG("aligning packet done size = %d offset %d addr %x\n", size, vifRegs->offset, vif->tag.addr);
} else if (v->size != (size>>2))ProcessMemSkip(size, unpackType, VIFdmanum);
}
else if (v->size != (size>>2))
ProcessMemSkip(size, unpackType, VIFdmanum);
if (vifRegs->cycle.cl >= vifRegs->cycle.wl) { // skipping write
@ -620,7 +627,7 @@ static void VIFunpack(u32 *data, vifCode *v, int size, const unsigned int VIFdma
}
else { /* filling write */
VIF_LOG("*PCSX2*: filling write\n");
VIF_LOG("VIFunpack - filling write\n");
VIFUNPACK_LOG("filling write %d cl %d, wl %d mask %x mode %x unpacktype %x\n", vifRegs->num, vifRegs->cycle.cl, vifRegs->cycle.wl, vifRegs->mask, vifRegs->mode, unpackType);
while (size >= ft->gsize || vifRegs->num > 0) {
@ -656,10 +663,6 @@ static void vuExecMicro( u32 addr, const u32 VIFdmanum )
{
int _cycles;
VURegs * VU;
//void (*_vuExecMicro)();
// MessageBox(NULL, "3d doesn't work\n", "Query", MB_OK);
// return;
if (VIFdmanum == 0) {
VU = &VU0;
@ -773,12 +776,12 @@ static __forceinline void _vif0mpgTransfer(u32 addr, u32 *data, int size) {
// Vif1 Data Transfer Commands
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
static int Vif0TransNull(u32 *data){ // Shouldnt go here
static int __fastcall Vif0TransNull(u32 *data){ // Shouldnt go here
SysPrintf("VIF0 Shouldnt go here CMD = %x\n", vif0Regs->code);
vif0.cmd = 0;
return 0;
}
static int Vif0TransSTMask(u32 *data){ // STMASK
static int __fastcall Vif0TransSTMask(u32 *data){ // STMASK
SetNewMask(g_vif0Masks, g_vif0HasMask3, data[0], vif0Regs->mask);
vif0Regs->mask = data[0];
VIF_LOG("STMASK == %x\n", vif0Regs->mask);
@ -788,7 +791,7 @@ static int Vif0TransSTMask(u32 *data){ // STMASK
return 1;
}
static int Vif0TransSTRow(u32 *data){ // STROW
static int __fastcall Vif0TransSTRow(u32 *data){ // STROW
int ret;
u32* pmem = &vif0Regs->r0+(vif0.tag.addr<<2);
@ -811,7 +814,7 @@ static int Vif0TransSTRow(u32 *data){ // STROW
return ret;
}
static int Vif0TransSTCol(u32 *data){ // STCOL
static int __fastcall Vif0TransSTCol(u32 *data){ // STCOL
int ret;
u32* pmem = &vif0Regs->c0+(vif0.tag.addr<<2);
@ -831,7 +834,7 @@ static int Vif0TransSTCol(u32 *data){ // STCOL
return ret;
}
static int Vif0TransMPG(u32 *data){ // MPG
static int __fastcall Vif0TransMPG(u32 *data){ // MPG
if (vif0.vifpacketsize < vif0.tag.size) {
_vif0mpgTransfer(vif0.tag.addr, data, vif0.vifpacketsize);
vif0.tag.addr += vif0.vifpacketsize << 2;
@ -847,26 +850,29 @@ static int Vif0TransMPG(u32 *data){ // MPG
}
}
static int Vif0TransUnpack(u32 *data){ // UNPACK
static int __fastcall Vif0TransUnpack(u32 *data) // UNPACK
{
FreezeXMMRegs(1);
if (vif0.vifpacketsize < vif0.tag.size) {
/* size is less that the total size, transfer is
'in pieces' */
VIFunpack(data, &vif0.tag, vif0.vifpacketsize, VIF0dmanum);
vif0.tag.size -= vif0.vifpacketsize;
FreezeXMMRegs(0);
return vif0.vifpacketsize;
} else {
int ret;
/* we got all the data, transfer it fully */
VIFunpack(data, &vif0.tag, vif0.tag.size, VIF0dmanum);
ret = vif0.tag.size;
vif0.tag.size = 0;
vif0.cmd = 0;
FreezeXMMRegs(0);
return ret;
}
if (vif0.vifpacketsize < vif0.tag.size)
{
/* size is less that the total size, transfer is
'in pieces' */
VIFunpack(data, &vif0.tag, vif0.vifpacketsize, VIF0dmanum);
vif0.tag.size -= vif0.vifpacketsize;
FreezeXMMRegs(0);
return vif0.vifpacketsize;
}
else
{
int ret;
/* we got all the data, transfer it fully */
VIFunpack(data, &vif0.tag, vif0.tag.size, VIF0dmanum);
ret = vif0.tag.size;
vif0.tag.size = 0;
vif0.cmd = 0;
FreezeXMMRegs(0);
return ret;
}
}
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
@ -1165,7 +1171,7 @@ void vif0Interrupt() {
}
// Vif1 Data Transfer Table
int (*Vif0TransTLB[128])(u32 *data) =
int (__fastcall *Vif0TransTLB[128])(u32 *data) =
{
Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , /*0x7*/
Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , Vif0TransNull , /*0xF*/
@ -1306,8 +1312,10 @@ void vif0Write32(u32 mem, u32 value) {
if( mem >= 0x10003900 && mem < 0x10003980 ) {
assert( (mem&0xf) == 0 );
if( mem < 0x10003940 ) g_vifRow0[(mem>>4)&3] = value;
else g_vifCol0[(mem>>4)&3] = value;
if( mem < 0x10003940 )
g_vifRow0[(mem>>4)&3] = value;
else
g_vifCol0[(mem>>4)&3] = value;
} else psHu32(mem) = value;
}
@ -1327,10 +1335,19 @@ void vif0Reset() {
vif0Regs->stat&= ~0xF000000; // FQC=0
}
void SaveState::vif0Freeze() {
Freeze(vif0);
if( IsLoading() )
SetNewMask(g_vif0Masks, g_vif0HasMask3, vif0Regs->mask, ~vif0Regs->mask);
void SaveState::vif0Freeze()
{
// Dunno if this one is needed, but whatever, it's small. :)
Freeze( g_vifCycles );
Freeze( vif0 );
if( GetVersion() >= 0x14 )
{
Freeze( g_vif1HasMask3 );
Freeze( g_vif1Masks );
Freeze( g_vifRow1 );
Freeze( g_vifCol1 );
}
}
//////////////////////////////////////////////////////////////////////////////
@ -1402,12 +1419,12 @@ static __forceinline void _vif1mpgTransfer(u32 addr, u32 *data, int size) {
// Vif1 Data Transfer Commands
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
static int Vif1TransNull(u32 *data){ // Shouldnt go here
static int __fastcall Vif1TransNull(u32 *data){ // Shouldnt go here
SysPrintf("Shouldnt go here CMD = %x\n", vif1Regs->code);
vif1.cmd = 0;
return 0;
}
static int Vif1TransSTMask(u32 *data){ // STMASK
static int __fastcall Vif1TransSTMask(u32 *data){ // STMASK
SetNewMask(g_vif1Masks, g_vif1HasMask3, data[0], vif1Regs->mask);
vif1Regs->mask = data[0];
VIF_LOG("STMASK == %x\n", vif1Regs->mask);
@ -1417,7 +1434,7 @@ static int Vif1TransSTMask(u32 *data){ // STMASK
return 1;
}
static int Vif1TransSTRow(u32 *data){
static int __fastcall Vif1TransSTRow(u32 *data){
int ret;
u32* pmem = &vif1Regs->r0+(vif1.tag.addr<<2);
@ -1439,7 +1456,7 @@ static int Vif1TransSTRow(u32 *data){
return ret;
}
static int Vif1TransSTCol(u32 *data){
static int __fastcall Vif1TransSTCol(u32 *data){
int ret;
u32* pmem = &vif1Regs->c0+(vif1.tag.addr<<2);
@ -1458,7 +1475,7 @@ static int Vif1TransSTCol(u32 *data){
return ret;
}
static int Vif1TransMPG(u32 *data){
static int __fastcall Vif1TransMPG(u32 *data){
if (vif1.vifpacketsize < vif1.tag.size) {
_vif1mpgTransfer(vif1.tag.addr, data, vif1.vifpacketsize);
vif1.tag.addr += vif1.vifpacketsize << 2;
@ -1476,7 +1493,7 @@ static int Vif1TransMPG(u32 *data){
u32 splittransfer[4];
u32 splitptr = 0;
static int Vif1TransDirectHL(u32 *data){
static int __fastcall Vif1TransDirectHL(u32 *data){
int ret = 0;
@ -1558,7 +1575,7 @@ static int Vif1TransDirectHL(u32 *data){
}
static int Vif1TransUnpack(u32 *data){
static int __fastcall Vif1TransUnpack(u32 *data){
FreezeXMMRegs(1);
if (vif1.vifpacketsize < vif1.tag.size)
@ -1718,7 +1735,7 @@ static void Vif1CMDNull(){ // invalid opcode
// Vif1 Data Transfer Table
int (*Vif1TransTLB[128])(u32 *data) =
int (__fastcall *Vif1TransTLB[128])(u32 *data) =
{
Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , /*0x7*/
Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , Vif1TransNull , /*0xF*/
@ -2236,10 +2253,20 @@ void vif1Reset() {
vif1Regs->stat&= ~0x1F000000; // FQC=0
}
void SaveState::vif1Freeze() {
void SaveState::vif1Freeze()
{
Freeze(vif1);
if( IsLoading() ){
if( GetVersion() >= 0x14 )
{
Freeze( g_vif1HasMask3 );
Freeze( g_vif1Masks );
Freeze( g_vifRow1 );
Freeze( g_vifCol1 );
}
/*if( IsLoading() ){
SetNewMask(g_vif1Masks, g_vif1HasMask3, vif1Regs->mask, ~vif1Regs->mask);
if(vif1ch->chcr & 0x100)vif1.done = 0;
}
}*/
}

View File

@ -48,39 +48,39 @@ extern int Path3transfer;
#define vif0ch ((DMACh*)&PS2MEM_HW[0x8000])
#define vif1ch ((DMACh*)&PS2MEM_HW[0x9000])
void UNPACK_S_32( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_S_32( u32 *dest, u32 *data, int size );
void UNPACK_S_16u( u32 *dest, u32 *data, int size );
void UNPACK_S_16s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_S_16u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_S_16s( u32 *dest, u32 *data, int size );
void UNPACK_S_8u( u32 *dest, u32 *data, int size );
void UNPACK_S_8s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_S_8u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_S_8s( u32 *dest, u32 *data, int size );
void UNPACK_V2_32( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V2_32( u32 *dest, u32 *data, int size );
void UNPACK_V2_16u( u32 *dest, u32 *data, int size );
void UNPACK_V2_16s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V2_16u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V2_16s( u32 *dest, u32 *data, int size );
void UNPACK_V2_8u( u32 *dest, u32 *data, int size );
void UNPACK_V2_8s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V2_8u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V2_8s( u32 *dest, u32 *data, int size );
void UNPACK_V3_32( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V3_32( u32 *dest, u32 *data, int size );
void UNPACK_V3_16u( u32 *dest, u32 *data, int size );
void UNPACK_V3_16s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V3_16u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V3_16s( u32 *dest, u32 *data, int size );
void UNPACK_V3_8u( u32 *dest, u32 *data, int size );
void UNPACK_V3_8s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V3_8u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V3_8s( u32 *dest, u32 *data, int size );
void UNPACK_V4_32( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V4_32( u32 *dest, u32 *data, int size );
void UNPACK_V4_16u( u32 *dest, u32 *data, int size );
void UNPACK_V4_16s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V4_16u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V4_16s( u32 *dest, u32 *data, int size );
void UNPACK_V4_8u( u32 *dest, u32 *data, int size );
void UNPACK_V4_8s( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V4_8u( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V4_8s( u32 *dest, u32 *data, int size );
void UNPACK_V4_5( u32 *dest, u32 *data, int size );
void __fastcall UNPACK_V4_5( u32 *dest, u32 *data, int size );
void vifDmaInit();
void vif0Init();

View File

@ -113,9 +113,9 @@ __forceinline DataType __fastcall MemOp_r0(u32 addr)
switch( DataSize )
{
case 8: return ((vltbMemR8FP*)RWFT[0][0][hand])(paddr);
case 16: return ((vltbMemR16FP*)RWFT[1][0][hand])(paddr);
case 32: return ((vltbMemR32FP*)RWFT[2][0][hand])(paddr);
case 8: return ((vtlbMemR8FP*)RWFT[0][0][hand])(paddr);
case 16: return ((vtlbMemR16FP*)RWFT[1][0][hand])(paddr);
case 32: return ((vtlbMemR32FP*)RWFT[2][0][hand])(paddr);
jNO_DEFAULT;
}
@ -144,8 +144,8 @@ __forceinline void __fastcall MemOp_r1(u32 addr, DataType* data)
switch( DataSize )
{
case 64: ((vltbMemR64FP*)RWFT[3][0][hand])(paddr, data); break;
case 128: ((vltbMemR128FP*)RWFT[4][0][hand])(paddr, data); break;
case 64: ((vtlbMemR64FP*)RWFT[3][0][hand])(paddr, data); break;
case 128: ((vtlbMemR128FP*)RWFT[4][0][hand])(paddr, data); break;
jNO_DEFAULT;
}
@ -170,9 +170,9 @@ __forceinline void __fastcall MemOp_w0(u32 addr, DataType data)
switch( DataSize )
{
case 8: return ((vltbMemW8FP*)RWFT[0][1][hand])(paddr, (u8)data);
case 16: return ((vltbMemW16FP*)RWFT[1][1][hand])(paddr, (u16)data);
case 32: return ((vltbMemW32FP*)RWFT[2][1][hand])(paddr, (u32)data);
case 8: return ((vtlbMemW8FP*)RWFT[0][1][hand])(paddr, (u8)data);
case 16: return ((vtlbMemW16FP*)RWFT[1][1][hand])(paddr, (u16)data);
case 32: return ((vtlbMemW32FP*)RWFT[2][1][hand])(paddr, (u32)data);
jNO_DEFAULT;
}
@ -198,8 +198,8 @@ __forceinline void __fastcall MemOp_w1(u32 addr,const DataType* data)
//SysPrintf("Translted 0x%08X to 0x%08X\n",addr,paddr);
switch( DataSize )
{
case 64: return ((vltbMemW64FP*)RWFT[3][1][hand])(paddr, data);
case 128: return ((vltbMemW128FP*)RWFT[4][1][hand])(paddr, data);
case 64: return ((vtlbMemW64FP*)RWFT[3][1][hand])(paddr, data);
case 128: return ((vtlbMemW128FP*)RWFT[4][1][hand])(paddr, data);
jNO_DEFAULT;
}
@ -348,8 +348,8 @@ void __fastcall vtlbDefaultPhyWrite128(u32 addr,const mem128_t* data) { Console:
// Note: All handlers persist across calls to vtlb_Reset(), but are wiped/invalidated by calls to vtlb_Init()
//
// Returns a handle for the newly created handler See .vtlb_MapHandler for use of the return value.
vtlbHandler vtlb_RegisterHandler( vltbMemR8FP* r8,vltbMemR16FP* r16,vltbMemR32FP* r32,vltbMemR64FP* r64,vltbMemR128FP* r128,
vltbMemW8FP* w8,vltbMemW16FP* w16,vltbMemW32FP* w32,vltbMemW64FP* w64,vltbMemW128FP* w128)
vtlbHandler vtlb_RegisterHandler( vtlbMemR8FP* r8,vtlbMemR16FP* r16,vtlbMemR32FP* r32,vtlbMemR64FP* r64,vtlbMemR128FP* r128,
vtlbMemW8FP* w8,vtlbMemW16FP* w16,vtlbMemW32FP* w32,vtlbMemW64FP* w64,vtlbMemW128FP* w128)
{
//write the code :p
vtlbHandler rv=vtlbHandlerCount++;

View File

@ -8,18 +8,18 @@ typedef u64 mem64_t;
typedef u64 mem128_t;
// Specialized function pointers for each read type
typedef mem8_t __fastcall vltbMemR8FP(u32 addr);
typedef mem16_t __fastcall vltbMemR16FP(u32 addr);
typedef mem32_t __fastcall vltbMemR32FP(u32 addr);
typedef void __fastcall vltbMemR64FP(u32 addr,mem64_t* data);
typedef void __fastcall vltbMemR128FP(u32 addr,mem128_t* data);
typedef mem8_t __fastcall vtlbMemR8FP(u32 addr);
typedef mem16_t __fastcall vtlbMemR16FP(u32 addr);
typedef mem32_t __fastcall vtlbMemR32FP(u32 addr);
typedef void __fastcall vtlbMemR64FP(u32 addr,mem64_t* data);
typedef void __fastcall vtlbMemR128FP(u32 addr,mem128_t* data);
// Specialized function pointers for each write type
typedef void __fastcall vltbMemW8FP(u32 addr,mem8_t data);
typedef void __fastcall vltbMemW16FP(u32 addr,mem16_t data);
typedef void __fastcall vltbMemW32FP(u32 addr,mem32_t data);
typedef void __fastcall vltbMemW64FP(u32 addr,const mem64_t* data);
typedef void __fastcall vltbMemW128FP(u32 addr,const mem128_t* data);
typedef void __fastcall vtlbMemW8FP(u32 addr,mem8_t data);
typedef void __fastcall vtlbMemW16FP(u32 addr,mem16_t data);
typedef void __fastcall vtlbMemW32FP(u32 addr,mem32_t data);
typedef void __fastcall vtlbMemW64FP(u32 addr,const mem64_t* data);
typedef void __fastcall vtlbMemW128FP(u32 addr,const mem128_t* data);
typedef u32 vtlbHandler;
@ -31,8 +31,8 @@ extern void vtlb_free( void* pmem, uint size );
//physical stuff
vtlbHandler vtlb_RegisterHandler( vltbMemR8FP* r8,vltbMemR16FP* r16,vltbMemR32FP* r32,vltbMemR64FP* r64,vltbMemR128FP* r128,
vltbMemW8FP* w8,vltbMemW16FP* w16,vltbMemW32FP* w32,vltbMemW64FP* w64,vltbMemW128FP* w128);
vtlbHandler vtlb_RegisterHandler( vtlbMemR8FP* r8,vtlbMemR16FP* r16,vtlbMemR32FP* r32,vtlbMemR64FP* r64,vtlbMemR128FP* r128,
vtlbMemW8FP* w8,vtlbMemW16FP* w16,vtlbMemW32FP* w32,vtlbMemW64FP* w64,vtlbMemW128FP* w128);
extern void vtlb_MapHandler(vtlbHandler handler,u32 start,u32 size);
extern void vtlb_MapBlock(void* base,u32 start,u32 size,u32 blocksize=0);

View File

@ -1097,8 +1097,8 @@ BEGIN
CONTROL "Use x1.5 Cycle Rate",IDC_EESYNC1,"Button",BS_AUTORADIOBUTTON,13,79,87,10
CONTROL "Use x2 Cycle Rate",IDC_EESYNC2,"Button",BS_AUTORADIOBUTTON,13,113,83,10
CONTROL "Use x3 Cycle Rate",IDC_EESYNC3,"Button",BS_AUTORADIOBUTTON,13,147,80,10
CONTROL "Enable IOP x2 Cycle Rate",IDC_IOPSYNC,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,174,97,98,10
CONTROL "WaitCycles Sync Hack",IDC_WAITCYCLES,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,174,138,90,10
CONTROL "Enable IOP x2 Cycle Rate",IDC_IOPSYNC,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,174,88,98,10
CONTROL "WaitCycles Sync Hack",IDC_WAITCYCLES,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,174,127,90,10
CONTROL "Escape Hack - Use Esc key to fully exit PCSX2.",IDC_ESCHACK,
"Button",BS_AUTOCHECKBOX | WS_TABSTOP,13,234,180,10
DEFPUSHBUTTON "OK",IDOK,217,242,50,14
@ -1106,15 +1106,15 @@ BEGIN
CTEXT "These hacks will speed up emulation but reduce emulation compatibility or cause visual errors. If you have problems, disable all these and try again!",IDC_HACKDESC,18,7,286,19
GROUPBOX "EmotionEngine (EE) Sync Hacks",IDC_STATIC,7,31,159,180
GROUPBOX "Miscellaneous",IDC_STATIC,7,220,194,33
LTEXT "Important: X2 and X3 sync hacks *will* cause choppy/skippy audio on many FMV movies.",IDC_STATIC,13,183,149,25
LTEXT "*OBSOLETE* Better off using the INTC Sync Hack instead.",IDC_STATIC,25,158,133,19
LTEXT "Important: X2 and X3 sync hacks *will* cause choppy/skippy audio on many FMV movies.",IDC_STATIC,13,188,149,21
LTEXT "Known to work well with a couple games, namely Shadow of the Colossus (but breaks most other games).",IDC_STATIC,25,158,133,28
LTEXT "Big speedup! Works well with many games.",IDC_STATIC,25,124,125,19
LTEXT "Most compatible option - recommended for everyone with high-end machines.",IDC_STATIC,25,55,136,19
LTEXT "Small speedup and works well with most games.",IDC_STATIC,186,109,134,22
LTEXT "Small speedup. Works well with most games, but may cause certain games to crash or freeze up during bootup or stage changes.",IDC_STATIC,186,150,141,39
LTEXT "Small speedup and works well with most games.",IDC_STATIC,186,100,134,22
LTEXT "Small speedup. Works well with most games, but may cause certain games to crash or freeze up during bootup or stage changes.",IDC_STATIC,186,139,141,39
LTEXT "Moderate speedup and works well with most games.",IDC_STATIC,25,90,129,19
CONTROL "INTC Sync Hack (experimental)",IDC_INTCSTATHACK,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,174,43,127,10
LTEXT "Huge speedup! And few negative side effects in most games. When enabling this it might be best to leave the EE sync hack set to Default.",IDC_STATIC,186,55,140,36
LTEXT "Huge speedup in many games, and a pretty high compatibility rate (some games still work better with EE sync hacks).",IDC_STATIC,186,55,140,28
END

View File

@ -61,7 +61,7 @@ extern "C" PCSX2_ALIGNED16(u32 s_TempDecompress[4]) = {0};
#include <xmmintrin.h>
#include <emmintrin.h>
void SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask)
void __fastcall SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask)
{
u32 i;
u32 prev = 0;
@ -98,7 +98,7 @@ void SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask)
#else // gcc
void SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask)
void __fastcall SetNewMask(u32* vif1masks, u32* hasmask, u32 mask, u32 oldmask)
{
u32 i;
u32 prev = 0;

View File

@ -742,10 +742,81 @@ void recDIVU1_constt(int info)
EERECOMPILE_CODE0(DIVU1, XMMINFO_READS|XMMINFO_READT);
//do EEINST_SETSIGNEXT
REC_FUNC_DEL( MADD, _Rd_ );
static PCSX2_ALIGNED16(u32 s_MaddMask[]) = { 0x80000000, 0, 0x80000000, 0 };
void recMADD()
{
EEINST_SETSIGNEXT(_Rs_);
EEINST_SETSIGNEXT(_Rt_);
if( GPR_IS_CONST2(_Rs_, _Rt_) ) {
u64 result = ((s64)g_cpuConstRegs[_Rs_].SL[0] * (s64)g_cpuConstRegs[_Rt_].SL[0]);
_deleteEEreg(XMMGPR_LO, 1);
_deleteEEreg(XMMGPR_HI, 1);
// dadd
MOV32MtoR( EAX, (int)&cpuRegs.LO.UL[ 0 ] );
MOV32MtoR( ECX, (int)&cpuRegs.HI.UL[ 0 ] );
ADD32ItoR( EAX, (u32)result&0xffffffff );
ADC32ItoR( ECX, (u32)(result>>32) );
CDQ();
if( _Rd_) {
_eeOnWriteReg(_Rd_, 1);
_deleteEEreg(_Rd_, 0);
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 0 ], EAX );
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 1 ], EDX );
}
MOV32RtoM( (int)&cpuRegs.LO.UL[0], EAX );
MOV32RtoM( (int)&cpuRegs.LO.UL[1], EDX );
MOV32RtoM( (int)&cpuRegs.HI.UL[0], ECX );
MOV32RtoR(EAX, ECX);
CDQ();
MOV32RtoM( (int)&cpuRegs.HI.UL[1], EDX );
return;
}
_deleteEEreg(XMMGPR_LO, 1);
_deleteEEreg(XMMGPR_HI, 1);
_deleteGPRtoXMMreg(_Rs_, 1);
_deleteGPRtoXMMreg(_Rt_, 1);
_deleteMMXreg(MMX_GPR+_Rs_, 1);
_deleteMMXreg(MMX_GPR+_Rt_, 1);
if( GPR_IS_CONST1(_Rs_) ) {
MOV32ItoR( EAX, g_cpuConstRegs[_Rs_].UL[0] );
MUL32M( (int)&cpuRegs.GPR.r[ _Rt_ ].UL[ 0 ] );
}
else if ( GPR_IS_CONST1(_Rt_) ) {
MOV32ItoR( EAX, g_cpuConstRegs[_Rt_].UL[0] );
MUL32M( (int)&cpuRegs.GPR.r[ _Rs_ ].UL[ 0 ] );
}
else {
MOV32MtoR( EAX, (int)&cpuRegs.GPR.r[ _Rs_ ].UL[ 0 ] );
MUL32M( (int)&cpuRegs.GPR.r[ _Rt_ ].UL[ 0 ] );
}
MOV32RtoR( ECX, EDX );
ADD32MtoR( EAX, (u32)&cpuRegs.LO.UL[0] );
ADC32MtoR( ECX, (u32)&cpuRegs.HI.UL[0] );
CDQ();
if( _Rd_ ) {
_eeOnWriteReg(_Rd_, 1);
_deleteEEreg(_Rd_, 0);
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 0 ], EAX );
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 1 ], EDX );
}
MOV32RtoM( (int)&cpuRegs.LO.UL[0], EAX );
MOV32RtoM( (int)&cpuRegs.LO.UL[1], EDX );
MOV32RtoM( (int)&cpuRegs.HI.UL[0], ECX );
MOV32RtoR(EAX, ECX);
CDQ();
MOV32RtoM( (int)&cpuRegs.HI.UL[1], EDX );
}
//static PCSX2_ALIGNED16(u32 s_MaddMask[]) = { 0x80000000, 0, 0x80000000, 0 };
void recMADDU()
{
@ -822,26 +893,153 @@ void recMADDU()
void recMADD1()
{
//SysPrintf("MADD1 email zero if abnormal behavior\n");
EEINST_SETSIGNEXT(_Rs_);
EEINST_SETSIGNEXT(_Rt_);
if( _Rd_ ) EEINST_SETSIGNEXT(_Rd_);
_deleteEEreg(XMMGPR_LO, 0);
_deleteEEreg(XMMGPR_HI, 0);
recCall( Interp::MADD1, _Rd_ );
if( GPR_IS_CONST2(_Rs_, _Rt_) ) {
u64 result = ((s64)g_cpuConstRegs[_Rs_].SL[0] * (s64)g_cpuConstRegs[_Rt_].SL[0]);
_deleteEEreg(XMMGPR_LO, 1);
_deleteEEreg(XMMGPR_HI, 1);
// dadd
MOV32MtoR( EAX, (int)&cpuRegs.LO.UL[ 2 ] );
MOV32MtoR( ECX, (int)&cpuRegs.HI.UL[ 2 ] );
ADD32ItoR( EAX, (u32)result&0xffffffff );
ADC32ItoR( ECX, (u32)(result>>32) );
CDQ();
if( _Rd_) {
_eeOnWriteReg(_Rd_, 1);
_deleteEEreg(_Rd_, 0);
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 0 ], EAX );
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 1 ], EDX );
}
MOV32RtoM( (int)&cpuRegs.LO.UL[2], EAX );
MOV32RtoM( (int)&cpuRegs.LO.UL[3], EDX );
MOV32RtoM( (int)&cpuRegs.HI.UL[2], ECX );
MOV32RtoR(EAX, ECX);
CDQ();
MOV32RtoM( (int)&cpuRegs.HI.UL[3], EDX );
return;
}
_deleteEEreg(XMMGPR_LO, 1);
_deleteEEreg(XMMGPR_HI, 1);
_deleteGPRtoXMMreg(_Rs_, 1);
_deleteGPRtoXMMreg(_Rt_, 1);
_deleteMMXreg(MMX_GPR+_Rs_, 1);
_deleteMMXreg(MMX_GPR+_Rt_, 1);
if( GPR_IS_CONST1(_Rs_) ) {
MOV32ItoR( EAX, g_cpuConstRegs[_Rs_].UL[0] );
IMUL32M( (int)&cpuRegs.GPR.r[ _Rt_ ].UL[ 0 ] );
}
else if ( GPR_IS_CONST1(_Rt_) ) {
MOV32ItoR( EAX, g_cpuConstRegs[_Rt_].UL[0] );
IMUL32M( (int)&cpuRegs.GPR.r[ _Rs_ ].UL[ 0 ] );
}
else {
MOV32MtoR( EAX, (int)&cpuRegs.GPR.r[ _Rs_ ].UL[ 0 ] );
IMUL32M( (int)&cpuRegs.GPR.r[ _Rt_ ].UL[ 0 ] );
}
MOV32RtoR( ECX, EDX );
ADD32MtoR( EAX, (u32)&cpuRegs.LO.UL[2] );
ADC32MtoR( ECX, (u32)&cpuRegs.HI.UL[2] );
CDQ();
if( _Rd_ ) {
_eeOnWriteReg(_Rd_, 1);
_deleteEEreg(_Rd_, 0);
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 0 ], EAX );
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 1 ], EDX );
}
MOV32RtoM( (int)&cpuRegs.LO.UL[2], EAX );
MOV32RtoM( (int)&cpuRegs.LO.UL[3], EDX );
MOV32RtoM( (int)&cpuRegs.HI.UL[2], ECX );
MOV32RtoR(EAX, ECX);
CDQ();
MOV32RtoM( (int)&cpuRegs.HI.UL[3], EDX );
}
//static PCSX2_ALIGNED16(u32 s_MaddMask[]) = { 0x80000000, 0, 0x80000000, 0 };
void recMADDU1()
{
//SysPrintf("MADDU1 email zero if abnormal behavior\n");
EEINST_SETSIGNEXT(_Rs_);
EEINST_SETSIGNEXT(_Rt_);
if( _Rd_ ) EEINST_SETSIGNEXT(_Rd_);
_deleteEEreg(XMMGPR_LO, 0);
_deleteEEreg(XMMGPR_HI, 0);
recCall( Interp::MADDU1, _Rd_ );
if( GPR_IS_CONST2(_Rs_, _Rt_) ) {
u64 result = ((u64)g_cpuConstRegs[_Rs_].UL[0] * (u64)g_cpuConstRegs[_Rt_].UL[0]);
_deleteEEreg(XMMGPR_LO, 1);
_deleteEEreg(XMMGPR_HI, 1);
// dadd
MOV32MtoR( EAX, (int)&cpuRegs.LO.UL[ 2 ] );
MOV32MtoR( ECX, (int)&cpuRegs.HI.UL[ 2 ] );
ADD32ItoR( EAX, (u32)result&0xffffffff );
ADC32ItoR( ECX, (u32)(result>>32) );
CDQ();
if( _Rd_) {
_eeOnWriteReg(_Rd_, 1);
_deleteEEreg(_Rd_, 0);
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 0 ], EAX );
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 1 ], EDX );
}
MOV32RtoM( (int)&cpuRegs.LO.UL[2], EAX );
MOV32RtoM( (int)&cpuRegs.LO.UL[3], EDX );
MOV32RtoM( (int)&cpuRegs.HI.UL[2], ECX );
MOV32RtoR(EAX, ECX);
CDQ();
MOV32RtoM( (int)&cpuRegs.HI.UL[3], EDX );
return;
}
_deleteEEreg(XMMGPR_LO, 1);
_deleteEEreg(XMMGPR_HI, 1);
_deleteGPRtoXMMreg(_Rs_, 1);
_deleteGPRtoXMMreg(_Rt_, 1);
_deleteMMXreg(MMX_GPR+_Rs_, 1);
_deleteMMXreg(MMX_GPR+_Rt_, 1);
if( GPR_IS_CONST1(_Rs_) ) {
MOV32ItoR( EAX, g_cpuConstRegs[_Rs_].UL[0] );
MUL32M( (int)&cpuRegs.GPR.r[ _Rt_ ].UL[ 0 ] );
}
else if ( GPR_IS_CONST1(_Rt_) ) {
MOV32ItoR( EAX, g_cpuConstRegs[_Rt_].UL[0] );
MUL32M( (int)&cpuRegs.GPR.r[ _Rs_ ].UL[ 0 ] );
}
else {
MOV32MtoR( EAX, (int)&cpuRegs.GPR.r[ _Rs_ ].UL[ 0 ] );
MUL32M( (int)&cpuRegs.GPR.r[ _Rt_ ].UL[ 0 ] );
}
MOV32RtoR( ECX, EDX );
ADD32MtoR( EAX, (u32)&cpuRegs.LO.UL[2] );
ADC32MtoR( ECX, (u32)&cpuRegs.HI.UL[2] );
CDQ();
if( _Rd_ ) {
_eeOnWriteReg(_Rd_, 1);
_deleteEEreg(_Rd_, 0);
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 0 ], EAX );
MOV32RtoM( (int)&cpuRegs.GPR.r[ _Rd_ ].UL[ 1 ], EDX );
}
MOV32RtoM( (int)&cpuRegs.LO.UL[2], EAX );
MOV32RtoM( (int)&cpuRegs.LO.UL[3], EDX );
MOV32RtoM( (int)&cpuRegs.HI.UL[2], ECX );
MOV32RtoR(EAX, ECX);
CDQ();
MOV32RtoM( (int)&cpuRegs.HI.UL[3], EDX );
}
#else
////////////////////////////////////////////////////
@ -953,4 +1151,4 @@ REC_FUNC_DEL( MADDU1, _Rd_ );
#endif
} } }
} } }