]> arthur.barton.de Git - ngircd-alex.git/blobdiff - src/ngircd/irc-info.c
Streamline effect of "MorePrivacy" option (WHOIS, LIST)
[ngircd-alex.git] / src / ngircd / irc-info.c
index aa98a5b560b163f4b96a5b4c7b1a20b7f4f6f2f3..1bbaf57b3b53a35e905be647c5f075690ade38ac 100644 (file)
@@ -1,6 +1,6 @@
 /*
  * ngIRCd -- The Next Generation IRC Daemon
- * Copyright (c)2001-2013 Alexander Barton (alex@barton.de) and Contributors.
+ * Copyright (c)2001-2014 Alexander Barton (alex@barton.de) and Contributors.
  *
  * This program is free software; you can redistribute it and/or modify
  * it under the terms of the GNU General Public License as published by
  * IRC info commands
  */
 
-#include "imp.h"
 #include <assert.h>
-#include <errno.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
 #include <strings.h>
+#include <time.h>
 
 #include "ngircd.h"
 #include "conn-func.h"
 #include "channel.h"
 #include "class.h"
 #include "conf.h"
-#include "defines.h"
 #include "lists.h"
-#include "log.h"
 #include "messages.h"
 #include "match.h"
-#include "tool.h"
 #include "parse.h"
 #include "irc.h"
 #include "irc-macros.h"
@@ -43,7 +39,6 @@
 #include "client-cap.h"
 #include "op.h"
 
-#include "exp.h"
 #include "irc-info.h"
 
 /* Local functions */
@@ -167,7 +162,7 @@ IRC_WHO_Channel(CLIENT *Client, CHANNEL *Chan, bool OnlyOps)
                if (OnlyOps && !is_ircop)
                        continue;
 
-               is_visible = Client_HasMode(c, 'i');
+               is_visible = !Client_HasMode(c, 'i');
                if (is_member || is_visible) {
                        memset(flags, 0, sizeof(flags));
 
@@ -318,48 +313,50 @@ IRC_WHOIS_SendReply(CLIENT *Client, CLIENT *from, CLIENT *c)
                                Client_Info(Client_Introducer(c))))
                return DISCONNECTED;
 
-       /* Channels */
-       snprintf(str, sizeof(str), RPL_WHOISCHANNELS_MSG,
-                Client_ID(from), Client_ID(c));
-       cl2chan = Channel_FirstChannelOf(c);
-       while (cl2chan) {
-               chan = Channel_GetChannel(cl2chan);
-               assert(chan != NULL);
-
-               /* next */
-               cl2chan = Channel_NextChannelOf(c, cl2chan);
-
-               /* Secret channel? */
-               if (Channel_HasMode(chan, 's')
-                   && !Channel_IsMemberOf(chan, Client))
-                       continue;
+       /* Channels, show only if client has no +I or if from is oper */
+       if(!(Client_HasMode(c, 'I')) || Client_HasMode(from, 'o'))  {
+               snprintf(str, sizeof(str), RPL_WHOISCHANNELS_MSG,
+                        Client_ID(from), Client_ID(c));
+               cl2chan = Channel_FirstChannelOf(c);
+               while (cl2chan) {
+                       chan = Channel_GetChannel(cl2chan);
+                       assert(chan != NULL);
+
+                       /* next */
+                       cl2chan = Channel_NextChannelOf(c, cl2chan);
+
+                       /* Secret channel? */
+                       if (Channel_HasMode(chan, 's')
+                           && !Channel_IsMemberOf(chan, Client))
+                               continue;
 
-               /* Local channel and request is not from a user? */
-               if (Client_Type(Client) == CLIENT_SERVER
-                   && Channel_IsLocal(chan))
-                       continue;
+                       /* Local channel and request is not from a user? */
+                       if (Client_Type(Client) == CLIENT_SERVER
+                           && Channel_IsLocal(chan))
+                               continue;
 
-               /* Concatenate channel names */
-               if (str[strlen(str) - 1] != ':')
-                       strlcat(str, " ", sizeof(str));
+                       /* Concatenate channel names */
+                       if (str[strlen(str) - 1] != ':')
+                               strlcat(str, " ", sizeof(str));
 
-               who_flags_qualifier(Client, Channel_UserModes(chan, c),
-                                   str, sizeof(str));
-               strlcat(str, Channel_Name(chan), sizeof(str));
+                       who_flags_qualifier(Client, Channel_UserModes(chan, c),
+                                           str, sizeof(str));
+                       strlcat(str, Channel_Name(chan), sizeof(str));
 
-               if (strlen(str) > (COMMAND_LEN - CHANNEL_NAME_LEN - 4)) {
-                       /* Line becomes too long: send it! */
+                       if (strlen(str) > (COMMAND_LEN - CHANNEL_NAME_LEN - 4)) {
+                               /* Line becomes too long: send it! */
+                               if (!IRC_WriteStrClient(Client, "%s", str))
+                                       return DISCONNECTED;
+                               snprintf(str, sizeof(str), RPL_WHOISCHANNELS_MSG,
+                                        Client_ID(from), Client_ID(c));
+                       }
+               }
+               if(str[strlen(str) - 1] != ':') {
+                       /* There is data left to send: */
                        if (!IRC_WriteStrClient(Client, "%s", str))
                                return DISCONNECTED;
-                       snprintf(str, sizeof(str), RPL_WHOISCHANNELS_MSG,
-                                Client_ID(from), Client_ID(c));
                }
        }
-       if(str[strlen(str) - 1] != ':') {
-               /* There is data left to send: */
-               if (!IRC_WriteStrClient(Client, "%s", str))
-                       return DISCONNECTED;
-       }
 
        /* IRC-Services? */
        if (Client_Type(c) == CLIENT_SERVICE &&
@@ -401,9 +398,16 @@ IRC_WHOIS_SendReply(CLIENT *Client, CLIENT *from, CLIENT *c)
                                Client_ID(from), Client_ID(c)))
                return DISCONNECTED;
 
+       /* Account name metadata? */
+       if (Client_AccountName(c) &&
+           !IRC_WriteStrClient(from, RPL_WHOISLOGGEDIN_MSG,
+                               Client_ID(from), Client_ID(c),
+                               Client_AccountName(c)))
+               return DISCONNECTED;
+
        /* Local client and requester is the user itself or an IRC Op? */
        if (Client_Conn(c) > NONE &&
-           (from == c || (!Conf_MorePrivacy && Client_HasMode(from, 'o')))) {
+           (from == c || Client_HasMode(from, 'o'))) {
                /* Client hostname */
                if (!IRC_WriteStrClient(from, RPL_WHOISHOST_MSG,
                                        Client_ID(from), Client_ID(c),
@@ -1099,10 +1103,19 @@ IRC_VERSION( CLIENT *Client, REQUEST *Req )
        }
 
        /* send version information */
-       return IRC_WriteStrClient(Client, RPL_VERSION_MSG, Client_ID(prefix),
-                                 PACKAGE_NAME, PACKAGE_VERSION,
-                                 NGIRCd_DebugLevel, Conf_ServerName,
-                                 NGIRCd_VersionAddition);
+       if (!IRC_WriteStrClient(Client, RPL_VERSION_MSG, Client_ID(prefix),
+                               PACKAGE_NAME, PACKAGE_VERSION,
+                               NGIRCd_DebugLevel, Conf_ServerName,
+                               NGIRCd_VersionAddition))
+               return DISCONNECTED;
+
+#ifndef STRICT_RFC
+       /* send RPL_ISUPPORT(005) numerics */
+       if (!IRC_Send_ISUPPORT(prefix))
+               return DISCONNECTED;
+#endif
+
+       return CONNECTED;
 } /* IRC_VERSION */
 
 /**