00001 /* 00002 * Thread.hpp 00003 * 00004 * Copyright (c) 2000, 2020, Oracle and/or its affiliates. All rights reserved. 00005 * 00006 * Oracle is a registered trademarks of Oracle Corporation and/or its 00007 * affiliates. 00008 * 00009 * This software is the confidential and proprietary information of Oracle 00010 * Corporation. You shall not disclose such confidential and proprietary 00011 * information and shall use it only in accordance with the terms of the 00012 * license agreement you entered into with Oracle. 00013 * 00014 * This notice may not be removed or altered. 00015 */ 00016 #ifndef COH_THREAD_HPP 00017 #define COH_THREAD_HPP 00018 00019 #include "coherence/lang/compatibility.hpp" 00020 00021 #include "coherence/lang/FinalHandle.hpp" 00022 #include "coherence/lang/FinalView.hpp" 00023 #include "coherence/lang/Object.hpp" 00024 #include "coherence/lang/ObjectArray.hpp" 00025 #include "coherence/lang/MemberView.hpp" 00026 #include "coherence/lang/Runnable.hpp" 00027 #include "coherence/lang/String.hpp" 00028 #include "coherence/lang/ThreadGroup.hpp" 00029 #include "coherence/lang/TypedHandle.hpp" 00030 #include "coherence/lang/Volatile.hpp" 00031 00032 COH_OPEN_NAMESPACE2(coherence,lang) 00033 00034 class TimeoutBlock; 00035 00036 /** 00037 * An Object representing a thread of execution. 00038 * 00039 * @author mf 2007.12.10 00040 */ 00041 class COH_EXPORT Thread 00042 : public class_spec<Thread, 00043 extends<Object>, 00044 implements<Runnable> > 00045 { 00046 friend class factory<Thread>; 00047 00048 // ----- State definition ----------------------------------------------- 00049 00050 public: 00051 typedef enum 00052 { 00053 state_initial = 0, // the thread has not yet started 00054 state_runnable = 1, // the thread has started 00055 state_interrupted = 2, // the thread has been interrupted 00056 state_terminated = 3 // the thread has completed execution 00057 } State; 00058 00059 00060 // ----- Maintenance definition ------------------------------------------ 00061 00062 protected: 00063 /** 00064 * Defines various thread maintenance tasks. 00065 */ 00066 typedef enum 00067 { 00068 none = 0, 00069 collect_stack = 1, 00070 compact_tls = 2 00071 } Maintenance; 00072 00073 00074 // ----- constructors --------------------------------------------------- 00075 00076 private: 00077 /** 00078 * Create a Thread. 00079 * 00080 * @param hRunnable the Runnable to execute 00081 * @param vsName the thread's name, or NULL for default 00082 * @param hGroup the thread's group, or NULL for parent's 00083 * @param cBytesStack the stack size, or 0 for default 00084 * 00085 * @return the handle to the new Thread 00086 */ 00087 Thread(Runnable::Handle hRunnable, 00088 String::View vsName = String::null_string, 00089 ThreadGroup::Handle hGroup = NULL, 00090 size32_t cBytesStack = 0); 00091 00092 00093 // ----- Runnable interface --------------------------------------------- 00094 00095 public: 00096 /** 00097 * {@inheritDoc} 00098 */ 00099 virtual void run(); 00100 00101 00102 // ----- Thread interface ----------------------------------------------- 00103 00104 public: 00105 /** 00106 * Return the Thread's unique ID. 00107 * 00108 * No two live thread's will have the same ID and no thread will have 00109 * an id of 0. 00110 * 00111 * @return the Thread's unique ID. 00112 */ 00113 virtual int64_t getId() const; 00114 00115 /** 00116 * Return the Thread's current state. 00117 * 00118 * @return the Thread's current state 00119 */ 00120 virtual State getState() const; 00121 00122 /** 00123 * Return the Thread's name. 00124 * 00125 * @return the Thread's name 00126 */ 00127 virtual String::View getName() const; 00128 00129 /** 00130 * Return this thread's group, or NULL if the thread has terminated. 00131 * 00132 * @return this thread's group 00133 */ 00134 virtual ThreadGroup::Handle getThreadGroup(); 00135 00136 /** 00137 * Return this thread's group, or NULL if the thread has terminated. 00138 * 00139 * @return this thread's group 00140 */ 00141 virtual ThreadGroup::View getThreadGroup() const; 00142 00143 /** 00144 * Tests if this thread is alive. A thread is alive if it has 00145 * been started and has not yet died. 00146 * 00147 * @return <code>true</code> if this thread is alive; 00148 * <code>false</code> otherwise. 00149 */ 00150 virtual bool isAlive() const; 00151 00152 /** 00153 * Begin executing the Thread's runnable on a new system thread. 00154 * 00155 * This method may only be called once per Thread instance. 00156 * 00157 * @throw IllegalStateException if a called on a Thread which is not 00158 * in the state state_initial. 00159 */ 00160 virtual void start(); 00161 00162 /** 00163 * Request that the Thread stop executing. 00164 */ 00165 virtual void interrupt(); 00166 00167 /** 00168 * Return true iff the thread is interrupted. 00169 * 00170 * Note, Unlike Thread::interrupted() this does not check if the thread has timed-out. 00171 * 00172 * @return true iff the thread is interrupted 00173 */ 00174 virtual bool isInterrupted() const; 00175 00176 /** 00177 * Wait for the Thread to reach the state_terminated state. 00178 */ 00179 virtual void join() const; 00180 00181 /** 00182 * Wait for the Thread to reach the state_terminated state. 00183 * 00184 * @param cMillis the maximum duration to wait, or zero for infinite 00185 */ 00186 virtual void join(int64_t cMillis) const; 00187 00188 /** 00189 * Set the Thread's name. 00190 * 00191 * @param vsName the Thread's name 00192 */ 00193 virtual void setName(String::View vsName); 00194 00195 protected: 00196 /** 00197 * Called automatically on the thread prior to termination. 00198 * 00199 * Any class extending this Thread and overriding this method much 00200 * call this implementation to ensure that join() operations complete. 00201 */ 00202 virtual void onExit(); 00203 00204 /** 00205 * Instruct the thread to perform maintenance. 00206 */ 00207 virtual void scheduleMaintenance(Maintenance nMaintenance) const; 00208 00209 00210 // ----- static helper methods ------------------------------------------ 00211 00212 public: 00213 /** 00214 * Return the Thread on which the caller is executing. 00215 * 00216 * @return the caller's thread 00217 */ 00218 static Thread::Handle currentThread(); 00219 00220 /** 00221 * Return a stack trace for this thread. 00222 * 00223 * @param cTrim the number of frames to trim from the top of the stack 00224 * 00225 * @return an array of StackTraceElements describing as much of the 00226 * thread's stack as can be determined 00227 */ 00228 static ObjectArray::Handle getStackTrace(size32_t cTrim = 0); 00229 00230 /** 00231 * Format a stack trace. 00232 * 00233 * @param vaStack the array of StackTraceElements to output, or NULL 00234 * for the stack of the current thread 00235 */ 00236 static String::View formatStackTrace(ObjectArray::View vaStack); 00237 00238 /** 00239 * Return the stack trace of all known threads as a String. 00240 * 00241 * This is a blocking operation, while the calling thread waits for 00242 * all known threads to report their stack. 00243 * 00244 * @param cMillisTimeout the maximum amount of time to wait for all 00245 * threads to report their stacks, or -1 for 00246 * the system default of twice the interrupt 00247 * resolution 00248 * 00249 * @return the stack traces 00250 */ 00251 static String::View formatStacks(int64_t cMillisTimeout = -1); 00252 00253 /** 00254 * Return true iff the caller's thread has been interrupted, or timed out. 00255 * 00256 * The thread's interrupt state is reset as part of this operation. 00257 * 00258 * @return true iff the caller's thread has been interrupted 00259 */ 00260 static bool interrupted(); 00261 00262 /** 00263 * Pause the current thread for the specified duration. 00264 * 00265 * @param cMillis the duration to pause the thread for. 00266 * 00267 * @throw InterruptedException if the thread is interrupted while 00268 * sleeping. 00269 */ 00270 static void sleep(int64_t cMillis); 00271 00272 /** 00273 * Temporarily pause the current thread. 00274 */ 00275 static void yield(); 00276 00277 /** 00278 * Return the number of milliseconds before the calling thread will timeout. 00279 * 00280 * Note if the current thread is timed out then invoking this method will 00281 * also interrupt the thread. 00282 * 00283 * @return the number of remaining milliseconds, 0 if timed out, or Integer64::max_value if disabled. 00284 */ 00285 static int64_t remainingTimeoutMillis(); 00286 00287 /** 00288 * Return true if the calling thread is timed out. 00289 * 00290 * Note if the current thread is timed out then invoking this method will 00291 * also interrupt the thread. 00292 * 00293 * @return true if the calling thread is timed out 00294 */ 00295 static bool isTimedOut(); 00296 00297 protected: 00298 /** 00299 * Instruct all threads to perform maintenance. 00300 */ 00301 static void doGlobalMaintenance(Maintenance nMaintenance); 00302 00303 private: 00304 /** 00305 * Specify the thread's timeout 00306 */ 00307 void setTimeout(int64_t timeout); 00308 00309 /** 00310 * Return the thread's timeout. 00311 */ 00312 int64_t getTimeout() const; 00313 00314 00315 // ----- Object interface ----------------------------------------------- 00316 00317 public: 00318 /** 00319 * {@inheritDoc} 00320 * 00321 * If the associated Runnable implements the 00322 * coherence::util::Describable interface that content will be included 00323 * as well. 00324 */ 00325 virtual TypedHandle<const String> toString() const; 00326 00327 00328 // ----- data members --------------------------------------------------- 00329 00330 protected: 00331 /** 00332 * The thread's group. 00333 */ 00334 MemberHandle<ThreadGroup> m_hGroup; 00335 00336 /** 00337 * The inner runnable associated with this Thread. 00338 */ 00339 MemberHandle<Runnable> m_hRunnable; 00340 00341 /** 00342 * The thread's name. 00343 */ 00344 MemberView<String> m_vsName; 00345 00346 /** 00347 * The thread's description. 00348 */ 00349 FinalView<String> f_vsDescription; 00350 00351 /** 00352 * The configured stack size; 00353 */ 00354 size32_t m_cBytesStack; 00355 00356 /** 00357 * The current thread state. 00358 */ 00359 Volatile<int32_t> m_nState; 00360 00361 /** 00362 * Bit mask identifying required maintenance tasks. 00363 */ 00364 mutable int m_nMaintenanceMask; 00365 00366 /** 00367 * The thread's timeout value. Value which are greater or equal to zero are used to indicate 00368 * timeout timestamps. Negative values are relative timeouts which haven't yet been 00369 * realized into a timestamp. This allows for an optimization where we can avoid obtaining 00370 * the current time when "setting" the timeout, and defer it until we are about to block. 00371 */ 00372 int64_t m_lTimeout; 00373 00374 00375 // ----- friends -------------------------------------------------------- 00376 00377 friend void coh_thread_cleanup(Thread*); 00378 friend Thread* coh_thread_current(); 00379 friend class System; 00380 friend class TimeoutBlock; 00381 }; 00382 00383 COH_CLOSE_NAMESPACE2 00384 00385 #endif // COH_THREAD_HPP