1 /*
2  * tclirc.c -- part of irc.mod
3  *
4  * $Id: tclirc.c,v 1.45 (0.9) 2004/01/12 01:11:40 [Xp-AvR] Exp $
5  */
6 
7 /* Streamlined by answer. */
8 static int tcl_chanlist STDVAR
9 {
10   char nuh[1024];
11   int f;
12   memberlist *m;
13   struct chanset_t *chan;
14   struct flag_record plus = { FR_CHAN | FR_GLOBAL | FR_BOT, 0, 0, 0, 0, 0 },
15                      minus = { FR_CHAN | FR_GLOBAL | FR_BOT, 0, 0, 0, 0, 0},
16                      user = { FR_CHAN | FR_GLOBAL | FR_BOT, 0, 0, 0, 0, 0 };
17 
18   BADARGS(2, 3, " channel ?flags?");
19 
20   chan = findchan_by_dname(argv[1]);
21   if (!chan) {
22     Tcl_AppendResult(irp, "invalid channel: ", argv[1], NULL);
23     return TCL_ERROR;
24   }
25   if (argc == 2) {
26     for (m = chan->channel.member; m && m->nick[0]; m = m->next)
27       Tcl_AppendElement(irp, m->nick);
28     return TCL_OK;
29   }
30   break_down_flags(argv[2], &plus, &minus);
31   f = (minus.global || minus.udef_global || minus.chan || minus.udef_chan ||
32        minus.bot);
33   if (!plus.global &&!plus.udef_global && !plus.chan && !plus.udef_chan &&
34       !plus.bot && !f)
35     return TCL_OK;
36   minus.match = plus.match ^ (FR_AND | FR_OR);
37 
38   for (m = chan->channel.member; m && m->nick[0]; m = m->next) {
39     if (!m->user) {
40       EvangelineSnprintf(nuh, sizeof nuh, "%s!%s", m->nick, m->userhost);
41       m->user = get_user_by_host(nuh);
42     }
43     get_user_flagrec(m->user, &user, argv[1]);
44     user.match = plus.match;
45     if (flagrec_eq(&plus, &user)) {
46       if (!f || !flagrec_eq(&minus, &user))
47         Tcl_AppendElement(irp, m->nick);
48     }
49   }
50   return TCL_OK;
51 }
52 
53 static int tcl_botisop STDVAR
54 {
55   struct chanset_t *chan, *thechan = NULL;
56 
57   BADARGS(1, 2, " ?channel?");
58 
59   if (argc > 1) {
60     chan = findchan_by_dname(argv[1]);
61     thechan = chan;
62     if (!thechan) {
63       Tcl_AppendResult(irp, "illegal channel: ", argv[1], NULL);
64       return TCL_ERROR;
65     }
66   } else
67     chan = chanset;
68 
69   while (chan && (thechan == NULL || thechan == chan)) {
70     if (me_op(chan)) {
71       Tcl_AppendResult(irp, "1", NULL);
72       return TCL_OK;
73     }
74     chan = chan->next;
75   }
76   Tcl_AppendResult(irp, "0", NULL);
77   return TCL_OK;
78 }
79 
80 static int tcl_ischanjuped STDVAR
81 {
82   struct chanset_t *chan;
83 
84   BADARGS(2, 2, " channel");
85 
86   chan = findchan_by_dname(argv[1]);
87   if (chan == NULL) {
88     Tcl_AppendResult(irp, "illegal channel: ", argv[1], NULL);
89     return TCL_ERROR;
90   }
91   if (channel_juped(chan))
92     Tcl_AppendResult(irp, "1", NULL);
93   else
94     Tcl_AppendResult(irp, "0", NULL);
95   return TCL_OK;
96 }
97 
98 static int tcl_botisvoice STDVAR
99 {
100   struct chanset_t *chan, *thechan = NULL;
101   memberlist *mx;
102 
103   BADARGS(1, 2, " ?channel?");
104 
105   if (argc > 1) {
106     chan = findchan_by_dname(argv[1]);
107     thechan = chan;
108     if (!thechan) {
109       Tcl_AppendResult(irp, "illegal channel: ", argv[1], NULL);
110       return TCL_ERROR;
111     }
112   } else
113     chan = chanset;
114 
115   while (chan && (thechan == NULL || thechan == chan)) {
116     if ((mx = ismember(chan, botname)) && chan_hasvoice(mx)) {
117       Tcl_AppendResult(irp, "1", NULL);
118       return TCL_OK;
119     }
120     chan = chan->next;
121   }
122   Tcl_AppendResult(irp, "0", NULL);
123   return TCL_OK;
124 }
125 
126 static int tcl_botonchan STDVAR
127 {
128   struct chanset_t *chan, *thechan = NULL;
129 
130   BADARGS(1, 2, " ?channel?");
131 
132   if (argc > 1) {
133     chan = findchan_by_dname(argv[1]);
134     thechan = chan;
135     if (!thechan) {
136       Tcl_AppendResult(irp, "illegal channel: ", argv[1], NULL);
137       return TCL_ERROR;
138     }
139   } else
140     chan = chanset;
141 
142   while (chan && (thechan == NULL || thechan == chan)) {
143     if (ismember(chan, botname)) {
144       Tcl_AppendResult(irp, "1", NULL);
145       return TCL_OK;
146     }
147     chan = chan->next;
148   }
149   Tcl_AppendResult(irp, "0", NULL);
150   return TCL_OK;
151 }
152 
153 static int tcl_isop STDVAR
154 {
155   struct chanset_t *chan, *thechan = NULL;
156   memberlist *mx;
157 
158   BADARGS(2, 3, " nick ?channel?");
159 
160   if (argc > 2) {
161     chan = findchan_by_dname(argv[2]);
162     thechan = chan;
163     if (!thechan) {
164       Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
165       return TCL_ERROR;
166     }
167   } else
168     chan = chanset;
169 
170   while (chan && (thechan == NULL || thechan == chan)) {
171     if ((mx = ismember(chan, argv[1])) && chan_hasop(mx)) {
172       Tcl_AppendResult(irp, "1", NULL);
173       return TCL_OK;
174     }
175     chan = chan->next;
176   }
177   Tcl_AppendResult(irp, "0", NULL);
178   return TCL_OK;
179 }
180 
181 static int tcl_isvoice STDVAR
182 {
183   struct chanset_t *chan, *thechan = NULL;
184   memberlist *mx;
185 
186   BADARGS(2, 3, " nick ?channel?");
187 
188   if (argc > 2) {
189     chan = findchan_by_dname(argv[2]);
190     thechan = chan;
191     if (!thechan) {
192       Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
193       return TCL_ERROR;
194     }
195   } else
196     chan = chanset;
197 
198   while (chan && (thechan == NULL || thechan == chan)) {
199     if ((mx = ismember(chan, argv[1])) && chan_hasvoice(mx)) {
200       Tcl_AppendResult(irp, "1", NULL);
201       return TCL_OK;
202     }
203     chan = chan->next;
204   }
205   Tcl_AppendResult(irp, "0", NULL);
206   return TCL_OK;
207 }
208 
209 static int tcl_wasop STDVAR
210 {
211   struct chanset_t *chan;
212   memberlist *mx;
213 
214   BADARGS(3, 3, " nick channel");
215 
216   chan = findchan_by_dname(argv[2]);
217   if (chan == NULL) {
218     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
219     return TCL_ERROR;
220   }
221   if ((mx = ismember(chan, argv[1])) && chan_wasop(mx))
222     Tcl_AppendResult(irp, "1", NULL);
223   else
224     Tcl_AppendResult(irp, "0", NULL);
225   return TCL_OK;
226 }
227 
228 static int tcl_onchan STDVAR
229 {
230   struct chanset_t *chan, *thechan = NULL;
231 
232   BADARGS(2, 3, " nickname ?channel?");
233 
234   if (argc > 2) {
235     chan = findchan_by_dname(argv[2]);
236     thechan = chan;
237     if (!thechan) {
238       Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
239       return TCL_ERROR;
240     }
241   } else
242     chan = chanset;
243 
244   while (chan && (thechan == NULL || thechan == chan)) {
245     if (ismember(chan, argv[1])) {
246       Tcl_AppendResult(irp, "1", NULL);
247       return TCL_OK;
248     }
249     chan = chan->next;
250   }
251   Tcl_AppendResult(irp, "0", NULL);
252   return TCL_OK;
253 }
254 
255 static int tcl_handonchan STDVAR
256 {
257   char nuh[1024];
258   struct chanset_t *chan, *thechan = NULL;
259   memberlist *m;
260 
261   BADARGS(2, 3, " handle ?channel?");
262 
263   if (argc > 2) {
264     chan = findchan_by_dname(argv[2]);
265     thechan = chan;
266     if (!thechan) {
267       Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
268       return TCL_ERROR;
269     }
270   } else
271     chan = chanset;
272 
273   while (chan && (thechan == NULL || thechan == chan)) {
274     for (m = chan->channel.member; m && m->nick[0]; m = m->next) {
275       if (!m->user) {
276         EvangelineSnprintf(nuh, sizeof nuh, "%s!%s", m->nick, m->userhost);
277         m->user = get_user_by_host(nuh);
278       }
279       if (m->user && !rfc_casecmp(m->user->handle, argv[1])) {
280         Tcl_AppendResult(irp, "1", NULL);
281         return TCL_OK;
282       }
283     }
284     chan = chan->next;
285   }
286   Tcl_AppendResult(irp, "0", NULL);
287   return TCL_OK;
288 }
289 
290 static int tcl_ischanban STDVAR
291 {
292   struct chanset_t *chan;
293 
294   BADARGS(3, 3, " ban channel");
295 
296   chan = findchan_by_dname(argv[2]);
297   if (chan == NULL) {
298     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
299     return TCL_ERROR;
300   }
301   if (ischanban(chan, argv[1]))
302     Tcl_AppendResult(irp, "1", NULL);
303   else
304     Tcl_AppendResult(irp, "0", NULL);
305   return TCL_OK;
306 }
307 
308 static int tcl_ischanexempt STDVAR
309 {
310   struct chanset_t *chan;
311 
312   BADARGS(3, 3, " exempt channel");
313 
314   chan = findchan_by_dname(argv[2]);
315   if (chan == NULL) {
316     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
317     return TCL_ERROR;
318   }
319   if (ischanexempt(chan, argv[1]))
320     Tcl_AppendResult(irp, "1", NULL);
321   else
322     Tcl_AppendResult(irp, "0", NULL);
323   return TCL_OK;
324 }
325 
326 static int tcl_ischaninvite STDVAR
327 {
328   struct chanset_t *chan;
329 
330   BADARGS(3, 3, " invite channel");
331 
332   chan = findchan_by_dname(argv[2]);
333   if (chan == NULL) {
334     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
335     return TCL_ERROR;
336   }
337   if (ischaninvite(chan, argv[1]))
338     Tcl_AppendResult(irp, "1", NULL);
339   else
340     Tcl_AppendResult(irp, "0", NULL);
341   return TCL_OK;
342 }
343 
344 static int tcl_getchanhost STDVAR
345 {
346   struct chanset_t *chan, *thechan = NULL;
347   memberlist *m;
348 
349   BADARGS(2, 3, " nickname ?channel?");
350 
351   if (argc > 2) {
352     chan = findchan_by_dname(argv[2]);
353     thechan = chan;
354     if (!thechan) {
355       Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
356       return TCL_ERROR;
357     }
358   } else
359     chan = chanset;
360 
361   while (chan && (thechan == NULL || thechan == chan)) {
362     m = ismember(chan, argv[1]);
363     if (m) {
364       Tcl_AppendResult(irp, m->userhost, NULL);
365       return TCL_OK;
366     }
367     chan = chan->next;
368   }
369   return TCL_OK;
370 }
371 
372 static int tcl_onchansplit STDVAR
373 {
374   struct chanset_t *chan, *thechan = NULL;
375   memberlist *m;
376 
377   BADARGS(2, 3, " nickname ?channel?");
378 
379   if (argc > 2) {
380     chan = findchan_by_dname(argv[2]);
381     thechan = chan;
382     if (!thechan) {
383       Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
384       return TCL_ERROR;
385     }
386   } else
387     chan = chanset;
388 
389   while (chan && (thechan == NULL || thechan == chan)) {
390     m = ismember(chan, argv[1]);
391     if (m && chan_issplit(m)) {
392       Tcl_AppendResult(irp, "1", NULL);
393       return TCL_OK;
394     }
395     chan = chan->next;
396   }
397   Tcl_AppendResult(irp, "0", NULL);
398   return TCL_OK;
399 }
400 
401 static int tcl_maskhost STDVAR
402 {
403   char new[121];
404 
405   BADARGS(2, 2, " nick!user@host");
406 
407   maskban(argv[1], new);
408   Tcl_AppendResult(irp, new, NULL);
409   return TCL_OK;
410 }
411 
412 static int tcl_getchanidle STDVAR
413 {
414   memberlist *m;
415   struct chanset_t *chan;
416   char s[20];
417   int x;
418 
419   BADARGS(3, 3, " nickname channel");
420 
421   if (!(chan = findchan_by_dname(argv[2]))) {
422     Tcl_AppendResult(irp, "invalid channel: ", argv[2], NULL);
423     return TCL_ERROR;
424   }
425   m = ismember(chan, argv[1]);
426 
427   if (m) {
428     x = (now - (m->last)) / 60;
429     simple_sprintf(s, "%d", x);
430     Tcl_AppendResult(irp, s, NULL);
431     return TCL_OK;
432   }
433   Tcl_AppendResult(irp, "0", NULL);
434   return TCL_OK;
435 }
436 
tcl_chanmasks(masklist * m,Tcl_Interp * irp)437 static inline int tcl_chanmasks(masklist *m, Tcl_Interp *irp)
438 {
439   char work[20], *p;
440   EVANGELINE_CONST char *list[3];
441 
442   for (; m && m->mask && m->mask[0]; m = m->next) {
443     list[0] = m->mask;
444     list[1] = m->who;
445     simple_sprintf(work, "%d", now - m->timer);
446     list[2] = work;
447     p = Tcl_Merge(3, list);
448     Tcl_AppendElement(irp, p);
449     Tcl_Free((char *) p);
450   }
451   return TCL_OK;
452 }
453 
454 static int tcl_chanbans STDVAR
455 {
456   struct chanset_t *chan;
457 
458   BADARGS(2, 2, " channel");
459 
460   chan = findchan_by_dname(argv[1]);
461   if (chan == NULL) {
462     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
463     return TCL_ERROR;
464   }
465   return tcl_chanmasks(chan->channel.ban, irp);
466 }
467 
468 static int tcl_chanexempts STDVAR
469 {
470   struct chanset_t *chan;
471 
472   BADARGS(2, 2, " channel");
473 
474   chan = findchan_by_dname(argv[1]);
475   if (chan == NULL) {
476     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
477     return TCL_ERROR;
478   }
479   return tcl_chanmasks(chan->channel.exempt, irp);
480 }
481 
482 static int tcl_chaninvites STDVAR
483 {
484   struct chanset_t *chan;
485 
486   BADARGS(2, 2, " channel");
487 
488   chan = findchan_by_dname(argv[1]);
489   if (chan == NULL) {
490     Tcl_AppendResult(irp, "illegal channel: ", argv[2], NULL);
491     return TCL_ERROR;
492   }
493   return tcl_chanmasks(chan->channel.invite, irp);
494 }
495 
496 static int tcl_getchanmode STDVAR
497 {
498   struct chanset_t *chan;
499 
500   BADARGS(2, 2, " channel");
501 
502   chan = findchan_by_dname(argv[1]);
503   if (chan == NULL) {
504     Tcl_AppendResult(irp, "invalid channel: ", argv[1], NULL);
505     return TCL_ERROR;
506   }
507   Tcl_AppendResult(irp, getchanmode(chan), NULL);
508   return TCL_OK;
509 }
510 
511 static int tcl_getchanjoin STDVAR
512 {
513   struct chanset_t *chan;
514   char s[21];
515   memberlist *m;
516 
517   BADARGS(3, 3, " nick channel");
518 
519   chan = findchan_by_dname(argv[2]);
520   if (chan == NULL) {
521     Tcl_AppendResult(irp, "invalid channel: ", argv[2], NULL);
522     return TCL_ERROR;
523   }
524   m = ismember(chan, argv[1]);
525 
526   if (m == NULL) {
527     Tcl_AppendResult(irp, argv[1], " is not on ", argv[2], NULL);
528     return TCL_ERROR;
529   }
530   sprintf(s, "%lu", m->joined);
531   Tcl_AppendResult(irp, s, NULL);
532   return TCL_OK;
533 }
534 
535 static int tcl_channame2dname STDVAR
536 {
537   struct chanset_t *chan;
538 
539   BADARGS(2, 2, " channel-name");
540 
541   chan = findchan(argv[1]);
542   if (chan) {
543     Tcl_AppendResult(irp, chan->dname, NULL);
544     return TCL_OK;
545   } else {
546     Tcl_AppendResult(irp, "invalid channel-name: ", argv[1], NULL);
547     return TCL_ERROR;
548   }
549 }
550 
551 static int tcl_chandname2name STDVAR
552 {
553   struct chanset_t *chan;
554 
555   BADARGS(2, 2, " channel-dname");
556 
557   chan = findchan_by_dname(argv[1]);
558   if (chan) {
559     Tcl_AppendResult(irp, chan->name, NULL);
560     return TCL_OK;
561   } else {
562     Tcl_AppendResult(irp, "invalid channel-dname: ", argv[1], NULL);
563     return TCL_ERROR;
564   }
565 }
566 
567 static int tcl_flushmode STDVAR
568 {
569   struct chanset_t *chan;
570 
571   BADARGS(2, 2, " channel");
572 
573   chan = findchan_by_dname(argv[1]);
574   if (chan == NULL) {
575     Tcl_AppendResult(irp, "invalid channel: ", argv[1], NULL);
576     return TCL_ERROR;
577   }
578   flush_mode(chan, NORMAL);
579   return TCL_OK;
580 }
581 
582 static int tcl_pushmode STDVAR
583 {
584   struct chanset_t *chan;
585   char plus, mode;
586 
587   BADARGS(3, 4, " channel mode ?arg?");
588 
589   chan = findchan_by_dname(argv[1]);
590   if (chan == NULL) {
591     Tcl_AppendResult(irp, "invalid channel: ", argv[1], NULL);
592     return TCL_ERROR;
593   }
594   plus = argv[2][0];
595 
596   mode = argv[2][1];
597   if ((plus != '+') && (plus != '-')) {
598     mode = plus;
599     plus = '+';
600   }
601   if (argc == 4)
602     add_mode(chan, plus, mode, argv[3]);
603   else
604     add_mode(chan, plus, mode, "");
605   return TCL_OK;
606 }
607 
608 static int tcl_resetbans STDVAR
609 {
610   struct chanset_t *chan;
611 
612   BADARGS(2, 2, " channel");
613 
614   chan = findchan_by_dname(argv[1]);
615   if (chan == NULL) {
616     Tcl_AppendResult(irp, "invalid channel ", argv[1], NULL);
617     return TCL_ERROR;
618   }
619   resetbans(chan);
620   return TCL_OK;
621 }
622 
623 static int tcl_resetexempts STDVAR
624 {
625   struct chanset_t *chan;
626 
627   BADARGS(2, 2, " channel");
628 
629   chan = findchan_by_dname(argv[1]);
630   if (chan == NULL) {
631     Tcl_AppendResult(irp, "invalid channel ", argv[1], NULL);
632     return TCL_ERROR;
633   }
634   resetexempts(chan);
635   return TCL_OK;
636 }
637 
638 static int tcl_resetinvites STDVAR
639 {
640   struct chanset_t *chan;
641 
642   BADARGS(2, 2, " channel");
643 
644   chan = findchan_by_dname(argv[1]);
645   if (chan == NULL) {
646     Tcl_AppendResult(irp, "invalid channel ", argv[1], NULL);
647     return TCL_ERROR;
648   }
649   resetinvites(chan);
650   return TCL_OK;
651 }
652 
653 static int tcl_resetchan STDVAR
654 {
655   struct chanset_t *chan;
656 
657   BADARGS(2, 2, " channel");
658 
659   chan = findchan_by_dname(argv[1]);
660   if (chan == NULL) {
661     Tcl_AppendResult(irp, "invalid channel ", argv[1], NULL);
662     return TCL_ERROR;
663   }
664   reset_chan_info(chan);
665   return TCL_OK;
666 }
667 
668 static int tcl_topic STDVAR
669 {
670   struct chanset_t *chan;
671 
672   BADARGS(2, 2, " channel");
673 
674   chan = findchan_by_dname(argv[1]);
675   if (chan == NULL) {
676     Tcl_AppendResult(irp, "invalid channel ", argv[1], NULL);
677     return TCL_ERROR;
678   }
679   Tcl_AppendResult(irp, chan->channel.topic, NULL);
680   return TCL_OK;
681 }
682 
683 static int tcl_hand2nick STDVAR
684 {
685   char nuh[1024];
686   memberlist *m;
687   struct chanset_t *chan, *thechan = NULL;
688 
689   BADARGS(2, 3, " handle ?channel?");
690 
691   if (argc > 2) {
692     chan = findchan_by_dname(argv[2]);
693     thechan = chan;
694     if (chan == NULL) {
695       Tcl_AppendResult(irp, "invalid channel: ", argv[2], NULL);
696       return TCL_ERROR;
697     }
698   } else
699     chan = chanset;
700 
701   while (chan && (thechan == NULL || thechan == chan)) {
702     for (m = chan->channel.member; m && m->nick[0]; m = m->next) {
703       if (!m->user && !m->tried_getuser) {
704         EvangelineSnprintf(nuh, sizeof nuh, "%s!%s", m->nick, m->userhost);
705         m->tried_getuser = 1;
706         m->user = get_user_by_host(nuh);
707       }
708       if (m->user && !rfc_casecmp(m->user->handle, argv[1])) {
709         Tcl_AppendResult(irp, m->nick, NULL);
710         return TCL_OK;
711       }
712     }
713     chan = chan->next;
714   }
715   return TCL_OK;
716 }
717 
718 static int tcl_nick2hand STDVAR
719 {
720   char nuh[1024];
721   memberlist *m;
722   struct chanset_t *chan, *thechan = NULL;
723 
724   BADARGS(2, 3, " nick ?channel?");
725 
726   if (argc > 2) {
727     chan = findchan_by_dname(argv[2]);
728     thechan = chan;
729     if (chan == NULL) {
730       Tcl_AppendResult(irp, "invalid channel: ", argv[2], NULL);
731       return TCL_ERROR;
732     }
733   } else
734     chan = chanset;
735 
736   while (chan && (thechan == NULL || thechan == chan)) {
737     m = ismember(chan, argv[1]);
738     if (m) {
739       if (!m->user) {
740         EvangelineSnprintf(nuh, sizeof nuh, "%s!%s", m->nick, m->userhost);
741         m->user = get_user_by_host(nuh);
742       }
743       Tcl_AppendResult(irp, m->user ? m->user->handle : "*", NULL);
744       return TCL_OK;
745     }
746     chan = chan->next;
747   }
748   return TCL_OK;
749 }
750 
751 static int tcl_putkick STDVAR
752 {
753   struct chanset_t *chan;
754   int k = 0, l;
755   char kicknick[512], *nick, *p, *comment = NULL;
756   memberlist *m;
757 
758   BADARGS(3, 4, " channel nick?s? ?comment?");
759 
760   chan = findchan_by_dname(argv[1]);
761   if (chan == NULL) {
762     Tcl_AppendResult(irp, "illegal channel: ", argv[1], NULL);
763     return TCL_ERROR;
764   }
765   if (argc == 4)
766     comment = argv[3];
767   else
768     comment = "";
769   if (!me_op(chan)) {
770     Tcl_AppendResult(irp, "need op", NULL);
771     return TCL_ERROR;
772   }
773 
774   kicknick[0] = 0;
775   p = argv[2];
776   while (p) {
777     nick = p;
778     p = strchr(nick, ',');
779     if (p) {
780       *p = 0;
781       p++;
782     }
783 
784     m = ismember(chan, nick);
785     if (!me_op(chan)) {
786       Tcl_AppendResult(irp, "need op", NULL);
787       return TCL_ERROR;
788     }
789     if (!m)
790       continue;
791     m->flags |= SENTKICK;
792     if (kicknick[0])
793       strcat(kicknick, ",");
794     strcat(kicknick, nick);
795     k++;
796 
797     l = strlen(chan->name) + strlen(kicknick) + strlen(comment);
798     if (((kick_method != 0) && (k == kick_method)) || (l > 480)) {
799       dprintf(DP_SERVER, "KICK %s %s :%s\n", chan->name, kicknick, comment);
800       k = 0;
801       kicknick[0] = 0;
802     }
803   }
804   if (k > 0)
805     dprintf(DP_SERVER, "KICK %s %s :%s\n", chan->name, kicknick, comment);
806   return TCL_OK;
807 }
808 
809 static tcl_cmds tclchan_cmds[] = {
810   {"chanlist",       tcl_chanlist},
811   {"botisop",        tcl_botisop},
812   {"botisvoice",     tcl_botisvoice},
813   {"isop",           tcl_isop},
814   {"wasop",          tcl_wasop},
815   {"isvoice",        tcl_isvoice},
816   {"onchan",         tcl_onchan},
817   {"handonchan",     tcl_handonchan},
818   {"ischanban",      tcl_ischanban},
819   {"ischanexempt",   tcl_ischanexempt},
820   {"ischaninvite",   tcl_ischaninvite},
821   {"ischanjuped",    tcl_ischanjuped},
822   {"getchanhost",    tcl_getchanhost},
823   {"onchansplit",    tcl_onchansplit},
824   {"maskhost",       tcl_maskhost},
825   {"getchanidle",    tcl_getchanidle},
826   {"chanbans",       tcl_chanbans},
827   {"chanexempts",    tcl_chanexempts},
828   {"chaninvites",    tcl_chaninvites},
829   {"hand2nick",      tcl_hand2nick},
830   {"nick2hand",      tcl_nick2hand},
831   {"getchanmode",    tcl_getchanmode},
832   {"getchanjoin",    tcl_getchanjoin},
833   {"flushmode",      tcl_flushmode},
834   {"pushmode",       tcl_pushmode},
835   {"resetbans",      tcl_resetbans},
836   {"resetexempts",   tcl_resetexempts},
837   {"resetinvites",   tcl_resetinvites},
838   {"resetchan",      tcl_resetchan},
839   {"topic",          tcl_topic},
840   {"botonchan",      tcl_botonchan},
841   {"putkick",        tcl_putkick},
842   {"channame2dname", tcl_channame2dname},
843   {"chandname2name", tcl_chandname2name},
844   {NULL,             NULL}
845 };
846