From 0f595e076f03c02b366901e8d3c5cc0c50681108 Mon Sep 17 00:00:00 2001 From: Max Christian Pohle Date: Tue, 23 Aug 2016 02:46:27 +0200 Subject: generic plugin manager example, fully working --- pluginmanager.hpp | 99 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 99 insertions(+) create mode 100644 pluginmanager.hpp (limited to 'pluginmanager.hpp') diff --git a/pluginmanager.hpp b/pluginmanager.hpp new file mode 100644 index 0000000..2415acf --- /dev/null +++ b/pluginmanager.hpp @@ -0,0 +1,99 @@ +/* + * pluginmanager.hpp + * + * Copyright 2009 Max Christian Pohle + * + * This program 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; either version 2 of the License, or + * (at your option) any later version. + * + * 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, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, + * MA 02110-1301, USA. + */ + +#ifndef pluginmanager +#define pluginmanager + #define PLUGIN_ENGINE_VERSION 1 + + #include + #include + #include + #include + #include + #include + + #include "plugins/plugin.hpp" + + using namespace std; + + template + class PluginManager + { + private: + int engine_version; + typedef T create(); + map plugins; + typename map::iterator iter; + + public: + PluginManager() : engine_version(PLUGIN_ENGINE_VERSION) {} + + T get_instance(string t) + { + iter = plugins.find(t); + if (iter != plugins.end()) + { return iter->second(); } + } + + list list_plugins() + { + list retval; + for(iter=plugins.begin(); iter!=plugins.end(); ++iter) + { retval.push_front(iter->first); } + return retval; + } + + void load_plugin(string filename) + { + std::stringstream serr; + char* dlsym_error; + std::cerr << "\n> OPENING " << filename << "..."; + void* plugin2open = dlopen(filename.c_str(), RTLD_LAZY); + if (dlsym_error = dlerror()) + { + std::stringstream a; + a << + std::string(filename) << + std::string(" is not a valid plugin\n\t") << + std::string(dlsym_error); + throw (char*) a.str().c_str(); + } + else + { + std::cerr << "done.\n"; + } + + create* f_creator = (create*) dlsym(plugin2open, "create"); + if (dlsym_error = dlerror()) + { + throw (char*)"plugin has no creation-interface" + ", so is obviously no subclass of 'Plugin'"; + } + else + { + std::cout << "> LOADING " << filename << "..."; + plugins.insert(make_pair(filename, f_creator)); + std::cout << "done.\n"; + } + } + }; + +#endif -- cgit v1.2.3