From e445530bbb1be65b2b4f74a99b3e0a2729456f44 Mon Sep 17 00:00:00 2001 From: Sandu Liviu Catalin Date: Fri, 2 Sep 2016 14:11:39 +0300 Subject: [PATCH] Implement a new module command that is called right before cosing the virtual machine to allow modules to release resources manually. Should fix a possible crash in the IRC plugin which was caused by the Session destructor to be called recursively when cleaned automatically by the VM. --- modules/irc/Module.cpp | 15 +++++++++++++-- modules/irc/Session.cpp | 2 ++ modules/json/Module.cpp | 12 ++++++++++++ modules/mg/Module.cpp | 12 ++++++++++++ modules/mmdb/Module.cpp | 12 ++++++++++++ modules/mysql/Module.cpp | 12 ++++++++++++ modules/sample/Module.cpp | 12 ++++++++++++ modules/sqlite/Module.cpp | 12 ++++++++++++ modules/xml/Module.cpp | 12 ++++++++++++ shared/SqMod.h | 1 + source/Core.cpp | 4 ++++ 11 files changed, 104 insertions(+), 2 deletions(-) diff --git a/modules/irc/Module.cpp b/modules/irc/Module.cpp index 12af3577..145e9d8a 100644 --- a/modules/irc/Module.cpp +++ b/modules/irc/Module.cpp @@ -99,6 +99,15 @@ static void OnSquirrelTerminate() NullFunction().ReleaseGently(); } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Terminate all sessions, if any + SessionTerminate(); +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -106,8 +115,6 @@ static void OnSquirrelReleased() { // Release the current virtual machine, if any DefaultVM::Set(nullptr); - // Terminate all sessions, if any - SessionTerminate(); } /* ------------------------------------------------------------------------------------------------ @@ -141,6 +148,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/irc/Session.cpp b/modules/irc/Session.cpp index 5083d819..6519c766 100644 --- a/modules/irc/Session.cpp +++ b/modules/irc/Session.cpp @@ -202,7 +202,9 @@ void Session::Destroy() { // Make sure there's even a session to release if (!m_Session) + { return; + } // Disconnect the session Disconnect(); // Break the association with this instance (paranoia) diff --git a/modules/json/Module.cpp b/modules/json/Module.cpp index 80dbc718..b75b876e 100644 --- a/modules/json/Module.cpp +++ b/modules/json/Module.cpp @@ -102,6 +102,14 @@ static void OnSquirrelTerminate() NullFunction().ReleaseGently(); } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -142,6 +150,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/mg/Module.cpp b/modules/mg/Module.cpp index bd9aa0c6..1c9fcfd7 100644 --- a/modules/mg/Module.cpp +++ b/modules/mg/Module.cpp @@ -186,6 +186,14 @@ static void OnSquirrelTerminate() // Release script resources... } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -226,6 +234,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/mmdb/Module.cpp b/modules/mmdb/Module.cpp index 5c7a6d51..03b803e6 100644 --- a/modules/mmdb/Module.cpp +++ b/modules/mmdb/Module.cpp @@ -78,6 +78,14 @@ static void OnSquirrelTerminate() // Release script resources... } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -118,6 +126,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/mysql/Module.cpp b/modules/mysql/Module.cpp index 201cc71a..09c22b7e 100644 --- a/modules/mysql/Module.cpp +++ b/modules/mysql/Module.cpp @@ -95,6 +95,14 @@ static void OnSquirrelTerminate() // Release script resources... } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -135,6 +143,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/sample/Module.cpp b/modules/sample/Module.cpp index 9c796f86..1282a288 100644 --- a/modules/sample/Module.cpp +++ b/modules/sample/Module.cpp @@ -89,6 +89,14 @@ static void OnSquirrelTerminate() // Release script resources... } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -129,6 +137,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/sqlite/Module.cpp b/modules/sqlite/Module.cpp index 492e1dd6..5b603264 100644 --- a/modules/sqlite/Module.cpp +++ b/modules/sqlite/Module.cpp @@ -99,6 +99,14 @@ static void OnSquirrelTerminate() // Release script resources... } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -139,6 +147,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/modules/xml/Module.cpp b/modules/xml/Module.cpp index 27ea09e7..c85ba3c6 100644 --- a/modules/xml/Module.cpp +++ b/modules/xml/Module.cpp @@ -377,6 +377,14 @@ static void OnSquirrelTerminate() // Release script resources... } +/* ------------------------------------------------------------------------------------------------ + * The virtual machined is about to be closed. Last chance to release anything manually. +*/ +static void OnSquirrelClosing() +{ + // Nothing to release manually... +} + /* ------------------------------------------------------------------------------------------------ * The virtual machined was closed and all memory associated with it was released. */ @@ -417,6 +425,10 @@ static uint8_t OnPluginCommand(uint32_t command_identifier, CCStr message) { OnSquirrelTerminate(); } break; + case SQMOD_CLOSING_CMD: + { + OnSquirrelClosing(); + } break; case SQMOD_RELEASED_CMD: { OnSquirrelReleased(); diff --git a/shared/SqMod.h b/shared/SqMod.h index ac3ceccf..e0186b08 100644 --- a/shared/SqMod.h +++ b/shared/SqMod.h @@ -58,6 +58,7 @@ extern "C" { #define SQMOD_INITIALIZE_CMD 0xDABBAD00 #define SQMOD_LOAD_CMD 0xDEADBABE #define SQMOD_TERMINATE_CMD 0xDEADC0DE + #define SQMOD_CLOSING_CMD 0xBAAAAAAD #define SQMOD_RELEASED_CMD 0xDEADBEAF #define SQMOD_API_VER 1 diff --git a/source/Core.cpp b/source/Core.cpp index b6207419..e35b3194 100644 --- a/source/Core.cpp +++ b/source/Core.cpp @@ -513,6 +513,10 @@ void Core::Terminate(bool shutdown) // Assertions during close may cause double delete/close! HSQUIRRELVM sq_vm = m_VM; m_VM = nullptr; + + cLogDbg(m_Verbosity >= 1, "Signaling outside plug-ins the virtual machine is closing"); + // Tell modules to do their monkey business + _Func->SendPluginCommand(SQMOD_CLOSING_CMD, ""); // Attempt to close the VM sq_close(sq_vm);