diff options
Diffstat (limited to 'OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs')
-rw-r--r-- | OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs | 567 |
1 files changed, 41 insertions, 526 deletions
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs b/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs index c9fc83a..41ac657 100644 --- a/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs +++ b/OpenSim/Region/ClientStack/LindenUDP/LLClientView.cs | |||
@@ -50,20 +50,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
50 | 50 | ||
51 | 51 | ||
52 | /// <summary> | 52 | /// <summary> |
53 | /// Class that keeps track of past packets so that they don't get | ||
54 | /// duplicated when the client doesn't get back an ack | ||
55 | /// </summary> | ||
56 | public class PacketDupeLimiter | ||
57 | { | ||
58 | public PacketType pktype; | ||
59 | public int timeIn; | ||
60 | public uint packetId; | ||
61 | public PacketDupeLimiter() | ||
62 | { | ||
63 | } | ||
64 | } | ||
65 | |||
66 | /// <summary> | ||
67 | /// Handles new client connections | 53 | /// Handles new client connections |
68 | /// Constructor takes a single Packet and authenticates everything | 54 | /// Constructor takes a single Packet and authenticates everything |
69 | /// </summary> | 55 | /// </summary> |
@@ -79,7 +65,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
79 | /* static variables */ | 65 | /* static variables */ |
80 | public static TerrainManager TerrainManager = new TerrainManager(new SecondLife()); | 66 | public static TerrainManager TerrainManager = new TerrainManager(new SecondLife()); |
81 | 67 | ||
82 | public delegate bool SynchronizeClientHandler(IScene scene, Packet packet, LLUUID agentID, ThrottleOutPacketType throttlePacketType); | ||
83 | public static SynchronizeClientHandler SynchronizeClient = null; | 68 | public static SynchronizeClientHandler SynchronizeClient = null; |
84 | /* private variables */ | 69 | /* private variables */ |
85 | private readonly LLUUID m_sessionId; | 70 | private readonly LLUUID m_sessionId; |
@@ -93,15 +78,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
93 | 78 | ||
94 | private bool m_clientBlocked = false; | 79 | private bool m_clientBlocked = false; |
95 | 80 | ||
96 | // for sim stats | ||
97 | private int m_packetsReceived = 0; | ||
98 | private int m_lastPacketsReceivedSentToScene = 0; | ||
99 | private int m_unAckedBytes = 0; | ||
100 | |||
101 | private int m_packetsSent = 0; | ||
102 | private int m_lastPacketsSentSentToScene = 0; | ||
103 | private int m_clearDuplicatePacketTrackingOlderThenXSeconds = 30; | ||
104 | |||
105 | private int m_probesWithNoIngressPackets = 0; | 81 | private int m_probesWithNoIngressPackets = 0; |
106 | private int m_lastPacketsReceived = 0; | 82 | private int m_lastPacketsReceived = 0; |
107 | private byte[] ZeroOutBuffer = new byte[4096]; | 83 | private byte[] ZeroOutBuffer = new byte[4096]; |
@@ -109,8 +85,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
109 | private readonly LLUUID m_agentId; | 85 | private readonly LLUUID m_agentId; |
110 | private readonly uint m_circuitCode; | 86 | private readonly uint m_circuitCode; |
111 | private int m_moneyBalance; | 87 | private int m_moneyBalance; |
112 | 88 | private IPacketHandler m_PacketHandler; | |
113 | private Dictionary<uint, PacketDupeLimiter> m_dupeLimiter = new Dictionary<uint, PacketDupeLimiter>(); | ||
114 | 89 | ||
115 | private int m_animationSequenceNumber = 1; | 90 | private int m_animationSequenceNumber = 1; |
116 | 91 | ||
@@ -118,8 +93,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
118 | 93 | ||
119 | private Dictionary<string, LLUUID> m_defaultAnimations = new Dictionary<string, LLUUID>(); | 94 | private Dictionary<string, LLUUID> m_defaultAnimations = new Dictionary<string, LLUUID>(); |
120 | 95 | ||
121 | private LLPacketTracker m_packetTracker; | ||
122 | |||
123 | /* protected variables */ | 96 | /* protected variables */ |
124 | 97 | ||
125 | protected static Dictionary<PacketType, PacketMethod> PacketHandlers = | 98 | protected static Dictionary<PacketType, PacketMethod> PacketHandlers = |
@@ -130,17 +103,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
130 | protected IScene m_scene; | 103 | protected IScene m_scene; |
131 | protected AgentCircuitManager m_authenticateSessionsHandler; | 104 | protected AgentCircuitManager m_authenticateSessionsHandler; |
132 | 105 | ||
133 | protected LLPacketQueue m_packetQueue; | ||
134 | |||
135 | protected Dictionary<uint, uint> m_pendingAcks = new Dictionary<uint, uint>(); | ||
136 | protected Dictionary<uint, Packet> m_needAck = new Dictionary<uint, Packet>(); | ||
137 | |||
138 | protected Timer m_ackTimer; | ||
139 | protected uint m_sequence = 0; | ||
140 | protected object m_sequenceLock = new object(); | ||
141 | protected const int MAX_APPENDED_ACKS = 10; | ||
142 | protected const int RESEND_TIMEOUT = 4000; | ||
143 | protected const int MAX_SEQUENCE = 0xFFFFFF; | ||
144 | protected LLPacketServer m_networkServer; | 106 | protected LLPacketServer m_networkServer; |
145 | 107 | ||
146 | /* public variables */ | 108 | /* public variables */ |
@@ -263,7 +225,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
263 | private UpdateVector handlerUpdateVector = null; //OnUpdatePrimGroupPosition; | 225 | private UpdateVector handlerUpdateVector = null; //OnUpdatePrimGroupPosition; |
264 | private UpdatePrimRotation handlerUpdatePrimRotation = null; //OnUpdatePrimGroupRotation; | 226 | private UpdatePrimRotation handlerUpdatePrimRotation = null; //OnUpdatePrimGroupRotation; |
265 | // private UpdatePrimGroupRotation handlerUpdatePrimGroupRotation = null; //OnUpdatePrimGroupMouseRotation; | 227 | // private UpdatePrimGroupRotation handlerUpdatePrimGroupRotation = null; //OnUpdatePrimGroupMouseRotation; |
266 | private PacketStats handlerPacketStats = null; // OnPacketStats;# | ||
267 | // private RequestAsset handlerRequestAsset = null; // OnRequestAsset; | 228 | // private RequestAsset handlerRequestAsset = null; // OnRequestAsset; |
268 | private UUIDNameRequest handlerTeleportHomeRequest = null; | 229 | private UUIDNameRequest handlerTeleportHomeRequest = null; |
269 | 230 | ||
@@ -378,13 +339,24 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
378 | get { return m_animationSequenceNumber++; } | 339 | get { return m_animationSequenceNumber++; } |
379 | } | 340 | } |
380 | 341 | ||
342 | public IPacketHandler PacketHandler | ||
343 | { | ||
344 | get { return m_PacketHandler; } | ||
345 | } | ||
346 | |||
347 | bool m_IsActive = true; | ||
348 | |||
349 | public bool IsActive | ||
350 | { | ||
351 | get { return m_IsActive; } | ||
352 | set { m_IsActive = value; } | ||
353 | } | ||
354 | |||
381 | /* METHODS */ | 355 | /* METHODS */ |
382 | 356 | ||
383 | public LLClientView(EndPoint remoteEP, IScene scene, AssetCache assetCache, LLPacketServer packServer, | 357 | public LLClientView(EndPoint remoteEP, IScene scene, AssetCache assetCache, LLPacketServer packServer, |
384 | AgentCircuitManager authenSessions, LLUUID agentId, LLUUID sessionId, uint circuitCode, EndPoint proxyEP) | 358 | AgentCircuitManager authenSessions, LLUUID agentId, LLUUID sessionId, uint circuitCode, EndPoint proxyEP) |
385 | { | 359 | { |
386 | m_packetTracker = new LLPacketTracker(this); | ||
387 | |||
388 | m_moneyBalance = 1000; | 360 | m_moneyBalance = 1000; |
389 | 361 | ||
390 | m_channelVersion = Helpers.StringToField(scene.GetSimulatorVersion()); | 362 | m_channelVersion = Helpers.StringToField(scene.GetSimulatorVersion()); |
@@ -414,7 +386,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
414 | // in it to process. It's an on-purpose threadlock though because | 386 | // in it to process. It's an on-purpose threadlock though because |
415 | // without it, the clientloop will suck up all sim resources. | 387 | // without it, the clientloop will suck up all sim resources. |
416 | 388 | ||
417 | m_packetQueue = new LLPacketQueue(agentId); | 389 | m_PacketHandler = new LLPacketHandler(this); |
390 | m_PacketHandler.SynchronizeClient = SynchronizeClient; | ||
418 | 391 | ||
419 | RegisterLocalPacketHandlers(); | 392 | RegisterLocalPacketHandlers(); |
420 | 393 | ||
@@ -423,7 +396,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
423 | m_clientThread.Name = "ClientThread"; | 396 | m_clientThread.Name = "ClientThread"; |
424 | m_clientThread.IsBackground = true; | 397 | m_clientThread.IsBackground = true; |
425 | m_clientThread.Start(); | 398 | m_clientThread.Start(); |
426 | ThreadTracker.Add(m_clientThread); | ||
427 | } | 399 | } |
428 | 400 | ||
429 | public void SetDebug(int newDebug) | 401 | public void SetDebug(int newDebug) |
@@ -444,12 +416,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
444 | DisableSimulatorPacket disable = (DisableSimulatorPacket)PacketPool.Instance.GetPacket(PacketType.DisableSimulator); | 416 | DisableSimulatorPacket disable = (DisableSimulatorPacket)PacketPool.Instance.GetPacket(PacketType.DisableSimulator); |
445 | OutPacket(disable, ThrottleOutPacketType.Unknown); | 417 | OutPacket(disable, ThrottleOutPacketType.Unknown); |
446 | 418 | ||
447 | m_packetQueue.Close(); | ||
448 | |||
449 | Thread.Sleep(2000); | 419 | Thread.Sleep(2000); |
450 | 420 | ||
451 | // Shut down timers | 421 | // Shut down timers |
452 | m_ackTimer.Stop(); | ||
453 | m_clientPingTimer.Stop(); | 422 | m_clientPingTimer.Stop(); |
454 | 423 | ||
455 | // This is just to give the client a reasonable chance of | 424 | // This is just to give the client a reasonable chance of |
@@ -479,7 +448,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
479 | { | 448 | { |
480 | // Pull Client out of Region | 449 | // Pull Client out of Region |
481 | m_log.Info("[CLIENT]: Close has been called"); | 450 | m_log.Info("[CLIENT]: Close has been called"); |
482 | m_packetQueue.Flush(); | 451 | m_PacketHandler.Flush(); |
483 | 452 | ||
484 | //raiseevent on the packet server to Shutdown the circuit | 453 | //raiseevent on the packet server to Shutdown the circuit |
485 | if (shutdownCircuit) | 454 | if (shutdownCircuit) |
@@ -509,20 +478,13 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
509 | public void Stop() | 478 | public void Stop() |
510 | { | 479 | { |
511 | // Shut down timers | 480 | // Shut down timers |
512 | m_ackTimer.Stop(); | ||
513 | m_clientPingTimer.Stop(); | 481 | m_clientPingTimer.Stop(); |
514 | } | 482 | } |
515 | 483 | ||
516 | public void Restart() | 484 | public void Restart() |
517 | { | 485 | { |
518 | // re-construct | 486 | // re-construct |
519 | m_pendingAcks = new Dictionary<uint, uint>(); | 487 | m_PacketHandler.Clear(); |
520 | m_needAck = new Dictionary<uint, Packet>(); | ||
521 | m_sequence += 1000000; | ||
522 | |||
523 | m_ackTimer = new Timer(750); | ||
524 | m_ackTimer.Elapsed += new ElapsedEventHandler(AckTimer_Elapsed); | ||
525 | m_ackTimer.Start(); | ||
526 | 488 | ||
527 | m_clientPingTimer = new Timer(5000); | 489 | m_clientPingTimer = new Timer(5000); |
528 | m_clientPingTimer.Elapsed += new ElapsedEventHandler(CheckClientConnectivity); | 490 | m_clientPingTimer.Elapsed += new ElapsedEventHandler(CheckClientConnectivity); |
@@ -531,8 +493,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
531 | 493 | ||
532 | public void Terminate() | 494 | public void Terminate() |
533 | { | 495 | { |
534 | // disable blocking queue | 496 | m_PacketHandler.Stop(); |
535 | m_packetQueue.Enqueue(null); | ||
536 | 497 | ||
537 | // wait for thread stoped | 498 | // wait for thread stoped |
538 | m_clientThread.Join(); | 499 | m_clientThread.Join(); |
@@ -638,7 +599,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
638 | m_log.Info("[CLIENT]: Entered loop"); | 599 | m_log.Info("[CLIENT]: Entered loop"); |
639 | while (true) | 600 | while (true) |
640 | { | 601 | { |
641 | LLQueItem nextPacket = m_packetQueue.Dequeue(); | 602 | LLQueItem nextPacket = m_PacketHandler.PacketQueue.Dequeue(); |
642 | if (nextPacket == null) | 603 | if (nextPacket == null) |
643 | { | 604 | { |
644 | m_log.Error("Got a NULL packet in Client Loop, bailing out of our client loop"); | 605 | m_log.Error("Got a NULL packet in Client Loop, bailing out of our client loop"); |
@@ -646,12 +607,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
646 | } | 607 | } |
647 | if (nextPacket.Incoming) | 608 | if (nextPacket.Incoming) |
648 | { | 609 | { |
649 | if (nextPacket.Packet.Type != PacketType.AgentUpdate) | ||
650 | { | ||
651 | m_packetsReceived++; | ||
652 | } | ||
653 | DebugPacket("IN", nextPacket.Packet); | 610 | DebugPacket("IN", nextPacket.Packet); |
654 | ProcessInPacket(nextPacket.Packet); | 611 | m_PacketHandler.ProcessInPacket(nextPacket.Packet); |
655 | } | 612 | } |
656 | else | 613 | else |
657 | { | 614 | { |
@@ -672,7 +629,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
672 | /// <param name="e"></param> | 629 | /// <param name="e"></param> |
673 | protected void CheckClientConnectivity(object sender, ElapsedEventArgs e) | 630 | protected void CheckClientConnectivity(object sender, ElapsedEventArgs e) |
674 | { | 631 | { |
675 | if (m_packetsReceived == m_lastPacketsReceived) | 632 | if (m_PacketHandler.PacketsReceived == m_PacketHandler.PacketsReceivedReported) |
676 | { | 633 | { |
677 | m_probesWithNoIngressPackets++; | 634 | m_probesWithNoIngressPackets++; |
678 | if ((m_probesWithNoIngressPackets > 30 && !m_clientBlocked) || (m_probesWithNoIngressPackets > 90 && m_clientBlocked)) | 635 | if ((m_probesWithNoIngressPackets > 30 && !m_clientBlocked) || (m_probesWithNoIngressPackets > 90 && m_clientBlocked)) |
@@ -693,19 +650,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
693 | { | 650 | { |
694 | // Something received in the meantime - we can reset the counters | 651 | // Something received in the meantime - we can reset the counters |
695 | m_probesWithNoIngressPackets = 0; | 652 | m_probesWithNoIngressPackets = 0; |
696 | m_lastPacketsReceived = m_packetsReceived; | ||
697 | } | 653 | } |
698 | 654 | ||
699 | //SendPacketStats(); | ||
700 | m_packetTracker.Process(); | ||
701 | |||
702 | if (m_terrainCheckerCount >= 4) | ||
703 | { | ||
704 | m_packetTracker.TerrainPacketCheck(); | ||
705 | // m_packetTracker.PrimPacketCheck(); | ||
706 | m_terrainCheckerCount = -1; | ||
707 | } | ||
708 | m_terrainCheckerCount++; | ||
709 | } | 655 | } |
710 | 656 | ||
711 | # region Setup | 657 | # region Setup |
@@ -719,9 +665,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
719 | //this.UploadAssets = new AgentAssetUpload(this, m_assetCache, m_inventoryCache); | 665 | //this.UploadAssets = new AgentAssetUpload(this, m_assetCache, m_inventoryCache); |
720 | 666 | ||
721 | // Establish our two timers. We could probably get this down to one | 667 | // Establish our two timers. We could probably get this down to one |
722 | m_ackTimer = new Timer(750); | ||
723 | m_ackTimer.Elapsed += new ElapsedEventHandler(AckTimer_Elapsed); | ||
724 | m_ackTimer.Start(); | ||
725 | 668 | ||
726 | m_clientPingTimer = new Timer(5000); | 669 | m_clientPingTimer = new Timer(5000); |
727 | m_clientPingTimer.Elapsed += new ElapsedEventHandler(CheckClientConnectivity); | 670 | m_clientPingTimer.Elapsed += new ElapsedEventHandler(CheckClientConnectivity); |
@@ -754,7 +697,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
754 | "[CLIENT]: New user request denied to avatar {0} connecting with circuit code {1} from {2}", | 697 | "[CLIENT]: New user request denied to avatar {0} connecting with circuit code {1} from {2}", |
755 | m_agentId, m_circuitCode, m_userEndPoint); | 698 | m_agentId, m_circuitCode, m_userEndPoint); |
756 | 699 | ||
757 | m_packetQueue.Close(); | 700 | m_PacketHandler.Stop(); |
758 | m_clientThread.Abort(); | 701 | m_clientThread.Abort(); |
759 | } | 702 | } |
760 | else | 703 | else |
@@ -920,7 +863,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
920 | public event FriendActionDelegate OnApproveFriendRequest; | 863 | public event FriendActionDelegate OnApproveFriendRequest; |
921 | public event FriendActionDelegate OnDenyFriendRequest; | 864 | public event FriendActionDelegate OnDenyFriendRequest; |
922 | public event FriendshipTermination OnTerminateFriendship; | 865 | public event FriendshipTermination OnTerminateFriendship; |
923 | public event PacketStats OnPacketStats; | ||
924 | public event MoneyTransferRequest OnMoneyTransferRequest; | 866 | public event MoneyTransferRequest OnMoneyTransferRequest; |
925 | public event EconomyDataRequest OnEconomyDataRequest; | 867 | public event EconomyDataRequest OnEconomyDataRequest; |
926 | public event MoneyBalanceRequest OnMoneyBalanceRequest; | 868 | public event MoneyBalanceRequest OnMoneyBalanceRequest; |
@@ -1105,7 +1047,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
1105 | public virtual void SendLayerData(float[] map) | 1047 | public virtual void SendLayerData(float[] map) |
1106 | { | 1048 | { |
1107 | ThreadPool.QueueUserWorkItem(new WaitCallback(DoSendLayerData), (object)map); | 1049 | ThreadPool.QueueUserWorkItem(new WaitCallback(DoSendLayerData), (object)map); |
1108 | |||
1109 | } | 1050 | } |
1110 | 1051 | ||
1111 | /// <summary> | 1052 | /// <summary> |
@@ -1166,11 +1107,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
1166 | /// <param name="map">heightmap</param> | 1107 | /// <param name="map">heightmap</param> |
1167 | public void SendLayerData(int px, int py, float[] map) | 1108 | public void SendLayerData(int px, int py, float[] map) |
1168 | { | 1109 | { |
1169 | SendLayerData(px, py, map, true); | ||
1170 | } | ||
1171 | |||
1172 | public void SendLayerData(int px, int py, float[] map, bool track) | ||
1173 | { | ||
1174 | try | 1110 | try |
1175 | { | 1111 | { |
1176 | int[] patches = new int[1]; | 1112 | int[] patches = new int[1]; |
@@ -1183,12 +1119,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
1183 | LayerDataPacket layerpack = LLClientView.TerrainManager.CreateLandPacket(map, patches); | 1119 | LayerDataPacket layerpack = LLClientView.TerrainManager.CreateLandPacket(map, patches); |
1184 | layerpack.Header.Zerocoded = true; | 1120 | layerpack.Header.Zerocoded = true; |
1185 | 1121 | ||
1186 | if (track) | ||
1187 | { | ||
1188 | layerpack.Header.Sequence = NextSeqNum(); | ||
1189 | m_packetTracker.TrackTerrainPacket(layerpack.Header.Sequence, px, py); | ||
1190 | } | ||
1191 | |||
1192 | OutPacket(layerpack, ThrottleOutPacketType.Land); | 1122 | OutPacket(layerpack, ThrottleOutPacketType.Land); |
1193 | } | 1123 | } |
1194 | catch (Exception e) | 1124 | catch (Exception e) |
@@ -2309,14 +2239,14 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
2309 | ulong regionHandle, ushort timeDilation, uint localID, PrimitiveBaseShape primShape, | 2239 | ulong regionHandle, ushort timeDilation, uint localID, PrimitiveBaseShape primShape, |
2310 | LLVector3 pos, LLVector3 vel, LLVector3 acc, LLQuaternion rotation, LLVector3 rvel, | 2240 | LLVector3 pos, LLVector3 vel, LLVector3 acc, LLQuaternion rotation, LLVector3 rvel, |
2311 | uint flags, LLUUID objectID, LLUUID ownerID, string text, byte[] color, | 2241 | uint flags, LLUUID objectID, LLUUID ownerID, string text, byte[] color, |
2312 | uint parentID, byte[] particleSystem, byte clickAction, bool track) | 2242 | uint parentID, byte[] particleSystem, byte clickAction) |
2313 | { | 2243 | { |
2314 | byte[] textureanim = new byte[0]; | 2244 | byte[] textureanim = new byte[0]; |
2315 | 2245 | ||
2316 | SendPrimitiveToClient(regionHandle, timeDilation, localID, primShape, pos, vel, | 2246 | SendPrimitiveToClient(regionHandle, timeDilation, localID, primShape, pos, vel, |
2317 | acc, rotation, rvel, flags, | 2247 | acc, rotation, rvel, flags, |
2318 | objectID, ownerID, text, color, parentID, particleSystem, | 2248 | objectID, ownerID, text, color, parentID, particleSystem, |
2319 | clickAction, textureanim, false, (uint)0, LLUUID.Zero, LLUUID.Zero, 0, 0, 0, track); | 2249 | clickAction, textureanim, false, (uint)0, LLUUID.Zero, LLUUID.Zero, 0, 0, 0); |
2320 | } | 2250 | } |
2321 | 2251 | ||
2322 | public void SendPrimitiveToClient( | 2252 | public void SendPrimitiveToClient( |
@@ -2324,7 +2254,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
2324 | LLVector3 pos, LLVector3 velocity, LLVector3 acceleration, LLQuaternion rotation, LLVector3 rotational_velocity, | 2254 | LLVector3 pos, LLVector3 velocity, LLVector3 acceleration, LLQuaternion rotation, LLVector3 rotational_velocity, |
2325 | uint flags, | 2255 | uint flags, |
2326 | LLUUID objectID, LLUUID ownerID, string text, byte[] color, uint parentID, byte[] particleSystem, | 2256 | LLUUID objectID, LLUUID ownerID, string text, byte[] color, uint parentID, byte[] particleSystem, |
2327 | byte clickAction, byte[] textureanim, bool attachment, uint AttachPoint, LLUUID AssetId, LLUUID SoundId, double SoundGain, byte SoundFlags, double SoundRadius, bool track) | 2257 | byte clickAction, byte[] textureanim, bool attachment, uint AttachPoint, LLUUID AssetId, LLUUID SoundId, double SoundGain, byte SoundFlags, double SoundRadius) |
2328 | { | 2258 | { |
2329 | 2259 | ||
2330 | if (rotation.X == rotation.Y && rotation.Y == rotation.Z && rotation.Z == rotation.W && rotation.W == 0) | 2260 | if (rotation.X == rotation.Y && rotation.Y == rotation.Z && rotation.Z == rotation.W && rotation.W == 0) |
@@ -2410,13 +2340,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
2410 | } | 2340 | } |
2411 | outPacket.Header.Zerocoded = true; | 2341 | outPacket.Header.Zerocoded = true; |
2412 | 2342 | ||
2413 | if (track) | 2343 | OutPacket(outPacket, ThrottleOutPacketType.LowpriorityTask); |
2414 | { | ||
2415 | outPacket.Header.Sequence = NextSeqNum(); | ||
2416 | m_packetTracker.TrackPrimPacket(outPacket.Header.Sequence, objectID); | ||
2417 | } | ||
2418 | |||
2419 | OutPacket(outPacket, ThrottleOutPacketType.Task); | ||
2420 | } | 2344 | } |
2421 | 2345 | ||
2422 | /// <summary> | 2346 | /// <summary> |
@@ -2440,7 +2364,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
2440 | terse.ObjectData[0] = CreatePrimImprovedBlock(localID, position, rotation, velocity, rotationalvelocity, state); // AssetID should fall into here probably somehow... | 2364 | terse.ObjectData[0] = CreatePrimImprovedBlock(localID, position, rotation, velocity, rotationalvelocity, state); // AssetID should fall into here probably somehow... |
2441 | terse.Header.Reliable = false; | 2365 | terse.Header.Reliable = false; |
2442 | terse.Header.Zerocoded = true; | 2366 | terse.Header.Zerocoded = true; |
2443 | OutPacket(terse, ThrottleOutPacketType.Task); | 2367 | OutPacket(terse, ThrottleOutPacketType.LowpriorityTask); |
2444 | } | 2368 | } |
2445 | 2369 | ||
2446 | public void SendPrimTerseUpdate(ulong regionHandle, ushort timeDilation, uint localID, LLVector3 position, | 2370 | public void SendPrimTerseUpdate(ulong regionHandle, ushort timeDilation, uint localID, LLVector3 position, |
@@ -2456,7 +2380,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
2456 | terse.ObjectData[0] = CreatePrimImprovedBlock(localID, position, rotation, velocity, rotationalvelocity, 0); | 2380 | terse.ObjectData[0] = CreatePrimImprovedBlock(localID, position, rotation, velocity, rotationalvelocity, 0); |
2457 | terse.Header.Reliable = false; | 2381 | terse.Header.Reliable = false; |
2458 | terse.Header.Zerocoded = true; | 2382 | terse.Header.Zerocoded = true; |
2459 | OutPacket(terse, ThrottleOutPacketType.Task); | 2383 | OutPacket(terse, ThrottleOutPacketType.LowpriorityTask); |
2460 | } | 2384 | } |
2461 | 2385 | ||
2462 | public void SendAssetUploadCompleteMessage(sbyte AssetType, bool Success, LLUUID AssetFullID) | 2386 | public void SendAssetUploadCompleteMessage(sbyte AssetType, bool Success, LLUUID AssetFullID) |
@@ -3736,7 +3660,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
3736 | /// <returns></returns> | 3660 | /// <returns></returns> |
3737 | public byte[] GetThrottlesPacked(float multiplier) | 3661 | public byte[] GetThrottlesPacked(float multiplier) |
3738 | { | 3662 | { |
3739 | return m_packetQueue.GetThrottlesPacked(multiplier); | 3663 | return m_PacketHandler.PacketQueue.GetThrottlesPacked(multiplier); |
3740 | } | 3664 | } |
3741 | /// <summary> | 3665 | /// <summary> |
3742 | /// sets the throttles from values supplied by the client | 3666 | /// sets the throttles from values supplied by the client |
@@ -3744,86 +3668,11 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
3744 | /// <param name="throttles"></param> | 3668 | /// <param name="throttles"></param> |
3745 | public void SetChildAgentThrottle(byte[] throttles) | 3669 | public void SetChildAgentThrottle(byte[] throttles) |
3746 | { | 3670 | { |
3747 | m_packetQueue.SetThrottleFromClient(throttles); | 3671 | m_PacketHandler.PacketQueue.SetThrottleFromClient(throttles); |
3748 | } | 3672 | } |
3749 | 3673 | ||
3750 | // Previously ClientView.m_packetQueue | 3674 | // Previously ClientView.m_packetQueue |
3751 | 3675 | ||
3752 | // A thread safe sequence number allocator. | ||
3753 | protected uint NextSeqNum() | ||
3754 | { | ||
3755 | // Set the sequence number | ||
3756 | uint seq = 1; | ||
3757 | lock (m_sequenceLock) | ||
3758 | { | ||
3759 | if (m_sequence >= MAX_SEQUENCE) | ||
3760 | { | ||
3761 | m_sequence = 1; | ||
3762 | } | ||
3763 | else | ||
3764 | { | ||
3765 | m_sequence++; | ||
3766 | } | ||
3767 | seq = m_sequence; | ||
3768 | } | ||
3769 | return seq; | ||
3770 | } | ||
3771 | |||
3772 | protected void AddAck(Packet Pack) | ||
3773 | { | ||
3774 | lock (m_needAck) | ||
3775 | { | ||
3776 | if (!m_needAck.ContainsKey(Pack.Header.Sequence)) | ||
3777 | { | ||
3778 | try | ||
3779 | { | ||
3780 | m_needAck.Add(Pack.Header.Sequence, Pack); | ||
3781 | m_unAckedBytes += Pack.ToBytes().Length; | ||
3782 | } | ||
3783 | //BUG: severity=major - This looks like a framework bug!? | ||
3784 | catch (Exception) // HACKY | ||
3785 | { | ||
3786 | // Ignore | ||
3787 | // Seems to throw a exception here occasionally | ||
3788 | // of 'duplicate key' despite being locked. | ||
3789 | // !?!?!? | ||
3790 | } | ||
3791 | } | ||
3792 | else | ||
3793 | { | ||
3794 | // Client.Log("Attempted to add a duplicate sequence number (" + | ||
3795 | // packet.Header.m_sequence + ") to the m_needAck dictionary for packet type " + | ||
3796 | // packet.Type.ToString(), Helpers.LogLevel.Warning); | ||
3797 | } | ||
3798 | } | ||
3799 | } | ||
3800 | /// <summary> | ||
3801 | /// Append any ACKs that need to be sent out to this packet | ||
3802 | /// </summary> | ||
3803 | /// <param name="Pack"></param> | ||
3804 | protected virtual void SetPendingAcks(ref Packet Pack) | ||
3805 | { | ||
3806 | |||
3807 | lock (m_pendingAcks) | ||
3808 | { | ||
3809 | // TODO: If we are over MAX_APPENDED_ACKS we should drain off some of these | ||
3810 | if (m_pendingAcks.Count > 0 && m_pendingAcks.Count < MAX_APPENDED_ACKS) | ||
3811 | { | ||
3812 | Pack.Header.AckList = new uint[m_pendingAcks.Count]; | ||
3813 | int i = 0; | ||
3814 | |||
3815 | foreach (uint ack in m_pendingAcks.Values) | ||
3816 | { | ||
3817 | Pack.Header.AckList[i] = ack; | ||
3818 | i++; | ||
3819 | } | ||
3820 | |||
3821 | m_pendingAcks.Clear(); | ||
3822 | Pack.Header.AppendedAcks = true; | ||
3823 | } | ||
3824 | } | ||
3825 | } | ||
3826 | |||
3827 | /// <summary> | 3676 | /// <summary> |
3828 | /// Helper routine to prepare the packet for sending to UDP client | 3677 | /// Helper routine to prepare the packet for sending to UDP client |
3829 | /// This converts it to bytes and puts it on the outgoing buffer | 3678 | /// This converts it to bytes and puts it on the outgoing buffer |
@@ -3834,24 +3683,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
3834 | // Keep track of when this packet was sent out | 3683 | // Keep track of when this packet was sent out |
3835 | Pack.TickCount = System.Environment.TickCount; | 3684 | Pack.TickCount = System.Environment.TickCount; |
3836 | 3685 | ||
3837 | if (!Pack.Header.Resent) | ||
3838 | { | ||
3839 | if (Pack.Header.Sequence == 0) | ||
3840 | { | ||
3841 | Pack.Header.Sequence = NextSeqNum(); | ||
3842 | } | ||
3843 | |||
3844 | if (Pack.Header.Reliable) //DIRTY HACK | ||
3845 | { | ||
3846 | AddAck(Pack); // this adds the need to ack this packet later | ||
3847 | |||
3848 | if (Pack.Type != PacketType.PacketAck && Pack.Type != PacketType.LogoutRequest) | ||
3849 | { | ||
3850 | SetPendingAcks(ref Pack); | ||
3851 | } | ||
3852 | } | ||
3853 | } | ||
3854 | |||
3855 | // Actually make the byte array and send it | 3686 | // Actually make the byte array and send it |
3856 | try | 3687 | try |
3857 | { | 3688 | { |
@@ -3886,249 +3717,22 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
3886 | /// <param name="NewPack"></param> | 3717 | /// <param name="NewPack"></param> |
3887 | public virtual void InPacket(Packet NewPack) | 3718 | public virtual void InPacket(Packet NewPack) |
3888 | { | 3719 | { |
3889 | if (!m_packetProcessingEnabled && NewPack.Type != PacketType.LogoutRequest) | 3720 | m_PacketHandler.InPacket(NewPack); |
3890 | { | ||
3891 | PacketPool.Instance.ReturnPacket(NewPack); | ||
3892 | return; | ||
3893 | } | ||
3894 | |||
3895 | // Handle appended ACKs | ||
3896 | if (NewPack != null) | ||
3897 | { | ||
3898 | if (NewPack.Header.AppendedAcks) | ||
3899 | { | ||
3900 | lock (m_needAck) | ||
3901 | { | ||
3902 | foreach (uint ackedPacketId in NewPack.Header.AckList) | ||
3903 | { | ||
3904 | RemovePacketFromNeedAckList(ackedPacketId); | ||
3905 | } | ||
3906 | } | ||
3907 | } | ||
3908 | |||
3909 | // Handle PacketAck packets | ||
3910 | if (NewPack.Type == PacketType.PacketAck) | ||
3911 | { | ||
3912 | PacketAckPacket ackPacket = (PacketAckPacket)NewPack; | ||
3913 | |||
3914 | lock (m_needAck) | ||
3915 | { | ||
3916 | foreach (PacketAckPacket.PacketsBlock block in ackPacket.Packets) | ||
3917 | { | ||
3918 | uint ackedPackId = block.ID; | ||
3919 | RemovePacketFromNeedAckList(ackedPackId); | ||
3920 | } | ||
3921 | } | ||
3922 | } | ||
3923 | else if ((NewPack.Type == PacketType.StartPingCheck)) | ||
3924 | { | ||
3925 | //reply to pingcheck | ||
3926 | StartPingCheckPacket startPing = (StartPingCheckPacket)NewPack; | ||
3927 | CompletePingCheckPacket endPing = (CompletePingCheckPacket)PacketPool.Instance.GetPacket(PacketType.CompletePingCheck); | ||
3928 | endPing.PingID.PingID = startPing.PingID.PingID; | ||
3929 | OutPacket(endPing, ThrottleOutPacketType.Task); | ||
3930 | } | ||
3931 | else | ||
3932 | { | ||
3933 | LLQueItem item = new LLQueItem(); | ||
3934 | item.Packet = NewPack; | ||
3935 | item.Incoming = true; | ||
3936 | m_packetQueue.Enqueue(item); | ||
3937 | } | ||
3938 | } | ||
3939 | } | ||
3940 | |||
3941 | private void RemovePacketFromNeedAckList(uint ackedPackId) | ||
3942 | { | ||
3943 | Packet ackedPacket; | ||
3944 | if (m_needAck.TryGetValue(ackedPackId, out ackedPacket)) | ||
3945 | { | ||
3946 | m_unAckedBytes -= ackedPacket.ToBytes().Length; | ||
3947 | m_needAck.Remove(ackedPackId); | ||
3948 | |||
3949 | m_packetTracker.PacketAck(ackedPackId); | ||
3950 | } | ||
3951 | } | 3721 | } |
3952 | 3722 | ||
3953 | /// <summary> | 3723 | /// <summary> |
3954 | /// The dreaded OutPacket. This should only be called from withink the ClientStack itself right now | 3724 | /// The dreaded OutPacket. This should only be called from within |
3955 | /// This is the entry point for simulator packets to go out to the client. | 3725 | /// the ClientStack itself right now |
3726 | /// This is the entry point for simulator packets to go out to | ||
3727 | /// the client. | ||
3956 | /// </summary> | 3728 | /// </summary> |
3957 | /// <param name="NewPack"></param> | 3729 | /// <param name="NewPack"></param> |
3958 | /// <param name="throttlePacketType">Corresponds to the type of data that is going out. Enum</param> | 3730 | /// <param name="throttlePacketType">Corresponds to the type of data that is going out. Enum</param> |
3959 | public virtual void OutPacket(Packet NewPack, ThrottleOutPacketType throttlePacketType) | 3731 | public virtual void OutPacket(Packet NewPack, ThrottleOutPacketType throttlePacketType) |
3960 | { | 3732 | { |
3961 | if ((SynchronizeClient != null) && (!IsActive)) | 3733 | m_PacketHandler.OutPacket(NewPack, throttlePacketType); |
3962 | { | ||
3963 | // Sending packet to active client's server. | ||
3964 | if (SynchronizeClient(m_scene, NewPack, m_agentId, throttlePacketType)) | ||
3965 | { | ||
3966 | return; | ||
3967 | } | ||
3968 | } | ||
3969 | |||
3970 | LLQueItem item = new LLQueItem(); | ||
3971 | item.Packet = NewPack; | ||
3972 | item.Incoming = false; | ||
3973 | item.throttleType = throttlePacketType; // Packet throttle type | ||
3974 | m_packetQueue.Enqueue(item); | ||
3975 | m_packetsSent++; | ||
3976 | } | ||
3977 | |||
3978 | # region Low Level Packet Methods | ||
3979 | |||
3980 | protected void ack_pack(Packet Pack) | ||
3981 | { | ||
3982 | if (Pack.Header.Reliable) | ||
3983 | { | ||
3984 | PacketAckPacket ack_it = (PacketAckPacket)PacketPool.Instance.GetPacket(PacketType.PacketAck); | ||
3985 | // TODO: don't create new blocks if recycling an old packet | ||
3986 | ack_it.Packets = new PacketAckPacket.PacketsBlock[1]; | ||
3987 | ack_it.Packets[0] = new PacketAckPacket.PacketsBlock(); | ||
3988 | ack_it.Packets[0].ID = Pack.Header.Sequence; | ||
3989 | ack_it.Header.Reliable = false; | ||
3990 | |||
3991 | OutPacket(ack_it, ThrottleOutPacketType.Unknown); | ||
3992 | } | ||
3993 | /* | ||
3994 | if (Pack.Header.Reliable) | ||
3995 | { | ||
3996 | lock (m_pendingAcks) | ||
3997 | { | ||
3998 | uint sequence = (uint)Pack.Header.m_sequence; | ||
3999 | if (!m_pendingAcks.ContainsKey(sequence)) { m_pendingAcks[sequence] = sequence; } | ||
4000 | } | ||
4001 | }*/ | ||
4002 | } | ||
4003 | |||
4004 | protected void ResendUnacked() | ||
4005 | { | ||
4006 | int now = System.Environment.TickCount; | ||
4007 | |||
4008 | lock (m_needAck) | ||
4009 | { | ||
4010 | foreach (Packet packet in m_needAck.Values) | ||
4011 | { | ||
4012 | if ((now - packet.TickCount > RESEND_TIMEOUT) && (!packet.Header.Resent)) | ||
4013 | { | ||
4014 | //m_log.Debug("[NETWORK]: Resending " + packet.Type.ToString() + " packet, " + | ||
4015 | //(now - packet.TickCount) + "ms have passed"); | ||
4016 | |||
4017 | packet.Header.Resent = true; | ||
4018 | OutPacket(packet, ThrottleOutPacketType.Resend); | ||
4019 | } | ||
4020 | } | ||
4021 | } | ||
4022 | } | 3734 | } |
4023 | 3735 | ||
4024 | protected void SendAcks() | ||
4025 | { | ||
4026 | lock (m_pendingAcks) | ||
4027 | { | ||
4028 | if (m_pendingAcks.Count > 0) | ||
4029 | { | ||
4030 | if (m_pendingAcks.Count > 250) | ||
4031 | { | ||
4032 | // FIXME: Handle the odd case where we have too many pending ACKs queued up | ||
4033 | m_log.Info("[NETWORK]: Too many ACKs queued up!"); | ||
4034 | return; | ||
4035 | } | ||
4036 | |||
4037 | //m_log.Info("[NETWORK]: Sending PacketAck"); | ||
4038 | |||
4039 | int i = 0; | ||
4040 | PacketAckPacket acks = (PacketAckPacket)PacketPool.Instance.GetPacket(PacketType.PacketAck); | ||
4041 | // TODO: don't create new blocks if recycling an old packet | ||
4042 | acks.Packets = new PacketAckPacket.PacketsBlock[m_pendingAcks.Count]; | ||
4043 | |||
4044 | foreach (uint ack in m_pendingAcks.Values) | ||
4045 | { | ||
4046 | acks.Packets[i] = new PacketAckPacket.PacketsBlock(); | ||
4047 | acks.Packets[i].ID = ack; | ||
4048 | i++; | ||
4049 | } | ||
4050 | |||
4051 | acks.Header.Reliable = false; | ||
4052 | OutPacket(acks, ThrottleOutPacketType.Unknown); | ||
4053 | |||
4054 | m_pendingAcks.Clear(); | ||
4055 | } | ||
4056 | } | ||
4057 | } | ||
4058 | |||
4059 | protected void AckTimer_Elapsed(object sender, ElapsedEventArgs ea) | ||
4060 | { | ||
4061 | SendAcks(); | ||
4062 | ResendUnacked(); | ||
4063 | SendPacketStats(); | ||
4064 | // TerrainPacketTrack(); | ||
4065 | } | ||
4066 | |||
4067 | /// <summary> | ||
4068 | /// Keeps track of the packet stats for the simulator stats reporter | ||
4069 | /// </summary> | ||
4070 | protected void SendPacketStats() | ||
4071 | { | ||
4072 | handlerPacketStats = OnPacketStats; | ||
4073 | if (handlerPacketStats != null) | ||
4074 | { | ||
4075 | handlerPacketStats(m_packetsReceived - m_lastPacketsReceivedSentToScene, m_packetsSent - m_lastPacketsSentSentToScene, m_unAckedBytes); | ||
4076 | m_lastPacketsReceivedSentToScene = m_packetsReceived; | ||
4077 | m_lastPacketsSentSentToScene = m_packetsSent; | ||
4078 | } | ||
4079 | } | ||
4080 | |||
4081 | |||
4082 | /// <summary> | ||
4083 | /// Emties out the old packets in the packet duplication tracking table. | ||
4084 | /// </summary> | ||
4085 | protected void ClearOldPacketDupeTracking() | ||
4086 | { | ||
4087 | lock (m_dupeLimiter) | ||
4088 | { | ||
4089 | List<uint> toEliminate = new List<uint>(); | ||
4090 | try | ||
4091 | { | ||
4092 | foreach (uint seq in m_dupeLimiter.Keys) | ||
4093 | { | ||
4094 | PacketDupeLimiter pkdata = null; | ||
4095 | m_dupeLimiter.TryGetValue(seq, out pkdata); | ||
4096 | if (pkdata != null) | ||
4097 | { | ||
4098 | // doing a foreach loop, so we don't want to modify the dictionary while we're searching it | ||
4099 | if (Util.UnixTimeSinceEpoch() - pkdata.timeIn > m_clearDuplicatePacketTrackingOlderThenXSeconds) | ||
4100 | toEliminate.Add(seq); | ||
4101 | } | ||
4102 | } | ||
4103 | } | ||
4104 | catch (InvalidOperationException) | ||
4105 | { | ||
4106 | m_log.Info("[PACKET]: Unable to clear dupe check packet data"); | ||
4107 | } | ||
4108 | |||
4109 | // remove the dupe packets that we detected in the loop above. | ||
4110 | uint[] seqsToRemove = toEliminate.ToArray(); | ||
4111 | for (int i = 0; i < seqsToRemove.Length; i++) | ||
4112 | { | ||
4113 | if (m_dupeLimiter.ContainsKey(seqsToRemove[i])) | ||
4114 | m_dupeLimiter.Remove(seqsToRemove[i]); | ||
4115 | } | ||
4116 | } | ||
4117 | } | ||
4118 | |||
4119 | #endregion | ||
4120 | |||
4121 | public void TriggerTerrainUnackedEvent(int patchX, int patchY) | ||
4122 | { | ||
4123 | handlerUnackedTerrain = OnUnackedTerrain; | ||
4124 | if (handlerUnackedTerrain != null) | ||
4125 | { | ||
4126 | handlerUnackedTerrain(this, patchX, patchY); | ||
4127 | } | ||
4128 | } | ||
4129 | |||
4130 | // Previously ClientView.ProcessPackets | ||
4131 | |||
4132 | public bool AddMoney(int debit) | 3736 | public bool AddMoney(int debit) |
4133 | { | 3737 | { |
4134 | if (m_moneyBalance + debit >= 0) | 3738 | if (m_moneyBalance + debit >= 0) |
@@ -4143,14 +3747,6 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
4143 | } | 3747 | } |
4144 | } | 3748 | } |
4145 | 3749 | ||
4146 | private bool m_packetProcessingEnabled = true; | ||
4147 | |||
4148 | public bool IsActive | ||
4149 | { | ||
4150 | get { return m_packetProcessingEnabled; } | ||
4151 | set { m_packetProcessingEnabled = value; } | ||
4152 | } | ||
4153 | |||
4154 | /// <summary> | 3750 | /// <summary> |
4155 | /// Breaks down the genericMessagePacket into specific events | 3751 | /// Breaks down the genericMessagePacket into specific events |
4156 | /// </summary> | 3752 | /// </summary> |
@@ -4206,31 +3802,8 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
4206 | /// all UDP packets from the client will end up here | 3802 | /// all UDP packets from the client will end up here |
4207 | /// </summary> | 3803 | /// </summary> |
4208 | /// <param name="Pack">libsecondlife.packet</param> | 3804 | /// <param name="Pack">libsecondlife.packet</param> |
4209 | protected void ProcessInPacket(Packet Pack) | 3805 | public void ProcessInPacket(Packet Pack) |
4210 | { | 3806 | { |
4211 | // always ack the packet! | ||
4212 | ack_pack(Pack); | ||
4213 | |||
4214 | // check for duplicate packets.. packets that the client is | ||
4215 | // resending because it didn't receive our ack | ||
4216 | |||
4217 | lock (m_dupeLimiter) | ||
4218 | { | ||
4219 | if (m_dupeLimiter.ContainsKey(Pack.Header.Sequence)) | ||
4220 | { | ||
4221 | //m_log.Info("[CLIENT]: Warning Duplicate packet detected" + Pack.Type.ToString() + " Dropping."); | ||
4222 | return; | ||
4223 | } | ||
4224 | else | ||
4225 | { | ||
4226 | PacketDupeLimiter pkdedupe = new PacketDupeLimiter(); | ||
4227 | pkdedupe.packetId = Pack.Header.ID; | ||
4228 | pkdedupe.pktype = Pack.Type; | ||
4229 | pkdedupe.timeIn = Util.UnixTimeSinceEpoch(); | ||
4230 | m_dupeLimiter.Add(Pack.Header.Sequence, pkdedupe); | ||
4231 | } | ||
4232 | } | ||
4233 | |||
4234 | // check if we've got a local packet handler for this packet.type. See RegisterLocalPacketHandlers() | 3807 | // check if we've got a local packet handler for this packet.type. See RegisterLocalPacketHandlers() |
4235 | if (ProcessPacketMethod(Pack)) | 3808 | if (ProcessPacketMethod(Pack)) |
4236 | { | 3809 | { |
@@ -4702,7 +4275,7 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
4702 | 4275 | ||
4703 | case PacketType.AgentThrottle: | 4276 | case PacketType.AgentThrottle: |
4704 | AgentThrottlePacket atpack = (AgentThrottlePacket)Pack; | 4277 | AgentThrottlePacket atpack = (AgentThrottlePacket)Pack; |
4705 | m_packetQueue.SetThrottleFromClient(atpack.Throttle.Throttles); | 4278 | m_PacketHandler.PacketQueue.SetThrottleFromClient(atpack.Throttle.Throttles); |
4706 | break; | 4279 | break; |
4707 | 4280 | ||
4708 | case PacketType.AgentPause: | 4281 | case PacketType.AgentPause: |
@@ -6648,76 +6221,18 @@ namespace OpenSim.Region.ClientStack.LindenUDP | |||
6648 | 6221 | ||
6649 | public ClientInfo GetClientInfo() | 6222 | public ClientInfo GetClientInfo() |
6650 | { | 6223 | { |
6651 | //MainLog.Instance.Verbose("CLIENT", "GetClientInfo BGN"); | 6224 | ClientInfo info = m_PacketHandler.GetClientInfo(); |
6652 | 6225 | ||
6653 | ClientInfo info = new ClientInfo(); | ||
6654 | info.userEP = this.m_userEndPoint; | 6226 | info.userEP = this.m_userEndPoint; |
6655 | info.proxyEP = this.m_proxyEndPoint; | 6227 | info.proxyEP = this.m_proxyEndPoint; |
6656 | info.agentcircuit = new sAgentCircuitData(RequestClientInfo()); | 6228 | info.agentcircuit = new sAgentCircuitData(RequestClientInfo()); |
6657 | 6229 | ||
6658 | info.pendingAcks = m_pendingAcks; | ||
6659 | |||
6660 | info.needAck = new Dictionary<uint, byte[]>(); | ||
6661 | |||
6662 | lock (m_needAck) | ||
6663 | { | ||
6664 | foreach (uint key in m_needAck.Keys) | ||
6665 | { | ||
6666 | info.needAck.Add(key, m_needAck[key].ToBytes()); | ||
6667 | } | ||
6668 | } | ||
6669 | |||
6670 | /* pending | ||
6671 | QueItem[] queitems = m_packetQueue.GetQueueArray(); | ||
6672 | |||
6673 | MainLog.Instance.Verbose("CLIENT", "Queue Count : [{0}]", queitems.Length); | ||
6674 | |||
6675 | for (int i = 0; i < queitems.Length; i++) | ||
6676 | { | ||
6677 | if (queitems[i].Incoming == false) | ||
6678 | { | ||
6679 | info.out_packets.Add(queitems[i].Packet.ToBytes()); | ||
6680 | MainLog.Instance.Verbose("CLIENT", "Add OutPacket [{0}]", queitems[i].Packet.Type.ToString()); | ||
6681 | } | ||
6682 | } | ||
6683 | */ | ||
6684 | |||
6685 | info.sequence = m_sequence; | ||
6686 | |||
6687 | //MainLog.Instance.Verbose("CLIENT", "GetClientInfo END"); | ||
6688 | |||
6689 | return info; | 6230 | return info; |
6690 | } | 6231 | } |
6691 | 6232 | ||
6692 | public void SetClientInfo(ClientInfo info) | 6233 | public void SetClientInfo(ClientInfo info) |
6693 | { | 6234 | { |
6694 | m_pendingAcks = info.pendingAcks; | 6235 | m_PacketHandler.SetClientInfo(info); |
6695 | |||
6696 | m_needAck = new Dictionary<uint, Packet>(); | ||
6697 | |||
6698 | Packet packet = null; | ||
6699 | int packetEnd = 0; | ||
6700 | byte[] zero = new byte[3000]; | ||
6701 | |||
6702 | foreach (uint key in info.needAck.Keys) | ||
6703 | { | ||
6704 | byte[] buff = info.needAck[key]; | ||
6705 | |||
6706 | packetEnd = buff.Length - 1; | ||
6707 | |||
6708 | try | ||
6709 | { | ||
6710 | packet = PacketPool.Instance.GetPacket(buff, ref packetEnd, zero); | ||
6711 | } | ||
6712 | catch (Exception) | ||
6713 | { | ||
6714 | |||
6715 | } | ||
6716 | |||
6717 | m_needAck.Add(key, packet); | ||
6718 | } | ||
6719 | |||
6720 | m_sequence = info.sequence; | ||
6721 | } | 6236 | } |
6722 | 6237 | ||
6723 | #region Media Parcel Members | 6238 | #region Media Parcel Members |