Go to the documentation of this file.00001
00002 #ifndef acsThreadBase_h
00003 #define acsThreadBase_h
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00035 #include <acsutil.h>
00036 #include <acsutilThreadInit.h>
00037
00038 #include <map>
00039 #include <vector>
00040
00041 #include <ace/Thread.h>
00042 #include <ace/Thread_Manager.h>
00043 #include <ace/Synch.h>
00044
00045 #include <acscommonC.h>
00046 #include <ace/SString.h>
00047 #include <logging.h>
00048 #include <loggingLoggable.h>
00049
00050 #include "acsthreadErrType.h"
00051 #include "acsThreadExport.h"
00052
00053 namespace ACS {
00054
00059 TimeInterval getTime();
00060
00106 class acsThread_EXPORT ThreadBase : public Logging::Loggable
00107 {
00108 public:
00109
00119 static TimeInterval defaultResponseTime;
00120
00129 static TimeInterval defaultSleepTime;
00130
00132 static ThreadBase * NullThreadBase;
00133
00135 static InitThreadFunc InitThread;
00136
00138 static DoneThreadFunc DoneThread;
00139
00140 public:
00141
00152 enum SleepReturn {
00153 SLEEP_OK=0,
00154 SLEEP_SUSPEND,
00155 SLEEP_INTERRUPTED,
00156 SLEEP_ERROR
00157 };
00158
00180 ThreadBase(const ACE_CString& _name, ACE_Thread_Manager* _threadManager,
00181 void* _threadProcedure, void* _parameter,
00182 const TimeInterval& _responseTime=ThreadBase::defaultResponseTime,
00183 const TimeInterval& _sleepTime=ThreadBase::defaultSleepTime,
00184 const bool _create=true,
00185 const long _thrFlags= THR_NEW_LWP | THR_DETACHED,
00186 const size_t _stackSize=ACE_DEFAULT_THREAD_STACKSIZE);
00187
00200 virtual ~ThreadBase();
00201
00213 static void setInitializers(InitThreadFunc InitThread_, DoneThreadFunc DoneThread_) {
00214 InitThread=InitThread_;
00215 DoneThread=DoneThread_;
00216 }
00217
00222 ACE_CString getName() const { return name_m; }
00223
00229 void* getThreadProcedure() const { return threadProcedure_mp; }
00230
00236 TimeInterval getResponseTime() const { return responseTime_m; }
00237
00243 void setResponseTime(const TimeInterval& _responseTime) { responseTime_m=_responseTime; };
00244
00250 TimeInterval getSleepTime() const { return sleepTime_m; }
00251
00257 void setSleepTime(const TimeInterval& _sleepTime) {
00258 sleepTime_m=_sleepTime;
00259 };
00260
00265 void setPriority(int _priority);
00266
00271 int getPriority();
00272
00280 bool suspend();
00281
00286 virtual bool resume();
00287
00292 bool isSuspended() const { return suspendStatus_m != 0; }
00293
00298 bool isStopped() const { return stopped_m; }
00299
00305 virtual void exit() { exitRequest_m=true; }
00306
00311 bool exitRequested() const { return exitRequest_m; }
00312
00318 void setStopped() { stopped_m=true; }
00319
00320
00331 bool stop( bool terminating = false );
00332
00333
00346 bool cancel();
00347
00356 bool terminate();
00357
00365 bool restart();
00366
00374 void makeTimeInterval();
00375
00384 bool isResponding() const;
00385
00390 bool isAlive() const { return !stopped_m; }
00391
00403 bool check();
00404
00429 SleepReturn sleep(TimeInterval timeIn100ns = 0) const;
00430
00431
00435 ACE_thread_t getThreadID() { return threadID_m; }
00436
00437 protected:
00452 bool create(const long _thrFlags= THR_NEW_LWP | THR_DETACHED);
00453
00459 virtual void yield();
00460
00461 private:
00462
00464 void* threadProcedure_mp;
00465
00467 const void* parameter_mp;
00468
00470 TimeInterval responseTime_m;
00471
00473 TimeInterval sleepTime_m;
00474
00476 TimeInterval timeStamp_m;
00477
00479 volatile int suspendStatus_m;
00480
00482 volatile bool exitRequest_m;
00483
00485 volatile bool stopped_m;
00486
00488 ACE_CString name_m;
00489
00490
00492 ACE_thread_t threadID_m;
00493
00495 long thrFlags_m;
00496
00498 size_t stackSize_m;
00499
00501 ACE_Thread_Manager * threadManager_mp;
00502
00504 mutable ACE_Thread_Semaphore m_suspendSemaphore;
00505 mutable ACE_Semaphore m_sleepSemaphore;
00506 };
00507
00508
00509
00511 typedef std::map<ACE_CString, ThreadBase*> ThreadMap;
00512
00513
00520
00521
00522
00528 class ThreadManagerBase
00529 {
00536
00537
00538 public:
00539
00543 ThreadManagerBase()
00544 {
00545 threadManager_mp = ACE_Thread_Manager::instance();
00546 }
00547
00552 ~ThreadManagerBase();
00553
00558 int getThreadCount() const {return threads_m.size();}
00559
00565 ACE_CString getThreadName(const int pos) const { return threads_m[pos]->getName(); }
00566
00567
00573 ThreadBase* getThreadAt(const int pos) const { return static_cast<ThreadBase*>(threads_m[pos]); }
00574
00575
00581 ThreadBase* getThreadByName(const ACE_CString& name) {
00582 ACE_Guard<ACE_Recursive_Thread_Mutex> guard(m_addRemoveMutex);
00583
00584 ThreadMap::iterator i = threadMap_m.find(name);
00585 if (i!=threadMap_m.end())
00586 return static_cast<ThreadBase*>((*i).second);
00587 else
00588 return NULL;
00589 }
00590
00596 ThreadBase* getThreadByID(ACE_thread_t id)
00597 {
00598
00599 for(unsigned int i=0UL; i < threads_m.size(); i++)
00600 if (threads_m[i]->getThreadID() == id)
00601 return threads_m[i];
00602 return NULL;
00603 }
00604
00605
00622 ThreadBase * create(const ACE_CString& name, void * threadProc, void * parameter,
00623 const TimeInterval& responseTime=ThreadBase::defaultResponseTime,
00624 const TimeInterval& sleepTime=ThreadBase::defaultSleepTime,
00625 const long _thrFlags= THR_NEW_LWP | THR_DETACHED,
00626 const size_t _stackSize=ACE_DEFAULT_THREAD_STACKSIZE);
00627
00636 bool add(const ACE_CString& name, ThreadBase * acsBaseThread);
00637
00644 bool stop(const ACE_CString& name);
00645
00651 bool stopAll();
00652
00658 void exit(const ACE_CString& name);
00659
00664 void exitAll();
00665
00673 bool cancel(const ACE_CString& name);
00674
00679 bool cancelAll();
00680
00686 bool terminate(const ACE_CString& name);
00687
00692 bool terminateAll();
00693
00700 bool restart(const ACE_CString& name);
00701
00706 bool restartAll();
00707
00713 bool restartDead();
00714
00720 bool suspend(const ACE_CString& name);
00721
00726 bool suspendAll();
00727
00733 bool resume(const ACE_CString& name);
00734
00739 bool resumeAll();
00740
00747 bool isAlive(const ACE_CString& name);
00748
00755 bool areAllAlive();
00756
00762 int join(const ACE_thread_t& tid);
00763
00769 int join(const ThreadBase *th);
00770
00775 ACE_Thread_Manager* getACEThreadManager() { return threadManager_mp; }
00776
00777 protected:
00778
00784 void add2map(const ACE_CString& name, ThreadBase* thread)
00785 {
00786
00787 threadMap_m[name]=thread;
00788 threads_m.push_back(thread);
00789 }
00790
00791 void removeFromMap(const ACE_CString& name)
00792 {
00793 ACE_Guard<ACE_Recursive_Thread_Mutex> guard(m_addRemoveMutex);
00794
00795 ThreadMap::iterator i = threadMap_m.find(name);
00796 if (i!=threadMap_m.end())
00797 {
00798 for (std::vector<ThreadBase*>::iterator thr = threads_m.begin(); thr!=threads_m.end(); ++thr)
00799 {
00800 if (static_cast<ThreadBase*>((*i).second) == *thr)
00801 {
00802 threads_m.erase(thr);
00803 break;
00804 }
00805 }
00806 }
00807 threadMap_m.erase(name);
00808 }
00809
00810 protected:
00812 ACE_Recursive_Thread_Mutex m_addRemoveMutex;
00813
00814 private:
00815
00817 ACE_Thread_Manager * threadManager_mp;
00818
00820 ThreadMap threadMap_m;
00821
00823 std::vector<ThreadBase*> threads_m;
00824
00828 void operator=(const ThreadManagerBase&);
00829
00833 ThreadManagerBase(const ThreadManagerBase&);
00834
00835 };
00836
00844 class ThreadBaseParameter {
00845
00846 public:
00847
00853 ThreadBaseParameter(ThreadBase * thread,
00854 const void * parameter = 0) :
00855 thread_mp(thread), parameter_mp(parameter) {}
00856
00861 const void * getParameter() const { return parameter_mp; }
00862
00867 ThreadBase * getThreadBase() const { return thread_mp; }
00868
00873
00874 private:
00875
00877 ThreadBase * thread_mp;
00878
00880 const void * parameter_mp;
00881 };
00882
00883
00918 class ThreadSyncGuard
00919 {
00920 public:
00921
00928 ThreadSyncGuard(ACE_Recursive_Thread_Mutex * mutex, bool block=true);
00929
00934 ~ThreadSyncGuard();
00935
00939 void acquire();
00940
00944 void release();
00945
00947 ACE_Recursive_Thread_Mutex * mutex_mp;
00948
00950 bool acquired_m;
00951 };
00952
00953 };
00954
00955 #endif
00956
00957
00958
00959
00960