Пример #1
0
        public NetState(Socket socket, MessagePump messagePump)
        {
            m_Socket      = socket;
            m_Buffer      = new ByteQueue();
            m_Seeded      = false;
            m_Running     = false;
            m_RecvBuffer  = m_ReceiveBufferPool.AcquireBuffer();
            m_MessagePump = messagePump;
            m_Gumps       = new List <Gump>();
            m_HuePickers  = new List <HuePicker>();
            m_Menus       = new List <IMenu>();
            m_Trades      = new List <SecureTrade>();

            m_SendQueue = new SendQueue();

            m_NextCheckActivity = DateTime.Now + TimeSpan.FromMinutes(0.5);

            m_Instances.Add(this);

            try {
                m_Address  = Utility.Intern((( IPEndPoint )m_Socket.RemoteEndPoint).Address);
                m_ToString = m_Address.ToString();
            } catch (Exception ex) {
                TraceException(ex);
                m_Address  = IPAddress.None;
                m_ToString = "(error)";
            }

            m_ConnectedOn = DateTime.Now;

            if (m_CreatedCallback != null)
            {
                m_CreatedCallback(this);
            }
        }
Пример #2
0
        /** client constructor, used to connect to other UO servers */
        public NetState(IPEndPoint connectTo, MessagePump messagePump)
        {
            m_Socket      = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
            m_EndPoint    = connectTo;
            m_Buffer      = new ByteQueue();
            m_Seeded      = true;
            m_Running     = false;
            m_Client      = true;
            m_RecvBuffer  = m_ReceiveBufferPool.AquireBuffer();
            m_MessagePump = messagePump;

            m_SendQueue = new SendQueue();

            m_NextCheckActivity = DateTime.Now + TimeSpan.FromMinutes(0.5);

            m_Instances.Add(this);

            try {
                m_Address  = m_EndPoint.Address;
                m_ToString = "[To GameServer " + m_EndPoint.ToString() + "]";
            } catch { m_Address = IPAddress.None; m_ToString = "(error)"; }

            if (m_CreatedCallback != null)
            {
                m_CreatedCallback(this);
            }
        }
Пример #3
0
        public NetState(Socket socket, MessagePump messagePump)
        {
            m_Socket      = socket;
            m_Buffer      = new ByteQueue();
            m_Seeded      = false;
            m_Running     = false;
            m_RecvBuffer  = m_ReceiveBufferPool.AquireBuffer();
            m_MessagePump = messagePump;

            m_SendQueue = new SendQueue();

            m_NextCheckActivity = DateTime.Now + TimeSpan.FromMinutes(0.5);

            m_Instances.Add(this);

            try{ m_Address = ((IPEndPoint)m_Socket.RemoteEndPoint).Address; m_ToString = m_Address.ToString(); }
            catch { m_Address = IPAddress.None; m_ToString = "(error)"; }

            m_Super = Core.Config.Login.IsSuperClient(m_ToString);

            if (m_CreatedCallback != null)
            {
                m_CreatedCallback(this);
            }
        }
Пример #4
0
        public NetState( Socket socket, NetServer netServer )
        {
            m_Socket = socket;
            m_NetServer = netServer;
            m_Buffer = new ByteQueue();
            m_Running = false;
            m_RecvBuffer = m_ReceiveBufferPool.AcquireBuffer();
            m_SendQueue = new SendQueue();

            m_NextCheckActivity = DateTime.Now + TimeSpan.FromMinutes( 0.5 );

            try
            {
                m_Address = ( (IPEndPoint) m_Socket.RemoteEndPoint ).Address;
                m_ToString = m_Address.ToString();
            }
            catch ( Exception ex )
            {
                TraceException( ex );
                m_Address = IPAddress.None;
                m_ToString = "(error)";
            }

            if ( m_CreatedCallback != null )
                m_CreatedCallback( this );
        }
Пример #5
0
        private static bool HandleSeed(NetState ns, ByteQueue buffer)
        {
            if (buffer.GetPacketID() == 0xEF)
            {
                // new packet in client	6.0.5.0	replaces the traditional seed method with a	seed packet
                // 0xEF	= 239 =	multicast IP, so this should never appear in a normal seed.	 So	this is	backwards compatible with older	clients.
                ns.Seeded = true;
                return(true);
            }
            else if (buffer.Length >= 4)
            {
                byte[] m_Peek = new byte[4];

                buffer.Dequeue(m_Peek, 0, 4);

                int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

                if (seed == 0)
                {
                    Utility.WriteConsole(ConsoleColor.Yellow, "Login: {0}: Invalid client detected, disconnecting", ns);
                    ns.Dispose();
                    return(false);
                }

                ns.m_Seed = seed;
                ns.Seeded = true;
                return(true);
            }
            else
            {
                return(false);
            }
        }
Пример #6
0
        private void InvokeReceived(NetState ns, ByteQueue buffer, out bool throttle)
        {
            throttle = false;

            if (Received != null)
            {
                Received(ns, buffer, out throttle);
            }
        }
Пример #7
0
        public virtual void Dispose(bool flush)
        {
            if (m_Socket == null || m_Disposing)
            {
                return;
            }

            m_Disposing = true;

            if (flush)
            {
                flush = Flush();
            }

            try {
                m_Socket.Shutdown(SocketShutdown.Both);
            } catch (SocketException ex) {
                TraceException(ex);
            }

            try {
                m_Socket.Close();
            } catch (SocketException ex) {
                TraceException(ex);
            }

            if (m_RecvBuffer != null)
            {
                lock (m_ReceiveBufferPool)
                    m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
            }

            m_Socket = null;

            m_Buffer     = null;
            m_RecvBuffer = null;

#if NewAsyncSockets
            m_ReceiveEventArgs = null;
            m_SendEventArgs    = null;
#else
            m_OnReceive = null;
            m_OnSend    = null;
#endif

            m_Running = false;

            lock (m_Disposed)
                m_Disposed.Enqueue(this);

            lock (m_SendQueue)
                if (/*!flush &&*/ !m_SendQueue.IsEmpty)
                {
                    m_SendQueue.Clear();
                }
        }
Пример #8
0
        public virtual void Dispose(bool flush)
        {
            // Genova: Usuário desconectando do servidor...
            if (m_Mobile is Mobile)
            {
                ControladorODBC.ODBCDispose(m_Mobile);
            }

            if (m_Socket == null || m_Disposing)
            {
                return;
            }

            m_Disposing = true;

            if (flush)
            {
                flush = Flush();
            }

            try {
                m_Socket.Shutdown(SocketShutdown.Both);
            } catch (SocketException ex) {
                TraceException(ex);
            }

            try {
                m_Socket.Close();

                SocketPool.ReleaseSocket(m_Socket);
            } catch (SocketException ex) {
                TraceException(ex);
            }

            if (m_RecvBuffer != null)
            {
                m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
            }

            m_Socket = null;

            m_Buffer     = null;
            m_RecvBuffer = null;
            m_OnReceive  = null;
            m_OnSend     = null;
            m_Running    = false;

            m_Disposed.Enqueue(this);

            if (/*!flush &&*/ !m_SendQueue.IsEmpty)
            {
                lock (m_SendQueue)
                    m_SendQueue.Clear();
            }
        }
Пример #9
0
        public void FinishDispose()
        {
            if (m_DisposeFinished)
            {
                return;
            }

            m_DisposeFinished = true;

            try
            {
                m_Socket.Shutdown(SocketShutdown.Both);
            }
            catch (SocketException ex)
            {
                TraceException(ex);
            }

            try
            {
                m_Socket.Close();
            }
            catch (SocketException ex)
            {
                TraceException(ex);
            }

            if (m_RecvBuffer != null)
            {
                m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
            }

            m_Socket = null;

            m_Buffer     = null;
            m_RecvBuffer = null;
            m_Running    = false;

            m_NetServer.OnDisposed(this);

            if (!m_SendQueue.IsEmpty)
            {
                lock (m_SendQueue)
                    m_SendQueue.Clear();
            }
        }
Пример #10
0
        private bool HandleSeed(NetState ns, ByteQueue buffer)
        {
            #region Enhance Client
            if (buffer.GetPacketID() == 0xFF)
            {
                // Packet 255 = 0xFF = Client KR.
                ns.IsKRClient = true;
                Console.WriteLine("KR-Client detected", ns);
            }
            #endregion
            if (buffer.GetPacketID() == 0xEF)
            {
                // new packet in client	6.0.5.0	replaces the traditional seed method with a	seed packet
                // 0xEF	= 239 =	multicast IP, so this should never appear in a normal seed.	 So	this is	backwards compatible with older	clients.
                ns.Seeded = true;
                return(true);
            }
            else if (buffer.Length >= 4)
            {
                var m_Peek = new byte[4];

                buffer.Dequeue(m_Peek, 0, 4);

                int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

                if (seed == 0)
                {
                    Utility.PushColor(ConsoleColor.Green);
                    Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns);
                    Utility.PopColor();
                    ns.Dispose();
                    return(false);
                }

                ns.m_Seed = seed;
                ns.Seeded = true;
                return(true);
            }
            else
            {
                return(false);
            }
        }
Пример #11
0
        public NetState(Socket socket, MessagePump messagePump)
        {
            Socket   = socket;
            m_Buffer = new ByteQueue();

            m_Running     = false;
            m_RecvBuffer  = m_ReceiveBufferPool.AcquireBuffer();
            m_MessagePump = messagePump;

            m_Gumps      = new List <Gump>();
            m_HuePickers = new List <HuePicker>();
            m_Menus      = new List <IMenu>();
            m_Trades     = new List <SecureTrade>();

            m_SendQueue = new SendQueue();

            m_NextCheckActivity = Core.TickCount + 30000;

            m_Instances.Add(this);

            try
            {
                m_Address  = Utility.Intern(((IPEndPoint)Socket.RemoteEndPoint).Address);
                m_ToString = m_Address.ToString();
            }
            catch (Exception ex)
            {
                TraceException(ex);
                m_Address  = IPAddress.None;
                m_ToString = "(error)";
            }

            m_ConnectedOn = DateTime.UtcNow;

            UpdateRange = Core.GlobalUpdateRange;

            if (CreatedCallback != null)
            {
                CreatedCallback(this);
            }
        }
Пример #12
0
        private void HandlePending()
        {
            lock ( m_PendingQueue )
            {
                while (m_PendingQueue.Count > 0)
                {
                    NetState ns = m_PendingQueue.Dequeue();

                    if (ns.Running)
                    {
                        ByteQueue buffer   = ns.Buffer;
                        bool      throttle = false;

                        if (buffer != null && buffer.Length > 0)
                        {
                            lock ( buffer )
                            {
                                InvokeReceived(ns, buffer, out throttle);
                            }
                        }

                        if (ns.Running)
                        {
                            if (throttle)
                            {
                                m_ThrottledQueue.Enqueue(ns);
                            }
                            else
                            {
                                ns.Continue();
                            }
                        }
                    }
                }

                while (m_ThrottledQueue.Count > 0)
                {
                    m_PendingQueue.Enqueue(m_ThrottledQueue.Dequeue());
                }
            }
        }
Пример #13
0
        public void Dispose(bool flush)
        {
            if (m_Socket == null || m_Disposing)
            {
                return;
            }

            m_Disposing = true;

            if (flush)
            {
                flush = Flush();
            }

            try { m_Socket.Shutdown(SocketShutdown.Both); }
            catch {}

            try { m_Socket.Close(); }
            catch {}

            if (m_RecvBuffer != null)
            {
                m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
            }

            m_Socket = null;

            m_Buffer     = null;
            m_RecvBuffer = null;
            m_OnReceive  = null;
            m_OnSend     = null;
            m_Running    = false;

            m_Disposed.Enqueue(this);

            if (/*!flush &&*/ !m_SendQueue.IsEmpty)
            {
                lock (m_SendQueue)
                    m_SendQueue.Clear();
            }
        }
Пример #14
0
        private void FinishDisposeNoLock()
        {
            if (m_DisposeFinished)
            {
                return;
            }

            m_DisposeFinished = true;

            try { m_Socket.Shutdown(SocketShutdown.Both); }
            catch {}

            try { m_Socket.Close(); }
            catch {}

            if (m_RecvBuffer != null)
            {
                m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
            }

            m_Socket = null;

            m_Buffer     = null;
            m_RecvBuffer = null;
            m_OnReceive  = null;
            m_OnSend     = null;
            m_Running    = false;

            lock (m_Disposed)
                m_Disposed.Enqueue(this);

            if (/*!flush &&*/ !m_SendQueue.IsEmpty)
            {
                lock (m_SendQueue)
                    m_SendQueue.Clear();
            }
        }
Пример #15
0
        public static bool HandleSeed(NetState ns, ByteQueue buffer)
        {
            if (buffer.GetPacketID() == 0xEF)
            {
                // new packet in client	6.0.5.0	replaces the traditional seed method with a	seed packet
                // 0xEF	= 239 =	multicast IP, so this should never appear in a normal seed.	 So	this is	backwards compatible with older	clients.
                ns.Seeded = true;
                return(true);
            }

            if (buffer.Length >= 4)
            {
                byte[] m_Peek = new byte[4];

                buffer.Dequeue(m_Peek, 0, 4);

                uint seed = (uint)((m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3]);

                if (seed == 0)
                {
                    Utility.PushColor(ConsoleColor.Red);
                    Console.WriteLine("Login: {0}: Invalid Client", ns);
                    Utility.PopColor();

                    ns.Dispose();

                    return(false);
                }

                ns.Seed   = seed;
                ns.Seeded = true;

                return(true);
            }

            return(false);
        }
Пример #16
0
        public bool HandleReceive(NetState ns)
        {
            ByteQueue buffer = ns.Buffer;

            if (buffer == null || buffer.Length <= 0)
            {
                return(true);
            }

            lock ( buffer )
            {
                int length = buffer.Length;

                if (!ns.Seeded)
                {
                    if (buffer.GetPacketID() == 0xEF)
                    {
                        // new packet in client 6.0.5.0 replaces the traditional seed method with a seed packet
                        // 0xEF = 239 = multicast IP, so this should never appear in a normal seed.  So this is backwards compatible with older clients.
                        ns.Seeded = true;
                    }
                    else if (buffer.Length >= 4)
                    {
                        buffer.Dequeue(m_Peek, 0, 4);

                        int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

                        if (seed == 0)
                        {
                            Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns);
                            ns.Dispose();
                            return(false);
                        }

                        ns.m_Seed = seed;
                        ns.Seeded = true;

                        length = buffer.Length;
                    }
                    else
                    {
                        return(true);
                    }
                }

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (!ns.SentFirstPacket && packetID != 0xF0 && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && packetID != 0x91 && packetID != 0xA4 && packetID != 0xEF)
                    {
                        Console.WriteLine("Client: {0}: Encrypted client detected, disconnecting", ns);
                        ns.Dispose();
                        break;
                    }

                    PacketHandler handler = ns.GetHandler(packetID);

                    if (handler == null)
                    {
                        byte[] data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);

                        new PacketReader(data, length, false).Trace(ns);

                        break;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                break;
                            }
                        }
                        else
                        {
                            break;
                        }
                    }

                    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;
                        }
                        else
                        {
                            ThrottlePacketCallback throttler = handler.ThrottleCallback;

                            if (throttler != null && !throttler(ns))
                            {
                                m_Throttled.Enqueue(ns);
                                return(false);
                            }

                            PacketReceiveProfile prof = PacketReceiveProfile.Acquire(packetID);

                            if (prof != null)
                            {
                                prof.Start();
                            }

                            byte[] packetBuffer;

                            if (BufferSize >= packetLength)
                            {
                                packetBuffer = m_Buffers.AcquireBuffer();
                            }
                            else
                            {
                                packetBuffer = new byte[packetLength];
                            }

                            packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                            PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                            handler.OnReceive(ns, r);
                            length = buffer.Length;

                            if (BufferSize >= packetLength)
                            {
                                m_Buffers.ReleaseBuffer(packetBuffer);
                            }

                            if (prof != null)
                            {
                                prof.Finish(packetLength);
                            }
                        }
                    }
                    else
                    {
                        break;
                    }
                }
            }

            return(true);
        }
Пример #17
0
        public void HandleReceive(NetState ns)
        {
            ByteQueue buffer = ns.Buffer;

            if (buffer == null || buffer.Length <= 0)
            {
                return;
            }

            lock (buffer)
            {
                if (!ns.Seeded)
                {
                    if (!HandleSeed(ns, buffer))
                    {
                        return;
                    }
                }

                int length = buffer.Length;

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (CheckEncrypted(ns, packetID))
                    {
                        break;
                    }

                    PacketHandler handler = ns.GetHandler(packetID);

                    if (handler == null)
                    {
                        byte[] data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);
                        new PacketReader(data, length, false).Trace(ns);
                        break;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                break;
                            }
                        }
                        else
                        {
                            break;
                        }
                    }

                    if (length >= packetLength)
                    {
                        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;

                        if (throttler != null && !throttler(ns))
                        {
                            // must be one of the other throttled packets
                            m_Throttled.Enqueue(ns);
                            return;
                        }

                        PacketReceiveProfile prof = null;

                        if (Core.Profiling)
                        {
                            prof = PacketReceiveProfile.Acquire(packetID);
                        }

                        if (prof != null)
                        {
                            prof.Start();
                        }

                        byte[] packetBuffer;

                        if (BufferSize >= packetLength)
                        {
                            packetBuffer = m_Buffers.AcquireBuffer();
                        }
                        else
                        {
                            packetBuffer = new byte[packetLength];
                        }

                        packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                        PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                        handler.OnReceive(ns, r);
                        length = buffer.Length;

                        if (BufferSize >= packetLength)
                        {
                            m_Buffers.ReleaseBuffer(packetBuffer);
                        }

                        if (prof != null)
                        {
                            prof.Finish(packetLength);
                        }
                    }
                    else
                    {
                        break;
                    }
                }
            }
        }
Пример #18
0
        public void HandleReceive(NetState ns)
        {
            ByteQueue buffer = ns.Buffer;

            if (buffer == null || buffer.Length <= 0)
            {
                return;
            }

            lock (buffer)
            {
                if (!ns.Seeded)
                {
                    if (!HandleSeed(ns, buffer))
                    {
                        return;
                    }
                }

                int length = buffer.Length;

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (CheckEncrypted(ns, packetID))
                    {
                        break;
                    }

                    PacketHandler handler = ns.GetHandler(packetID);

                    if (handler == null)
                    {
                        var data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);
                        new PacketReader(data, length, false).Trace(ns);
                        break;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                break;
                            }
                        }
                        else
                        {
                            break;
                        }
                    }

                    if (length >= packetLength)
                    {
                        if (handler.Ingame)
                        {
                            if (ns.Mobile == null)
                            {
                                Utility.PushColor(ConsoleColor.DarkRed);
                                Console.WriteLine(
                                    "Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", ns, packetID);
                                Utility.PopColor();
                                ns.Dispose();
                                break;
                            }
                            else if (ns.Mobile.Deleted)
                            {
                                ns.Dispose();
                                break;
                            }
                        }

                        ThrottlePacketCallback throttler = handler.ThrottleCallback;

                        if (throttler != null && !throttler(ns))
                        {
                            m_Throttled.Enqueue(ns);
                            return;
                        }

                        PacketReceiveProfile prof = null;

                        if (Core.Profiling)
                        {
                            prof = PacketReceiveProfile.Acquire(packetID);
                        }

                        if (prof != null)
                        {
                            prof.Start();
                        }

                        byte[] packetBuffer;

                        if (BufferSize >= packetLength)
                        {
                            packetBuffer = m_Buffers.AcquireBuffer();
                        }
                        else
                        {
                            packetBuffer = new byte[packetLength];
                        }

                        packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                        PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                        handler.OnReceive(ns, r);
                        length = buffer.Length;

                        if (BufferSize >= packetLength)
                        {
                            m_Buffers.ReleaseBuffer(packetBuffer);
                        }

                        if (prof != null)
                        {
                            prof.Finish(packetLength);
                        }
                    }
                    else
                    {
                        break;
                    }
                }
            }
            #region Enhance Client
            // Would be nicer to detect the enhanced client in clientversion.cs
            // It seems that UOKR-EH sends a version number bigger 66.0.0.0, UOSA-EH bigger 67.0.0.0
            try
            {
                if (ns.Version.Major > 8)
                {
                    ns.IsKRClient = true;
                }
            }
            //Standard classic client does not display version this early, so we can rule SA enhanced client out
            catch
            {
                ns.IsKRClient = false;
            }
            return;

            #endregion
        }
Пример #19
0
        public bool HandleReceive(NetState ns)
        {
            ByteQueue buffer = ns.Buffer;

            if (buffer == null || buffer.Length <= 0)
            {
                return(true);
            }

            lock ( buffer )
            {
                int length = buffer.Length;

                if (!ns.Seeded)
                {
                    if (buffer.Length >= 4)
                    {
                        buffer.Dequeue(m_Peek, 0, 4);

                        int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

                        if (seed == 0)
                        {
                            Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns);
                            ns.Dispose();
                            return(false);
                        }

                        ns.m_Seed = seed;
                        ns.Seeded = true;

                        length = buffer.Length;
                    }
                    else
                    {
                        return(true);
                    }
                }

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (!ns.SentFirstPacket && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && packetID != 0x91 && packetID != 0xA4)
                    {
                        Console.WriteLine("Client: {0}: Encrypted client detected, disconnecting", ns);
                        ns.Dispose();
                        break;
                    }

                    PacketHandler handler = PacketHandlers.GetHandler(packetID);

                    if (handler == null)
                    {
                        byte[] data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);

                        new PacketReader(data, length, false).Trace(ns);

                        break;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                break;
                            }
                        }
                        else
                        {
                            break;
                        }
                    }

                    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;
                        }
                        else
                        {
                            ThrottlePacketCallback throttler = handler.ThrottleCallback;

                            if (throttler != null && !throttler(ns))
                            {
                                m_Throttled.Enqueue(ns);
                                return(false);
                            }

                            PacketProfile profile = PacketProfile.GetIncomingProfile(packetID);
                            DateTime      start   = (profile == null ? DateTime.MinValue : DateTime.Now);

                            byte[] packetBuffer;

                            if (BufferSize >= packetLength)
                            {
                                packetBuffer = m_Buffers.AcquireBuffer();
                            }
                            else
                            {
                                packetBuffer = new byte[packetLength];
                            }

                            packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                            PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                            handler.OnReceive(ns, r);
                            length = buffer.Length;

                            if (BufferSize >= packetLength)
                            {
                                m_Buffers.ReleaseBuffer(packetBuffer);
                            }

                            if (profile != null)
                            {
                                profile.Record(packetLength, DateTime.Now - start);
                            }
                        }
                    }
                    else
                    {
                        break;
                    }
                }
            }

            return(true);
        }
Пример #20
0
        private void OnReceived(NetState state, ByteQueue buffer, out bool throttle)
        {
            throttle = false;
            GameClient client;

            if (!m_Clients.TryGetValue(state, out client))
            {
                Logger.Error("Inconsistent game server state: game client for {0} not found", state);
                return;
            }

            if (!client.Seeded)
            {
                if (buffer.GetPacketID() == 0xEF)
                {
                    client.Seeded = true;
                }
                else if (buffer.Length >= 4)
                {
                    byte[] peek = new byte[4];
                    buffer.Dequeue(peek, 0, 4);

                    int seed = (peek[0] << 24) | (peek[1] << 16) | (peek[2] << 8) | peek[3];

                    if (seed == 0)
                    {
                        Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", client);
                        client.Dispose();

                        return;
                    }

                    client.m_Seed = seed;
                    client.Seeded = true;
                }
                else
                {
                    return;                     // Need at least 4 bytes for the seed
                }
            }

            int length = buffer.Length;

            while (length > 0 && buffer.Length > 0)
            {
                int packetID = buffer.GetPacketID();

                if (!client.SentFirstPacket && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && packetID != 0x91 && packetID != 0xA4 && packetID != 0xEF)
                {
                    Console.WriteLine("Client: {0}: Encrypted client detected, disconnecting", client);
                    client.Dispose();
                    return;
                }

                PacketHandler handler = m_Handlers.GetHandler(packetID);

                if (handler == null)
                {
                    byte[] data = new byte[length];
                    length = buffer.Dequeue(data, 0, length);

                    if (Environment.Logging)
                    {
                        PacketReader reader = PacketReader.CreateInstance(data, length, false);
                        reader.Trace(client);
                        PacketReader.ReleaseInstance(reader);
                    }

                    return;
                }

                int packetLength = handler.Length;

                if (packetLength == 0)
                {
                    // Dynamic length packet. Need at leaset 3 bytes (1 packet cmd + 2 length)

                    if (length >= 3)
                    {
                        packetLength = buffer.GetPacketLength();

                        if (packetLength < 3)
                        {
                            client.Dispose();
                            return;
                        }
                    }
                    else
                    {
                        break;
                    }
                }

                if (length >= packetLength)
                {
                    if (handler.Ingame && client.Mobile == null)
                    {
                        Console.WriteLine("Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", client, packetID);
                        client.Dispose();
                        return;
                    }
                    else if (handler.Ingame && client.Mobile.Deleted)
                    {
                        client.Dispose();
                        return;
                    }
                    else
                    {
                        ThrottlePacketCallback throttler = handler.ThrottleCallback;

                        if (throttler != null && !throttler(client))
                        {
                            throttle = true;
                            return;
                        }

                        PacketProfile profile = PacketProfile.GetIncomingProfile(packetID);
                        DateTime      start   = (profile == null ? DateTime.MinValue : DateTime.Now);

                        byte[] packetBuffer;

                        if (BufferSize >= packetLength)
                        {
                            packetBuffer = m_Buffers.AcquireBuffer();
                        }
                        else
                        {
                            packetBuffer = new byte[packetLength];
                        }

                        packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                        PacketReader reader = PacketReader.CreateInstance(packetBuffer, packetLength, handler.Length != 0);

                        try
                        {
                            handler.OnReceive(client, reader);
                        }
                        catch (Exception e)
                        {
                            Logger.Error("Exception disarmed in HandleReceive from {0}: {1}", client.Address, e);
                        }

                        PacketReader.ReleaseInstance(reader);

                        length = buffer.Length;

                        if (BufferSize >= packetLength)
                        {
                            m_Buffers.ReleaseBuffer(packetBuffer);
                        }

                        if (profile != null)
                        {
                            profile.Record(packetLength, DateTime.Now - start);
                        }
                    }
                }
                else
                {
                    break;
                }
            }
        }
Пример #21
0
        private void OnReceived( NetState state, ByteQueue buffer, out bool throttle )
        {
            throttle = false;
            GameClient client;

            if ( !m_Clients.TryGetValue( state, out client ) )
            {
                Logger.Error( "Inconsistent game server state: game client for {0} not found", state );
                return;
            }

            if ( !client.Seeded )
            {
                if ( buffer.GetPacketID() == 0xEF )
                {
                    client.Seeded = true;
                }
                else if ( buffer.Length >= 4 )
                {
                    byte[] peek = new byte[4];
                    buffer.Dequeue( peek, 0, 4 );

                    int seed = ( peek[0] << 24 ) | ( peek[1] << 16 ) | ( peek[2] << 8 ) | peek[3];

                    if ( seed == 0 )
                    {
                        Console.WriteLine( "Login: {0}: Invalid client detected, disconnecting", client );
                        client.Dispose();

                        return;
                    }

                    client.m_Seed = seed;
                    client.Seeded = true;
                }
                else
                {
                    return; // Need at least 4 bytes for the seed
                }
            }

            int length = buffer.Length;

            while ( length > 0 && buffer.Length > 0 )
            {
                int packetID = buffer.GetPacketID();

                if ( !client.SentFirstPacket && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && packetID != 0x91 && packetID != 0xA4 && packetID != 0xEF )
                {
                    Console.WriteLine( "Client: {0}: Encrypted client detected, disconnecting", client );
                    client.Dispose();
                    return;
                }

                PacketHandler handler = m_Handlers.GetHandler( packetID );

                if ( handler == null )
                {
                    byte[] data = new byte[length];
                    length = buffer.Dequeue( data, 0, length );

                    if ( Environment.Logging )
                    {
                        PacketReader reader = PacketReader.CreateInstance( data, length, false );
                        reader.Trace( client );
                        PacketReader.ReleaseInstance( reader );
                    }

                    return;
                }

                int packetLength = handler.Length;

                if ( packetLength == 0 )
                {
                    // Dynamic length packet. Need at leaset 3 bytes (1 packet cmd + 2 length)

                    if ( length >= 3 )
                    {
                        packetLength = buffer.GetPacketLength();

                        if ( packetLength < 3 )
                        {
                            client.Dispose();
                            return;
                        }
                    }
                    else
                    {
                        break;
                    }
                }

                if ( length >= packetLength )
                {
                    if ( handler.Ingame && client.Mobile == null )
                    {
                        Console.WriteLine( "Client: {0}: Sent ingame packet (0x{1:X2}) before having been attached to a mobile", client, packetID );
                        client.Dispose();
                        return;
                    }
                    else if ( handler.Ingame && client.Mobile.Deleted )
                    {
                        client.Dispose();
                        return;
                    }
                    else
                    {
                        ThrottlePacketCallback throttler = handler.ThrottleCallback;

                        if ( throttler != null && !throttler( client ) )
                        {
                            throttle = true;
                            return;
                        }

                        PacketProfile profile = PacketProfile.GetIncomingProfile( packetID );
                        DateTime start = ( profile == null ? DateTime.MinValue : DateTime.Now );

                        byte[] packetBuffer;

                        if ( BufferSize >= packetLength )
                            packetBuffer = m_Buffers.AcquireBuffer();
                        else
                            packetBuffer = new byte[packetLength];

                        packetLength = buffer.Dequeue( packetBuffer, 0, packetLength );

                        PacketReader reader = PacketReader.CreateInstance( packetBuffer, packetLength, handler.Length != 0 );

                        try
                        {
                            handler.OnReceive( client, reader );
                        }
                        catch ( Exception e )
                        {
                            Logger.Error( "Exception disarmed in HandleReceive from {0}: {1}", client.Address, e );
                        }

                        PacketReader.ReleaseInstance( reader );

                        length = buffer.Length;

                        if ( BufferSize >= packetLength )
                            m_Buffers.ReleaseBuffer( packetBuffer );

                        if ( profile != null )
                            profile.Record( packetLength, DateTime.Now - start );
                    }
                }
                else
                {
                    break;
                }
            }
        }
Пример #22
0
        private bool HandleReceive(NetState ns)
        {
            lock ( ns )
            {
                ByteQueue buffer = ns.Buffer;

                if (buffer == null)
                {
                    return(true);
                }

                int length = buffer.Length;

                if (!ns.Seeded)
                {
                    if (length >= 4)
                    {
                        buffer.Dequeue(m_Peek, 0, 4);

                        int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

                        if (log.IsDebugEnabled)
                        {
                            log.DebugFormat("Login: {0}: Seed is 0x{1:X8}", ns, seed);
                        }

                        if (seed == 0)
                        {
                            log.WarnFormat("Login: {0}: Invalid client detected, disconnecting", ns);
                            ns.Dispose();
                            return(false);
                        }

                        ns.m_Seed = seed;
                        ns.Seeded = true;
                    }

                    return(true);
                }

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (!ns.SentFirstPacket && packetID != 0xF0 && packetID != 0xF1 && packetID != 0xCF && packetID != 0x80 && packetID != 0x91 && packetID != 0xA4 && packetID != 0xBF)
                    {
                        log.WarnFormat("Client: {0}: Encrypted client detected, disconnecting", ns);
                        ns.Dispose();
                        break;
                    }

                    PacketHandler handler = ns.GetHandler(packetID);

                    if (handler == null)
                    {
                        byte[] data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);

                        new PacketReader(data, length, false).Trace(ns);

                        break;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                break;
                            }
                        }
                        else
                        {
                            break;
                        }
                    }

                    if (length >= packetLength)
                    {
                        if (handler.Ingame && ns.Mobile == null)
                        {
                            log.WarnFormat("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;
                        }
                        else
                        {
                            ThrottlePacketCallback throttler = handler.ThrottleCallback;

                            if (throttler != null && !throttler(ns))
                            {
                                m_Throttled.Enqueue(ns);
                                return(false);
                            }

                            PacketProfile profile = PacketProfile.GetIncomingProfile(packetID);
                            DateTime      start   = (profile == null ? DateTime.MinValue : DateTime.UtcNow);

                            byte[] packetBuffer;

                            if (BufferSize >= packetLength)
                            {
                                packetBuffer = m_Buffers.AquireBuffer();
                            }
                            else
                            {
                                packetBuffer = new byte[packetLength];
                            }

                            packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                            PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                            try {
                                handler.OnReceive(ns, r);
                            } catch (Exception e) {
                                log.Fatal(String.Format("Exception disarmed in HandleReceive from {0}",
                                                        ns.Address), e);
                            }

                            length = buffer.Length;

                            if (BufferSize >= packetLength)
                            {
                                m_Buffers.ReleaseBuffer(packetBuffer);
                            }

                            if (profile != null)
                            {
                                profile.Record(packetLength, DateTime.UtcNow - start);
                            }
                        }
                    }
                    else
                    {
                        break;
                    }
                }
            }

            return(true);
        }
Пример #23
0
        public virtual void Dispose(bool flush)
        {
            if (Socket == null || m_Disposing)
            {
                return;
            }

            m_Disposing = true;

            if (flush)
            {
                Flush();
            }

            try
            {
                Socket.Shutdown(SocketShutdown.Both);
            }
            catch (SocketException ex)
            {
                TraceException(ex);
            }

            try
            {
                Socket.Close();
            }
            catch (SocketException ex)
            {
                TraceException(ex);
            }

            if (m_RecvBuffer != null)
            {
                lock (m_ReceiveBufferPool)
                {
                    m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
                }
            }

            Socket = null;

            PacketEncoder   = null;
            PacketEncryptor = null;

            m_Buffer     = null;
            m_RecvBuffer = null;

            m_OnReceive = null;
            m_OnSend    = null;

            m_Running = false;

            lock (m_Disposed)
            {
                m_Disposed.Enqueue(this);
            }

            lock (m_SendQueue)
            {
                if (!m_SendQueue.IsEmpty)
                {
                    m_SendQueue.Clear();
                }
            }
        }
Пример #24
0
        private void InvokeReceived( NetState ns, ByteQueue buffer, out bool throttle )
        {
            throttle = false;

            if ( Received != null )
                Received( ns, buffer, out throttle );
        }
Пример #25
0
        public bool HandleReceive(NetState ns)
        {
            ByteQueue buffer = ns.Buffer;

            if (buffer == null || buffer.Length <= 0)
            {
                return(true);
            }

            lock (buffer)
            {
                int length = buffer.Length;

                if (!ns.Seeded)
                {
                    #region Enhanced Client
                    if (buffer.GetPacketID() == 0xFF)
                    {
                        // Packet 255 = 0xFF = Client KR.
                        ns.IsKRClient = true;
                        Console.WriteLine("KR-Client detected", ns);
                    }
                    #endregion

                    if (buffer.GetPacketID() == 0xEF)
                    {
                        // new packet in client	6.0.5.0	replaces the traditional seed method with a	seed packet
                        // 0xEF	= 239 =	multicast IP, so this should never appear in a normal seed.	 So	this is	backwards compatible with older	clients.
                        ns.Seeded = true;
                    }
                    else if (buffer.Length >= 4)
                    {
                        buffer.Dequeue(m_Peek, 0, 4);

                        int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

                        if (seed == 0)
                        {
                            Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns);
                            ns.Dispose();
                            return(false);
                        }

                        ns.m_Seed = seed;
                        ns.Seeded = true;

                        length = buffer.Length;
                    }
                    else
                    {
                        return(true);
                    }
                }

                int[] seedablePackets = new int[]
                {
                    0xF0,        //Unknown - hijacked by Krrios client for login level acknowledgement
                    0xF1,        //Unknown, sent in reply to 0xF2 - also hijacked by some freeshard clients for listings
                    0xCF,        //Login to login server (with username and password) (possibly unused by EA)
                    0x80,        //Login to login server (with username and password)
                    0x91,        //Login to game server (with username and password)
                    0xA4,        //Hardware info
                    0xEF,        //KR and 2D login seed with version
                    0xE4,        //Enhanced Client (KR) encyrption response (to 0xE3 encryption request)
                    0xFF,        //
                    0x52         //Post bulletin board message - did we hijack this by accident for remoting/region watcher?
                };

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (!ns.SentFirstPacket && Array.IndexOf <int>(seedablePackets, packetID) == -1)
                    {
                        Console.WriteLine("Client: {0}: Encrypted client detected, disconnecting", ns);
                        ns.Dispose();
                        break;
                    }

                    PacketHandler handler = ns.GetHandler(packetID);

                    if (handler == null)
                    {
                        byte[] data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);

                        new PacketReader(data, length, false).Trace(ns);

                        break;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                break;
                            }
                        }
                        else
                        {
                            break;
                        }
                    }

                    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;
                        }
                        else
                        {
                            ThrottlePacketCallback throttler = handler.ThrottleCallback;

                            if (throttler != null && !throttler(ns))
                            {
                                m_Throttled.Enqueue(ns);
                                return(false);
                            }

                            PacketReceiveProfile prof = PacketReceiveProfile.Acquire(packetID);

                            if (prof != null)
                            {
                                prof.Start();
                            }

                            byte[] packetBuffer;

                            if (BufferSize >= packetLength)
                            {
                                packetBuffer = m_Buffers.AcquireBuffer();
                            }
                            else
                            {
                                packetBuffer = new byte[packetLength];
                            }

                            packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                            PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                            handler.OnReceive(ns, r);
                            length = buffer.Length;

                            if (BufferSize >= packetLength)
                            {
                                m_Buffers.ReleaseBuffer(packetBuffer);
                            }

                            if (prof != null)
                            {
                                prof.Finish(packetLength);
                            }
                        }
                    }
                    else
                    {
                        break;
                    }
                }
            }

            #region Enhanced Client
            // ToDo clean this up
            // Would be nicer to detect the enhanced client in clientversion.cs
            // It seems that UOKR-EH sends a version number bigger 66.0.0.0, UOSA-EH bigger 67.0.0.0
            try
            {
                if (ns.Version.Major > 8)
                {
                    ns.IsKRClient = true;
                }
            }
            catch
            {
                //Standard classic client does not display version this early, so we can rule SA enhanced client out
                ns.IsKRClient = false;
            }
            #endregion

            return(true);
        }
Пример #26
0
        public virtual void Dispose(bool flush)
        {
            if (Socket == null || m_Disposing)
            {
                return;
            }

            m_Disposing = true;

            if (flush)
            {
                Flush();
            }

            try
            {
                Socket.Shutdown(SocketShutdown.Both);
            }
            catch (SocketException ex)
            {
                TraceException(ex);
            }

            try
            {
                Socket.Close();
            }
            catch (SocketException ex)
            {
                TraceException(ex);
            }

            Socket = null;

            if (m_RecvBuffer != null)
            {
                lock (m_ReceiveBufferPool)
                {
                    m_ReceiveBufferPool.ReleaseBuffer(m_RecvBuffer);
                }
            }

            m_Buffer     = null;
            m_RecvBuffer = null;

            m_OnReceive = null;
            m_OnSend    = null;

            m_Running = false;

            /*
             * m_Trades = null;
             * m_Gumps = null;
             * m_Menus = null;
             * m_HuePickers = null;
             */
            lock (m_Disposed)
                m_Disposed.Enqueue(this);

            lock (m_SendQueue)
                if (!m_SendQueue.IsEmpty)
                {
                    m_SendQueue.Clear();
                }
        }
Пример #27
0
        public void FinishDispose()
        {
            if ( m_DisposeFinished )
                return;

            m_DisposeFinished = true;

            try
            {
                m_Socket.Shutdown( SocketShutdown.Both );
            }
            catch ( SocketException ex )
            {
                TraceException( ex );
            }

            try
            {
                m_Socket.Close();
            }
            catch ( SocketException ex )
            {
                TraceException( ex );
            }

            if ( m_RecvBuffer != null )
                m_ReceiveBufferPool.ReleaseBuffer( m_RecvBuffer );

            m_Socket = null;

            m_Buffer = null;
            m_RecvBuffer = null;
            m_Running = false;

            m_NetServer.OnDisposed( this );

            if ( !m_SendQueue.IsEmpty )
            {
                lock ( m_SendQueue )
                    m_SendQueue.Clear();
            }
        }
Пример #28
0
        public void HandleReceive(NetState ns)
        {
            ByteQueue buffer = ns.Buffer;

            if (buffer == null || buffer.Length <= 0)
            {
                return;
            }

            lock (buffer)
            {
                if (!ns.Seeded && !HandleSeed(ns, buffer))
                {
                    return;
                }

                int length = buffer.Length;

                while (length > 0 && ns.Running)
                {
                    int packetID = buffer.GetPacketID();

                    if (CheckEncrypted(ns, packetID))
                    {
                        return;
                    }

                    PacketHandler handler = NetState.GetHandler(packetID);

                    if (handler == null)
                    {
                        byte[] data = new byte[length];
                        length = buffer.Dequeue(data, 0, length);
                        new PacketReader(data, length, false).Trace(ns);
                        return;
                    }

                    int packetLength = handler.Length;

                    if (packetLength <= 0)
                    {
                        if (length >= 3)
                        {
                            packetLength = buffer.GetPacketLength();

                            if (packetLength < 3)
                            {
                                ns.Dispose();
                                return;
                            }
                        }
                        else
                        {
                            return;
                        }
                    }

                    if (length < packetLength)
                    {
                        return;
                    }

                    if (handler.Ingame)
                    {
                        if (ns.Mobile == null)
                        {
                            Utility.PushColor(ConsoleColor.Red);
                            Console.WriteLine("Client: {0}: Packet (0x{1:X2}) Requires State Mobile", ns, packetID);
                            Utility.PopColor();

                            ns.Dispose();
                            return;
                        }

                        if (ns.Mobile.Deleted)
                        {
                            Utility.PushColor(ConsoleColor.Red);
                            Console.WriteLine("Client: {0}: Packet (0x{1:X2}) Ivalid State Mobile", ns, packetID);
                            Utility.PopColor();

                            ns.Dispose();
                            return;
                        }
                    }

                    ThrottlePacketCallback throttler = handler.ThrottleCallback;

                    if (throttler != null)
                    {
                        if (!throttler(ns, out bool drop))
                        {
                            if (!drop)
                            {
                                m_Throttled.Enqueue(ns);
                            }
                            else
                            {
                                buffer.Dequeue(new byte[packetLength], 0, packetLength);
                            }

                            return;
                        }
                    }

                    PacketReceiveProfile prof = null;

                    if (Core.Profiling)
                    {
                        prof = PacketReceiveProfile.Acquire(packetID);
                    }

                    if (prof != null)
                    {
                        prof.Start();
                    }

                    byte[] packetBuffer;

                    if (BufferSize >= packetLength)
                    {
                        packetBuffer = m_Buffers.AcquireBuffer();
                    }
                    else
                    {
                        packetBuffer = new byte[packetLength];
                    }

                    packetLength = buffer.Dequeue(packetBuffer, 0, packetLength);

                    if (packetBuffer != null && packetBuffer.Length > 0 && packetLength > 0)
                    {
                        PacketReader r = new PacketReader(packetBuffer, packetLength, handler.Length != 0);

                        handler.OnReceive(ns, r);

                        if (BufferSize >= packetLength)
                        {
                            m_Buffers.ReleaseBuffer(packetBuffer);
                        }
                    }

                    if (prof != null)
                    {
                        prof.Finish(packetLength);
                    }

                    length = buffer.Length;
                }
            }
        }
Пример #29
0
		private bool HandleSeed(NetState ns, ByteQueue buffer)
		{
			if (buffer.GetPacketID() == 0xEF)
			{
				// new packet in client	6.0.5.0	replaces the traditional seed method with a	seed packet
				// 0xEF	= 239 =	multicast IP, so this should never appear in a normal seed.	 So	this is	backwards compatible with older	clients.
				ns.Seeded = true;
				return true;
			}
			else if (buffer.Length >= 4)
			{
				var m_Peek = new byte[4];

				buffer.Dequeue(m_Peek, 0, 4);

				int seed = (m_Peek[0] << 24) | (m_Peek[1] << 16) | (m_Peek[2] << 8) | m_Peek[3];

				if (seed == 0)
				{
					Utility.PushColor(ConsoleColor.Green);
					Console.WriteLine("Login: {0}: Invalid client detected, disconnecting", ns);
					Utility.PopColor();
					ns.Dispose();
					return false;
				}

				ns.m_Seed = seed;
				ns.Seeded = true;
				return true;
			}
			else
			{
				return false;
			}
		}