Selectable amount of rewind states no longer dummy. Fixed loading rewind when none left. Todo: make the state prior loadable too.

This commit is contained in:
n-a-c-h
2005-04-10 07:29:04 +00:00
parent 7a706dcd65
commit 2ee4e8184e
2 changed files with 55 additions and 155 deletions

View File

@@ -55,21 +55,17 @@ EXTSYM fxbit67pcal,SfxSFR,nosprincr,cpucycle,switchtovirqdeb,switchtonmideb
EXTSYM MovieSeekBehind,SaveSramData,BackupCVFrame,RestoreCVFrame,loadstate EXTSYM MovieSeekBehind,SaveSramData,BackupCVFrame,RestoreCVFrame,loadstate
EXTSYM KeyInsrtChap,KeyNextChap,KeyPrevChap,MovieInsertChapter,MovieSeekAhead EXTSYM KeyInsrtChap,KeyNextChap,KeyPrevChap,MovieInsertChapter,MovieSeekAhead
EXTSYM ResetDuringMovie,EMUPauseKey,INCRFrameKey,MovieWaiting,NoInputRead EXTSYM ResetDuringMovie,EMUPauseKey,INCRFrameKey,MovieWaiting,NoInputRead
EXTSYM AllocatedRewindStates
%ifdef __MSDOS__ %ifdef __MSDOS__
EXTSYM dssel EXTSYM dssel
%endif %endif
SECTION .data SECTION .data
NEWSYM CBackupPos, dd 0
NEWSYM PBackupPos, dd 0
NEWSYM tempedx, dd 0 NEWSYM tempedx, dd 0
NEWSYM tempesi, dd 0 NEWSYM tempesi, dd 0
NEWSYM tempedi, dd 0 NEWSYM tempedi, dd 0
NEWSYM tempebp, dd 0 NEWSYM tempebp, dd 0
NEWSYM RewindOldPos, dd 0
NEWSYM RewindPos, dd 0
NEWSYM RewindTimer, dd 0 NEWSYM RewindTimer, dd 0
NEWSYM BackState, db 1 NEWSYM BackState, db 1
NEWSYM BackStateSize, dd 6 NEWSYM BackStateSize, dd 6
@@ -96,76 +92,39 @@ NEWSYM ProcessRewind
cmp byte[pressed+eax],1 cmp byte[pressed+eax],1
jne near .notokay jne near .notokay
mov byte[pressed+eax],2 mov byte[pressed+eax],2
mov eax,[RewindOldPos]
cmp [RewindPos],eax
je near .notokay
dec dword[RewindPos]
and dword[RewindPos],0Fh
mov eax,[RewindOldPos]
cmp [RewindPos],eax
je .notokay2
dec dword[RewindPos]
and dword[RewindPos],0Fh
mov eax,[RewindPos]
mov [PBackupPos],eax
push ecx
push ebx
pushad pushad
call RestoreCVFrame call RestoreCVFrame
popad popad
mov esi,[tempesi] mov esi,[tempesi]
mov edi,[tempedi] mov edi,[tempedi]
mov ebp,[tempebp] mov ebp,[tempebp]
; Clear Cache Check
mov ebx,vidmemch2
mov ecx,4096+4096+4096
.next
mov byte[ebx],1
inc ebx
dec ecx
jnz .next
pop ebx
pop ecx
inc dword[RewindPos]
and dword[RewindPos],0Fh
mov edx,[tempedx] mov edx,[tempedx]
.notokay .notokay
ret ret
.notokay2
inc dword[RewindPos]
and dword[RewindPos],0Fh
ret
NEWSYM UpdateRewind NEWSYM UpdateRewind
push eax cmp byte[AllocatedRewindStates],0
je .norewinds
cmp dword[KeyRewind],0 cmp dword[KeyRewind],0
je .notftimer je .norewinds
call ProcessRewind
dec dword[RewindTimer] dec dword[RewindTimer]
jnz .notftimer jnz .checkrewind
jmp .okay
.notftimer
pop eax
ret
.okay
mov eax,[RewindPos]
mov [CBackupPos],eax
mov [tempedx],edx mov [tempedx],edx
mov [tempesi],esi mov [tempesi],esi
mov [tempedi],edi mov [tempedi],edi
mov [tempebp],ebp mov [tempebp],ebp
pushad pushad
call BackupCVFrame call BackupCVFrame
popad popad
inc dword[RewindPos]
and dword[RewindPos],0Fh .checkrewind
mov eax,[RewindOldPos] call ProcessRewind
cmp [RewindPos],eax .norewinds
jne .noteq
inc dword[RewindOldPos]
and dword[RewindOldPos],0Fh
.noteq
pop eax
ret ret
SECTION .data SECTION .data

View File

@@ -192,47 +192,51 @@ static void memcpyrinc(unsigned char **src, void *dest, size_t len)
extern unsigned int RewindTimer; extern unsigned int RewindTimer;
extern unsigned char RewindStates; extern unsigned char RewindStates;
unsigned char *StateBackup = 0; unsigned char *StateBackup = 0;
unsigned char AllocatedRewindStates, LatestRewindPos, EarliestRewindPos;
size_t rewind_state_size, cur_zst_size, old_zst_size; size_t rewind_state_size, cur_zst_size, old_zst_size;
/* A nice idea, but needs more ported from the assembly first. extern unsigned char RewindFrames, romispal;
size_t RewindPos, RewindEarliestPos; extern unsigned char MovieProcessing;
void zmv_rewind_save(size_t, bool);
void zmv_rewind_load(size_t, bool);
#define ActualRewindFrames (RewindFrames * (romispal ? 25 : 30))
void BackupCVFrame() void BackupCVFrame()
{ {
unsigned char *RewindBufferPos = StateBackup + RewindPos*rewind_state_size; unsigned char *RewindBufferPos = StateBackup + LatestRewindPos*rewind_state_size;
printf("Backing up rewind in slot #%u\n", RewindPos); printf("Backing up rewind in slot #%u\n", LatestRewindPos);
if (MovieProcessing == 1) { zmv_rewind_save(LatestRewindPos, true); }
else if (MovieProcessing == 2) { zmv_rewind_save(LatestRewindPos, false); }
copy_state_data(RewindBufferPos, memcpyinc, false); copy_state_data(RewindBufferPos, memcpyinc, false);
RewindPos++;
if (RewindPos == RewindStates) LatestRewindPos = (LatestRewindPos != AllocatedRewindStates-1) ? LatestRewindPos+1 : 0;
if (LatestRewindPos == EarliestRewindPos)
{ {
RewindPos = 0; EarliestRewindPos = (EarliestRewindPos != AllocatedRewindStates-1) ? EarliestRewindPos+1 : 0;
} }
if (RewindPos == RewindEarliestPos)
{ RewindTimer = ActualRewindFrames;
RewindEarliestPos++;
if (RewindEarliestPos == RewindStates)
{
RewindEarliestPos = 0;
}
}
RewindTimer = 60*3;
} }
void RestoreCVFrame() void RestoreCVFrame()
{ {
if (RewindPos != RewindEarliestPos)
{
unsigned char *RewindBufferPos; unsigned char *RewindBufferPos;
if (!RewindPos) if (LatestRewindPos != EarliestRewindPos)
{ {
RewindPos = RewindStates; LatestRewindPos = (LatestRewindPos) ? LatestRewindPos-1 : AllocatedRewindStates-1;
} }
RewindPos--;
RewindBufferPos = StateBackup + RewindPos*rewind_state_size; RewindBufferPos = StateBackup + LatestRewindPos*rewind_state_size;
printf("Restoring rewind in slot #%u\n", RewindPos); printf("Restoring rewind in slot #%u\n", LatestRewindPos);
if (MovieProcessing == 1) { zmv_rewind_load(LatestRewindPos, true); }
else if (MovieProcessing == 2) { zmv_rewind_load(LatestRewindPos, false); }
copy_state_data(RewindBufferPos, memcpyrinc, true); copy_state_data(RewindBufferPos, memcpyrinc, true);
//Clear Cache Check //Clear Cache Check
@@ -240,27 +244,7 @@ void RestoreCVFrame()
memset(vidmemch4, 1, sizeof(vidmemch4)); memset(vidmemch4, 1, sizeof(vidmemch4));
memset(vidmemch8, 1, sizeof(vidmemch8)); memset(vidmemch8, 1, sizeof(vidmemch8));
RewindTimer = 60*3; RewindTimer = ActualRewindFrames;
}
}
void MultipleFrameBack(unsigned int i)
{
while (i--)
{
if (RewindPos != RewindEarliestPos)
{
if (!RewindPos)
{
RewindPos = RewindStates;
}
RewindPos--;
}
else
{
break;
}
}
} }
void SetupRewindBuffer() void SetupRewindBuffer()
@@ -272,47 +256,7 @@ void SetupRewindBuffer()
StateBackup = (unsigned char *)malloc(rewind_state_size*RewindStates); StateBackup = (unsigned char *)malloc(rewind_state_size*RewindStates);
if (StateBackup) { break; } if (StateBackup) { break; }
} }
} AllocatedRewindStates = RewindStates;
*/
extern unsigned int CBackupPos, PBackupPos, RewindPos, RewindOldPos;
extern unsigned char RewindFrames, romispal;
extern unsigned char MovieProcessing;
void zmv_rewind_save(size_t, bool);
void zmv_rewind_load(size_t, bool);
#define ActualRewindFrames (RewindFrames * (romispal ? 25 : 30))
void BackupCVFrame()
{
unsigned char *RewindBufferPos = StateBackup + CBackupPos*rewind_state_size;
//printf("Backing up rewind in slot #%u\n", CBackupPos);
copy_state_data(RewindBufferPos, memcpyinc, false);
if (MovieProcessing == 1) { zmv_rewind_save(CBackupPos, true); }
else if (MovieProcessing == 2) { zmv_rewind_save(CBackupPos, false); }
RewindTimer = ActualRewindFrames;
}
void RestoreCVFrame()
{
unsigned char *RewindBufferPos = StateBackup + PBackupPos*rewind_state_size;
//printf("Restoring rewind in slot #%u\n", PBackupPos);
copy_state_data(RewindBufferPos, memcpyrinc, true);
if (MovieProcessing == 1) { zmv_rewind_load(PBackupPos, true); }
else if (MovieProcessing == 2) { zmv_rewind_load(PBackupPos, false); }
RewindTimer = ActualRewindFrames;
}
void SetupRewindBuffer()
{
if (StateBackup){ free(StateBackup); }
RewindStates = 16;
StateBackup = 0;
StateBackup = (unsigned char *)malloc(rewind_state_size*RewindStates);
if (!StateBackup)
{
asm_call(outofmemory);
}
} }
static size_t state_size; static size_t state_size;
@@ -324,18 +268,15 @@ static void state_size_tally(unsigned char **dest, void *src, size_t len)
void InitRewindVars() void InitRewindVars()
{ {
#ifndef __MSDOS__ //When all the code is ported to C, we can make this work with DOS too
unsigned char almost_useless_array[1]; //An array is needed for copy_state_data to give the correct size unsigned char almost_useless_array[1]; //An array is needed for copy_state_data to give the correct size
state_size = 0; state_size = 0;
copy_state_data(almost_useless_array, state_size_tally, false); copy_state_data(almost_useless_array, state_size_tally, false);
rewind_state_size = state_size; rewind_state_size = state_size;
SetupRewindBuffer(); SetupRewindBuffer();
RewindPos = 0; LatestRewindPos = 0;
RewindOldPos = 0; EarliestRewindPos = 0;
//RewindEarliestPos = 0; RewindTimer = 1;
RewindTimer = ActualRewindFrames;
#endif
} }
//This is used to preserve system load state between loads //This is used to preserve system load state between loads