protected override void OnClientConnect(IAsyncResult result) { try { IClientMetadata state; int id; lock (ConnectedClients) { id = !ConnectedClients.Any() ? 1 : ConnectedClients.Keys.Max() + 1; state = new ClientMetadata(((Socket)result.AsyncState).EndAccept(result), id); CanAcceptConnections.Set(); ConnectedClients.Add(id, state); } //If the server shouldn't accept the IP do nothing. if (!IsConnectionAllowed(state)) { Log("A blacklisted ip tried to connect to the server: ipv4:" + state.RemoteIPv4 + " ipv6: " + state.RemoteIPv6); lock (ConnectedClients) { ConnectedClients.Remove(id); } return; } Task.Run(() => { var stream = new NetworkStream(state.Listener); //Create SslStream state.SslStream = new SslStream(stream, false, AcceptCertificate); var success = Authenticate(state).Result; if (success) { RaiseClientConnected(state); Receive(state); } else { lock (ConnectedClients) { ConnectedClients.Remove(id); } Log("Unable to authenticate server."); } }, new CancellationTokenSource(10000).Token); } catch (Exception ex) { CanAcceptConnections.Set(); RaiseLog(ex); RaiseErrorThrown(ex); } }
/// <summary> /// Start listening on specified port and ip. /// <para/>The limit is the maximum amount of client which can connect at one moment. You can just fill in 'null' or "" as the ip value. /// That way it will automatically choose an ip to listen to. Using IPAddress.Any. /// </summary> /// <param name="ip">The ip the server will be listening to.</param> /// <param name="port">The port on which the server will be running.</param> /// <param name="limit">Optional parameter, default value is 500.</param> public override void StartListening(string ip, int port, int limit = 500) { if (port < 1 || port > 65535) { throw new ArgumentOutOfRangeException(nameof(port)); } if (limit < 0) { throw new ArgumentException("Limit cannot be under 0."); } if (limit == 0) { throw new ArgumentException("Limit cannot be 0."); } Port = port; Ip = ip; var endpoint = new IPEndPoint(DetermineListenerIp(ip), port); TokenSource = new CancellationTokenSource(); Token = TokenSource.Token; Task.Run(SendFromQueue, Token); Task.Run(() => { try { using (var listener = new Socket(endpoint.AddressFamily, SocketType.Stream, ProtocolType.Tcp)) { Listener = listener; listener.Bind(endpoint); listener.Listen(Limit); RaiseServerHasStarted(); while (!Token.IsCancellationRequested) { CanAcceptConnections.Reset(); listener.BeginAccept(OnClientConnect, listener); CanAcceptConnections.WaitOne(); } } } catch (ObjectDisposedException ode) { RaiseErrorThrown(ode); } catch (SocketException se) { throw new Exception(se.ToString()); } }, Token); }
protected override void OnClientConnect(IAsyncResult result) { if (Token.IsCancellationRequested) { return; } CanAcceptConnections.Set(); try { ISocketState state; lock (ConnectedClients) { var id = !ConnectedClients.Any() ? 1 : ConnectedClients.Keys.Max() + 1; state = new SocketState(((Socket)result.AsyncState).EndAccept(result), id); //If the server shouldn't accept the IP do nothing. if (!IsConnectionAllowed(state)) { return; } var client = ConnectedClients.FirstOrDefault(x => x.Value == state); if (client.Value == state) { id = client.Key; ConnectedClients.Remove(id); ConnectedClients.Add(id, state); } else { ConnectedClients.Add(id, state); } ClientConnectedInvoke(id, state); } StartReceiving(state); } catch (ObjectDisposedException ode) { InvokeErrorThrown(ode); } catch (SocketException se) { this.InvokeErrorThrown(se); } }
protected override void OnClientConnect(IAsyncResult result) { CanAcceptConnections.Set(); try { ISocketState state; int id; lock (ConnectedClients) { id = !ConnectedClients.Any() ? 1 : ConnectedClients.Keys.Max() + 1; state = new SocketState(((Socket)result.AsyncState).EndAccept(result), id); } //If the server shouldn't accept the IP do nothing. if (!IsConnectionAllowed(state)) { return; } var stream = new NetworkStream(state.Listener); //Create SslStream state.SslStream = new SslStream(stream, false, new RemoteCertificateValidationCallback(AcceptCertificate)); Task.Run(() => { var success = Authenticate(state).Result; if (success) { lock (ConnectedClients) { ConnectedClients.Add(id, state); } ClientConnectedInvoke(id, state); StartReceiving(state); } else { throw new AuthenticationException("Unable to authenticate server."); } }, new CancellationTokenSource(10000).Token); } catch (SocketException se) { throw new Exception(se.ToString()); } }