ViewVC Help
View File | Revision Log | Show Annotations | View Changeset | Root Listing
root/svn/ircd-hybrid/trunk/modules/m_set.c
Revision: 1155
Committed: Tue Aug 9 20:27:45 2011 UTC (14 years ago) by michael
Content type: text/x-csrc
Original Path: ircd-hybrid/modules/m_set.c
File size: 18564 byte(s)
Log Message:
- recreate "trunk"

File Contents

# User Rev Content
1 adx 30 /*
2     * ircd-hybrid: an advanced Internet Relay Chat Daemon(ircd).
3     * m_set.c: Sets a server parameter.
4     *
5     * Copyright (C) 2002 by the past and present ircd coders, and others.
6     *
7     * This program is free software; you can redistribute it and/or modify
8     * it under the terms of the GNU General Public License as published by
9     * the Free Software Foundation; either version 2 of the License, or
10     * (at your option) any later version.
11     *
12     * This program is distributed in the hope that it will be useful,
13     * but WITHOUT ANY WARRANTY; without even the implied warranty of
14     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15     * GNU General Public License for more details.
16     *
17     * You should have received a copy of the GNU General Public License
18     * along with this program; if not, write to the Free Software
19     * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
20     * USA
21     *
22 knight 31 * $Id$
23 adx 30 */
24    
25     /* rewritten by jdc */
26    
27     #include "stdinc.h"
28     #include "handlers.h"
29     #include "client.h"
30     #include "event.h"
31     #include "irc_string.h"
32     #include "ircd.h"
33     #include "numeric.h"
34     #include "fdlist.h"
35     #include "s_bsd.h"
36     #include "s_serv.h"
37     #include "send.h"
38     #include "common.h" /* for NO */
39     #include "channel.h"
40     #include "s_log.h"
41     #include "s_conf.h"
42     #include "msg.h"
43     #include "parse.h"
44     #include "modules.h"
45     #include "s_user.h"
46    
47    
48     static void mo_set(struct Client *, struct Client *, int, char *[]);
49    
50     struct Message set_msgtab = {
51     "SET", 0, 0, 0, 0, MFLG_SLOW, 0,
52 michael 946 {m_unregistered, m_not_oper, rfc1459_command_send_error, m_ignore, mo_set, m_ignore}
53 adx 30 };
54    
55     void
56     _modinit(void)
57     {
58     mod_add_cmd(&set_msgtab);
59     }
60    
61     void
62     _moddeinit(void)
63     {
64     mod_del_cmd(&set_msgtab);
65     }
66    
67 knight 31 const char *_version = "$Revision$";
68 adx 30
69     /* Structure used for the SET table itself */
70     struct SetStruct
71     {
72     const char *name;
73     void (*handler)();
74 michael 1013 const int wants_char; /* 1 if it expects (char *, [int]) */
75     const int wants_int; /* 1 if it expects ([char *], int) */
76 adx 30 /* eg: 0, 1 == only an int arg
77     * eg: 1, 1 == char and int args */
78     };
79    
80     static void quote_autoconn(struct Client *, const char *, int);
81     static void quote_autoconnall(struct Client *, int);
82     static void quote_floodcount(struct Client *, int);
83     static void quote_identtimeout(struct Client *, int);
84     static void quote_idletime(struct Client *, int);
85     static void quote_log(struct Client *, int);
86     static void quote_max(struct Client *, int);
87     static void quote_msglocale(struct Client *, char *);
88     static void quote_spamnum(struct Client *, int);
89     static void quote_spamtime(struct Client *, int);
90     static void quote_splitmode(struct Client *, char *);
91     static void quote_splitnum(struct Client *, int);
92     static void quote_splitusers(struct Client *, int);
93     static void list_quote_commands(struct Client *);
94     static void quote_jfloodtime(struct Client *, int);
95     static void quote_jfloodcount(struct Client *, int);
96     static void quote_rejecttime(struct Client *, int);
97    
98     /*
99     * If this ever needs to be expanded to more than one arg of each
100     * type, want_char/want_int could be the count of the arguments,
101     * instead of just a boolean flag...
102     *
103     * -davidt
104     */
105    
106 michael 1013 static const struct SetStruct set_cmd_table[] =
107 adx 30 {
108     /* name function string arg int arg */
109     /* -------------------------------------------------------- */
110     { "AUTOCONN", quote_autoconn, 1, 1 },
111     { "AUTOCONNALL", quote_autoconnall, 0, 1 },
112     { "FLOODCOUNT", quote_floodcount, 0, 1 },
113     { "IDENTTIMEOUT", quote_identtimeout, 0, 1 },
114     { "IDLETIME", quote_idletime, 0, 1 },
115     { "LOG", quote_log, 0, 1 },
116     { "MAX", quote_max, 0, 1 },
117     { "MSGLOCALE", quote_msglocale, 1, 0 },
118     { "SPAMNUM", quote_spamnum, 0, 1 },
119     { "SPAMTIME", quote_spamtime, 0, 1 },
120     { "SPLITMODE", quote_splitmode, 1, 0 },
121     { "SPLITNUM", quote_splitnum, 0, 1 },
122     { "SPLITUSERS", quote_splitusers, 0, 1 },
123     { "JFLOODTIME", quote_jfloodtime, 0, 1 },
124     { "JFLOODCOUNT", quote_jfloodcount, 0, 1 },
125     { "REJECTTIME", quote_rejecttime, 0, 1 },
126     /* -------------------------------------------------------- */
127 michael 946 { NULL, NULL, 0, 0 }
128 adx 30 };
129    
130     /*
131     * list_quote_commands() sends the client all the available commands.
132     * Four to a line for now.
133     */
134     static void
135     list_quote_commands(struct Client *source_p)
136     {
137     int j = 0;
138 michael 1013 const struct SetStruct *tab = set_cmd_table;
139 michael 896 const char *names[4] = { "", "", "", "" };
140 adx 30
141     sendto_one(source_p, ":%s NOTICE %s :Available QUOTE SET commands:",
142     me.name, source_p->name);
143    
144 michael 1013 for (; tab->handler; ++tab)
145 adx 30 {
146 michael 1013 names[j++] = tab->name;
147 adx 30
148     if (j > 3)
149     {
150     sendto_one(source_p, ":%s NOTICE %s :%s %s %s %s",
151     me.name, source_p->name,
152     names[0], names[1],
153     names[2], names[3]);
154     j = 0;
155     names[0] = names[1] = names[2] = names[3] = "";
156     }
157    
158     }
159 michael 896
160 adx 30 if (j)
161     sendto_one(source_p, ":%s NOTICE %s :%s %s %s %s",
162     me.name, source_p->name,
163     names[0], names[1],
164     names[2], names[3]);
165     }
166    
167     /* SET AUTOCONN */
168     static void
169     quote_autoconn(struct Client *source_p, const char *arg, int newval)
170     {
171 michael 896 struct AccessItem *aconf;
172    
173     if (arg != NULL)
174     {
175     struct ConfItem *conf = find_exact_name_conf(SERVER_TYPE, arg, NULL, NULL);
176    
177     if (conf != NULL)
178     {
179     aconf = map_to_conf(conf);
180     if (newval)
181     SetConfAllowAutoConn(aconf);
182     else
183     ClearConfAllowAutoConn(aconf);
184    
185     sendto_realops_flags(UMODE_ALL, L_ALL,
186     "%s has changed AUTOCONN for %s to %i",
187 michael 1141 get_oper_name(source_p), arg, newval);
188 michael 896 sendto_one(source_p,
189     ":%s NOTICE %s :AUTOCONN for %s is now set to %i",
190     me.name, source_p->name, arg, newval);
191     }
192     else
193     {
194     sendto_one(source_p, ":%s NOTICE %s :Can't find %s",
195     me.name, source_p->name, arg);
196     }
197     }
198     else
199     {
200     sendto_one(source_p, ":%s NOTICE %s :Please specify a server name!",
201     me.name, source_p->name);
202     }
203 adx 30 }
204    
205     /* SET AUTOCONNALL */
206     static void
207     quote_autoconnall(struct Client *source_p, int newval)
208     {
209     if (newval >= 0)
210     {
211     sendto_realops_flags(UMODE_ALL, L_ALL, "%s has changed AUTOCONNALL to %i",
212 michael 1141 get_oper_name(source_p), newval);
213 adx 30
214     GlobalSetOptions.autoconn = newval;
215     }
216     else
217     sendto_one(source_p, ":%s NOTICE %s :AUTOCONNALL is currently %i",
218     me.name, source_p->name, GlobalSetOptions.autoconn);
219     }
220    
221     /* SET FLOODCOUNT */
222     static void
223     quote_floodcount(struct Client *source_p, int newval)
224     {
225     if (newval >= 0)
226     {
227     GlobalSetOptions.floodcount = newval;
228     sendto_realops_flags(UMODE_ALL, L_ALL,
229 michael 1141 "%s has changed FLOODCOUNT to %i",
230     get_oper_name(source_p), GlobalSetOptions.floodcount);
231 adx 30 }
232     else
233     sendto_one(source_p, ":%s NOTICE %s :FLOODCOUNT is currently %i",
234     me.name, source_p->name, GlobalSetOptions.floodcount);
235     }
236    
237     /* SET IDENTTIMEOUT */
238     static void
239     quote_identtimeout(struct Client *source_p, int newval)
240     {
241     if (!IsAdmin(source_p))
242     {
243     sendto_one(source_p, form_str(ERR_NOPRIVS),
244     me.name, source_p->name, "set");
245     return;
246     }
247    
248     if (newval > 0)
249     {
250     sendto_realops_flags(UMODE_ALL, L_ALL,
251     "%s has changed IDENTTIMEOUT to %d",
252     get_oper_name(source_p), newval);
253     GlobalSetOptions.ident_timeout = newval;
254     }
255     else
256     sendto_one(source_p, ":%s NOTICE %s :IDENTTIMEOUT is currently %d",
257     me.name, source_p->name, GlobalSetOptions.ident_timeout);
258     }
259    
260     /* SET IDLETIME */
261     static void
262     quote_idletime(struct Client *source_p, int newval)
263     {
264     if (newval >= 0)
265     {
266     if (newval == 0)
267     {
268     sendto_realops_flags(UMODE_ALL, L_ALL,
269     "%s has disabled idletime checking",
270 michael 1141 get_oper_name(source_p));
271 adx 30 GlobalSetOptions.idletime = 0;
272     }
273     else
274     {
275     sendto_realops_flags(UMODE_ALL, L_ALL,
276     "%s has changed IDLETIME to %i",
277 michael 1141 get_oper_name(source_p), newval);
278     GlobalSetOptions.idletime = (newval * 60);
279 adx 30 }
280     }
281     else
282     {
283     sendto_one(source_p, ":%s NOTICE %s :IDLETIME is currently %i",
284     me.name, source_p->name, GlobalSetOptions.idletime/60);
285     }
286     }
287    
288     /* SET LOG */
289     static void
290 michael 896 quote_log(struct Client *source_p, int newval)
291 adx 30 {
292     if (newval >= 0)
293     {
294     if (newval < L_WARN)
295     {
296     sendto_one(source_p, ":%s NOTICE %s :LOG must be > %d (L_WARN)",
297     me.name, source_p->name, L_WARN);
298     return;
299     }
300    
301     if (newval > L_DEBUG)
302     newval = L_DEBUG;
303    
304     set_log_level(newval);
305 michael 1141 sendto_realops_flags(UMODE_ALL, L_ALL, "%s has changed LOG level to %i (%s)",
306     get_oper_name(source_p), get_log_level(),
307 michael 1013 get_log_level_as_string(get_log_level()));
308 adx 30 }
309     else
310     sendto_one(source_p, ":%s NOTICE %s :LOG level is currently %i (%s)",
311     me.name, source_p->name, get_log_level(),
312     get_log_level_as_string(get_log_level()));
313     }
314    
315     /* SET MAX */
316     static void
317 michael 896 quote_max(struct Client *source_p, int newval)
318 adx 30 {
319     if (newval > 0)
320     {
321     recalc_fdlimit(NULL);
322    
323     if (newval > MAXCLIENTS_MAX)
324     {
325     sendto_one(source_p,
326     ":%s NOTICE %s :You cannot set MAXCLIENTS to > %d, restoring to %d",
327 michael 1140 me.name, source_p->name, MAXCLIENTS_MAX, ServerInfo.max_clients);
328 adx 30 return;
329     }
330    
331     if (newval < MAXCLIENTS_MIN)
332     {
333     sendto_one(source_p,
334     ":%s NOTICE %s :You cannot set MAXCLIENTS to < %d, restoring to %d",
335     me.name, source_p->name, MAXCLIENTS_MIN, ServerInfo.max_clients);
336     return;
337     }
338    
339     ServerInfo.max_clients = newval;
340    
341     sendto_realops_flags(UMODE_ALL, L_ALL,
342 michael 1141 "%s set new MAXCLIENTS to %d (%d current)",
343 michael 1142 get_oper_name(source_p), ServerInfo.max_clients, Count.local);
344 adx 30 }
345     else
346     sendto_one(source_p, ":%s NOTICE %s :Current MAXCLIENTS = %d (%d)",
347     me.name, source_p->name, ServerInfo.max_clients, Count.local);
348     }
349    
350     /* SET MSGLOCALE */
351     static void
352 michael 896 quote_msglocale(struct Client *source_p, char *locale)
353 adx 30 {
354     if (locale != NULL)
355     {
356     set_locale(locale);
357     rebuild_isupport_message_line();
358     sendto_one(source_p, ":%s NOTICE %s :Set MSGLOCALE to '%s'",
359     me.name, source_p->name, get_locale());
360     }
361     else
362     sendto_one(source_p, ":%s NOTICE %s :MSGLOCALE is currently '%s'",
363     me.name, source_p->name, get_locale());
364     }
365    
366     /* SET SPAMNUM */
367     static void
368 michael 896 quote_spamnum(struct Client *source_p, int newval)
369 adx 30 {
370 michael 646 if (newval >= 0)
371 adx 30 {
372     if (newval == 0)
373     {
374     sendto_realops_flags(UMODE_ALL, L_ALL,
375     "%s has disabled ANTI_SPAMBOT", source_p->name);
376     GlobalSetOptions.spam_num = newval;
377     return;
378     }
379    
380     GlobalSetOptions.spam_num = IRCD_MAX(newval, MIN_SPAM_NUM);
381 michael 1141 sendto_realops_flags(UMODE_ALL, L_ALL, "%s has changed SPAMNUM to %i",
382     get_oper_name(source_p), GlobalSetOptions.spam_num);
383 adx 30 }
384     else
385     sendto_one(source_p, ":%s NOTICE %s :SPAMNUM is currently %i",
386 michael 1013 me.name, source_p->name, GlobalSetOptions.spam_num);
387 adx 30 }
388    
389     /* SET SPAMTIME */
390     static void
391 michael 896 quote_spamtime(struct Client *source_p, int newval)
392 adx 30 {
393     if (newval > 0)
394     {
395     GlobalSetOptions.spam_time = IRCD_MAX(newval, MIN_SPAM_TIME);
396     sendto_realops_flags(UMODE_ALL, L_ALL, "%s has changed SPAMTIME to %i",
397 michael 1141 get_oper_name(source_p), GlobalSetOptions.spam_time);
398 adx 30 }
399     else
400     sendto_one(source_p, ":%s NOTICE %s :SPAMTIME is currently %i",
401 michael 1013 me.name, source_p->name, GlobalSetOptions.spam_time);
402 adx 30 }
403    
404     /* this table is what splitmode may be set to */
405     static const char *splitmode_values[] =
406     {
407     "OFF",
408     "ON",
409     "AUTO",
410     NULL
411     };
412    
413     /* this table is what splitmode may be */
414     static const char *splitmode_status[] =
415     {
416     "OFF",
417     "AUTO (OFF)",
418     "ON",
419     "AUTO (ON)",
420     NULL
421     };
422    
423     /* SET SPLITMODE */
424     static void
425     quote_splitmode(struct Client *source_p, char *charval)
426     {
427     if (charval)
428     {
429     int newval;
430    
431 michael 896 for (newval = 0; splitmode_values[newval]; ++newval)
432 adx 30 if (irccmp(splitmode_values[newval], charval) == 0)
433     break;
434    
435     /* OFF */
436     if (newval == 0)
437     {
438     sendto_realops_flags(UMODE_ALL, L_ALL,
439     "%s is disabling splitmode",
440     get_oper_name(source_p));
441    
442     splitmode = 0;
443     splitchecking = 0;
444    
445     eventDelete(check_splitmode, NULL);
446     }
447     /* ON */
448     else if (newval == 1)
449     {
450     sendto_realops_flags(UMODE_ALL, L_ALL,
451     "%s is enabling and activating splitmode",
452     get_oper_name(source_p));
453    
454     splitmode = 1;
455     splitchecking = 0;
456    
457     /* we might be deactivating an automatic splitmode, so pull the event */
458     eventDelete(check_splitmode, NULL);
459     }
460     /* AUTO */
461     else if (newval == 2)
462     {
463     sendto_realops_flags(UMODE_ALL, L_ALL,
464     "%s is enabling automatic splitmode",
465     get_oper_name(source_p));
466    
467     splitchecking = 1;
468     check_splitmode(NULL);
469     }
470     }
471     else
472     /* if we add splitchecking to splitmode*2 we get a unique table to
473     * pull values back out of, splitmode can be four states - but you can
474     * only set to three, which means we cant use the same table --fl_
475     */
476     sendto_one(source_p, ":%s NOTICE %s :SPLITMODE is currently %s",
477     me.name, source_p->name,
478 michael 1141 splitmode_status[(splitchecking + (splitmode * 2))]);
479 adx 30 }
480    
481     /* SET SPLITNUM */
482     static void
483     quote_splitnum(struct Client *source_p, int newval)
484     {
485     if (newval >= 0)
486     {
487     sendto_realops_flags(UMODE_ALL, L_ALL,
488     "%s has changed SPLITNUM to %i",
489 michael 1141 get_oper_name(source_p), newval);
490 adx 30 split_servers = newval;
491    
492     if (splitchecking)
493     check_splitmode(NULL);
494     }
495     else
496     sendto_one(source_p, ":%s NOTICE %s :SPLITNUM is currently %i",
497     me.name, source_p->name, split_servers);
498     }
499    
500     /* SET SPLITUSERS */
501     static void
502     quote_splitusers(struct Client *source_p, int newval)
503     {
504     if (newval >= 0)
505     {
506     sendto_realops_flags(UMODE_ALL, L_ALL,
507     "%s has changed SPLITUSERS to %i",
508 michael 1141 get_oper_name(source_p), newval);
509 adx 30 split_users = newval;
510    
511     if (splitchecking)
512     check_splitmode(NULL);
513     }
514     else
515     sendto_one(source_p, ":%s NOTICE %s :SPLITUSERS is currently %i",
516     me.name, source_p->name, split_users);
517     }
518    
519     /* SET JFLOODTIME */
520     static void
521     quote_jfloodtime(struct Client *source_p, int newval)
522     {
523     if (newval >= 0)
524     {
525     sendto_realops_flags(UMODE_ALL, L_ALL,
526     "%s has changed JFLOODTIME to %i",
527 michael 1141 get_oper_name(source_p), newval);
528 adx 30 GlobalSetOptions.joinfloodtime = newval;
529     }
530     else
531     sendto_one(source_p, ":%s NOTICE %s :JFLOODTIME is currently %i",
532     me.name, source_p->name, GlobalSetOptions.joinfloodtime);
533     }
534    
535     /* SET JFLOODCOUNT */
536     static void
537     quote_jfloodcount(struct Client *source_p, int newval)
538     {
539     if (newval >= 0)
540     {
541     sendto_realops_flags(UMODE_ALL, L_ALL,
542     "%s has changed JFLOODCOUNT to %i",
543 michael 1141 get_oper_name(source_p), newval);
544 adx 30 GlobalSetOptions.joinfloodcount = newval;
545     }
546     else
547     sendto_one(source_p, ":%s NOTICE %s :JFLOODCOUNT is currently %i",
548     me.name, source_p->name, GlobalSetOptions.joinfloodcount);
549     }
550    
551     /* SET REJECTTIME */
552     static void
553     quote_rejecttime(struct Client *source_p, int newval)
554     {
555     if (newval >= 0)
556     {
557     sendto_realops_flags(UMODE_ALL, L_ALL,
558     "%s has changed REJECTTIME to %i seconds",
559 michael 1141 get_oper_name(source_p), newval);
560 adx 30 GlobalSetOptions.rejecttime = newval;
561     }
562     else
563     sendto_one(source_p, ":%s NOTICE %s :REJECTTIME is currently %i seconds",
564     me.name, source_p->name, GlobalSetOptions.rejecttime);
565     }
566    
567     /*
568     * mo_set - SET command handler
569     * set options while running
570     */
571     static void
572     mo_set(struct Client *client_p, struct Client *source_p,
573     int parc, char *parv[])
574     {
575     int n;
576     int newval;
577     const char *arg = NULL;
578     const char *intarg = NULL;
579 michael 1013 const struct SetStruct *tab = set_cmd_table;
580 adx 30
581     if (parc > 1)
582     {
583 michael 1013 /*
584     * Go through all the commands in set_cmd_table, until one is
585     * matched.
586 adx 30 */
587 michael 1013 for (; tab->handler; ++tab)
588 adx 30 {
589 michael 1013 if (!irccmp(tab->name, parv[1]))
590 adx 30 {
591     /*
592     * Command found; now execute the code
593     */
594     n = 2;
595    
596 michael 1013 if (tab->wants_char)
597 adx 30 arg = parv[n++];
598    
599 michael 1013 if (tab->wants_int)
600 adx 30 intarg = parv[n++];
601    
602     if ((n - 1) > parc)
603     {
604     if (parc > 2)
605     sendto_one(source_p,
606     ":%s NOTICE %s :SET %s expects (\"%s%s\") args",
607 michael 1013 me.name, source_p->name, tab->name,
608     (tab->wants_char ? "string, " : ""),
609     (tab->wants_char ? "int" : ""));
610 adx 30 }
611    
612     if (parc <= 2)
613     {
614     arg = NULL;
615     intarg = NULL;
616     }
617    
618 michael 1013 if (!strcmp(tab->name, "AUTOCONN") && (parc < 4))
619 adx 30 {
620     sendto_one(source_p, form_str(ERR_NEEDMOREPARAMS),
621     me.name, source_p->name, "SET");
622     return;
623     }
624    
625 michael 1013 if (tab->wants_int && (parc > 2))
626 adx 30 {
627     if (intarg)
628     {
629     if (irccmp(intarg, "yes") == 0 || irccmp(intarg, "on") == 0)
630     newval = 1;
631     else if (irccmp(intarg, "no") == 0|| irccmp(intarg, "off") == 0)
632     newval = 0;
633     else
634     newval = atoi(intarg);
635     }
636     else
637     {
638     newval = -1;
639     }
640    
641     if (newval < 0)
642     {
643     sendto_one(source_p,
644     ":%s NOTICE %s :Value less than 0 illegal for %s",
645     me.name, source_p->name,
646 michael 1013 tab->name);
647 adx 30
648     return;
649     }
650     }
651     else
652     newval = -1;
653    
654 michael 1013 if (tab->wants_char)
655 adx 30 {
656 michael 1013 if (tab->wants_int)
657     tab->handler(source_p, arg, newval);
658 adx 30 else
659 michael 1013 tab->handler(source_p, arg);
660 adx 30 return;
661     }
662     else
663     {
664 michael 1013 if (tab->wants_int)
665     tab->handler(source_p, newval);
666 adx 30 else
667     /* Just in case someone actually wants a
668     * set function that takes no args.. *shrug* */
669 michael 1013 tab->handler(source_p);
670 adx 30 return;
671     }
672     }
673     }
674    
675     /*
676     * Code here will be executed when a /QUOTE SET command is not
677     * found within set_cmd_table.
678     */
679     sendto_one(source_p, ":%s NOTICE %s :Variable not found.",
680     me.name, source_p->name);
681     return;
682     }
683    
684     list_quote_commands(source_p);
685     }

Properties

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