]> git.netwichtig.de Git - user/henk/code/inspircd.git/blob - include/users.h
Provide error output on failure to load a core command; to console on startup, and...
[user/henk/code/inspircd.git] / include / users.h
1 /*       +------------------------------------+
2  *       | Inspire Internet Relay Chat Daemon |
3  *       +------------------------------------+
4  *
5  *  InspIRCd: (C) 2002-2007 InspIRCd Development Team
6  * See: http://www.inspircd.org/wiki/index.php/Credits
7  *
8  * This program is free but copyrighted software; see
9  *            the file COPYING for details.
10  *
11  * ---------------------------------------------------
12  */
13
14 #ifndef __USERS_H__
15 #define __USERS_H__
16
17 #include <string>
18 #include "inspircd_config.h"
19 #include "socket.h"
20 #include "channels.h"
21 #include "inspstring.h"
22 #include "connection.h"
23 #include "hashcomp.h"
24 #include "dns.h"
25
26 /** Channel status for a user
27  */
28 enum ChanStatus {
29         /** Op */
30         STATUS_OP     = 4,
31         /** Halfop */
32         STATUS_HOP    = 2,
33         /** Voice */
34         STATUS_VOICE  = 1,
35         /** None */
36         STATUS_NORMAL = 0
37 };
38
39 /** connect class types
40  */
41 enum ClassTypes {
42         /** connect:allow */
43         CC_ALLOW = 0,
44         /** connect:deny */
45         CC_DENY  = 1
46 };
47
48 /** RFC1459 channel modes
49  */
50 enum UserModes {
51         /** +s: Server notices */
52         UM_SERVERNOTICE = 's' - 65,
53         /** +w: WALLOPS */
54         UM_WALLOPS = 'w' - 65,
55         /** +i: Invisible */
56         UM_INVISIBLE = 'i' - 65,
57         /** +o: Operator */
58         UM_OPERATOR = 'o' - 65,
59         /** +n: Server notice mask */
60         UM_SNOMASK = 'n' - 65
61 };
62
63 /** Registration state of a user, e.g.
64  * have they sent USER, NICK, PASS yet?
65  */
66 enum RegistrationState {
67
68 #ifndef WIN32   // Burlex: This is already defined in win32, luckily it is still 0.
69         REG_NONE = 0,           /* Has sent nothing */
70 #endif
71
72         REG_USER = 1,           /* Has sent USER */
73         REG_NICK = 2,           /* Has sent NICK */
74         REG_NICKUSER = 3,       /* Bitwise combination of REG_NICK and REG_USER */
75         REG_ALL = 7             /* REG_NICKUSER plus next bit along */
76 };
77
78 /* Required forward declaration */
79 class InspIRCd;
80
81 /** Derived from Resolver, and performs user forward/reverse lookups.
82  */
83 class CoreExport UserResolver : public Resolver
84 {
85  private:
86         /** User this class is 'attached' to.
87          */
88         userrec* bound_user;
89         /** File descriptor teh lookup is bound to
90          */
91         int bound_fd;
92         /** True if the lookup is forward, false if is a reverse lookup
93          */
94         bool fwd;
95  public:
96         /** Create a resolver.
97          * @param Instance The creating instance
98          * @param user The user to begin lookup on
99          * @param to_resolve The IP or host to resolve
100          * @param qt The query type
101          * @param cache Modified by the constructor if the result was cached
102          */
103         UserResolver(InspIRCd* Instance, userrec* user, std::string to_resolve, QueryType qt, bool &cache);
104
105         /** Called on successful lookup
106          * @param result Result string
107          * @param ttl Time to live for result
108          * @param cached True if the result was found in the cache
109          */
110         void OnLookupComplete(const std::string &result, unsigned int ttl, bool cached);
111
112         /** Called on failed lookup
113          * @param e Error code
114          * @param errormessage Error message string
115          */
116         void OnError(ResolverError e, const std::string &errormessage);
117 };
118
119
120 /** Holds information relevent to &lt;connect allow&gt; and &lt;connect deny&gt; tags in the config file.
121  */
122 class CoreExport ConnectClass : public classbase
123 {
124  private:
125         /** Type of line, either CC_ALLOW or CC_DENY
126          */
127         char type;
128         /** Max time to register the connection in seconds
129          */
130         unsigned int registration_timeout;
131         /** Number of lines in buffer before excess flood is triggered
132          */
133         unsigned int flood;
134         /** Host mask for this line
135          */
136         std::string host;
137         /** Number of seconds between pings for this line
138          */
139         unsigned int pingtime;
140         /** (Optional) Password for this line
141          */
142         std::string pass;
143
144         /** Threshold value for flood disconnect
145          */
146         unsigned int threshold;
147
148         /** Maximum size of sendq for users in this class (bytes)
149          */
150         unsigned long sendqmax;
151
152         /** Maximum size of recvq for users in this class (bytes)
153          */
154         unsigned long recvqmax;
155
156         /** Local max when connecting by this connection class
157          */
158         unsigned long maxlocal;
159
160         /** Global max when connecting by this connection class
161          */
162         unsigned long maxglobal;
163         /** Port number this connect class applies to
164          */
165         int port;
166
167 public:
168
169         /** Create a new connect class with no settings.
170          */
171         ConnectClass() : type(CC_DENY), registration_timeout(0), flood(0), host(""), pingtime(0), pass(""),
172                         threshold(0), sendqmax(0), recvqmax(0), maxlocal(0), maxglobal(0) { }
173
174         /** Create a new connect class to ALLOW connections.
175          * @param timeout The registration timeout
176          * @param fld The flood value
177          * @param hst The IP mask to allow
178          * @param ping The ping frequency
179          * @param pas The password to be used
180          * @param thres The flooding threshold
181          * @param sendq The maximum sendq value
182          * @param recvq The maximum recvq value
183          * @param maxl The maximum local sessions
184          * @param maxg The maximum global sessions
185          */
186         ConnectClass(unsigned int timeout, unsigned int fld, const std::string &hst, unsigned int ping,
187                         const std::string &pas, unsigned int thres, unsigned long sendq, unsigned long recvq,
188                         unsigned long maxl, unsigned long maxg, int p = 0) :
189                         type(CC_ALLOW), registration_timeout(timeout), flood(fld), host(hst), pingtime(ping), pass(pas),
190                         threshold(thres), sendqmax(sendq), recvqmax(recvq), maxlocal(maxl), maxglobal(maxg), port(p) { }
191
192         /** Create a new connect class to DENY  connections
193          * @param hst The IP mask to deny
194          */
195         ConnectClass(const std::string &hst) : type(CC_DENY), registration_timeout(0), flood(0), host(hst), pingtime(0),
196                         pass(""), threshold(0), sendqmax(0), recvqmax(0), maxlocal(0), maxglobal(0), port(0) { }
197
198         /** Returns the type, CC_ALLOW or CC_DENY
199          */
200         char GetType()
201         {
202                 return (type == CC_ALLOW ? CC_ALLOW : CC_DENY);
203         }
204
205         /** Returns the registration timeout
206          */
207         unsigned int GetRegTimeout()
208         {
209                 return (registration_timeout ? registration_timeout : 90);
210         }
211
212         /** Returns the flood limit
213          */
214         unsigned int GetFlood()
215         {
216                 return (threshold ? flood : 999);
217         }
218
219         /** Returns the allowed or denied IP mask
220          */
221         const std::string& GetHost()
222         {
223                 return host;
224         }
225
226         int GetPort()
227         {
228                 return port;
229         }
230
231         /** Returns the ping frequency
232          */
233         unsigned int GetPingTime()
234         {
235                 return (pingtime ? pingtime : 120);
236         }
237
238         /** Returns the password or an empty string
239          */
240         const std::string& GetPass()
241         {
242                 return pass;
243         }
244
245         /** Returns the flood threshold value
246          */
247         unsigned int GetThreshold()
248         {
249                 return (threshold ? threshold : 1);
250         }
251
252         /** Returns the maximum sendq value
253          */
254         unsigned long GetSendqMax()
255         {
256                 return (sendqmax ? sendqmax : 262114);
257         }
258
259         /** Returns the maximum recvq value
260          */
261         unsigned long GetRecvqMax()
262         {
263                 return (recvqmax ? recvqmax : 4096);
264         }
265
266         /** Returusn the maximum number of local sessions
267          */
268         unsigned long GetMaxLocal()
269         {
270                 return maxlocal;
271         }
272
273         /** Returns the maximum number of global sessions
274          */
275         unsigned long GetMaxGlobal()
276         {
277                 return maxglobal;
278         }
279 };
280
281 /** Holds a complete list of all channels to which a user has been invited and has not yet joined.
282  */
283 typedef std::vector<irc::string> InvitedList;
284
285 /** Holds a complete list of all allow and deny tags from the configuration file (connection classes)
286  */
287 typedef std::vector<ConnectClass> ClassVector;
288
289 /** Typedef for the list of user-channel records for a user
290  */
291 typedef std::map<chanrec*, char> UserChanList;
292
293 /** Shorthand for an iterator into a UserChanList
294  */
295 typedef UserChanList::iterator UCListIter;
296
297 /* Required forward declaration
298  */
299 class userrec;
300
301 /** Visibility data for a user.
302  * If a user has a non-null instance of this class in their userrec,
303  * then it is used to determine if this user is visible to other users
304  * or not.
305  */
306 class CoreExport VisData
307 {
308  public:
309         /** Create a visdata
310          */
311         VisData();
312         /** Destroy a visdata
313          */
314         virtual ~VisData();
315         /** Is this user visible to some other user?
316          * @param user The other user to compare to
317          * @return true True if the user is visible to the other user, false if not
318          */
319         virtual bool VisibleTo(userrec* user);
320 };
321
322 /** Holds all information about a user
323  * This class stores all information about a user connected to the irc server. Everything about a
324  * connection is stored here primarily, from the user's socket ID (file descriptor) through to the
325  * user's nickname and hostname. Use the FindNick method of the InspIRCd class to locate a specific user
326  * by nickname, or the FindDescriptor method of the InspIRCd class to find a specific user by their
327  * file descriptor value.
328  */
329 class CoreExport userrec : public connection
330 {
331  private:
332         /** Pointer to creator.
333          * This is required to make use of core functions
334          * from within the userrec class.
335          */
336         InspIRCd* ServerInstance;
337
338         /** A list of channels the user has a pending invite to.
339          * Upon INVITE channels are added, and upon JOIN, the
340          * channels are removed from this list.
341          */
342         InvitedList invites;
343
344         /** Number of channels this user is currently on
345          */
346         unsigned int ChannelCount;
347
348         /** Cached nick!ident@host value using the real hostname
349          */
350         char* cached_fullhost;
351
352         /** Cached nick!ident@ip value using the real IP address
353          */
354         char* cached_hostip;
355
356         /** Cached nick!ident@host value using the masked hostname
357          */
358         char* cached_makehost;
359
360         /** Cached nick!ident@realhost value using the real hostname
361          */
362         char* cached_fullrealhost;
363
364         /** When we erase the user (in the destructor),
365          * we call this method to subtract one from all
366          * mode characters this user is making use of.
367          */
368         void DecrementModes();
369
370         /** Oper-only quit message for this user if non-null
371          */
372         char* operquit;
373
374  public:
375         /** Resolvers for looking up this users IP address
376          * This will occur if and when res_reverse completes.
377          * When this class completes its lookup, userrec::dns_done
378          * will be set from false to true.
379          */
380         UserResolver* res_forward;
381
382         /** Resolvers for looking up this users hostname
383          * This is instantiated by userrec::StartDNSLookup(),
384          * and on success, instantiates userrec::res_reverse.
385          */
386         UserResolver* res_reverse;
387
388         /** User visibility state, see definition of VisData.
389          */
390         VisData* Visibility;
391
392         /** Stored reverse lookup from res_forward
393          */
394         std::string stored_host;
395
396         /** Starts a DNS lookup of the user's IP.
397          * This will cause two UserResolver classes to be instantiated.
398          * When complete, these objects set userrec::dns_done to true.
399          */
400         void StartDNSLookup();
401
402         /** The users nickname.
403          * An invalid nickname indicates an unregistered connection prior to the NICK command.
404          * Use InspIRCd::IsNick() to validate nicknames.
405          */
406         char nick[NICKMAX];
407
408         /** The users ident reply.
409          * Two characters are added to the user-defined limit to compensate for the tilde etc.
410          */
411         char ident[IDENTMAX+2];
412
413         /** The host displayed to non-opers (used for cloaking etc).
414          * This usually matches the value of userrec::host.
415          */
416         char dhost[65];
417
418         /** The users full name (GECOS).
419          */
420         char fullname[MAXGECOS+1];
421
422         /** The user's mode list.
423          * This is NOT a null terminated string! In the 1.1 version of InspIRCd
424          * this is an array of values in a similar way to channel modes.
425          * A value of 1 in field (modeletter-65) indicates that the mode is
426          * set, for example, to work out if mode +s is set, we  check the field
427          * userrec::modes['s'-65] != 0.
428          * The following RFC characters o, w, s, i have constants defined via an
429          * enum, such as UM_SERVERNOTICE and UM_OPETATOR.
430          */
431         char modes[64];
432
433         /** What snomasks are set on this user.
434          * This functions the same as the above modes.
435          */
436         char snomasks[64];
437
438         /** Channels this user is on, and the permissions they have there
439          */
440         UserChanList chans;
441
442         /** The server the user is connected to.
443          */
444         const char* server;
445
446         /** The user's away message.
447          * If this string is empty, the user is not marked as away.
448          */
449         char awaymsg[MAXAWAY+1];
450
451         /** Number of lines the user can place into the buffer
452          * (up to the global NetBufferSize bytes) before they
453          * are disconnected for excess flood
454          */
455         int flood;
456
457         /** Timestamp of current time + connection class timeout.
458          * This user must send USER/NICK before this timestamp is
459          * reached or they will be disconnected.
460          */
461         time_t timeout;
462
463         /** The oper type they logged in as, if they are an oper.
464          * This is used to check permissions in operclasses, so that
465          * we can say 'yay' or 'nay' to any commands they issue.
466          * The value of this is the value of a valid 'type name=' tag.
467          */
468         char oper[NICKMAX];
469
470         /** True when DNS lookups are completed.
471          * The UserResolver classes res_forward and res_reverse will
472          * set this value once they complete.
473          */
474         bool dns_done;
475
476         /** Number of seconds between PINGs for this user (set from &lt;connect:allow&gt; tag
477          */
478         unsigned int pingmax;
479
480         /** Password specified by the user when they registered.
481          * This is stored even if the <connect> block doesnt need a password, so that
482          * modules may check it.
483          */
484         char password[64];
485
486         /** User's receive queue.
487          * Lines from the IRCd awaiting processing are stored here.
488          * Upgraded april 2005, old system a bit hairy.
489          */
490         std::string recvq;
491
492         /** User's send queue.
493          * Lines waiting to be sent are stored here until their buffer is flushed.
494          */
495         std::string sendq;
496
497         /** Flood counters - lines received
498          */
499         int lines_in;
500
501         /** Flood counters - time lines_in is due to be reset
502          */
503         time_t reset_due;
504
505         /** Flood counters - Highest value lines_in may reach before the user gets disconnected
506          */
507         long threshold;
508
509         /** If this is set to true, then all read operations for the user
510          * are dropped into the bit-bucket.
511          * This is used by the global CullList, but please note that setting this value
512          * alone will NOT cause the user to quit. This means it can be used seperately,
513          * for example by shun modules etc.
514          */
515         bool muted;
516
517         /** IPV4 or IPV6 ip address. Use SetSockAddr to set this and GetProtocolFamily/
518          * GetIPString/GetPort to obtain its values.
519          */
520         sockaddr* ip;
521
522         /** Initialize the clients sockaddr
523          * @param protocol_family The protocol family of the IP address, AF_INET or AF_INET6
524          * @param ip A human-readable IP address for this user matching the protcol_family
525          * @param port The port number of this user or zero for a remote user
526          */
527         void SetSockAddr(int protocol_family, const char* ip, int port);
528
529         /** Get port number from sockaddr
530          * @return The port number of this user.
531          */
532         int GetPort();
533
534         /** Get protocol family from sockaddr
535          * @return The protocol family of this user, either AF_INET or AF_INET6
536          */
537         int GetProtocolFamily();
538
539         /** Get IP string from sockaddr, using static internal buffer
540          * @return The IP string
541          */
542         const char* GetIPString();
543
544         /** Get IP string from sockaddr, using caller-specified buffer
545          * @param buf A buffer to use
546          * @return The IP string
547          */
548         const char* GetIPString(char* buf);
549
550         /* Write error string
551          */
552         std::string WriteError;
553
554         /** Maximum size this user's sendq can become.
555          * Copied from the connect class on connect.
556          */
557         long sendqmax;
558
559         /** Maximum size this user's recvq can become.
560          * Copied from the connect class on connect.
561          */
562         long recvqmax;
563
564         /** This is true if the user matched an exception when they connected to the ircd.
565          * It isnt valid after this point, and you should not attempt to do anything with it
566          * after this point, because the eline might be removed at a later time, and/or no
567          * longer be applicable to this user. It is only used to save doing the eline lookup
568          * twice (instead we do it once and set this value).
569          */
570         bool exempt;
571
572         /** Default constructor
573          * @throw Nothing at present
574          */
575         userrec(InspIRCd* Instance);
576
577         /** Returns the full displayed host of the user
578          * This member function returns the hostname of the user as seen by other users
579          * on the server, in nick!ident&at;host form.
580          * @return The full masked host of the user
581          */
582         virtual char* GetFullHost();
583
584         /** Returns the full real host of the user
585          * This member function returns the hostname of the user as seen by other users
586          * on the server, in nick!ident&at;host form. If any form of hostname cloaking is in operation,
587          * e.g. through a module, then this method will ignore it and return the true hostname.
588          * @return The full real host of the user
589          */
590         virtual char* GetFullRealHost();
591
592         /** This clears any cached results that are used for GetFullRealHost() etc.
593          * The results of these calls are cached as generating them can be generally expensive.
594          */
595         void InvalidateCache();
596
597         /** Create a displayable mode string for this users snomasks
598          * @return The notice mask character sequence
599          */
600         const char* FormatNoticeMasks();
601
602         /** Process a snomask modifier string, e.g. +abc-de
603          * @param sm A sequence of notice mask characters
604          * @return The cleaned mode sequence which can be output,
605          * e.g. in the above example if masks c and e are not
606          * valid, this function will return +ab-d
607          */
608         std::string ProcessNoticeMasks(const char *sm);
609
610         /** Returns true if a notice mask is set
611          * @param sm A notice mask character to check
612          * @return True if the notice mask is set
613          */
614         bool IsNoticeMaskSet(unsigned char sm);
615
616         /** Changed a specific notice mask value
617          * @param sm The server notice mask to change
618          * @param value An on/off value for this mask
619          */
620         void SetNoticeMask(unsigned char sm, bool value);
621
622         /** Create a displayable mode string for this users umodes
623          * @param The mode string
624          */
625         const char* FormatModes();
626
627         /** Returns true if a specific mode is set
628          * @param m The user mode
629          * @return True if the mode is set
630          */
631         bool IsModeSet(unsigned char m);
632
633         /** Set a specific usermode to on or off
634          * @param m The user mode
635          * @param value On or off setting of the mode
636          */
637         void SetMode(unsigned char m, bool value);
638
639         /** Returns true if a user is invited to a channel.
640          * @param channel A channel name to look up
641          * @return True if the user is invited to the given channel
642          */
643         virtual bool IsInvited(const irc::string &channel);
644
645         /** Adds a channel to a users invite list (invites them to a channel)
646          * @param channel A channel name to add
647          */
648         virtual void InviteTo(const irc::string &channel);
649
650         /** Removes a channel from a users invite list.
651          * This member function is called on successfully joining an invite only channel
652          * to which the user has previously been invited, to clear the invitation.
653          * @param channel The channel to remove the invite to
654          */
655         virtual void RemoveInvite(const irc::string &channel);
656
657         /** Returns true or false for if a user can execute a privilaged oper command.
658          * This is done by looking up their oper type from userrec::oper, then referencing
659          * this to their oper classes and checking the commands they can execute.
660          * @param command A command (should be all CAPS)
661          * @return True if this user can execute the command
662          */
663         bool HasPermission(const std::string &command);
664
665         /** Calls read() to read some data for this user using their fd.
666          * @param buffer The buffer to read into
667          * @param size The size of data to read
668          * @return The number of bytes read, or -1 if an error occured.
669          */
670         int ReadData(void* buffer, size_t size);
671
672         /** This method adds data to the read buffer of the user.
673          * The buffer can grow to any size within limits of the available memory,
674          * managed by the size of a std::string, however if any individual line in
675          * the buffer grows over 600 bytes in length (which is 88 chars over the
676          * RFC-specified limit per line) then the method will return false and the
677          * text will not be inserted.
678          * @param a The string to add to the users read buffer
679          * @return True if the string was successfully added to the read buffer
680          */
681         bool AddBuffer(std::string a);
682
683         /** This method returns true if the buffer contains at least one carriage return
684          * character (e.g. one complete line may be read)
685          * @return True if there is at least one complete line in the users buffer
686          */
687         bool BufferIsReady();
688
689         /** This function clears the entire buffer by setting it to an empty string.
690          */
691         void ClearBuffer();
692
693         /** This method returns the first available string at the tail end of the buffer
694          * and advances the tail end of the buffer past the string. This means it is
695          * a one way operation in a similar way to strtok(), and multiple calls return
696          * multiple lines if they are available. The results of this function if there
697          * are no lines to be read are unknown, always use BufferIsReady() to check if
698          * it is ok to read the buffer before calling GetBuffer().
699          * @return The string at the tail end of this users buffer
700          */
701         std::string GetBuffer();
702
703         /** Sets the write error for a connection. This is done because the actual disconnect
704          * of a client may occur at an inopportune time such as half way through /LIST output.
705          * The WriteErrors of clients are checked at a more ideal time (in the mainloop) and
706          * errored clients purged.
707          * @param error The error string to set.
708          */
709         void SetWriteError(const std::string &error);
710
711         /** Returns the write error which last occured on this connection or an empty string
712          * if none occured.
713          * @return The error string which has occured for this user
714          */
715         const char* GetWriteError();
716
717         /** Adds to the user's write buffer.
718          * You may add any amount of text up to this users sendq value, if you exceed the
719          * sendq value, SetWriteError() will be called to set the users error string to
720          * "SendQ exceeded", and further buffer adds will be dropped.
721          * @param data The data to add to the write buffer
722          */
723         void AddWriteBuf(const std::string &data);
724
725         /** Flushes as much of the user's buffer to the file descriptor as possible.
726          * This function may not always flush the entire buffer, rather instead as much of it
727          * as it possibly can. If the send() call fails to send the entire buffer, the buffer
728          * position is advanced forwards and the rest of the data sent at the next call to
729          * this method.
730          */
731         void FlushWriteBuf();
732
733         /** Returns the list of channels this user has been invited to but has not yet joined.
734          * @return A list of channels the user is invited to
735          */
736         InvitedList* GetInviteList();
737
738         /** Creates a wildcard host.
739          * Takes a buffer to use and fills the given buffer with the host in the format *!*@hostname
740          * @return The wildcarded hostname in *!*@host form
741          */
742         char* MakeWildHost();
743
744         /** Creates a usermask with real host.
745          * Takes a buffer to use and fills the given buffer with the hostmask in the format user@host
746          * @return the usermask in the format user@host
747          */
748         char* MakeHost();
749
750         /** Creates a usermask with real ip.
751          * Takes a buffer to use and fills the given buffer with the ipmask in the format user@ip
752          * @return the usermask in the format user@ip
753          */
754         char* MakeHostIP();
755
756         /** Shuts down and closes the user's socket
757          * This will not cause the user to be deleted. Use InspIRCd::QuitUser for this,
758          * which will call CloseSocket() for you.
759          */
760         void CloseSocket();
761
762         /** Disconnect a user gracefully
763          * @param user The user to remove
764          * @param r The quit reason to show to normal users
765          * @param oreason The quit reason to show to opers
766          * @return Although this function has no return type, on exit the user provided will no longer exist.
767          */
768         static void QuitUser(InspIRCd* Instance, userrec *user, const std::string &r, const char* oreason = "");
769
770         /** Add the user to WHOWAS system
771          */
772         void AddToWhoWas();
773
774         /** Oper up the user using the given opertype.
775          * This will also give the +o usermode.
776          * @param opertype The oper type to oper as
777          */
778         void Oper(const std::string &opertype);
779
780         /** Call this method to find the matching <connect> for a user, and to check them against it.
781          */
782         void CheckClass();
783
784         /** Use this method to fully connect a user.
785          * This will send the message of the day, check G/K/E lines, etc.
786          */
787         void FullConnect();
788
789         /** Change this users hash key to a new string.
790          * You should not call this function directly. It is used by the core
791          * to update the users hash entry on a nickchange.
792          * @param New new user_hash key
793          * @return Pointer to userrec in hash (usually 'this')
794          */
795         userrec* UpdateNickHash(const char* New);
796
797         /** Force a nickname change.
798          * If the nickname change fails (for example, because the nick in question
799          * already exists) this function will return false, and you must then either
800          * output an error message, or quit the user for nickname collision.
801          * @param newnick The nickname to change to
802          * @return True if the nickchange was successful.
803          */
804         bool ForceNickChange(const char* newnick);
805
806         /** Add a client to the system.
807          * This will create a new userrec, insert it into the user_hash,
808          * initialize it as not yet registered, and add it to the socket engine.
809          * @param Instance a pointer to the server instance
810          * @param socket The socket id (file descriptor) this user is on
811          * @param port The port number this user connected on
812          * @param iscached This variable is reserved for future use
813          * @param ip The IP address of the user
814          * @return This function has no return value, but a call to AddClient may remove the user.
815          */
816         static void AddClient(InspIRCd* Instance, int socket, int port, bool iscached, int socketfamily, sockaddr* ip);
817
818         /** Oper down.
819          * This will clear the +o usermode and unset the user's oper type
820          */
821         void UnOper();
822
823         /** Return the number of global clones of this user
824          * @return The global clone count of this user
825          */
826         unsigned long GlobalCloneCount();
827
828         /** Return the number of local clones of this user
829          * @return The local clone count of this user
830          */
831         unsigned long LocalCloneCount();
832
833         /** Remove all clone counts from the user, you should
834          * use this if you change the user's IP address in
835          * userrec::ip after they have registered.
836          */
837         void RemoveCloneCounts();
838
839         /** Write text to this user, appending CR/LF.
840          * @param text A std::string to send to the user
841          */
842         void Write(std::string text);
843
844         /** Write text to this user, appending CR/LF.
845          * @param text The format string for text to send to the user
846          * @param ... POD-type format arguments
847          */
848         void Write(const char *text, ...);
849
850         /** Write text to this user, appending CR/LF and prepending :server.name
851          * @param text A std::string to send to the user
852          */
853         void WriteServ(const std::string& text);
854
855         /** Write text to this user, appending CR/LF and prepending :server.name
856          * @param text The format string for text to send to the user
857          * @param ... POD-type format arguments
858          */
859         void WriteServ(const char* text, ...);
860
861         /** Write text to this user, appending CR/LF and prepending :nick!user@host of the user provided in the first parameter.
862          * @param user The user to prepend the :nick!user@host of
863          * @param text A std::string to send to the user
864          */
865         void WriteFrom(userrec *user, const std::string &text);
866
867         /** Write text to this user, appending CR/LF and prepending :nick!user@host of the user provided in the first parameter.
868          * @param user The user to prepend the :nick!user@host of
869          * @param text The format string for text to send to the user
870          * @param ... POD-type format arguments
871          */
872         void WriteFrom(userrec *user, const char* text, ...);
873
874         /** Write text to the user provided in the first parameter, appending CR/LF, and prepending THIS user's :nick!user@host.
875          * @param dest The user to route the message to
876          * @param text A std::string to send to the user
877          */
878         void WriteTo(userrec *dest, const std::string &data);
879
880         /** Write text to the user provided in the first parameter, appending CR/LF, and prepending THIS user's :nick!user@host.
881          * @param dest The user to route the message to
882          * @param text The format string for text to send to the user
883          * @param ... POD-type format arguments
884          */
885         void WriteTo(userrec *dest, const char *data, ...);
886
887         /** Write to all users that can see this user (including this user in the list), appending CR/LF
888          * @param text A std::string to send to the users
889          */
890         void WriteCommon(const std::string &text);
891
892         /** Write to all users that can see this user (including this user in the list), appending CR/LF
893          * @param text The format string for text to send to the users
894          * @param ... POD-type format arguments
895          */
896         void WriteCommon(const char* text, ...);
897
898         /** Write to all users that can see this user (not including this user in the list), appending CR/LF
899          * @param text The format string for text to send to the users
900          * @param ... POD-type format arguments
901          */
902         void WriteCommonExcept(const char* text, ...);
903
904         /** Write to all users that can see this user (not including this user in the list), appending CR/LF
905          * @param text A std::string to send to the users
906          */
907         void WriteCommonExcept(const std::string &text);
908
909         /** Write a quit message to all common users, as in userrec::WriteCommonExcept but with a specific
910          * quit message for opers only.
911          * @param normal_text Normal user quit message
912          * @param oper_text Oper only quit message
913          */
914         void WriteCommonQuit(const std::string &normal_text, const std::string &oper_text);
915
916         /** Write a WALLOPS message from this user to all local opers.
917          * If this user is not opered, the function will return without doing anything.
918          * @param text The format string to send in the WALLOPS message
919          * @param ... Format arguments
920          */
921         void WriteWallOps(const char* text, ...);
922
923         /** Write a WALLOPS message from this user to all local opers.
924          * If this user is not opered, the function will return without doing anything.
925          * @param text The text to send in the WALLOPS message
926          */
927         void WriteWallOps(const std::string &text);
928
929         /** Return true if the user shares at least one channel with another user
930          * @param other The other user to compare the channel list against
931          * @return True if the given user shares at least one channel with this user
932          */
933         bool SharesChannelWith(userrec *other);
934
935         /** Change the displayed host of a user.
936          * ALWAYS use this function, rather than writing userrec::dhost directly,
937          * as this triggers module events allowing the change to be syncronized to
938          * remote servers. This will also emulate a QUIT and rejoin (where configured)
939          * before setting their host field.
940          * @param host The new hostname to set
941          * @return True if the change succeeded, false if it didn't
942          */
943         bool ChangeDisplayedHost(const char* host);
944
945         /** Change the ident (username) of a user.
946          * ALWAYS use this function, rather than writing userrec::ident directly,
947          * as this correctly causes the user to seem to quit (where configured)
948          * before setting their ident field.
949          * @param host The new ident to set
950          * @return True if the change succeeded, false if it didn't
951          */
952         bool ChangeIdent(const char* newident);
953
954         /** Change a users realname field.
955          * ALWAYS use this function, rather than writing userrec::fullname directly,
956          * as this triggers module events allowing the change to be syncronized to
957          * remote servers.
958          * @param gecos The user's new realname
959          * @return True if the change succeeded, false if otherwise
960          */
961         bool ChangeName(const char* gecos);
962
963         /** Send a command to all local users from this user
964          * The command given must be able to send text with the
965          * first parameter as a servermask (e.g. $*), so basically
966          * you should use PRIVMSG or NOTICE.
967          * @param command the command to send
968          * @param text The text format string to send
969          * @param ... Format arguments
970          */
971         void SendAll(const char* command, char* text, ...);
972
973         /** Compile a channel list for this user, and send it to the user 'source'
974          * Used internally by WHOIS
975          * @param The user to send the channel list to if it is not too long
976          * @return This user's channel list
977          */
978         std::string ChannelList(userrec* source);
979
980         /** Split the channel list in cl which came from dest, and spool it to this user
981          * Used internally by WHOIS
982          * @param dest The user the original channel list came from
983          * @param cl The  channel list as a string obtained from userrec::ChannelList()
984          */
985         void SplitChanList(userrec* dest, const std::string &cl);
986
987         /** Remove this user from all channels they are on, and delete any that are now empty.
988          * This is used by QUIT, and will not send part messages!
989          */
990         void PurgeEmptyChannels();
991
992         /** Get the connect class which matches this user's host or IP address
993          * @return A reference to this user's connect class
994          */
995         ConnectClass* GetClass();
996
997         /** Show the message of the day to this user
998          */
999         void ShowMOTD();
1000
1001         /** Show the server RULES file to this user
1002          */
1003         void ShowRULES();
1004
1005         /** Set oper-specific quit message shown to opers only when the user quits
1006          * (overrides any sent by QuitUser)
1007          */
1008         void SetOperQuit(const std::string &oquit);
1009
1010         /** Get oper-specific quit message shown only to opers when the user quits.
1011          * (overrides any sent by QuitUser)
1012          */
1013         const char* GetOperQuit();
1014
1015         /** Handle socket event.
1016          * From EventHandler class.
1017          * @param et Event type
1018          * @param errornum Error number for EVENT_ERROR events
1019          */
1020         void HandleEvent(EventType et, int errornum = 0);
1021
1022         /** Default destructor
1023          */
1024         virtual ~userrec();
1025 };
1026
1027 /* Configuration callbacks */
1028 class ServerConfig;
1029
1030 #endif
1031