Skip to content

Commit 1f2dc7a

Browse files
committed
Addendum to d2ef262 (Also fix some issues with other CTimer hooks)
1 parent 3c26865 commit 1f2dc7a

File tree

1 file changed

+60
-1
lines changed

1 file changed

+60
-1
lines changed

Client/multiplayer_sa/CMultiplayerSA_Rendering.cpp

Lines changed: 60 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -376,11 +376,68 @@ static void __declspec(naked) HOOK_CTimer_Update()
376376
__asm
377377
{
378378
popad
379-
mov ecx,dword ptr ds:[0B7CB28h]
379+
// Original code: mov ecx, ds:_timerFunction
380+
// GTA has its own NULL check at 0x561B19, so we just execute the original instruction
381+
mov ecx, dword ptr ds:[0B7CB28h]
380382
jmp CONTINUE_CTimer_Update
381383
}
382384
}
383385

386+
//////////////////////////////////////////////////////////////////////////////////////////
387+
//
388+
// CTimer::Suspend / CTimer::Resume
389+
//
390+
// Prevent crashes if _timerFunction is NULL during init
391+
//
392+
//////////////////////////////////////////////////////////////////////////////////////////
393+
#define HOOKPOS_CTimer_Suspend 0x5619E9
394+
#define HOOKSIZE_CTimer_Suspend 6
395+
static const DWORD CONTINUE_CTimer_Suspend = 0x5619EF;
396+
static void _declspec(naked) HOOK_CTimer_Suspend()
397+
{
398+
_asm
399+
{
400+
// Check if _timerFunction is NULL
401+
mov eax, dword ptr ds:[0B7CB28h]
402+
test eax, eax
403+
jz skip_suspend
404+
405+
// Original code: call [_timerFunction]
406+
call eax
407+
jmp CONTINUE_CTimer_Suspend
408+
409+
skip_suspend:
410+
// If NULL, return zero timestamp (EAX:EDX = 0) to avoid corrupting pause time
411+
xor eax, eax
412+
xor edx, edx
413+
jmp CONTINUE_CTimer_Suspend
414+
}
415+
}
416+
417+
#define HOOKPOS_CTimer_Resume 0x561A11
418+
#define HOOKSIZE_CTimer_Resume 6
419+
static const DWORD CONTINUE_CTimer_Resume = 0x561A17;
420+
static void _declspec(naked) HOOK_CTimer_Resume()
421+
{
422+
_asm
423+
{
424+
// Check if _timerFunction is NULL
425+
mov eax, dword ptr ds:[0B7CB28h]
426+
test eax, eax
427+
jz skip_resume
428+
429+
// Original code: call [_timerFunction]
430+
call eax
431+
jmp CONTINUE_CTimer_Resume
432+
433+
skip_resume:
434+
// If NULL, return zero timestamp (EAX:EDX = 0) to avoid corrupting resume time calculations
435+
xor eax, eax
436+
xor edx, edx
437+
jmp CONTINUE_CTimer_Resume
438+
}
439+
}
440+
384441
//////////////////////////////////////////////////////////////////////////////////////////
385442
//
386443
// Photograph screen grab in windowed mode
@@ -788,6 +845,8 @@ void CMultiplayerSA::InitHooks_Rendering()
788845
EZHookInstall(Check_NoOfVisibleEntities);
789846
EZHookInstall(WinLoop);
790847
EZHookInstall(CTimer_Update);
848+
EZHookInstall(CTimer_Suspend);
849+
EZHookInstall(CTimer_Resume);
791850
EZHookInstall(psGrabScreen);
792851
EZHookInstallChecked(CClouds_RenderSkyPolys);
793852
EZHookInstallChecked(RwCameraSetNearClipPlane);

0 commit comments

Comments
 (0)