aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs
diff options
context:
space:
mode:
Diffstat (limited to 'OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs')
-rw-r--r--OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs116
1 files changed, 53 insertions, 63 deletions
diff --git a/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs b/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs
index 3881bdb..80ef95e 100644
--- a/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs
+++ b/OpenSim/Region/ClientStack/LindenUDP/LLUDPServer.cs
@@ -118,6 +118,9 @@ namespace OpenSim.Region.ClientStack.LindenUDP
118 private int m_recvBufferSize; 118 private int m_recvBufferSize;
119 /// <summary>Flag to process packets asynchronously or synchronously</summary> 119 /// <summary>Flag to process packets asynchronously or synchronously</summary>
120 private bool m_asyncPacketHandling; 120 private bool m_asyncPacketHandling;
121 /// <summary>Track whether or not a packet was sent in the
122 /// OutgoingPacketHandler loop so we know when to sleep</summary>
123 private bool m_packetSentLastLoop;
121 124
122 /// <summary>The measured resolution of Environment.TickCount</summary> 125 /// <summary>The measured resolution of Environment.TickCount</summary>
123 public float TickCountResolution { get { return m_tickCountResolution; } } 126 public float TickCountResolution { get { return m_tickCountResolution; } }
@@ -745,10 +748,10 @@ namespace OpenSim.Region.ClientStack.LindenUDP
745 748
746 while (base.IsRunning) 749 while (base.IsRunning)
747 { 750 {
748 IncomingPacket incomingPacket = null;
749
750 try 751 try
751 { 752 {
753 IncomingPacket incomingPacket = null;
754
752 if (packetInbox.Dequeue(100, ref incomingPacket)) 755 if (packetInbox.Dequeue(100, ref incomingPacket))
753 Util.FireAndForget(ProcessInPacket, incomingPacket); 756 Util.FireAndForget(ProcessInPacket, incomingPacket);
754 } 757 }
@@ -769,83 +772,70 @@ namespace OpenSim.Region.ClientStack.LindenUDP
769 // on to en-US to avoid number parsing issues 772 // on to en-US to avoid number parsing issues
770 Culture.SetCurrentCulture(); 773 Culture.SetCurrentCulture();
771 774
772 int now = Environment.TickCount;
773 int elapsedMS = 0;
774 int elapsed100MS = 0;
775 int elapsed500MS = 0;
776
777 while (base.IsRunning) 775 while (base.IsRunning)
778 { 776 {
779 try 777 try
780 { 778 {
781 bool resendUnacked = false; 779 m_packetSentLastLoop = false;
782 bool sendAcks = false;
783 bool sendPings = false;
784 bool packetSent = false;
785 780
786 elapsedMS += Environment.TickCount - now; 781 m_scene.ClientManager.ForEachSync(ClientOutgoingPacketHandler);
787 782
788 // Check for pending outgoing resends every 100ms 783 // If no packets at all were sent, sleep to avoid chewing up CPU cycles
789 if (elapsedMS >= 100) 784 // when there is nothing to do
790 { 785 if (!m_packetSentLastLoop)
791 resendUnacked = true; 786 Thread.Sleep(20);
792 elapsedMS -= 100; 787 }
793 ++elapsed100MS; 788 catch (Exception ex)
794 } 789 {
795 // Check for pending outgoing ACKs every 500ms 790 m_log.Error("[LLUDPSERVER]: OutgoingPacketHandler loop threw an exception: " + ex.Message, ex);
796 if (elapsed100MS >= 5) 791 }
797 { 792 }
798 sendAcks = true; 793 }
799 elapsed100MS = 0;
800 ++elapsed500MS;
801 }
802 // Send pings to clients every 5000ms
803 if (elapsed500MS >= 10)
804 {
805 sendPings = true;
806 elapsed500MS = 0;
807 }
808 794
809 m_scene.ClientManager.ForEachSync( 795 private void ClientOutgoingPacketHandler(IClientAPI client)
810 delegate(IClientAPI client) 796 {
797 try
798 {
799 if (client is LLClientView)
800 {
801 LLUDPClient udpClient = ((LLClientView)client).UDPClient;
802
803 int thisTick = Environment.TickCount & Int32.MaxValue;
804 int elapsedMS = thisTick - udpClient.TickLastOutgoingPacketHandler;
805
806 if (udpClient.IsConnected)
807 {
808 // Check for pending outgoing resends every 100ms
809 if (elapsedMS >= 100)
811 { 810 {
812 try 811 ResendUnacked(udpClient);
812
813 // Check for pending outgoing ACKs every 500ms
814 if (elapsedMS >= 500)
813 { 815 {
814 if (client is LLClientView) 816 SendAcks(udpClient);
817
818 // Send pings to clients every 5000ms
819 if (elapsedMS >= 5000)
815 { 820 {
816 LLUDPClient udpClient = ((LLClientView)client).UDPClient; 821 SendPing(udpClient);
817
818 if (udpClient.IsConnected)
819 {
820 if (udpClient.DequeueOutgoing())
821 packetSent = true;
822 if (resendUnacked)
823 ResendUnacked(udpClient);
824 if (sendAcks)
825 {
826 SendAcks(udpClient);
827 udpClient.SendPacketStats();
828 }
829 if (sendPings)
830 SendPing(udpClient);
831 }
832 } 822 }
833 } 823 }
834 catch (Exception ex)
835 {
836 m_log.Error("[LLUDPSERVER]: OutgoingPacketHandler iteration for " + client.Name + " threw an exception: " + ex.Message, ex);
837 }
838 } 824 }
839 );
840 825
841 if (!packetSent) 826 // Dequeue any outgoing packets that are within the throttle limits
842 Thread.Sleep(20); 827 if (udpClient.DequeueOutgoing())
843 } 828 m_packetSentLastLoop = true;
844 catch (Exception ex) 829 }
845 { 830
846 m_log.Error("[LLUDPSERVER]: OutgoingPacketHandler loop threw an exception: " + ex.Message, ex); 831 udpClient.TickLastOutgoingPacketHandler = thisTick;
847 } 832 }
848 } 833 }
834 catch (Exception ex)
835 {
836 m_log.Error("[LLUDPSERVER]: OutgoingPacketHandler iteration for " + client.Name +
837 " threw an exception: " + ex.Message, ex);
838 }
849 } 839 }
850 840
851 private void ProcessInPacket(object state) 841 private void ProcessInPacket(object state)