/[cvs]/eggdrop1.4/src/tcluser.c
ViewVC logotype

Annotation of /eggdrop1.4/src/tcluser.c

Parent Directory Parent Directory | Revision Log Revision Log | View Revision Graph Revision Graph


Revision 1.13 - (hide annotations) (download) (as text)
Sun Jan 30 22:21:18 2000 UTC (19 years, 6 months ago) by per
Branch: MAIN
CVS Tags: eggdrop104030RC2, eggdrop10403RC1, eggdrop10404, eggdrop10403, HEAD
Changes since 1.12: +2 -3 lines
File MIME type: text/x-chdr
passwdok2(dw), botattr(dw) and kickmsg(eule)

1 guppy 1.10 /*
2 segfault 1.1 * tcluser.c -- handles:
3 guppy 1.10 * Tcl stubs for the user-record-oriented commands
4 segfault 1.1 *
5     * dprintf'ized, 1aug1996
6 guppy 1.10 *
7 per 1.13 * $Id: tcluser.c,v 1.12 2000/01/17 16:14:45 per Exp $
8 segfault 1.1 */
9 guppy 1.10 /*
10     * Copyright (C) 1997 Robey Pointer
11 per 1.11 * Copyright (C) 1999, 2000 Eggheads
12 guppy 1.10 *
13     * This program is free software; you can redistribute it and/or
14     * modify it under the terms of the GNU General Public License
15     * as published by the Free Software Foundation; either version 2
16     * of the License, or (at your option) any later version.
17     *
18     * This program is distributed in the hope that it will be useful,
19     * but WITHOUT ANY WARRANTY; without even the implied warranty of
20     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21     * GNU General Public License for more details.
22     *
23     * You should have received a copy of the GNU General Public License
24     * along with this program; if not, write to the Free Software
25     * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
26 segfault 1.1 */
27    
28     #include "main.h"
29     #include "users.h"
30     #include "chan.h"
31     #include "tandem.h"
32    
33     /* eggdrop always uses the same interpreter */
34     extern Tcl_Interp *interp;
35     extern struct userrec *userlist;
36 per 1.12 extern int default_flags, dcc_total, ignore_time;
37 segfault 1.1 extern struct dcc_t *dcc;
38 per 1.12 extern char origbotname[], botnetnick[];
39 segfault 1.1 extern time_t now;
40    
41     /***********************************************************************/
42    
43     static int tcl_countusers STDVAR {
44 guppy 1.9 Context;
45 segfault 1.1 BADARGS(1, 1, "");
46     Tcl_AppendResult(irp, int_to_base10(count_users(userlist)), NULL);
47     return TCL_OK;
48     }
49    
50     static int tcl_validuser STDVAR {
51 guppy 1.9 Context;
52 segfault 1.1 BADARGS(2, 2, " handle");
53     Tcl_AppendResult(irp, get_user_by_handle(userlist, argv[1]) ? "1" : "0",
54     NULL);
55     return TCL_OK;
56     }
57     static int tcl_finduser STDVAR {
58     struct userrec *u;
59    
60 guppy 1.9 Context;
61 segfault 1.1 BADARGS(2, 2, " nick!user@host");
62     u = get_user_by_host(argv[1]);
63     Tcl_AppendResult(irp, u ? u->handle : "*", NULL);
64     return TCL_OK;
65     }
66    
67     static int tcl_passwdOk STDVAR {
68     struct userrec *u;
69    
70 guppy 1.9 Context;
71 segfault 1.1 BADARGS(3, 3, " handle passwd");
72     Tcl_AppendResult(irp, ((u = get_user_by_handle(userlist, argv[1])) &&
73     u_pass_match(u, argv[2])) ? "1" : "0", NULL);
74     return TCL_OK;
75     }
76    
77     static int tcl_chattr STDVAR {
78     char *chan, *chg, work[100];
79     struct flag_record pls, mns, user;
80     struct userrec *u;
81    
82 guppy 1.9 Context;
83 segfault 1.1 BADARGS(2, 4, " handle ?changes? ?channel?");
84     if ((argv[1][0] == '*') || !(u = get_user_by_handle(userlist, argv[1]))) {
85     Tcl_AppendResult(irp, "*", NULL);
86     return TCL_OK;
87     }
88     if (argc == 4) {
89     user.match = FR_GLOBAL | FR_CHAN;
90     chan = argv[3];
91     chg = argv[2];
92 guppy 1.3 } else if ((argc == 3)
93     && (argv[2][0] && (strchr(CHANMETA, argv[2][0]) != NULL))) {
94 segfault 1.1 /* We need todo extra checking here to stop us mixing up +channel's
95     * with flags. <cybah> */
96     if (!findchan(argv[2]) && argv[2][0] != '+') {
97     /* Channel doesnt exist, and it cant possibly be flags as there
98     * is no + at the start of the string. */
99     Tcl_AppendResult(irp, "no such channel", NULL);
100     return TCL_ERROR;
101     } else if(findchan(argv[2])) {
102     /* Channel exists */
103     user.match = FR_GLOBAL | FR_CHAN;
104     chan = argv[2];
105     chg = NULL;
106     } else {
107     /* 3rd possibility... channel doesnt exist, does start with a +.
108     * In this case we assume the string is flags. */
109     user.match = FR_GLOBAL;
110     chan = NULL;
111     chg = argv[2];
112     }
113     } else {
114     user.match = FR_GLOBAL;
115     chan = NULL;
116     chg = argv[2];
117     }
118     if (chan && !findchan(chan)) {
119     Tcl_AppendResult(irp, "no such channel", NULL);
120     return TCL_ERROR;
121     }
122     get_user_flagrec(u, &user, chan);
123     /* make changes */
124     if (chg) {
125     pls.match = user.match;
126     break_down_flags(chg, &pls, &mns);
127     /* no-one can change these flags on-the-fly */
128     pls.global &=~(USER_BOT);
129     mns.global &=~(USER_BOT);
130     if (chan) {
131     pls.chan &= ~(BOT_SHARE);
132     mns.chan &= ~(BOT_SHARE);
133     }
134     user.global = sanity_check((user.global |pls.global) &~mns.global);
135     user.udef_global = (user.udef_global | pls.udef_global)
136     & ~mns.udef_global;
137     if (chan) {
138     user.chan = chan_sanity_check((user.chan | pls.chan) & ~mns.chan,
139     user.global);
140     user.udef_chan = (user.udef_chan | pls.udef_chan) & ~mns.udef_chan;
141     }
142     set_user_flagrec(u, &user, chan);
143     }
144     /* retrieve current flags and return them */
145     build_flags(work, &user, NULL);
146     Tcl_AppendResult(irp, work, NULL);
147     return TCL_OK;
148     }
149    
150     static int tcl_botattr STDVAR {
151     char *chan, *chg, work[100];
152     struct flag_record pls, mns, user;
153     struct userrec *u;
154    
155 guppy 1.9 Context;
156 segfault 1.1 BADARGS(2, 4, " bot-handle ?changes? ?channel?");
157     u = get_user_by_handle(userlist, argv[1]);
158     if ((argv[1][0] == '*') || !u || !(u->flags & USER_BOT)) {
159     Tcl_AppendResult(irp, "*", NULL);
160     return TCL_OK;
161     }
162     if (argc == 4) {
163     user.match = FR_BOT | FR_CHAN;
164     chan = argv[3];
165     chg = argv[2];
166 guppy 1.3 } else if ((argc == 3)
167     && (argv[2][0] && (strchr(CHANMETA, argv[2][0]) != NULL))) {
168 segfault 1.1 /* We need todo extra checking here to stop us mixing up +channel's
169     * with flags. <cybah> */
170     if (!findchan(argv[2]) && argv[2][0] != '+') {
171     /* Channel doesnt exist, and it cant possibly be flags as there
172     * is no + at the start of the string. */
173     Tcl_AppendResult(irp, "no such channel", NULL);
174     return TCL_ERROR;
175     } else if(findchan(argv[2])) {
176     /* Channel exists */
177     user.match = FR_BOT | FR_CHAN;
178     chan = argv[2];
179     chg = NULL;
180     } else {
181     /* 3rd possibility... channel doesnt exist, does start with a +.
182     * In this case we assume the string is flags. */
183     user.match = FR_BOT;
184     chan = NULL;
185     chg = argv[2];
186     }
187     } else {
188     user.match = FR_BOT;
189     chan = NULL;
190     chg = argv[2];
191     }
192     if (chan && !findchan(chan)) {
193     Tcl_AppendResult(irp, "no such channel", NULL);
194     return TCL_ERROR;
195     }
196     get_user_flagrec(u, &user, chan);
197     /* make changes */
198     if (chg) {
199     pls.match = user.match;
200     break_down_flags(chg, &pls, &mns);
201     /* no-one can change these flags on-the-fly */
202     if (chan) {
203     pls.chan &= BOT_SHARE;
204     mns.chan &= BOT_SHARE;
205     }
206     user.bot = sanity_check((user.bot | pls.bot) & ~mns.bot);
207     if (chan) {
208 per 1.13 user.chan = (user.chan | pls.chan) & ~mns.chan;
209 segfault 1.1 user.udef_chan = (user.udef_chan | pls.udef_chan) & ~mns.udef_chan;
210     }
211     set_user_flagrec(u, &user, chan);
212     }
213     /* retrieve current flags and return them */
214     build_flags(work, &user, NULL);
215     Tcl_AppendResult(irp, work, NULL);
216     return TCL_OK;
217     }
218    
219     static int tcl_matchattr STDVAR {
220     struct userrec *u;
221     struct flag_record plus, minus, user;
222     int ok = 0, f;
223    
224 guppy 1.9 Context;
225 segfault 1.1 BADARGS(3, 4, " handle flags ?channel?");
226 guppy 1.9 Context; /* a2 - Last context: tcluser.c/184 */
227 segfault 1.1 if ((u = get_user_by_handle(userlist, argv[1])) &&
228     ((argc == 3) || findchan(argv[3]))) {
229 guppy 1.9 Context; /* a2 - Last context: tcluser.c/184 */
230 segfault 1.1 user.match = FR_GLOBAL | (argc == 4 ? FR_CHAN : 0) | FR_BOT;
231     get_user_flagrec(u, &user, argv[3]);
232     plus.match = user.match;
233     break_down_flags(argv[2], &plus, &minus);
234     f = (minus.global || minus.udef_global || minus.chan ||
235     minus.udef_chan || minus.bot);
236     if (flagrec_eq(&plus, &user)) {
237 guppy 1.9 Context; /* a2 - Last context: tcluser.c/184 */
238 segfault 1.1 if (!f)
239     ok = 1;
240     else {
241     minus.match = plus.match ^ (FR_AND | FR_OR);
242     if (!flagrec_eq(&minus, &user))
243     ok = 1;
244     }
245     }
246     }
247 guppy 1.9 Context; /* a2 - Last context: tcluser.c/184 */
248 segfault 1.1 Tcl_AppendResult(irp, ok ? "1" : "0", NULL);
249     return TCL_OK;
250     }
251    
252     static int tcl_adduser STDVAR {
253 guppy 1.9 Context;
254 guppy 1.8 BADARGS(2, 3, " handle ?hostmask?");
255 segfault 1.1 if (strlen(argv[1]) > HANDLEN)
256     argv[1][HANDLEN] = 0;
257     if ((argv[1][0] == '*') || get_user_by_handle(userlist, argv[1]))
258     Tcl_AppendResult(irp, "0", NULL);
259     else {
260     userlist = adduser(userlist, argv[1], argv[2], "-", default_flags);
261     Tcl_AppendResult(irp, "1", NULL);
262     }
263     return TCL_OK;
264     }
265    
266     static int tcl_addbot STDVAR {
267     struct bot_addr *bi;
268     char *p, *q;
269    
270 guppy 1.9 Context;
271 segfault 1.1 BADARGS(3, 3, " handle address");
272     if (strlen(argv[1]) > HANDLEN)
273     argv[1][HANDLEN] = 0;
274     if (get_user_by_handle(userlist, argv[1]))
275     Tcl_AppendResult(irp, "0", NULL);
276     else if (argv[1][0] == '*')
277     Tcl_AppendResult(irp, "0", NULL);
278     else {
279     userlist = adduser(userlist, argv[1], "none", "-", USER_BOT);
280     bi = user_malloc(sizeof(struct bot_addr));
281     q = strchr(argv[2], ':');
282     if (!q) {
283     bi->address = user_malloc(strlen(argv[2]) + 1);
284     strcpy(bi->address, argv[2]);
285     bi->telnet_port = 3333;
286     bi->relay_port = 3333;
287     } else {
288     bi->address = user_malloc(q - argv[2] + 1);
289     strncpy(bi->address, argv[2], q - argv[2]);
290     bi->address[q - argv[2]] = 0;
291     p = q + 1;
292     bi->telnet_port = atoi(p);
293     q = strchr(p, '/');
294     if (!q)
295     bi->relay_port = bi->telnet_port;
296     else
297     bi->relay_port = atoi(q + 1);
298     }
299     set_user(&USERENTRY_BOTADDR, get_user_by_handle(userlist, argv[1]), bi);
300     Tcl_AppendResult(irp, "1", NULL);
301     }
302     return TCL_OK;
303     }
304    
305     static int tcl_deluser STDVAR {
306 guppy 1.9 Context;
307 segfault 1.1 BADARGS(2, 2, " handle");
308     Tcl_AppendResult(irp, (argv[1][0] == '*') ? "0" :
309     int_to_base10(deluser(argv[1])), NULL);
310     return TCL_OK;
311     }
312    
313     static int tcl_delhost STDVAR {
314 guppy 1.9 Context;
315 segfault 1.1 BADARGS(3, 3, " handle hostmask");
316     if ((!get_user_by_handle(userlist, argv[1])) || (argv[1][0] == '*')) {
317     Tcl_AppendResult(irp, "non-existent user", NULL);
318     return TCL_ERROR;
319     }
320     Tcl_AppendResult(irp, delhost_by_handle(argv[1], argv[2]) ? "1" : "0",
321     NULL);
322     return TCL_OK;
323     }
324    
325     static int tcl_userlist STDVAR {
326     struct userrec *u = userlist;
327     struct flag_record user, plus, minus;
328     int ok = 1, f = 0;
329    
330 guppy 1.9 Context;
331 segfault 1.1 BADARGS(1, 3, " ?flags ?channel??");
332     if ((argc == 3) && !findchan(argv[2])) {
333     Tcl_AppendResult(irp, "Invalid channel: ", argv[2], NULL);
334     return TCL_ERROR;
335     }
336     if (argc >= 2) {
337     plus.match = FR_GLOBAL | FR_CHAN | FR_BOT;
338     break_down_flags(argv[1], &plus, &minus);
339     f = (minus.global || minus.udef_global || minus.chan ||
340     minus.udef_chan || minus.bot);
341     }
342     minus.match = plus.match ^ (FR_AND | FR_OR);
343     while (u) {
344     if (argc >= 2) {
345     user.match = FR_GLOBAL | FR_CHAN | FR_BOT | (argc == 3 ? 0 : FR_ANYWH);
346     get_user_flagrec(u, &user, argv[2]); /* argv[2] == NULL for argc = 2 ;) */
347     if (flagrec_eq(&plus, &user) && !(f && flagrec_eq(&minus, &user)))
348     ok = 1;
349     else
350     ok = 0;
351     }
352     if (ok)
353     Tcl_AppendElement(interp, u->handle);
354     u = u->next;
355     }
356     return TCL_OK;
357     }
358    
359     static int tcl_save STDVAR {
360 guppy 1.9 Context;
361 segfault 1.1 write_userfile(-1);
362     return TCL_OK;
363     }
364    
365     static int tcl_reload STDVAR {
366 guppy 1.9 Context;
367 segfault 1.1 reload();
368     return TCL_OK;
369     }
370    
371     static int tcl_chnick STDVAR {
372     struct userrec *u;
373 guppy 1.5 char newhand[HANDLEN + 1];
374 segfault 1.1 int x = 1, i;
375    
376 guppy 1.9 Context;
377 segfault 1.1 BADARGS(3, 3, " oldnick newnick");
378     u = get_user_by_handle(userlist, argv[1]);
379     if (!u)
380     x = 0;
381     else {
382 guppy 1.5 strncpy(newhand, argv[2], HANDLEN);
383     newhand[HANDLEN] = 0;
384     for (i = 0; i < strlen(newhand); i++)
385     if ((newhand[i] <= 32) || (newhand[i] >= 127) || (newhand[i] == '@'))
386     newhand[i] = '?';
387     if (strchr(BADHANDCHARS, newhand[0]) != NULL)
388 segfault 1.1 x = 0;
389 guppy 1.5 else if (strlen(newhand) < 1)
390 segfault 1.1 x = 0;
391 guppy 1.5 else if (get_user_by_handle(userlist, newhand))
392 segfault 1.1 x = 0;
393 guppy 1.6 else if (!strcasecmp(botnetnick, newhand) &&
394     (!(u->flags & USER_BOT) || nextbot (argv [1]) != -1))
395     x = 0;
396 guppy 1.5 else if (newhand[0] == '*')
397 segfault 1.1 x = 0;
398     }
399     if (x)
400 guppy 1.5 x = change_handle(u, newhand);
401 segfault 1.1
402     Tcl_AppendResult(irp, x ? "1" : "0", NULL);
403     return TCL_OK;
404     }
405    
406     static int tcl_getting_users STDVAR {
407     int i;
408    
409 guppy 1.9 Context;
410 segfault 1.1 BADARGS(1, 1, "");
411     for (i = 0; i < dcc_total; i++) {
412     if ((dcc[i].type == &DCC_BOT) &&
413     (dcc[i].status & STAT_GETTING)) {
414     Tcl_AppendResult(irp, "1", NULL);
415     return TCL_OK;
416     }
417     }
418     Tcl_AppendResult(irp, "0", NULL);
419     return TCL_OK;
420     }
421    
422     static int tcl_isignore STDVAR {
423 guppy 1.9 Context;
424 segfault 1.1 BADARGS(2, 2, " nick!user@host");
425     Tcl_AppendResult(irp, match_ignore(argv[1]) ? "1" : "0", NULL);
426     return TCL_OK;
427     }
428    
429     static int tcl_newignore STDVAR {
430     time_t expire_time;
431     char ign[UHOSTLEN], cmt[66], from[HANDLEN + 1];
432    
433 guppy 1.9 Context;
434 segfault 1.1 BADARGS(4, 5, " hostmask creator comment ?lifetime?");
435 guppy 1.5 strncpy(ign, argv[1], UHOSTMAX);
436     ign[UHOSTMAX] = 0;
437 segfault 1.1 strncpy(from, argv[2], HANDLEN);
438     from[HANDLEN] = 0;
439     strncpy(cmt, argv[3], 65);
440     cmt[65] = 0;
441     if (argc == 4)
442     expire_time = now + (60 * ignore_time);
443     else {
444     if (atol(argv[4]) == 0)
445     expire_time = 0L;
446     else
447     expire_time = now + (60 * atol(argv[4]));
448     }
449     addignore(ign, from, cmt, expire_time);
450    
451     return TCL_OK;
452     }
453    
454     static int tcl_killignore STDVAR {
455 guppy 1.9 Context;
456 segfault 1.1 BADARGS(2, 2, " hostmask");
457     Tcl_AppendResult(irp, delignore(argv[1]) ? "1" : "0", NULL);
458     return TCL_OK;
459     }
460    
461     /* { hostmask note expire-time create-time creator } */
462     static int tcl_ignorelist STDVAR {
463     struct igrec *i;
464     char ts[21], ts1[21], *list[5], *p;
465    
466 guppy 1.9 Context;
467 segfault 1.1 BADARGS(1, 1, "");
468     for (i = global_ign; i; i = i->next) {
469     list[0] = i->igmask;
470     list[1] = i->msg;
471     sprintf(ts, "%lu", i->expire);
472     list[2] = ts;
473     sprintf(ts1, "%lu", i->added);
474     list[3] = ts1;
475     list[4] = i->user;
476     p = Tcl_Merge(5, list);
477     Tcl_AppendElement(irp, p);
478 guppy 1.7 Tcl_Free((char *) p);
479 segfault 1.1 }
480     return TCL_OK;
481     }
482    
483     static int tcl_getuser STDVAR {
484     struct user_entry_type *et;
485     struct userrec *u;
486     struct user_entry *e;
487    
488 guppy 1.9 Context;
489 segfault 1.1 BADARGS(3, 999, " handle type");
490     if (!(et = find_entry_type(argv[2]))) {
491     Tcl_AppendResult(irp, "No such info type: ", argv[2], NULL);
492     return TCL_ERROR;
493     }
494     if (!(u = get_user_by_handle(userlist, argv[1]))) {
495     if (argv[1][0] != '*') {
496     Tcl_AppendResult(irp, "No such user.", NULL);
497     return TCL_ERROR;
498     } else
499     return TCL_OK; /* silently ignore user * */
500     }
501     e = find_user_entry(et, u);
502    
503     if (e)
504     return et->tcl_get(irp, u, e, argc, argv);
505     return TCL_OK;
506     }
507    
508     static int tcl_setuser STDVAR {
509     struct user_entry_type *et;
510     struct userrec *u;
511     struct user_entry *e;
512     int r;
513    
514 guppy 1.9 Context;
515 segfault 1.1 BADARGS(3, 999, " handle type ?setting....?");
516     if (!(et = find_entry_type(argv[2]))) {
517     Tcl_AppendResult(irp, "No such info type: ", argv[2], NULL);
518     return TCL_ERROR;
519     }
520     if (!(u = get_user_by_handle(userlist, argv[1]))) {
521     if (argv[1][0] != '*') {
522     Tcl_AppendResult(irp, "No such user.", NULL);
523     return TCL_ERROR;
524     } else
525     return TCL_OK; /* silently ignore user * */
526     }
527     if (!(e = find_user_entry(et, u))) {
528     e = user_malloc(sizeof(struct user_entry));
529    
530     e->type = et;
531     e->name = NULL;
532     e->u.list = NULL;
533     list_insert((&(u->entries)), e);
534     }
535     r = et->tcl_set(irp, u, e, argc, argv);
536 guppy 1.2 /* yeah... e is freed, and we read it... (tcl: setuser hand HOSTS none) */
537 segfault 1.1 if (!e->u.list) {
538 arthur2 1.4 if (list_delete((struct list_type **) &(u->entries),
539     (struct list_type *) e))
540     nfree(e);
541 guppy 1.2 /* else maybe already freed... (entry_type==HOSTS) <drummer> */
542 segfault 1.1 }
543     return r;
544     }
545    
546     tcl_cmds tcluser_cmds[] =
547     {
548     {"countusers", tcl_countusers},
549     {"validuser", tcl_validuser},
550     {"finduser", tcl_finduser},
551     {"passwdok", tcl_passwdOk},
552     {"chattr", tcl_chattr},
553     {"botattr", tcl_botattr},
554     {"matchattr", tcl_matchattr},
555     {"matchchanattr", tcl_matchattr},
556     {"adduser", tcl_adduser},
557     {"addbot", tcl_addbot},
558     {"deluser", tcl_deluser},
559     {"delhost", tcl_delhost},
560     {"userlist", tcl_userlist},
561     {"save", tcl_save},
562     {"reload", tcl_reload},
563     {"chnick", tcl_chnick},
564     {"getting-users", tcl_getting_users},
565     {"isignore", tcl_isignore},
566     {"newignore", tcl_newignore},
567     {"killignore", tcl_killignore},
568     {"ignorelist", tcl_ignorelist},
569     {"getuser", tcl_getuser},
570     {"setuser", tcl_setuser},
571     {0, 0}
572     };

webmaster@eggheads.org
ViewVC Help
Powered by ViewVC 1.1.23