1 /++ 2 Definitions of struct aggregates used throughout the library, representing 3 [IRCEvent]s and thereto related objects like [IRCServer] and [IRCUser]. 4 5 Things related to actually parsing IRC do not belong here; what's here 6 should only be applicable to be used as a header. 7 8 The only lu dependency should be [lu.uda]. 9 +/ 10 module dialect.defs; 11 12 private: 13 14 import lu.uda; 15 16 public: 17 18 final: 19 pure: 20 nothrow: 21 @nogc: 22 23 24 // IRCEvent 25 /++ 26 A single IRC event, parsed from server input. 27 28 The [IRCEvent] struct is a construct with fields extracted from raw server 29 strings. Since structs are not polymorphic the [IRCEvent.Type|Type] enum 30 dictates what kind of event it is. 31 +/ 32 struct IRCEvent 33 { 34 private: 35 import std.typecons : Nullable; 36 37 /++ 38 How many elements should be allocated for auxiliary strings. 39 40 `RPL_ISUPPORT` can contain a lot of strings and should be considered the 41 worst case. 42 +/ 43 enum numAuxStrings = 16; 44 45 /++ 46 How many elements should be allocated for counts. 47 +/ 48 enum numCounts = 16; 49 50 public: 51 /++ 52 [Type]s of [IRCEvent]s. 53 54 Taken from https://tools.ietf.org/html/rfc1459 with many additions. 55 56 Some are outright fabrications of ours, like [Type.CHAN|CHAN] and 57 [Type.QUERY|QUERY]. These are not prefixed with `RPL_` and `ERR_` 58 (but not all such are made up, like [Type.AWAY|AWAY] and 59 [Type.CHGHOST|CHGHOST] that are properly [Type.AWAY|AWAY] and 60 [Type.CHGHOST|CHGHOST]). 61 62 See_Also: 63 https://tools.ietf.org/html/rfc1459 64 https://www.alien.net.au/irc/irc2numerics.html 65 https://defs.ircdocs.horse 66 +/ 67 enum Type 68 { 69 UNSET, /// Invalid [IRCEvent] with no [Type]. 70 ANY, /// Meta-[Type] for *any* kind of [IRCEvent]. 71 ERROR, /// Generic error [Type]. 72 NUMERIC, /// *Numeric* event of an unknown [Type]. 73 PRIVMSG, /// Private message or channel message. 74 CHAN, /// Channel message. 75 QUERY, /// Private query message. 76 EMOTE, /// CTCP **ACTION**; `/me slaps Foo with a large trout`. 77 SELFQUERY, /// A message from you in a query (CAP `znc.in/self-message`). 78 SELFCHAN, /// A message from you in a channel (CAP `znc.in/self-message`). 79 SELFEMOTE, /// A CTCP ACTION from you. (Twitch etc) 80 AWAY, /// Someone flagged themselves as away (from keyboard). 81 BACK, /// Someone returned from `AWAY`. 82 JOIN, /// Someone joined a channel. 83 PART, /// Someone left a channel. 84 QUIT, /// Someone quit the server. 85 KICK, /// Someone was kicked from a channel. 86 INVITE, /// You were invited to a channel. 87 NOTICE, /// A server `NOTICE` event. 88 PING, /// The server periodically `PING`ed you. 89 PONG, /// The server actually `PONG`ed you. 90 NICK, /// Someone changed nickname. 91 MODE, /// Someone changed the modes of a channel. 92 SELFQUIT, /// You quit the server. 93 SELFJOIN, /// You joined a channel. 94 SELFPART, /// You left a channel. 95 SELFMODE, /// You changed your modes. 96 SELFNICK, /// You changed your nickname. 97 SELFKICK, /// You were kicked. 98 TOPIC, /// Someone changed channel topic. 99 CAP, /// CAPability exchange during connect. 100 CTCP_VERSION,/// Something requested your version info. 101 CTCP_TIME, /// Something requested your time. 102 CTCP_PING, /// Something pinged you. 103 CTCP_CLIENTINFO,/// Something asked what CTCP events the client can handle. 104 CTCP_DCC, /// Something requested a DCC connection (chat, file transfer). 105 CTCP_SOURCE,/// Something requested an URL to the client source code. 106 CTCP_USERINFO,/// Something requested the nickname and user of the client. 107 CTCP_FINGER,/// Someone requested miscellaneous info about the client. 108 CTCP_LAG, /// Something requested LAG info? 109 CTCP_AVATAR,/// Someone requested an avatar image. 110 CTCP_SLOTS, /// Someone broadcast their file transfer slots. 111 ACCOUNT, /// Someone logged in on nickname services. 112 WALLOPS, /// "WALLOPS messages are for broadcasting network information and its status to following users." 113 SASL_AUTHENTICATE,/// SASL authentication negotiation. 114 AUTH_CHALLENGE, /// Authentication challenge. 115 AUTH_FAILURE, /// Authentication failure. 116 AUTH_SUCCESS, /// Authentication success. 117 CHGHOST, /// User "changes host", which is a thing on some networks. 118 CHANNELFORBIDDEN, // = 926, // <nickname> <channel> :Channel <channel> is forbidden: This channel is closed by request of the channel operators. 119 BOTSNOTWELCOME, // = 931, // <nickname> :Malicious bot, spammers, and other automated systems of dubious origins are NOT welcome here. 120 ENDOFSPAMFILTERLIST,// = 940, // <nickname> <channel> :End of channel spamfilter list 121 SPAMFILTERLIST, // = 941, 122 NICKUNLOCKED, // = 945, 123 NICKNOTLOCKED, // = 946, 124 ENDOFEXEMPTOPSLIST,// = 953 // End of exempt channel ops list. 125 MODELIST, // = 961 /// +noctcp +nickflood 5:60 +nonotice +flood 30:5 +joinflood 5:1 +noextmsg +topiclock +globalflood 10:5 126 ENDOFMODELIST, // = 960 // End of mode list. 127 ENDOFCHANNELACCLIST, // = 911 // End of Channel Access List 128 THISSERVERINSTEAD,// = 010 // <nickname> <new server> +<port> :Please use this Server/Port instead$ 129 130 // Twitch specifics 131 USERSTATE, /// Twitch user information. 132 ROOMSTATE, /// Twitch channel information. 133 GLOBALUSERSTATE, /// Twitch information about self upon login. 134 CLEARCHAT, /// Twitch `CLEARCHAT` event, clearing the chat or banning a user. 135 CLEARMSG, /// Twitch `CLEARMSG` event, deletes a sent message. 136 USERNOTICE, /// Twitch subscription or resubscription event. 137 RECONNECT, /// Twitch `RECONNECT` event; Twitch IRC processes restarting. 138 WHISPER, /// Twitch private query message. 139 TWITCH_NOTICE, /// Twitch generic server notice, see `event.aux`. 140 TWITCH_ERROR, /// Twitch generic error, see `event.aux`. 141 TWITCH_TIMEOUT, /// Twitch temporary ban (seconds in `count`). 142 TWITCH_BAN, /// Twitch permanent ban. 143 TWITCH_SUB, /// Twitch subscription event, including resubs. 144 TWITCH_CHEER, /// Twitch "bits" donation. 145 TWITCH_SUBGIFT, /// Twitch subscription gift event. 146 TWITCH_BITSBADGETIER, /// Twitch event, unsure of its meaning. 147 TWITCH_RAID, /// Twitch raid. 148 TWITCH_UNRAID, /// End of a Twitch raid. 149 TWITCH_RITUAL, /// Twitch Ritual event. 150 TWITCH_REWARDGIFT,/// Twitch "reward gift". 151 TWITCH_GIFTCHAIN, /// Twitch "continuing the gift sub" 152 TWITCH_SUBUPGRADE,/// Twitch, someone paying to upgrade their subscription. 153 TWITCH_CHARITY, /// Twitch charity donation. 154 TWITCH_BULKGIFT, /// Twitch no-target multiple gift event. 155 TWITCH_EXTENDSUB, /// Twitch sub extension. 156 TWITCH_GIFTRECEIVED , /// Twitch Prime community gift received. 157 TWITCH_PAYFORWARD,/// Twitch paying forward of gifts. 158 TWITCH_CROWDCHANT,/// Twitch message with some emotes. 159 TWITCH_ANNOUNCEMENT, /// Twitch channel announcement. 160 TWITCH_DIRECTCHEER, /// Twitch direct cheer with real currency. 161 TWITCH_INTRO, /// Twitch, someone introducing themselves in a channel. 162 163 RPL_WELCOME, // = 001, // ":Welcome to <server name> <user>" 164 RPL_YOURHOST, // = 002, // ":Your host is <servername>, running version <version>" 165 RPL_CREATED, // = 003, // ":This server was created <date>" 166 RPL_MYINFO, // = 004, // "<server_name> <version> <user_modes> <chan_modes>" 167 RPL_BOUNCE, // = 005, // CONFLICT ":Try server <server_name>, port <port_number>" 168 RPL_ISUPPORT, // = 005, // (server information, different syntax) 169 RPL_MAP, // = 006, 170 RPL_MAPEND, // = 007, 171 RPL_SNOMASK, // = 008, // Server notice mask (hex) 172 RPL_STATMEMTOT, // = 009, 173 //RPL_BOUNCE, // = 010, // CONFLICT "<hostname> <port> :<info>", 174 //RPL_STATMEM, // = 010, // deprecated, prefer THISSERVERINSTEAD 175 RPL_YOURCOOKIE, // = 014, 176 //RPL_MAP, // = 015, 177 RPL_MAPMORE, // = 016, 178 //RPL_MAPEND, // = 017, 179 RPL_HELLO, // = 020, 180 RPL_APASSWARN_SET, // = 030, 181 RPL_APASSWARN_SECRET, // = 031, 182 RPL_APASSWARN_CLEAR, // = 032, 183 RPL_YOURID, // = 042, // <nickname> <id> :your unique ID 184 RPL_SAVENICK, // = 043, // Sent to the client when their nickname was forced to change due to a collision 185 RPL_ATTEMPTINGJUNC, // = 050, 186 RPL_ATTEMPTINGREROUTE, // = 051, 187 188 RPL_REMOTEISUPPORT, // 105, 189 190 RPL_TRACELINK, // = 200, // "Link <version & debug level> <destination> <next server>" 191 RPL_TRACECONNECTING, // = 201, // "Try. <class> <server>" 192 RPL_TRACEHANDSHAKE, // = 202, // "H.S. <class> <server>" 193 RPL_TRACEUNKNOWN, // = 203, // "???? <class> [<client IP address in dot form>]" 194 RPL_TRACEOPERATOR, // = 204, // "Oper <class> <nick>" 195 RPL_TRACEUSER, // = 205, // "User <class> <nick>" 196 RPL_TRACESERVER, // = 206, // "Serv <class> <int>S <int>C <server> <nick!user|*!*>@<host|server>" 197 RPL_TRACESERVICE, // = 207, // "Service <class> <name> <type> <active_type> 198 RPL_TRACENEWTYPE, // = 208, // "<newtype> 0 <client name>" 199 RPL_TRACECLASS, // = 209, // "Class <class> <count>" 200 RPL_TRACERECONNECT, // = 210, // CONFLICT 201 RPL_STATSHELP, // = 210, // CONFLICT 202 RPL_STATS, // = 210, // Used instead of having multiple stats numerics 203 RPL_STATSLINKINFO, // = 211, // "<linkname> <sendq> <sent messages> <sent bytes> <received messages> <received bytes> <time open>" 204 RPL_STATSCOMMAND, // = 212, // "<command> <count>" 205 RPL_STATSCLINE, // = 213, // "C <host> * <name> <port> <class>" 206 RPL_STATSNLINE, // = 214, // "N <host> * <name> <port> <class>" 207 RPL_STATSILINE, // = 215, // "I <host> * <host> <port> <class>" 208 RPL_STATSKLINE, // = 216, // "K <host> * <username> <port> <class>" 209 RPL_STATSPLINE, // = 217, // CONFLICT 210 RPL_STATSQLINE, // = 217, 211 RPL_STATSYLINE, // = 218 // "Y <class> <ping frequency> <connect frequency> <max sendq>" 212 RPL_ENDOFSTATS, // = 219, // "<stats letter> :End of /STATS report" 213 RPL_STATSBLINE, // = 220, // CONFLICT 214 RPL_STATSWLINE, // = 220, // CONFLICT 215 //RPL_STATSPLINE, // = 220, 216 RPL_UMODEIS, // = 221, // "<user mode string>" 217 //RPL_STATSBLINE, // = 222, // CONFLICT 218 RPL_SQLINE_NICK, // = 222, // CONFLICT 219 RPL_CODEPAGE, // = 222, // CONFLICT 220 RPL_STATSJLINE, // = 222, // CONFLICT 221 RPL_MODLIST, // = 222, 222 RPL_STATSGLINE, // = 223, // CONFLICT 223 RPL_CHARSET, // = 223, // CONFLICT 224 RPL_STATSELINE, // = 223, 225 RPL_STATSTLINE, // = 224, // CONFLICT 226 RPL_STATSFLINE, // = 224, 227 //RPL_STATSELINE, // = 225, // CONFLICT 228 RPL_STATSZLINE, // = 225, // CONFLICT 229 RPL_STATSCLONE, // = 225, // CONFLICT 230 RPL_STATSDLINE, // = 225, 231 //RPL_STATSNLINE, // = 226, // CONFLICT 232 RPL_STATSALINE, // = 226, // CONFLICT 233 RPL_STATSCOUNT, // = 226, 234 //RPL_STATSGLINE, // = 227, // CONFLICT 235 RPL_STATSVLINE, // = 227, // CONFLICT 236 //RPL_STATSBLINE, // = 227, 237 RPL_STATSBANVER, // = 228, // CONFLICT 238 //RPL_STATSQLINE, // = 228, 239 RPL_STATSSPAMF, // = 229, 240 RPL_STATSEXCEPTTKL, // = 230, 241 RPL_SERVICEINFO, // = 231, // (reserved numeric) 242 RPL_RULES, // = 232, // CONFLICT 243 RPL_ENDOFSERVICES, // = 232, // (reserved numeric) 244 RPL_SERVICE, // = 233, // (reserved numeric) 245 RPL_SERVLIST, // = 234, // (reserved numeric) 246 RPL_SERVLISTEND, // = 235, // (reserved numeric) 247 RPL_STATSVERBOSE, // = 236, // Verbose server list? 248 RPL_STATSENGINE, // = 237, // Engine name? 249 //RPL_STATSFLINE, // = 238, // Feature lines? 250 RPL_STATSIAUTH, // = 239, 251 RPL_STATSXLINE, // = 240, // CONFLICT 252 //RPL_STATSVLINE, // = 240, 253 RPL_STATSLLINE, // = 241, // "L <hostmask> * <servername> <maxdepth>" 254 RPL_STATSUPTIME, // = 242, // ":Server Up %d days %d:%02d:%02d" 255 RPL_STATSOLINE, // = 243, // "O <hostmask> * <name>" 256 RPL_STATSHLINE, // = 244, // "H <hostmask> * <servername>" 257 //RPL_STATSTLINE, // = 245, // CONFLICT 258 RPL_STATSSLINE, // = 245, 259 RPL_STATSSERVICE, // = 246, // CONFLICT 260 //RPL_STATSTLINE, // = 246, // CONFLICT 261 RPL_STATSULINE, // = 246, // CONFLICT 262 RPL_STATSPING, // = 246, 263 //RPL_STATSXLINE, // = 247, // CONFLICT 264 //RPL_STATSGLINE, // = 247, // CONFLICT 265 //RPL_STATSBLINE, // = 247, 266 RPL_STATSDEFINE, // = 248, // CONFLICT 267 //RPL_STATSULINE, // = 248, 268 RPL_STATSDEBUG, // = 249, // CONFLICT 269 //RPL_STATSULINE, // = 249, 270 //RPL_STATSDLINE, // = 250, // CONFLICT 271 RPL_STATSCONN, // = 250, 272 RPL_LUSERCLIENT, // = 251, // ":There are <integer> users and <integer> invisible on <integer> servers" 273 RPL_LUSEROP, // = 252, // "<integer> :operator(s) online" 274 RPL_LUSERUNKNOWN, // = 253, // "<integer> :unknown connection(s)" 275 RPL_LUSERCHANNELS, // = 254, // "<integer> :channels formed" 276 RPL_LUSERME, // = 255, // ":I have <integer> clients and <integer> servers" 277 RPL_ADMINME, // = 256, // "<server> :Administrative info" 278 RPL_ADMINLOC1, // = 257, // ":<admin info>" 279 RPL_ADMINLOC2, // = 258, // ":<admin info>" 280 RPL_ADMINEMAIL, // = 259, // ":<admin info>" 281 RPL_TRACELOG, // = 261, // "File <logfile> <debug level>" 282 RPL_TRACEPING, // = 262, // CONFLICT 283 RPL_TRACEEND, // = 262, // "<server_name> <version>[.<debug_level>] :<info>" 284 RPL_TRYAGAIN, // = 263, // "<command> :<info>" 285 RPL_USINGSSL, // = 264, 286 RPL_LOCALUSERS, // = 265, // Also known as RPL_CURRENT_LOCAL 287 RPL_GLOBALUSERS, // = 266, // Also known as RPL_CURRENT_GLOBAL 288 RPL_START_NETSTAT, // = 267, 289 RPL_NETSTAT, // = 268, 290 RPL_END_NETSTAT, // = 269, 291 RPL_MAPUSERS, // = 270, // CONFLICT 292 RPL_PRIVS, // = 270, 293 RPL_SILELIST, // = 271, 294 RPL_ENDOFSILELIST, // = 272, 295 RPL_NOTIFY, // = 273, 296 RPL_STATSDELTA, // = 274, // CONFLICT 297 RPL_ENDNOTIFY, // = 274, 298 //RPL_USINGSSL, // = 275, // CONFLICT 299 //RPL_STATSDLINE, // = 275, 300 RPL_VCHANEXIST, // = 276, // CONFLICT 301 RPL_WHOISCERTFP, // = 276, // CONFLICT 302 RPL_STATSRLINE, // = 276, 303 RPL_VCHANLIST, // = 277, 304 RPL_VCHANHELP, // = 278, 305 RPL_GLIST, // = 280 306 RPL_ENDOFGLIST, // = 281, // CONFLICT 307 RPL_ACCEPTLIST, // = 281, 308 RPL_JUPELIST, // = 282, // CONFLICT 309 RPL_ENDOFACCEPT, // = 282, 310 RPL_ENDOFJUPELIST, // = 283, // CONFLICT 311 RPL_ALIST, // = 283, 312 RPL_FEATURE, // = 284, // CONFLICT 313 RPL_ENDOFALIST, // = 284, 314 RPL_CHANINFO_HANDLE, // = 285, // CONFLICT 315 RPL_NEWHOSTIS, // = 285, // CONFLICT 316 RPL_GLIST_HASH, // = 285, 317 RPL_CHKHEAD, // = 286, // CONFLICT 318 RPL_CHANINFO_USERS, // = 286, 319 RPL_CHANUSER, // = 287 // CONFLICT 320 RPL_CHANINFO_CHOPS, // = 287, 321 RPL_PATCHHEAD, // = 288, // CONFLICT 322 RPL_CHANINFO_VOICES, // = 288, 323 RPL_PATCHCON, // = 289, // CONFLICT 324 RPL_CHANINFO_AWAY, // = 289, 325 RPL_CHANINFO_HELPHDR, // = 290, // CONFLICT 326 RPL_DATASTR, // = 290, // CONFLICT 327 RPL_HELPHDR, // = 290, // CONFLICT 328 RPL_CHANINFO_OPERS, // = 290, 329 RPL_ENDOFCHECK, // = 291, // CONFLICT 330 RPL_HELPOP, // = 291, // CONFLICT 331 RPL_CHANINFO_BANNED, // = 291, 332 ERR_SEARCHNOMATCH, // = 292 , // CONFLICT 333 RPL_HELPTLR, // = 292, // CONFLICT 334 RPL_CHANINFO_BANS, // = 292, 335 RPL_HELPHLP, // = 293, // CONFLICT 336 RPL_CHANINFO_INVITE, // = 293, 337 RPL_HELPFWD, // = 294, // CONFLICT 338 RPL_CHANINFO_INVITES, // = 294, 339 RPL_HELPIGN, // = 295, // CONFLICT 340 RPL_CHANINFO_KICK, // = 295, 341 RPL_CHANINFO_KICKS, // = 296, 342 RPL_END_CHANINFO, // = 299, 343 344 RPL_NONE, // = 300, // Dummy reply number. Not used. 345 RPL_AWAY, // = 301 // "<nick> :<away message>" 346 RPL_USERHOST, // = 302 // ":[<reply>{<space><reply>}]" 347 RPL_ISON, // = 303, // ":[<nick> {<space><nick>}]" 348 RPL_SYNTAX, // = 304, // CONFLICT 349 RPL_TEXT, // = 304, 350 RPL_UNAWAY, // = 305, // ":You are no longer marked as being away" 351 RPL_NOWAWAY, // = 306, // ":You have been marked as being away" 352 RPL_SUSERHOST, // = 307, // CONFLICT 353 RPL_USERIP, // = 307, // CONFLICT 354 RPL_WHOISREGNICK, // = 307 // <nickname> :has identified for this nick 355 RPL_WHOISADMIN, // = 308, // CONFLICT 356 RPL_RULESSTART, // = 308, // CONFLICT 357 RPL_NOTIFYACTION, // = 308, 358 RPL_WHOISHELPER, // = 309, // CONFLICT 359 RPL_ENDOFRULES, // = 309, // CONFLICT 360 //RPL_WHOISADMIN, // = 309, // CONFLICT 361 RPL_NICKTRACE, // = 309, 362 RPL_WHOISSERVICE, // = 310, // CONFLICT 363 RPL_WHOISHELPOP, // = 310, // CONFLICT 364 RPL_WHOISSVCMSG, // = 310, 365 RPL_WHOISUSER, // = 311, // "<nick> <user> <host> * :<real name>" 366 RPL_WHOISSERVER, // = 312, // "<nick> <server> :<server info>" 367 RPL_WHOISOPERATOR, // = 313, // "<nick> :is an IRC operator" 368 RPL_WHOWASUSER, // = 314, // "<nick> <user> <host> * :<real name>" 369 RPL_ENDOFWHO, // = 315, // "<name> :End of /WHO list" 370 RPL_WHOISPRIVDEAF, // = 316 // CONFLICT 371 RPL_WHOISCHANOP, // = 316, // (reserved numeric) 372 RPL_WHOISIDLE, // = 317, // "<nick> <integer> :seconds idle" 373 RPL_ENDOFWHOIS, // = 318, // "<nick> :End of /WHOIS list" 374 RPL_WHOISCHANNELS, // = 319, // "<nick> :{[@|+]<channel><space>}" 375 RPL_WHOISVIRT, // = 320, // CONFLICT 376 RPL_WHOIS_HIDDEN, // = 320, // CONFLICT 377 RPL_WHOISSPECIAL, // = 320, 378 RPL_LISTSTART, // = 321, // "Channel :Users Name" 379 RPL_LIST, // = 322, // "<channel> <# visible> :<topic>" 380 RPL_LISTEND, // = 323, // ":End of /LIST" 381 RPL_CHANNELMODEIS, // = 324, // "<channel> <mode> <mode params>" 382 RPL_WHOISWEBIRC, // = 325, // CONFLICT 383 RPL_CHANNELMLOCKIS, // = 325, // CONFLICT 384 RPL_UNIQOPIS, // = 325, // CONFLICT 385 RPL_CHANNELPASSIS, // = 325, 386 RPL_NOCHANPASS, // = 326, 387 //RPL_WHOISHOST, // = 327, // CONFLICT 388 RPL_CHPASSUNKNOWN, // = 327, 389 RPL_CHANNEL_URL, // = 328 // "http://linux.chat" 390 RPL_CREATIONTIME, // = 329, 391 RPL_WHOWAS_TIME, // = 330, // CONFLICT 392 RPL_WHOISACCOUNT, // = 330 // "<nickname> <account> :is logged in as" 393 RPL_NOTOPIC, // = 331, // "<channel> :No topic is set" 394 RPL_TOPIC, // = 332, // "<channel> :<topic>" 395 RPL_TOPICWHOTIME, // = 333, // "#channel user!~ident@address 1476294377" 396 RPL_COMMANDSYNTAX, // = 334, // CONFLICT 397 RPL_LISTSYNTAX, // = 334, // CONFLICT 398 RPL_LISTUSAGE, // = 334, 399 RPL_WHOISTEXT, // = 335, // CONFLICT 400 RPL_WHOISACCOUNTONLY, // = 335, // CONFLICT 401 RPL_WHOISBOT, // = 335, // "<nick> <othernick> :is a Bot on <server>" 402 //RPL_WHOISBOT, // = 336, // CONFLICT 403 RPL_INVITELIST, // = 336, 404 //RPL_WHOISTEXT, // = 337, // CONFLICT 405 RPL_ENDOFINVITELIST, // = 337, // CONFLICT 406 RPL_CHANPASSOK, // = 338, // CONFLICT 407 RPL_WHOISACTUALLY, // = 338, 408 RPL_WHOISMARKS, // = 339, // CONFLICT 409 RPL_BADCHANPASS, // = 339, 410 //RPL_USERIP, // = 340, 411 RPL_INVITING, // = 341, // "<channel> <nick>" 412 RPL_SUMMONING, // = 342, // "<user> :Summoning user to IRC" 413 RPL_WHOISKILL, // = 343, 414 RPL_REOPLIST, // = 344, // "<channel> <mask>" 415 RPL_ENDOFREOPLIST, // = 345, // CONFLICT 416 RPL_INVITED, // = 345, 417 //RPL_INVITELIST, // = 346, 418 //RPL_ENDOFINVITELIST, // = 347, 419 RPL_EXCEPTLIST, // = 348, 420 RPL_ENDOFEXCEPTLIST, // = 349, 421 RPL_VERSION, // = 351, // "<version>.<debuglevel> <server> :<comments>" 422 RPL_WHOREPLY, // = 352, // "<channel> <user> <host> <server> <nick> | <H|G>[*][@|+] :<hopcount> <real name>" 423 RPL_NAMREPLY, // = 353, // "<channel> :[[@|+]<nick> [[@|+]<nick> [...]]]" 424 RPL_WHOSPCRPL, // = 354, 425 RPL_NAMREPLY_, // = 355, 426 //RPL_MAP, // = 357, 427 //RPL_MAPMORE, // = 358, 428 //RPL_MAPEND, // = 359, 429 RPL_WHOWASREAL, // = 360, 430 RPL_KILLDONE, // = 361, // (reserved numeric) 431 RPL_CLOSING, // = 362, // (reserved numeric) 432 RPL_CLOSEEND, // = 363, // (reserved numeric) 433 RPL_LINKS, // = 364, // "<mask> <server> :<hopcount> <server info>" 434 RPL_ENDOFLINKS, // = 365, // "<mask> :End of /LINKS list" 435 RPL_ENDOFNAMES, // = 366, // "<channel> :End of /NAMES list" 436 RPL_BANLIST, // = 367, // "<channel> <banid>" 437 RPL_ENDOFBANLIST, // = 368, // "<channel> :End of channel ban list" 438 RPL_ENDOFWHOWAS, // = 369, // "<nick> :End of WHOWAS" 439 RPL_INFO, // = 371, // ":<string>" 440 RPL_MOTD, // = 372, // ":- <text>" 441 RPL_INFOSTART, // = 373, // (reserved numeric) 442 RPL_ENDOFINFO, // = 374, // ":End of /INFO list" 443 RPL_MOTDSTART, // = 375, // ":- <server> Message of the day - " 444 RPL_ENDOFMOTD, // = 376, // ":End of /MOTD command" 445 RPL_SPAM, // = 377, // CONFLICT 446 RPL_KICKEXPIRED, // = 377, 447 RPL_BANEXPIRED, // = 378, // CONFLICT 448 //RPL_MOTD, // = 378, // CONFLICT 449 RPL_WHOISHOST, // = 378 // <nickname> :is connecting from *@<address> <ip> 450 RPL_KICKLINKED, // = 379, // CONFLICT 451 RPL_WHOWASIP, // = 379, // CONFLICT 452 RPL_WHOISMODES, // = 379, // <nickname> :is using modes <modes> 453 RPL_YOURHELPER, // = 380, // CONFLICT 454 RPL_BANLINKED, // = 380, 455 RPL_YOUREOPER, // = 381, // ":You are now an IRC operator" 456 RPL_REHASHING, // = 382, // "<config file> :Rehashing" 457 RPL_YOURESERVICE, // = 383, 458 RPL_MYPORTIS, // = 384, 459 RPL_NOTOPERANYMORE, // = 385, 460 RPL_IRCOPS, // = 386, // CONFLICT 461 RPL_IRCOPSHEADER, // = 386, // CONFLICT 462 RPL_RSACHALLENGE, // = 386, // CONFLICT 463 RPL_QLIST, // = 386, 464 RPL_ENDOFIRCOPS, // = 387, // CONFLICT 465 //RPL_IRCOPS, // = 387, // CONFLICT 466 RPL_ENDOFQLIST, // = 387, 467 //RPL_ENDOFIRCOPS, // = 388, // CONFLICT 468 //RPL_ALIST, // = 388, 469 //RPL_ENDOFALIST, // = 389, 470 RPL_TIME, // = 391, // "<server> :<string showing server's local time>" 471 RPL_USERSTART, // = 392, // ":UserID Terminal Host" 472 RPL_USERS, // = 393, // ":%-8s %-9s %-8s" 473 RPL_ENDOFUSERS, // = 394, // ":End of users" 474 RPL_NOUSERS, // = 395, // ":Nobody logged in" 475 RPL_VISIBLEHOST, // = 396, // CONFLICT 476 RPL_HOSTHIDDEN, // = 396, // <nickname> <host> :is now your hidden host 477 478 ERR_UNKNOWNERROR, // = 400, 479 ERR_NOSUCHNICK, // = 401, // "<nickname> :No such nick/channel" 480 ERR_NOSUCHSERVER, // = 402, // "<server name> :No such server" 481 ERR_NOSUCHCHANNEL, // = 403, // "<channel name> :No such channel" 482 ERR_CANNOTSENDTOCHAN, // = 404, // "<channel name> :Cannot send to channel" 483 ERR_TOOMANYCHANNELS, // = 405, // "<channel name> :You have joined too many channels" 484 ERR_WASNOSUCHNICK, // = 406, // "<nickname> :There was no such nickname" 485 ERR_TOOMANYTARGETS, // = 407, // "<target> :Duplicate recipients. No message delivered"" 486 ERR_NOCTRLSONCHAN, // = 408, // CONFLICT 487 ERR_NOCOLORSONCHAN, // = 408, // CONFLICT 488 ERR_NOSUCHSERVICE, // = 408, 489 ERR_NOORIGIN, // = 409, // ":No origin specified" 490 ERR_INVALIDCAPCMD, // = 410, 491 ERR_NORECIPIENT, // = 411, // ":No recipient given (<command>)" 492 ERR_NOTEXTTOSEND, // = 412, // ":No text to send" 493 ERR_NOTOPLEVEL, // = 413, // "<mask> :No toplevel domain specified" 494 ERR_WILDTOPLEVEL, // = 414, // "<mask> :Wildcard in toplevel domain" 495 ERR_BADMASK, // = 415, 496 ERR_QUERYTOOLONG, // = 416, // CONFLICT 497 ERR_TOOMANYMATCHES, // = 416, 498 ERR_INPUTTOOLONG, // = 417, 499 ERR_LENGTHTRUNCATED, // = 419, 500 ERR_UNKNOWNCOMMAND, // = 421, // "<command> :Unknown command" 501 ERR_NOMOTD, // = 422, // ":MOTD File is missing" 502 ERR_NOADMININFO, // = 423, // "<server> :No administrative info available" 503 ERR_FILEERROR, // = 424, // ":File error doing <file op> on <file>" 504 ERR_NOOPERMOTD, // = 425, 505 ERR_TOOMANYAWAY, // = 429, 506 ERR_EVENTNICKCHANGE, // = 430, 507 ERR_NONICKNAMEGIVEN, // = 431, // ":No nickname given" 508 ERR_ERRONEOUSNICKNAME, // = 432,// "<nick> :Erroneus nickname" 509 ERR_NICKNAMEINUSE, // = 433, // "<nick> :Nickname is already in use" 510 ERR_SERVICENAMEINUSE, // = 434, //CONFLICT 511 ERR_NORULES, // = 434, 512 ERR_SERVICECONFUSED, // = 435 // CONFLICT 513 ERR_BANONCHAN, // = 435 // <nickname> <target nickname> <channel> :Cannot change nickname while banned on channel 514 ERR_NICKCOLLISION, // = 436, // "<nick> :Nickname collision KILL" 515 ERR_BANNICKCHANGE, // = 437, // CONFLICT 516 ERR_UNAVAILRESOURCE, // = 437, // <nickname> <channel> :Nick/channel is temporarily unavailable 517 ERR_DEAD, // = 438, // CONFLICT 518 ERR_NICKTOOFAST, // = 438, 519 ERR_TARGETTOOFAST, // = 439, // <nickname> :This server has anti-spambot mechanisms enabled. 520 ERR_SERVICESDOWN, // = 440, 521 ERR_USERNOTINCHANNEL, // = 441, // "<nick> <channel> :They aren't on that channel" 522 ERR_NOTONCHANNEL, // = 442, // "<channel> :You're not on that channel" 523 ERR_USERONCHANNEL, // = 443, // "<user> <channel> :is already on channel" 524 ERR_NOLOGIN, // = 444, // "<user> :User not logged in" 525 ERR_SUMMONDISABLED, // = 445, // ":SUMMON has been disabled" 526 ERR_USERSDISABLED, // = 446, // ":USERS has been disabled" 527 ERR_NONICKCHANGE, // = 447, 528 ERR_FORBIDDENCHANNEL, // = 448, 529 ERR_NOTIMPLEMENTED, // = 449, 530 ERR_NOTREGISTERED, // = 451, // ":You have not registered" 531 ERR_IDCOLLISION, // = 452, 532 ERR_NICKLOST, // = 453, 533 //ERR_IDCOLLISION, // = 455 // <nickname> :Your username <nickname> contained the invalid character(s) <characters> and has been changed to mrkaufma. Please use only the characters 0-9 a-z A-Z _ - or . in your username. Your username is the part before the @ in your email address. 534 ERR_HOSTILENAME, // = 455, 535 ERR_ACCEPTFULL, // = 456 536 ERR_ACCEPTEXIST, // = 457, 537 ERR_ACCEPTNOT, // = 458, 538 ERR_NOHIDING, // = 459, 539 ERR_NOTFORHALFOPS, // = 460, 540 ERR_NEEDMOREPARAMS, // = 461, // "<command> :Not enough parameters" 541 ERR_ALREADYREGISTERED, // = 462,// ":You may not reregister" 542 ERR_NOPERMFORHOST, // = 463, // ":Your host isn't among the privileged" 543 ERR_PASSWDMISMATCH, // = 464, // ":Password incorrect" 544 ERR_YOUREBANNEDCREEP, // = 465, // ":You are banned from this server" 545 ERR_YOUWILLBEBANNED, // = 466 // (reserved numeric) 546 ERR_KEYSET, // = 467, // "<channel> :Channel key already set" 547 ERR_NOCODEPAGE, // = 468, // CONFLICT 548 ERR_ONLYSERVERSCANCHANGE, // = 468,// CONFLICT 549 ERR_INVALIDUSERNAME, // = 468, 550 ERR_LINKSET, // = 469, 551 ERR_7BIT, // = 470, // CONFLICT 552 ERR_KICKEDFROMCHAN, // = 470, // CONFLICT 553 ERR_LINKCHANNEL, // = 470 // <#original> <#new> :Forwarding to another channel 554 ERR_CHANNELISFULL, // = 471, // "<channel> :Cannot join channel (+l)" 555 ERR_UNKNOWNMODE, // = 472, // "<char> :is unknown mode char to me" 556 ERR_INVITEONLYCHAN, // = 473, // "<channel> :Cannot join channel (+i)" 557 ERR_BANNEDFROMCHAN, // = 474, // "<channel> :Cannot join channel (+b)" 558 ERR_BADCHANNELKEY, // = 475, // "<channel> :Cannot join channel (+k)" 559 ERR_BADCHANMASK, // = 476, // (reserved numeric) 560 ERR_NOCHANMODES, // = 477 // CONFLICT 561 ERR_NEEDREGGEDNICK, // = 477 // <nickname> <channel> :Cannot join channel (+r) - you need to be identified with services 562 ERR_BANLISTFULL, // = 478, 563 ERR_NOCOLOR, // = 479, // CONFLICT 564 ERR_BADCHANNAME, // = 479, 565 ERR_LINKFAIL, // = 479, // CONFLICT 566 ERR_THROTTLE, // = 480, // CONFLICT 567 ERR_NOWALLOP, // = 480, // CONFLICT 568 ERR_SSLONLYCHAN, // = 480, // CONFLICT 569 ERR_NOULINE, // = 480, // CONFLICT 570 ERR_CANNOTKNOCK, // = 480, 571 ERR_NOPRIVILEGES, // = 481, // ":Permission Denied- You're not an IRC operator" 572 ERR_CHANOPRIVSNEEDED, // = 482, // [sic] "<channel> :You're not channel operator" 573 ERR_CANTKILLSERVER, // = 483, // ":You cant kill a server!" 574 ERR_ATTACKDENY, // = 484, // CONFLICT 575 ERR_DESYNC, // = 484, // CONFLICT 576 ERR_ISCHANSERVICE, // = 484, // CONFLICT 577 ERR_RESTRICTED, // = 484, 578 ERR_BANNEDNICK, // = 485, // CONFLICT 579 ERR_CHANBANREASON, // = 485, // CONFLICT 580 ERR_KILLDENY, // = 485, // CONFLICT 581 ERR_CANTKICKADMIN, // = 485, // CONFLICT 582 ERR_ISREALSERVICE, // = 485, // CONFLICT 583 ERR_UNIQPRIVSNEEDED, // = 485, 584 ERR_ACCOUNTONLY, // = 486, // CONFLICT 585 ERR_RLINED, // = 486, // CONFLICT 586 ERR_HTMDIABLED, // = 486, // CONFLICT 587 ERR_NONONREG, // = 486, 588 ERR_NONONSSL, // = 487, // CONFLICT 589 ERR_NOTFORUSERS, // = 487, // CONFLICT 590 ERR_CHANTOORECENT, // = 487, // CONFLICT 591 ERR_MSGSERVICES, // = 487 // <nickname> :Error! "/msg NickServ" is no longer supported. Use "/msg NickServ@services.dal.net" or "/NickServ" instead. 592 ERR_HTMDISABLED, // = 488, // CONFLICT 593 ERR_NOSSL, // = 488, // CONFLICT 594 ERR_TSLESSCHAN, // = 488, 595 ERR_VOICENEEDED, // = 489, // CONFLICT 596 ERR_SECUREONLYCHAN, // = 489, 597 ERR_NOSWEAR, // = 490, // CONFLICT 598 ERR_ALLMUSTSSL, // = 490, 599 ERR_NOOPERHOST, // = 491, // ":No O-lines for your host" 600 ERR_CANNOTSENDTOUSER, // = 492, // CONFLICT 601 ERR_NOCTCP, // = 492, // CONFLICT 602 ERR_NOTCP, // = 492, // CONFLICT 603 ERR_NOSERVICEHOST, // = 492, // (reserved numeric) 604 ERR_NOSHAREDCHAN, // = 493 // CONFLICT 605 ERR_NOFEATURE, // = 493, 606 ERR_OWNMODE, // = 494, // CONFLICT 607 ERR_BADFEATVALUE, // = 494, 608 ERR_DELAYREJOIN, // = 495, // CONFLICT 609 ERR_BADLOGTYPE, // = 495, 610 ERR_BADLOGSYS, // = 496, 611 ERR_BADLOGVALUE, // = 497, 612 ERR_ISOPERLCHAN, // = 498, 613 ERR_CHANOWNPRIVNEEDED, // = 499, 614 615 ERR_NOREHASHPARAM, // = 500, // CONFLICT 616 ERR_TOOMANYJOINS, // = 500, 617 ERR_UNKNOWNSNOMASK, // = 501, // CONFLICT 618 ERR_UMODEUNKNOWNFLAG, // = 501, // ":Unknown MODE flag" 619 ERR_USERSDONTMATCH, // = 502, // ":Cant change mode for other users" 620 ERR_VWORLDWARN, // = 503, // CONFLICT 621 ERR_GHOSTEDCLIENT, // = 503, 622 ERR_USERNOTONSERV, // = 504, 623 ERR_SILELISTFULL, // = 511, 624 ERR_NOSUCHGLINE, // = 512, // CONFLICT 625 ERR_TOOMANYWATCH, // = 512, 626 //ERR_BADPING, // 513, // CONFLICT 627 ERR_NEEDPONG, // = 513, // <nickname> :To connect type /QUOTE PONG <number> 628 ERR_NOSUCHJUPE, // = 514, // CONFLICT 629 ERR_TOOMANYDCC, // = 514, // CONFLICT 630 ERR_INVALID_ERROR, // = 514, 631 ERR_BADEXPIRE, // = 515, 632 ERR_DONTCHEAT, // = 516, 633 ERR_DISABLED, // = 517, 634 ERR_NOINVITE, // = 518, // CONFLICT 635 ERR_LONGMASK, // = 518, 636 ERR_ADMONLY, // = 519, // CONFLICT 637 ERR_TOOMANYUSERS, // = 519, 638 ERR_WHOTRUNC, // = 520, // CONFLICT 639 ERR_MASKTOOWIDE, // = 520, // CONFLICT 640 ERR_OPERONLY, // = 520, 641 //ERR_NOSUCHGLINE, // = 521, // CONFLICT 642 ERR_LISTSYNTAX, // = 521, 643 ERR_WHOSYNTAX, // = 522, 644 ERR_WHOLIMEXCEED, // = 523, 645 ERR_OPERSPVERIFY, // = 524, // CONFLICT 646 ERR_QUARANTINED, // = 524, // CONFLICT 647 ERR_HELPNOTFOUND, // = 524, 648 ERR_INVALIDKEY, // = 525, // CONFLICT 649 ERR_REMOTEPFX, // = 525, 650 ERR_PFXUNROUTABLE, // = 526, 651 ERR_CANTSENDTOUSER, // = 531, 652 ERR_BADHOSTMASK, // = 550, 653 ERR_HOSTUNAVAIL, // = 551, 654 ERR_USINGSLINE, // = 552, 655 ERR_STATSSLINE, // = 553, 656 ERR_NOTLOWEROPLEVEL, // = 560, 657 ERR_NOTMANAGER, // = 561, 658 ERR_CHANSECURED, // = 562, 659 ERR_UPASSSET, // = 563, 660 ERR_UPASSNOTSET, // = 564, 661 ERR_NOMANAGER, // = 566, 662 ERR_UPASS_SAME_APASS, // = 567, 663 RPL_NOMOTD, // = 568 // CONFLICT 664 ERR_LASTERROR, // = 568, 665 RPL_REAWAY, // = 597, 666 RPL_GONEAWAY, // = 598, 667 RPL_NOTAWAY, // = 599, 668 669 RPL_LOGON, // = 600, 670 RPL_LOGOFF, // = 601, 671 RPL_WATCHOFF, // = 602, 672 RPL_WATCHSTAT, // = 603, 673 RPL_NOWON, // = 604, 674 RPL_NOWFF, // = 605, 675 RPL_WATCHLIST, // = 606, 676 RPL_ENDOFWATCHLIST, // = 607, 677 RPL_WATCHCLEAR, // = 608, 678 RPL_NOWISAWAY, // = 609, 679 RPL_ISOPER, // = 610 // CONFLICT 680 //RPL_MAPMORE, // = 610, 681 RPL_ISLOCOP, // = 611, 682 RPL_ISNOTOPER, // = 612, 683 RPL_ENDOFISOPER, // = 613, 684 //RPL_MAPMORE, // = 615, // CONFLICT 685 //RPL_WHOISMODES, // = 615, 686 //RPL_WHOISHOST, // = 616, 687 RPL_WHOISSSLFP, // = 617, // CONFLICT 688 //RPL_WHOISBOT, // = 617, // CONFLICT 689 RPL_DCCSTATUS, // = 617, 690 RPL_DCCLIST, // = 618, 691 RPL_WHOWASHOST, // = 619, // CONFLICT 692 RPL_ENDOFDCCLIST, // = 619, 693 //RPL_RULESSTART, // = 620, // CONFLICT 694 RPL_DCCINFO, // = 620, 695 //RPL_RULES, // = 621, 696 //RPL_ENDOFRULES, // = 622, 697 //RPL_MAPMORE, // = 623, 698 RPL_OMOTDSTART, // = 624, 699 RPL_OMOTD, // = 625 700 RPL_ENDOFO, // = 626, 701 RPL_SETTINGS, // = 630, 702 RPL_ENDOFSETTINGS, // = 631, 703 RPL_DUMPING, // = 640, 704 RPL_DUMPRPL, // = 641, 705 RPL_EODUMP, // = 642, 706 RPL_SPAMCMDFWD, // = 659, 707 RPL_TRACEROUTE_HOP, // = 660, 708 RPL_TRACEROUTE_START, // = 661, 709 RPL_MODECHANGEWARN, // = 662, 710 RPL_CHANREDIR, // = 663, 711 RPL_SERVMODEIS, // = 664, 712 RPL_OTHERUMODEIS, // = 665, 713 RPL_ENDOF_GENERIC, // = 666, 714 RPL_WHOWASDETAILS, // = 670, // CONFLICT 715 RPL_STARTTLS, // = 670, 716 RPL_WHOISSECURE, // = 671 // "<nickname> :is using a secure connection" 717 RPL_UNKNOWNMODES, // = 672, // CONFLICT 718 RPL_WHOISREALIP, // 672, 719 RPL_CANNOTSETMODES, // = 673, 720 RPL_WHOISYOURID, // = 674, 721 RPL_LUSERSTAFF, // = 678, 722 RPL_TIMEONSERVERIS, // = 679, 723 RPL_NETWORKS, // = 682, 724 RPL_YOURLANGUAGEIS, // = 687, 725 RPL_LANGUAGE, // = 688, 726 RPL_WHOISSTAFF, // = 689, 727 RPL_WHOISLANGUAGE, // = 690, 728 ERR_STARTTLS, // = 691, 729 730 //RPL_MODLIST, // = 702, // CONFLICT 731 RPL_COMMANDS, // = 702, 732 RPL_ENDOFMODLIST, // = 703, // CONFLICT 733 RPL_COMMANDSEND, // = 703, 734 RPL_HELPSTART, // = 704 // <nickname> index :Help topics available to users: 735 RPL_HELPTXT, // = 705 // <nickname> index :ACCEPT\tADMIN\tAWAY\tCHALLENGE 736 RPL_ENDOFHELP, // = 706 // <nickname> index :End of /HELP. 737 ERR_TARGCHANGE, // = 707, 738 RPL_ETRACEFULL, // = 708, 739 RPL_ETRACE, // = 709, 740 RPL_KNOCK, // = 710, 741 RPL_KNOCKDLVR, // = 711, 742 ERR_TOOMANYKNOCK, // = 712, 743 ERR_CHANOPEN, // = 713, 744 ERR_KNOCKONCHAN, // = 714, 745 ERR_KNOCKDISABLED, // = 715, // CONFLICT 746 ERR_TOOMANYINVITE, // = 715, // CONFLICT 747 RPL_INVITETHROTTLE, // = 715, 748 RPL_TARGUMODEG, // = 716, 749 RPL_TARGNOTIFY, // = 717, 750 RPL_UMODEGMSG, // = 718, 751 //RPL_OMOTDSTART, // = 720 752 //RPL_OMOTD, // = 721, 753 RPL_ENDOFOMOTD, // = 722, 754 ERR_NOPRIVS, // = 723, 755 RPL_TESTMASK, // = 724, 756 RPL_TESTLINE, // = 725, 757 RPL_NOTESTLINE, // = 726, 758 RPL_TESTMASKGECOS, // = 727, 759 RPL_QUIETLIST, // = 728, // also 344 on oftc 760 RPL_ENDOFQUIETLIST, // = 729, 761 RPL_MONONLINE, // = 730, 762 RPL_MONOFFLINE, // = 731, 763 RPL_MONLIST, // = 732, 764 RPL_ENDOFMONLIST, // = 733, 765 ERR_MONLISTFULL, // = 734, 766 RPL_RSACHALLENGE2, // = 740, 767 RPL_ENDOFRSACHALLENGE2, // = 741, 768 ERR_MLOCKRESTRICTED, // = 742, 769 ERR_INVALIDBAN, // = 743, 770 ERR_TOPICLOCK, // = 744, 771 RPL_SCANMATCHED, // = 750, 772 RPL_SCANUMODES, // = 751, 773 RPL_ETRACEEND, // = 759, 774 RPL_WHOISKEYVALUE, // = 760, 775 RPL_KEYVALUE, // = 761, 776 RPL_METADATAEND, // = 762, 777 ERR_METADATALIMIT, // = 764, 778 ERR_TARGETINVALID, // = 765, 779 ERR_NOMATCHINGKEY, // = 766, 780 ERR_KEYINVALID, // = 767, 781 ERR_KEYNOTSET, // = 768, 782 ERR_KEYNOPERMISSION, // = 769, 783 RPL_XINFO, // = 771, 784 RPL_XINFOSTART, // = 773 785 RPL_XINFOEND, // = 774, 786 787 RPL_CHECK, // = 802, 788 789 RPL_LOGGEDIN, // = 900, // <nickname>!<ident>@<address> <nickname> :You are now logged in as <nickname> 790 RPL_LOGGEDOUT, // = 901, 791 ERR_NICKLOCKED, // = 902, 792 RPL_SASLSUCCESS, // = 903, // :cherryh.freenode.net 903 kameloso^ :SASL authentication successful 793 ERR_SASLFAIL, // = 904, // :irc.rizon.no 904 kameloso^^ :SASL authentication failed" 794 ERR_SASLTOOLONG, // = 905, 795 ERR_SASLABORTED, // = 906, // :orwell.freenode.net 906 kameloso^ :SASL authentication aborted 796 ERR_SASLALREADY, // = 907, 797 RPL_SASLMECHS, // = 908, 798 ERR_WORDFILTERED, // = 936, 799 ERR_CANTUNLOADMODULE, // = 972, // CONFLICT 800 ERR_CANNOTDOCOMMAND, // = 972, 801 ERR_CANNOTCHANGEUMODE, // = 973, 802 ERR_CANTLOADMODULE, // = 974, // CONFLICT 803 ERR_CANNOTCHANGECHANMODE, // = 974, 804 ERR_CANNOTCHANGESERVERMODE, // = 975,// CONFLICT 805 //ERR_LASTERROR, // = 975, // CONFLICT 806 RPL_LOADEDMODULE, // = 975, 807 ERR_CANNOTSENDTONICK, // = 976, 808 ERR_UNKNOWNSERVERMODE, // = 977, 809 ERR_SERVERMODELOCK, // = 979, 810 ERR_BADCHARENCODING, // = 980, 811 ERR_TOOMANYLANGUAGES, // = 981, 812 ERR_NOLANGUAGE, // = 982, 813 ERR_TEXTTOOSHORT, // = 983, 814 815 ERR_NUMERIC_ERR, // = 999 816 } 817 818 /* 819 /++ 820 Run this to generate the Type[n] map. 821 822 HAS NOT BEEN TESTED IN YEARS. There's been no need for it. 823 Don't expect it to work. 824 +/ 825 void generateTypenums() 826 { 827 import std.regex; 828 import std.algorithm; 829 import std.stdio; 830 831 enum pattern = r" *([A-Z0-9_]+),? [/= ]* ([0-9]+),?.*"; 832 static engine = ctRegex!pattern; 833 string[1024] arr; 834 835 foreach (const line; s.splitter("\n")) 836 { 837 auto hits = line.matchFirst(engine); 838 if (hits.length < 2) continue; 839 840 try 841 { 842 size_t idx = hits[2].to!size_t; 843 if (arr[idx] != typeof(arr[idx]).init) stderr.writeln("DUPLICATE! ", idx); 844 arr[idx] = hits[1]; 845 } 846 catch (Exception e) 847 { 848 //writeln(e.msg, ": ", line); 849 } 850 } 851 852 writeln("static immutable Type[1024] typenums =\n["); 853 854 foreach (immutable i, const val; arr) 855 { 856 if (!val.length) continue; 857 858 writefln(" %-3d : Type.%s,", i, val); 859 } 860 861 writeln("];"); 862 } 863 */ 864 865 /++ 866 The event type, signifying what *kind* of event this is. 867 +/ 868 Type type; 869 870 /++ 871 The raw IRC string, untouched. 872 +/ 873 @Hidden string raw; 874 875 /++ 876 The name of whoever (or whatever) sent this event. 877 +/ 878 IRCUser sender; 879 880 /++ 881 The channel the event transpired in, or is otherwise related to. 882 +/ 883 string channel; 884 885 /++ 886 The target user of the event. 887 +/ 888 IRCUser target; 889 890 /++ 891 The main body of text of the event. 892 +/ 893 string content; 894 895 /++ 896 Auxiliary string array. 897 +/ 898 string[numAuxStrings] aux; 899 900 /++ 901 IRCv3 message tags attached to this event 902 +/ 903 string tags; 904 905 /++ 906 With a numeric event, the number of the event type. 907 +/ 908 uint num; 909 910 /++ 911 Count array. 912 +/ 913 Nullable!long[numCounts] count; 914 915 /++ 916 A timestamp of when the event transpired. 917 +/ 918 @Hidden long time; 919 920 /++ 921 What errors occurred during parsing, if any. 922 +/ 923 string errors; 924 925 version(TwitchSupport) 926 { 927 /++ 928 The Twitch emotes in the message, if any. 929 +/ 930 string emotes; 931 932 /++ 933 The Twitch ID of this message. 934 +/ 935 string id; 936 } 937 } 938 939 940 // IRCServer 941 /++ 942 Aggregate of all information and state pertaining to the connected IRC 943 server. Some fields are transient on a per-connection basis and should not 944 be serialised. 945 +/ 946 struct IRCServer 947 { 948 /++ 949 Server daemons, or families of server programs. 950 951 Many daemons handle some events slightly differently than others do, and 952 by tracking which daemon the server is running we can apply the 953 differences and always have an appropriate tables of events. 954 +/ 955 enum Daemon 956 { 957 unset, /// Unset or invalid daemon. 958 unknown, /// Reported but unknown daemon. 959 960 unreal, 961 solanum, 962 inspircd, 963 bahamut, 964 ratbox, 965 u2, 966 hybrid, 967 snircd, 968 rizon, 969 undernet, 970 ircdseven, 971 twitch, 972 bsdunix, 973 mfvx, 974 975 charybdis, 976 sorircd, 977 978 ircu, 979 aircd, 980 rfc1459, 981 rfc2812, 982 nefarious, 983 rusnet, 984 austhex, 985 ircnet, 986 ptlink, 987 ultimate, 988 anothernet, 989 bdqircd, 990 chatircd, 991 irch, 992 ithildin, 993 } 994 995 /++ 996 Case mappings used by an IRC server. 997 998 These decide how case-insensitivity works. 999 +/ 1000 enum CaseMapping 1001 { 1002 /// The lowercase of `[A-Z]` is `[a-z]`. 1003 ascii, 1004 /// `ascii`, plus the lowercase of `[]\^` is `{}|~`. 1005 rfc1459, 1006 /// `rfc1459`, except no `^` for `~`. 1007 strict_rfc1459, 1008 } 1009 1010 /++ 1011 Server address (or IP). 1012 +/ 1013 string address; 1014 1015 /++ 1016 The port to connect to, usually `6667`-`6669`. 1017 +/ 1018 ushort port; 1019 1020 @Unserialisable 1021 { 1022 /++ 1023 The server daemon family the server is running. 1024 +/ 1025 Daemon daemon; 1026 1027 /++ 1028 Server network string, like Freenode, QuakeNet, Rizon. 1029 +/ 1030 string network; 1031 1032 /++ 1033 The reported daemon, with version. 1034 +/ 1035 string daemonstring; 1036 1037 /++ 1038 The IRC server address handed to us by the round robin pool. 1039 +/ 1040 string resolvedAddress; 1041 1042 /++ 1043 Max nickname length as per IRC specs, but not the de facto standard. 1044 +/ 1045 uint maxNickLength = 9; 1046 1047 /++ 1048 Max channel name length as per IRC specs, or as reported. 1049 +/ 1050 uint maxChannelLength = 200; 1051 1052 /++ 1053 A = Mode that adds or removes a nick or address to a list. 1054 Always has a parameter. 1055 +/ 1056 string aModes; // = "eIbq"; 1057 1058 /++ 1059 B = Mode that changes a setting and always has a parameter. 1060 +/ 1061 string bModes; // = "k"; 1062 1063 /++ 1064 C = Mode that changes a setting and only has a parameter when set. 1065 +/ 1066 string cModes; // = "flj"; 1067 1068 /++ 1069 D = Mode that changes a setting and never has a parameter. 1070 +/ 1071 string dModes; // = "CFLMPQScgimnprstz"; 1072 1073 /++ 1074 Prefix characters by mode character; `o` by `@`, `v` by `+`, etc. 1075 +/ 1076 char[char] prefixchars; 1077 1078 /++ 1079 Character channel mode prefixes (`o`, `v`, `h`, ...) 1080 +/ 1081 string prefixes; 1082 1083 /++ 1084 Supported channel prefix characters, as announced by the server in 1085 the [dialect.defs.IRCEvent.Type.RPL_ISUPPORT|RPL_ISUPPORT]` event, 1086 before the MOTD. 1087 +/ 1088 string chantypes = "#"; 1089 1090 /++ 1091 The current case mapping, dictating how case-insensitivity works. 1092 +/ 1093 CaseMapping caseMapping; 1094 1095 /++ 1096 `EXTBAN` prefix character. 1097 +/ 1098 char extbanPrefix = '$'; 1099 1100 /++ 1101 `EXTBAN` types. 1102 +/ 1103 string extbanTypes; 1104 1105 /++ 1106 The modechar for mode exceptions. 1107 +/ 1108 char exceptsChar = 'e'; 1109 1110 /++ 1111 The modechar for invite exceptions. 1112 +/ 1113 char invexChar = 'I'; 1114 1115 /++ 1116 Contents of the [IRCEvent.Type.RPL_ISUPPORT|RPL_ISUPPORT] response(s). 1117 +/ 1118 string supports; 1119 } 1120 1121 /++ 1122 Constructor. 1123 +/ 1124 auto this( 1125 const string address, 1126 const ushort port) pure @safe nothrow @nogc 1127 { 1128 this.address = address; 1129 this.port = port; 1130 } 1131 } 1132 1133 1134 // IRCUser 1135 /++ 1136 An aggregate of fields representing a single user on IRC. 1137 1138 Instances of these should not survive a disconnect and reconnect; they are 1139 transient on a per-connection basis and should not be serialised. 1140 +/ 1141 struct IRCUser 1142 { 1143 /++ 1144 The user's nickname. 1145 +/ 1146 string nickname; 1147 1148 version(BotElements) 1149 { 1150 /++ 1151 Classifiers; roles which a user is one of. 1152 +/ 1153 enum Class 1154 { 1155 unset, /// Unknown, yet to be determined. 1156 blacklist, /// A blacklisted user. 1157 anyone, /// Any user. 1158 registered, /// A user registered with services. 1159 whitelist, /// A whitelisted user. 1160 elevated, /// An elevated user, something in between `whitelist` and `operator`. 1161 operator, /// A user enjoying operator (or moderator) privileges. 1162 staff, /// The owner of a channel; an elevated user but not a full administrator. 1163 admin, /// An administrator, in a bot-like context. 1164 } 1165 1166 /++ 1167 User classifier. 1168 +/ 1169 Class class_; 1170 } 1171 1172 /++ 1173 The user's GECOS/"real name". 1174 +/ 1175 string realName; 1176 1177 /++ 1178 The user's IDENT identification. 1179 +/ 1180 string ident; 1181 1182 /++ 1183 The reported user address, which may be a cloak. 1184 +/ 1185 string address; 1186 1187 /++ 1188 Services account name (to `NickServ`, `AuthServ`, `Q`, etc). 1189 +/ 1190 string account; 1191 1192 /++ 1193 Timestamp when the user was last modified. 1194 +/ 1195 @Hidden long updated; 1196 1197 version(TwitchSupport) 1198 { 1199 // Twitch has some extra features. 1200 1201 /++ 1202 The alternate "display name" of the user. 1203 +/ 1204 string displayName; 1205 1206 /++ 1207 The Twitch badges this user has. 1208 +/ 1209 string badges; 1210 1211 /++ 1212 The Twitch colour (RRGGBB) to tint the user's nickname with. 1213 +/ 1214 string colour; 1215 1216 /++ 1217 The Twitch ID of this user's account. 1218 +/ 1219 uint id; 1220 } 1221 1222 /++ 1223 Create a new [IRCUser] based on a `*!*@*` mask string. 1224 +/ 1225 this(string userstring) pure @safe 1226 { 1227 import std.format : formattedRead; 1228 1229 userstring.formattedRead("%s!%s@%s", nickname, ident, address); 1230 if (nickname == "*") nickname = string.init; 1231 if (ident == "*") ident = string.init; 1232 if (address == "*") address = string.init; 1233 } 1234 1235 /// 1236 unittest 1237 { 1238 { 1239 immutable user = IRCUser("nickname!~ident@address"); 1240 assert((user.nickname == "nickname"), user.nickname); 1241 assert((user.ident == "~ident"), user.ident); 1242 assert((user.address == "address"), user.address); 1243 } 1244 { 1245 immutable user = IRCUser("*!~ident@address"); 1246 assert(!user.nickname.length, user.nickname); 1247 assert((user.ident == "~ident"), user.ident); 1248 assert((user.address == "address"), user.address); 1249 } 1250 { 1251 immutable user = IRCUser("*!*@*"); 1252 assert(!user.nickname.length, user.nickname); 1253 assert(!user.ident.length, user.ident); 1254 assert(!user.address.length, user.address); 1255 } 1256 } 1257 1258 /++ 1259 Create a new [IRCUser] inheriting passed `nickname`, `ident`, and 1260 `address` strings. 1261 +/ 1262 auto this( 1263 const string nickname, 1264 const string ident, 1265 const string address) pure @safe nothrow @nogc 1266 { 1267 this.nickname = nickname; 1268 this.ident = ident; 1269 this.address = address; 1270 } 1271 1272 /++ 1273 Makes an educated guess that a sender is a server. 1274 1275 Returns: 1276 `true` if the sender nickname and/or address looks to be a server's, 1277 `false` if not. 1278 +/ 1279 auto isServer() const @property pure @safe nothrow @nogc 1280 { 1281 import std.string : indexOf; 1282 return !nickname.length && (address.indexOf('.') != -1); 1283 } 1284 1285 /// 1286 @safe unittest 1287 { 1288 IRCUser user; 1289 1290 user.address = "blah.freenode.net"; 1291 assert(user.isServer); 1292 1293 user.nickname = "foo"; 1294 assert(!user.isServer); 1295 1296 user.nickname = string.init; 1297 user.address = "nodots"; 1298 assert(!user.isServer); // unsure what to even make of no-dot addresses 1299 1300 // :kameloso MODE kameloso :+i 1301 user.nickname = "kameloso"; 1302 user.address = string.init; 1303 assert(!user.isServer); 1304 } 1305 1306 /++ 1307 Compares two [IRCUser]s with each other, ignoring members considered to 1308 be extra or optional. 1309 1310 Params: 1311 that = Second user to compare this one with. 1312 1313 Returns: 1314 `true` if the users match, `false` if not. 1315 +/ 1316 auto opEquals(const IRCUser that) const pure @safe nothrow @nogc 1317 { 1318 return 1319 (this.nickname == that.nickname) && 1320 (this.ident == that.ident) && 1321 (this.address == that.address); 1322 } 1323 1324 /++ 1325 Produces a hash for this [IRCUser]. 1326 1327 Returns: 1328 A hash. 1329 +/ 1330 auto toHash() const pure @safe 1331 { 1332 return this.hostmask.hashOf; 1333 } 1334 1335 // toString 1336 /++ 1337 Formats this [IRCUser] into a hostmask representing its values. 1338 Stores the result in the passed output range sink. 1339 1340 Params: 1341 sink = Output range sink to save the hostmask string to. 1342 +/ 1343 void toString(Sink)(auto ref Sink sink) const @safe 1344 { 1345 import std.format : formattedWrite; 1346 1347 immutable nickname = this.nickname.length ? this.nickname : "*"; 1348 immutable ident = this.ident.length ? this.ident : "*"; 1349 immutable address = this.address.length ? this.address : "*"; 1350 1351 sink.formattedWrite("%s!%s@%s", nickname, ident, address); 1352 } 1353 1354 // hostmask 1355 /++ 1356 Formats this [IRCUser] into a hostmask representing its values. 1357 Merely wraps [toString] and returns a newly allocated string. 1358 1359 Returns: 1360 A hostmask "*!*@*" string. 1361 +/ 1362 string hostmask() pure @safe const 1363 { 1364 import std.array : Appender; 1365 1366 Appender!(char[]) sink; 1367 sink.reserve(nickname.length + ident.length + address.length + 5); // for ! and @ as well as *** 1368 1369 this.toString(sink); 1370 return sink.data; 1371 } 1372 1373 /// 1374 @safe unittest 1375 { 1376 { 1377 const user = IRCUser("nickname", "ident", "address.tld"); 1378 immutable hostmask = user.hostmask; 1379 assert((hostmask == "nickname!ident@address.tld"), hostmask); 1380 } 1381 { 1382 const user = IRCUser("nickname", string.init, "address.tld"); 1383 immutable hostmask = user.hostmask; 1384 assert((hostmask == "nickname!*@address.tld"), hostmask); 1385 } 1386 { 1387 const user = IRCUser(string.init, string.init, "address.tld"); 1388 immutable hostmask = user.hostmask; 1389 assert((hostmask == "*!*@address.tld"), hostmask); 1390 } 1391 { 1392 const IRCUser user; 1393 immutable hostmask = user.hostmask; 1394 assert((hostmask == "*!*@*"), hostmask); 1395 } 1396 } 1397 } 1398 1399 1400 // Typenums 1401 /++ 1402 Reverse mappings of *numerics* to [IRCEvent.Type|Type]s. 1403 1404 One `base` table that covers most cases, and then specialised arrays for 1405 different server daemons, to meld into `base` for a union of the two 1406 (or more). This speeds up translation greatly and allows us to have 1407 different mappings for different daemons. 1408 +/ 1409 struct Typenums 1410 { 1411 private: 1412 alias Type = IRCEvent.Type; 1413 1414 public: 1415 /++ 1416 Default mappings. 1417 +/ 1418 static immutable Type[1024] base = 1419 [ 1420 1 : Type.RPL_WELCOME, 1421 2 : Type.RPL_YOURHOST, 1422 3 : Type.RPL_CREATED, 1423 4 : Type.RPL_MYINFO, 1424 5 : Type.RPL_ISUPPORT, 1425 6 : Type.RPL_MAP, 1426 7 : Type.RPL_MAPEND, 1427 8 : Type.RPL_SNOMASK, 1428 9 : Type.RPL_STATMEMTOT, 1429 10 : Type.THISSERVERINSTEAD, // was Type.RPL_STATMEM 1430 14 : Type.RPL_YOURCOOKIE, 1431 15 : Type.RPL_MAP, 1432 16 : Type.RPL_MAPMORE, 1433 17 : Type.RPL_MAPEND, 1434 20 : Type.RPL_HELLO, 1435 30 : Type.RPL_APASSWARN_SET, 1436 31 : Type.RPL_APASSWARN_SECRET, 1437 32 : Type.RPL_APASSWARN_CLEAR, 1438 42 : Type.RPL_YOURID, 1439 43 : Type.RPL_SAVENICK, 1440 50 : Type.RPL_ATTEMPTINGJUNC, 1441 51 : Type.RPL_ATTEMPTINGREROUTE, 1442 105 : Type.RPL_REMOTEISUPPORT, 1443 200 : Type.RPL_TRACELINK, 1444 201 : Type.RPL_TRACECONNECTING, 1445 202 : Type.RPL_TRACEHANDSHAKE, 1446 203 : Type.RPL_TRACEUNKNOWN, 1447 204 : Type.RPL_TRACEOPERATOR, 1448 205 : Type.RPL_TRACEUSER, 1449 206 : Type.RPL_TRACESERVER, 1450 207 : Type.RPL_TRACESERVICE, 1451 208 : Type.RPL_TRACENEWTYPE, 1452 209 : Type.RPL_TRACECLASS, 1453 210 : Type.RPL_STATS, 1454 211 : Type.RPL_STATSLINKINFO, 1455 212 : Type.RPL_STATSCOMMAND, 1456 213 : Type.RPL_STATSCLINE, 1457 214 : Type.RPL_STATSNLINE, 1458 215 : Type.RPL_STATSILINE, 1459 216 : Type.RPL_STATSKLINE, 1460 217 : Type.RPL_STATSQLINE, 1461 218 : Type.RPL_STATSYLINE, 1462 219 : Type.RPL_ENDOFSTATS, 1463 220 : Type.RPL_STATSPLINE, 1464 221 : Type.RPL_UMODEIS, 1465 222 : Type.RPL_MODLIST, 1466 223 : Type.RPL_STATSELINE, 1467 224 : Type.RPL_STATSFLINE, 1468 225 : Type.RPL_STATSDLINE, 1469 226 : Type.RPL_STATSCOUNT, 1470 227 : Type.RPL_STATSBLINE, 1471 228 : Type.RPL_STATSQLINE, 1472 229 : Type.RPL_STATSSPAMF, 1473 230 : Type.RPL_STATSEXCEPTTKL, 1474 231 : Type.RPL_SERVICEINFO, 1475 232 : Type.RPL_ENDOFSERVICES, 1476 233 : Type.RPL_SERVICE, 1477 234 : Type.RPL_SERVLIST, 1478 235 : Type.RPL_SERVLISTEND, 1479 236 : Type.RPL_STATSVERBOSE, 1480 237 : Type.RPL_STATSENGINE, 1481 238 : Type.RPL_STATSFLINE, 1482 239 : Type.RPL_STATSIAUTH, 1483 240 : Type.RPL_STATSVLINE, 1484 241 : Type.RPL_STATSLLINE, 1485 242 : Type.RPL_STATSUPTIME, 1486 243 : Type.RPL_STATSOLINE, 1487 244 : Type.RPL_STATSHLINE, 1488 245 : Type.RPL_STATSSLINE, 1489 246 : Type.RPL_STATSPING, 1490 247 : Type.RPL_STATSBLINE, 1491 248 : Type.RPL_STATSULINE, 1492 249 : Type.RPL_STATSULINE, 1493 250 : Type.RPL_STATSCONN, 1494 251 : Type.RPL_LUSERCLIENT, 1495 252 : Type.RPL_LUSEROP, 1496 253 : Type.RPL_LUSERUNKNOWN, 1497 254 : Type.RPL_LUSERCHANNELS, 1498 255 : Type.RPL_LUSERME, 1499 256 : Type.RPL_ADMINME, 1500 257 : Type.RPL_ADMINLOC1, 1501 258 : Type.RPL_ADMINLOC2, 1502 259 : Type.RPL_ADMINEMAIL, 1503 261 : Type.RPL_TRACELOG, 1504 262 : Type.RPL_TRACEEND, 1505 263 : Type.RPL_TRYAGAIN, 1506 264 : Type.RPL_USINGSSL, 1507 265 : Type.RPL_LOCALUSERS, 1508 266 : Type.RPL_GLOBALUSERS, 1509 267 : Type.RPL_START_NETSTAT, 1510 268 : Type.RPL_NETSTAT, 1511 269 : Type.RPL_END_NETSTAT, 1512 270 : Type.RPL_PRIVS, 1513 271 : Type.RPL_SILELIST, 1514 272 : Type.RPL_ENDOFSILELIST, 1515 273 : Type.RPL_NOTIFY, 1516 274 : Type.RPL_ENDNOTIFY, 1517 275 : Type.RPL_STATSDLINE, 1518 276 : Type.RPL_STATSRLINE, 1519 277 : Type.RPL_VCHANLIST, 1520 278 : Type.RPL_VCHANHELP, 1521 280 : Type.RPL_GLIST, 1522 281 : Type.RPL_ACCEPTLIST, 1523 282 : Type.RPL_ENDOFACCEPT, 1524 283 : Type.RPL_ALIST, 1525 284 : Type.RPL_ENDOFALIST, 1526 285 : Type.RPL_GLIST_HASH, 1527 286 : Type.RPL_CHANINFO_USERS, 1528 287 : Type.RPL_CHANINFO_CHOPS, 1529 288 : Type.RPL_CHANINFO_VOICES, 1530 289 : Type.RPL_CHANINFO_AWAY, 1531 290 : Type.RPL_CHANINFO_OPERS, 1532 291 : Type.RPL_CHANINFO_BANNED, 1533 292 : Type.RPL_CHANINFO_BANS, 1534 293 : Type.RPL_CHANINFO_INVITE, 1535 294 : Type.RPL_CHANINFO_INVITES, 1536 295 : Type.RPL_CHANINFO_KICK, 1537 296 : Type.RPL_CHANINFO_KICKS, 1538 299 : Type.RPL_END_CHANINFO, 1539 300 : Type.RPL_NONE, 1540 301 : Type.RPL_AWAY, 1541 302 : Type.RPL_USERHOST, 1542 303 : Type.RPL_ISON, 1543 304 : Type.RPL_TEXT, 1544 305 : Type.RPL_UNAWAY, 1545 306 : Type.RPL_NOWAWAY, 1546 307 : Type.RPL_WHOISREGNICK, 1547 308 : Type.RPL_NOTIFYACTION, 1548 309 : Type.RPL_NICKTRACE, 1549 310 : Type.RPL_WHOISSVCMSG, 1550 311 : Type.RPL_WHOISUSER, 1551 312 : Type.RPL_WHOISSERVER, 1552 313 : Type.RPL_WHOISOPERATOR, 1553 314 : Type.RPL_WHOWASUSER, 1554 315 : Type.RPL_ENDOFWHO, 1555 316 : Type.RPL_WHOISCHANOP, 1556 317 : Type.RPL_WHOISIDLE, 1557 318 : Type.RPL_ENDOFWHOIS, 1558 319 : Type.RPL_WHOISCHANNELS, 1559 320 : Type.RPL_WHOISSPECIAL, 1560 321 : Type.RPL_LISTSTART, 1561 322 : Type.RPL_LIST, 1562 323 : Type.RPL_LISTEND, 1563 324 : Type.RPL_CHANNELMODEIS, 1564 325 : Type.RPL_CHANNELPASSIS, 1565 326 : Type.RPL_NOCHANPASS, 1566 327 : Type.RPL_CHPASSUNKNOWN, 1567 328 : Type.RPL_CHANNEL_URL, 1568 329 : Type.RPL_CREATIONTIME, 1569 330 : Type.RPL_WHOISACCOUNT, 1570 331 : Type.RPL_NOTOPIC, 1571 332 : Type.RPL_TOPIC, 1572 333 : Type.RPL_TOPICWHOTIME, 1573 334 : Type.RPL_LISTUSAGE, 1574 335 : Type.RPL_WHOISBOT, 1575 336 : Type.RPL_INVITELIST, 1576 337 : Type.RPL_ENDOFINVITELIST, 1577 338 : Type.RPL_WHOISACTUALLY, 1578 339 : Type.RPL_BADCHANPASS, 1579 340 : Type.RPL_USERIP, 1580 341 : Type.RPL_INVITING, 1581 342 : Type.RPL_SUMMONING, 1582 343 : Type.RPL_WHOISKILL, 1583 345 : Type.RPL_INVITED, 1584 346 : Type.RPL_INVITELIST, 1585 347 : Type.RPL_ENDOFINVITELIST, 1586 348 : Type.RPL_EXCEPTLIST, 1587 349 : Type.RPL_ENDOFEXCEPTLIST, 1588 351 : Type.RPL_VERSION, 1589 352 : Type.RPL_WHOREPLY, 1590 353 : Type.RPL_NAMREPLY, 1591 354 : Type.RPL_WHOSPCRPL, 1592 355 : Type.RPL_NAMREPLY_, 1593 357 : Type.RPL_MAP, 1594 358 : Type.RPL_MAPMORE, 1595 359 : Type.RPL_MAPEND, 1596 360 : Type.RPL_WHOWASREAL, 1597 361 : Type.RPL_KILLDONE, 1598 362 : Type.RPL_CLOSING, 1599 363 : Type.RPL_CLOSEEND, 1600 364 : Type.RPL_LINKS, 1601 365 : Type.RPL_ENDOFLINKS, 1602 366 : Type.RPL_ENDOFNAMES, 1603 367 : Type.RPL_BANLIST, 1604 368 : Type.RPL_ENDOFBANLIST, 1605 369 : Type.RPL_ENDOFWHOWAS, 1606 371 : Type.RPL_INFO, 1607 372 : Type.RPL_MOTD, 1608 373 : Type.RPL_INFOSTART, 1609 374 : Type.RPL_ENDOFINFO, 1610 375 : Type.RPL_MOTDSTART, 1611 376 : Type.RPL_ENDOFMOTD, 1612 377 : Type.RPL_KICKEXPIRED, 1613 378 : Type.RPL_WHOISHOST, 1614 379 : Type.RPL_WHOISMODES, 1615 380 : Type.RPL_BANLINKED, 1616 381 : Type.RPL_YOUREOPER, 1617 382 : Type.RPL_REHASHING, 1618 383 : Type.RPL_YOURESERVICE, 1619 384 : Type.RPL_MYPORTIS, 1620 385 : Type.RPL_NOTOPERANYMORE, 1621 386 : Type.RPL_QLIST, 1622 387 : Type.RPL_ENDOFQLIST, 1623 388 : Type.RPL_ALIST, 1624 389 : Type.RPL_ENDOFALIST, 1625 391 : Type.RPL_TIME, 1626 392 : Type.RPL_USERSTART, 1627 393 : Type.RPL_USERS, 1628 394 : Type.RPL_ENDOFUSERS, 1629 395 : Type.RPL_NOUSERS, 1630 396 : Type.RPL_HOSTHIDDEN, 1631 400 : Type.ERR_UNKNOWNERROR, 1632 401 : Type.ERR_NOSUCHNICK, 1633 402 : Type.ERR_NOSUCHSERVER, 1634 403 : Type.ERR_NOSUCHCHANNEL, 1635 404 : Type.ERR_CANNOTSENDTOCHAN, 1636 405 : Type.ERR_TOOMANYCHANNELS, 1637 406 : Type.ERR_WASNOSUCHNICK, 1638 407 : Type.ERR_TOOMANYTARGETS, 1639 408 : Type.ERR_NOSUCHSERVICE, 1640 409 : Type.ERR_NOORIGIN, 1641 410 : Type.ERR_INVALIDCAPCMD, 1642 411 : Type.ERR_NORECIPIENT, 1643 412 : Type.ERR_NOTEXTTOSEND, 1644 413 : Type.ERR_NOTOPLEVEL, 1645 414 : Type.ERR_WILDTOPLEVEL, 1646 415 : Type.ERR_BADMASK, 1647 416 : Type.ERR_TOOMANYMATCHES, 1648 417 : Type.ERR_INPUTTOOLONG, 1649 419 : Type.ERR_LENGTHTRUNCATED, 1650 421 : Type.ERR_UNKNOWNCOMMAND, 1651 422 : Type.ERR_NOMOTD, 1652 423 : Type.ERR_NOADMININFO, 1653 424 : Type.ERR_FILEERROR, 1654 425 : Type.ERR_NOOPERMOTD, 1655 429 : Type.ERR_TOOMANYAWAY, 1656 430 : Type.ERR_EVENTNICKCHANGE, 1657 431 : Type.ERR_NONICKNAMEGIVEN, 1658 432 : Type.ERR_ERRONEOUSNICKNAME, 1659 433 : Type.ERR_NICKNAMEINUSE, 1660 434 : Type.ERR_NORULES, 1661 435 : Type.ERR_BANONCHAN, 1662 436 : Type.ERR_NICKCOLLISION, 1663 437 : Type.ERR_UNAVAILRESOURCE, 1664 438 : Type.ERR_NICKTOOFAST, 1665 439 : Type.ERR_TARGETTOOFAST, 1666 440 : Type.ERR_SERVICESDOWN, 1667 441 : Type.ERR_USERNOTINCHANNEL, 1668 442 : Type.ERR_NOTONCHANNEL, 1669 443 : Type.ERR_USERONCHANNEL, 1670 444 : Type.ERR_NOLOGIN, 1671 445 : Type.ERR_SUMMONDISABLED, 1672 446 : Type.ERR_USERSDISABLED, 1673 447 : Type.ERR_NONICKCHANGE, 1674 448 : Type.ERR_FORBIDDENCHANNEL, 1675 449 : Type.ERR_NOTIMPLEMENTED, 1676 451 : Type.ERR_NOTREGISTERED, 1677 452 : Type.ERR_IDCOLLISION, 1678 453 : Type.ERR_NICKLOST, 1679 455 : Type.ERR_HOSTILENAME, 1680 456 : Type.ERR_ACCEPTFULL, 1681 457 : Type.ERR_ACCEPTEXIST, 1682 458 : Type.ERR_ACCEPTNOT, 1683 459 : Type.ERR_NOHIDING, 1684 460 : Type.ERR_NOTFORHALFOPS, 1685 461 : Type.ERR_NEEDMOREPARAMS, 1686 462 : Type.ERR_ALREADYREGISTERED, 1687 463 : Type.ERR_NOPERMFORHOST, 1688 464 : Type.ERR_PASSWDMISMATCH, 1689 465 : Type.ERR_YOUREBANNEDCREEP, 1690 466 : Type.ERR_YOUWILLBEBANNED, 1691 467 : Type.ERR_KEYSET, 1692 468 : Type.ERR_INVALIDUSERNAME, 1693 469 : Type.ERR_LINKSET, 1694 470 : Type.ERR_LINKCHANNEL, 1695 471 : Type.ERR_CHANNELISFULL, 1696 472 : Type.ERR_UNKNOWNMODE, 1697 473 : Type.ERR_INVITEONLYCHAN, 1698 474 : Type.ERR_BANNEDFROMCHAN, 1699 475 : Type.ERR_BADCHANNELKEY, 1700 476 : Type.ERR_BADCHANMASK, 1701 477 : Type.ERR_NEEDREGGEDNICK, 1702 478 : Type.ERR_BANLISTFULL, 1703 479 : Type.ERR_BADCHANNAME, 1704 480 : Type.ERR_CANNOTKNOCK, 1705 481 : Type.ERR_NOPRIVILEGES, 1706 482 : Type.ERR_CHANOPRIVSNEEDED, 1707 483 : Type.ERR_CANTKILLSERVER, 1708 484 : Type.ERR_RESTRICTED, 1709 485 : Type.ERR_UNIQPRIVSNEEDED, 1710 486 : Type.ERR_NONONREG, 1711 487 : Type.ERR_MSGSERVICES, 1712 488 : Type.ERR_TSLESSCHAN, 1713 489 : Type.ERR_SECUREONLYCHAN, 1714 490 : Type.ERR_ALLMUSTSSL, 1715 491 : Type.ERR_NOOPERHOST, 1716 492 : Type.ERR_NOSERVICEHOST, 1717 493 : Type.ERR_NOFEATURE, 1718 494 : Type.ERR_BADFEATVALUE, 1719 495 : Type.ERR_BADLOGTYPE, 1720 496 : Type.ERR_BADLOGSYS, 1721 497 : Type.ERR_BADLOGVALUE, 1722 498 : Type.ERR_ISOPERLCHAN, 1723 499 : Type.ERR_CHANOWNPRIVNEEDED, 1724 500 : Type.ERR_TOOMANYJOINS, 1725 501 : Type.ERR_UMODEUNKNOWNFLAG, 1726 502 : Type.ERR_USERSDONTMATCH, 1727 503 : Type.ERR_GHOSTEDCLIENT, 1728 504 : Type.ERR_USERNOTONSERV, 1729 511 : Type.ERR_SILELISTFULL, 1730 512 : Type.ERR_TOOMANYWATCH, 1731 513 : Type.ERR_NEEDPONG, 1732 514 : Type.ERR_INVALID_ERROR, 1733 515 : Type.ERR_BADEXPIRE, 1734 516 : Type.ERR_DONTCHEAT, 1735 517 : Type.ERR_DISABLED, 1736 518 : Type.ERR_LONGMASK, 1737 519 : Type.ERR_TOOMANYUSERS, 1738 520 : Type.ERR_OPERONLY, 1739 521 : Type.ERR_LISTSYNTAX, 1740 522 : Type.ERR_WHOSYNTAX, 1741 523 : Type.ERR_WHOLIMEXCEED, 1742 524 : Type.ERR_HELPNOTFOUND, 1743 525 : Type.ERR_REMOTEPFX, 1744 526 : Type.ERR_PFXUNROUTABLE, 1745 531 : Type.ERR_CANTSENDTOUSER, 1746 550 : Type.ERR_BADHOSTMASK, 1747 551 : Type.ERR_HOSTUNAVAIL, 1748 552 : Type.ERR_USINGSLINE, 1749 553 : Type.ERR_STATSSLINE, 1750 560 : Type.ERR_NOTLOWEROPLEVEL, 1751 561 : Type.ERR_NOTMANAGER, 1752 562 : Type.ERR_CHANSECURED, 1753 563 : Type.ERR_UPASSSET, 1754 564 : Type.ERR_UPASSNOTSET, 1755 566 : Type.ERR_NOMANAGER, 1756 567 : Type.ERR_UPASS_SAME_APASS, 1757 568 : Type.ERR_LASTERROR, 1758 597 : Type.RPL_REAWAY, 1759 598 : Type.RPL_GONEAWAY, 1760 599 : Type.RPL_NOTAWAY, 1761 600 : Type.RPL_LOGON, 1762 601 : Type.RPL_LOGOFF, 1763 602 : Type.RPL_WATCHOFF, 1764 603 : Type.RPL_WATCHSTAT, 1765 604 : Type.RPL_NOWON, 1766 605 : Type.RPL_NOWFF, 1767 606 : Type.RPL_WATCHLIST, 1768 607 : Type.RPL_ENDOFWATCHLIST, 1769 608 : Type.RPL_WATCHCLEAR, 1770 609 : Type.RPL_NOWISAWAY, 1771 610 : Type.RPL_MAPMORE, 1772 611 : Type.RPL_ISLOCOP, 1773 612 : Type.RPL_ISNOTOPER, 1774 613 : Type.RPL_ENDOFISOPER, 1775 615 : Type.RPL_WHOISMODES, 1776 616 : Type.RPL_WHOISHOST, 1777 617 : Type.RPL_DCCSTATUS, 1778 618 : Type.RPL_DCCLIST, 1779 619 : Type.RPL_ENDOFDCCLIST, 1780 620 : Type.RPL_DCCINFO, 1781 621 : Type.RPL_RULES, 1782 622 : Type.RPL_ENDOFRULES, 1783 623 : Type.RPL_MAPMORE, 1784 624 : Type.RPL_OMOTDSTART, 1785 625 : Type.RPL_OMOTD, 1786 626 : Type.RPL_ENDOFO, 1787 630 : Type.RPL_SETTINGS, 1788 631 : Type.RPL_ENDOFSETTINGS, 1789 640 : Type.RPL_DUMPING, 1790 641 : Type.RPL_DUMPRPL, 1791 642 : Type.RPL_EODUMP, 1792 659 : Type.RPL_SPAMCMDFWD, 1793 660 : Type.RPL_TRACEROUTE_HOP, 1794 661 : Type.RPL_TRACEROUTE_START, 1795 662 : Type.RPL_MODECHANGEWARN, 1796 663 : Type.RPL_CHANREDIR, 1797 664 : Type.RPL_SERVMODEIS, 1798 665 : Type.RPL_OTHERUMODEIS, 1799 666 : Type.RPL_ENDOF_GENERIC, 1800 670 : Type.RPL_STARTTLS, 1801 671 : Type.RPL_WHOISSECURE, 1802 672 : Type.RPL_WHOISREALIP, 1803 673 : Type.RPL_CANNOTSETMODES, 1804 674 : Type.RPL_WHOISYOURID, 1805 678 : Type.RPL_LUSERSTAFF, 1806 679 : Type.RPL_TIMEONSERVERIS, 1807 682 : Type.RPL_NETWORKS, 1808 687 : Type.RPL_YOURLANGUAGEIS, 1809 688 : Type.RPL_LANGUAGE, 1810 689 : Type.RPL_WHOISSTAFF, 1811 690 : Type.RPL_WHOISLANGUAGE, 1812 691 : Type.ERR_STARTTLS, 1813 702 : Type.RPL_COMMANDS, 1814 703 : Type.RPL_COMMANDSEND, 1815 704 : Type.RPL_HELPSTART, 1816 705 : Type.RPL_HELPTXT, 1817 706 : Type.RPL_ENDOFHELP, 1818 707 : Type.ERR_TARGCHANGE, 1819 708 : Type.RPL_ETRACEFULL, 1820 709 : Type.RPL_ETRACE, 1821 710 : Type.RPL_KNOCK, 1822 711 : Type.RPL_KNOCKDLVR, 1823 712 : Type.ERR_TOOMANYKNOCK, 1824 713 : Type.ERR_CHANOPEN, 1825 714 : Type.ERR_KNOCKONCHAN, 1826 715 : Type.RPL_INVITETHROTTLE, 1827 716 : Type.RPL_TARGUMODEG, 1828 717 : Type.RPL_TARGNOTIFY, 1829 718 : Type.RPL_UMODEGMSG, 1830 720 : Type.RPL_OMOTDSTART, 1831 721 : Type.RPL_OMOTD, 1832 722 : Type.RPL_ENDOFOMOTD, 1833 723 : Type.ERR_NOPRIVS, 1834 724 : Type.RPL_TESTMASK, 1835 725 : Type.RPL_TESTLINE, 1836 726 : Type.RPL_NOTESTLINE, 1837 727 : Type.RPL_TESTMASKGECOS, 1838 728 : Type.RPL_QUIETLIST, 1839 729 : Type.RPL_ENDOFQUIETLIST, 1840 730 : Type.RPL_MONONLINE, 1841 731 : Type.RPL_MONOFFLINE, 1842 732 : Type.RPL_MONLIST, 1843 733 : Type.RPL_ENDOFMONLIST, 1844 734 : Type.ERR_MONLISTFULL, 1845 740 : Type.RPL_RSACHALLENGE2, 1846 741 : Type.RPL_ENDOFRSACHALLENGE2, 1847 742 : Type.ERR_MLOCKRESTRICTED, 1848 743 : Type.ERR_INVALIDBAN, 1849 744 : Type.ERR_TOPICLOCK, 1850 750 : Type.RPL_SCANMATCHED, 1851 751 : Type.RPL_SCANUMODES, 1852 759 : Type.RPL_ETRACEEND, 1853 760 : Type.RPL_WHOISKEYVALUE, 1854 761 : Type.RPL_KEYVALUE, 1855 762 : Type.RPL_METADATAEND, 1856 764 : Type.ERR_METADATALIMIT, 1857 765 : Type.ERR_TARGETINVALID, 1858 766 : Type.ERR_NOMATCHINGKEY, 1859 767 : Type.ERR_KEYINVALID, 1860 768 : Type.ERR_KEYNOTSET, 1861 769 : Type.ERR_KEYNOPERMISSION, 1862 771 : Type.RPL_XINFO, 1863 773 : Type.RPL_XINFOSTART, 1864 774 : Type.RPL_XINFOEND, 1865 802 : Type.RPL_CHECK, 1866 900 : Type.RPL_LOGGEDIN, 1867 901 : Type.RPL_LOGGEDOUT, 1868 902 : Type.ERR_NICKLOCKED, 1869 903 : Type.RPL_SASLSUCCESS, 1870 904 : Type.ERR_SASLFAIL, 1871 905 : Type.ERR_SASLTOOLONG, 1872 906 : Type.ERR_SASLABORTED, 1873 907 : Type.ERR_SASLALREADY, 1874 908 : Type.RPL_SASLMECHS, 1875 911 : Type.ENDOFCHANNELACCLIST, 1876 960 : Type.ENDOFMODELIST, 1877 961 : Type.MODELIST, 1878 931 : Type.BOTSNOTWELCOME, 1879 926 : Type.CHANNELFORBIDDEN, 1880 936 : Type.ERR_WORDFILTERED, 1881 940 : Type.ENDOFSPAMFILTERLIST, 1882 941 : Type.SPAMFILTERLIST, 1883 945 : Type.NICKUNLOCKED, 1884 946 : Type.NICKNOTLOCKED, 1885 972 : Type.ERR_CANNOTDOCOMMAND, 1886 973 : Type.ERR_CANNOTCHANGEUMODE, 1887 974 : Type.ERR_CANNOTCHANGECHANMODE, 1888 975 : Type.RPL_LOADEDMODULE, 1889 976 : Type.ERR_CANNOTSENDTONICK, 1890 977 : Type.ERR_UNKNOWNSERVERMODE, 1891 979 : Type.ERR_SERVERMODELOCK, 1892 980 : Type.ERR_BADCHARENCODING, 1893 981 : Type.ERR_TOOMANYLANGUAGES, 1894 982 : Type.ERR_NOLANGUAGE, 1895 983 : Type.ERR_TEXTTOOSHORT, 1896 999 : Type.ERR_NUMERIC_ERR, 1897 ]; 1898 1899 /++ 1900 Delta typenum mappings for servers running the `UnrealIRCd` daemon. 1901 1902 - https://www.unrealircd.org 1903 +/ 1904 static immutable Type[975] unreal = 1905 [ 1906 6 : Type.RPL_MAP, 1907 7 : Type.RPL_MAPEND, 1908 210 : Type.RPL_STATSHELP, 1909 220 : Type.RPL_STATSBLINE, 1910 222 : Type.RPL_SQLINE_NICK, 1911 223 : Type.RPL_STATSGLINE, 1912 224 : Type.RPL_STATSTLINE, 1913 225 : Type.RPL_STATSELINE, 1914 226 : Type.RPL_STATSNLINE, 1915 227 : Type.RPL_STATSVLINE, 1916 228 : Type.RPL_STATSBANVER, 1917 232 : Type.RPL_RULES, 1918 247 : Type.RPL_STATSXLINE, 1919 250 : Type.RPL_STATSCONN, 1920 290 : Type.RPL_HELPHDR, 1921 291 : Type.RPL_HELPOP, 1922 292 : Type.RPL_HELPTLR, 1923 293 : Type.RPL_HELPHLP, 1924 294 : Type.RPL_HELPFWD, 1925 295 : Type.RPL_HELPIGN, 1926 307 : Type.RPL_WHOISREGNICK, 1927 308 : Type.RPL_RULESSTART, 1928 309 : Type.RPL_ENDOFRULES, 1929 310 : Type.RPL_WHOISHELPOP, 1930 320 : Type.RPL_WHOISSPECIAL, 1931 334 : Type.RPL_LISTSYNTAX, 1932 335 : Type.RPL_WHOISBOT, 1933 378 : Type.RPL_WHOISHOST, 1934 379 : Type.RPL_WHOISMODES, 1935 386 : Type.RPL_QLIST, 1936 387 : Type.RPL_ENDOFQLIST, 1937 388 : Type.RPL_ALIST, 1938 434 : Type.ERR_NORULES, 1939 435 : Type.ERR_SERVICECONFUSED, 1940 438 : Type.ERR_ONLYSERVERSCANCHANGE, 1941 470 : Type.ERR_LINKCHANNEL, 1942 477 : Type.ERR_NEEDREGGEDNICK, 1943 479 : Type.ERR_LINKFAIL, 1944 480 : Type.ERR_CANNOTKNOCK, 1945 484 : Type.ERR_ATTACKDENY, 1946 485 : Type.ERR_KILLDENY, 1947 486 : Type.ERR_HTMDISABLED, // CONFLICT ERR_NONONREG 1948 487 : Type.ERR_NOTFORUSERS, 1949 488 : Type.ERR_HTMDISABLED, // again? 1950 489 : Type.ERR_SECUREONLYCHAN, // AKA ERR_SSLONLYCHAN 1951 490 : Type.ERR_ALLMUSTSSL, // CONFLICT ERR_NOSWEAR 1952 492 : Type.ERR_NOCTCP, 1953 500 : Type.ERR_TOOMANYJOINS, 1954 518 : Type.ERR_NOINVITE, 1955 519 : Type.ERR_ADMONLY, 1956 520 : Type.ERR_OPERONLY, 1957 524 : Type.ERR_OPERSPVERIFY, 1958 610 : Type.RPL_MAPMORE, 1959 972 : Type.ERR_CANNOTDOCOMMAND, 1960 974 : Type.ERR_CANNOTCHANGECHANMODE, 1961 ]; 1962 1963 /++ 1964 Delta typenum mappings for servers running the `ircu` (Undernet) daemon. 1965 1966 - http://coder-com.undernet.org 1967 +/ 1968 static immutable Type[569] ircu = 1969 [ 1970 15 : Type.RPL_MAP, 1971 16 : Type.RPL_MAPMORE, 1972 17 : Type.RPL_MAPEND, 1973 222 : Type.RPL_STATSJLINE, 1974 228 : Type.RPL_STATSQLINE, 1975 238 : Type.RPL_STATSFLINE, 1976 246 : Type.RPL_STATSTLINE, 1977 247 : Type.RPL_STATSGLINE, 1978 248 : Type.RPL_STATSULINE, 1979 250 : Type.RPL_STATSCONN, 1980 270 : Type.RPL_PRIVS, 1981 275 : Type.RPL_STATSDLINE, 1982 276 : Type.RPL_STATSRLINE, 1983 281 : Type.RPL_ENDOFGLIST, 1984 282 : Type.RPL_JUPELIST, 1985 283 : Type.RPL_ENDOFJUPELIST, 1986 284 : Type.RPL_FEATURE, 1987 330 : Type.RPL_WHOISACCOUNT, 1988 334 : Type.RPL_LISTUSAGE, 1989 338 : Type.RPL_WHOISACTUALLY, 1990 391 : Type.RPL_TIME, 1991 437 : Type.ERR_BANNICKCHANGE, 1992 438 : Type.ERR_NICKTOOFAST, 1993 468 : Type.ERR_INVALIDUSERNAME, 1994 477 : Type.ERR_NEEDREGGEDNICK, 1995 493 : Type.ERR_NOFEATURE, 1996 494 : Type.ERR_BADFEATVALUE, 1997 495 : Type.ERR_BADLOGTYPE, 1998 512 : Type.ERR_NOSUCHGLINE, 1999 514 : Type.ERR_INVALID_ERROR, 2000 518 : Type.ERR_LONGMASK, 2001 519 : Type.ERR_TOOMANYUSERS, 2002 520 : Type.ERR_MASKTOOWIDE, 2003 524 : Type.ERR_QUARANTINED, 2004 568 : Type.ERR_LASTERROR, 2005 ]; 2006 2007 /++ 2008 Delta typenum mappings for servers running the `aircd` (?) daemon. 2009 2010 "After AnotherNet had become a commercial and proprietary-client chat 2011 network, the former users of AnotherNet's #trax decided to found their 2012 own network - "where free speech and ideas would be able to run 2013 unbounded through the pastures of #trax and #coders". They use the 2014 "`aircd`" IRC daemon, coded by an ex-member of the demoscene, simon 2015 kirby." 2016 +/ 2017 static immutable Type[471] aircd = 2018 [ 2019 210 : Type.RPL_STATS, 2020 274 : Type.RPL_ENDNOTIFY, 2021 285 : Type.RPL_CHANINFO_HANDLE, 2022 286 : Type.RPL_CHANINFO_USERS, 2023 287 : Type.RPL_CHANINFO_CHOPS, 2024 288 : Type.RPL_CHANINFO_VOICES, 2025 289 : Type.RPL_CHANINFO_AWAY, 2026 290 : Type.RPL_CHANINFO_OPERS, 2027 291 : Type.RPL_CHANINFO_BANNED, 2028 292 : Type.RPL_CHANINFO_BANS, 2029 293 : Type.RPL_CHANINFO_INVITE, 2030 294 : Type.RPL_CHANINFO_INVITES, 2031 295 : Type.RPL_CHANINFO_KICKS, 2032 308 : Type.RPL_NOTIFYACTION, 2033 309 : Type.RPL_NICKTRACE, 2034 377 : Type.RPL_KICKEXPIRED, 2035 378 : Type.RPL_BANEXPIRED, 2036 379 : Type.RPL_KICKLINKED, 2037 380 : Type.RPL_BANLINKED, 2038 470 : Type.ERR_KICKEDFROMCHAN, 2039 ]; 2040 2041 /++ 2042 Delta typenum mappings for servers adhering to the `RFC1459` draft. 2043 2044 - https://tools.ietf.org/html/rfc1459 2045 +/ 2046 static immutable Type[502] rfc1459 = 2047 [ 2048 214 : Type.RPL_STATSNLINE, 2049 217 : Type.RPL_STATSQLINE, 2050 232 : Type.RPL_ENDOFSERVICES, 2051 316 : Type.RPL_WHOISCHANOP, // deprecated 2052 391 : Type.RPL_TIME, 2053 492 : Type.ERR_NOSERVICEHOST, 2054 501 : Type.ERR_UMODEUNKNOWNFLAG, 2055 ]; 2056 2057 /++ 2058 Delta typenum mappings for servers adhering to the `RFC2812` draft. 2059 2060 - https://tools.ietf.org/html/rfc2812 2061 +/ 2062 static immutable Type[485] rfc2812 = 2063 [ 2064 240 : Type.RPL_STATSVLINE, 2065 246 : Type.RPL_STATSPING, 2066 247 : Type.RPL_STATSBLINE, 2067 250 : Type.RPL_STATSDLINE, 2068 262 : Type.RPL_TRACEEND, 2069 325 : Type.RPL_UNIQOPIS, 2070 437 : Type.ERR_UNAVAILRESOURCE, 2071 477 : Type.ERR_NOCHANMODES, 2072 484 : Type.ERR_RESTRICTED, 2073 ]; 2074 2075 /++ 2076 Delta typenum mappings for servers running the `IRCD-Hybrid` daemon. 2077 2078 - http://www.ircd-hybrid.org 2079 +/ 2080 static immutable Type[716] hybrid = 2081 [ 2082 220 : Type.RPL_STATSPLINE, 2083 224 : Type.RPL_STATSFLINE, 2084 225 : Type.RPL_STATSDLINE, 2085 226 : Type.RPL_STATSALINE, 2086 245 : Type.RPL_STATSSLINE, // CONFLICT: Type.RPL_STATSTLINE 2087 246 : Type.RPL_STATSSERVICE, // CONFLICT: Type.RPL_STATSULINE 2088 247 : Type.RPL_STATSXLINE, 2089 249 : Type.RPL_STATSDEBUG, 2090 276 : Type.RPL_WHOISCERTFP, // oftc-hybrid? 2091 335 : Type.RPL_WHOISTEXT, 2092 336 : Type.RPL_INVITELIST, 2093 337 : Type.RPL_ENDOFINVITELIST, // CONFLICT: Type.RPL_WHOISTEXT 2094 344 : Type.RPL_QUIETLIST, // oftc 2095 345 : Type.RPL_ENDOFQUIETLIST, // CONFLICT: Type.RPL_INVITED, oftc 2096 386 : Type.RPL_RSACHALLENGE, 2097 396 : Type.RPL_VISIBLEHOST, 2098 408 : Type.ERR_NOCTRLSONCHAN, 2099 479 : Type.ERR_BADCHANNAME, 2100 480 : Type.ERR_SSLONLYCHAN, // deprecated 2101 484 : Type.ERR_DESYNC, 2102 485 : Type.ERR_CHANBANREASON, 2103 492 : Type.ERR_NOCTCP, 2104 503 : Type.ERR_GHOSTEDCLIENT, 2105 524 : Type.ERR_HELPNOTFOUND, 2106 715 : Type.ERR_TOOMANYINVITE, 2107 ]; 2108 2109 /++ 2110 Delta typenum mappings for servers running the `Solanum` daemon. 2111 2112 - https://github.com/solanum-ircd/solanum 2113 +/ 2114 static immutable Type[250] solanum = 2115 [ 2116 249 : Type.RPL_STATSPLINE, 2117 ]; 2118 2119 /++ 2120 Delta typenum mappings for servers running the `Bahamut` daemon 2121 (DALnet). 2122 2123 - https://www.dal.net/?page=bahamut 2124 +/ 2125 static immutable Type[621] bahamut = 2126 [ 2127 220 : Type.RPL_STATSBLINE, 2128 222 : Type.RPL_STATSBLINE, 2129 223 : Type.RPL_STATSELINE, 2130 224 : Type.RPL_STATSFLINE, 2131 225 : Type.RPL_STATSCLONE, // DEPRECATED CONFLICT: Type.RPL_STATSZLINE 2132 226 : Type.RPL_STATSCOUNT, 2133 227 : Type.RPL_STATSGLINE, 2134 245 : Type.RPL_STATSSLINE, 2135 275 : Type.RPL_USINGSSL, 2136 307 : Type.RPL_WHOISREGNICK, 2137 308 : Type.RPL_WHOISADMIN, 2138 309 : Type.RPL_WHOISADMIN, // duplicate? 2139 310 : Type.RPL_WHOISSVCMSG, 2140 334 : Type.RPL_COMMANDSYNTAX, 2141 338 : Type.RPL_WHOISACTUALLY, 2142 408 : Type.ERR_NOCOLORSONCHAN, 2143 435 : Type.ERR_BANONCHAN, 2144 468 : Type.ERR_ONLYSERVERSCANCHANGE, 2145 477 : Type.ERR_NEEDREGGEDNICK, 2146 484 : Type.ERR_DESYNC, 2147 487 : Type.ERR_MSGSERVICES, 2148 488 : Type.ERR_NOSSL, 2149 493 : Type.ERR_NOSHAREDCHAN, 2150 494 : Type.ERR_OWNMODE, 2151 512 : Type.ERR_TOOMANYWATCH, 2152 514 : Type.ERR_TOOMANYDCC, 2153 521 : Type.ERR_LISTSYNTAX, 2154 617 : Type.RPL_DCCSTATUS, 2155 619 : Type.RPL_ENDOFDCCLIST, 2156 620 : Type.RPL_DCCINFO, 2157 ]; 2158 2159 /++ 2160 Delta typenum mappings for servers running the `snircd` daemon 2161 (QuakeNet), based on `ircu`. 2162 2163 - https://development.quakenet.org 2164 +/ 2165 static immutable Type[554] snircd = 2166 [ 2167 285 : Type.RPL_NEWHOSTIS, 2168 286 : Type.RPL_CHKHEAD, 2169 287 : Type.RPL_CHANUSER, 2170 288 : Type.RPL_PATCHHEAD, 2171 289 : Type.RPL_PATCHCON, 2172 290 : Type.RPL_DATASTR, 2173 291 : Type.RPL_ENDOFCHECK, 2174 485 : Type.ERR_ISREALSERVICE, 2175 486 : Type.ERR_ACCOUNTONLY, 2176 553 : Type.ERR_STATSSLINE, 2177 ]; 2178 2179 /++ 2180 Delta typenum mappings for servers running the `Nefarious` or 2181 `Nefarious2` daemons, based on `ircu`. 2182 2183 - https://github.com/evilnet/nefarious 2184 - https://github.com/evilnet/nefarious2 2185 +/ 2186 static immutable Type[976] nefarious = 2187 [ 2188 220 : Type.RPL_STATSWLINE, 2189 292 : Type.ERR_SEARCHNOMATCH, 2190 316 : Type.RPL_WHOISPRIVDEAF, 2191 320 : Type.RPL_WHOISWEBIRC, 2192 335 : Type.RPL_WHOISACCOUNTONLY, 2193 336 : Type.RPL_WHOISBOT, 2194 339 : Type.RPL_WHOISMARKS, 2195 386 : Type.RPL_IRCOPSHEADER, 2196 387 : Type.RPL_IRCOPS, 2197 388 : Type.RPL_ENDOFIRCOPS, 2198 521 : Type.ERR_NOSUCHGLINE, 2199 568 : Type.RPL_NOMOTD, 2200 617 : Type.RPL_WHOISSSLFP, 2201 975 : Type.ERR_LASTERROR, 2202 ]; 2203 2204 /++ 2205 Delta typenum mappings for `RusNet` servers. Unsure of what daemon they 2206 run. 2207 2208 - http://www.rus-net.org 2209 +/ 2210 static immutable Type[501] rusnet = 2211 [ 2212 222 : Type.RPL_CODEPAGE, 2213 223 : Type.RPL_CHARSET, 2214 327 : Type.RPL_WHOISHOST, 2215 468 : Type.ERR_NOCODEPAGE, 2216 470 : Type.ERR_7BIT, 2217 479 : Type.ERR_NOCOLOR, 2218 480 : Type.ERR_NOWALLOP, 2219 486 : Type.ERR_RLINED, 2220 500 : Type.ERR_NOREHASHPARAM, 2221 ]; 2222 2223 /++ 2224 Delta typenum mappings for `Rizon` network servers. Supposedly they use 2225 a mixture of Hybrid typenums, plus a few of their own. 2226 2227 - https://www.rizon.net 2228 +/ 2229 static immutable Type[716] rizon = 2230 [ 2231 227 : Type.RPL_STATSBLINE, 2232 672 : Type.RPL_WHOISREALIP, 2233 715 : Type.RPL_INVITETHROTTLE, 2234 ]; 2235 2236 /++ 2237 Delta typenum mappings for `austHex` AUSTNet Development servers. 2238 2239 - https://sourceforge.net/projects/austhex 2240 +/ 2241 static immutable Type[521] austHex = 2242 [ 2243 240 : Type.RPL_STATSXLINE, 2244 307 : Type.RPL_SUSERHOST, 2245 309 : Type.RPL_WHOISHELPER, 2246 310 : Type.RPL_WHOISSERVICE, 2247 320 : Type.RPL_WHOISVIRT, 2248 357 : Type.RPL_MAP, 2249 358 : Type.RPL_MAPMORE, 2250 359 : Type.RPL_MAPEND, 2251 377 : Type.RPL_SPAM, // deprecated 2252 378 : Type.RPL_MOTD, 2253 380 : Type.RPL_YOURHELPER, 2254 434 : Type.ERR_SERVICENAMEINUSE, 2255 480 : Type.ERR_NOULINE, 2256 503 : Type.ERR_VWORLDWARN, 2257 520 : Type.ERR_WHOTRUNC, // deprecated 2258 ]; 2259 2260 /++ 2261 Delta typenum mappings for the `IRCnet` network of servers. Unsure of 2262 what server daemon they run. 2263 2264 - http://www.ircnet.org 2265 +/ 2266 static immutable Type[489] ircNet = 2267 [ 2268 245 : Type.RPL_STATSSLINE, 2269 248 : Type.RPL_STATSDEFINE, 2270 274 : Type.RPL_STATSDELTA, 2271 344 : Type.RPL_REOPLIST, 2272 345 : Type.RPL_ENDOFREOPLIST, 2273 438 : Type.ERR_DEAD, 2274 487 : Type.ERR_CHANTOORECENT, 2275 488 : Type.ERR_TSLESSCHAN, 2276 ]; 2277 2278 /++ 2279 Delta typenum mappings for servers running the `PTlink` daemon. 2280 2281 - https://sourceforge.net/projects/ptlinksoft 2282 +/ 2283 static immutable Type[616] ptlink = 2284 [ 2285 247 : Type.RPL_STATSXLINE, 2286 484 : Type.ERR_DESYNC, 2287 485 : Type.ERR_CANTKICKADMIN, 2288 615 : Type.RPL_MAPMORE, 2289 ]; 2290 2291 /++ 2292 Delta typenum mappings for servers running the `InspIRCd` daemon. 2293 2294 - http://www.inspircd.org 2295 +/ 2296 static immutable Type[976] inspIRCd = 2297 [ 2298 270 : Type.RPL_MAPUSERS, 2299 304 : Type.RPL_SYNTAX, 2300 379 : Type.RPL_WHOWASIP, // also encountered as Type.RPL_WHOISMODES? 2301 495 : Type.ERR_DELAYREJOIN, 2302 501 : Type.ERR_UNKNOWNSNOMASK, 2303 702 : Type.RPL_COMMANDS, 2304 703 : Type.RPL_COMMANDSEND, 2305 953 : Type.ENDOFEXEMPTOPSLIST, 2306 972 : Type.ERR_CANTUNLOADMODULE, 2307 974 : Type.ERR_CANTLOADMODULE, 2308 975 : Type.RPL_LOADEDMODULE 2309 ]; 2310 2311 /++ 2312 Delta typenum mapping for servers running the `ultimate` daemon. 2313 Based off of `Bahamut`. 2314 +/ 2315 static immutable Type[624] ultimate = 2316 [ 2317 275 : Type.RPL_USINGSSL, 2318 386 : Type.RPL_IRCOPS, 2319 387 : Type.RPL_ENDOFIRCOPS, 2320 434 : Type.ERR_NORULES, 2321 610 : Type.RPL_ISOPER, 2322 615 : Type.RPL_WHOISMODES, 2323 616 : Type.RPL_WHOISHOST, 2324 617 : Type.RPL_WHOISBOT, 2325 619 : Type.RPL_WHOWASHOST, 2326 620 : Type.RPL_RULESSTART, 2327 621 : Type.RPL_RULES, 2328 622 : Type.RPL_ENDOFRULES, 2329 623 : Type.RPL_MAPMORE, 2330 ]; 2331 2332 /++ 2333 Delta typenum mappings extending `ircu` typenums, for UnderNet. 2334 2335 - https://github.com/UndernetIRC/ircu2 2336 +/ 2337 static immutable Type[490] undernet = 2338 [ 2339 396 : Type.RPL_HOSTHIDDEN, 2340 484 : Type.ERR_ISCHANSERVICE, 2341 489 : Type.ERR_VOICENEEDED, 2342 ]; 2343 2344 /++ 2345 Delta typenum mapping for servers running the `ratbox` daemon. It is 2346 primarily used on EFnet. 2347 2348 - https://www.ratbox.org 2349 +/ 2350 static immutable Type[716] ratBox = 2351 [ 2352 480 : Type.ERR_THROTTLE, 2353 485 : Type.ERR_BANNEDNICK, // deprecated 2354 702 : Type.RPL_MODLIST, 2355 703 : Type.RPL_ENDOFMODLIST, 2356 715 : Type.ERR_KNOCKDISABLED, 2357 ]; 2358 2359 /++ 2360 Delta typenum mappings for servers running the `charybdis` daemon. 2361 2362 - https://github.com/charybdis-ircd/charybdis 2363 +/ 2364 static immutable Type[495] charybdis = 2365 [ 2366 492 : Type.ERR_CANNOTSENDTOUSER, 2367 494 : Type.ERR_OWNMODE, 2368 ]; 2369 2370 /++ 2371 Delta typenum mappings for servers running the `sorircd` daemon 2372 (SorceryNet). 2373 2374 - http://www.nongnu.org/snservices/sorircd.html 2375 +/ 2376 static immutable Type[326] sorircd = 2377 [ 2378 325 : Type.RPL_CHANNELMLOCKIS, // deprecated 2379 ]; 2380 2381 /* 2382 static immutable Type[321] anothernet = 2383 [ 2384 320 : Type.RPL_WHOIS_HIDDEN, 2385 ]; 2386 2387 static immutable Type[392] bdqIRCd = 2388 [ 2389 391 : Type.RPL_TIME, 2390 ]; 2391 2392 static immutable Type[488] chatIRCd = 2393 [ 2394 487 : Type.ERR_NONONSSL, 2395 ]; 2396 2397 static immutable Type[515] irch = 2398 [ 2399 514 : Type.ERR_NOSUCHJUPE, 2400 ]; 2401 2402 static immutable Type[672] ithildin = 2403 [ 2404 672 : Type.RPL_UNKNOWNMODES, 2405 ]; 2406 */ 2407 } 2408 2409 2410 // IRCChannel 2411 /++ 2412 Aggregate personifying an IRC channel and its state. 2413 2414 An IRC channel may have a topic, a creation date, and one or more *modes*. 2415 Modes define how the channel behaves and how it treats its users, including 2416 which ones have operator and voice status, as well as which are banned, and more. 2417 +/ 2418 struct IRCChannel 2419 { 2420 /++ 2421 A channel mode. 2422 2423 Some modes overwrite themselves; a channel may be `+i` or `-i`, never 2424 `i` twice. Others stack; a channel may have an arbitrary number of `b` 2425 bans. We try our best to support both. 2426 +/ 2427 static struct Mode 2428 { 2429 /++ 2430 The character that implies this [Mode] (`i`, `z`, `l` ...). 2431 +/ 2432 char modechar; 2433 2434 /++ 2435 The data associated with the [Mode], if applicable. This is often a 2436 number, such as what `l` takes (join limit). 2437 +/ 2438 string data; 2439 2440 /++ 2441 The user associated with the [Mode], when it is not just [Mode.data|data]. 2442 +/ 2443 IRCUser user; 2444 2445 /++ 2446 The channel this mode refers to, where applicable. 2447 +/ 2448 string channel; 2449 2450 /++ 2451 Users that are explicitly exempt from the [Mode]. 2452 +/ 2453 IRCUser[] exceptions; 2454 2455 /++ 2456 Whether or not this [Mode] should be considered to be its own antithesis. 2457 +/ 2458 bool negated; 2459 2460 /++ 2461 Compare two [Mode]s with each other to see if they are both of the 2462 same type, as well as having the same [data] and/or [user]. 2463 2464 Params: 2465 that = Other [Mode] to compare this one with. 2466 2467 Returns: 2468 `true` if the [Mode]s match, `false` if not. 2469 +/ 2470 auto opEquals(const Mode that) const pure @safe nothrow @nogc 2471 { 2472 // Ignore exemptions when comparing Modes 2473 immutable charMatch = (this.modechar == that.modechar); 2474 immutable dataMatch = (this.data == that.data); 2475 immutable userMatch = (this.user == that.user); // IRCUser.opEquals 2476 immutable chanMatch = (this.channel == that.channel); 2477 2478 immutable match = (charMatch && dataMatch && userMatch && chanMatch); 2479 return negated ? !match : match; 2480 } 2481 2482 /++ 2483 Produces a hash for this [Mode]. 2484 2485 Returns: 2486 A hash. 2487 +/ 2488 auto toHash() const pure @safe 2489 { 2490 import std.conv : text; 2491 return text(modechar, data, user.hashOf, channel, negated).hashOf; 2492 } 2493 } 2494 2495 /++ 2496 The channel name. 2497 +/ 2498 string name; 2499 2500 /++ 2501 The current topic of the channel, as set by operators. 2502 +/ 2503 string topic; 2504 2505 /++ 2506 The current non-[data]-sporting [Mode]s of the channel. 2507 +/ 2508 string modechars; 2509 2510 /++ 2511 Array of all [Mode]s that are not simply represented in [modechars]. 2512 +/ 2513 Mode[] modes; 2514 2515 /++ 2516 Associative array of all the nicknames inhabiting the channel. 2517 +/ 2518 bool[string] users; 2519 2520 /++ 2521 Associative array of nicknames with a prefixing channel mode (operator, 2522 halfops, voiced, ...) keyed by modechar. 2523 +/ 2524 bool[string][char] mods; 2525 2526 /++ 2527 Template to deduplicate code for mods shorthands. 2528 2529 Params: 2530 prefix = Mode character. 2531 2532 Returns: 2533 A `bool[string]` hashmap of all users with the given mode character 2534 as keys. 2535 +/ 2536 ref bool[string] modsShorthand(char prefix)() 2537 { 2538 auto modsOp = prefix in mods; 2539 2540 if (!modsOp) 2541 { 2542 this.mods[prefix][string.init] = false; 2543 modsOp = prefix in this.mods; 2544 (*modsOp).remove(string.init); 2545 } 2546 2547 return *modsOp; 2548 } 2549 2550 /++ 2551 Array of channel operators. 2552 +/ 2553 alias ops = modsShorthand!'o'; 2554 2555 /++ 2556 Array of channel halfops. 2557 +/ 2558 alias halfops = modsShorthand!'h'; 2559 2560 /++ 2561 Array of voiced channel users. 2562 +/ 2563 alias voiced = modsShorthand!'v'; 2564 2565 /++ 2566 When the channel was created, expressed in UNIX time. 2567 +/ 2568 long created; 2569 } 2570 2571 2572 // IRCClient 2573 /++ 2574 Aggregate collecting all the relevant settings, options and state needed for 2575 a connection to an IRC server. 2576 2577 Many fields are transient and unfit to be saved to disk. 2578 +/ 2579 struct IRCClient 2580 { 2581 /++ 2582 Client nickname. 2583 +/ 2584 string nickname; // = "kameloso"; 2585 2586 /++ 2587 Client "user". 2588 +/ 2589 string user; // = "kameloso"; 2590 2591 /++ 2592 Client GECOS/"real name". 2593 +/ 2594 string realName; // = "kameloso IRC bot"; 2595 2596 @Unserialisable 2597 { 2598 /++ 2599 The original client nickname before connecting, in case it changed. 2600 +/ 2601 string origNickname; 2602 2603 /++ 2604 Client IDENT identifier. Defaults to "~`user`". 2605 Unused but keep for future expansion. 2606 +/ 2607 string ident; 2608 2609 version(TwitchSupport) 2610 { 2611 /++ 2612 Our Twitch display name or alias. 2613 +/ 2614 string displayName; 2615 } 2616 2617 /++ 2618 The current modechars active on the client (e.g. "ix"); 2619 +/ 2620 string modes; 2621 } 2622 }