muhstik

- irc flooding solution
git clone git://git.acid.vegas/muhstik.git
Log | Files | Refs | Archive | README

mass.c (7030B)

      1 /* Muhstik, Copyright (C) 2001-2002, Louis Bavoil <mulder@gmx.fr>       */
      2 /*                        2009-2011, Leon Kaiser <literalka@gnaa.eu>    */
      3 /*                                                                      */
      4 /* This program is free software; you can redistribute it and/or        */
      5 /* modify it under the terms of the GNU Library General Public License  */
      6 /* as published by the Free Software Foundation; either version 2       */
      7 /* of the License, or (at your option) any later version.               */
      8 /*                                                                      */
      9 /* This program is distributed in the hope that it will be useful,      */
     10 /* but WITHOUT ANY WARRANTY; without even the implied warranty of       */
     11 /* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the        */
     12 /* GNU Library General Public License for more details.                 */
     13 
     14 /* {{{ Header includes */
     15 #include <stdio.h>
     16 #include <stdlib.h>
     17 #include <time.h>
     18 #include <unistd.h>
     19 
     20 #include "../include/mass.h"
     21 #include "../include/control.h"
     22 #include "../include/net.h"
     23 #include "../include/string.h"
     24 #include "../include/lists.h"
     25 /* }}} */
     26 /* {{{ Variables */
     27 /* {{{ External Variables */
     28 extern char *channel[];
     29 extern char *broth[];
     30 extern clone_t *cl[];
     31 extern config_t conf;
     32 extern queue names_op[];
     33 extern queue names[];
     34 /* }}} */
     35 /*{{{ Global variables */
     36 int mass_ch;
     37 int mass_mode;
     38 char *mass_reas;
     39 char *mass_server;
     40 /* }}} */
     41 /* }}} */
     42 /* {{{ Massmode functions */
     43 /* {{{ multimode() */
     44 void multimode(clone_t *clone, char *chan, char *sign, int n, char *nicks, int uniq)
     45 {
     46      char modes[MINIBUF];
     47      int i;
     48 
     49      memset(modes, 0, sizeof(modes));
     50 
     51      StrCat(modes, " ", sizeof(modes));
     52      StrCat(modes, sign, sizeof(modes));
     53      for (i = 0; i < n; ++i)
     54      {
     55           StrCat(modes, "o", sizeof(modes));
     56      }
     57 
     58      if (uniq)
     59      {
     60           send2server(clone, "MODE %s%s%s\n", chan, modes, nicks);
     61      }
     62      else
     63      {
     64           send_sock(clone->sock, "MODE %s%s%s\n", chan, modes, nicks);
     65      }
     66 }
     67 /* }}} */
     68 /* {{{ (de)opping and kicking functions */
     69 /* TODO: Deop +{h,a,q}, if possible. */
     70 void massdeop(clone_t *clone, int chid)
     71 {
     72      int i;
     73      int n = 0;
     74      char nicks[BIGBUF];
     75      queue *list;
     76 
     77      memset(nicks, 0, sizeof(nicks));
     78      list = &names_op[chid];
     79 
     80      for (i = 0; *list && i < conf.multi_deop; ++i)
     81      {
     82           if (is_enemy((*list)->data))
     83           {
     84                StrCat(nicks, " ", sizeof(nicks));
     85                StrCat(nicks, (*list)->data, sizeof(nicks));
     86                ++n;
     87           }
     88           rotate_cell(list);
     89      }
     90 
     91      if (n > 0)
     92      {
     93           multimode(clone, channel[chid], "-", n, nicks, 1);
     94      }
     95 }
     96 
     97 void massop(clone_t *clone, int chid)
     98 {
     99      register int i;
    100      register int j;
    101      clone_t **pcl;
    102      char nicks[BIGBUF];
    103 
    104      memset(nicks, 0, sizeof(nicks));
    105 
    106      for (i = j = 0, pcl = cl; j < conf.multi_op && i < MAX_CLONES; ++i, ++pcl)
    107      {
    108           if ((*pcl) && (*pcl) != clone && (*pcl)->online && (*pcl)->needop[chid])
    109           {
    110                (*pcl)->needop[chid] = 0;
    111                StrCat(nicks, " ", sizeof(nicks));
    112                StrCat(nicks, (*pcl)->nick, sizeof(nicks));
    113                ++j;
    114           }
    115      }
    116 
    117      if (j > 0)
    118      {
    119           multimode(clone, channel[chid], "+", j, nicks, 0);
    120      }
    121 }
    122 
    123 void force_massop()
    124 {
    125      register int i;
    126      char **pt;
    127      clone_t **pcl;
    128      clone_t *one;
    129 
    130      for (i = 0, pcl = cl; i < MAX_CLONES; ++i, ++pcl)
    131      {
    132           if ((*pcl) && (*pcl)->online && !(*pcl)->restricted && !(*pcl)->op[mass_ch] && (one = getop(mass_ch)))
    133           {
    134                op(one, mass_ch, (*pcl)->nick);
    135           }
    136      }
    137 
    138      for (i = 0, pt = broth; i < MAX_BROTHERS; ++i, ++pt)
    139      {
    140           if ((*pt) && (one = getop(mass_ch)))
    141           {
    142                op(one, mass_ch, *pt);
    143           }
    144      }
    145 }
    146 
    147 void _masskick(clone_t *clone, int chid, queue **list)
    148 {
    149      int n;
    150      char buffer[BIGBUF];
    151 
    152      memset(buffer, 0, sizeof(buffer));
    153 
    154      for (n = 0; **list && n < conf.multi_kick; ++n)
    155      {
    156           if (n > 0)
    157           {
    158                StrCat(buffer, ",", BIGBUF);
    159           }
    160           StrCat(buffer, (**list)->data, BIGBUF);
    161           free_cell(*list);
    162      }
    163 
    164      kick(clone, chid, buffer, mass_reas ? mass_reas : NULL, 0);
    165 }
    166 
    167 void _massdeop(clone_t *clone, int chid, queue **list)
    168 {
    169      int i;
    170      char nicks[BIGBUF];
    171 
    172      memset(nicks, 0, sizeof(nicks));
    173 
    174      for (i = 0; **list && i < conf.multi_deop; ++i)
    175      {
    176           StrCat(nicks, " ", sizeof(nicks));
    177           StrCat(nicks, (**list)->data, sizeof(nicks));
    178           free_cell(*list);
    179      }
    180 
    181      if (i > 0)
    182      {
    183           multimode(clone, channel[chid], "-", i, nicks, 0);
    184      }
    185 }
    186 /* }}} */
    187 /* {{{ massdo()ing functions */
    188 void massdo(queue *list, int chid, int mode)
    189 {
    190      int id;
    191      clone_t **pcl;
    192      int n;
    193 
    194      for (n = 0; *list && n < 10; ++n)
    195      {
    196           for (id = 0, pcl = cl; *list && id < MAX_CLONES; ++id, ++pcl)
    197           {
    198                if (is_op(*pcl, chid))
    199                {
    200                     switch (mode)
    201                     {
    202                          case MK:
    203                               _masskick(*pcl, chid, &list);
    204                               break;
    205                          case MD:
    206                               _massdeop(*pcl, chid, &list);
    207                               break;
    208                          case MKB:
    209                               kickban(*pcl, (*list)->data);
    210                               free_cell(list);
    211                               break;
    212                     }
    213                     (*pcl)->lastsend = time(NULL);
    214                }
    215           } /* bracket might be after the `usleep()' -- Leon */
    216           usleep(500000);
    217      }
    218 }
    219 
    220 void takeover(queue *list)
    221 {
    222      register int i;
    223      clone_t **pcl;
    224 
    225      for (i = 0, pcl = cl; *list && i < MAX_CLONES; ++i, ++pcl)
    226      {
    227           if ((*pcl) && (*pcl)->online && (*pcl)->server == mass_server)
    228           {
    229                send_irc_nick(*pcl, (*list)->data);
    230                free_cell(list);
    231           }
    232      }
    233 }
    234 
    235 void *init_massdo(int chid, int mode)
    236 {
    237      queue list1 = NULL;
    238      queue list2 = NULL;
    239      queue plist;
    240 
    241      for (plist = names_op[chid]; plist; plist = plist->next)
    242      {
    243           if (mode == TO || is_enemy(plist->data))
    244           {
    245                add_queue(plist->data, &list1);
    246           }
    247      }
    248      for (plist = names[chid]; plist; plist = plist->next)
    249      {
    250           if (mode != TO && mode != MD && is_enemy(plist->data))
    251           {
    252                add_queue(plist->data, &list2);
    253           }
    254      }
    255 
    256      switch (mode)
    257      {
    258           case MKB:
    259           case MK:
    260                massdo(&list1, chid, mode);
    261                massdo(&list2, chid, mode);
    262                break;
    263           case MD:
    264                massdo(&list1, chid, mode);
    265                break;
    266           case TO:
    267                takeover(&list1);
    268                break;
    269      }
    270 
    271      clear_queue(&list1);
    272      clear_queue(&list2);
    273 
    274      return NULL;
    275 }
    276 /* }}} */
    277 /* }}} */