/[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.2 - (hide annotations) (download) (as text)
Sun Jun 27 20:37:25 1999 UTC (20 years, 1 month ago) by guppy
Branch: MAIN
Changes since 1.1: +3 -1 lines
File MIME type: text/x-chdr
A whole bunch of drummer patches

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

webmaster@eggheads.org
ViewVC Help
Powered by ViewVC 1.1.23