plugin_factory.hh
Go to the documentation of this file.
00001 // Copyright Vladimir Prus 2004.
00002 // Distributed under the Boost Software License, Version 1.0.
00003 // (See accompanying file LICENSE_1_0.txt
00004 // or copy at http://www.boost.org/LICENSE_1_0.txt)
00005 
00006 #ifndef BOOST_PLUGIN_FACTORY_VP_2004_08_25
00007 #define BOOST_PLUGIN_FACTORY_VP_2004_08_25
00008 
00009 #include <utilmm/plugin/virtual_constructors.hh>
00010 #include <utilmm/plugin/dll.hh>
00011 #include <utilmm/plugin/abstract_factory.hh>
00012 #include <utility>
00013 #include <stdexcept>
00014 #include <string>
00015 #include <utility>
00016 
00017 namespace utilmm { namespace plugin {
00018 
00019     namespace {
00020         typedef std::map<std::string, boost::any> exported_plugins_t;
00021         typedef exported_plugins_t& (*get_plugins_list_t)();
00022         typedef exported_plugins_t& (get_plugins_list_np)();
00023 
00024         template<class BasePlugin>
00025         std::pair<abstract_factory<BasePlugin>*,
00026                   dll_handle >
00027         get_abstract_factory(const dll& d, const std::string& klass)
00028         {
00029             boost::shared_ptr<get_plugins_list_np> f; 
00030             f = d.template get<exported_plugins_t& (*)()>("boost_exported_plugins_list");    
00031             exported_plugins_t& e = (*f)();
00032             
00033             if (e.count(klass)) {
00034 
00035                 abstract_factory<BasePlugin>** xw = 
00036                     boost::any_cast<abstract_factory<BasePlugin>*>(&(e[klass]));
00037 
00038                 if (!xw) {
00039                     throw std::logic_error("Can't cast to the right factor type\n");                    
00040                 }
00041                 abstract_factory<BasePlugin>* w = *xw;
00042                 return make_pair(w, f);
00043             } else {
00044                 throw std::logic_error("Class of the specified name is not found");
00045             }
00046         }
00047 
00048     }
00049 
00050 
00051 
00052     struct empty_plugin_factory_item {
00053         void create(int****);
00054     protected:
00055         dll m_dll;
00056     };
00057 
00058     template<class BasePlugin, class Base, class Parameters>
00059     struct plugin_factory_item {                
00060     };
00061 
00062     template<class BasePlugin, class Base>
00063     struct plugin_factory_item<BasePlugin, Base, boost::mpl::list<> > : public Base { 
00064         using Base::create;
00065         BasePlugin* create(const std::string& name)
00066         {
00067             std::pair<abstract_factory<BasePlugin>*,
00068                 dll_handle > r = get_abstract_factory<BasePlugin>(this->m_dll, name);
00069             return r.first->create(r.second);            
00070         }
00071     };
00072 
00073     template<class BasePlugin, class Base, class A1>
00074     struct plugin_factory_item<BasePlugin, Base, boost::mpl::list<A1> > : public Base {                
00075         using Base::create;
00076         BasePlugin* create(const std::string& name, A1 a1)
00077         {
00078             std::pair<abstract_factory<BasePlugin>*,
00079                 dll_handle > r = get_abstract_factory<BasePlugin>(this->m_dll, name);
00080             return r.first->create(r.second, a1);            
00081         }
00082     };
00083 
00084     template<class BasePlugin, class Base, class A1, class A2>
00085     struct plugin_factory_item<BasePlugin, Base, boost::mpl::list<A1, A2> > : public Base {                
00086         using Base::create;
00087         BasePlugin* create(const std::string& name, A1 a1, A2 a2)
00088         {
00089             std::pair<abstract_factory<BasePlugin>*,
00090                 dll_handle > r = get_abstract_factory<BasePlugin>(this->m_dll, name);
00091             return r.first->create(r.second, a1, a2);            
00092         }
00093     };
00094 
00095 #if 0
00096 
00097     template<class BasePlugin, class Base, class Parameters>
00098     struct plugin_factory_item 
00099         : public Base,
00100           public plugin_factory_item_N<BasePlugin, Parameters>
00101 
00102     {
00103         using Base::create;
00104         using plugin_factory_item_N<BasePlugin, Parameters>::create;
00105     };
00106 #endif
00107 
00108     using namespace boost::mpl::placeholders;
00109 
00110     template<class BasePlugin>
00111     struct plugin_factory : 
00112         public boost::mpl::inherit_linearly<
00113         typename virtual_constructors<BasePlugin>::type,
00114         plugin_factory_item<BasePlugin, _, _>,
00115         empty_plugin_factory_item>::type 
00116     {        
00117         plugin_factory(const dll& d)
00118         {
00119             this->m_dll = d;
00120         }
00121     };
00122 
00123 }}
00124 
00125 #endif


utilmm
Author(s): Sylvain Joyeux/sylvain.joyeux@m4x.org
autogenerated on Wed Sep 16 2015 07:05:43