/// <summary> /// Fires the ClientDisconnected event. /// </summary> /// <param name="client">Client that disconnected</param> public void FireClientDisconnected(Client client) { PluginUtils.ProtectedInvoke(() => { ClientDisconnected?.Invoke(client); }, "ClientDisconnected"); }
/// <summary> /// Fires any registered callbacks for the specified packet type. /// </summary> /// <param name="client">Client that recieved the packet</param> /// <param name="packet">Packet that was recieved</param> public void FireServerPacket(Client client, Packet packet) { PluginUtils.ProtectedInvoke(() => { // Fire general server packet callbacks ServerPacketRecieved?.Invoke(client, packet); // Fire specific hook callbacks if applicable try { foreach (var pair in _packetHooks) { if (pair.Value.Contains(packet.Type)) { pair.Key(client, packet); } } } catch { } try { foreach (var pair in _genericPacketHooks) { if (pair.Value == packet.GetType()) { (pair.Key as Delegate).Method?.Invoke((pair.Key as Delegate).Target, new object[2] { client, Convert.ChangeType(packet, pair.Value) }); } } } catch { } }, "ServerPacket"); }
public void FireServerPacket(Client client, Packet packet) { PluginUtils.ProtectedInvoke(() => { if (ServerPacketRecieved != null) { ServerPacketRecieved(client, packet); } foreach (var pair in _packetHooks) { if (pair.Value.Contains(packet.Type)) { pair.Key(client, packet); } } try { foreach (var pair in _genericPacketHooks) { if (pair.Value == packet.GetType()) { (pair.Key as Delegate).Method?.Invoke((pair.Key as Delegate).Target, new object[2] { client, Convert.ChangeType(packet, pair.Value) }); } } } catch { } }, "ServerPacket"); }
private void Send(Packet packet, bool client) { lock (client ? _clientLock : _serverLock) { bool success = PluginUtils.ProtectedInvoke(() => { MemoryStream ms = new MemoryStream(); using (PacketWriter w = new PacketWriter(ms)) { w.Write((int)0); w.Write(packet.Id); packet.Write(w); } byte[] data = ms.ToArray(); PacketWriter.BlockCopyInt32(data, data.Length); if (client) { _clientSendState.Cipher(data); _clientStream.Write(data, 0, data.Length); } else { _serverSendState.Cipher(data); _serverStream.Write(data, 0, data.Length); } }, "PacketSend (packet = " + packet?.Type + ")", typeof(IOException)); if (!success) { Dispose(); } } }
/// <summary> /// Fires any registered callbacks for the specified packet type. /// </summary> /// <param name="client">Client that recieved the packet</param> /// <param name="packet">Packet that was recieved</param> public void FireClientPacket(Client client, Packet packet) { PluginUtils.ProtectedInvoke(() => { // Fire command callbacks if (packet.Type == PacketType.PLAYERTEXT) { PlayerTextPacket playerText = (PlayerTextPacket)packet; string text = playerText.Text.Replace("/", "").ToLower(); string command = text.Contains(' ') ? text.Split(' ')[0].ToLower() : text; string[] args = text.Contains(' ') ? text.Split(' ').Skip(1).ToArray() : new string[0]; foreach (var pair in _commandHooks) { if (pair.Value.Contains(command)) { packet.Send = false; pair.Key(client, command, args); } } } // Fire general client packet callbacks if (ClientPacketRecieved != null) { ClientPacketRecieved(client, packet); } // Fire specific hook callbacks if applicable foreach (var pair in _packetHooks) { if (pair.Value.Contains(packet.Type)) { pair.Key(client, packet); } } try { foreach (var pair in _genericPacketHooks) { if (pair.Value == packet.GetType()) { (pair.Key as Delegate).Method.Invoke((pair.Key as Delegate).Target, new object[2] { client, Convert.ChangeType(packet, pair.Value) }); } } } catch { } }, "ClientPacket"); }
/// <summary> /// Stops the client listener if it's running. /// Fires the ProxyListenStopped event. /// </summary> public void Stop() { if (_localListener == null) { return; } PluginUtils.Log("Listener", "Stopping local listener..."); _localListener.Stop(); _localListener = null; PluginUtils.ProtectedInvoke(() => { ProxyListenStopped?.Invoke(this); }, "ProxyListenStopped"); }
private void LocalConnect(IAsyncResult ar) { PluginUtils.ProtectedInvoke(() => { TcpClient client = _localListener.EndAcceptTcpClient(ar); Client ci = new Client(this, client); PluginUtils.Log("Listener", "Client received."); PluginUtils.ProtectedInvoke(() => { ClientBeginConnect?.Invoke(ci); }, "ClientBeginConnect"); }, "LocalConnect", typeof(ObjectDisposedException)); PluginUtils.ProtectedInvoke(() => { _localListener?.BeginAcceptTcpClient(LocalConnect, null); }, "ClientListenerBeginListen"); }
private void ServerConnected(IAsyncResult ar) { bool success = PluginUtils.ProtectedInvoke(() => { _serverConnection.EndConnect(ar); _serverStream = _serverConnection.GetStream(); SendToServer(ar.AsyncState as Packet); BeginRead(0, 4, false); _proxy.FireClientConnected(this); PluginUtils.Log("Client", "Connected to remote host."); }, "ClientServerConnect"); if (!success) { State.ConTargetAddress = Proxy.DefaultServer; State.ConTargetPort = 2050; Dispose(); } }
/// <summary> /// Starts a client listener on 127.0.0.1:2050. /// Fires the ProxyListenStarted event if successful. /// </summary> public void Start() { PluginUtils.Log("Listener", "Starting local listener..."); bool success = PluginUtils.ProtectedInvoke(() => { _localListener = new TcpListener(IPAddress.Parse("127.0.0.1"), 2050); _localListener.Start(); _localListener.BeginAcceptTcpClient(new AsyncCallback(LocalConnect), null); PluginUtils.Log("Listener", "Local listener started."); }, "ClientListenerStart"); if (!success) { return; } PluginUtils.ProtectedInvoke(() => { ProxyListenStarted?.Invoke(this); }, "ProxyListenStarted"); }
private void RemoteRead(IAsyncResult ar) { NetworkStream stream = (ar.AsyncState as Tuple <NetworkStream, PacketBuffer>).Item1; PacketBuffer buffer = (ar.AsyncState as Tuple <NetworkStream, PacketBuffer>).Item2; bool isClient = stream == _clientStream; RC4Cipher cipher = isClient ? _clientReceiveState : _serverReceiveState; bool success = PluginUtils.ProtectedInvoke(() => { if (!stream.CanRead) { return; } int read; try { read = stream.EndRead(ar); } catch { return; } buffer.Advance(read); if (read == 0) { Dispose(); return; } else if (buffer.Index == 4) { // We have the first four bytes, resize the client buffer buffer.Resize(IPAddress.NetworkToHostOrder( BitConverter.ToInt32(buffer.Bytes, 0))); BeginRead(buffer.Index, buffer.BytesRemaining(), isClient); } else if (buffer.BytesRemaining() > 0) { // Awaiting the rest of the packet BeginRead(buffer.Index, buffer.BytesRemaining(), isClient); } else { // We have the full packet cipher.Cipher(buffer.Bytes); byte[] temp = (byte[])buffer.Bytes.Clone(); if (_proxy.IsHooked((PacketType)buffer.Bytes[4])) { temp = null; //If a packet isn't hooked then just send the raw data (no packet processing). Helps with broken/missing packet types. } Packet packet = Packet.Create(buffer.Bytes); if (isClient) { _proxy.FireClientPacket(this, packet); } else { _proxy.FireServerPacket(this, packet); } if (packet.Send) { Send(packet, !isClient, temp); } buffer.Reset(); BeginRead(0, 4, isClient); } }, "RemoteRead (isClient = " + isClient + ")", typeof(IOException)); if (!success) { Dispose(); } }
private void RemoteRead(IAsyncResult ar) { NetworkStream stream = (ar.AsyncState as Tuple <NetworkStream, PacketBuffer>).Item1; PacketBuffer buffer = (ar.AsyncState as Tuple <NetworkStream, PacketBuffer>).Item2; bool isClient = stream == _clientStream; RC4Cipher cipher = isClient ? _clientReceiveState : _serverReceiveState; bool success = PluginUtils.ProtectedInvoke(() => { if (!stream.CanRead) { return; } int read; try { read = stream.EndRead(ar); } catch { return; } buffer.Advance(read); if (read == 0) { Dispose(); return; } else if (buffer.Index == 4) { // We have the first four bytes, resize the client buffer int len = IPAddress.NetworkToHostOrder( BitConverter.ToInt32(buffer.Bytes, 0)); if (len == 1014001516) //known issue { throw new Exception("Invalid Buffer Size Problem: Try joining a non-proxy server then switching to the proxy server again. More info: https://www.mpgh.net/forum/showthread.php?t=1196439"); } buffer.Resize(len); BeginRead(buffer.Index, buffer.BytesRemaining(), isClient); } else if (buffer.BytesRemaining() > 0) { // Awaiting the rest of the packet BeginRead(buffer.Index, buffer.BytesRemaining(), isClient); } else { // We have the full packet cipher.Cipher(buffer.Bytes); Packet packet = Packet.Create(buffer.Bytes); if (isClient) { _proxy.FireClientPacket(this, packet); } else { _proxy.FireServerPacket(this, packet); } if (packet.Send) { Send(packet, !isClient); } buffer.Reset(); BeginRead(0, 4, isClient); } }, "RemoteRead (isClient = " + isClient + ")", typeof(IOException)); if (!success) { Dispose(); } }
private void RemoteRead(IAsyncResult ar) { NetworkStream stream = (ar.AsyncState as Tuple <NetworkStream, PacketBuffer>).Item1; PacketBuffer buffer = (ar.AsyncState as Tuple <NetworkStream, PacketBuffer>).Item2; bool isClient = stream == _clientStream; RC4Cipher cipher = isClient ? _clientReceiveState : _serverReceiveState; bool success = PluginUtils.ProtectedInvoke(() => { if (!stream.CanRead) { return; } int read; try { read = stream.EndRead(ar); } catch { return; } buffer.Advance(read); if (read == 0) { Dispose(); return; } else if (buffer.Index == 4) { buffer.Resize(IPAddress.NetworkToHostOrder( BitConverter.ToInt32(buffer.Bytes, 0))); BeginRead(buffer.Index, buffer.BytesRemaining(), isClient); } else if (buffer.BytesRemaining() > 0) { BeginRead(buffer.Index, buffer.BytesRemaining(), isClient); } else { cipher.Cipher(buffer.Bytes); Packet packet = Packet.Create(buffer.Bytes); if (isClient) { _proxy.FireClientPacket(this, packet); } else { _proxy.FireServerPacket(this, packet); } if (packet.Send) { Send(packet, !isClient); } buffer.Reset(); BeginRead(0, 4, isClient); } }, "RemoteRead (isClient = " + isClient + ")", typeof(IOException)); if (!success) { Dispose(); } }