summaryrefslogtreecommitdiff
path: root/include
diff options
context:
space:
mode:
authorAttila Molnar <attilamolnar@hush.com>2015-12-01 12:23:50 +0100
committerAttila Molnar <attilamolnar@hush.com>2015-12-01 12:23:50 +0100
commit44b5a8fa89d8c2bda767c0d5fe77c4d31061ce2b (patch)
tree0f1b3d375efd8584858e7df906de6bc322f4b5c6 /include
parent0a12e928e61cdb5366f0ad8ffb9d912eb14c5878 (diff)
parent19cc9292ab5889fa09962820f3179e8078bec956 (diff)
Merge branch 'master+reloadmod'
Diffstat (limited to 'include')
-rw-r--r--include/extensible.h13
-rw-r--r--include/modules.h16
-rw-r--r--include/modules/reload.h80
3 files changed, 99 insertions, 10 deletions
diff --git a/include/extensible.h b/include/extensible.h
index a2c104377..5ac4fa9da 100644
--- a/include/extensible.h
+++ b/include/extensible.h
@@ -121,11 +121,20 @@ class CoreExport Extensible : public classbase
class CoreExport ExtensionManager
{
- std::map<std::string, reference<ExtensionItem> > types;
public:
+ typedef std::map<std::string, reference<ExtensionItem> > ExtMap;
+
bool Register(ExtensionItem* item);
void BeginUnregister(Module* module, std::vector<reference<ExtensionItem> >& list);
ExtensionItem* GetItem(const std::string& name);
+
+ /** Get all registered extensions keyed by their names
+ * @return Const map of ExtensionItem pointers keyed by their names
+ */
+ const ExtMap& GetExts() const { return types; }
+
+ private:
+ ExtMap types;
};
/** Base class for items that are NOT synchronized between servers */
@@ -192,6 +201,7 @@ class CoreExport LocalStringExt : public SimpleExtItem<std::string>
LocalStringExt(const std::string& key, ExtensibleType exttype, Module* owner);
virtual ~LocalStringExt();
std::string serialize(SerializeFormat format, const Extensible* container, void* item) const;
+ void unserialize(SerializeFormat format, Extensible* container, const std::string& value);
};
class CoreExport LocalIntExt : public LocalExtItem
@@ -200,6 +210,7 @@ class CoreExport LocalIntExt : public LocalExtItem
LocalIntExt(const std::string& key, ExtensibleType exttype, Module* owner);
virtual ~LocalIntExt();
std::string serialize(SerializeFormat format, const Extensible* container, void* item) const;
+ void unserialize(SerializeFormat format, Extensible* container, const std::string& value);
intptr_t get(const Extensible* container) const;
intptr_t set(Extensible* container, intptr_t value);
void unset(Extensible* container) { set(container, 0); }
diff --git a/include/modules.h b/include/modules.h
index c938e6a9d..f86f88087 100644
--- a/include/modules.h
+++ b/include/modules.h
@@ -1035,9 +1035,6 @@ class CoreExport ModuleManager : public fakederef<ModuleManager>
PRIO_STATE_LAST
} prioritizationState;
- /** Internal unload module hook */
- bool CanUnload(Module*);
-
/** Loads all core modules (cmd_*)
*/
void LoadCoreModules(std::map<std::string, ServiceList>& servicemap);
@@ -1165,18 +1162,19 @@ class CoreExport ModuleManager : public fakederef<ModuleManager>
*/
bool Unload(Module* module);
- /** Run an asynchronous reload of the given module. When the reload is
- * complete, the callback will be run with true if the reload succeeded
- * and false if it did not.
- */
- void Reload(Module* module, HandlerBase1<void, bool>* callback);
-
/** Called by the InspIRCd constructor to load all modules from the config file.
*/
void LoadAll();
void UnloadAll();
void DoSafeUnload(Module*);
+ /** Check if a module can be unloaded and if yes, prepare it for unload
+ * @param mod Module to be unloaded
+ * @return True if the module is unloadable, false otherwise.
+ * If true the module must be unloaded in the current main loop iteration.
+ */
+ bool CanUnload(Module* mod);
+
/** Find a module by name, and return a Module* to it.
* This is preferred over iterating the module lists yourself.
* @param name The module name to look up
diff --git a/include/modules/reload.h b/include/modules/reload.h
new file mode 100644
index 000000000..dcdbc95e9
--- /dev/null
+++ b/include/modules/reload.h
@@ -0,0 +1,80 @@
+/*
+ * InspIRCd -- Internet Relay Chat Daemon
+ *
+ * Copyright (C) 2015 Attila Molnar <attilamolnar@hush.com>
+ *
+ * This file is part of InspIRCd. InspIRCd is free software: you can
+ * redistribute it and/or modify it under the terms of the GNU General Public
+ * License as published by the Free Software Foundation, version 2.
+ *
+ * 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 <http://www.gnu.org/licenses/>.
+ */
+
+
+#pragma once
+
+#include "event.h"
+
+namespace ReloadModule
+{
+ class EventListener;
+ class DataKeeper;
+
+ /** Container for data saved by modules before another module is reloaded.
+ */
+ class CustomData
+ {
+ struct Data
+ {
+ EventListener* handler;
+ void* data;
+ Data(EventListener* Handler, void* moddata) : handler(Handler), data(moddata) { }
+ };
+ typedef std::vector<Data> List;
+ List list;
+
+ public:
+ /** Add data to the saved state of a module.
+ * The provided handler's OnReloadModuleRestore() method will be called when the reload is done with the pointer
+ * provided.
+ * @param handler Handler for restoring the data
+ * @param data Pointer to the data, will be passed back to the provided handler's OnReloadModuleRestore() after the
+ * reload finishes
+ */
+ void add(EventListener* handler, void* data)
+ {
+ list.push_back(Data(handler, data));
+ }
+
+ friend class DataKeeper;
+ };
+
+ class EventListener : public Events::ModuleEventListener
+ {
+ public:
+ EventListener(Module* mod)
+ : ModuleEventListener(mod, "event/reloadmodule")
+ {
+ }
+
+ /** Called whenever a module is about to be reloaded. Use this event to save data related to the module that you want
+ * to be restored after the reload.
+ * @param mod Module to be reloaded
+ * @param cd CustomData instance that can store your data once.
+ */
+ virtual void OnReloadModuleSave(Module* mod, CustomData& cd) = 0;
+
+ /** Restore data after a reload. Only called if data was added in OnReloadModuleSave().
+ * @param mod Reloaded module, if NULL the reload failed and the module no longer exists
+ * @param data Pointer that was passed to CustomData::add() in OnReloadModuleSave() at the time when the module's state
+ * was saved
+ */
+ virtual void OnReloadModuleRestore(Module* mod, void* data) = 0;
+ };
+}