/* * Loop that listens and reacts to all input for this connection */ private void ClientThread() { int requestCount = 0; byte[] bytesFrom; string dataFromClient; string rCount; // Why isn't Connected working??? while (clientSocket != null && clientSocket.Connected) { try { requestCount++; NetworkStream networkStream = clientSocket.GetStream(); // clear the buffer and wait for input try { if (passedMsg.Length > 0) { dataFromClient = passedMsg; passedMsg = ""; } else { bytesFrom = new byte[1024]; networkStream.Read(bytesFrom, 0, bytesFrom.Length); dataFromClient = System.Text.Encoding.ASCII.GetString(bytesFrom); dataFromClient = dataFromClient.Replace("\0", string.Empty).Trim(); } rCount = Convert.ToString(requestCount); } catch (Exception ex) { if (this.clientSocket.Connected) { // read error mw.Display("DOCHAT - Read error: " + ex.Message, 1); } else { // Client has disconnected mw.Display("DOCHAT - Client disconnected ->" + ThreadGUID, 7); } dataFromClient = string.Empty; } // It's not possible to receive a zero length string // so if we find one then we'll assume a disconnect if (dataFromClient.Trim().Length == 0) { mw.Display(">>> Null data from client " + ThreadGUID + "\r\n>>>Closing Connection\r\n"); break; } dataFromClient = cs.MsgProc(dataFromClient.Trim(), ThreadGUID); // If there's a message, send the info out to all connections if (dataFromClient.Length > 0) { cs.Broadcast(dataFromClient, ThreadGUID); } } catch (Exception ex) { mw.Display(string.Format("DOCHAT - ID {0} - Error: {1}", ThreadGUID, ex.ToString()), 1); } }//end while mw.Display(string.Format("DOCHAT - Lost Connection {0}", ThreadGUID), 7); destroyMe = true; }//end doChat
public void Process(ref ClassCommandInfo cmdInfo) { string cmd; string msg = cmdInfo.msg; string replay; ClassUsers targetUser; ClassRooms rm; ClassRooms currentRoom = (ClassRooms)roomHash[cmdInfo.ThisUser.CurrentRoom]; switch (cmdInfo.command) { case "MSG": // private msg - MGS usernick msg string toUser = msg.Substring(0, msg.IndexOf(' ')).Trim(); replay = string.Format("/{0} {1} {2}\r\n", cmdInfo.command, toUser, msg); // must have a space or there is no message if (msg.Contains(" ")) { ClassUsers toU = chatServer.usersList.Find(x => x.NickName.Equals(toUser, StringComparison.OrdinalIgnoreCase)); rm = (ClassRooms)roomHash[toU.CurrentRoom]; // Are you trying to talk to a speaker? bool OK2Speak = toU.Seating != 3; // If they are talking to a speaker in the same room, then if (OK2Speak == false && toU.CurrentRoom == cmdInfo.ThisUser.CurrentRoom) { // are they sysadmin? OK2Speak = OK2Speak || cmdInfo.ThisUser.IsAdmin; // are they moderators or admin? OK2Speak = OK2Speak || ((rm.admin + rm.moderators).Contains(cmdInfo.ThisUser.RegisteredGUID)); // are they another speaker? OK2Speak = OK2Speak || cmdInfo.ThisUser.Seating == 3; } if (OK2Speak) { chatServer.SendPrvMsg(cmdInfo.ThisUser, toU, msg.Substring(msg.IndexOf(' ')).Trim()); } else { // general public tried to talk to a speaker cmdInfo.msgOut = replay + "You are not authorized to send a private msg to a speaker"; } } cmdInfo.command = string.Empty; break; case "ENTER": if (cmdInfo.userIdx >= 0) { // break out the topic if it exists string topic = string.Empty; if (msg.Contains(" ")) { topic = msg.Substring(msg.IndexOf(" ")).Trim(); msg = msg.Substring(0, msg.IndexOf(" ")).Trim().ToUpper(); // room name } else { msg = msg.ToUpper(); } replay = string.Format("/{0} {1} {2}\r\n", cmdInfo.command, topic, msg); if (roomHash.Contains(msg)) { // get the room rm = (ClassRooms)roomHash[msg]; int seating = 0; // here we control seating - chack to see if they gave a password if (topic.Length > 0 && rm.privateSeats > 0) { if (rm.password.Equals(topic)) { seating = 1; } else { cmdInfo.msgOut = replay + "Invalid Password"; seating = -1; } } // is there any seating available? if (seating == 0 && rm.privacySetting == 3) { // is this an invited speaker? // if so, set seating to 3 } // you're allowed to try to enter if (seating >= 0) { EnterRoom(ref cmdInfo, msg, seating); } } else { // clean up the room name so only has A-Z, 0-9, or _ and - string roomName = regex.Replace(msg.ToUpper(), ""); // Is there a saved room with this name? bool validName = (File.Exists(chatServer.LocalPath + roomName + SmallDataHandler.dataExt) == false); if (validName) { if (cusswords.Length > 0) { for (int i = 0; i < cusswords.Length; i++) { if (roomName.ToLower().Contains(cusswords[i])) { validName = false; break; } } } // is it a valid name and is it a valid length? if (validName && Enumerable.Range(3, 15).Contains(roomName.Length)) { if (roomHash.Contains(roomName) == false) { cmdInfo.msgOut = replay + "You have created " + roomName; ClassRooms room = new ClassRooms(cmdInfo.ThisUser.RegisteredGUID, roomName, topic); roomHash.Add(roomName, room); } EnterRoom(ref cmdInfo, roomName, 0); } else { cmdInfo.msgOut = replay + string.Format("Sorry, {0} is invalid. It can only contain letters, numbers, underscore, and dashes with length between 3 and 15 characters and not contain black listed words.", msg.ToUpper()); } } else { // You can't create this room cmdInfo.msgOut = replay + string.Format("Sorry, room {0} has a profile and must be loaded by room owner or a moderator", msg.ToUpper()); } } } break; // PRIVACY - 0=not private, 1=invite only, 2=PW invite // SEATS - x/y/z where x is number of public seats, y is number of private seats, z is speaker seats // RECORD - NO|YES - turn recording on or off case "CHANGE": // update room properties - CHANGE PRIVACY|RECORD|SEATS|TOPIC <value> msg += " "; replay = string.Format("/{0} {1}\r\n", cmdInfo.command, msg); if (cmdInfo.userIdx >= 0) { cmd = msg.Substring(0, msg.IndexOf(" ")).Trim().ToUpper(); msg = msg.Substring(msg.IndexOf(" ")).Trim(); int ivalue = 0; rm = (ClassRooms)roomHash[cmdInfo.ThisUser.CurrentRoom]; if (rm.admin.Equals(cmdInfo.ThisUser.RegisteredGUID)) { switch (cmd) { case "SPEAKER": // extend or revoke speaker invitation cmd = "/" + msg.ToUpper() + "/"; cmd = Names2IDs(cmd); if (rm.speakers.Contains(cmd)) { rm.moderators = rm.speakers.Replace(cmd, "/"); } else { rm.speakers += cmd; } rm.speakers = rm.speakers.Replace("//", "/"); roomHash[cmdInfo.ThisUser.CurrentRoom] = rm; cmdInfo.msgOut = replay + string.Format("Speaker List\r\n--------------------\r\n{0}", IDs2Names(rm.speakers, "nickname").Substring(1).Replace("/", "\r\n")); break; case "MOD": // find the nick cmd = "/" + msg.ToUpper() + "/"; cmd = Names2IDs(cmd); if (rm.moderators.Contains(cmd)) { rm.moderators = rm.moderators.Replace(cmd, "/"); } else { rm.moderators += cmd; } rm.moderators = rm.moderators.Replace("//", "/"); roomHash[cmdInfo.ThisUser.CurrentRoom] = rm; cmdInfo.msgOut = replay + string.Format("Moderator List\r\n--------------------\r\n{0}", IDs2Names(rm.moderators, "nickname").Substring(1).Replace("/", "\r\n")); break; case "PASSWORD": // add a password for private seating rm.password = regex.Replace(msg, ""); cmdInfo.msgOut = replay + string.Format("Password set to '{0}'", rm.password); break; case "PRIVACY": // set privacy level if (int.TryParse(msg, out ivalue)) { if (ivalue > 2) { cmdInfo.msgOut = replay + string.Format("Valid privacy settings are 0=OPEN, 1=INVITE, 2=PASSWORD\r\n" + "Higher values are automatically assigned based on other room settings.\r\n" + "Use /HELP command for more information."); } else { rm.privacySetting = ivalue; cmdInfo.msgOut = replay + string.Format("Privacy set to {0}", ivalue); rm.speakerSeats = 0; } } else { cmdInfo.msgOut = replay + string.Format("Failed to convert '{0}' to an integer", msg); } break; case "RECORD": if (msg.ToUpper().Equals("ON")) { cmdInfo.msgOut = replay + "N/A - Recording turned on"; rm.record = true; } else { cmdInfo.msgOut = replay + "N/A - Recording turned off"; // turn off recording rm.record = false; } break; case "SEATS": string[] s = msg.Split('/'); if (s.Length > 2) { if (int.TryParse(s[0], out ivalue)) { rm.publicSeats = ivalue; // anyone can join these - when privacy level>0 then listen only } if (int.TryParse(s[1], out ivalue)) { rm.privateSeats = ivalue; // password entry - can speak except when in forum, then submits questions to top of list } if (int.TryParse(s[2], out ivalue)) { rm.speakerSeats = ivalue; // invitation only - forum setting only and can speak freely } if (rm.speakerSeats > 0) { rm.privacySetting = 3; // if you have speakers, its a FORUM and entry is restricted } cmdInfo.msgOut = replay + string.Format("Seats are set to {0} public, {1} private, and {2} speaker", rm.publicSeats, rm.privateSeats, rm.speakerSeats); } else { cmdInfo.msgOut = replay + string.Format("You sent SEATS {0} and format must be 9/9/9", msg); } break; case "TOPIC": // filter content of topic rm.topic = msg; cmdInfo.msgOut = replay + string.Format("Room topic is '{0}'", rm.topic); break; default: cmdInfo.msgOut = replay + string.Format("Unknown CHANGE command {0}", cmd); break; } roomHash[cmdInfo.ThisUser.CurrentRoom] = rm; } else { cmdInfo.msgOut = replay + "You are not an admin for this room"; } } break; // If in a speaker room, turn general chat on/off case "FORUM": cmdInfo.msgOut = string.Format("/{0}\r\n", cmdInfo.command); if (currentRoom.privacySetting > 2) { // room admin or moderator? (sysadmin can't control this) if ((currentRoom.moderators + currentRoom.admin).Contains(cmdInfo.ThisUser.RegisteredGUID)) { if (msg.ToUpper().Equals("START")) { chatServer.Broadcast("Quiet please, forum is starting...", cmdInfo.ThisUser.RegisteredGUID); currentRoom.privacySetting = 4; } if (msg.ToUpper().Equals("END")) { currentRoom.privacySetting = 3; chatServer.Broadcast("Thank you, the forum has ended...", cmdInfo.ThisUser.RegisteredGUID); } roomHash[cmdInfo.ThisUser.CurrentRoom] = currentRoom; } } break; case "RMSAVE": // SAVE a room msg += " "; replay = string.Format("/{0}\r\n", cmdInfo.command); rm = (ClassRooms)roomHash[cmdInfo.ThisUser.CurrentRoom]; if (rm.admin.Equals(cmdInfo.ThisUser.RegisteredGUID)) { SmallDataHandler sdh = new SmallDataHandler(chatServer.LocalPath); SmallFileHandlerStructure rec; // Room table holds the following (reclen=150, fields=12) // RMI|RoomName|Topic|Seats|Admin|PW // MOD|Moderator List (10 per line) // SPK|Speaker List (10 per line) // BAN|Banned RegIDs (10 per line) // Save the file try { // delete a bak file if (File.Exists(chatServer.LocalPath + rm.name + ".bak")) { File.Delete(chatServer.LocalPath + rm.name + ".bak"); } // rename the file to a BAK if (File.Exists(chatServer.LocalPath + rm.name + SmallDataHandler.dataExt)) { File.Move(chatServer.LocalPath + rm.name + SmallDataHandler.dataExt, chatServer.LocalPath + rm.name + ".bak"); } // create a new one if (sdh.Create(rm.name, 150, 12)) { // Save the room info //------------------------------ rec = sdh.BlankRec(); rec.Fields[0] = "RMI"; rec.Fields[1] = rm.name; rec.Fields[2] = rm.topic; rec.Fields[3] = "" + rm.publicSeats + "/" + rm.privateSeats + "/" + rm.speakerSeats; rec.Fields[4] = rm.admin; rec.Fields[5] = rm.password; sdh.AddRec(rec); // save moderators //------------------------------ rec = sdh.BlankRec(); string[] info = rm.moderators.Split('/'); rec.Fields[0] = "MOD"; int j = 0; int i = 0; // You can only have 10 mods saved to file while (j < info.Length && i < 10) { // save a nonblank mod listing if (info[j].Length > 0) { rec.Fields[1 + i++] = info[j]; } // next mod in list j++; } sdh.AddRec(rec); // save speakers //------------------------------ rec = sdh.BlankRec(); info = rm.speakers.Split('/'); rec.Fields[0] = "SPK"; j = 0; i = 0; // You can only have 10 speakers saved to file while (j < info.Length && i < 10) { // save a nonblank mod listing if (info[j].Length > 0) { rec.Fields[1 + i++] = info[j]; } // next mod in list j++; } sdh.AddRec(rec); // save Banned list //------------------------------ info = rm.banned.Split('/'); j = 0; i = 0; // Banned list goes on forever while (j < info.Length) { if (j % 10 == 0) { if (j > 0) { sdh.AddRec(rec); } rec = sdh.BlankRec(); rec.Fields[0] = "BAN"; i = 0; } // save a nonblank mod listing if (info[j].Length > 0) { rec.Fields[1 + i++] = info[j]; } // next mod in list j++; } if (rec.Fields[1].Length > 0) { sdh.AddRec(rec); } cmdInfo.msgOut = string.Format("Room prifile for {0} has been saved", rm.name); } else { cmdInfo.msgOut = replay + string.Format("Failed to save room\r\nError: {0} - {1}", sdh.ErrorCode, sdh.ErrorMessage); } } catch (Exception ex) { cmdInfo.msgOut = replay + "Failed to save room\r\nError: " + ex.Message; } finally { cmdInfo.command = string.Empty; sdh.Close(); } } else { cmdInfo.msgOut = replay + "You aren't the room adminstrator"; } break; case "RMLOAD": replay = string.Format("/{0} {1}\r\n", cmdInfo.command, msg); cmd = string.Empty; if (msg.Contains(' ')) { cmd = msg.Substring(msg.IndexOf(' ')).Trim(); msg = msg.Substring(0, msg.IndexOf(' ')).Trim(); } if (msg.Length > 0) { SmallDataHandler sdh = new SmallDataHandler(chatServer.LocalPath); SmallFileHandlerStructure rec; if (roomHash.ContainsKey(cmd.Length > 0 ? cmd : msg)) { cmdInfo.msgOut = replay + "Room is already loaded"; } else { rm = new ClassRooms(msg, msg, ""); if (File.Exists(chatServer.LocalPath + msg + SmallDataHandler.dataExt)) { try { if (sdh.Open(msg)) { rec = sdh.ReadAtIndex(1); // room info if (rec.Fields[0].Equals("RMI")) { if (cmd.Length == 0) { // load admin ID, room name, topic, and password rm = new ClassRooms(rec.Fields[4], rec.Fields[1], rec.Fields[2]) { password = rec.Fields[5] }; } else { // load admin ID, room name, topic, and password rm = new ClassRooms(cmdInfo.ThisUser.RegisteredGUID, cmd, rec.Fields[2]) { password = rec.Fields[5] }; } string[] seats = rec.Fields[3].Split('/'); int.TryParse(seats[0], out rm.publicSeats); if (seats.Length > 1) { int.TryParse(seats[1], out rm.privateSeats); } if (seats.Length > 2) { int.TryParse(seats[2], out rm.speakerSeats); } } // if trying to copy, check to see if room is password protected if (cmd.Length == 0 || rm.password.Length == 0) { // continue to load info, read in moderators rec = sdh.ReadAtIndex(2); // moderators if (rec.Fields[0].Equals("MOD")) { for (int j = 1; j < rec.Fields.Length; j++) { rm.moderators += rec.Fields[j] + "/"; } while (rm.moderators.Contains("//")) { rm.moderators = rm.moderators.Replace("//", "/"); } } // read in speakers rec = sdh.ReadAtIndex(3); if (rec.Fields[0].Equals("SPK")) { for (int j = 1; j < rec.Fields.Length; j++) { rm.speakers += rec.Fields[j] + "/"; } while (rm.speakers.Contains("//")) { rm.speakers = rm.speakers.Replace("//", "/"); } } // read in banned users int i = 4; while (i <= sdh.RecCount) { rec = sdh.ReadAtIndex(i); if (rec.Fields[0].Equals("BAN")) { for (int j = 1; j < rec.Fields.Length; j++) { rm.banned += rec.Fields[j] + "/"; } } i++; } while (rm.banned.Contains("//")) { rm.banned = rm.banned.Replace("//", "/"); } // final check to see if ok for this user to load the room if (rm.admin.Equals(cmdInfo.ThisUser.RegisteredGUID) || rm.moderators.Contains(cmdInfo.ThisUser.RegisteredGUID)) { // create the room in the hash table if it // hasn't been done already if (roomHash.ContainsKey(rm.name) == false) { roomHash.Add(rm.name, rm); } // Enter the room EnterRoom(ref cmdInfo, rm.name, 0); if (cmd.Length > 0) { cmdInfo.msgOut = "You copied room profile " + msg + " as " + cmd; } else { cmdInfo.msgOut = "You loaded room profile " + msg; } } else { // not authorized cmdInfo.msgOut = "You are not an admin or moderator for this room profile"; } } else { // can't copy a PW protected room cmdInfo.msgOut = "You cannot copy a password protected room"; } } else { cmdInfo.msgOut = replay + string.Format("Failed to save room\r\nError: {0} - {1}", sdh.ErrorCode, sdh.ErrorMessage); } } catch (Exception ex) { cmdInfo.msgOut = replay + "Failed to save room\r\nError: " + ex.Message; } finally { cmdInfo.command = string.Empty; sdh.Close(); } } else { cmdInfo.msgOut = "Table for room " + msg + " was not found"; } } } break; case "BAN": // admin/moderator can ban someone from the room - BAN <nick>|<IP> // BAN ? returns a list replay = string.Format("/{0} {1}\r\n", cmdInfo.command, msg); if (msg.Contains("?") == false) { if (cmdInfo.userIdx >= 0) { rm = (ClassRooms)roomHash[cmdInfo.ThisUser.CurrentRoom]; if (rm.admin.Equals(cmdInfo.ThisUser.RegisteredGUID) || rm.moderators.Contains("/" + cmdInfo.ThisUser.RegisteredGUID + "/")) // are you an admin or moderator? { // find the user to ban string banID = "/" + userReg.GetUserRecord(msg).GetField("RecID") + "/"; if (banID.Length > 2) // found the nick { if (rm.banned.Contains(banID) == false) { currentRoom.banned += banID; } else { currentRoom.banned = currentRoom.banned.Replace(banID, "/"); } currentRoom.banned = currentRoom.banned.Replace("//", "/"); roomHash[cmdInfo.ThisUser.CurrentRoom] = currentRoom; } else { cmdInfo.msgOut = replay + msg + " isn't a registered user"; } } else { cmdInfo.msgOut = replay + "You don't have the power to kick someone from this room"; } } } cmdInfo.msgOut = replay + "\r\nBanned Users\r\n---------------------------------\r\n"; if (currentRoom.banned.Length > 2) { cmdInfo.msgOut += userReg.IDs2Names(currentRoom.banned, "nickname").Substring(1).Replace("/", "\r\n") + "\r\n"; } else { cmdInfo.msgOut += "No banned users"; } //cmdInfo.command = string.Empty; break; case "KICK": // admin or moderator can kick someone out of private channel, but they can just come back in - KICK <usernick> [<message>] replay = string.Format("/{0} {1}\r\n", cmdInfo.command, msg); if (cmdInfo.userIdx >= 0) { rm = (ClassRooms)roomHash[cmdInfo.ThisUser.CurrentRoom]; if (rm.admin.Equals(cmdInfo.ThisUser.RegisteredGUID) || rm.moderators.Contains("/" + cmdInfo.ThisUser.RegisteredGUID + "/")) // are you an admin or moderator? { msg += " "; cmd = msg.Substring(0, msg.IndexOf(" ")).Trim().ToUpper(); // usernick msg = msg.Substring(msg.IndexOf(" ")).Trim(); // message, if any // find the user to kick int targetIdx = chatServer.usersList.FindIndex(x => x.NickName.Equals(cmd, StringComparison.OrdinalIgnoreCase)); if (targetIdx >= 0) // found the nick { targetUser = chatServer.usersList[targetIdx]; if (targetUser.CurrentRoom.Equals(cmdInfo.ThisUser.CurrentRoom)) // are they in this room? { if (rm.admin.Equals(targetUser.UserName)) // is the person to be kicked an admin? { cmdInfo.msgOut = replay + "You can't kick the room admin"; } else if (rm.moderators.Contains("/" + targetUser.RegisteredGUID + "/")) // is the person to be kicked a moderator { cmdInfo.msgOut = replay + "You can't kick a room moderator"; } else { // OK, kick them back to the lobby EnterRoom(ref cmdInfo, "LOBBY", 0); chatServer.BroadcastMsgToRoom(cmdInfo.ThisUser.CurrentRoom, targetUser.NickName + " kicked out of the room by " + cmdInfo.ThisUser.NickName); chatServer.SendToGUID(targetUser.ThreadGUID, "You were kicked to the lobby" + (msg.Length > 0 ? " with message " + msg : "")); cmdInfo.command = string.Empty; } } else { cmdInfo.msgOut = replay + targetUser.NickName + " isn't in this room"; } } else { cmdInfo.msgOut = replay + cmd + " isn't in this room"; } } else { cmdInfo.msgOut = replay + "You don't have the power to kick someone from this room"; } } break; case "ROOMS": string rooms = "/ROOMS\r\n\r\nRoom List\r\n------------------------------\r\n\r\n"; foreach (DictionaryEntry r in roomHash) { ClassRooms rInfo = (ClassRooms)r.Value; string privacy = "O"; privacy = PrivacyType(rInfo.privacySetting); // get number of people in each seating type int[] seated = new int[] { rInfo.publicSeats, rInfo.privateSeats, rInfo.speakerSeats }; for (int i = 0; i < chatServer.usersList.Count; i++) { if (chatServer.usersList[i].CurrentRoom.Equals(rInfo.name)) { seated[chatServer.usersList[i].Seating]--; } } // list the room and seats available if (rInfo.privateSeats > 0 || rInfo.speakerSeats > 0) { privacy += string.Format(" - {0}/{1}/{2}", seated[0], seated[1], seated[2]); } else { privacy += string.Format(" - {0}", seated[0]); } rooms += string.Format("{0} ({1} seats) {2}", rInfo.name, privacy, (rInfo.topic.Length > 0 ? " - " + rInfo.topic : "")) + "\r\n"; } cmdInfo.msgOut = rooms + "\r\n------------------------------\r\n"; break; case "IGNORE": // toggle ignoring someone replay = string.Format("/{0} {1}", cmdInfo.command, msg); chatServer.Ignore(cmdInfo.ThisUser.ThreadGUID, msg); cmdInfo.msgOut = "Ignore List\r\n-----------------------\r\n" + IDs2NameList(cmdInfo.ThisUser.IgnoreList, "nickname"); cmdInfo.command = string.Empty; break; case "RMINFO": rm = (ClassRooms)roomHash[cmdInfo.ThisUser.CurrentRoom]; cmdInfo.msgOut = "/RMINFO\r\n"; cmdInfo.msgOut += string.Format("Name: {0}\r\n", rm.name); cmdInfo.msgOut += string.Format("Topic: {0}\r\n", rm.topic); cmdInfo.msgOut += string.Format("Seating: {0}/{1}/{2}\r\n", rm.publicSeats, rm.privateSeats, rm.speakerSeats); cmdInfo.msgOut += string.Format("Password: {0}\r\n", (rm.password.Length > 0 ? "**********" : "")); cmdInfo.msgOut += string.Format("Privacy: {0} - {1}\r\n", rm.privacySetting, PrivacyType(rm.privacySetting)); cmdInfo.msgOut += string.Format("Admin: {0}\r\n", IDs2NameList("/" + rm.admin + "/", "nickname")); cmdInfo.msgOut += string.Format("Moderators: {0}\r\n", IDs2NameList(rm.moderators, "nickname")); cmdInfo.msgOut += string.Format("Banned : {0}\r\n\r\n", IDs2NameList(rm.banned, "nickname")); break; default: break; } if (cmdInfo.msgOut.Length > 0) { cmdInfo.command = string.Empty; } return; }
/* * Loop that listens and reacts to all input for this connection */ private void DoChat() { int requestCount = 0; byte[] bytesFrom; string dataFromClient; string rCount; while (this.clientSocket.Connected) { try { requestCount++; NetworkStream networkStream = clientSocket.GetStream(); // clear the buffer and wait for input try { bytesFrom = new byte[1024]; networkStream.Read(bytesFrom, 0, bytesFrom.Length); dataFromClient = System.Text.Encoding.ASCII.GetString(bytesFrom); dataFromClient = dataFromClient.Replace("\0", string.Empty).Trim(); mw.Display("From client - " + clNo + " -> " + dataFromClient); rCount = Convert.ToString(requestCount); } catch (Exception ex) { if (this.clientSocket.Connected) { // read error mw.Display("DOCHAT - Read error: " + ex.Message); } else { // Client has disconnected mw.Display("DOCHAT - Client disconnected ->" + clNo); } dataFromClient = string.Empty; } // break out server command and add space to protect the code string msg = dataFromClient.Trim(); //mw.Display("from=" + NickName + "\r\nmsg=" + msg); // Is there a command (starts with /) if (msg.Length > 1) { cs.LastMsgAt(clNo); // update time of last message if (msg.Substring(0, 1).Equals("/")) { // Process the command msg += " "; string command = msg.Substring(1, msg.IndexOf(' ') - 1).Trim().ToUpper(); msg = msg.Substring(msg.IndexOf(' ')).Trim(); dataFromClient = string.Empty; //Console.WriteLine("Processing command " + command); switch (command) { case "NAMES": // return user list - LIST string names = "/NAMES\r\n\r\nNames List\r\n--------------------\r\n"; for (int i = 0; i < cs.users.Count; i++) { names += string.Format("{0} @ {1}", cs.users[i].NickName, cs.users[i].LastMsg.ToString("HH:mm")) + "\r\n"; } names += "\r\n--------------------\r\n"; cs.sendOut(clNo, names); break; case "KICK": // kick nick - KICK usernick break; case "NICK": // Change the nickname // no spaces, no parens, 20 char max - dems da rules msg = msg.Replace("(", "").Replace(")", "").Replace(" ", ""); msg = (msg.Length > 20 ? msg.Substring(0, 20) : msg); if (cs.NickExists(msg) >= 0) { dataFromClient = "-> " + NickName + " has changed their nickname to " + msg; NickName = msg.Trim(); } else { cs.sendOut(clNo, "Nickname already exists"); } break; case "REG": // register user - REG username pw break; case "PASS": // change password - PASS old new break; case "MSG": // private msg - MGS usernick msg string toUser = msg.Substring(0, msg.IndexOf(' ')).Trim(); // must have a space or there is no message if (msg.Contains(' ')) { cs.SendTo(NickName, toUser, msg.Substring(msg.IndexOf(' ')).Trim()); } break; case "HELP": // return help screen - HELP cs.Help(clNo); break; default: // unknown command - respond with error to user mw.Display("DOCHAT - Unknown command: " + command); break; } } else { // normal message dataFromClient = NickName + ": " + msg; } } // If there's a message, send the info out to all connections if (dataFromClient.Length > 0) { cs.Broadcast(dataFromClient, clNo); } } catch (Exception ex) { mw.Display(string.Format("DOCHAT - ID {0} - Error: {1}", clNo, ex.ToString())); } }//end while mw.Display(string.Format("DOCHAT - Lost Connection {0}", clNo)); destroyMe = true; }//end doChat