ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/svn/ircd-hybrid/branches/8.2.x/modules/m_whois.c
Revision: 4617
Committed: Sun Sep 7 13:00:55 2014 UTC (11 years, 10 months ago) by michael
Content type: text/x-csrc
File size: 9780 byte(s)
Log Message:
- Renamed Channel::chname to Channel::name

File Contents

# User Rev Content
1 adx 30 /*
2 michael 2820 * ircd-hybrid: an advanced, lightweight Internet Relay Chat Daemon (ircd)
3 adx 30 *
4 michael 2820 * Copyright (c) 1997-2014 ircd-hybrid development team
5 adx 30 *
6     * This program is free software; you can redistribute it and/or modify
7     * it under the terms of the GNU General Public License as published by
8     * the Free Software Foundation; either version 2 of the License, or
9     * (at your option) any later version.
10     *
11     * This program is distributed in the hope that it will be useful,
12     * but WITHOUT ANY WARRANTY; without even the implied warranty of
13     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14     * GNU General Public License for more details.
15     *
16     * You should have received a copy of the GNU General Public License
17     * along with this program; if not, write to the Free Software
18 michael 4564 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301
19 adx 30 * USA
20     */
21    
22 michael 2820 /*! \file m_whois.c
23     * \brief Includes required functions for processing the WHOIS command.
24     * \version $Id$
25     */
26    
27 adx 30 #include "stdinc.h"
28 michael 1011 #include "list.h"
29 adx 30 #include "client.h"
30     #include "hash.h"
31     #include "channel.h"
32     #include "channel_mode.h"
33     #include "ircd.h"
34     #include "numeric.h"
35 michael 1309 #include "conf.h"
36 michael 3347 #include "misc.h"
37     #include "server.h"
38     #include "user.h"
39 adx 30 #include "send.h"
40     #include "irc_string.h"
41     #include "parse.h"
42     #include "modules.h"
43    
44 michael 1243
45 michael 3514 static int
46     whois_can_see_channels(struct Channel *chptr,
47     struct Client *source_p,
48     struct Client *target_p)
49     {
50     if (PubChannel(chptr) && !HasUMode(target_p, UMODE_HIDECHANS))
51     return 1;
52    
53     if (source_p == target_p || IsMember(source_p, chptr))
54     return 1;
55    
56     if (HasUMode(source_p, UMODE_ADMIN))
57     return 2;
58     return 0;
59     }
60    
61 adx 30 /* whois_person()
62     *
63     * inputs - source_p client to report to
64     * - target_p client to report on
65     * output - NONE
66     * side effects -
67     */
68     static void
69     whois_person(struct Client *source_p, struct Client *target_p)
70     {
71 michael 3215 char buf[IRCD_BUFSIZE] = "";
72 michael 1874 const dlink_node *lp = NULL;
73     char *t = NULL;
74 adx 30 int cur_len = 0;
75 michael 1874 int show_ip = 0;
76     int mlen = 0;
77     int tlen = 0;
78 michael 1243 int reply_to_send = 0;
79 adx 30
80 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISUSER, target_p->name,
81     target_p->username, target_p->host,
82     target_p->info);
83 adx 30
84 michael 3109 cur_len = mlen = snprintf(buf, sizeof(buf), numeric_form(RPL_WHOISCHANNELS),
85 michael 1233 me.name, source_p->name, target_p->name, "");
86 adx 30 t = buf + mlen;
87    
88     DLINK_FOREACH(lp, target_p->channel.head)
89     {
90 michael 1874 const struct Membership *ms = lp->data;
91 michael 3514 int show = whois_can_see_channels(ms->chptr, source_p, target_p);
92 adx 30
93 michael 3514 if (show)
94 adx 30 {
95 michael 4617 if ((cur_len + 4 + strlen(ms->chptr->name) + 1) > (IRCD_BUFSIZE - 2))
96 adx 30 {
97 michael 2224 *(t - 1) = '\0';
98     sendto_one(source_p, "%s", buf);
99     cur_len = mlen;
100     t = buf + mlen;
101 adx 30 }
102    
103 michael 3514 tlen = sprintf(t, "%s%s%s ", show == 2 ? "~" : "", get_member_status(ms, 1),
104 michael 4617 ms->chptr->name);
105 adx 30 t += tlen;
106     cur_len += tlen;
107 michael 1243 reply_to_send = 1;
108 adx 30 }
109     }
110    
111     if (reply_to_send)
112     {
113     *(t - 1) = '\0';
114     sendto_one(source_p, "%s", buf);
115     }
116    
117 michael 2748 if ((ConfigServerHide.hide_servers || IsHidden(target_p->servptr)) &&
118     !(HasUMode(source_p, UMODE_OPER) || target_p == source_p))
119 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISSERVER, target_p->name,
120     ConfigServerHide.hidden_name,
121 michael 4341 ConfigServerInfo.network_desc);
122 adx 30 else
123 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISSERVER, target_p->name,
124     target_p->servptr->name, target_p->servptr->info);
125 adx 30
126 michael 1164 if (HasUMode(target_p, UMODE_REGISTERED))
127 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISREGNICK, target_p->name);
128 michael 1158
129 michael 2478 if (!IsDigit(target_p->svid[0]))
130 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISACCOUNT, target_p->name,
131     target_p->svid);
132 michael 2478
133 michael 1483 if (target_p->away[0])
134 michael 3109 sendto_one_numeric(source_p, &me, RPL_AWAY, target_p->name,
135     target_p->away);
136 adx 30
137 michael 2580 if (HasUMode(target_p, UMODE_CALLERID|UMODE_SOFTCALLERID))
138     {
139     int callerid = !!HasUMode(target_p, UMODE_CALLERID);
140 michael 3109
141     sendto_one_numeric(source_p, &me, RPL_TARGUMODEG, target_p->name,
142     callerid ? "+g" : "+G",
143     callerid ? "server side ignore" :
144     "server side ignore with the exception of common channels");
145 michael 2580 }
146 adx 660
147 michael 1219 if (HasUMode(target_p, UMODE_OPER))
148 michael 1294 if (!HasUMode(target_p, UMODE_HIDDEN) || HasUMode(source_p, UMODE_OPER))
149 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISOPERATOR, target_p->name,
150 michael 2727 HasUMode(target_p, UMODE_ADMIN) ? "is a Server Administrator" :
151     "is an IRC Operator");
152 adx 30
153 michael 2511 if (HasUMode(target_p, UMODE_WEBIRC))
154 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISTEXT, target_p->name,
155     "User connected using a webirc gateway");
156 michael 2511
157 michael 2529 if (HasUMode(source_p, UMODE_ADMIN) || source_p == target_p)
158     {
159     char *m = buf;
160     *m++ = '+';
161    
162 michael 3283 for (unsigned int i = 0; i < 128; ++i)
163 michael 2529 if (HasUMode(target_p, user_modes[i]))
164     *m++ = (char)i;
165     *m = '\0';
166    
167 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISMODES, target_p->name, buf);
168 michael 2529 }
169    
170 michael 1811 if (target_p->sockhost[0] && strcmp(target_p->sockhost, "0"))
171 adx 30 {
172 michael 1547 if (HasUMode(source_p, UMODE_ADMIN) || source_p == target_p)
173     show_ip = 1;
174     else if (IsIPSpoof(target_p))
175 michael 4341 show_ip = (HasUMode(source_p, UMODE_OPER) && !ConfigGeneral.hide_spoof_ips);
176 michael 1547 else
177     show_ip = 1;
178 db 280
179 michael 3109
180     sendto_one_numeric(source_p, &me, RPL_WHOISACTUALLY, target_p->name,
181     show_ip ? target_p->sockhost : "255.255.255.255");
182 adx 30 }
183    
184 michael 2246 if (HasUMode(target_p, UMODE_SSL))
185 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISSECURE, target_p->name);
186 michael 2246
187 michael 2229 if (!EmptyString(target_p->certfp))
188 michael 2536 if (target_p == source_p || HasUMode(source_p, UMODE_ADMIN))
189 michael 3109 sendto_one_numeric(source_p, &me, RPL_WHOISCERTFP, target_p->name, target_p->certfp);
190 michael 2229
191 michael 1997 if (MyConnect(target_p))
192 michael 3507 if (!HasUMode(target_p, UMODE_HIDEIDLE) || HasUMode(source_p, UMODE_OPER) ||
193     source_p == target_p)
194     sendto_one_numeric(source_p, &me, RPL_WHOISIDLE, target_p->name,
195     idle_time_get(source_p, target_p),
196 michael 4589 target_p->connection->firsttime);
197 adx 30 }
198 michael 1230
199 michael 1997 /* do_whois()
200     *
201     * inputs - pointer to /whois source
202     * - number of parameters
203     * - pointer to parameters array
204     * output - pointer to void
205     * side effects - Does whois
206     */
207     static void
208 michael 2354 do_whois(struct Client *source_p, const char *name)
209 michael 1997 {
210     struct Client *target_p = NULL;
211    
212 michael 3160 if ((target_p = find_person(source_p, name)))
213 michael 1997 whois_person(source_p, target_p);
214 michael 2354 else if (!IsDigit(*name))
215 michael 3109 sendto_one_numeric(source_p, &me, ERR_NOSUCHNICK, name);
216 michael 1997
217 michael 3109 sendto_one_numeric(source_p, &me, RPL_ENDOFWHOIS, name);
218 michael 1997 }
219    
220 michael 3295 /*! \brief WHOIS command handler
221     *
222     * \param source_p Pointer to allocated Client struct from which the message
223     * originally comes from. This can be a local or remote client.
224     * \param parc Integer holding the number of supplied arguments.
225     * \param parv Argument vector where parv[0] .. parv[parc-1] are non-NULL
226     * pointers.
227     * \note Valid arguments for this command are:
228     * - parv[0] = command
229     * - parv[1] = nickname/servername
230     * - parv[2] = nickname
231     */
232 michael 2820 static int
233 michael 3156 m_whois(struct Client *source_p, int parc, char *parv[])
234 michael 1997 {
235     static time_t last_used = 0;
236    
237     if (parc < 2 || EmptyString(parv[1]))
238     {
239 michael 3109 sendto_one_numeric(source_p, &me, ERR_NONICKNAMEGIVEN);
240 michael 2820 return 0;
241 michael 1997 }
242    
243     if (parc > 2 && !EmptyString(parv[2]))
244     {
245     /* seeing as this is going across servers, we should limit it */
246 michael 4341 if ((last_used + ConfigGeneral.pace_wait_simple) > CurrentTime)
247 michael 1997 {
248 michael 3109 sendto_one_numeric(source_p, &me, RPL_LOAD2HI);
249 michael 2820 return 0;
250 michael 1997 }
251    
252     last_used = CurrentTime;
253    
254     /*
255     * if we have serverhide enabled, they can either ask the clients
256 michael 4299 * server, or our server.. I don't see why they would need to ask
257 michael 1997 * anything else for info about the client.. --fl_
258     */
259 michael 2196 if (ConfigServerHide.disable_remote_commands)
260 michael 1997 parv[1] = parv[2];
261    
262 michael 3156 if (hunt_server(source_p, ":%s WHOIS %s :%s", 1,
263 michael 1997 parc, parv) != HUNTED_ISME)
264 michael 2820 return 0;
265 michael 1997
266     parv[1] = parv[2];
267     }
268    
269 michael 2354 do_whois(source_p, parv[1]);
270 michael 2820 return 0;
271 michael 1997 }
272    
273 michael 3295 /*! \brief WHOIS command handler
274     *
275     * \param source_p Pointer to allocated Client struct from which the message
276     * originally comes from. This can be a local or remote client.
277     * \param parc Integer holding the number of supplied arguments.
278     * \param parv Argument vector where parv[0] .. parv[parc-1] are non-NULL
279     * pointers.
280     * \note Valid arguments for this command are:
281     * - parv[0] = command
282     * - parv[1] = nickname/servername
283     * - parv[2] = nickname
284     */
285 michael 2820 static int
286 michael 3156 mo_whois(struct Client *source_p, int parc, char *parv[])
287 michael 1997 {
288     if (parc < 2 || EmptyString(parv[1]))
289     {
290 michael 3109 sendto_one_numeric(source_p, &me, ERR_NONICKNAMEGIVEN);
291 michael 2820 return 0;
292 michael 1997 }
293    
294     if (parc > 2 && !EmptyString(parv[2]))
295     {
296 michael 3156 if (hunt_server(source_p, ":%s WHOIS %s :%s", 1,
297 michael 1997 parc, parv) != HUNTED_ISME)
298 michael 2820 return 0;
299 michael 1997
300     parv[1] = parv[2];
301     }
302    
303 michael 2354 do_whois(source_p, parv[1]);
304 michael 2820 return 0;
305 michael 1997 }
306    
307 michael 2820 static struct Message whois_msgtab =
308     {
309 michael 4546 "WHOIS", NULL, 0, 0, 0, MAXPARA, MFLG_SLOW, 0,
310 michael 1230 { m_unregistered, m_whois, mo_whois, m_ignore, mo_whois, m_ignore }
311     };
312    
313     static void
314     module_init(void)
315     {
316     mod_add_cmd(&whois_msgtab);
317     }
318    
319     static void
320     module_exit(void)
321     {
322     mod_del_cmd(&whois_msgtab);
323     }
324    
325 michael 2820 struct module module_entry =
326     {
327 michael 1230 .node = { NULL, NULL, NULL },
328     .name = NULL,
329     .version = "$Revision$",
330     .handle = NULL,
331     .modinit = module_init,
332     .modexit = module_exit,
333     .flags = 0
334     };

Properties

Name Value
svn:eol-style native
svn:keywords Id Revision