diff --git a/core/ConVarManager.cpp b/core/ConVarManager.cpp index 4282a971..5e9a5ff4 100644 --- a/core/ConVarManager.cpp +++ b/core/ConVarManager.cpp @@ -37,6 +37,7 @@ #include "sm_srvcmds.h" #include "sm_stringutil.h" #include +#include ConVarManager g_ConVarManager; @@ -45,31 +46,14 @@ SH_DECL_HOOK5_void(IServerPluginCallbacks, OnQueryCvarValueFinished, SH_NOATTRIB const ParamType CONVARCHANGE_PARAMS[] = {Param_Cell, Param_String, Param_String}; typedef List ConVarList; +KTrie convar_cache; ConVarManager::ConVarManager() : m_ConVarType(0), m_bIsDLLQueryHooked(false), m_bIsVSPQueryHooked(false) { -#if PLAPI_VERSION < 12 - m_IgnoreHandle = false; -#endif - - /* Create a convar lookup trie */ - m_ConVarCache = sm_trie_create(); } ConVarManager::~ConVarManager() { - List::iterator iter; - - /* Destroy our convar lookup trie */ - sm_trie_destroy(m_ConVarCache); - - /* Destroy all the ConVarInfo structures */ - for (iter = m_ConVars.begin(); iter != m_ConVars.end(); iter++) - { - delete (*iter); - } - - m_ConVars.clear(); } void ConVarManager::OnSourceModAllInitialized() @@ -101,6 +85,48 @@ void ConVarManager::OnSourceModAllInitialized() void ConVarManager::OnSourceModShutdown() { + List::iterator iter = m_ConVars.begin(); + HandleSecurity sec(NULL, g_pCoreIdent); + + /* Iterate list of ConVarInfo structures, remove every one of them */ + while (iter != m_ConVars.end()) + { + ConVarInfo *pInfo = (*iter); + + iter = m_ConVars.erase(iter); + + g_HandleSys.FreeHandle(pInfo->handle, &sec); + if (pInfo->pChangeForward != NULL) + { + g_Forwards.ReleaseForward(pInfo->pChangeForward); + } + if (pInfo->sourceMod) + { + /* If we created it, we won't be tracking it, therefore it is + * safe to remove everything in one go. + */ + META_UNREGCVAR(pInfo->pVar); + delete [] pInfo->pVar->GetName(); + delete [] pInfo->pVar->GetHelpText(); + delete [] pInfo->pVar->GetDefault(); + delete pInfo->pVar; + } + else + { + /* If we didn't create it, we might be tracking it. Also, + * it could be unreadable. + */ + UntrackConCommandBase(pInfo->pVar, this); + } + + /* It's not safe to read the name here, so we simply delete the + * the info struct and clear the lookup cache at the end. + */ + delete pInfo; + } + convar_cache.clear(); + + /* Unhook things */ if (m_bIsDLLQueryHooked) { SH_REMOVE_HOOK_MEMFUNC(IServerGameDLL, OnQueryCvarValueFinished, gamedll, this, &ConVarManager::OnQueryCvarValueFinished, false); @@ -112,21 +138,6 @@ void ConVarManager::OnSourceModShutdown() m_bIsVSPQueryHooked = false; } - IChangeableForward *fwd; - List::iterator i; - - /* Iterate list of ConVarInfo structures */ - for (i = m_ConVars.begin(); i != m_ConVars.end(); i++) - { - fwd = (*i)->pChangeForward; - - /* Free any convar-change forwards that still exist */ - if (fwd) - { - g_Forwards.ReleaseForward(fwd); - } - } - /* Remove the 'convars' option from the 'sm' console command */ g_RootMenu.RemoveRootConsoleCommand("cvars", this); @@ -165,54 +176,55 @@ void ConVarManager::OnSourceModVSPReceived() m_bIsVSPQueryHooked = true; } -#if PLAPI_VERSION >= 12 -void ConVarManager::OnUnlinkConCommandBase(PluginId id, ConCommandBase *pCommand) +bool convar_cache_lookup(const char *name, ConVarInfo **pVar) +{ + ConVarInfo **pLookup = convar_cache.retrieve(name); + if (pLookup != NULL) + { + *pVar = *pLookup; + return true; + } + else + { + return false; + } +} + +void ConVarManager::OnUnlinkConCommandBase(ConCommandBase *pBase, const char *name, bool is_read_safe) { /* Only check convars that have not been created by SourceMod's core */ - if (id != g_PLID && !pCommand->IsCommand()) - { - ConVarInfo *pInfo; - const char *cvarName = pCommand->GetName(); - HandleSecurity sec(NULL, g_pCoreIdent); - bool handleExists = sm_trie_retrieve(m_ConVarCache, cvarName, reinterpret_cast(&pInfo)); - - if (handleExists) - { - g_HandleSys.FreeHandle(pInfo->handle, &sec); - sm_trie_delete(m_ConVarCache, cvarName); - m_ConVars.remove(pInfo); - } - } -} - -#else - -/* I truly detest this code */ -void ConVarManager::OnMetamodPluginUnloaded(PluginId id) -{ ConVarInfo *pInfo; - const char *cvarName; + if (!convar_cache_lookup(name, &pInfo)) + { + return; + } + HandleSecurity sec(NULL, g_pCoreIdent); - List::iterator i; - for (i = m_ConVars.begin(); i != m_ConVars.end(); i++) + /* Remove it from our cache */ + m_ConVars.remove(pInfo); + convar_cache.remove(name); + + /* Now make sure no plugins are referring to this pointer */ + IPluginIterator *pl_iter = g_PluginSys.GetPluginIterator(); + while (pl_iter->MorePlugins()) { - pInfo = (*i); - cvarName = pInfo->name; + IPlugin *pl = pl_iter->GetPlugin(); - if (cvarName && !icvar->FindVar(cvarName)) + ConVarList *pConVarList; + if (pl->GetProperty("ConVarList", (void **)&pConVarList, true) + && pConVarList != NULL) { - m_IgnoreHandle = true; - g_HandleSys.FreeHandle(pInfo->handle, &sec); - - sm_trie_delete(m_ConVarCache, cvarName); - m_ConVars.erase(i); - - delete [] cvarName; + pConVarList->remove(pInfo->pVar); } + + pl_iter->NextPlugin(); } + + /* Free resources */ + g_HandleSys.FreeHandle(pInfo->handle, &sec); + delete pInfo; } -#endif void ConVarManager::OnPluginUnloaded(IPlugin *plugin) { @@ -227,33 +239,6 @@ void ConVarManager::OnPluginUnloaded(IPlugin *plugin) void ConVarManager::OnHandleDestroy(HandleType_t type, void *object) { -#if PLAPI_VERSION < 12 - /* Lovely workaround for our workaround! */ - if (m_IgnoreHandle) - { - m_IgnoreHandle = false; - return; - } -#endif - - ConVarInfo *info; - ConVar *pConVar = static_cast(object); - - /* Find convar in lookup trie */ - sm_trie_retrieve(m_ConVarCache, pConVar->GetName(), reinterpret_cast(&info)); - - /* If convar was created by SourceMod plugin... */ - if (info->sourceMod) - { - /* Then unlink it from SourceMM */ - g_SMAPI->UnregisterConCommandBase(g_PLAPI, pConVar); - - /* Delete string allocations */ - delete [] pConVar->GetName(); - delete [] pConVar->GetDefault(); - delete [] pConVar->GetHelpText(); - delete pConVar; - } } void ConVarManager::OnRootConsoleCommand(const char *cmdname, const CCommand &command) @@ -320,28 +305,33 @@ Handle_t ConVarManager::CreateConVar(IPluginContext *pContext, const char *name, AddConVarToPluginList(pContext, pConVar); /* First find out if we already have a handle to it */ - if (sm_trie_retrieve(m_ConVarCache, name, (void **)&pInfo)) + if (convar_cache_lookup(name, &pInfo)) { return pInfo->handle; } else { - /* If we don't, then create a new handle from the convar */ - hndl = g_HandleSys.CreateHandle(m_ConVarType, pConVar, NULL, g_pCoreIdent, NULL); - /* Create and initialize ConVarInfo structure */ pInfo = new ConVarInfo(); - pInfo->handle = hndl; pInfo->sourceMod = false; pInfo->pChangeForward = NULL; pInfo->origCallback = pConVar->GetCallback(); - #if PLAPI_VERSION < 12 - pInfo->name = sm_strdup(pConVar->GetName()); - #endif + pInfo->pVar = pConVar; + + /* If we don't, then create a new handle from the convar */ + hndl = g_HandleSys.CreateHandle(m_ConVarType, pInfo, NULL, g_pCoreIdent, NULL); + if (hndl == BAD_HANDLE) + { + delete pInfo; + return BAD_HANDLE; + } + + pInfo->handle = hndl; /* Insert struct into caches */ m_ConVars.push_back(pInfo); - sm_trie_insert(m_ConVarCache, name, pInfo); + convar_cache.insert(name, pInfo); + TrackConCommandBase(pConVar, this); return hndl; } @@ -360,28 +350,33 @@ Handle_t ConVarManager::CreateConVar(IPluginContext *pContext, const char *name, pBase = const_cast(pBase->GetNext()); } - /* Since an existing convar (or concmd with the same name) was not found , now we can finally create it */ - pConVar = new ConVar(sm_strdup(name), sm_strdup(defaultVal), flags, sm_strdup(description), hasMin, min, hasMax, max); - - /* Add convar to plugin's list */ - AddConVarToPluginList(pContext, pConVar); - - /* Create a handle from the new convar */ - hndl = g_HandleSys.CreateHandle(m_ConVarType, pConVar, NULL, g_pCoreIdent, NULL); - /* Create and initialize ConVarInfo structure */ pInfo = new ConVarInfo(); pInfo->handle = hndl; pInfo->sourceMod = true; pInfo->pChangeForward = NULL; pInfo->origCallback = NULL; -#if PLAPI_VERSION < 12 - pInfo->name = NULL; -#endif + + /* Create a handle from the new convar */ + hndl = g_HandleSys.CreateHandle(m_ConVarType, pInfo, NULL, g_pCoreIdent, NULL); + if (hndl == BAD_HANDLE) + { + delete pInfo; + return BAD_HANDLE; + } + + pInfo->handle = hndl; + + /* Since an existing convar (or concmd with the same name) was not found , now we can finally create it */ + pConVar = new ConVar(sm_strdup(name), sm_strdup(defaultVal), flags, sm_strdup(description), hasMin, min, hasMax, max); + pInfo->pVar = pConVar; + + /* Add convar to plugin's list */ + AddConVarToPluginList(pContext, pConVar); /* Insert struct into caches */ m_ConVars.push_back(pInfo); - sm_trie_insert(m_ConVarCache, name, pInfo); + convar_cache.insert(name, pInfo); return hndl; } @@ -402,27 +397,32 @@ Handle_t ConVarManager::FindConVar(const char *name) } /* At this point, the convar exists. So, find out if we already have a handle */ - if (sm_trie_retrieve(m_ConVarCache, name, (void **)&pInfo)) + if (convar_cache_lookup(name, &pInfo)) { return pInfo->handle; } - /* If we don't have a handle, then create a new one */ - hndl = g_HandleSys.CreateHandle(m_ConVarType, pConVar, NULL, g_pCoreIdent, NULL); - /* Create and initialize ConVarInfo structure */ pInfo = new ConVarInfo(); - pInfo->handle = hndl; pInfo->sourceMod = false; pInfo->pChangeForward = NULL; pInfo->origCallback = pConVar->GetCallback(); -#if PLAPI_VERSION < 12 - pInfo->name = sm_strdup(pConVar->GetName()); -#endif + pInfo->pVar = pConVar; + + /* If we don't have a handle, then create a new one */ + hndl = g_HandleSys.CreateHandle(m_ConVarType, pInfo, NULL, g_pCoreIdent, NULL); + if (hndl == BAD_HANDLE) + { + delete pInfo; + return BAD_HANDLE; + } + + pInfo->handle = hndl; /* Insert struct into our caches */ m_ConVars.push_back(pInfo); - sm_trie_insert(m_ConVarCache, name, pInfo); + convar_cache.insert(name, pInfo); + TrackConCommandBase(pConVar, this); return hndl; } @@ -433,7 +433,7 @@ void ConVarManager::HookConVarChange(ConVar *pConVar, IPluginFunction *pFunction IChangeableForward *pForward; /* Find the convar in the lookup trie */ - if (sm_trie_retrieve(m_ConVarCache, pConVar->GetName(), (void **)&pInfo)) + if (convar_cache_lookup(pConVar->GetName(), &pInfo)) { /* Get the forward */ pForward = pInfo->pChangeForward; @@ -460,7 +460,7 @@ void ConVarManager::UnhookConVarChange(ConVar *pConVar, IPluginFunction *pFuncti IPluginContext *pContext = pFunction->GetParentContext(); /* Find the convar in the lookup trie */ - if (sm_trie_retrieve(m_ConVarCache, pConVar->GetName(), (void **)&pInfo)) + if (convar_cache_lookup(pConVar->GetName(), &pInfo)) { /* Get the forward */ pForward = pInfo->pChangeForward; @@ -569,11 +569,13 @@ void ConVarManager::OnConVarChanged(ConVar *pConVar, const char *oldValue) return; } - Trie *pCache = g_ConVarManager.GetConVarCache(); ConVarInfo *pInfo; /* Find the convar in the lookup trie */ - sm_trie_retrieve(pCache, pConVar->GetName(), (void **)&pInfo); + if (!convar_cache_lookup(pConVar->GetName(), &pInfo)) + { + return; + } FnChangeCallback_t origCallback = pInfo->origCallback; IChangeableForward *pForward = pInfo->pChangeForward; @@ -642,6 +644,23 @@ void ConVarManager::OnQueryCvarValueFinished(QueryCvarCookie_t cookie, edict_t * } } +HandleError ConVarManager::ReadConVarHandle(Handle_t hndl, ConVar **pVar) +{ + ConVarInfo *pInfo; + HandleError error; + + if ((error = g_HandleSys.ReadHandle(hndl, m_ConVarType, NULL, (void **)&pInfo)) != HandleError_None) + { + return error; + } + + if (pVar) + { + *pVar = pInfo->pVar; + } + + return error; +} static int s_YamagramState = 0; diff --git a/core/ConVarManager.h b/core/ConVarManager.h index 61cb360a..d9cfea24 100644 --- a/core/ConVarManager.h +++ b/core/ConVarManager.h @@ -34,13 +34,13 @@ #include "sm_globals.h" #include "sourcemm_api.h" -#include "sm_trie.h" #include #include #include #include #include #include +#include "concmd_cleaner.h" using namespace SourceHook; @@ -49,13 +49,11 @@ using namespace SourceHook; */ struct ConVarInfo { - Handle_t handle; /**< Handle to convar */ + Handle_t handle; /**< Handle to self */ bool sourceMod; /**< Determines whether or not convar was created by a SourceMod plugin */ IChangeableForward *pChangeForward; /**< Forward associated with convar */ FnChangeCallback_t origCallback; /**< The original callback function */ -#if PLAPI_VERSION < 12 - const char *name; /**< Name of convar */ -#endif + ConVar *pVar; /**< The actual convar */ }; /** @@ -72,7 +70,8 @@ class ConVarManager : public SMGlobalClass, public IHandleTypeDispatch, public IPluginsListener, - public IRootConsoleCommand + public IRootConsoleCommand, + public IConCommandTracker { public: ConVarManager(); @@ -87,22 +86,8 @@ public: // IPluginsListener void OnPluginUnloaded(IPlugin *plugin); public: //IRootConsoleCommand void OnRootConsoleCommand(const char *cmdname, const CCommand &command); -public: - /** - * Get the 'ConVar' handle type ID. - */ - inline HandleType_t GetHandleType() - { - return m_ConVarType; - } - - /** - * Get the convar lookup trie. - */ - inline Trie *GetConVarCache() - { - return m_ConVarCache; - } +public: //IConCommandTracker + void OnUnlinkConCommandBase(ConCommandBase *pBase, const char *name, bool is_read_safe); public: /** * Create a convar and return a handle to it. @@ -133,17 +118,8 @@ public: bool IsQueryingSupported(); -#if PLAPI_VERSION >= 12 - /** - * Called when Metamod:Source is about to remove convar - */ - void OnUnlinkConCommandBase(PluginId id, ConCommandBase *pCommand); -#else - /** - * Called when Metamod:Source has unloaded a plugin - */ - void OnMetamodPluginUnloaded(PluginId id); -#endif + HandleError ReadConVarHandle(Handle_t hndl, ConVar **pVar); + private: /** * Adds a convar to a plugin's list. @@ -168,12 +144,8 @@ private: HandleType_t m_ConVarType; List m_ConVars; List m_ConVarQueries; - Trie *m_ConVarCache; bool m_bIsDLLQueryHooked; bool m_bIsVSPQueryHooked; -#if PLAPI_VERSION < 12 - bool m_IgnoreHandle; -#endif }; extern ConVarManager g_ConVarManager; diff --git a/core/concmd_cleaner.cpp b/core/concmd_cleaner.cpp new file mode 100644 index 00000000..da3ce6a0 --- /dev/null +++ b/core/concmd_cleaner.cpp @@ -0,0 +1,175 @@ +/** + * vim: set ts=4 : + * ============================================================================= + * SourceMod + * Copyright (C) 2004-2007 AlliedModders LLC. All rights reserved. + * ============================================================================= + * + * This program is free software; you can redistribute it and/or modify it under + * the terms of the GNU General Public License, version 3.0, as published by the + * Free Software Foundation. + * + * This program 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 General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see . + * + * As a special exception, AlliedModders LLC gives you permission to link the + * code of this program (as well as its derivative works) to "Half-Life 2," the + * "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software + * by the Valve Corporation. You must obey the GNU General Public License in + * all respects for all other code used. Additionally, AlliedModders LLC grants + * this exception to all derivative works. AlliedModders LLC defines further + * exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007), + * or . + * + * Version: $Id$ + */ + +#include "sm_globals.h" +#include +#include +#include "concmd_cleaner.h" +#include "sm_stringutil.h" +#include "sourcemm_api.h" + +#if defined ORANGEBOX_BUILD +SH_DECL_HOOK1_void(ICvar, UnregisterConCommand, SH_NOATTRIB, 0, ConCommandBase *); +#endif + +using namespace SourceHook; + +struct ConCommandInfo +{ + ConCommandBase *pBase; + IConCommandTracker *cls; + char name[64]; +}; + +List tracked_bases; + +ConCommandBase *FindConCommandBase(const char *name); + +class ConCommandCleaner : public SMGlobalClass +{ +public: +#if defined ORANGEBOX_BUILD + void OnSourceModAllInitialized() + { + SH_ADD_HOOK(ICvar, UnregisterConCommand, SH_NOATTRIB, SH_MEMBER(this, &ConCommandCleaner::UnlinkConCommandBase), false); + } + + void OnSourceModShutdown() + { + SH_REMOVE_HOOK(ICvar, UnregisterConCommand, SH_NOATTRIB, SH_MEMBER(this, &ConCommandCleaner::UnlinkConCommandBase), false); + } +#endif + + void UnlinkConCommandBase(ConCommandBase *pBase) + { + ConCommandInfo *pInfo; + List::iterator iter = tracked_bases.begin(); + + if (pBase) + { + while (iter != tracked_bases.end()) + { + if ((*iter)->pBase == pBase) + { + pInfo = (*iter); + iter = tracked_bases.erase(iter); + pInfo->cls->OnUnlinkConCommandBase(pBase, pBase->GetName(), true); + delete pInfo; + } + else + { + iter++; + } + } + } + else + { + while (iter != tracked_bases.end()) + { + /* This is just god-awful! */ + if (FindConCommandBase((*iter)->name) != (*iter)->pBase) + { + pInfo = (*iter); + iter = tracked_bases.erase(iter); + pInfo->cls->OnUnlinkConCommandBase(pBase, pBase->GetName(), true); + delete pInfo; + } + else + { + iter++; + } + } + } + } + + void AddTarget(ConCommandBase *pBase, IConCommandTracker *cls) + { + ConCommandInfo *info = new ConCommandInfo; + + info->pBase = pBase; + info->cls = cls; + strncopy(info->name, pBase->GetName(), sizeof(info->name)); + + tracked_bases.push_back(info); + } + + void RemoveTarget(ConCommandBase *pBase, IConCommandTracker *cls) + { + List::iterator iter; + ConCommandInfo *pInfo; + + iter = tracked_bases.begin(); + while (iter != tracked_bases.end()) + { + pInfo = (*iter); + if (pInfo->pBase == pBase && pInfo->cls == cls) + { + delete pInfo; + iter = tracked_bases.erase(iter); + } + else + { + iter++; + } + } + } +} s_ConCmdTracker; + +ConCommandBase *FindConCommandBase(const char *name) +{ + const ConCommandBase *pBase = icvar->GetCommands(); + + while (pBase != NULL) + { + if (strcmp(pBase->GetName(), name) == 0) + { + return const_cast(pBase); + } + pBase = pBase->GetNext(); + } + + return NULL; +} + +void TrackConCommandBase(ConCommandBase *pBase, IConCommandTracker *me) +{ + s_ConCmdTracker.AddTarget(pBase, me); +} + +void UntrackConCommandBase(ConCommandBase *pBase, IConCommandTracker *me) +{ + s_ConCmdTracker.RemoveTarget(pBase, me); +} + +void Global_OnUnlinkConCommandBase(ConCommandBase *pBase) +{ + s_ConCmdTracker.UnlinkConCommandBase(pBase); +} diff --git a/core/concmd_cleaner.h b/core/concmd_cleaner.h new file mode 100644 index 00000000..e7e46ede --- /dev/null +++ b/core/concmd_cleaner.h @@ -0,0 +1,41 @@ +/** + * vim: set ts=4 : + * ============================================================================= + * SourceMod + * Copyright (C) 2004-2007 AlliedModders LLC. All rights reserved. + * ============================================================================= + * + * This program is free software; you can redistribute it and/or modify it under + * the terms of the GNU General Public License, version 3.0, as published by the + * Free Software Foundation. + * + * This program 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 General Public License for more + * details. + * + * You should have received a copy of the GNU General Public License along with + * this program. If not, see . + * + * As a special exception, AlliedModders LLC gives you permission to link the + * code of this program (as well as its derivative works) to "Half-Life 2," the + * "Source Engine," the "SourcePawn JIT," and any Game MODs that run on software + * by the Valve Corporation. You must obey the GNU General Public License in + * all respects for all other code used. Additionally, AlliedModders LLC grants + * this exception to all derivative works. AlliedModders LLC defines further + * exceptions, found in LICENSE.txt (as of this writing, version JULY-31-2007), + * or . + * + * Version: $Id$ + */ + +class IConCommandTracker +{ +public: + virtual void OnUnlinkConCommandBase(ConCommandBase *pBase, const char *name, bool is_read_safe) = 0; +}; + +void TrackConCommandBase(ConCommandBase *pBase, IConCommandTracker *me); +void UntrackConCommandBase(ConCommandBase *pBase, IConCommandTracker *me); +void Global_OnUnlinkConCommandBase(ConCommandBase *pBase); + diff --git a/core/msvc8/sourcemod_mm.vcproj b/core/msvc8/sourcemod_mm.vcproj index 3f63ef4b..2d01ff19 100644 --- a/core/msvc8/sourcemod_mm.vcproj +++ b/core/msvc8/sourcemod_mm.vcproj @@ -609,6 +609,10 @@ RelativePath="..\ChatTriggers.cpp" > + + @@ -803,6 +807,10 @@ RelativePath="..\..\public\compat_wrappers.h" > + + diff --git a/core/smn_console.cpp b/core/smn_console.cpp index b18d376c..921639f2 100644 --- a/core/smn_console.cpp +++ b/core/smn_console.cpp @@ -110,7 +110,9 @@ static void NotifyConVar(ConVar *pConVar) if (IsFlagSet(pConVar, FCVAR_PROTECTED)) { pEvent->SetString("cvarvalue", "***PROTECTED***"); - } else { + } + else + { pEvent->SetString("cvarvalue", pConVar->GetString()); } @@ -141,7 +143,7 @@ static cell_t sm_CreateConVar(IPluginContext *pContext, const cell_t *params) if (hndl == BAD_HANDLE) { - return pContext->ThrowNativeError("Convar \"%s\" was not created. A console command with the same name already exists.", name); + return pContext->ThrowNativeError("Convar \"%s\" was not created. A console command with the same might already exist.", name); } return hndl; @@ -162,7 +164,7 @@ static cell_t sm_HookConVarChange(IPluginContext *pContext, const cell_t *params HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -186,7 +188,7 @@ static cell_t sm_UnhookConVarChange(IPluginContext *pContext, const cell_t *para HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -210,7 +212,7 @@ static cell_t sm_GetConVarBool(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -225,7 +227,7 @@ static cell_t sm_GetConVarInt(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -241,7 +243,7 @@ static cell_t sm_SetConVarNum(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -270,7 +272,7 @@ static cell_t sm_GetConVarFloat(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -287,7 +289,7 @@ static cell_t sm_SetConVarFloat(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -317,7 +319,7 @@ static cell_t sm_GetConVarString(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -334,7 +336,7 @@ static cell_t sm_SetConVarString(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -366,7 +368,7 @@ static cell_t sm_ResetConVar(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -395,7 +397,7 @@ static cell_t sm_GetConVarFlags(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -410,7 +412,7 @@ static cell_t sm_SetConVarFlags(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -427,7 +429,7 @@ static cell_t sm_GetConVarBounds(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -461,7 +463,7 @@ static cell_t sm_SetConVarBounds(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); @@ -488,7 +490,7 @@ static cell_t sm_GetConVarName(IPluginContext *pContext, const cell_t *params) HandleError err; ConVar *pConVar; - if ((err=g_HandleSys.ReadHandle(hndl, g_ConVarManager.GetHandleType(), NULL, (void **)&pConVar)) + if ((err=g_ConVarManager.ReadConVarHandle(hndl, &pConVar)) != HandleError_None) { return pContext->ThrowNativeError("Invalid convar handle %x (error %d)", hndl, err); diff --git a/core/sourcemm_api.cpp b/core/sourcemm_api.cpp index c9504b44..bfc4504d 100644 --- a/core/sourcemm_api.cpp +++ b/core/sourcemm_api.cpp @@ -33,7 +33,7 @@ #include "sourcemm_api.h" #include "sm_version.h" #include "Logger.h" -#include "ConVarManager.h" +#include "concmd_cleaner.h" SourceMod_Core g_SourceMod_Core; IVEngineServer *engine = NULL; @@ -203,14 +203,18 @@ void SourceMod_Core::OnVSPListening(IServerPluginCallbacks *iface) } } -#if PLAPI_VERSION >= 12 +#if defined METAMOD_PLAPI_VERSION + void SourceMod_Core::OnUnlinkConCommandBase(PluginId id, ConCommandBase *pCommand) { - g_ConVarManager.OnUnlinkConCommandBase(id, pCommand); + Global_OnUnlinkConCommandBase(pCommand); } + #else + void SourceMod_Core::OnPluginUnload(PluginId id) { - g_ConVarManager.OnMetamodPluginUnloaded(id); + Global_OnUnlinkConCommandBase(NULL); } + #endif diff --git a/core/sourcemm_api.h b/core/sourcemm_api.h index 0b27fe88..7fba5258 100644 --- a/core/sourcemm_api.h +++ b/core/sourcemm_api.h @@ -74,7 +74,7 @@ public: const char *GetLogTag(); public: void OnVSPListening(IServerPluginCallbacks *iface); -#if PLAPI_VERSION >= 12 +#if defined METAMOD_PLAPI_VERSION void OnUnlinkConCommandBase(PluginId id, ConCommandBase *pCommand); #else void OnPluginUnload(PluginId id);