monitor.h

Go to the documentation of this file.
00001 
00014 #ifndef _DLR_THREAD_MONITOR_H_
00015 #define _DLR_THREAD_MONITOR_H_
00016 
00017 #include <vector>
00018 #include <boost/thread.hpp>
00019 #include <dlrCommon/referenceCount.h>
00020 
00021 namespace dlr {
00022 
00023   namespace thread {
00024 
00025     // Forward declarations.
00026     class Monitor;
00027     class Condition;
00028 
00029     
00037     class Token {
00038       friend class Monitor;
00039       friend class Condition;
00040       
00041     public:
00042       Token();
00043       Token(const Token& other);
00044       ~Token();
00045       operator bool();
00046 
00047     private:
00048       Token(boost::timed_mutex& mutex);
00049       Token(boost::timed_mutex& mutex, double timeout);
00050       boost::timed_mutex::scoped_lock& getLock();
00051       boost::timed_mutex::scoped_timed_lock& getTimedLock();
00052       bool isTimed();
00053       Token& operator=(const Token& other);
00054 
00055       bool m_isTimed;
00056       boost::timed_mutex::scoped_lock* m_lockPtr;
00057       boost::timed_mutex::scoped_timed_lock* m_timedLockPtr;
00058 
00059       // We use ReferenceCount directly, rather than through a
00060       // pointer, because Token objects are never expected to be
00061       // shared between threads, so thread isn't an issue.
00062       ReferenceCount m_referenceCount;
00063     };
00064 
00065     
00072     class Condition {
00073       friend class Monitor;
00074     public:
00075       Condition(const Condition& other);
00076       ~Condition();
00077       Condition& operator=(const Condition& other);
00078 
00079     private:
00080       Condition(boost::condition* conditionPtr);
00081       void signalOne();
00082       void signalAll();
00083       void wait(Token& token);
00084       bool wait(Token& token, double timeout);
00085 
00086       boost::condition* m_conditionPtr;
00087     };
00088 
00089     
00090 
00186     class Monitor
00187     {
00188     public:
00189 
00193       Monitor();
00194 
00195 
00204       Monitor(const Monitor& other);
00205 
00206 
00210       virtual
00211       ~Monitor();
00212 
00213 
00223       Monitor&
00224       operator=(const Monitor& other);
00225 
00226 
00237       void
00238       makeCopyable(bool copyableFlag=true) {m_isCopyable = copyableFlag;}
00239 
00240     protected:
00241 
00250       void
00251       copyOther(const Monitor& other);
00252 
00253       
00278       Condition
00279       createCondition(bool doInitialize = true);
00280 
00281 
00291       Token
00292       getToken() {return Token(*m_tokenMutexPtr);}
00293 
00294       
00304       Token
00305       getToken(double timeout) {return Token(*m_tokenMutexPtr, timeout);}
00306 
00307 
00312       void
00313       releaseResources();
00314 
00315       
00331       void
00332       signalOne(Condition& condition) {condition.signalOne();}
00333 
00334       
00345       void
00346       signalAll(Condition& condition) {condition.signalAll();}
00347 
00348       
00362       void
00363       wait(Condition& condition, Token& token) {condition.wait(token);}
00364         
00365 
00386       bool
00387       wait(Condition& condition, Token& token, double timeout) {
00388         return condition.wait(token, timeout);
00389       }
00390 
00391 
00392     private:
00393 
00394       // We need a mutex in order to implement the virtual token.
00395       boost::timed_mutex* m_tokenMutexPtr;
00396 
00397       // This vector lets us manage deletion of condition objects
00398       // explicitly, rather than relying on the Condition class to do
00399       // so.  This is important because the Condition class destructor
00400       // is not always called in a protected section of code.
00401       std::vector<boost::condition*>* m_boostConditionVectorPtr;
00402       
00403       // This bool indicates whether or not copying should be allowed.
00404       bool m_isCopyable;
00405       
00406       // Note that thread-safety requires us to use a pointer here.
00407       size_t* m_referenceCountPtr;
00408     };
00409 
00410   } // namespace thread
00411 
00412 } // namespace dlr
00413 
00414 #endif /* #ifndef _DLR_THREAD_MONITOR_H_ */

Generated on Mon Jul 9 20:34:03 2007 for dlrLibs Utility Libraries by  doxygen 1.5.2