aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Framework/Monitoring/Watchdog.cs
diff options
context:
space:
mode:
authorJustin Clark-Casey (justincc)2014-09-05 23:20:59 +0100
committerJustin Clark-Casey (justincc)2014-09-05 23:20:59 +0100
commit41f2f3132bdcbfb8020c7fd6e5f3b7e48c75b1cf (patch)
treec3f55715685c213673697e09d234e82616f0dc9c /OpenSim/Framework/Monitoring/Watchdog.cs
parentMake LLUDP output queue refill thread active by default, since load tests hav... (diff)
downloadopensim-SC-41f2f3132bdcbfb8020c7fd6e5f3b7e48c75b1cf.zip
opensim-SC-41f2f3132bdcbfb8020c7fd6e5f3b7e48c75b1cf.tar.gz
opensim-SC-41f2f3132bdcbfb8020c7fd6e5f3b7e48c75b1cf.tar.bz2
opensim-SC-41f2f3132bdcbfb8020c7fd6e5f3b7e48c75b1cf.tar.xz
For monitoring purposes, start non-timeout tasks (which do not currently use a threadpool) via Watchdog.RunInThread() rather than Util.RunThreadNoTimeout()
The functionality is the same but this allow us to monitor such tasks via "show threads" and abort them for test purposes, etc. Also extends thread names to provide more info (e.g. SendInitialDataToClient says what client the task is for).
Diffstat (limited to '')
-rw-r--r--OpenSim/Framework/Monitoring/Watchdog.cs60
1 files changed, 49 insertions, 11 deletions
diff --git a/OpenSim/Framework/Monitoring/Watchdog.cs b/OpenSim/Framework/Monitoring/Watchdog.cs
index 427ed7b..e9e7bd2 100644
--- a/OpenSim/Framework/Monitoring/Watchdog.cs
+++ b/OpenSim/Framework/Monitoring/Watchdog.cs
@@ -187,15 +187,16 @@ namespace OpenSim.Framework.Monitoring
187 /// <param name="priority">Priority to run the thread at</param> 187 /// <param name="priority">Priority to run the thread at</param>
188 /// <param name="isBackground">True to run this thread as a background thread, otherwise false</param> 188 /// <param name="isBackground">True to run this thread as a background thread, otherwise false</param>
189 /// <param name="alarmIfTimeout">Trigger an alarm function is we have timed out</param> 189 /// <param name="alarmIfTimeout">Trigger an alarm function is we have timed out</param>
190 /// <param name="log">If true then creation of thread is logged.</param>
190 /// <returns>The newly created Thread object</returns> 191 /// <returns>The newly created Thread object</returns>
191 public static Thread StartThread( 192 public static Thread StartThread(
192 ThreadStart start, string name, ThreadPriority priority, bool isBackground, bool alarmIfTimeout) 193 ThreadStart start, string name, ThreadPriority priority, bool isBackground, bool alarmIfTimeout, bool log = true)
193 { 194 {
194 return StartThread(start, name, priority, isBackground, alarmIfTimeout, null, DEFAULT_WATCHDOG_TIMEOUT_MS); 195 return StartThread(start, name, priority, isBackground, alarmIfTimeout, null, DEFAULT_WATCHDOG_TIMEOUT_MS, log);
195 } 196 }
196 197
197 /// <summary> 198 /// <summary>
198 /// Start a new thread that is tracked by the watchdog timer 199 /// Start a new thread that is tracked by the watchdog
199 /// </summary> 200 /// </summary>
200 /// <param name="start">The method that will be executed in a new thread</param> 201 /// <param name="start">The method that will be executed in a new thread</param>
201 /// <param name="name">A name to give to the new thread</param> 202 /// <param name="name">A name to give to the new thread</param>
@@ -208,10 +209,11 @@ namespace OpenSim.Framework.Monitoring
208 /// Normally, this will just return some useful debugging information. 209 /// Normally, this will just return some useful debugging information.
209 /// </param> 210 /// </param>
210 /// <param name="timeout">Number of milliseconds to wait until we issue a warning about timeout.</param> 211 /// <param name="timeout">Number of milliseconds to wait until we issue a warning about timeout.</param>
212 /// <param name="log">If true then creation of thread is logged.</param>
211 /// <returns>The newly created Thread object</returns> 213 /// <returns>The newly created Thread object</returns>
212 public static Thread StartThread( 214 public static Thread StartThread(
213 ThreadStart start, string name, ThreadPriority priority, bool isBackground, 215 ThreadStart start, string name, ThreadPriority priority, bool isBackground,
214 bool alarmIfTimeout, Func<string> alarmMethod, int timeout) 216 bool alarmIfTimeout, Func<string> alarmMethod, int timeout, bool log = true)
215 { 217 {
216 Thread thread = new Thread(start); 218 Thread thread = new Thread(start);
217 thread.Name = name; 219 thread.Name = name;
@@ -222,8 +224,9 @@ namespace OpenSim.Framework.Monitoring
222 = new ThreadWatchdogInfo(thread, timeout) 224 = new ThreadWatchdogInfo(thread, timeout)
223 { AlarmIfTimeout = alarmIfTimeout, AlarmMethod = alarmMethod }; 225 { AlarmIfTimeout = alarmIfTimeout, AlarmMethod = alarmMethod };
224 226
225 m_log.DebugFormat( 227 if (log)
226 "[WATCHDOG]: Started tracking thread {0}, ID {1}", twi.Thread.Name, twi.Thread.ManagedThreadId); 228 m_log.DebugFormat(
229 "[WATCHDOG]: Started tracking thread {0}, ID {1}", twi.Thread.Name, twi.Thread.ManagedThreadId);
227 230
228 lock (m_threads) 231 lock (m_threads)
229 m_threads.Add(twi.Thread.ManagedThreadId, twi); 232 m_threads.Add(twi.Thread.ManagedThreadId, twi);
@@ -234,6 +237,39 @@ namespace OpenSim.Framework.Monitoring
234 } 237 }
235 238
236 /// <summary> 239 /// <summary>
240 /// Run the callback in a new thread immediately. If the thread exits with an exception log it but do
241 /// not propogate it.
242 /// </summary>
243 /// <param name="callback">Code for the thread to execute.</param>
244 /// <param name="name">Name of the thread</param>
245 /// <param name="obj">Object to pass to the thread.</param>
246 public static void RunInThread(WaitCallback callback, string name, object obj, bool log = false)
247 {
248 if (Util.FireAndForgetMethod == FireAndForgetMethod.RegressionTest)
249 {
250 Culture.SetCurrentCulture();
251 callback(obj);
252 return;
253 }
254
255 ThreadStart ts = new ThreadStart(delegate()
256 {
257 try
258 {
259 Culture.SetCurrentCulture();
260 callback(obj);
261 Watchdog.RemoveThread(log:false);
262 }
263 catch (Exception e)
264 {
265 m_log.Error(string.Format("[WATCHDOG]: Exception in thread {0}.", name), e);
266 }
267 });
268
269 StartThread(ts, name, ThreadPriority.Normal, true, false, log:log);
270 }
271
272 /// <summary>
237 /// Marks the current thread as alive 273 /// Marks the current thread as alive
238 /// </summary> 274 /// </summary>
239 public static void UpdateThread() 275 public static void UpdateThread()
@@ -244,24 +280,26 @@ namespace OpenSim.Framework.Monitoring
244 /// <summary> 280 /// <summary>
245 /// Stops watchdog tracking on the current thread 281 /// Stops watchdog tracking on the current thread
246 /// </summary> 282 /// </summary>
283 /// <param name="log">If true then normal events in thread removal are not logged.</param>
247 /// <returns> 284 /// <returns>
248 /// True if the thread was removed from the list of tracked 285 /// True if the thread was removed from the list of tracked
249 /// threads, otherwise false 286 /// threads, otherwise false
250 /// </returns> 287 /// </returns>
251 public static bool RemoveThread() 288 public static bool RemoveThread(bool log = true)
252 { 289 {
253 return RemoveThread(Thread.CurrentThread.ManagedThreadId); 290 return RemoveThread(Thread.CurrentThread.ManagedThreadId, log);
254 } 291 }
255 292
256 private static bool RemoveThread(int threadID) 293 private static bool RemoveThread(int threadID, bool log = true)
257 { 294 {
258 lock (m_threads) 295 lock (m_threads)
259 { 296 {
260 ThreadWatchdogInfo twi; 297 ThreadWatchdogInfo twi;
261 if (m_threads.TryGetValue(threadID, out twi)) 298 if (m_threads.TryGetValue(threadID, out twi))
262 { 299 {
263 m_log.DebugFormat( 300 if (log)
264 "[WATCHDOG]: Removing thread {0}, ID {1}", twi.Thread.Name, twi.Thread.ManagedThreadId); 301 m_log.DebugFormat(
302 "[WATCHDOG]: Removing thread {0}, ID {1}", twi.Thread.Name, twi.Thread.ManagedThreadId);
265 303
266 twi.Cleanup(); 304 twi.Cleanup();
267 m_threads.Remove(threadID); 305 m_threads.Remove(threadID);