00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include <config.h>
00021
00022 #include <string>
00023 #include <vector>
00024 #include <map>
00025
00026 #include <drizzled/module/registry.h>
00027 #include <drizzled/module/library.h>
00028 #include <drizzled/module/graph.h>
00029 #include <drizzled/module/vertex_handle.h>
00030
00031 #include <drizzled/plugin.h>
00032 #include <drizzled/show.h>
00033 #include <drizzled/cursor.h>
00034 #include <drizzled/abort_exception.h>
00035 #include <drizzled/util/find_ptr.h>
00036
00037 #include <boost/bind.hpp>
00038 #include <boost/foreach.hpp>
00039
00040 using namespace std;
00041
00042 namespace drizzled {
00043
00044 module::Registry::Registry() :
00045 module_registry_(),
00046 depend_graph_(new module::Graph()),
00047 plugin_registry(),
00048 deps_built_(false)
00049 { }
00050
00051
00052 module::Registry::~Registry()
00053 {
00054
00055
00056
00057
00058
00059 BOOST_FOREACH(plugin::Plugin::map::reference it, plugin_registry)
00060 it.second->shutdownPlugin();
00061
00062 plugin::Plugin::vector error_plugins;
00063 BOOST_FOREACH(plugin::Plugin::map::reference it, plugin_registry)
00064 {
00065 if (it.second->removeLast())
00066 error_plugins.push_back(it.second);
00067 else
00068 delete it.second;
00069 }
00070
00071 BOOST_FOREACH(plugin::Plugin::vector::reference it, error_plugins)
00072 delete it;
00073
00074 plugin_registry.clear();
00075
00076 #if 0
00077
00078
00079
00080
00081 BOOST_FOREACH(ModuleMap::reference it, module_registry_)
00082 delete it.second;
00083 module_registry_.clear();
00084 #endif
00085 BOOST_FOREACH(LibraryMap::reference it, library_registry_)
00086 delete it.second;
00087 library_registry_.clear();
00088 }
00089
00090 void module::Registry::shutdown()
00091 {
00092 delete &singleton();
00093 }
00094
00095 module::Module* module::Registry::find(const std::string& name)
00096 {
00097 return find_ptr2(module_registry_, boost::to_lower_copy(name));
00098 }
00099
00100 void module::Registry::add(module::Module *handle)
00101 {
00102 std::string add_str(boost::to_lower_copy(handle->getName()));
00103
00104 module_registry_[add_str]= handle;
00105
00106 Vertex vertex_info(add_str, handle);
00107 VertexDesc handle_vertex= boost::add_vertex(depend_graph_->getGraph());
00108 depend_graph_->properties(handle_vertex)= vertex_info;
00109
00110 handle->setVertexHandle(new VertexHandle(handle_vertex));
00111 }
00112
00113 void module::Registry::remove(module::Module *handle)
00114 {
00115 module_registry_.erase(boost::to_lower_copy(handle->getName()));
00116 }
00117
00118 void module::Registry::buildDeps()
00119 {
00120 BOOST_FOREACH(ModuleMap::reference map_iter, module_registry_)
00121 {
00122 Module* handle= map_iter.second;
00123 BOOST_FOREACH(Module::Depends::const_reference handle_deps, handle->getDepends())
00124 {
00125 std::string dep_str(boost::to_lower_copy(handle_deps));
00126 bool found_dep= false;
00127 for (vertex_iter it= boost::vertices(depend_graph_->getGraph()).first; it != vertices(depend_graph_->getGraph()).second; it++)
00128 {
00129 if (depend_graph_->properties(*it).getName() == dep_str)
00130 {
00131 found_dep= true;
00132 add_edge(handle->getVertexHandle()->getVertexDesc(), *it, depend_graph_->getGraph());
00133 break;
00134 }
00135 }
00136 if (not found_dep)
00137 {
00138 errmsg_printf(error::ERROR, _("Couldn't process plugin module dependencies. %s depends on %s but %s is not to be loaded.\n"),
00139 handle->getName().c_str(), dep_str.c_str(), dep_str.c_str());
00140 DRIZZLE_ABORT;
00141 }
00142 }
00143 }
00144 deps_built_= true;
00145 }
00146
00147 module::Registry::ModuleList module::Registry::getList()
00148 {
00149 if (not deps_built_)
00150 buildDeps();
00151 VertexList vertex_list;
00152 boost::topological_sort(depend_graph_->getGraph(), std::back_inserter(vertex_list));
00153 ModuleList plugins;
00154 BOOST_FOREACH(VertexList::reference it, vertex_list)
00155 {
00156 if (Module* mod_ptr= depend_graph_->properties(it).getModule())
00157 plugins.push_back(mod_ptr);
00158 }
00159 return plugins;
00160 }
00161
00162 module::Library *module::Registry::addLibrary(const std::string &plugin_name, bool builtin)
00163 {
00164
00165 module::Library *library= findLibrary(plugin_name);
00166 if (library)
00167 return library;
00168
00169 library= module::Library::loadLibrary(plugin_name, builtin);
00170 if (library)
00171 {
00172
00173 library_registry_.insert(make_pair(plugin_name, library));
00174 }
00175 return library;
00176 }
00177
00178 void module::Registry::removeLibrary(const std::string &plugin_name)
00179 {
00180 LibraryMap::iterator iter= library_registry_.find(plugin_name);
00181 if (iter != library_registry_.end())
00182 {
00183 delete iter->second;
00184 library_registry_.erase(iter);
00185 }
00186 }
00187
00188 module::Library *module::Registry::findLibrary(const std::string &plugin_name) const
00189 {
00190 return find_ptr2(library_registry_, plugin_name);
00191 }
00192
00193 void module::Registry::shutdownModules()
00194 {
00195 module_shutdown(*this);
00196 }
00197
00198 }