/// <summary> /// Sends packet to the destination. /// </summary> public void Send(NetworkMessage msg) { if (OnSend != null) { OnSend.BeginInvoke(msg, null, null); } pipe.Write(msg.GetData(), 0, msg.Length); }
public void ProcessFromClient(byte[] buffer) { int length = buffer.Length; Array.Copy(buffer, clientRecvMsg.GetBuffer(), length); clientRecvMsg.Length = length; OnReceivedDataFromClient(clientRecvMsg.GetData()); switch (protocol) { case Protocol.None: case Protocol.Login: ParseFirstClientMsg(); break; case Protocol.World: bool decryptOkay = clientRecvMsg.XteaDecrypt(client.IO.XteaKey); if (decryptOkay) { clientRecvMsg.Position = 6; int msgLength = (int)clientRecvMsg.GetUInt16() + 8; int position = clientRecvMsg.Position; if (!ParsePacketFromClient(client, clientRecvMsg, serverSendMsg)) { //unknown packet byte[] unknown = clientRecvMsg.GetBytes(clientRecvMsg.Length - clientRecvMsg.Position); OnSplitPacketFromClient(unknown[0], unknown); } byte[] data = new byte[clientRecvMsg.Position - position]; Array.Copy(clientRecvMsg.GetBuffer(), position, data, 0, data.Length); OnSplitPacketFromClient(data[0], data); } break; } }
public void ProcessFromServer(byte[] buffer) { int length = (int)BitConverter.ToUInt16(buffer, 0) + 2; if (length > buffer.Length) { // Packet is split into multiple chunks if (partialPacketSize == 0) { // This is the first chunk fullPacketSize = length; Array.Copy(buffer, serverRecvMsg.GetBuffer(), buffer.Length); partialPacketSize = buffer.Length; return; } else { // This is a subsequent chunk Array.Copy(buffer, 0, serverRecvMsg.GetBuffer(), partialPacketSize, buffer.Length); partialPacketSize += buffer.Length; if (partialPacketSize < fullPacketSize) { // Packet is still incomplete return; } else { // Packet is complete serverRecvMsg.Length = fullPacketSize; } } } else { fullPacketSize = 0; partialPacketSize = 0; Array.Copy(buffer, serverRecvMsg.GetBuffer(), length); serverRecvMsg.Length = length; } OnReceivedDataFromServer(serverRecvMsg.GetData()); switch (protocol) { case Protocol.Login: break; case Protocol.World: bool decryptOkay = serverRecvMsg.XteaDecrypt(client.IO.XteaKey); if (decryptOkay) { serverRecvMsg.Position = 6; int msgSize = (int)serverRecvMsg.GetUInt16() + 8; clientSendMsg.Reset(); while (serverRecvMsg.Position < msgSize) { int position = serverRecvMsg.Position; bool parsed = false; try { parsed = ParsePacketFromServer(client, serverRecvMsg, clientSendMsg); } catch (Exception ex) { WriteDebug(ex.Message + "\nStackTrace: " + ex.StackTrace); } if (!parsed) { if (serverRecvMsg.Length - serverRecvMsg.Position > 0 && serverRecvMsg.Length < serverRecvMsg.GetBuffer().Length) { byte[] unknown = serverRecvMsg.GetBytes(serverRecvMsg.Length - serverRecvMsg.Position); OnSplitPacketFromServer(unknown[0], unknown); } break; } if (serverRecvMsg.Position - position > 0) { byte[] data = new byte[serverRecvMsg.Position - position]; Array.Copy(serverRecvMsg.GetBuffer(), position, data, 0, data.Length); OnSplitPacketFromServer(data[0], data); } } } break; case Protocol.None: break; } }
public NetworkMessage(NetworkMessage msg) : this(msg.GetData()) { this.position = msg.position; }
private void LoginServerReceived(IAsyncResult ar) { try { int dataLength = loginSocket.EndReceive(ar); if (dataLength > 0) { byte[] tmp = new byte[dataLength]; Array.Copy(dataLoginServer, tmp, dataLength); NetworkMessage msg = new NetworkMessage(tmp); msg.PrepareToRead(xteaKey.ToUInt32Array()); msg.GetUInt16(); while (msg.Position < msg.Length) { byte cmd = msg.GetByte(); string message; switch (cmd) { case 0x0A: //Error message message = msg.GetString(); if (LoginServer_OnError != null) LoginServer_OnError(message); break; case 0x0B: //For your information message = msg.GetString(); if (LoginServer_FYI != null) LoginServer_FYI(message); break; case 0x14: //MOTD message = msg.GetString(); if (LoginServer_MOTD != null) LoginServer_MOTD(message); break; case 0x1E: //Patching exe/dat/spr messages case 0x1F: case 0x20: if (LoginServer_Patching != null) LoginServer_Patching("A new client is available."); return; case 0x28: //Select another login server if (LoginServer_SelectAnother != null) LoginServer_SelectAnother("Select another login server."); if (retry) { if (loginServerIndex < maxLoginServers - 1) { loginServerIndex++; TryLoginServer(); } else { if (LoginServer_CouldNotConnect != null) LoginServer_CouldNotConnect("Select another login server."); loginSocket.Disconnect(true); if (Socket_Disconnected != null) Socket_Disconnected("dataLength<=0"); } } break; case 0x64: //character list int nChars = (int)msg.GetByte(); charList = new CharacterLoginInfo[nChars]; for (int i = 0; i < nChars; i++) { charList[i].CharName = msg.GetString(); charList[i].WorldName = msg.GetString(); charList[i].WorldIP = msg.GetUInt32(); charList[i].WorldIPString = IPBytesToString(BitConverter.GetBytes(charList[i].WorldIP), 0); charList[i].WorldPort = msg.GetUInt16(); } if (LoginServer_CharList != null) LoginServer_CharList("Charlist received."); loginSocket.Disconnect(true); if (Socket_Disconnected != null) Socket_Disconnected("Charlist received."); return; default: //Notify about an unknown message if (LoginServer_UnknownMsg != null) LoginServer_UnknownMsg(msg.GetData().ToHexString()); loginSocket.Disconnect(true); if (Socket_Disconnected != null) Socket_Disconnected("Unknown Message."); break; } } } else //we didn't receive anything { if (LoginServer_ReceivedNothing != null) LoginServer_ReceivedNothing("Nothing received on LoginServerIndex=" + loginServerIndex); if (retry) { if (loginServerIndex < maxLoginServers - 1) { loginServerIndex++; TryLoginServer(); } else { if (LoginServer_CouldNotConnect != null) LoginServer_CouldNotConnect("dataLength<=0"); loginSocket.Disconnect(true); if (Socket_Disconnected != null) Socket_Disconnected("dataLength<=0"); } } } } catch (Exception) {} }
/// <summary> /// Sends packet to the destination. /// </summary> public void Send(NetworkMessage msg) { if (OnSend != null) OnSend.BeginInvoke(msg, null, null); pipe.Write(msg.GetData(), 0, msg.Length); }
private void ServerReadCallBack(IAsyncResult ar) { byte[] serverData = null; try { int read = serverStream.EndRead(ar); if (read < 2) { Restart(); return; } lastInteraction = DateTime.Now; int pSize = (int)BitConverter.ToUInt16(serverRecvMsg.GetBuffer(), 0) + 2; while (read < pSize) { if (serverStream.CanRead) { read += serverStream.Read(serverRecvMsg.GetBuffer(), read, pSize - read); } else { throw new Exception("Connection broken."); } } serverRecvMsg.Length = pSize; switch (protocol) { case Protocol.Login: ParseCharacterList(); break; case Protocol.World: OnReceivedDataFromServer(serverRecvMsg.GetData()); serverData = serverRecvMsg.GetData(); if (serverRecvMsg.XteaDecrypt(xteaKey)) { serverRecvMsg.Position = serverRecvMsg.GetPacketHeaderSize(); int msgSize = (int)serverRecvMsg.GetUInt16() + serverRecvMsg.GetPacketHeaderSize() + 2; clientSendMsg.Reset(); while (serverRecvMsg.Position < msgSize) { int position = serverRecvMsg.Position; byte type = serverRecvMsg.PeekByte(); lastReceivedPacketTypes.Push(type); if (!ParsePacketFromServer(client, serverRecvMsg, clientSendMsg)) { byte[] unknown = serverRecvMsg.GetBytes(serverRecvMsg.Length - serverRecvMsg.Position); OnSplitPacketFromServer(unknown[0], unknown); WriteDebug("Unknown incoming packet, type: " + type.ToString("X") + ", data: " + unknown.ToHexString()); clientSendMsg.AddBytes(unknown); break; } byte[] data = new byte[serverRecvMsg.Position - position]; Array.Copy(serverRecvMsg.GetBuffer(), position, data, 0, data.Length); OnSplitPacketFromServer(data[0], data); } if (AllowIncomingModification && clientSendMsg.Length > clientSendMsg.GetPacketHeaderSize() + 2) { clientSendMsg.InsetLogicalPacketHeader(); clientSendMsg.PrepareToSend(xteaKey); SendToClient(clientSendMsg.GetData()); } else { SendToClient(serverData); } } else { SendToClient(serverData); } serverStream.BeginRead(serverRecvMsg.GetBuffer(), 0, 2, new AsyncCallback(ServerReadCallBack), null); break; case Protocol.None: SendToClient(serverRecvMsg.GetData()); break; } } catch (System.IO.IOException) { } catch (ObjectDisposedException) { } catch (Exception ex) { WriteDebug(ex.ToString()); if (serverData != null) { SendToClient(serverData); serverStream.BeginRead(serverRecvMsg.GetBuffer(), 0, 2, new AsyncCallback(ServerReadCallBack), null); } //Restart(); } }
private void ClientReadCallBack(IAsyncResult ar) { byte[] clientData = null; try { int read = clientStream.EndRead(ar); if (read < 2) { Restart(); return; } int pSize = (int)BitConverter.ToUInt16(clientRecvMsg.GetBuffer(), 0) + 2; while (read < pSize) { if (clientStream.CanRead) { read += clientStream.Read(clientRecvMsg.GetBuffer(), read, pSize - read); } else { throw new Exception("Connection broken."); } } clientRecvMsg.Length = pSize; switch (protocol) { case Protocol.None: ParseFirstClientMsg(); break; case Protocol.World: OnReceivedDataFromClient(clientRecvMsg.GetData()); clientData = clientRecvMsg.GetData(); if (clientRecvMsg.XteaDecrypt(xteaKey)) { clientRecvMsg.Position = clientRecvMsg.GetPacketHeaderSize(); int msgLength = (int)clientRecvMsg.GetUInt16() + 8; serverSendMsg.Reset(); int position = clientRecvMsg.Position; if (!ParsePacketFromClient(client, clientRecvMsg, serverSendMsg)) { //unknown packet byte[] unknown = clientRecvMsg.GetBytes(clientRecvMsg.Length - clientRecvMsg.Position); OnSplitPacketFromClient(unknown[0], unknown); WriteDebug("Unknown outgoing packet: " + unknown.ToHexString()); serverSendMsg.AddBytes(unknown); } byte[] data = new byte[clientRecvMsg.Position - position]; Array.Copy(clientRecvMsg.GetBuffer(), position, data, 0, data.Length); OnSplitPacketFromClient(data[0], data); if (AllowOutgoingModification && serverSendMsg.Length > serverSendMsg.GetPacketHeaderSize() + 2) { serverSendMsg.InsetLogicalPacketHeader(); serverSendMsg.PrepareToSend(xteaKey); SendToServer(serverSendMsg.GetData()); } else { SendToServer(clientData); } } else { SendToServer(clientData); } clientStream.BeginRead(clientRecvMsg.GetBuffer(), 0, 2, new AsyncCallback(ClientReadCallBack), null); break; case Protocol.Login: break; } } catch (ObjectDisposedException) { /*We don't have to log this exception. */ } catch (System.IO.IOException ex) { WriteDebug(ex.ToString()); } catch (Exception ex) { WriteDebug(ex.ToString()); if (clientData != null) { SendToServer(clientData); } } }
public bool Send(SendMethod method) { if (msg == null) { msg = new NetworkMessage(Client, 4048); } switch (method) { case SendMethod.Proxy: lock (msgLock) { msg.Reset(); ToNetworkMessage(msg); if (msg.Length > 8) { msg.InsetLogicalPacketHeader(); msg.PrepareToSend(); if (Destination == PacketDestination.Client) { Client.IO.Proxy.SendToClient(msg.GetData()); } else if (Destination == PacketDestination.Server) { Client.IO.Proxy.SendToServer(msg.GetData()); } return(true); } } break; case SendMethod.HookProxy: lock (msgLock) { msg.Reset(); ToNetworkMessage(msg); if (msg.Length > 8) { msg.InsetLogicalPacketHeader(); msg.PrepareToSend(); Pipes.HookSendToServerPacket.Send(Client, msg.GetData()); return(true); } } break; case SendMethod.Memory: lock (msgLock) { msg.Reset(); ToNetworkMessage(msg); if (Destination == PacketDestination.Server) { if (msg.Length > 8) { msg.InsetLogicalPacketHeader(); msg.PrepareToSend(); return(SendPacketToServerByMemory(Client, msg.GetData())); } } else if (Destination == PacketDestination.Client) { byte[] data = new byte[msg.GetData().Length - 8]; Array.Copy(msg.GetData(), 8, data, 0, data.Length); SendPacketToClientByMemory(Client, data); } } break; } return(false); }