From 28d1dbfee4256a97744ed1cebe21971adf5fdaef Mon Sep 17 00:00:00 2001
From: Justin Clark-Casey (justincc)
Date: Fri, 21 Nov 2014 01:08:58 +0000
Subject: Move conditionals which control whether a task is placed in the
JobEngine inside Watchdog.RunJob() (renamed from RunWhenPossible) and
generalize them.
---
OpenSim/Framework/Monitoring/Watchdog.cs | 39 ++++++++++++++++++++++++++++++--
1 file changed, 37 insertions(+), 2 deletions(-)
(limited to 'OpenSim/Framework/Monitoring')
diff --git a/OpenSim/Framework/Monitoring/Watchdog.cs b/OpenSim/Framework/Monitoring/Watchdog.cs
index ebbf095..0feec7c 100644
--- a/OpenSim/Framework/Monitoring/Watchdog.cs
+++ b/OpenSim/Framework/Monitoring/Watchdog.cs
@@ -454,7 +454,38 @@ namespace OpenSim.Framework.Monitoring
m_watchdogTimer.Start();
}
- public static void RunWhenPossible(string jobType, WaitCallback callback, string name, object obj, bool log = false)
+ ///
+ /// Run a job.
+ ///
+ ///
+ /// This differs from direct scheduling (e.g. Util.FireAndForget) in that a job can be run in the job
+ /// engine if it is running, where all jobs are currently performed in sequence on a single thread. This is
+ /// to prevent observed overload and server freeze problems when there are hundreds of connections which all attempt to
+ /// perform work at once (e.g. in conference situations). With lower numbers of connections, the small
+ /// delay in performing jobs in sequence rather than concurrently has not been notiecable in testing, though a future more
+ /// sophisticated implementation could perform jobs concurrently when the server is under low load.
+ ///
+ /// However, be advised that some callers of this function rely on all jobs being performed in sequence if any
+ /// jobs are performed in sequence (i.e. if jobengine is active or not). Therefore, expanding the jobengine
+ /// beyond a single thread will require considerable thought.
+ ///
+ /// Also, any jobs submitted must be guaranteed to complete within a reasonable timeframe (e.g. they cannot
+ /// incorporate a network delay with a long timeout). At the moment, work that could suffer such issues
+ /// should still be run directly with RunInThread(), Util.FireAndForget(), etc. This is another area where
+ /// the job engine could be improved and so CPU utilization improved by better management of concurrency within
+ /// OpenSimulator.
+ ///
+ /// General classification for the job (e.g. "RezAttachments").
+ /// Callback for job.
+ /// Specific name of job (e.g. "RezAttachments for Joe Bloggs"
+ /// Object to pass to callback when run
+ /// If set to true then the job may be run in ths calling thread.
+ /// If the true then the job must never timeout.
+ /// If set to true then extra logging is performed.
+ public static void RunJob(
+ string jobType, WaitCallback callback, string name, object obj,
+ bool canRunInThisThread = false, bool mustNotTimeout = false,
+ bool log = false)
{
if (Util.FireAndForgetMethod == FireAndForgetMethod.RegressionTest)
{
@@ -465,8 +496,12 @@ namespace OpenSim.Framework.Monitoring
if (JobEngine.IsRunning)
JobEngine.QueueRequest(name, callback, obj);
- else
+ else if (canRunInThisThread)
+ callback(obj);
+ else if (mustNotTimeout)
RunInThread(callback, name, obj, log);
+ else
+ Util.FireAndForget(callback, obj, name);
}
}
}
\ No newline at end of file
--
cgit v1.1