From a9c1f3fdb4f7c7de0fe5e61ed0ecad7318137973 Mon Sep 17 00:00:00 2001 From: Tedd Hansen Date: Fri, 1 Feb 2008 20:12:25 +0000 Subject: Experimental Moved DotNetScriptEngine configuration to config file. Added option to share script execution threads between regions. --- .../Common/ScriptEngineBase/EventQueueManager.cs | 52 +++++++++++++++++++--- .../ScriptEngineBase/EventQueueThreadClass.cs | 6 ++- .../Common/ScriptEngineBase/ScriptEngine.cs | 6 +++ 3 files changed, 55 insertions(+), 9 deletions(-) (limited to 'OpenSim/Region/ScriptEngine/Common') diff --git a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueManager.cs b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueManager.cs index 70db724..730b63e 100644 --- a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueManager.cs +++ b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueManager.cs @@ -69,21 +69,25 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase /// /// List of threads processing event queue /// - private List eventQueueThreads = new List(); - private object eventQueueThreadsLock = new object(); + private List eventQueueThreads;// = new List(); + private object eventQueueThreadsLock;// = new object(); + + private static List staticEventQueueThreads;// = new List(); + private static object staticEventQueueThreadsLock;// = new object(); public object queueLock = new object(); // Mutex lock object /// /// How many threads to process queue with /// - private int numberOfThreads = 2; + private int numberOfThreads; /// /// Maximum time one function can use for execution before we perform a thread kill /// - private int maxFunctionExecutionTimems = 50; - private bool EnforceMaxExecutionTime = true; + private int maxFunctionExecutionTimems; + private bool EnforceMaxExecutionTime; + /// /// Queue containing events waiting to be executed @@ -138,6 +142,36 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase { m_ScriptEngine = _ScriptEngine; + + // Create thread pool list and lock object + // Determine from config if threads should be dedicated to regions or shared + if (m_ScriptEngine.ScriptConfigSource.GetBoolean("PrivateRegionThreads", false)) + { + // PRIVATE THREAD POOL PER REGION + eventQueueThreads = new List(); + eventQueueThreadsLock = new object(); + } + else + { + // SHARED THREAD POOL + // Crate the objects in statics + if (staticEventQueueThreads == null) + staticEventQueueThreads = new List(); + if (staticEventQueueThreadsLock == null) + staticEventQueueThreadsLock = new object(); + + // Create local reference to them + eventQueueThreads = staticEventQueueThreads; + eventQueueThreadsLock = staticEventQueueThreadsLock; + } + + numberOfThreads = m_ScriptEngine.ScriptConfigSource.GetInt("NumberOfScriptThreads", 2); + + maxFunctionExecutionTimems = m_ScriptEngine.ScriptConfigSource.GetInt("MaxEventExecutionTimeMs", 5000); + EnforceMaxExecutionTime = m_ScriptEngine.ScriptConfigSource.GetBoolean("EnforceMaxEventExecutionTime", false); + + + // Start function max exec time enforcement thread if (EnforceMaxExecutionTime) { @@ -150,9 +184,10 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase // // Start event queue processing threads (worker threads) // + lock (eventQueueThreadsLock) { - for (int ThreadCount = 0; ThreadCount <= numberOfThreads; ThreadCount++) + for (int ThreadCount = eventQueueThreads.Count; ThreadCount <= numberOfThreads; ThreadCount++) { StartNewThreadClass(); } @@ -315,7 +350,7 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase } } - private static void AbortThreadClass(EventQueueThreadClass threadClass) + private void AbortThreadClass(EventQueueThreadClass threadClass) { try { @@ -326,12 +361,15 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase Console.WriteLine("Could you please report this to Tedd:"); Console.WriteLine("Script thread execution timeout kill ended in exception: " + ex.ToString()); } + m_ScriptEngine.Log.Debug("DotNetEngine", "Killed script execution thread, count: " + eventQueueThreads.Count); } private void StartNewThreadClass() { EventQueueThreadClass eqtc = new EventQueueThreadClass(this); eventQueueThreads.Add(eqtc); + m_ScriptEngine.Log.Debug("DotNetEngine", "Started new script execution thread, count: " + eventQueueThreads.Count); + } } } \ No newline at end of file diff --git a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueThreadClass.cs b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueThreadClass.cs index ad79fbc..67cf0e2 100644 --- a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueThreadClass.cs +++ b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/EventQueueThreadClass.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Text; using System.Threading; using libsecondlife; +using Nini.Config; using OpenSim.Framework; using OpenSim.Region.Environment.Scenes.Scripting; @@ -16,7 +17,7 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase /// /// How many ms to sleep if queue is empty /// - private int nothingToDoSleepms = 50; + private int nothingToDoSleepms;// = 50; public DateTime LastExecutionStarted; public bool InExecution = false; @@ -28,6 +29,7 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase public EventQueueThreadClass(EventQueueManager eqm) { eventQueueManager = eqm; + nothingToDoSleepms = eqm.m_ScriptEngine.ScriptConfigSource.GetInt("SleepTimeIfNoScriptExecutionMs", 50); Start(); } @@ -183,7 +185,7 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase } catch (ThreadAbortException tae) { - throw tae; + eventQueueManager.m_ScriptEngine.Log.Notice("ScriptEngine", "ThreadAbortException while executing function."); } catch (Exception e) { diff --git a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/ScriptEngine.cs b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/ScriptEngine.cs index da0baba..8b64d3d 100644 --- a/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/ScriptEngine.cs +++ b/OpenSim/Region/ScriptEngine/Common/ScriptEngineBase/ScriptEngine.cs @@ -51,10 +51,15 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase public AppDomainManager m_AppDomainManager; public LSLLongCmdHandler m_LSLLongCmdHandler; + public IConfigSource ConfigSource; + public IConfig ScriptConfigSource; + public abstract string ScriptConfigSourceName { get; } + public ScriptManager GetScriptManager() { return _GetScriptManager(); } + public abstract ScriptManager _GetScriptManager(); private LogBase m_log; @@ -74,6 +79,7 @@ namespace OpenSim.Region.ScriptEngine.Common.ScriptEngineBase { World = Sceneworld; m_log = logger; + ScriptConfigSource = ConfigSource.Configs[ScriptConfigSourceName]; Log.Verbose("ScriptEngine", "DotNet & LSL ScriptEngine initializing"); -- cgit v1.1