diff --git a/Cargo.lock b/Cargo.lock index 7537e3a..013985d 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1,6 +1,6 @@ # This file is automatically @generated by Cargo. # It is not intended for manual editing. -version = 3 +version = 4 [[package]] name = "autocfg" @@ -56,8 +56,9 @@ name = "fourat" version = "0.1.0" dependencies = [ "crossterm", - "getrandom", + "getrandom 0.2.10", "mio", + "rand", ] [[package]] @@ -68,14 +69,26 @@ checksum = "be4136b2a15dd319360be1c07d9933517ccf0be8f16bf62a3bee4f0d618df427" dependencies = [ "cfg-if", "libc", - "wasi", + "wasi 0.11.0+wasi-snapshot-preview1", +] + +[[package]] +name = "getrandom" +version = "0.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73fea8450eea4bac3940448fb7ae50d91f034f941199fcd9d909a5a07aa455f0" +dependencies = [ + "cfg-if", + "libc", + "r-efi", + "wasi 0.14.2+wasi-0.2.4", ] [[package]] name = "libc" -version = "0.2.149" +version = "0.2.172" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a08173bc88b7955d1b3145aa561539096c421ac8debde8cbc3612ec635fee29b" +checksum = "d750af042f7ef4f724306de029d18836c26c1765a54a6a3f094cbd23a7267ffa" [[package]] name = "lock_api" @@ -101,7 +114,7 @@ checksum = "8f3d0b296e374a4e6f3c7b0a1f5a51d748a0d34c85e7dc48fc3fa9a87657fe09" dependencies = [ "libc", "log", - "wasi", + "wasi 0.11.0+wasi-snapshot-preview1", "windows-sys", ] @@ -128,6 +141,68 @@ dependencies = [ "windows-targets", ] +[[package]] +name = "ppv-lite86" +version = "0.2.21" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "85eae3c4ed2f50dcfe72643da4befc30deadb458a9b590d720cde2f2b1e97da9" +dependencies = [ + "zerocopy", +] + +[[package]] +name = "proc-macro2" +version = "1.0.95" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "02b3e5e68a3a1a02aad3ec490a98007cbc13c37cbe84a3cd7b8e406d76e7f778" +dependencies = [ + "unicode-ident", +] + +[[package]] +name = "quote" +version = "1.0.40" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1885c039570dc00dcb4ff087a89e185fd56bae234ddc7f056a945bf36467248d" +dependencies = [ + "proc-macro2", +] + +[[package]] +name = "r-efi" +version = "5.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "74765f6d916ee2faa39bc8e68e4f3ed8949b48cccdac59983d287a7cb71ce9c5" + +[[package]] +name = "rand" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9fbfd9d094a40bf3ae768db9361049ace4c0e04a4fd6b359518bd7b73a73dd97" +dependencies = [ + "rand_chacha", + "rand_core", +] + +[[package]] +name = "rand_chacha" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3022b5f1df60f26e1ffddd6c66e8aa15de382ae63b3a0c1bfc0e4d3e3f325cb" +dependencies = [ + "ppv-lite86", + "rand_core", +] + +[[package]] +name = "rand_core" +version = "0.9.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "99d9a13982dcf210057a8a78572b2217b667c3beacbf3a0d8b454f6f82837d38" +dependencies = [ + "getrandom 0.3.2", +] + [[package]] name = "redox_syscall" version = "0.4.1" @@ -179,12 +254,38 @@ version = "1.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "942b4a808e05215192e39f4ab80813e599068285906cc91aa64f923db842bd5a" +[[package]] +name = "syn" +version = "2.0.101" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8ce2b7fc941b3a24138a0a7cf8e858bfc6a992e7978a068a5c760deb0ed43caf" +dependencies = [ + "proc-macro2", + "quote", + "unicode-ident", +] + +[[package]] +name = "unicode-ident" +version = "1.0.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5a5f39404a5da50712a4c1eecf25e90dd62b613502b7e925fd4e4d19b5c96512" + [[package]] name = "wasi" version = "0.11.0+wasi-snapshot-preview1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423" +[[package]] +name = "wasi" +version = "0.14.2+wasi-0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "9683f9a5a998d873c0d21fcbe3c083009670149a8fab228644b8bd36b2c48cb3" +dependencies = [ + "wit-bindgen-rt", +] + [[package]] name = "winapi" version = "0.3.9" @@ -272,3 +373,32 @@ name = "windows_x86_64_msvc" version = "0.48.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ed94fce61571a4006852b7389a063ab983c02eb1bb37b47f8272ce92d06d9538" + +[[package]] +name = "wit-bindgen-rt" +version = "0.39.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6f42320e61fe2cfd34354ecb597f86f413484a798ba44a8ca1165c58d42da6c1" +dependencies = [ + "bitflags 2.4.1", +] + +[[package]] +name = "zerocopy" +version = "0.8.25" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a1702d9583232ddb9174e01bb7c15a2ab8fb1bc6f227aa1233858c351a3ba0cb" +dependencies = [ + "zerocopy-derive", +] + +[[package]] +name = "zerocopy-derive" +version = "0.8.25" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "28a6e20d751156648aa063f3800b706ee209a32c0b4d9f24be3d980b01be55ef" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] diff --git a/Cargo.toml b/Cargo.toml index 1cf07fd..a5c86e0 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -21,3 +21,4 @@ path = "./src/pandora.rs" crossterm = "0.27.0" getrandom = "0.2.10" mio = "0.8.10" +rand = "0.9.1" diff --git a/src/server.rs b/src/server.rs index f187b81..2238554 100644 --- a/src/server.rs +++ b/src/server.rs @@ -11,6 +11,7 @@ use std::fs; use std::io; use mio::net::{TcpListener, TcpStream}; use mio::{Poll, Interest, Token, Events}; +use rand::seq::IndexedRandom; type Result = result::Result; @@ -21,6 +22,356 @@ const MESSAGE_RATE: Duration = Duration::from_secs(1); const SLOWLORIS_LIMIT: Duration = Duration::from_millis(200); const STRIKE_LIMIT: usize = 10; +//Adjectives and names from docker name generator project +const ADJECTIVES: &[&str] = &[ + "admiring", + "adoring", + "affectionate", + "agitated", + "amazing", + "angry", + "awesome", + "beautiful", + "blissful", + "bold", + "boring", + "brave", + "busy", + "charming", + "clever", + "compassionate", + "competent", + "condescending", + "confident", + "cool", + "cranky", + "crazy", + "dazzling", + "determined", + "distracted", + "dreamy", + "eager", + "ecstatic", + "elastic", + "elated", + "elegant", + "eloquent", + "epic", + "exciting", + "fervent", + "festive", + "flamboyant", + "focused", + "friendly", + "frosty", + "funny", + "gallant", + "gifted", + "goofy", + "gracious", + "great", + "happy", + "hardcore", + "heuristic", + "hopeful", + "hungry", + "infallible", + "inspiring", + "intelligent", + "interesting", + "jolly", + "jovial", + "keen", + "kind", + "laughing", + "loving", + "lucid", + "magical", + "modest", + "musing", + "mystifying", + "naughty", + "nervous", + "nice", + "nifty", + "nostalgic", + "objective", + "optimistic", + "peaceful", + "pedantic", + "pensive", + "practical", + "priceless", + "quirky", + "quizzical", + "recursing", + "relaxed", + "reverent", + "romantic", + "sad", + "serene", + "sharp", + "silly", + "sleepy", + "stoic", + "strange", + "stupefied", + "suspicious", + "sweet", + "tender", + "thirsty", + "trusting", + "unruffled", + "upbeat", + "vibrant", + "vigilant", + "vigorous", + "wizardly", + "wonderful", + "xenodochial", + "youthful", + "zealous", + "zen", + ]; + +const NAMES: &[&str] = &["agnesi", + "albattani", + "allen", + "almeida", + "antonelli", + "archimedes", + "ardinghelli", + "aryabhata", + "austin", + "babbage", + "banach", + "banzai", + "bardeen", + "bartik", + "bassi", + "beaver", + "bell", + "benz", + "bhabha", + "bhaskara", + "black", + "blackburn", + "blackwell", + "bohr", + "booth", + "borg", + "bose", + "bouman", + "boyd", + "brahmagupta", + "brattain", + "brown", + "buck", + "burnell", + "cannon", + "carson", + "cartwright", + "carver", + "cerf", + "chandrasekhar", + "chaplygin", + "chatelet", + "chatterjee", + "chaum", + "chebyshev", + "clarke", + "cohen", + "colden", + "cori", + "cray", + "curie", + "curran", + "darwin", + "davinci", + "dewdney", + "dhawan", + "diffie", + "dijkstra", + "dirac", + "driscoll", + "dubinsky", + "easley", + "edison", + "einstein", + "elbakyan", + "elgamal", + "elion", + "ellis", + "engelbart", + "euclid", + "euler", + "faraday", + "feistel", + "fermat", + "fermi", + "feynman", + "franklin", + "gagarin", + "galileo", + "galois", + "ganguly", + "gates", + "gauss", + "germain", + "goldberg", + "goldstine", + "goldwasser", + "golick", + "goodall", + "gould", + "greider", + "grothendieck", + "haibt", + "hamilton", + "haslett", + "hawking", + "heisenberg", + "hellman", + "hermann", + "herschel", + "hertz", + "heyrovsky", + "hodgkin", + "hofstadter", + "hoover", + "hopper", + "hugle", + "hypatia", + "ishizaka", + "jackson", + "jang", + "jemison", + "jennings", + "jepsen", + "johnson", + "joliot", + "jones", + "kalam", + "kapitsa", + "kare", + "keldysh", + "keller", + "kepler", + "khayyam", + "khorana", + "kilby", + "kirch", + "knuth", + "kowalevski", + "lalande", + "lamarr", + "lamport", + "leakey", + "leavitt", + "lederberg", + "lehmann", + "lewin", + "lichterman", + "liskov", + "lovelace", + "lumiere", + "mahavira", + "margulis", + "matsumoto", + "maxwell", + "mayer", + "mccarthy", + "mcclintock", + "mclaren", + "mclean", + "mcnulty", + "meitner", + "mendel", + "mendeleev", + "meninsky", + "merkle", + "mestorf", + "mirzakhani", + "montalcini", + "moore", + "morse", + "moser", + "murdock", + "napier", + "nash", + "neumann", + "newton", + "nightingale", + "nobel", + "noether", + "northcutt", + "noyce", + "panini", + "pare", + "pascal", + "pasteur", + "payne", + "perlman", + "pike", + "poincare", + "poitras", + "proskuriakova", + "ptolemy", + "raman", + "ramanujan", + "rhodes", + "ride", + "ritchie", + "robinson", + "roentgen", + "rosalind", + "rubin", + "saha", + "sammet", + "sanderson", + "satoshi", + "shamir", + "shannon", + "shaw", + "shirley", + "shockley", + "shtern", + "sinoussi", + "snyder", + "solomon", + "spence", + "stonebraker", + "sutherland", + "swanson", + "swartz", + "swirles", + "taussig", + "tesla", + "tharp", + "thompson", + "torvalds", + "tu", + "turing", + "varahamihira", + "vaughan", + "villani", + "visvesvaraya", + "volhard", + "wescoff", + "wilbur", + "wiles", + "williams", + "williamson", + "wilson", + "wing", + "wozniak", + "wright", + "wu", + "yalow", + "yonath", + "zhukovsky", + ]; + struct Sens(T); impl fmt::Display for Sens { @@ -40,6 +391,7 @@ struct Client { connected_at: SystemTime, authed: bool, addr: SocketAddr, + username: String, } enum Sinner { @@ -89,6 +441,7 @@ impl Server { fn client_connected(&mut self, mut author: TcpStream, author_addr: SocketAddr, token: Token) { let now = SystemTime::now(); + let username = generate_username(); if let Some(sinner) = self.sinners.get_mut(&author_addr.ip()) { match sinner { @@ -116,25 +469,27 @@ impl Server { } } - println!("INFO: Client {author_addr} connected", author_addr = Sens(author_addr)); + println!("INFO: Client {author_addr} connected, username is {username}", author_addr = Sens(author_addr)); self.clients.insert(token, Client { conn: author, last_message: now - 2*MESSAGE_RATE, connected_at: now, authed: false, addr: author_addr, + username, }); } fn client_read(&mut self, token: Token) { if let Some(author) = self.clients.get_mut(&token) { let author_addr: SocketAddr = author.addr.clone(); + let username = author.username.clone(); let mut buffer = [0; 64]; let bytes: Vec<_> = match author.conn.read(&mut buffer) { Ok(0) => { // TODO: we need to distinguish between willful client disconnects and banned disconnects // Banned Sinners may try to use this to fill up all the space on the hard drive - println!("INFO: Client {author_addr} disconnected", author_addr = Sens(author_addr)); + println!("INFO: Client {username}@{author_addr} disconnected", author_addr = Sens(author_addr), username=author.username); // TODO: if the disconnected client was not authorized we may probably want to strike their // IP, because they are probably constantly connecting/disconnecting trying to evade the // strike. @@ -171,7 +526,7 @@ impl Server { println!("INFO: Client {author_addr} sent message {bytes:?}", author_addr = Sens(author_addr)); for (client_token, client) in self.clients.iter_mut() { if *client_token != token && client.authed { - let _ = writeln!(client.conn, "{text}").map_err(|err| { + let _ = writeln!(client.conn, "[{}]: {text}", username).map_err(|err| { eprintln!("ERROR: could not broadcast message to all the clients from {author_addr}: {err}", author_addr = Sens(author_addr), err = Sens(err)) }); } @@ -262,6 +617,15 @@ fn generate_token() -> Result { Ok(token) } +fn generate_username() -> String { + let mut username = String::new(); + + username.push_str(ADJECTIVES.choose(&mut rand::rng()).unwrap()); + username.push_str(&"_".to_string()); + username.push_str(NAMES.choose(&mut rand::rng()).unwrap()); + + username +} fn main() -> Result<()> { let token = generate_token()?; let token_file_path = "./TOKEN";