diff --git a/pcsx2/Recording/InputRecording.cpp b/pcsx2/Recording/InputRecording.cpp index 3459752b17..5f9af204a7 100644 --- a/pcsx2/Recording/InputRecording.cpp +++ b/pcsx2/Recording/InputRecording.cpp @@ -39,10 +39,10 @@ void SaveStateBase::InputRecordingFreeze() Freeze(g_FrameCount); #ifndef DISABLE_RECORDING - // Loading a save-state is an asynchronous task, if we are playing a recording + // Loading a save-state is an asynchronous task. If we are playing a recording // that starts from a savestate (not power-on) and the starting (pcsx2 internal) frame // marker has not been set (which comes from the save-state), we initialize it. - if (g_InputRecording.IsSavestateInitializing()) + if (g_InputRecording.IsInitialLoad()) { g_InputRecording.SetStartingFrame(g_FrameCount); } @@ -52,12 +52,7 @@ void SaveStateBase::InputRecordingFreeze() // detect loading a savestate as a frame being drawn g_InputRecordingControls.SetFrameCountTracker(g_FrameCount); - // If the starting savestate has been loaded (on a current-frame recording) and a save-state is loaded while recording - // or replaying the movie it is an undo operation that needs to be tracked. - // - // The reason it's also an undo operation when replaying is because the user can switch modes at any time - // and begin undoing. While this isn't impossible to resolve, it's a separate issue and not of the utmost importance (this is just interesting metadata) - if (IsLoading() && !g_InputRecording.IsSavestateInitializing()) + if (IsLoading()) { g_InputRecording.SetFrameCounter(g_FrameCount); } @@ -66,6 +61,28 @@ void SaveStateBase::InputRecordingFreeze() } #ifndef DISABLE_RECORDING +// Save or load PCSX2's global frame counter (g_FrameCount) along with each full/fast boot +// +// This is to prevent any inaccuracy issues caused by having a different +// internal emulation frame count than what it was at the beginning of the +// original recording +void Pcsx2App::RecordingReset() +{ + // Booting is an asynchronous task. If we are playing a recording + // that starts from power-on and the starting (pcsx2 internal) frame + // marker has not been set, we initialize it. + if (g_InputRecording.IsInitialLoad()) + { + g_InputRecording.SetStartingFrame(0); + } + else if (g_InputRecording.IsActive()) + { + // Explicitly set the frame change tracking variable as to not + // detect rebooting as a frame being drawn + g_InputRecordingControls.SetFrameCountTracker(g_FrameCount); + g_InputRecording.SetFrameCounter(0); + } +} InputRecording g_InputRecording; @@ -157,9 +174,9 @@ bool InputRecording::IsActive() return state != InputRecordingMode::NotActive; } -bool InputRecording::IsSavestateInitializing() +bool InputRecording::IsInitialLoad() { - return savestateInitializing; + return initialLoad; } bool InputRecording::IsReplaying() @@ -212,11 +229,6 @@ void InputRecording::RecordModeToggle() } } -void InputRecording::SavestateInitialized() -{ - savestateInitializing = false; -} - void InputRecording::SetFrameCounter(u32 newGFrameCount) { // Forces inputRecording to wait for a confirmed pause before resetting @@ -256,13 +268,13 @@ void InputRecording::SetFrameCounter(u32 newGFrameCount) void InputRecording::SetStartingFrame(u32 newStartingFrame) { startingFrame = newStartingFrame; - if (savestateInitializing) + if (inputRecordingData.FromSaveState()) { // TODO - make a function of my own to simplify working with the logging macros recordingConLog(wxString::Format(L"[REC]: Internal Starting Frame: %d\n", startingFrame)); - savestateInitializing = false; } frameCounter = 0; + initialLoad = false; } void InputRecording::Stop() @@ -277,15 +289,22 @@ void InputRecording::Stop() bool InputRecording::Create(wxString FileName, bool fromSaveState, wxString authorName) { - savestateInitializing = fromSaveState; if (!inputRecordingData.OpenNew(FileName, fromSaveState)) { return false; } - if (!fromSaveState) + initialLoad = true; + if (fromSaveState) + { + if (wxFileExists(FileName + "_SaveState.p2s")) + { + wxCopyFile(FileName + "_SaveState.p2s", FileName + "_SaveState.p2s.bak", true); + } + StateCopy_SaveToFile(FileName + "_SaveState.p2s"); + } + else { - SetStartingFrame(0); sApp.SysExecute(g_Conf->CdvdSource); } @@ -332,13 +351,12 @@ bool InputRecording::Play(wxString fileName) inputRecordingData.Close(); return false; } - savestateInitializing = true; + initialLoad = true; StateCopy_LoadFromFile(inputRecordingData.GetFilename() + "_SaveState.p2s"); } else { - savestateInitializing = false; - SetStartingFrame(0); + initialLoad = true; sApp.SysExecute(g_Conf->CdvdSource); } diff --git a/pcsx2/Recording/InputRecording.h b/pcsx2/Recording/InputRecording.h index e174e48f77..566cc2eb9c 100644 --- a/pcsx2/Recording/InputRecording.h +++ b/pcsx2/Recording/InputRecording.h @@ -43,10 +43,10 @@ public: // If there is currently an input recording being played back or actively being recorded bool IsActive(); - // Whether or not the recording's initial save state has yet to be loaded or saved and + // Whether or not the recording's initial state has yet to be loaded or saved and // the rest of the recording can be initialized // This is not applicable to recordings from a "power-on" state - bool IsSavestateInitializing(); + bool IsInitialLoad(); // If there is currently an input recording being played back bool IsReplaying(); @@ -66,9 +66,6 @@ public: // Switches between recording and replaying the active input recording file void RecordModeToggle(); - // Mark the recording's initial savestate as having been loaded or saved successfully - void SavestateInitialized(); - // Set the running frame counter for the input recording to an arbitrary value void SetFrameCounter(u32 newGFrameCount); @@ -95,7 +92,7 @@ private: // DEPRECATED: Slated for removal bool fInterruptFrame = false; InputRecordingFile inputRecordingData; - bool savestateInitializing = false; + bool initialLoad = false; u32 startingFrame = 0; s32 frameCounter = 0; bool incrementUndo = false; diff --git a/pcsx2/Recording/InputRecordingFile.cpp b/pcsx2/Recording/InputRecordingFile.cpp index 7d797eacd0..fe5177bf2a 100644 --- a/pcsx2/Recording/InputRecordingFile.cpp +++ b/pcsx2/Recording/InputRecordingFile.cpp @@ -138,11 +138,6 @@ bool InputRecordingFile::OpenNew(const wxString path, bool fromSavestate) if (open(path, true)) { savestate.fromSavestate = true; - if (wxFileExists(path + "_SaveState.p2s")) - { - wxCopyFile(path + "_SaveState.p2s", path + "_SaveState.p2s.bak", true); - } - StateCopy_SaveToFile(path + "_SaveState.p2s"); return true; } } diff --git a/pcsx2/gui/App.h b/pcsx2/gui/App.h index 435646e3ff..99ca9c4391 100644 --- a/pcsx2/gui/App.h +++ b/pcsx2/gui/App.h @@ -561,6 +561,11 @@ public: void SysExecute(); void SysExecute( CDVD_SourceType cdvdsrc, const wxString& elf_override=wxEmptyString ); void LogicalVsync(); + +#ifndef DISABLE_RECORDING + void RecordingReset(); +#endif + SysMainMemory& GetVmReserve(); @@ -641,10 +646,6 @@ public: bool OnCmdLineError( wxCmdLineParser& parser ); bool ParseOverrides( wxCmdLineParser& parser ); -#ifndef DISABLE_RECORDING - void ResetRecordingCounter(); -#endif - #ifdef __WXDEBUG__ void OnAssertFailure( const wxChar *file, int line, const wxChar *func, const wxChar *cond, const wxChar *msg ); #endif diff --git a/pcsx2/gui/AppMain.cpp b/pcsx2/gui/AppMain.cpp index a9c32c3544..0794f7741a 100644 --- a/pcsx2/gui/AppMain.cpp +++ b/pcsx2/gui/AppMain.cpp @@ -1153,23 +1153,10 @@ void Pcsx2App::SysExecute( CDVD_SourceType cdvdsrc, const wxString& elf_override { SysExecutorThread.PostEvent( new SysExecEvent_Execute(cdvdsrc, elf_override) ); #ifndef DISABLE_RECORDING - ResetRecordingCounter(); + RecordingReset(); #endif } -#ifndef DISABLE_RECORDING -// Sets the frame counter for a running input recording file to the proper displacement -// from the recording's starting frame to the g_framecount of a fresh emulation boot/reboot -// Simply: frameCounter = -startingFrame -void Pcsx2App::ResetRecordingCounter() -{ - if (g_InputRecording.IsActive()) - { - g_InputRecording.SetFrameCounter(0); - } -} -#endif - // Returns true if there is a "valid" virtual machine state from the user's perspective. This // means the user has started the emulator and not issued a full reset. // Thread Safety: The state of the system can change in parallel to execution of the