From 00130841db6756caf62207dca3b56efc87b5ea0d Mon Sep 17 00:00:00 2001 From: Melanie Date: Tue, 3 Nov 2009 20:23:50 +0000 Subject: Remove parallel loading from XEngine, but retain the new design where all scripts are loaded from the same thread, rather than launching a new one for each script. This is only marginally slower, but avoids the race condition that led to script engine failure. --- OpenSim/Region/ScriptEngine/XEngine/XEngine.cs | 27 ++++++++++++++++++-------- 1 file changed, 19 insertions(+), 8 deletions(-) (limited to 'OpenSim/Region/ScriptEngine/XEngine') diff --git a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs index b0fce75..a60c0ba 100644 --- a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs +++ b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs @@ -51,7 +51,6 @@ using OpenSim.Region.ScriptEngine.Shared.Instance; using OpenSim.Region.ScriptEngine.Interfaces; using ScriptCompileQueue = OpenSim.Framework.LocklessQueue; -using Parallel = OpenSim.Framework.Parallel; namespace OpenSim.Region.ScriptEngine.XEngine { @@ -494,7 +493,16 @@ namespace OpenSim.Region.ScriptEngine.XEngine if (m_CurrentCompile == null) { - m_CurrentCompile = m_ThreadPool.QueueWorkItem(DoOnRezScriptQueue, null); + // NOTE: Although we use a lockless queue, the lock here + // is required. It ensures that there are never two + // compile threads running, which, due to a race + // conndition, might otherwise happen + // + lock (m_CompileQueue) + { + if (m_CurrentCompile == null) + m_CurrentCompile = m_ThreadPool.QueueWorkItem(DoOnRezScriptQueue, null); + } } } } @@ -514,16 +522,19 @@ namespace OpenSim.Region.ScriptEngine.XEngine } } - List compiles = new List(); object[] o; while (m_CompileQueue.Dequeue(out o)) + DoOnRezScript(o); + + // NOTE: Despite having a lockless queue, this lock is required + // to make sure there is never no compile thread while there + // are still scripts to compile. This could otherwise happen + // due to a race condition + // + lock (m_CompileQueue) { - compiles.Add(o); + m_CurrentCompile = null; } - - Parallel.For(0, compiles.Count, delegate(int i) { DoOnRezScript(compiles[i]); }); - - m_CurrentCompile = null; m_Scene.EventManager.TriggerEmptyScriptCompileQueue(m_ScriptFailCount, m_ScriptErrorMessage); m_ScriptFailCount = 0; -- cgit v1.1