From 41019b691ba4f7ce04f47d351bb31d826bd63821 Mon Sep 17 00:00:00 2001 From: Mark Sturgill Date: Sat, 12 Oct 2013 15:53:29 -0700 Subject: [PATCH] delta recursion protection flush in send completion --- Server/Item.cs | 28 ++++++++++++++++++++++------ Server/Mobile.cs | 23 +++++++++++++++++++---- Server/Network/MessagePump.cs | 16 +++++++++------- Server/Network/NetState.cs | 6 ++++++ 4 files changed, 56 insertions(+), 17 deletions(-) diff --git a/Server/Item.cs b/Server/Item.cs index 29ff8df21..ef96c2843 100644 --- a/Server/Item.cs +++ b/Server/Item.cs @@ -3039,9 +3039,17 @@ namespace Server { SetFlag( ImplFlag.InQueue, true ); - if (_processing) - Console.WriteLine(new System.Diagnostics.StackTrace()); - m_DeltaQueue.Add( this ); + if (_processing) { + try { + using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) { + op.WriteLine("# {0}", DateTime.UtcNow); + op.WriteLine(new System.Diagnostics.StackTrace()); + op.WriteLine(); + } + } catch { } + } else { + m_DeltaQueue.Add(this); + } } Core.Set(); @@ -3055,9 +3063,17 @@ namespace Server { SetFlag( ImplFlag.InQueue, false ); - if (_processing) - Console.WriteLine(new System.Diagnostics.StackTrace()); - m_DeltaQueue.Remove( this ); + if (_processing) { + try { + using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) { + op.WriteLine("# {0}", DateTime.UtcNow); + op.WriteLine(new System.Diagnostics.StackTrace()); + op.WriteLine(); + } + } catch { } + } else { + m_DeltaQueue.Remove( this ); + } } } diff --git a/Server/Mobile.cs b/Server/Mobile.cs index 00a6d9a43..0556792e3 100644 --- a/Server/Mobile.cs +++ b/Server/Mobile.cs @@ -10005,6 +10005,7 @@ namespace Server } private static Queue m_DeltaQueue = new Queue(); + private static Queue m_DeltaQueueR = new Queue(); private bool m_InDeltaQueue; private MobileDelta m_DeltaFlags; @@ -10020,9 +10021,21 @@ namespace Server { m_InDeltaQueue = true; - if (_processing) - Console.WriteLine(new System.Diagnostics.StackTrace()); - m_DeltaQueue.Enqueue( this ); + if (_processing) { + lock (m_DeltaQueueR) { + m_DeltaQueueR.Enqueue(this); + + try { + using (StreamWriter op = new StreamWriter("delta-recursion.log", true)) { + op.WriteLine("# {0}", DateTime.UtcNow); + op.WriteLine(new System.Diagnostics.StackTrace()); + op.WriteLine(); + } + } catch { } + } + } else { + m_DeltaQueue.Enqueue( this ); + } } Core.Set(); @@ -10524,7 +10537,7 @@ namespace Server } } - public static bool _processing = false; + private static bool _processing = false; public static void ProcessDeltaQueue() { @@ -10533,6 +10546,8 @@ namespace Server Parallel.ForEach( m_DeltaQueue, m => m.ProcessDelta() ); m_DeltaQueue.Clear(); _processing = false; + Parallel.ForEach( m_DeltaQueueR, m => m.ProcessDelta() ); + m_DeltaQueueR.Clear(); #else int count = m_DeltaQueue.Count; int index = 0; diff --git a/Server/Network/MessagePump.cs b/Server/Network/MessagePump.cs index 7a0743131..1309f3c02 100644 --- a/Server/Network/MessagePump.cs +++ b/Server/Network/MessagePump.cs @@ -220,13 +220,15 @@ namespace Server.Network } if ( length >= packetLength ) { - if ( handler.Ingame && ns.Mobile == null ) { - Console.WriteLine( "Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", ns, packetID ); - ns.Dispose(); - break; - } else if ( handler.Ingame && ns.Mobile.Deleted ) { - ns.Dispose(); - break; + if (handler.Ingame) { + if (ns.Mobile == null ) { + Console.WriteLine( "Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", ns, packetID ); + ns.Dispose(); + break; + } else if (ns.Mobile.Deleted) { + ns.Dispose(); + break; + } } ThrottlePacketCallback throttler = handler.ThrottleCallback; diff --git a/Server/Network/NetState.cs b/Server/Network/NetState.cs index a33d43ffa..09c368ae2 100644 --- a/Server/Network/NetState.cs +++ b/Server/Network/NetState.cs @@ -772,6 +772,9 @@ namespace Server.Network { lock ( m_SendQueue ) { gram = m_SendQueue.Dequeue(); + + if (gram == null && m_SendQueue.IsFlushReady) + gram = m_SendQueue.CheckFlushReady(); } if ( gram != null ) { @@ -943,6 +946,9 @@ namespace Server.Network { lock (m_SendQueue) { gram = m_SendQueue.Dequeue(); + + if (gram == null && m_SendQueue.IsFlushReady) + gram = m_SendQueue.CheckFlushReady(); } if (gram != null) {