private static string HandleConsoleCommands(IClientConnectable client, string incomingData) { if (client == null) { throw new ArgumentNullException("Error: NetworkServer.HandleConsoleCommands null client"); } if (incomingData == null) { throw new ArgumentNullException("Error: NetworkServer.HandleConsoleCommands null data"); } if (incomingData.Length == 0) { throw new ArgumentNullException("Error: NetworkServer.HandleConsoleCommands empty data"); } List <string> args = new List <string>(incomingData.Split(' ')); if (args.Count > 0) { string arg0 = args[0].ToLower(); if (arg0.Contains("help")) { return("Console commands: '/disconnect' or '/dcon' disconnects client"); } else if (arg0.Contains("disconnect") || arg0.Contains("dcon")) { DisconnectClient(client, "You have been disconnected from the server.", "client disconnect"); return("Client Disconnect Confirm"); } } return($"Unhandled or unknown command: {incomingData}, type '/help' for help."); }
private static void AddClient(IClientConnectable client) { if (client == null) { throw new ArgumentNullException("Error: NetworkServer.AddClient null client"); } lock (Clients) { Clients.Add(client); } Log($" > {client.Nickname} connected!\n"); }
public static bool TryTransmitToClient(IClientConnectable client, string text) { if (client == null) { throw new ArgumentNullException("Error: NetworkServer.TransmitToClient null client"); } if (!Clients.Contains(client)) { return(false); } if (text == null) { throw new ArgumentNullException("Error: NetworkServer.TransmitToClient null string"); } if (text.Length == 0) { throw new ArgumentException("Error: NetworkServer.TransmitToClient empty string"); } if (text.Length > 0) { try { byte[] msg = Encoding.ASCII.GetBytes(text); client.Socket.SendAsync(msg, SocketFlags.None); return(true); } catch (SocketException ex) { ErrorMessage(ex); RemoveClient(client, false); return(false); } catch (Exception ex) { ErrorMessage(ex); RemoveClient(client, false); return(false); } } return(false); }
private static void RemoveClient(IClientConnectable client, bool wasGraceful, string extraInfo = "") { if (client == null) { throw new ArgumentNullException("Error: NetworkServer.RemoveClient null client"); } if (extraInfo == null) { extraInfo = ""; } // extraInfo.Length == 0 OK if (wasGraceful) { if (extraInfo != "") { Log($" > {client.Nickname} disconnected: {extraInfo}\n"); } else { Log($" > {client.Nickname} disconnected!\n"); } } if (client.Socket.Connected) { client.Socket.Close(); } lock (Clients) { if (Clients.Contains(client)) { Clients.Remove(client); } } }
private static void TryAcceptConnection <T>(IAsyncResult AR) where T : IClientConnectable { if (listenerClosed) { return; } try { Socket newSocket = listenerSocket.EndAccept(AR); IClientConnectable newClient = (T)Activator.CreateInstance(typeof(T), new object[] { newSocket, ++ClientCounter }); AddClient(newClient); newClient.Socket.BeginReceive(newClient.Buffer, 0, BufferSize, SocketFlags.None, new AsyncCallback(OnReceiveData), newClient); listenerSocket.BeginAccept(new AsyncCallback(TryAcceptConnection <T>), null); if (TryTransmitToClient(newClient, "\nYou are now connected to the network server. For connection-related support, type '/help'.\n\n")) { TryTransmitToClient(newClient, newClient.GetImmediateReplyForClient()); } } catch (Exception ex) { ErrorMessage(ex); } }
// ======================================================================================= // ASYNC RECEIVER // ======================================================================================= private static void OnReceiveData(IAsyncResult ar) { IClientConnectable thisClient = (IClientConnectable)ar.AsyncState; if (thisClient == null) { return; } if (!Clients.Contains(thisClient)) { Log($"Discarding listener for {thisClient}.\n"); return; } int bytesReceived = 0; if (thisClient.Socket.Connected) { try { bytesReceived = thisClient.Socket.EndReceive(ar); if (bytesReceived > 0) { string incomingData = Encoding.ASCII.GetString(thisClient.Buffer, 0, bytesReceived).Trim(); if (incomingData.Length > 0 && incomingData.Substring(0, 1) == "/") { string feedback = HandleConsoleCommands(thisClient, incomingData); if (TryTransmitToClient(thisClient, $"{feedback}\n")) { thisClient.Socket.BeginReceive(thisClient.Buffer, 0, BufferSize, 0, new AsyncCallback(OnReceiveData), thisClient); } } else { Log($"{thisClient.Nickname}: [{incomingData}]\n"); thisClient.HandleInputFromClientToServer(incomingData); if (TryTransmitToClient(thisClient, thisClient.GetImmediateReplyForClient())) { thisClient.Socket.BeginReceive(thisClient.Buffer, 0, BufferSize, 0, new AsyncCallback(OnReceiveData), thisClient); } } } } catch (SocketException ex) { switch (ex.ErrorCode) { case 10054: Log($"Error ({ex.ErrorCode}): {thisClient.Nickname} dropped!\n"); RemoveClient(thisClient, false); break; default: ErrorMessage($"SocketException ({ex.ErrorCode}): {ex.Message}!", ex); break; } if (thisClient.Socket.Connected) { thisClient.Socket.Close(); } } catch (Exception ex) { ErrorMessage(ex); } } }