diff -r 4b3d32330007 -r cf8bdfcf6503 core/sourcemod.cpp --- a/core/sourcemod.cpp Wed Aug 21 10:55:12 2013 -0400 +++ b/core/sourcemod.cpp Thu Aug 22 14:05:44 2013 -0700 @@ -129,6 +129,8 @@ return ConfigResult_Ignore; } +static bool sSourceModInitialized = false; + bool SourceModBase::InitializeSourceMod(char *error, size_t maxlength, bool late) { const char *gamepath = g_SMAPI->GetBaseDir(); @@ -240,6 +242,8 @@ g_pSourcePawn2->SetDebugListener(logicore.debugger); + sSourceModInitialized = true; + /* Hook this now so we can detect startup without calling StartSourceMod() */ SH_ADD_HOOK(IServerGameDLL, LevelInit, gamedll, SH_MEMBER(this, &SourceModBase::LevelInit), false); @@ -475,69 +479,74 @@ void SourceModBase::CloseSourceMod() { - /* Force a level end */ - LevelShutdown(); + if (!sSourceModInitialized) + return; + + SH_REMOVE_HOOK(IServerGameDLL, LevelInit, gamedll, SH_MEMBER(this, &SourceModBase::LevelInit), false); + if (g_Loaded) + { + /* Force a level end */ + LevelShutdown(); + ShutdownServices(); + } + + /* Rest In Peace */ + ShutdownLogicBridge(); + ShutdownJIT(); +} + +void SourceModBase::ShutdownServices() +{ /* Unload plugins */ scripts->Shutdown(); /* Unload extensions */ extsys->Shutdown(); - SH_REMOVE_HOOK(IServerGameDLL, LevelInit, gamedll, SH_MEMBER(this, &SourceModBase::LevelInit), false); + if (g_pOnMapEnd) + g_Forwards.ReleaseForward(g_pOnMapEnd); - if (g_Loaded) + /* Notify! */ + SMGlobalClass *pBase = SMGlobalClass::head; + while (pBase) { - if (g_pOnMapEnd) - { - g_Forwards.ReleaseForward(g_pOnMapEnd); - } - - /* Notify! */ - SMGlobalClass *pBase = SMGlobalClass::head; - while (pBase) - { - pBase->OnSourceModShutdown(); - pBase = pBase->m_pGlobalClassNext; - } - - /* Delete all data packs */ - CStack::iterator iter; - CDataPack *pd; - for (iter=m_freepacks.begin(); iter!=m_freepacks.end(); iter++) - { - pd = (*iter); - delete pd; - } - m_freepacks.popall(); - - /* Notify! */ - pBase = SMGlobalClass::head; - while (pBase) - { - pBase->OnSourceModAllShutdown(); - pBase = pBase->m_pGlobalClassNext; - } - - if (enginePatch) - { - SH_RELEASE_CALLCLASS(enginePatch); - enginePatch = NULL; - } - - if (gamedllPatch) - { - SH_RELEASE_CALLCLASS(gamedllPatch); - gamedllPatch = NULL; - } - - SH_REMOVE_HOOK(IServerGameDLL, LevelShutdown, gamedll, SH_MEMBER(this, &SourceModBase::LevelShutdown), false); - SH_REMOVE_HOOK(IServerGameDLL, GameFrame, gamedll, SH_MEMBER(&g_Timers, &TimerSystem::GameFrame), false); + pBase->OnSourceModShutdown(); + pBase = pBase->m_pGlobalClassNext; } - /* Rest In Peace */ - ShutdownLogicBridge(); - ShutdownJIT(); + /* Delete all data packs */ + CStack::iterator iter; + CDataPack *pd; + for (iter=m_freepacks.begin(); iter!=m_freepacks.end(); iter++) + { + pd = (*iter); + delete pd; + } + m_freepacks.popall(); + + /* Notify! */ + pBase = SMGlobalClass::head; + while (pBase) + { + pBase->OnSourceModAllShutdown(); + pBase = pBase->m_pGlobalClassNext; + } + + if (enginePatch) + { + SH_RELEASE_CALLCLASS(enginePatch); + enginePatch = NULL; + } + + if (gamedllPatch) + { + SH_RELEASE_CALLCLASS(gamedllPatch); + gamedllPatch = NULL; + } + + SH_REMOVE_HOOK(IServerGameDLL, LevelShutdown, gamedll, SH_MEMBER(this, &SourceModBase::LevelShutdown), false); + SH_REMOVE_HOOK(IServerGameDLL, GameFrame, gamedll, SH_MEMBER(&g_Timers, &TimerSystem::GameFrame), false); } void SourceModBase::LogMessage(IExtension *pExt, const char *format, ...)