diff options
Diffstat (limited to 'OpenSim/Region/ScriptEngine/DotNetEngine/ScriptManager.cs')
-rw-r--r-- | OpenSim/Region/ScriptEngine/DotNetEngine/ScriptManager.cs | 816 |
1 files changed, 408 insertions, 408 deletions
diff --git a/OpenSim/Region/ScriptEngine/DotNetEngine/ScriptManager.cs b/OpenSim/Region/ScriptEngine/DotNetEngine/ScriptManager.cs index 055acc4..ec50b93 100644 --- a/OpenSim/Region/ScriptEngine/DotNetEngine/ScriptManager.cs +++ b/OpenSim/Region/ScriptEngine/DotNetEngine/ScriptManager.cs | |||
@@ -1,408 +1,408 @@ | |||
1 | /* | 1 | /* |
2 | * Copyright (c) Contributors, http://opensimulator.org/ | 2 | * Copyright (c) Contributors, http://opensimulator.org/ |
3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. | 3 | * See CONTRIBUTORS.TXT for a full list of copyright holders. |
4 | * | 4 | * |
5 | * Redistribution and use in source and binary forms, with or without | 5 | * Redistribution and use in source and binary forms, with or without |
6 | * modification, are permitted provided that the following conditions are met: | 6 | * modification, are permitted provided that the following conditions are met: |
7 | * * Redistributions of source code must retain the above copyright | 7 | * * Redistributions of source code must retain the above copyright |
8 | * notice, this list of conditions and the following disclaimer. | 8 | * notice, this list of conditions and the following disclaimer. |
9 | * * Redistributions in binary form must reproduce the above copyright | 9 | * * Redistributions in binary form must reproduce the above copyright |
10 | * notice, this list of conditions and the following disclaimer in the | 10 | * notice, this list of conditions and the following disclaimer in the |
11 | * documentation and/or other materials provided with the distribution. | 11 | * documentation and/or other materials provided with the distribution. |
12 | * * Neither the name of the OpenSim Project nor the | 12 | * * Neither the name of the OpenSim Project nor the |
13 | * names of its contributors may be used to endorse or promote products | 13 | * names of its contributors may be used to endorse or promote products |
14 | * derived from this software without specific prior written permission. | 14 | * derived from this software without specific prior written permission. |
15 | * | 15 | * |
16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS AND ANY | 16 | * THIS SOFTWARE IS PROVIDED BY THE DEVELOPERS ``AS IS AND ANY |
17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED | 17 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE | 18 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY | 19 | * DISCLAIMED. IN NO EVENT SHALL THE CONTRIBUTORS BE LIABLE FOR ANY |
20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES | 20 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; | 21 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND | 22 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 23 | * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS | 24 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 25 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
26 | * | 26 | * |
27 | */ | 27 | */ |
28 | /* Original code: Tedd Hansen */ | 28 | /* Original code: Tedd Hansen */ |
29 | using System; | 29 | using System; |
30 | using System.Collections.Generic; | 30 | using System.Collections.Generic; |
31 | using System.Text; | 31 | using System.Text; |
32 | using System.Threading; | 32 | using System.Threading; |
33 | using System.Reflection; | 33 | using System.Reflection; |
34 | using System.Runtime.Remoting; | 34 | using System.Runtime.Remoting; |
35 | using System.Runtime.Serialization; | 35 | using System.Runtime.Serialization; |
36 | using System.Runtime.Serialization.Formatters.Binary; | 36 | using System.Runtime.Serialization.Formatters.Binary; |
37 | using OpenSim.Region.Environment.Scenes; | 37 | using OpenSim.Region.Environment.Scenes; |
38 | using OpenSim.Region.Environment.Scenes.Scripting; | 38 | using OpenSim.Region.Environment.Scenes.Scripting; |
39 | using OpenSim.Region.ScriptEngine.DotNetEngine.Compiler; | 39 | using OpenSim.Region.ScriptEngine.DotNetEngine.Compiler; |
40 | using OpenSim.Region.ScriptEngine.DotNetEngine.Compiler.LSL; | 40 | using OpenSim.Region.ScriptEngine.DotNetEngine.Compiler.LSL; |
41 | using OpenSim.Region.ScriptEngine.Common; | 41 | using OpenSim.Region.ScriptEngine.Common; |
42 | using libsecondlife; | 42 | using libsecondlife; |
43 | 43 | ||
44 | 44 | ||
45 | namespace OpenSim.Region.ScriptEngine.DotNetEngine | 45 | namespace OpenSim.Region.ScriptEngine.DotNetEngine |
46 | { | 46 | { |
47 | /// <summary> | 47 | /// <summary> |
48 | /// Loads scripts | 48 | /// Loads scripts |
49 | /// Compiles them if necessary | 49 | /// Compiles them if necessary |
50 | /// Execute functions for EventQueueManager (Sends them to script on other AppDomain for execution) | 50 | /// Execute functions for EventQueueManager (Sends them to script on other AppDomain for execution) |
51 | /// </summary> | 51 | /// </summary> |
52 | [Serializable] | 52 | [Serializable] |
53 | public class ScriptManager | 53 | public class ScriptManager |
54 | { | 54 | { |
55 | #region Declares | 55 | #region Declares |
56 | private Thread scriptLoadUnloadThread; | 56 | private Thread scriptLoadUnloadThread; |
57 | private int scriptLoadUnloadThread_IdleSleepms = 100; | 57 | private int scriptLoadUnloadThread_IdleSleepms = 100; |
58 | private Queue<LoadStruct> loadQueue = new Queue<LoadStruct>(); | 58 | private Queue<LoadStruct> loadQueue = new Queue<LoadStruct>(); |
59 | private Queue<UnloadStruct> unloadQueue = new Queue<UnloadStruct>(); | 59 | private Queue<UnloadStruct> unloadQueue = new Queue<UnloadStruct>(); |
60 | private struct LoadStruct | 60 | private struct LoadStruct |
61 | { | 61 | { |
62 | public uint localID; | 62 | public uint localID; |
63 | public LLUUID itemID; | 63 | public LLUUID itemID; |
64 | public string script; | 64 | public string script; |
65 | } | 65 | } |
66 | private struct UnloadStruct | 66 | private struct UnloadStruct |
67 | { | 67 | { |
68 | public uint localID; | 68 | public uint localID; |
69 | public LLUUID itemID; | 69 | public LLUUID itemID; |
70 | } | 70 | } |
71 | 71 | ||
72 | // Object<string, Script<string, script>> | 72 | // Object<string, Script<string, script>> |
73 | // IMPORTANT: Types and MemberInfo-derived objects require a LOT of memory. | 73 | // IMPORTANT: Types and MemberInfo-derived objects require a LOT of memory. |
74 | // Instead use RuntimeTypeHandle, RuntimeFieldHandle and RunTimeHandle (IntPtr) instead! | 74 | // Instead use RuntimeTypeHandle, RuntimeFieldHandle and RunTimeHandle (IntPtr) instead! |
75 | internal Dictionary<uint, Dictionary<LLUUID, LSL_BaseClass>> Scripts = new Dictionary<uint, Dictionary<LLUUID, LSL_BaseClass>>(); | 75 | internal Dictionary<uint, Dictionary<LLUUID, LSL_BaseClass>> Scripts = new Dictionary<uint, Dictionary<LLUUID, LSL_BaseClass>>(); |
76 | public Scene World | 76 | public Scene World |
77 | { | 77 | { |
78 | get | 78 | get |
79 | { | 79 | { |
80 | return m_scriptEngine.World; | 80 | return m_scriptEngine.World; |
81 | } | 81 | } |
82 | } | 82 | } |
83 | #endregion | 83 | #endregion |
84 | #region Object init/shutdown | 84 | #region Object init/shutdown |
85 | private ScriptEngine m_scriptEngine; | 85 | private ScriptEngine m_scriptEngine; |
86 | public ScriptManager(ScriptEngine scriptEngine) | 86 | public ScriptManager(ScriptEngine scriptEngine) |
87 | { | 87 | { |
88 | m_scriptEngine = scriptEngine; | 88 | m_scriptEngine = scriptEngine; |
89 | AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(CurrentDomain_AssemblyResolve); | 89 | AppDomain.CurrentDomain.AssemblyResolve += new ResolveEventHandler(CurrentDomain_AssemblyResolve); |
90 | scriptLoadUnloadThread = new Thread(ScriptLoadUnloadThreadLoop); | 90 | scriptLoadUnloadThread = new Thread(ScriptLoadUnloadThreadLoop); |
91 | scriptLoadUnloadThread.Name = "ScriptLoadUnloadThread"; | 91 | scriptLoadUnloadThread.Name = "ScriptLoadUnloadThread"; |
92 | scriptLoadUnloadThread.IsBackground = true; | 92 | scriptLoadUnloadThread.IsBackground = true; |
93 | scriptLoadUnloadThread.Priority = ThreadPriority.BelowNormal; | 93 | scriptLoadUnloadThread.Priority = ThreadPriority.BelowNormal; |
94 | scriptLoadUnloadThread.Start(); | 94 | scriptLoadUnloadThread.Start(); |
95 | 95 | ||
96 | } | 96 | } |
97 | ~ScriptManager () | 97 | ~ScriptManager () |
98 | { | 98 | { |
99 | // Abort load/unload thread | 99 | // Abort load/unload thread |
100 | try | 100 | try |
101 | { | 101 | { |
102 | if (scriptLoadUnloadThread != null) | 102 | if (scriptLoadUnloadThread != null) |
103 | { | 103 | { |
104 | if (scriptLoadUnloadThread.IsAlive == true) | 104 | if (scriptLoadUnloadThread.IsAlive == true) |
105 | { | 105 | { |
106 | scriptLoadUnloadThread.Abort(); | 106 | scriptLoadUnloadThread.Abort(); |
107 | scriptLoadUnloadThread.Join(); | 107 | scriptLoadUnloadThread.Join(); |
108 | } | 108 | } |
109 | } | 109 | } |
110 | } | 110 | } |
111 | catch | 111 | catch |
112 | { | 112 | { |
113 | } | 113 | } |
114 | } | 114 | } |
115 | #endregion | 115 | #endregion |
116 | #region Load / Unload scripts (Thread loop) | 116 | #region Load / Unload scripts (Thread loop) |
117 | private void ScriptLoadUnloadThreadLoop() | 117 | private void ScriptLoadUnloadThreadLoop() |
118 | { | 118 | { |
119 | try | 119 | try |
120 | { | 120 | { |
121 | while (true) | 121 | while (true) |
122 | { | 122 | { |
123 | if (loadQueue.Count == 0 && unloadQueue.Count == 0) | 123 | if (loadQueue.Count == 0 && unloadQueue.Count == 0) |
124 | Thread.Sleep(scriptLoadUnloadThread_IdleSleepms); | 124 | Thread.Sleep(scriptLoadUnloadThread_IdleSleepms); |
125 | 125 | ||
126 | if (loadQueue.Count > 0) | 126 | if (loadQueue.Count > 0) |
127 | { | 127 | { |
128 | LoadStruct item = loadQueue.Dequeue(); | 128 | LoadStruct item = loadQueue.Dequeue(); |
129 | _StartScript(item.localID, item.itemID, item.script); | 129 | _StartScript(item.localID, item.itemID, item.script); |
130 | } | 130 | } |
131 | 131 | ||
132 | if (unloadQueue.Count > 0) | 132 | if (unloadQueue.Count > 0) |
133 | { | 133 | { |
134 | UnloadStruct item = unloadQueue.Dequeue(); | 134 | UnloadStruct item = unloadQueue.Dequeue(); |
135 | _StopScript(item.localID, item.itemID); | 135 | _StopScript(item.localID, item.itemID); |
136 | } | 136 | } |
137 | 137 | ||
138 | 138 | ||
139 | 139 | ||
140 | } | 140 | } |
141 | } | 141 | } |
142 | catch (ThreadAbortException tae) | 142 | catch (ThreadAbortException tae) |
143 | { | 143 | { |
144 | string a = tae.ToString(); | 144 | string a = tae.ToString(); |
145 | a = ""; | 145 | a = ""; |
146 | // Expected | 146 | // Expected |
147 | } | 147 | } |
148 | 148 | ||
149 | } | 149 | } |
150 | #endregion | 150 | #endregion |
151 | #region Helper functions | 151 | #region Helper functions |
152 | private static Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args) | 152 | private static Assembly CurrentDomain_AssemblyResolve(object sender, ResolveEventArgs args) |
153 | { | 153 | { |
154 | 154 | ||
155 | //Console.WriteLine("ScriptManager.CurrentDomain_AssemblyResolve: " + args.Name); | 155 | //Console.WriteLine("ScriptManager.CurrentDomain_AssemblyResolve: " + args.Name); |
156 | return Assembly.GetExecutingAssembly().FullName == args.Name ? Assembly.GetExecutingAssembly() : null; | 156 | return Assembly.GetExecutingAssembly().FullName == args.Name ? Assembly.GetExecutingAssembly() : null; |
157 | 157 | ||
158 | } | 158 | } |
159 | 159 | ||
160 | 160 | ||
161 | #endregion | 161 | #endregion |
162 | #region Internal functions to keep track of script | 162 | #region Internal functions to keep track of script |
163 | internal Dictionary<LLUUID, LSL_BaseClass>.KeyCollection GetScriptKeys(uint localID) | 163 | internal Dictionary<LLUUID, LSL_BaseClass>.KeyCollection GetScriptKeys(uint localID) |
164 | { | 164 | { |
165 | if (Scripts.ContainsKey(localID) == false) | 165 | if (Scripts.ContainsKey(localID) == false) |
166 | return null; | 166 | return null; |
167 | 167 | ||
168 | Dictionary<LLUUID, LSL_BaseClass> Obj; | 168 | Dictionary<LLUUID, LSL_BaseClass> Obj; |
169 | Scripts.TryGetValue(localID, out Obj); | 169 | Scripts.TryGetValue(localID, out Obj); |
170 | 170 | ||
171 | return Obj.Keys; | 171 | return Obj.Keys; |
172 | 172 | ||
173 | } | 173 | } |
174 | 174 | ||
175 | internal LSL_BaseClass GetScript(uint localID, LLUUID itemID) | 175 | internal LSL_BaseClass GetScript(uint localID, LLUUID itemID) |
176 | { | 176 | { |
177 | if (Scripts.ContainsKey(localID) == false) | 177 | if (Scripts.ContainsKey(localID) == false) |
178 | return null; | 178 | return null; |
179 | 179 | ||
180 | Dictionary<LLUUID, LSL_BaseClass> Obj; | 180 | Dictionary<LLUUID, LSL_BaseClass> Obj; |
181 | Scripts.TryGetValue(localID, out Obj); | 181 | Scripts.TryGetValue(localID, out Obj); |
182 | if (Obj.ContainsKey(itemID) == false) | 182 | if (Obj.ContainsKey(itemID) == false) |
183 | return null; | 183 | return null; |
184 | 184 | ||
185 | // Get script | 185 | // Get script |
186 | LSL_BaseClass Script; | 186 | LSL_BaseClass Script; |
187 | Obj.TryGetValue(itemID, out Script); | 187 | Obj.TryGetValue(itemID, out Script); |
188 | 188 | ||
189 | return Script; | 189 | return Script; |
190 | 190 | ||
191 | } | 191 | } |
192 | internal void SetScript(uint localID, LLUUID itemID, LSL_BaseClass Script) | 192 | internal void SetScript(uint localID, LLUUID itemID, LSL_BaseClass Script) |
193 | { | 193 | { |
194 | // Create object if it doesn't exist | 194 | // Create object if it doesn't exist |
195 | if (Scripts.ContainsKey(localID) == false) | 195 | if (Scripts.ContainsKey(localID) == false) |
196 | { | 196 | { |
197 | Scripts.Add(localID, new Dictionary<LLUUID, LSL_BaseClass>()); | 197 | Scripts.Add(localID, new Dictionary<LLUUID, LSL_BaseClass>()); |
198 | } | 198 | } |
199 | 199 | ||
200 | // Delete script if it exists | 200 | // Delete script if it exists |
201 | Dictionary<LLUUID, LSL_BaseClass> Obj; | 201 | Dictionary<LLUUID, LSL_BaseClass> Obj; |
202 | Scripts.TryGetValue(localID, out Obj); | 202 | Scripts.TryGetValue(localID, out Obj); |
203 | if (Obj.ContainsKey(itemID) == true) | 203 | if (Obj.ContainsKey(itemID) == true) |
204 | Obj.Remove(itemID); | 204 | Obj.Remove(itemID); |
205 | 205 | ||
206 | // Add to object | 206 | // Add to object |
207 | Obj.Add(itemID, Script); | 207 | Obj.Add(itemID, Script); |
208 | 208 | ||
209 | } | 209 | } |
210 | internal void RemoveScript(uint localID, LLUUID itemID) | 210 | internal void RemoveScript(uint localID, LLUUID itemID) |
211 | { | 211 | { |
212 | // Don't have that object? | 212 | // Don't have that object? |
213 | if (Scripts.ContainsKey(localID) == false) | 213 | if (Scripts.ContainsKey(localID) == false) |
214 | return; | 214 | return; |
215 | 215 | ||
216 | // Delete script if it exists | 216 | // Delete script if it exists |
217 | Dictionary<LLUUID, LSL_BaseClass> Obj; | 217 | Dictionary<LLUUID, LSL_BaseClass> Obj; |
218 | Scripts.TryGetValue(localID, out Obj); | 218 | Scripts.TryGetValue(localID, out Obj); |
219 | if (Obj.ContainsKey(itemID) == true) | 219 | if (Obj.ContainsKey(itemID) == true) |
220 | Obj.Remove(itemID); | 220 | Obj.Remove(itemID); |
221 | 221 | ||
222 | } | 222 | } |
223 | #endregion | 223 | #endregion |
224 | #region Start/Stop script | 224 | #region Start/Stop script |
225 | /// <summary> | 225 | /// <summary> |
226 | /// Fetches, loads and hooks up a script to an objects events | 226 | /// Fetches, loads and hooks up a script to an objects events |
227 | /// </summary> | 227 | /// </summary> |
228 | /// <param name="itemID"></param> | 228 | /// <param name="itemID"></param> |
229 | /// <param name="localID"></param> | 229 | /// <param name="localID"></param> |
230 | public void StartScript(uint localID, LLUUID itemID, string Script) | 230 | public void StartScript(uint localID, LLUUID itemID, string Script) |
231 | { | 231 | { |
232 | LoadStruct ls = new LoadStruct(); | 232 | LoadStruct ls = new LoadStruct(); |
233 | ls.localID = localID; | 233 | ls.localID = localID; |
234 | ls.itemID = itemID; | 234 | ls.itemID = itemID; |
235 | ls.script = Script; | 235 | ls.script = Script; |
236 | loadQueue.Enqueue(ls); | 236 | loadQueue.Enqueue(ls); |
237 | } | 237 | } |
238 | /// <summary> | 238 | /// <summary> |
239 | /// Disables and unloads a script | 239 | /// Disables and unloads a script |
240 | /// </summary> | 240 | /// </summary> |
241 | /// <param name="localID"></param> | 241 | /// <param name="localID"></param> |
242 | /// <param name="itemID"></param> | 242 | /// <param name="itemID"></param> |
243 | public void StopScript(uint localID, LLUUID itemID) | 243 | public void StopScript(uint localID, LLUUID itemID) |
244 | { | 244 | { |
245 | UnloadStruct ls = new UnloadStruct(); | 245 | UnloadStruct ls = new UnloadStruct(); |
246 | ls.localID = localID; | 246 | ls.localID = localID; |
247 | ls.itemID = itemID; | 247 | ls.itemID = itemID; |
248 | unloadQueue.Enqueue(ls); | 248 | unloadQueue.Enqueue(ls); |
249 | } | 249 | } |
250 | 250 | ||
251 | private void _StartScript(uint localID, LLUUID itemID, string Script) | 251 | private void _StartScript(uint localID, LLUUID itemID, string Script) |
252 | { | 252 | { |
253 | //IScriptHost root = host.GetRoot(); | 253 | //IScriptHost root = host.GetRoot(); |
254 | Console.WriteLine("ScriptManager StartScript: localID: " + localID + ", itemID: " + itemID); | 254 | Console.WriteLine("ScriptManager StartScript: localID: " + localID + ", itemID: " + itemID); |
255 | 255 | ||
256 | // We will initialize and start the script. | 256 | // We will initialize and start the script. |
257 | // It will be up to the script itself to hook up the correct events. | 257 | // It will be up to the script itself to hook up the correct events. |
258 | string FileName = ""; | 258 | string FileName = ""; |
259 | 259 | ||
260 | IScriptHost m_host = World.GetSceneObjectPart(localID); | 260 | IScriptHost m_host = World.GetSceneObjectPart(localID); |
261 | 261 | ||
262 | try | 262 | try |
263 | { | 263 | { |
264 | 264 | ||
265 | 265 | ||
266 | 266 | ||
267 | 267 | ||
268 | // Create a new instance of the compiler (currently we don't want reuse) | 268 | // Create a new instance of the compiler (currently we don't want reuse) |
269 | OpenSim.Region.ScriptEngine.DotNetEngine.Compiler.LSL.Compiler LSLCompiler = new OpenSim.Region.ScriptEngine.DotNetEngine.Compiler.LSL.Compiler(); | 269 | OpenSim.Region.ScriptEngine.DotNetEngine.Compiler.LSL.Compiler LSLCompiler = new OpenSim.Region.ScriptEngine.DotNetEngine.Compiler.LSL.Compiler(); |
270 | // Compile (We assume LSL) | 270 | // Compile (We assume LSL) |
271 | FileName = LSLCompiler.CompileFromLSLText(Script); | 271 | FileName = LSLCompiler.CompileFromLSLText(Script); |
272 | //Console.WriteLine("Compilation of " + FileName + " done"); | 272 | //Console.WriteLine("Compilation of " + FileName + " done"); |
273 | // * Insert yield into code | 273 | // * Insert yield into code |
274 | FileName = ProcessYield(FileName); | 274 | FileName = ProcessYield(FileName); |
275 | 275 | ||
276 | 276 | ||
277 | #if DEBUG | 277 | #if DEBUG |
278 | long before; | 278 | long before; |
279 | before = GC.GetTotalMemory(true); | 279 | before = GC.GetTotalMemory(true); |
280 | #endif | 280 | #endif |
281 | LSL_BaseClass CompiledScript; | 281 | LSL_BaseClass CompiledScript; |
282 | CompiledScript = m_scriptEngine.m_AppDomainManager.LoadScript(FileName); | 282 | CompiledScript = m_scriptEngine.m_AppDomainManager.LoadScript(FileName); |
283 | #if DEBUG | 283 | #if DEBUG |
284 | Console.WriteLine("Script " + itemID + " occupies {0} bytes", GC.GetTotalMemory(true) - before); | 284 | Console.WriteLine("Script " + itemID + " occupies {0} bytes", GC.GetTotalMemory(true) - before); |
285 | #endif | 285 | #endif |
286 | 286 | ||
287 | // Add it to our script memstruct | 287 | // Add it to our script memstruct |
288 | SetScript(localID, itemID, CompiledScript); | 288 | SetScript(localID, itemID, CompiledScript); |
289 | 289 | ||
290 | // We need to give (untrusted) assembly a private instance of BuiltIns | 290 | // We need to give (untrusted) assembly a private instance of BuiltIns |
291 | // this private copy will contain Read-Only FullitemID so that it can bring that on to the server whenever needed. | 291 | // this private copy will contain Read-Only FullitemID so that it can bring that on to the server whenever needed. |
292 | 292 | ||
293 | 293 | ||
294 | LSL_BuiltIn_Commands LSLB = new LSL_BuiltIn_Commands(m_scriptEngine, m_host, localID, itemID); | 294 | LSL_BuiltIn_Commands LSLB = new LSL_BuiltIn_Commands(m_scriptEngine, m_host, localID, itemID); |
295 | 295 | ||
296 | // Start the script - giving it BuiltIns | 296 | // Start the script - giving it BuiltIns |
297 | CompiledScript.Start(LSLB); | 297 | CompiledScript.Start(LSLB); |
298 | 298 | ||
299 | // Fire the first start-event | 299 | // Fire the first start-event |
300 | m_scriptEngine.m_EventQueueManager.AddToScriptQueue(localID, itemID, "state_entry", new object[] { }); | 300 | m_scriptEngine.m_EventQueueManager.AddToScriptQueue(localID, itemID, "state_entry", new object[] { }); |
301 | 301 | ||
302 | 302 | ||
303 | } | 303 | } |
304 | catch (Exception e) | 304 | catch (Exception e) |
305 | { | 305 | { |
306 | //m_scriptEngine.Log.Error("ScriptEngine", "Error compiling script: " + e.ToString()); | 306 | //m_scriptEngine.Log.Error("ScriptEngine", "Error compiling script: " + e.ToString()); |
307 | try | 307 | try |
308 | { | 308 | { |
309 | // DISPLAY ERROR INWORLD | 309 | // DISPLAY ERROR INWORLD |
310 | string text = "Error compiling script:\r\n" + e.Message.ToString(); | 310 | string text = "Error compiling script:\r\n" + e.Message.ToString(); |
311 | if (text.Length > 1500) | 311 | if (text.Length > 1500) |
312 | text = text.Substring(0, 1500); | 312 | text = text.Substring(0, 1500); |
313 | World.SimChat(Helpers.StringToField(text), 1, m_host.AbsolutePosition, m_host.Name, m_host.UUID); | 313 | World.SimChat(Helpers.StringToField(text), 1, m_host.AbsolutePosition, m_host.Name, m_host.UUID); |
314 | } | 314 | } |
315 | catch (Exception e2) | 315 | catch (Exception e2) |
316 | { | 316 | { |
317 | m_scriptEngine.Log.Error("ScriptEngine", "Error displaying error in-world: " + e2.ToString()); | 317 | m_scriptEngine.Log.Error("ScriptEngine", "Error displaying error in-world: " + e2.ToString()); |
318 | } | 318 | } |
319 | } | 319 | } |
320 | 320 | ||
321 | 321 | ||
322 | 322 | ||
323 | } | 323 | } |
324 | 324 | ||
325 | private void _StopScript(uint localID, LLUUID itemID) | 325 | private void _StopScript(uint localID, LLUUID itemID) |
326 | { | 326 | { |
327 | // Stop script | 327 | // Stop script |
328 | Console.WriteLine("Stop script localID: " + localID + " LLUID: " + itemID.ToString()); | 328 | Console.WriteLine("Stop script localID: " + localID + " LLUID: " + itemID.ToString()); |
329 | 329 | ||
330 | 330 | ||
331 | // Stop long command on script | 331 | // Stop long command on script |
332 | m_scriptEngine.m_LSLLongCmdHandler.RemoveScript(localID, itemID); | 332 | m_scriptEngine.m_LSLLongCmdHandler.RemoveScript(localID, itemID); |
333 | 333 | ||
334 | LSL_BaseClass LSLBC = GetScript(localID, itemID); | 334 | LSL_BaseClass LSLBC = GetScript(localID, itemID); |
335 | if (LSLBC == null) | 335 | if (LSLBC == null) |
336 | return; | 336 | return; |
337 | 337 | ||
338 | // TEMP: First serialize it | 338 | // TEMP: First serialize it |
339 | //GetSerializedScript(localID, itemID); | 339 | //GetSerializedScript(localID, itemID); |
340 | 340 | ||
341 | 341 | ||
342 | try | 342 | try |
343 | { | 343 | { |
344 | // Get AppDomain | 344 | // Get AppDomain |
345 | AppDomain ad = LSLBC.Exec.GetAppDomain(); | 345 | AppDomain ad = LSLBC.Exec.GetAppDomain(); |
346 | // Tell script not to accept new requests | 346 | // Tell script not to accept new requests |
347 | GetScript(localID, itemID).Exec.StopScript(); | 347 | GetScript(localID, itemID).Exec.StopScript(); |
348 | // Remove from internal structure | 348 | // Remove from internal structure |
349 | RemoveScript(localID, itemID); | 349 | RemoveScript(localID, itemID); |
350 | // Tell AppDomain that we have stopped script | 350 | // Tell AppDomain that we have stopped script |
351 | m_scriptEngine.m_AppDomainManager.StopScript(ad); | 351 | m_scriptEngine.m_AppDomainManager.StopScript(ad); |
352 | } | 352 | } |
353 | catch(Exception e) | 353 | catch(Exception e) |
354 | { | 354 | { |
355 | Console.WriteLine("Exception stopping script localID: " + localID + " LLUID: " + itemID.ToString() + ": " + e.ToString()); | 355 | Console.WriteLine("Exception stopping script localID: " + localID + " LLUID: " + itemID.ToString() + ": " + e.ToString()); |
356 | } | 356 | } |
357 | } | 357 | } |
358 | private string ProcessYield(string FileName) | 358 | private string ProcessYield(string FileName) |
359 | { | 359 | { |
360 | // TODO: Create a new assembly and copy old but insert Yield Code | 360 | // TODO: Create a new assembly and copy old but insert Yield Code |
361 | //return TempDotNetMicroThreadingCodeInjector.TestFix(FileName); | 361 | //return TempDotNetMicroThreadingCodeInjector.TestFix(FileName); |
362 | return FileName; | 362 | return FileName; |
363 | } | 363 | } |
364 | #endregion | 364 | #endregion |
365 | #region Perform event execution in script | 365 | #region Perform event execution in script |
366 | /// <summary> | 366 | /// <summary> |
367 | /// Execute a LL-event-function in Script | 367 | /// Execute a LL-event-function in Script |
368 | /// </summary> | 368 | /// </summary> |
369 | /// <param name="localID">Object the script is located in</param> | 369 | /// <param name="localID">Object the script is located in</param> |
370 | /// <param name="itemID">Script ID</param> | 370 | /// <param name="itemID">Script ID</param> |
371 | /// <param name="FunctionName">Name of function</param> | 371 | /// <param name="FunctionName">Name of function</param> |
372 | /// <param name="args">Arguments to pass to function</param> | 372 | /// <param name="args">Arguments to pass to function</param> |
373 | internal void ExecuteEvent(uint localID, LLUUID itemID, string FunctionName, object[] args) | 373 | internal void ExecuteEvent(uint localID, LLUUID itemID, string FunctionName, object[] args) |
374 | { | 374 | { |
375 | 375 | ||
376 | // Execute a function in the script | 376 | // Execute a function in the script |
377 | //m_scriptEngine.Log.Verbose("ScriptEngine", "Executing Function localID: " + localID + ", itemID: " + itemID + ", FunctionName: " + FunctionName); | 377 | //m_scriptEngine.Log.Verbose("ScriptEngine", "Executing Function localID: " + localID + ", itemID: " + itemID + ", FunctionName: " + FunctionName); |
378 | LSL_BaseClass Script = m_scriptEngine.m_ScriptManager.GetScript(localID, itemID); | 378 | LSL_BaseClass Script = m_scriptEngine.m_ScriptManager.GetScript(localID, itemID); |
379 | if (Script == null) | 379 | if (Script == null) |
380 | return; | 380 | return; |
381 | 381 | ||
382 | // Must be done in correct AppDomain, so leaving it up to the script itself | 382 | // Must be done in correct AppDomain, so leaving it up to the script itself |
383 | Script.Exec.ExecuteEvent(FunctionName, args); | 383 | Script.Exec.ExecuteEvent(FunctionName, args); |
384 | 384 | ||
385 | } | 385 | } |
386 | #endregion | 386 | #endregion |
387 | 387 | ||
388 | #region Script serialization/deserialization | 388 | #region Script serialization/deserialization |
389 | public void GetSerializedScript(uint localID, LLUUID itemID) | 389 | public void GetSerializedScript(uint localID, LLUUID itemID) |
390 | { | 390 | { |
391 | // Serialize the script and return it | 391 | // Serialize the script and return it |
392 | // Should not be a problem | 392 | // Should not be a problem |
393 | System.IO.FileStream fs = System.IO.File.Create("SERIALIZED_SCRIPT_" + itemID); | 393 | System.IO.FileStream fs = System.IO.File.Create("SERIALIZED_SCRIPT_" + itemID); |
394 | BinaryFormatter b = new BinaryFormatter(); | 394 | BinaryFormatter b = new BinaryFormatter(); |
395 | b.Serialize(fs, GetScript(localID,itemID)); | 395 | b.Serialize(fs, GetScript(localID,itemID)); |
396 | fs.Close(); | 396 | fs.Close(); |
397 | 397 | ||
398 | 398 | ||
399 | } | 399 | } |
400 | public void PutSerializedScript(uint localID, LLUUID itemID) | 400 | public void PutSerializedScript(uint localID, LLUUID itemID) |
401 | { | 401 | { |
402 | // Deserialize the script and inject it into an AppDomain | 402 | // Deserialize the script and inject it into an AppDomain |
403 | 403 | ||
404 | // How to inject into an AppDomain? | 404 | // How to inject into an AppDomain? |
405 | } | 405 | } |
406 | #endregion | 406 | #endregion |
407 | } | 407 | } |
408 | } | 408 | } |