From 50fb6ade910b61cd7b791ccdee53c6b5e86d7387 Mon Sep 17 00:00:00 2001 From: RD42 <42702181+dashr9230@users.noreply.github.com> Date: Thu, 11 Apr 2024 22:50:27 +0800 Subject: [PATCH] [server] Implement few CGameMode member functions --- server/gamemodes.cpp | 135 +++++++++++++++++++++++++++++++++++++++++-- server/gamemodes.h | 21 +++++-- 2 files changed, 146 insertions(+), 10 deletions(-) diff --git a/server/gamemodes.cpp b/server/gamemodes.cpp index 3c5b9bf..fd815bd 100644 --- a/server/gamemodes.cpp +++ b/server/gamemodes.cpp @@ -1,24 +1,149 @@ #include "main.h" +#define CHECK_INIT() { if (!m_bInitialised) return 0; }; + +extern "C" int amx_CoreInit(AMX* amx); +extern "C" int amx_CoreCleanup(AMX* amx); +extern "C" int amx_FloatInit(AMX* amx); +extern "C" int amx_FloatCleanup(AMX* amx); +extern "C" int amx_StringInit(AMX* amx); +extern "C" int amx_StringCleanup(AMX* amx); +extern "C" int amx_FileInit(AMX* amx); +extern "C" int amx_FileCleanup(AMX* amx); +extern "C" int amx_TimeInit(AMX* amx); +extern "C" int amx_TimeCleanup(AMX* amx); + +int AMXAPI aux_LoadProgram(AMX* amx, char* filename); +int AMXAPI aux_FreeProgram(AMX *amx); +void AMXPrintError(CGameMode* pGameMode, AMX *amx, int error); +int amx_CustomInit(AMX *amx); +int amx_sampDbInit(AMX *amx); +int amx_sampDbCleanup(AMX *amx); + +char szGameModeFileName[256]; + +extern CNetGame* pNetGame; + +//---------------------------------------------------------------------------------- + CGameMode::CGameMode() { - field_68 = 0; - field_69 = 0; + m_bInitialised = false; + m_bSleeping = false; } +//---------------------------------------------------------------------------------- + CGameMode::~CGameMode() { Unload(); } +//---------------------------------------------------------------------------------- + bool CGameMode::Load(char* pFileName) { - // TODO: CGameMode::Load W .text:0046F560 L .text:080A4E90 - return false; + if (m_bInitialised) + Unload(); + + FILE* f = fopen(pFileName, "rb"); + if (!f) return false; + fclose(f); + + memset((void*)&m_amx, 0, sizeof(AMX)); + m_fSleepTime = 0.0f; + strcpy(szGameModeFileName, pFileName); + + int err = aux_LoadProgram(&m_amx, szGameModeFileName); + if (err != AMX_ERR_NONE) + { + AMXPrintError(this, &m_amx, err); + logprintf("Failed to load '%s' script.", szGameModeFileName); + return false; + } + + amx_CoreInit(&m_amx); + amx_FloatInit(&m_amx); + amx_StringInit(&m_amx); + amx_FileInit(&m_amx); + amx_TimeInit(&m_amx); + amx_CustomInit(&m_amx); + amx_sampDbInit(&m_amx); + + m_bInitialised = true; + + // Execute OnGameModeInit callback, if it exists! + int tmp; + if (!amx_FindPublic(&m_amx, "OnGameModeInit", &tmp)) + amx_Exec(&m_amx, (cell*)&tmp, tmp); + pNetGame->GetFilterScripts()->OnGameModeInit(); + // ---------------------------------------------- + + // Call in filterscripts + pNetGame->GetFilterScripts()->OnGameModeInit(); + + cell ret = 0; + err = amx_Exec(&m_amx, &ret, AMX_EXEC_MAIN); + if (err == AMX_ERR_SLEEP) + { + m_bSleeping = true; + m_fSleepTime = ((float)ret / 1000.0f); + } + else if (err != AMX_ERR_NONE) + { + m_bSleeping = false; + AMXPrintError(this, &m_amx, err); + } + + return true; } +//---------------------------------------------------------------------------------- + void CGameMode::Unload() { - // TODO: CGameMode::Unload() W .text:0046D7B0 L .text:080A4DB0 + // Execute OnGameModeExit callback, if it exists! + int tmp; + if (!amx_FindPublic(&m_amx, "OnGameModeExit", &tmp)) + amx_Exec(&m_amx, (cell*)&tmp, tmp); + // ---------------------------------------------- + + // Call in filterscripts + pNetGame->GetFilterScripts()->OnGameModeExit(); + CScriptTimers* pScriptTimers = pNetGame->GetTimers(); + if(pScriptTimers) pScriptTimers->DeleteForMode(&m_amx); + + if (m_bInitialised) + { + aux_FreeProgram(&m_amx); + amx_sampDbCleanup(&m_amx); + amx_TimeCleanup(&m_amx); + amx_FileCleanup(&m_amx); + amx_StringCleanup(&m_amx); + amx_FloatCleanup(&m_amx); + amx_CoreCleanup(&m_amx); + } + m_bInitialised = false; + m_bSleeping = false; +} + +//---------------------------------------------------------------------------------- + +//---------------------------------------------------------------------------------- + +int CGameMode::CallPublic(char* szFuncName) +{ + CHECK_INIT(); + + int idx; + cell ret = 0; + + if (!amx_FindPublic(&m_amx, szFuncName, &idx)) + amx_Exec(&m_amx, &ret, idx); + return (int)ret; +} + +//---------------------------------------------------------------------------------- + } diff --git a/server/gamemodes.h b/server/gamemodes.h index 6ac5274..ebfbcc2 100644 --- a/server/gamemodes.h +++ b/server/gamemodes.h @@ -2,20 +2,31 @@ #ifndef SAMPSRV_GAMEMODES_H #define SAMPSRV_GAMEMODES_H -class CGameMode // size: WL 110 +extern char szGameModeFileName[256]; + +//---------------------------------------------------------------------------------- + +class CGameMode { private: - char gap0[104]; - char field_68; - char field_69; - char gap6A[4]; + AMX m_amx; + bool m_bInitialised; + bool m_bSleeping; + float m_fSleepTime; public: CGameMode(); ~CGameMode(); + char* GetFileName() { return &szGameModeFileName[0]; }; + bool Load(char* pFileName); void Unload(); + + int CallPublic(char* szFuncName); + }; +//---------------------------------------------------------------------------------- + #endif