//GiGaHeRz's SPU2 Driver //Copyright (c) 2003-2008, David Quintana // //This library is free software; you can redistribute it and/or //modify it under the terms of the GNU Lesser General Public //License as published by the Free Software Foundation; either //version 2.1 of the License, or (at your option) any later version. // //This library is distributed in the hope that it will be useful, //but WITHOUT ANY WARRANTY; without even the implied warranty of //MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU //Lesser General Public License for more details. // //You should have received a copy of the GNU Lesser General Public //License along with this library; if not, write to the Free Software //Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA // #include "Global.h" #include "PS2E-spu2.h" #ifdef _MSC_VER # include "Windows.h" #endif FILE* s2rfile; void s2r_write16(s16 data) { fwrite(&data,2,1,s2rfile); } void s2r_write32(u32 data) { fwrite(&data,4,1,s2rfile); } #define EMITC(i,a) s2r_write32(((u32)(i&0x7)<<29)|(a&0x1FFFFFFF)) int s2r_open(u32 ticks, char *filename) { s2rfile=fopen(filename,"wb"); if(s2rfile) s2r_write32(ticks); return s2rfile?0:-1; } void s2r_readreg(u32 ticks,u32 addr) { if(!s2rfile) return; s2r_write32(ticks); EMITC(0,addr); } void s2r_writereg(u32 ticks,u32 addr,s16 value) { if(!s2rfile) return; s2r_write32(ticks); EMITC(1,addr); s2r_write16(value); } void s2r_writedma4(u32 ticks,u16*data,u32 len) { u32 i; if(!s2rfile) return; s2r_write32(ticks); EMITC(2,len); for(i=0;i 10) WaitTime = 10; if(WaitTime == 0) WaitTime = 1; SleepEx(WaitTime, TRUE); // Refresh current time after sleeping u64 Current = HighResCounter(); u32 delta = (u32)floor((Current-HighResPrev) / HighResScale + 0.5); // We lose some precision here, cycles might drift away over long periods of time ;P // Calculate time delta CurrentIOPCycle += delta; HighResPrev += (u64)floor(delta * HighResScale + 0.5); // Trying to compensate drifting mentioned above, not necessarily useful. return delta; } #ifdef WIN32 BOOL WINAPI HandlerRoutine(DWORD dwCtrlType) { Running = false; return TRUE; } #endif #include "Windows/Dialogs.h" EXPORT_C_(void) s2r_replay(HWND hwnd, HINSTANCE hinst, LPSTR filename, int nCmdShow) { #ifndef ENABLE_NEW_IOPDMA_SPU2 int events=0; Running = true; #ifdef WIN32 AllocConsole(); SetConsoleCtrlHandler(HandlerRoutine, TRUE); conprintf("Playing %s file on %x...",filename,hwnd); #endif // load file FILE *file=fopen(filename,"rb"); if(!file) { conprintf("Could not open the replay file."); return; } // if successful, init the plugin #define TryRead(dest,size,count,file) if(fread(dest,size,count,file)>29; sval&=0x1FFFFFFF; u32 TargetCycle = ccycle * 768; while(TargetCycle > CurrentIOPCycle) { u32 delta = WaitSync(TargetCycle); SPU2async(delta); } switch(evid) { case 0: SPU2read(sval); break; case 1: TryRead(&tval,2,1,file); SPU2write(sval,tval); break; case 2: TryRead(dmabuffer,sval,2,file); SPU2writeDMA4Mem(dmabuffer,sval); break; case 3: TryRead(dmabuffer,sval,2,file); SPU2writeDMA7Mem(dmabuffer,sval); break; default: // not implemented return; break; } events++; } Finish: //shutdown SPU2close(); SPU2shutdown(); fclose(file); conprintf("Finished playing %s file (%d cycles, %d events).",filename,CurrentIOPCycle,events); #ifdef WIN32 FreeConsole(); #endif replay_mode=false; #endif } #endif