diff options
4 files changed, 137 insertions, 2 deletions
diff --git a/OpenSim/Region/ClientStack/LindenUDP/ILLPacketHandler.cs b/OpenSim/Region/ClientStack/LindenUDP/ILLPacketHandler.cs index 09edc94..31f9580 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/ILLPacketHandler.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/ILLPacketHandler.cs | |||
@@ -31,9 +31,10 @@ using OpenMetaverse.Packets; | |||
31 | using OpenSim.Framework; | 31 | using OpenSim.Framework; |
32 | 32 | ||
33 | namespace OpenSim.Region.ClientStack.LindenUDP | 33 | namespace OpenSim.Region.ClientStack.LindenUDP |
34 | { | 34 | { |
35 | public delegate void PacketStats(int inPackets, int outPackets, int unAckedBytes); | 35 | public delegate void PacketStats(int inPackets, int outPackets, int unAckedBytes); |
36 | public delegate void PacketDrop(Packet pack, Object id); | 36 | public delegate void PacketDrop(Packet pack, Object id); |
37 | public delegate void QueueEmpty(ThrottleOutPacketType queue); | ||
37 | public delegate bool SynchronizeClientHandler(IScene scene, Packet packet, UUID agentID, ThrottleOutPacketType throttlePacketType); | 38 | public delegate bool SynchronizeClientHandler(IScene scene, Packet packet, UUID agentID, ThrottleOutPacketType throttlePacketType); |
38 | 39 | ||
39 | /// <summary> | 40 | /// <summary> |
@@ -44,6 +45,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
44 | { | 45 | { |
45 | event PacketStats OnPacketStats; | 46 | event PacketStats OnPacketStats; |
46 | event PacketDrop OnPacketDrop; | 47 | event PacketDrop OnPacketDrop; |
48 | event QueueEmpty OnQueueEmpty; | ||
47 | SynchronizeClientHandler SynchronizeClient { set; } | 49 | SynchronizeClientHandler SynchronizeClient { set; } |
48 | 50 | ||
49 | int PacketsReceived { get; } | 51 | int PacketsReceived { get; } |
@@ -61,7 +63,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
61 | /// <summary> | 63 | /// <summary> |
62 | /// Take action depending on the type and contents of an received packet. | 64 | /// Take action depending on the type and contents of an received packet. |
63 | /// </summary> | 65 | /// </summary> |
64 | /// <param name="item"></param> | 66 | /// <param name="item"></param> |
65 | void ProcessInPacket(LLQueItem item); | 67 | void ProcessInPacket(LLQueItem item); |
66 | 68 | ||
67 | void ProcessOutPacket(LLQueItem item); | 69 | void ProcessOutPacket(LLQueItem item); |
@@ -76,5 +78,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
76 | void SetClientInfo(ClientInfo info); | 78 | void SetClientInfo(ClientInfo info); |
77 | void AddImportantPacket(PacketType type); | 79 | void AddImportantPacket(PacketType type); |
78 | void RemoveImportantPacket(PacketType type); | 80 | void RemoveImportantPacket(PacketType type); |
81 | int GetQueueCount(ThrottleOutPacketType queue); | ||
79 | } | 82 | } |
80 | } | 83 | } |
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLPacketHandler.cs b/OpenSim/Region/ClientStack/LindenUDP/LLPacketHandler.cs index 67ece75..37f6ca7 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/LLPacketHandler.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/LLPacketHandler.cs | |||
@@ -129,6 +129,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
129 | // | 129 | // |
130 | public event PacketStats OnPacketStats; | 130 | public event PacketStats OnPacketStats; |
131 | public event PacketDrop OnPacketDrop; | 131 | public event PacketDrop OnPacketDrop; |
132 | public event QueueEmpty OnQueueEmpty; | ||
132 | 133 | ||
133 | 134 | ||
134 | //private SynchronizeClientHandler m_SynchronizeClient = null; | 135 | //private SynchronizeClientHandler m_SynchronizeClient = null; |
@@ -172,6 +173,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
172 | 173 | ||
173 | m_PacketQueue = new LLPacketQueue(client.AgentId, userSettings); | 174 | m_PacketQueue = new LLPacketQueue(client.AgentId, userSettings); |
174 | 175 | ||
176 | m_PacketQueue.OnQueueEmpty += TriggerOnQueueEmpty; | ||
177 | |||
175 | m_AckTimer.Elapsed += AckTimerElapsed; | 178 | m_AckTimer.Elapsed += AckTimerElapsed; |
176 | m_AckTimer.Start(); | 179 | m_AckTimer.Start(); |
177 | } | 180 | } |
@@ -769,6 +772,16 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
769 | handlerPacketDrop(packet, id); | 772 | handlerPacketDrop(packet, id); |
770 | } | 773 | } |
771 | 774 | ||
775 | private void TriggerOnQueueEmpty(ThrottleOutPacketType queue) | ||
776 | { | ||
777 | QueueEmpty handlerQueueEmpty = OnQueueEmpty; | ||
778 | |||
779 | if (handlerQueueEmpty == null) | ||
780 | return; | ||
781 | |||
782 | handlerQueueEmpty(queue); | ||
783 | } | ||
784 | |||
772 | // Convert the packet to bytes and stuff it onto the send queue | 785 | // Convert the packet to bytes and stuff it onto the send queue |
773 | // | 786 | // |
774 | public void ProcessOutPacket(LLQueItem item) | 787 | public void ProcessOutPacket(LLQueItem item) |
@@ -850,5 +863,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
850 | m_PacketQueue.Close(); | 863 | m_PacketQueue.Close(); |
851 | Thread.CurrentThread.Abort(); | 864 | Thread.CurrentThread.Abort(); |
852 | } | 865 | } |
866 | |||
867 | public int GetQueueCount(ThrottleOutPacketType queue) | ||
868 | { | ||
869 | return m_PacketQueue.GetQueueCount(queue); | ||
870 | } | ||
853 | } | 871 | } |
854 | } | 872 | } |
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLPacketQueue.cs b/OpenSim/Region/ClientStack/LindenUDP/LLPacketQueue.cs index 6dd0697..d4d654f 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/LLPacketQueue.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/LLPacketQueue.cs | |||
@@ -105,6 +105,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
105 | 105 | ||
106 | private UUID m_agentId; | 106 | private UUID m_agentId; |
107 | 107 | ||
108 | public event QueueEmpty OnQueueEmpty; | ||
109 | |||
108 | public LLPacketQueue(UUID agentId, ClientStackUserSettings userSettings) | 110 | public LLPacketQueue(UUID agentId, ClientStackUserSettings userSettings) |
109 | { | 111 | { |
110 | // While working on this, the BlockingQueue had me fooled for a bit. | 112 | // While working on this, the BlockingQueue had me fooled for a bit. |
@@ -293,30 +295,42 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
293 | if (LandOutgoingPacketQueue.Count > 0) | 295 | if (LandOutgoingPacketQueue.Count > 0) |
294 | { | 296 | { |
295 | SendQueue.Enqueue(LandOutgoingPacketQueue.Dequeue()); | 297 | SendQueue.Enqueue(LandOutgoingPacketQueue.Dequeue()); |
298 | TriggerOnQueueEmpty(ThrottleOutPacketType.Land); | ||
296 | } | 299 | } |
297 | if (WindOutgoingPacketQueue.Count > 0) | 300 | if (WindOutgoingPacketQueue.Count > 0) |
298 | { | 301 | { |
299 | SendQueue.Enqueue(WindOutgoingPacketQueue.Dequeue()); | 302 | SendQueue.Enqueue(WindOutgoingPacketQueue.Dequeue()); |
303 | TriggerOnQueueEmpty(ThrottleOutPacketType.Wind); | ||
300 | } | 304 | } |
301 | if (CloudOutgoingPacketQueue.Count > 0) | 305 | if (CloudOutgoingPacketQueue.Count > 0) |
302 | { | 306 | { |
303 | SendQueue.Enqueue(CloudOutgoingPacketQueue.Dequeue()); | 307 | SendQueue.Enqueue(CloudOutgoingPacketQueue.Dequeue()); |
308 | TriggerOnQueueEmpty(ThrottleOutPacketType.Cloud); | ||
304 | } | 309 | } |
310 | bool tasksSent = false; | ||
305 | if (TaskOutgoingPacketQueue.Count > 0) | 311 | if (TaskOutgoingPacketQueue.Count > 0) |
306 | { | 312 | { |
313 | tasksSent = true; | ||
307 | SendQueue.PriorityEnqueue(TaskOutgoingPacketQueue.Dequeue()); | 314 | SendQueue.PriorityEnqueue(TaskOutgoingPacketQueue.Dequeue()); |
308 | } | 315 | } |
309 | if (TaskLowpriorityPacketQueue.Count > 0) | 316 | if (TaskLowpriorityPacketQueue.Count > 0) |
310 | { | 317 | { |
318 | tasksSent = true; | ||
311 | SendQueue.Enqueue(TaskLowpriorityPacketQueue.Dequeue()); | 319 | SendQueue.Enqueue(TaskLowpriorityPacketQueue.Dequeue()); |
312 | } | 320 | } |
321 | if (tasksSent) | ||
322 | { | ||
323 | TriggerOnQueueEmpty(ThrottleOutPacketType.Task); | ||
324 | } | ||
313 | if (TextureOutgoingPacketQueue.Count > 0) | 325 | if (TextureOutgoingPacketQueue.Count > 0) |
314 | { | 326 | { |
315 | SendQueue.Enqueue(TextureOutgoingPacketQueue.Dequeue()); | 327 | SendQueue.Enqueue(TextureOutgoingPacketQueue.Dequeue()); |
328 | TriggerOnQueueEmpty(ThrottleOutPacketType.Texture); | ||
316 | } | 329 | } |
317 | if (AssetOutgoingPacketQueue.Count > 0) | 330 | if (AssetOutgoingPacketQueue.Count > 0) |
318 | { | 331 | { |
319 | SendQueue.Enqueue(AssetOutgoingPacketQueue.Dequeue()); | 332 | SendQueue.Enqueue(AssetOutgoingPacketQueue.Dequeue()); |
333 | TriggerOnQueueEmpty(ThrottleOutPacketType.Asset); | ||
320 | } | 334 | } |
321 | } | 335 | } |
322 | // m_log.Info("[THROTTLE]: Processed " + throttleLoops + " packets"); | 336 | // m_log.Info("[THROTTLE]: Processed " + throttleLoops + " packets"); |
@@ -405,6 +419,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
405 | bool qchanged = true; | 419 | bool qchanged = true; |
406 | 420 | ||
407 | ResetCounters(); | 421 | ResetCounters(); |
422 | |||
423 | List<ThrottleOutPacketType> Empty = new List<ThrottleOutPacketType>(); | ||
408 | // m_log.Info("[THROTTLE]: Entering Throttle"); | 424 | // m_log.Info("[THROTTLE]: Entering Throttle"); |
409 | while (TotalThrottle.UnderLimit() && qchanged && throttleLoops <= MaxThrottleLoops) | 425 | while (TotalThrottle.UnderLimit() && qchanged && throttleLoops <= MaxThrottleLoops) |
410 | { | 426 | { |
@@ -431,6 +447,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
431 | TotalThrottle.AddBytes(qpack.Length); | 447 | TotalThrottle.AddBytes(qpack.Length); |
432 | LandThrottle.AddBytes(qpack.Length); | 448 | LandThrottle.AddBytes(qpack.Length); |
433 | qchanged = true; | 449 | qchanged = true; |
450 | |||
451 | if (LandOutgoingPacketQueue.Count == 0) | ||
452 | Empty.Add(ThrottleOutPacketType.Land); | ||
434 | } | 453 | } |
435 | 454 | ||
436 | if ((WindOutgoingPacketQueue.Count > 0) && WindThrottle.UnderLimit()) | 455 | if ((WindOutgoingPacketQueue.Count > 0) && WindThrottle.UnderLimit()) |
@@ -441,6 +460,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
441 | TotalThrottle.AddBytes(qpack.Length); | 460 | TotalThrottle.AddBytes(qpack.Length); |
442 | WindThrottle.AddBytes(qpack.Length); | 461 | WindThrottle.AddBytes(qpack.Length); |
443 | qchanged = true; | 462 | qchanged = true; |
463 | |||
464 | if (WindOutgoingPacketQueue.Count == 0) | ||
465 | Empty.Add(ThrottleOutPacketType.Wind); | ||
444 | } | 466 | } |
445 | 467 | ||
446 | if ((CloudOutgoingPacketQueue.Count > 0) && CloudThrottle.UnderLimit()) | 468 | if ((CloudOutgoingPacketQueue.Count > 0) && CloudThrottle.UnderLimit()) |
@@ -451,6 +473,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
451 | TotalThrottle.AddBytes(qpack.Length); | 473 | TotalThrottle.AddBytes(qpack.Length); |
452 | CloudThrottle.AddBytes(qpack.Length); | 474 | CloudThrottle.AddBytes(qpack.Length); |
453 | qchanged = true; | 475 | qchanged = true; |
476 | |||
477 | if (CloudOutgoingPacketQueue.Count == 0) | ||
478 | Empty.Add(ThrottleOutPacketType.Cloud); | ||
454 | } | 479 | } |
455 | 480 | ||
456 | if ((TaskOutgoingPacketQueue.Count > 0 || TaskLowpriorityPacketQueue.Count > 0) && TaskThrottle.UnderLimit()) | 481 | if ((TaskOutgoingPacketQueue.Count > 0 || TaskLowpriorityPacketQueue.Count > 0) && TaskThrottle.UnderLimit()) |
@@ -470,6 +495,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
470 | TotalThrottle.AddBytes(qpack.Length); | 495 | TotalThrottle.AddBytes(qpack.Length); |
471 | TaskThrottle.AddBytes(qpack.Length); | 496 | TaskThrottle.AddBytes(qpack.Length); |
472 | qchanged = true; | 497 | qchanged = true; |
498 | |||
499 | if (TaskOutgoingPacketQueue.Count == 0 && TaskLowpriorityPacketQueue.Count == 0) | ||
500 | Empty.Add(ThrottleOutPacketType.Task); | ||
473 | } | 501 | } |
474 | 502 | ||
475 | if ((TextureOutgoingPacketQueue.Count > 0) && TextureThrottle.UnderLimit()) | 503 | if ((TextureOutgoingPacketQueue.Count > 0) && TextureThrottle.UnderLimit()) |
@@ -480,6 +508,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
480 | TotalThrottle.AddBytes(qpack.Length); | 508 | TotalThrottle.AddBytes(qpack.Length); |
481 | TextureThrottle.AddBytes(qpack.Length); | 509 | TextureThrottle.AddBytes(qpack.Length); |
482 | qchanged = true; | 510 | qchanged = true; |
511 | |||
512 | if (TextureOutgoingPacketQueue.Count == 0) | ||
513 | Empty.Add(ThrottleOutPacketType.Texture); | ||
483 | } | 514 | } |
484 | 515 | ||
485 | if ((AssetOutgoingPacketQueue.Count > 0) && AssetThrottle.UnderLimit()) | 516 | if ((AssetOutgoingPacketQueue.Count > 0) && AssetThrottle.UnderLimit()) |
@@ -490,12 +521,30 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
490 | TotalThrottle.AddBytes(qpack.Length); | 521 | TotalThrottle.AddBytes(qpack.Length); |
491 | AssetThrottle.AddBytes(qpack.Length); | 522 | AssetThrottle.AddBytes(qpack.Length); |
492 | qchanged = true; | 523 | qchanged = true; |
524 | |||
525 | if (AssetOutgoingPacketQueue.Count == 0) | ||
526 | Empty.Add(ThrottleOutPacketType.Asset); | ||
493 | } | 527 | } |
494 | } | 528 | } |
495 | // m_log.Info("[THROTTLE]: Processed " + throttleLoops + " packets"); | 529 | // m_log.Info("[THROTTLE]: Processed " + throttleLoops + " packets"); |
530 | |||
531 | foreach (ThrottleOutPacketType t in Empty) | ||
532 | { | ||
533 | TriggerOnQueueEmpty(t); | ||
534 | } | ||
496 | } | 535 | } |
497 | } | 536 | } |
498 | 537 | ||
538 | private void TriggerOnQueueEmpty(ThrottleOutPacketType queue) | ||
539 | { | ||
540 | QueueEmpty handlerQueueEmpty = OnQueueEmpty; | ||
541 | |||
542 | if (handlerQueueEmpty == null) | ||
543 | return; | ||
544 | |||
545 | handlerQueueEmpty(queue); | ||
546 | } | ||
547 | |||
499 | private void ThrottleTimerElapsed(object sender, ElapsedEventArgs e) | 548 | private void ThrottleTimerElapsed(object sender, ElapsedEventArgs e) |
500 | { | 549 | { |
501 | // just to change the signature, and that ProcessThrottle | 550 | // just to change the signature, and that ProcessThrottle |
@@ -704,5 +753,26 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
704 | { | 753 | { |
705 | get { return throttleMultiplier; } | 754 | get { return throttleMultiplier; } |
706 | } | 755 | } |
756 | |||
757 | public int GetQueueCount(ThrottleOutPacketType queue) | ||
758 | { | ||
759 | switch (queue) | ||
760 | { | ||
761 | case ThrottleOutPacketType.Land: | ||
762 | return LandOutgoingPacketQueue.Count; | ||
763 | case ThrottleOutPacketType.Wind: | ||
764 | return WindOutgoingPacketQueue.Count; | ||
765 | case ThrottleOutPacketType.Cloud: | ||
766 | return CloudOutgoingPacketQueue.Count; | ||
767 | case ThrottleOutPacketType.Task: | ||
768 | return TaskOutgoingPacketQueue.Count; | ||
769 | case ThrottleOutPacketType.Texture: | ||
770 | return TextureOutgoingPacketQueue.Count; | ||
771 | case ThrottleOutPacketType.Asset: | ||
772 | return AssetOutgoingPacketQueue.Count; | ||
773 | } | ||
774 | |||
775 | return 0; | ||
776 | } | ||
707 | } | 777 | } |
708 | } | 778 | } |
diff --git a/OpenSim/Services/Connectors/Asset/AssetServiceConnector.cs b/OpenSim/Services/Connectors/Asset/AssetServiceConnector.cs index ffc8e4c..d16112d 100644 --- a/OpenSim/Services/Connectors/Asset/AssetServiceConnector.cs +++ b/OpenSim/Services/Connectors/Asset/AssetServiceConnector.cs | |||
@@ -32,9 +32,11 @@ using System.IO; | |||
32 | using System.Reflection; | 32 | using System.Reflection; |
33 | using Nini.Config; | 33 | using Nini.Config; |
34 | using OpenSim.Framework; | 34 | using OpenSim.Framework; |
35 | using OpenSim.Framework.Console; | ||
35 | using OpenSim.Framework.Communications; | 36 | using OpenSim.Framework.Communications; |
36 | using OpenSim.Framework.Servers.HttpServer; | 37 | using OpenSim.Framework.Servers.HttpServer; |
37 | using OpenSim.Services.Interfaces; | 38 | using OpenSim.Services.Interfaces; |
39 | using OpenMetaverse; | ||
38 | 40 | ||
39 | namespace OpenSim.Services.Connectors | 41 | namespace OpenSim.Services.Connectors |
40 | { | 42 | { |
@@ -79,6 +81,10 @@ namespace OpenSim.Services.Connectors | |||
79 | throw new Exception("Asset connector init error"); | 81 | throw new Exception("Asset connector init error"); |
80 | } | 82 | } |
81 | m_ServerURI = serviceURI; | 83 | m_ServerURI = serviceURI; |
84 | |||
85 | MainConsole.Instance.Commands.AddCommand("asset", false, "dump asset", | ||
86 | "dump asset <id> <file>", | ||
87 | "dump one cached asset", HandleDumpAsset); | ||
82 | } | 88 | } |
83 | 89 | ||
84 | protected void SetCache(IImprovedAssetCache cache) | 90 | protected void SetCache(IImprovedAssetCache cache) |
@@ -264,5 +270,43 @@ namespace OpenSim.Services.Connectors | |||
264 | } | 270 | } |
265 | return false; | 271 | return false; |
266 | } | 272 | } |
273 | |||
274 | private void HandleDumpAsset(string module, string[] args) | ||
275 | { | ||
276 | if (args.Length != 4) | ||
277 | { | ||
278 | MainConsole.Instance.Output("Syntax: dump asset <id> <file>"); | ||
279 | return; | ||
280 | } | ||
281 | |||
282 | UUID assetID; | ||
283 | |||
284 | if (!UUID.TryParse(args[2], out assetID)) | ||
285 | { | ||
286 | MainConsole.Instance.Output("Invalid asset ID"); | ||
287 | return; | ||
288 | } | ||
289 | |||
290 | if (m_Cache == null) | ||
291 | { | ||
292 | MainConsole.Instance.Output("Instance uses no cache"); | ||
293 | return; | ||
294 | } | ||
295 | |||
296 | AssetBase asset = asset = m_Cache.Get(assetID.ToString()); | ||
297 | |||
298 | if (asset == null) | ||
299 | { | ||
300 | MainConsole.Instance.Output("Asset not found in cache"); | ||
301 | return; | ||
302 | } | ||
303 | |||
304 | string fileName = args[3]; | ||
305 | |||
306 | FileStream fs = File.Create(fileName); | ||
307 | fs.Write(asset.Data, 0, asset.Data.Length); | ||
308 | |||
309 | fs.Close(); | ||
310 | } | ||
267 | } | 311 | } |
268 | } | 312 | } |