From e87dfd48bf501a16ffd418138a5fff10e7de7c53 Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Mon, 11 Nov 2019 12:51:09 +0000 Subject: [PATCH] Yengine: we also need to cancel timer events in queue, because some bad scripts that do work on X --- .../ScriptEngine/Interfaces/IScriptEngine.cs | 1 + .../Api/Implementation/Plugins/Timer.cs | 3 +- .../Region/ScriptEngine/XEngine/XEngine.cs | 4 +++ .../Region/ScriptEngine/YEngine/XMREngine.cs | 13 +++++++- .../Region/ScriptEngine/YEngine/XMRInstRun.cs | 31 +++++++++++++++++++ 5 files changed, 50 insertions(+), 2 deletions(-) diff --git a/OpenSim/Region/ScriptEngine/Interfaces/IScriptEngine.cs b/OpenSim/Region/ScriptEngine/Interfaces/IScriptEngine.cs index 2e1dbbeada..fa20606173 100644 --- a/OpenSim/Region/ScriptEngine/Interfaces/IScriptEngine.cs +++ b/OpenSim/Region/ScriptEngine/Interfaces/IScriptEngine.cs @@ -54,6 +54,7 @@ namespace OpenSim.Region.ScriptEngine.Interfaces IScriptModule ScriptModule { get; } + void CancelScriptEvent(UUID itemID, string eventName); /// /// Post an event to a single script /// diff --git a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/Plugins/Timer.cs b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/Plugins/Timer.cs index cae1c14263..f8dea98eea 100644 --- a/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/Plugins/Timer.cs +++ b/OpenSim/Region/ScriptEngine/Shared/Api/Implementation/Plugins/Timer.cs @@ -110,8 +110,9 @@ namespace OpenSim.Region.ScriptEngine.Shared.Api.Plugins string key = MakeTimerKey(m_localID, m_itemID); lock (TimerListLock) { - if (Timers.ContainsKey(key)) + if (Timers.TryGetValue(key, out TimerInfo ts)) { + m_CmdManager.m_ScriptEngine.CancelScriptEvent(ts.itemID, "timer"); Timers.Remove(key); } } diff --git a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs index af82dc8890..9e47530304 100755 --- a/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs +++ b/OpenSim/Region/ScriptEngine/XEngine/XEngine.cs @@ -1794,6 +1794,10 @@ namespace OpenSim.Region.ScriptEngine.XEngine return result; } + public void CancelScriptEvent(UUID itemID, string eventName) + { + } + /// /// Post an event to a single script /// diff --git a/OpenSim/Region/ScriptEngine/YEngine/XMREngine.cs b/OpenSim/Region/ScriptEngine/YEngine/XMREngine.cs index f30ecc8bdd..d2b4ebd7b6 100644 --- a/OpenSim/Region/ScriptEngine/YEngine/XMREngine.cs +++ b/OpenSim/Region/ScriptEngine/YEngine/XMREngine.cs @@ -854,7 +854,7 @@ namespace OpenSim.Region.ScriptEngine.Yengine public bool PostScriptEvent(UUID itemID, EventParams parms) { XMRInstance instance = GetInstance(itemID); - if(instance == null) + if (instance == null) return false; TraceCalls("[YEngine]: YEngine.PostScriptEvent({0},{1})", itemID.ToString(), parms.EventName); @@ -863,6 +863,17 @@ namespace OpenSim.Region.ScriptEngine.Yengine return true; } + public void CancelScriptEvent(UUID itemID, string eventName) + { + XMRInstance instance = GetInstance(itemID); + if (instance == null) + return; + + TraceCalls("[YEngine]: YEngine.CancelScriptEvent({0},{1})", itemID.ToString(), eventName); + + instance.CancelEvent(eventName); + } + // Events targeted at all scripts in the given prim. // localID = which prim // parms = event to post diff --git a/OpenSim/Region/ScriptEngine/YEngine/XMRInstRun.cs b/OpenSim/Region/ScriptEngine/YEngine/XMRInstRun.cs index 30e397b105..57b9e2d7ab 100644 --- a/OpenSim/Region/ScriptEngine/YEngine/XMRInstRun.cs +++ b/OpenSim/Region/ScriptEngine/YEngine/XMRInstRun.cs @@ -237,6 +237,37 @@ namespace OpenSim.Region.ScriptEngine.Yengine } } + public void CancelEvent(string eventName) + { + ScriptEventCode evc; + try + { + evc = (ScriptEventCode)Enum.Parse(typeof(ScriptEventCode), eventName); + } + catch + { + return; + } + + lock (m_QueueLock) + { + if(m_EventQueue.Count == 0) + return; + + LinkedListNode lln2 = null; + for (lln2 = m_EventQueue.First; lln2 != null; lln2 = lln2.Next) + { + EventParams evt2 = lln2.Value; + if(evt2.EventName.Equals(eventName)) + { + m_EventQueue.Remove(lln2); + if (evc >= 0 && m_EventCounts[(int)evc] > 0) + m_EventCounts[(int)evc]--; + } + } + } + } + // This is called in the script thread to step script until it calls // CheckRun(). It returns what the instance's next state should be, // ONSLEEPQ, ONYIELDQ, SUSPENDED or FINISHED.