private static async Task Main() { _server = new Server(CancellationTokenSource); var listener = new TcpListener(IPAddress.Loopback, Port); listener.Start(); Console.WriteLine($"Server started on port: {Port}."); var requestTasks = new HashSet <Task>(); while (!CancellationTokenSource.IsCancellationRequested) { try { //With wait cancellation allows to cancel the acceptTcpClientAsync, if the server is currently //waiting for more connections and someone already shut it down var client = await listener .AcceptTcpClientAsync() .WithWaitCancellation(CancellationTokenSource.Token); //used to let the client know that he is now connected //server "handshake" await WriteResponse(client.GetStream(), ResponseFactory.SuccessResponse("Connection established with success.")); Console.WriteLine($"connection accepted with id: {_connectionIdCounter++}.\n"); //add the client to a task container "requestTasks" that will be awaited on server shutdown requestTasks.Add(HandleResponse(client, _connectionIdCounter)); //if the server limit was reached stop receiving more requests until one of the current ones finishes if (requestTasks.Count == MaximumConcurrentClients) { requestTasks.Remove(await Task.WhenAny(requestTasks)); } } catch (OperationCanceledException) { //on cancellation a shutdown is occurring, no need to handle the exception } catch (Exception e) { Console.WriteLine($"Unknown error: {e.Message}"); } } //wait for all tasks to be completed except the one that initiated the shutdown while (requestTasks.Count > 1) { requestTasks.Remove(await Task.WhenAny(requestTasks)); } //terminates the timeout on server shutdown _server.NotifyServerShutdownIsComplete(); //Wait for the last task to complete await Task.WhenAny(requestTasks); listener.Stop(); Console.Write("Server shutdown successful.\n"); }