From f4502df850146b15e8067bb317c2aa7d5ca358c4 Mon Sep 17 00:00:00 2001 From: Artem Pavlenko Date: Mon, 27 Nov 2006 21:13:15 +0000 Subject: [PATCH] 1. register singleton destruction with std::atexit 2. allow connection pool to grow (up to max) --- include/mapnik/pool.hpp | 25 ++++-- include/mapnik/utils.hpp | 91 ++++---------------- plugins/input/postgis/connection.hpp | 3 + plugins/input/postgis/connection_manager.hpp | 11 ++- plugins/input/postgis/postgis.cpp | 2 +- 5 files changed, 45 insertions(+), 87 deletions(-) diff --git a/include/mapnik/pool.hpp b/include/mapnik/pool.hpp index ea71dd1cb..fb749e1d8 100644 --- a/include/mapnik/pool.hpp +++ b/include/mapnik/pool.hpp @@ -68,25 +68,25 @@ namespace mapnik typedef std::deque ContType; Creator creator_; - const int initialSize_; - const int maxSize_; + const unsigned initialSize_; + const unsigned maxSize_; ContType usedPool_; ContType unusedPool_; boost::mutex mutex_; public: - Pool(const Creator& creator,int initialSize=5,int maxSize=20) + Pool(const Creator& creator,unsigned initialSize=1, unsigned maxSize=10) :creator_(creator), initialSize_(initialSize), maxSize_(maxSize) { - for (int i=0;i +#include #include #include #include @@ -66,18 +67,21 @@ namespace mapnik int Test::* pMember_; int (Test::*pMemberFn_)(int); }; + public: + static T* create() { static MaxAlign staticMemory; return new(&staticMemory) T; } + static void destroy(volatile T* obj) { obj->~T(); } }; - + template class CreatePolicy=CreateStatic> class singleton { @@ -90,14 +94,20 @@ namespace mapnik { throw std::runtime_error("dead reference!"); } + + static void DestroySingleton() + { + CreatePolicy::destroy(pInstance_); + pInstance_ = 0; + destroyed_=true; +#ifdef MAPNIK_DEBUG + std::clog << " destroyed singleton \n"; +#endif + } + protected: static mutex mutex_; singleton() {} - virtual ~singleton() - { - CreatePolicy::destroy(pInstance_); - destroyed_=true; - } public: static T* instance() { @@ -113,6 +123,8 @@ namespace mapnik else { pInstance_=CreatePolicy::create(); + // register destruction + std::atexit(&DestroySingleton); } } } @@ -126,72 +138,7 @@ namespace mapnik template class CreatePolicy> T* singleton::pInstance_=0; template class CreatePolicy> bool singleton::destroyed_=false; - - template class Handle - { - T* ptr_; - int* pCount_; - public: - T* operator->() {return ptr_;} - const T* operator->() const {return ptr_;} - Handle(T* ptr) - :ptr_(ptr),pCount_(new int(1)) {} - Handle(const Handle& rhs) - :ptr_(rhs.ptr_),pCount_(rhs.pCount_) - { - (*pCount_)++; - } - Handle& operator=(const Handle& rhs) - { - if (ptr_==rhs.ptr_) return *this; - if (--(*pCount_)==0) - { - delete ptr_; - delete pCount_; - } - ptr_=rhs.ptr_; - pCount_=rhs.pCount_; - (*pCount_)++; - return *this; - } - ~Handle() - { - if (--(*pCount_)==0) - { - delete ptr_; - delete pCount_; - } - } - }; - - //converters - class BadConversion : public std::runtime_error - { - public: - BadConversion(const std::string& s) - :std::runtime_error(s) - {} - }; - - template - inline std::string toString(const T& x) - { - std::ostringstream o; - if (!(o << x)) - throw BadConversion(std::string("toString(") - + typeid(x).name() + ")"); - return o.str(); - } - - template - inline void fromString(const std::string& s, T& x, - bool failIfLeftoverChars = true) - { - std::istringstream i(s); - char c; - if (!(i >> x) || (failIfLeftoverChars && i.get(c))) - throw BadConversion("fromString("+s+")"); - } + } diff --git a/plugins/input/postgis/connection.hpp b/plugins/input/postgis/connection.hpp index 137d1ab56..c5f163f16 100644 --- a/plugins/input/postgis/connection.hpp +++ b/plugins/input/postgis/connection.hpp @@ -89,6 +89,9 @@ public: ~Connection() { PQfinish(conn_); +#ifdef MAPNIK_DEBUG + std::clog << "close connection " << conn_ << "\n"; +#endif } }; diff --git a/plugins/input/postgis/connection_manager.hpp b/plugins/input/postgis/connection_manager.hpp index 765f02ff3..99d63ce76 100644 --- a/plugins/input/postgis/connection_manager.hpp +++ b/plugins/input/postgis/connection_manager.hpp @@ -76,7 +76,7 @@ class ConnectionManager : public singleton public: - bool registerPool(const ConnectionCreator& creator,int initialSize,int maxSize) + bool registerPool(const ConnectionCreator& creator,unsigned initialSize,unsigned maxSize) { mutex::scoped_lock lock(mutex_); if (pools_.find(creator.id())==pools_.end()) @@ -89,7 +89,7 @@ public: } - const boost::shared_ptr& getPool(const std::string& key) + boost::shared_ptr getPool(std::string const& key) { mutex::scoped_lock lock(mutex_); ContType::const_iterator itr=pools_.find(key); @@ -101,7 +101,7 @@ public: return emptyPool; } - const HolderType& get(const std::string& key) + HolderType get(std::string const& key) { mutex::scoped_lock lock(mutex_); ContType::const_iterator itr=pools_.find(key); @@ -110,10 +110,9 @@ public: boost::shared_ptr pool=itr->second; return pool->borrowObject(); } - static const HolderType EmptyConn; - return EmptyConn; + return HolderType(); } - + private: ConnectionManager() {} ConnectionManager(const ConnectionManager&); diff --git a/plugins/input/postgis/postgis.cpp b/plugins/input/postgis/postgis.cpp index 2875b3adc..9dbac08a2 100644 --- a/plugins/input/postgis/postgis.cpp +++ b/plugins/input/postgis/postgis.cpp @@ -54,7 +54,7 @@ postgis_datasource::postgis_datasource(parameters const& params) params.get("password")) { ConnectionManager *mgr=ConnectionManager::instance(); - mgr->registerPool(creator_,10,20); + mgr->registerPool(creator_,5,10); shared_ptr > pool=mgr->getPool(creator_.id()); if (pool)