From 523213060b315c677bf3142b5d2925460a49c9ed Mon Sep 17 00:00:00 2001
From: Justin Clark-Casey (justincc)
Date: Thu, 13 Dec 2012 21:02:55 +0000
Subject: Add WaitForEventCompletionOnScriptStop [XEngine] config param to
OpenSimDefaults.ini to allow change of the wait time for an event to complete
on script removal before aborting its thread
Default is 1000, as has previously been the case.
This parameter exists for further debug work concerning mono 2.10 crashes that may be related to locks not being removed on Thread.Abort
---
OpenSim/Region/ScriptEngine/XEngine/XEngine.cs | 34 ++++++++++++++++++--------
1 file changed, 24 insertions(+), 10 deletions(-)
(limited to 'OpenSim/Region/ScriptEngine')
diff --git a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs
index 828f2fb..1dd50c7 100644
--- a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs
+++ b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs
@@ -107,6 +107,24 @@ namespace OpenSim.Region.ScriptEngine.XEngine
private IXmlRpcRouter m_XmlRpcRouter;
private int m_EventLimit;
private bool m_KillTimedOutScripts;
+
+ ///
+ /// Number of milliseconds we will wait for a script event to complete on script stop before we forcibly abort
+ /// its thread.
+ ///
+ ///
+ /// It appears that if a script thread is aborted whilst it is holding ReaderWriterLockSlim (possibly the write
+ /// lock) then the lock is not properly released. This causes mono 2.6, 2.10 and possibly
+ /// later to crash, sometimes with symptoms such as a leap to 100% script usage and a vm thead dump showing
+ /// all threads waiting on release of ReaderWriterLockSlim write thread which none of the threads listed
+ /// actually hold.
+ ///
+ /// Pausing for event completion reduces the risk of this happening. However, it may be that aborting threads
+ /// is not a mono issue per se but rather a risky activity in itself in an AppDomain that is not immediately
+ /// shutting down.
+ ///
+ private int m_WaitForEventCompletionOnScriptStop = 1000;
+
private string m_ScriptEnginesPath = null;
private ExpiringCache m_runFlags = new ExpiringCache();
@@ -249,6 +267,9 @@ namespace OpenSim.Region.ScriptEngine.XEngine
m_EventLimit = m_ScriptConfig.GetInt("EventLimit", 30);
m_KillTimedOutScripts = m_ScriptConfig.GetBoolean("KillTimedOutScripts", false);
m_SaveTime = m_ScriptConfig.GetInt("SaveInterval", 120) * 1000;
+ m_WaitForEventCompletionOnScriptStop
+ = m_ScriptConfig.GetInt("WaitForEventCompletionOnScriptStop", m_WaitForEventCompletionOnScriptStop);
+
m_ScriptEnginesPath = m_ScriptConfig.GetString("ScriptEnginesPath", "ScriptEngines");
m_Prio = ThreadPriority.BelowNormal;
@@ -1335,9 +1356,7 @@ namespace OpenSim.Region.ScriptEngine.XEngine
instance.ClearQueue();
- // Give the script some time to finish processing its last event. Simply aborting the script thread can
- // cause issues on mono 2.6, 2.10 and possibly later where locks are not released properly on abort.
- instance.Stop(1000);
+ instance.Stop(m_WaitForEventCompletionOnScriptStop);
// bool objectRemoved = false;
@@ -1687,16 +1706,11 @@ namespace OpenSim.Region.ScriptEngine.XEngine
public void StopScript(UUID itemID)
{
IScriptInstance instance = GetInstance(itemID);
+
if (instance != null)
- {
- // Give the script some time to finish processing its last event. Simply aborting the script thread can
- // cause issues on mono 2.6, 2.10 and possibly later where locks are not released properly on abort.
- instance.Stop(1000);
- }
+ instance.Stop(m_WaitForEventCompletionOnScriptStop);
else
- {
m_runFlags.AddOrUpdate(itemID, false, 240);
- }
}
public DetectParams GetDetectParams(UUID itemID, int idx)
--
cgit v1.1