1 // ==============================================================
2 //	This file is part of Glest Shared Library (www.glest.org)
3 //
4 //	Copyright (C) 2009-2010 Titus Tscharntke (info@titusgames.de) and
5 //                          Mark Vejvoda (mark_vejvoda@hotmail.com)
6 //
7 //	You can redistribute this code and/or modify it under
8 //	the terms of the GNU General Public License as published
9 //	by the Free Software Foundation; either version 2 of the
10 //	License, or (at your option) any later version
11 // ==============================================================
12 #ifndef _SHARED_PLATFORMCOMMON_BASETHREAD_H_
13 #define _SHARED_PLATFORMCOMMON_BASETHREAD_H_
14 
15 #include "leak_dumper.h"
16 #include "thread.h"
17 #include <string>
18 #include <map>
19 
20 using namespace Shared::Platform;
21 using namespace std;
22 
23 namespace Shared { namespace PlatformCommon {
24 
25 // =====================================================
26 //	class BaseThread
27 // =====================================================
28 
29 class BaseThread : public Thread
30 {
31 protected:
32 	Mutex *mutexRunning;
33 	Mutex *mutexQuit;
34 	Mutex *mutexBeginExecution;
35 	Mutex *mutexDeleteSelfOnExecutionDone;
36 
37     Mutex *mutexThreadObjectAccessor;
38 
39     bool threadOwnerValid;
40     Mutex *mutexThreadOwnerValid;
41 
42 	Mutex *mutexExecutingTask;
43 	bool executingTask;
44 
45 	void *ptr;
46 	static Mutex mutexMasterThreadList;
47 	static std::map<void *,int> masterThreadList;
48 
49 	bool quit;
50 	bool running;
51 	string uniqueID;
52 	bool hasBeginExecution;
53 	bool deleteSelfOnExecutionDone;
54 
55 	Mutex *mutexStarted;
56 	bool started;
57 
58 	virtual void setQuitStatus(bool value);
59 	void deleteSelfIfRequired();
60 
61 	void *genericData;
62 
63 
64 public:
65 	BaseThread();
66 	virtual ~BaseThread();
67 	virtual void execute()=0;
68 
69 	virtual void signalQuit();
70 	virtual bool getQuitStatus();
71 	virtual bool getRunningStatus();
72 
73 	virtual bool getStarted();
74 	virtual void setStarted(bool value);
75 
76 	virtual bool getHasBeginExecution();
77 	virtual void setHasBeginExecution(bool value);
78 
79     static bool shutdownAndWait(BaseThread *ppThread);
80     virtual bool shutdownAndWait();
81     virtual bool canShutdown(bool deleteSelfIfShutdownDelayed=false);
82 
83     virtual bool getDeleteSelfOnExecutionDone();
84 	virtual void setDeleteSelfOnExecutionDone(bool value);
85 
setUniqueID(string value)86     void setUniqueID(string value) { uniqueID = value; }
getUniqueID()87     string getUniqueID() { return uniqueID; }
88 
89     virtual void setRunningStatus(bool value);
90 
91     void setExecutingTask(bool value);
92     bool getExecutingTask();
93 
94 
95     void setThreadOwnerValid(bool value);
96     bool getThreadOwnerValid();
97     Mutex * getMutexThreadOwnerValid();
98 
99     Mutex * getMutexThreadObjectAccessor();
100 
101 	template <typename T>
getGenericData()102 	T * getGenericData() {
103 		return genericData;
104 	}
105 	template <typename T>
setGenericData(T * value)106 	void setGenericData(T *value) {
107 		genericData = value;
108 	}
109 
110     static bool isThreadDeleted(void *ptr);
111 };
112 
113 class RunningStatusSafeWrapper {
114 protected:
115 	BaseThread *thread;
116 public:
117 
RunningStatusSafeWrapper(BaseThread * thread)118 	RunningStatusSafeWrapper(BaseThread *thread) {
119 		this->thread = thread;
120 		Enable();
121 	}
~RunningStatusSafeWrapper()122 	~RunningStatusSafeWrapper() {
123 		Disable();
124 	}
125 
Enable()126 	void Enable() {
127 		if(this->thread != NULL) {
128 			this->thread->setRunningStatus(true);
129 		}
130 	}
Disable()131 	void Disable() {
132 		if(this->thread != NULL) {
133 		    this->thread->setRunningStatus(false);
134 		}
135 	}
136 };
137 
138 class ExecutingTaskSafeWrapper {
139 protected:
140 	BaseThread *thread;
141 public:
142 
ExecutingTaskSafeWrapper(BaseThread * thread)143 	ExecutingTaskSafeWrapper(BaseThread *thread) {
144 		this->thread = thread;
145 		Enable();
146 	}
~ExecutingTaskSafeWrapper()147 	~ExecutingTaskSafeWrapper() {
148 		Disable();
149 	}
150 
Enable()151 	void Enable() {
152 		if(this->thread != NULL) {
153 			this->thread->setExecutingTask(true);
154 		}
155 	}
Disable()156 	void Disable() {
157 		if(this->thread != NULL) {
158 		    this->thread->setExecutingTask(false);
159 		}
160 	}
161 };
162 
163 
164 }}//end namespace
165 
166 #endif
167