/////////////////////////////////////////////////////////////////////////////// // // Copyright (C) 2010-2011 Artyom Beilis (Tonkikh) // // Distributed under: // // the Boost Software License, Version 1.0. // (See accompanying file LICENSE_1_0.txt or copy at // http://www.boost.org/LICENSE_1_0.txt) // // or (at your opinion) under: // // The MIT License // (See accompanying file MIT.txt or a copy at // http://www.opensource.org/licenses/mit-license.php) // /////////////////////////////////////////////////////////////////////////////// #define CPPDB_SOURCE #include #include #include #include namespace cppdb { struct connections_manager::data{}; connections_manager::connections_manager() {} // Borland erros on hidden destructors in classes without only static methods. #ifndef __BORLANDC__ connections_manager::~connections_manager() {} #endif connections_manager &connections_manager::instance() { static connections_manager mgr; return mgr; } namespace { struct init { init() { connections_manager::instance(); } } initializer; } ref_ptr connections_manager::open(std::string const &cs) { ref_ptr p; /// seems we may be using pool if(cs.find("@pool_size")!=std::string::npos) { mutex::guard l(lock_); connections_type::iterator pool_ptr = connections_.find(cs); if(pool_ptr!=connections_.end()) p = pool_ptr->second; } if(p) { return p->open(); } else { connection_info ci(cs); return open(ci); } } ref_ptr connections_manager::open(connection_info const &ci) { if(ci.get("@pool_size",0)==0) { return driver_manager::instance().connect(ci); } ref_ptr p; { mutex::guard l(lock_); ref_ptr &ref_p = connections_[ci.connection_string]; if(!ref_p) { ref_p = pool::create(ci); } p=ref_p; } return p->open(); } void connections_manager::gc() { std::vector > pools_; pools_.reserve(100); { mutex::guard l(lock_); for(connections_type::iterator p=connections_.begin();p!=connections_.end();++p) { pools_.push_back(p->second); } } for(unsigned i=0;igc(); } pools_.clear(); { mutex::guard l(lock_); for(connections_type::iterator p=connections_.begin();p!=connections_.end();) { if(p->second->use_count() == 1) { pools_.push_back(p->second); connections_type::iterator tmp = p; ++p; connections_.erase(tmp); } else ++p; } } pools_.clear(); } } // cppdb