modules/channels/userchan.c File Reference

Go to the source code of this file.

Functions

struct chanuserrec * get_chanrec (struct userrec *u, char *chname)
static struct chanuserrec * add_chanrec (struct userrec *u, char *chname)
static void add_chanrec_by_handle (struct userrec *bu, char *hand, char *chname)
static void get_handle_chaninfo (char *handle, char *chname, char *s)
static void set_handle_chaninfo (struct userrec *bu, char *handle, char *chname, char *info)
static void del_chanrec (struct userrec *u, char *chname)
static void set_handle_laston (char *chan, struct userrec *u, time_t n)
static int u_sticky_mask (maskrec *u, char *uhost)
static int u_setsticky_mask (int type, struct chanset_t *chan, char *uhost, int sticky)
static int u_equals_mask (maskrec *u, char *mask)
static int u_match_mask (maskrec *rec, char *mask)
static int u_delmask (char type, struct chanset_t *c, char *who, int doit)
static int u_addmask (char type, struct chanset_t *chan, char *who, char *from, char *note, time_t expire_time, int flags)
static void display_ban (int idx, int number, maskrec *ban, struct chanset_t *chan, int show_inact)
static void display_exempt (int idx, int number, maskrec *exempt, struct chanset_t *chan, int show_inact)
static void display_invite (int idx, int number, maskrec *invite, struct chanset_t *chan, int show_inact)
static void tell_bans (int idx, int show_inact, char *match)
static void tell_exempts (int idx, int show_inact, char *match)
static void tell_invites (int idx, int show_inact, char *match)
static int write_bans (FILE *f, int idx)
static int write_exempts (FILE *f, int idx)
static int write_invites (FILE *f, int idx)
static void channels_writeuserfile (void)
static int expired_mask (struct chanset_t *chan, char *who)
static void check_expired_bans (void)
static void check_expired_exempts (void)
static void check_expired_invites (void)


Function Documentation

static struct chanuserrec* add_chanrec ( struct userrec *  u,
char *  chname 
) [static, read]

Definition at line 39 of file userchan.c.

References NULL.

00040 {
00041   struct chanuserrec *ch = NULL;
00042 
00043   if (findchan_by_dname(chname)) {
00044     ch = malloc(sizeof(struct chanuserrec));
00045 
00046     ch->next = u->chanrec;
00047     u->chanrec = ch;
00048     ch->info = NULL;
00049     ch->flags = 0;
00050     ch->flags_udef = 0;
00051     ch->laston = 0;
00052     strlcpy(ch->channel, chname, sizeof ch->channel);
00053   }
00054   return ch;
00055 }

static void add_chanrec_by_handle ( struct userrec *  bu,
char *  hand,
char *  chname 
) [static]

Definition at line 57 of file userchan.c.

References add_chanrec, and get_chanrec.

00058 {
00059   struct userrec *u;
00060 
00061   u = get_user_by_handle(bu, hand);
00062   if (!u)
00063     return;
00064   if (!get_chanrec(u, chname))
00065     add_chanrec(u, chname);
00066 }

static void channels_writeuserfile ( void   )  [static]

Definition at line 905 of file userchan.c.

References _, LOG_MISC, putlog(), write_bans, write_channels(), write_exempts, and write_invites.

Referenced by channels_close(), and start().

00906 {
00907   char   s[1024];
00908   FILE  *f;
00909   int  ret = 0;
00910 
00911   simple_sprintf(s, "%s~new", userfile);
00912   f = fopen(s, "a");
00913   if (f) {
00914     ret = write_bans(f, -1);
00915     ret += write_exempts(f, -1);
00916     ret += write_invites(f, -1);
00917     fclose(f);
00918   }
00919   if (ret < 3)
00920     putlog(LOG_MISC, "*", _("ERROR writing user file."));
00921   write_channels();
00922 }

static void check_expired_bans ( void   )  [static]

Definition at line 981 of file userchan.c.

References _, expired_mask, irccmp(), LOG_MISC, now, NULL, putlog(), and u_delmask.

Referenced by channels_close(), and start().

00982 {
00983   maskrec *u, *u2;
00984   struct chanset_t *chan;
00985   masklist *b;
00986 
00987   for (u = global_bans; u; u = u2) { 
00988     u2 = u->next;
00989     if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
00990       putlog(LOG_MISC, "*", "%s %s (%s)", _("No longer banning"),
00991        u->mask, _("expired"));
00992       for (chan = chanset; chan; chan = chan->next)
00993   for (b = chan->channel.ban; b->mask[0]; b = b->next)
00994     if (!irccmp(b->mask, u->mask) &&
00995         expired_mask(chan, b->who) && b->timer != now) {
00996       add_mode(chan, '-', 'b', u->mask);
00997       b->timer = now;
00998     }
00999       u_delmask('b', NULL, u->mask, 1);
01000     }
01001   }
01002   /* Check for specific channel-domain bans expiring */
01003   for (chan = chanset; chan; chan = chan->next) {
01004     for (u = chan->bans; u; u = u2) {
01005       u2 = u->next;
01006       if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
01007   putlog(LOG_MISC, "*", "%s %s %s %s (%s)", _("No longer banning"),
01008          u->mask, _("on"), chan->dname, _("expired"));
01009   for (b = chan->channel.ban; b->mask[0]; b = b->next)
01010     if (!irccmp(b->mask, u->mask) &&
01011         expired_mask(chan, b->who) && b->timer != now) {
01012       add_mode(chan, '-', 'b', u->mask);
01013       b->timer = now;
01014     }
01015   u_delmask('b', chan, u->mask, 1);
01016       }
01017     }
01018   }
01019 }

static void check_expired_exempts ( void   )  [static]

Definition at line 1023 of file userchan.c.

References _, expired_mask, irccmp(), LOG_MISC, now, NULL, putlog(), u_delmask, and wild_match().

Referenced by channels_close(), and start().

01024 {
01025   maskrec *u, *u2;
01026   struct chanset_t *chan;
01027   masklist *b, *e;
01028   int match;
01029 
01030   if (!use_exempts)
01031     return;
01032   for (u = global_exempts; u; u = u2) {
01033     u2 = u->next;
01034     if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
01035       putlog(LOG_MISC, "*", "%s %s (%s)", _("No longer ban exempting"),
01036        u->mask, _("expired"));
01037       for (chan = chanset; chan; chan = chan->next) {
01038         match = 0;
01039         b = chan->channel.ban;
01040         while (b->mask[0] && !match) {
01041           if (wild_match(b->mask, u->mask) ||
01042             wild_match(u->mask, b->mask))
01043             match = 1;
01044           else
01045             b = b->next;
01046         }
01047         if (match)
01048           putlog(LOG_MISC, chan->dname,
01049             "Exempt not expired on channel %s. Ban still set!",
01050             chan->dname);
01051   else
01052     for (e = chan->channel.exempt; e->mask[0]; e = e->next)
01053       if (!irccmp(e->mask, u->mask) &&
01054     expired_mask(chan, e->who) && e->timer != now) {
01055         add_mode(chan, '-', 'e', u->mask);
01056         e->timer = now;
01057       }
01058       }
01059       u_delmask('e', NULL, u->mask,1);
01060     }
01061   }
01062   /* Check for specific channel-domain exempts expiring */
01063   for (chan = chanset; chan; chan = chan->next) {
01064     for (u = chan->exempts; u; u = u2) {
01065       u2 = u->next;
01066       if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
01067         match=0;
01068         b = chan->channel.ban;
01069         while (b->mask[0] && !match) {
01070           if (wild_match(b->mask, u->mask) ||
01071             wild_match(u->mask, b->mask))
01072             match=1;
01073           else
01074             b = b->next;
01075         }
01076         if (match)
01077           putlog(LOG_MISC, chan->dname,
01078             "Exempt not expired on channel %s. Ban still set!",
01079             chan->dname);
01080         else {
01081           putlog(LOG_MISC, "*", "%s %s %s %s (%s)", _("No longer ban exempting"),
01082      u->mask, _("on"), chan->dname, _("expired"));
01083     for (e = chan->channel.exempt; e->mask[0]; e = e->next)
01084       if (!irccmp(e->mask, u->mask) &&
01085     expired_mask(chan, e->who) && e->timer != now) {
01086         add_mode(chan, '-', 'e', u->mask);
01087         e->timer = now;
01088       }
01089           u_delmask('e', chan, u->mask, 1);
01090         }
01091       }
01092     }
01093   }
01094 }

static void check_expired_invites ( void   )  [static]

Definition at line 1098 of file userchan.c.

References _, expired_mask, irccmp(), LOG_MISC, now, NULL, putlog(), and u_delmask.

Referenced by channels_close(), and start().

01099 {
01100   maskrec *u, *u2;
01101   struct chanset_t *chan;
01102   masklist *b;
01103 
01104   if (!use_invites)
01105     return;
01106   for (u = global_invites; u; u = u2) {
01107     u2 = u->next;
01108     if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
01109       putlog(LOG_MISC, "*", "%s %s (%s)", _("No longer inviteing"),
01110        u->mask, _("expired"));
01111       for (chan = chanset; chan; chan = chan->next)
01112   if (!(chan->channel.mode & CHANINV))
01113     for (b = chan->channel.invite; b->mask[0]; b = b->next)
01114       if (!irccmp(b->mask, u->mask) &&
01115     expired_mask(chan, b->who) && b->timer != now) {
01116         add_mode(chan, '-', 'I', u->mask);
01117         b->timer = now;
01118       }
01119       u_delmask('I', NULL, u->mask,1);
01120     }
01121   }
01122   /* Check for specific channel-domain invites expiring */
01123   for (chan = chanset; chan; chan = chan->next) {
01124     for (u = chan->invites; u; u = u2) {
01125       u2 = u->next;
01126       if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
01127   putlog(LOG_MISC, "*", "%s %s %s %s (%s)", _("No longer inviteing"),
01128          u->mask, _("on"), chan->dname, _("expired"));
01129   if (!(chan->channel.mode & CHANINV))
01130     for (b = chan->channel.invite; b->mask[0]; b = b->next)
01131       if (!irccmp(b->mask, u->mask) &&
01132     expired_mask(chan, b->who) && b->timer != now) {
01133         add_mode(chan, '-', 'I', u->mask);
01134         b->timer = now;
01135       }
01136   u_delmask('I', chan, u->mask, 1);
01137       }
01138     }
01139   }
01140 }

static void del_chanrec ( struct userrec *  u,
char *  chname 
) [static]

Definition at line 118 of file userchan.c.

References irccmp(), and NULL.

00119 {
00120   struct chanuserrec *ch = u->chanrec, *lst = NULL;
00121 
00122   while (ch) {
00123     if (!irccmp(chname, ch->channel)) {
00124       if (lst == NULL)
00125   u->chanrec = ch->next;
00126       else
00127   lst->next = ch->next;
00128       if (ch->info != NULL)
00129   free(ch->info);
00130       free(ch);
00131       return;
00132     }
00133     lst = ch;
00134     ch = ch->next;
00135   }
00136 }

static void display_ban ( int  idx,
int  number,
maskrec *  ban,
struct chanset_t *  chan,
int  show_inact 
) [static]

Definition at line 368 of file userchan.c.

References _, ischanban, and now.

Referenced by tell_bans().

00370 {
00371   char dates[81], s[41];
00372 
00373   if (ban->added) {
00374     daysago(now, ban->added, s);
00375     sprintf(dates, "%s %s", _("Created"), s);
00376     if (ban->added < ban->lastactive) {
00377       strcat(dates, ", ");
00378       strcat(dates, _("last used"));
00379       strcat(dates, " ");
00380       daysago(now, ban->lastactive, s);
00381       strcat(dates, s);
00382     }
00383   } else
00384     dates[0] = 0;
00385   if (ban->flags & MASKREC_PERM)
00386     strcpy(s, "(perm)");
00387   else {
00388     char s1[41];
00389 
00390     days(ban->expire, now, s1);
00391     sprintf(s, "(expires %s)", s1);
00392   }
00393   if (ban->flags & MASKREC_STICKY)
00394     strcat(s, " (sticky)");
00395   if (!chan || ischanban(chan, ban->mask)) {
00396     if (number >= 0) {
00397       dprintf(idx, "  [%3d] %s %s\n", number, ban->mask, s);
00398     } else {
00399       dprintf(idx, "BAN: %s %s\n", ban->mask, s);
00400     }
00401   } else if (show_inact) {
00402     if (number >= 0) {
00403       dprintf(idx, "! [%3d] %s %s\n", number, ban->mask, s);
00404     } else {
00405       dprintf(idx, "BAN (%s): %s %s\n", _("inactive"), ban->mask, s);
00406     }
00407   } else
00408     return;
00409   dprintf(idx, "        %s: %s\n", ban->user, ban->desc);
00410   if (dates[0])
00411     dprintf(idx, "        %s\n", dates);
00412 }

static void display_exempt ( int  idx,
int  number,
maskrec *  exempt,
struct chanset_t *  chan,
int  show_inact 
) [static]

Definition at line 416 of file userchan.c.

References _, ischanexempt, and now.

Referenced by tell_exempts().

00418 {
00419   char dates[81], s[41];
00420 
00421   if (exempt->added) {
00422     daysago(now, exempt->added, s);
00423     sprintf(dates, "%s %s", _("Created"), s);
00424     if (exempt->added < exempt->lastactive) {
00425       strcat(dates, ", ");
00426       strcat(dates, _("last used"));
00427       strcat(dates, " ");
00428       daysago(now, exempt->lastactive, s);
00429       strcat(dates, s);
00430     }
00431   } else
00432     dates[0] = 0;
00433   if (exempt->flags & MASKREC_PERM)
00434     strcpy(s, "(perm)");
00435   else {
00436     char s1[41];
00437 
00438     days(exempt->expire, now, s1);
00439     sprintf(s, "(expires %s)", s1);
00440   }
00441   if (exempt->flags & MASKREC_STICKY)
00442     strcat(s, " (sticky)");
00443   if (!chan || ischanexempt(chan, exempt->mask)) {
00444     if (number >= 0) {
00445       dprintf(idx, "  [%3d] %s %s\n", number, exempt->mask, s);
00446     } else {
00447       dprintf(idx, "EXEMPT: %s %s\n", exempt->mask, s);
00448     }
00449   } else if (show_inact) {
00450     if (number >= 0) {
00451       dprintf(idx, "! [%3d] %s %s\n", number, exempt->mask, s);
00452     } else {
00453       dprintf(idx, "EXEMPT (%s): %s %s\n", _("inactive"), exempt->mask, s);
00454     }
00455   } else
00456     return;
00457   dprintf(idx, "        %s: %s\n", exempt->user, exempt->desc);
00458   if (dates[0])
00459     dprintf(idx, "        %s\n", dates);
00460 }

static void display_invite ( int  idx,
int  number,
maskrec *  invite,
struct chanset_t *  chan,
int  show_inact 
) [static]

Definition at line 464 of file userchan.c.

References _, ischaninvite, and now.

Referenced by tell_invites().

00466 {
00467   char dates[81], s[41];
00468 
00469   if (invite->added) {
00470     daysago(now, invite->added, s);
00471     sprintf(dates, "%s %s", _("Created"), s);
00472     if (invite->added < invite->lastactive) {
00473       strcat(dates, ", ");
00474       strcat(dates, _("last used"));
00475       strcat(dates, " ");
00476       daysago(now, invite->lastactive, s);
00477       strcat(dates, s);
00478     }
00479   } else
00480     dates[0] = 0;
00481   if (invite->flags & MASKREC_PERM)
00482     strcpy(s, "(perm)");
00483   else {
00484     char s1[41];
00485 
00486     days(invite->expire, now, s1);
00487     sprintf(s, "(expires %s)", s1);
00488   }
00489   if (invite->flags & MASKREC_STICKY)
00490     strcat(s, " (sticky)");
00491   if (!chan || ischaninvite(chan, invite->mask)) {
00492     if (number >= 0) {
00493       dprintf(idx, "  [%3d] %s %s\n", number, invite->mask, s);
00494     } else {
00495       dprintf(idx, "INVITE: %s %s\n", invite->mask, s);
00496     }
00497   } else if (show_inact) {
00498     if (number >= 0) {
00499       dprintf(idx, "! [%3d] %s %s\n", number, invite->mask, s);
00500     } else {
00501       dprintf(idx, "INVITE (%s): %s %s\n", _("inactive"), invite->mask, s);
00502     }
00503   } else
00504     return;
00505   dprintf(idx, "        %s: %s\n", invite->user, invite->desc);
00506   if (dates[0])
00507     dprintf(idx, "        %s\n", dates);
00508 }

static int expired_mask ( struct chanset_t *  chan,
char *  who 
) [static]

Definition at line 934 of file userchan.c.

References botname, irccmp(), NULL, and USER_BOT.

00935 {
00936   char buf[UHOSTLEN], *nick, *uhost;
00937   struct userrec *u;
00938   memberlist *m, *m2;
00939 
00940   /* Always expire masks, regardless of who set it? */
00941   if (force_expire)
00942     return 1;
00943 
00944   strlcpy(buf, who, sizeof buf);
00945   nick = strtok(buf, "!");
00946   uhost = strtok(NULL, "!");
00947 
00948   if (!nick)
00949     return 1;
00950 
00951   m = ismember(chan, nick);
00952   if (!m)
00953     for (m2 = chan->channel.member; m2 && m2->nick[0]; m2 = m2->next)
00954       if (!strcasecmp(uhost, m2->userhost)) {
00955   m = m2;
00956   break;
00957       }
00958 
00959   if (!m || !chan_hasop(m) || !irccmp(m->nick, botname))
00960     return 1;
00961 
00962   /* At this point we know the person/bot who set the mask is currently
00963    * present in the channel and has op.
00964    */
00965 
00966   if (m->user)
00967     u = m->user;
00968   else {
00969     simple_sprintf(buf, "%s!%s", m->nick, m->userhost);
00970     u = get_user_by_host(buf);
00971   }
00972   /* Do not expire masks set by bots. */
00973   if (u && u->flags & USER_BOT)
00974     return 0;
00975   else
00976     return 1;
00977 }

struct chanuserrec* get_chanrec ( struct userrec *  u,
char *  chname 
) [read]

Definition at line 29 of file userchan.c.

References irccmp(), and NULL.

00030 {
00031   struct chanuserrec *ch;
00032 
00033   for (ch = u->chanrec; ch; ch = ch->next) 
00034     if (!irccmp(ch->channel, chname))
00035       return ch;
00036   return NULL;
00037 }

static void get_handle_chaninfo ( char *  handle,
char *  chname,
char *  s 
) [static]

Definition at line 68 of file userchan.c.

References get_chanrec, and NULL.

00069 {
00070   struct userrec *u;
00071   struct chanuserrec *ch;
00072 
00073   u = get_user_by_handle(userlist, handle);
00074   if (u == NULL) {
00075     s[0] = 0;
00076     return;
00077   }
00078   ch = get_chanrec(u, chname);
00079   if (ch == NULL) {
00080     s[0] = 0;
00081     return;
00082   }
00083   if (ch->info == NULL) {
00084     s[0] = 0;
00085     return;
00086   }
00087   strcpy(s, ch->info);
00088   return;
00089 }

static void set_handle_chaninfo ( struct userrec *  bu,
char *  handle,
char *  chname,
char *  info 
) [static]

Definition at line 91 of file userchan.c.

References add_chanrec_by_handle, get_chanrec, and NULL.

00093 {
00094   struct userrec *u;
00095   struct chanuserrec *ch;
00096   struct chanset_t *cst;
00097 
00098   u = get_user_by_handle(bu, handle);
00099   if (!u)
00100     return;
00101   ch = get_chanrec(u, chname);
00102   if (!ch) {
00103     add_chanrec_by_handle(bu, handle, chname);
00104     ch = get_chanrec(u, chname);
00105   }
00106   if (info)
00107     if (strlen(info) > 80)
00108       info[80] = 0;
00109   if (ch->info != NULL)
00110     free(ch->info);
00111   if (info && info[0])
00112     ch->info = strdup(info);
00113   else
00114     ch->info = NULL;
00115   cst = findchan_by_dname(chname);
00116 }

static void set_handle_laston ( char *  chan,
struct userrec *  u,
time_t  n 
) [static]

Definition at line 138 of file userchan.c.

References get_chanrec.

00139 {
00140   struct chanuserrec *ch;
00141 
00142   if (!u)
00143     return;
00144   touch_laston(u, chan, n);
00145   ch = get_chanrec(u, chan);
00146   if (!ch)
00147     return;
00148   ch->laston = n;
00149 }

static void tell_bans ( int  idx,
int  show_inact,
char *  match 
) [static]

Definition at line 510 of file userchan.c.

References _, display_ban(), now, NULL, u_equals_mask, and wild_match().

Referenced by cmd_bans().

00511 {
00512   char *p = NULL, *chname;
00513   int k = 1;
00514   struct chanset_t *chan = NULL;
00515   maskrec *u;
00516 
00517   /* Was a channel given? */
00518   if (match[0]) {
00519     p = strdup(match);
00520     chname = strtok(p, " ");
00521     if (chname && (strchr(CHANMETA, chname[0]))) {
00522       chan = findchan_by_dname(chname);
00523       if (!chan) {
00524   dprintf(idx, "%s.\n", _("No such channel defined"));
00525   return;
00526       }
00527     } else
00528       match = chname;
00529     if (p)
00530       free_null(p);
00531   }
00532 
00533   /* don't return here, we want to show global bans even if no chan */
00534   if (!chan && !(chan = findchan_by_dname(dcc[idx].u.chat->con_chan)) &&
00535       !(chan = chanset))
00536     chan = NULL;
00537 
00538   if (chan && show_inact)
00539     dprintf(idx, "%s:   (! = %s %s)\n", _("Global bans"),
00540       _("not active on"), chan->dname);
00541   else
00542     dprintf(idx, "%s:\n", _("Global bans"));
00543   for (u = global_bans; u; u = u->next) {
00544     if (match[0]) {
00545       if ((wild_match(match, u->mask)) ||
00546     (wild_match(match, u->desc)) ||
00547     (wild_match(match, u->user)))
00548   display_ban(idx, k, u, chan, 1);
00549       k++;
00550     } else
00551       display_ban(idx, k++, u, chan, show_inact);
00552   }
00553   if (chan) {
00554     if (show_inact)
00555       dprintf(idx, _("Channel bans for %s:   (! = not active, * = not placed by bot)\n"),
00556         chan->dname);
00557     else
00558       dprintf(idx, _("Channel bans for %s:  (* = not placed by bot)\n"),
00559         chan->dname);
00560     for (u = chan->bans; u; u = u->next) {
00561       if (match[0]) {
00562         if ((wild_match(match, u->mask)) ||
00563         (wild_match(match, u->desc)) ||
00564       (wild_match(match, u->user)))
00565     display_ban(idx, k, u, chan, 1);
00566   k++;
00567       } else
00568   display_ban(idx, k++, u, chan, show_inact);
00569     }
00570     if (chan->status & CHAN_ACTIVE) {
00571       masklist *b;
00572       /* FIXME: possible buffer overflow in fill[] */
00573       char buf[UHOSTLEN], *nick, *uhost, fill[UHOSTLEN * 2];
00574       int min, sec;
00575 
00576       for (b = chan->channel.ban; b && b->mask[0]; b = b->next) {    
00577   if ((!u_equals_mask(global_bans, b->mask)) &&
00578       (!u_equals_mask(chan->bans, b->mask))) {
00579     strlcpy(buf, b->who, sizeof buf);
00580     nick = strtok(buf, "!");
00581     uhost = strtok(NULL, "!");
00582     if (nick)
00583       sprintf(fill, "%s (%s!%s)", b->mask, nick, uhost);
00584     else
00585       sprintf(fill, "%s (server %s)", b->mask, uhost);
00586     if (b->timer != 0) {
00587       min = (now - b->timer) / 60;
00588       sec = (now - b->timer) - (min * 60);
00589       sprintf(buf, " (active %02d:%02d)", min, sec);
00590       strcat(fill, buf);
00591     }
00592     if ((!match[0]) || (wild_match(match, b->mask)))
00593       dprintf(idx, "* [%3d] %s\n", k, fill);
00594     k++;
00595   }
00596       }
00597     }
00598   }
00599   if (k == 1)
00600     dprintf(idx, _("(There are no bans, permanent or otherwise.)\n"));
00601   if ((!show_inact) && (!match[0]))
00602     dprintf(idx, _("Use .bans all to see the total list.\n"));
00603 }

static void tell_exempts ( int  idx,
int  show_inact,
char *  match 
) [static]

Definition at line 605 of file userchan.c.

References _, display_exempt(), now, NULL, u_equals_mask, and wild_match().

Referenced by cmd_exempts().

00606 {
00607   char *p = NULL, *chname;
00608   int k = 1;
00609   struct chanset_t *chan = NULL;
00610   maskrec *u;
00611 
00612   /* Was a channel given? */
00613   if (match[0]) {
00614     p = strdup(match);
00615     chname = strtok(p, " ");
00616     if (chname && (strchr(CHANMETA, chname[0]))) {
00617       chan = findchan_by_dname(chname);
00618       if (!chan) {
00619   dprintf(idx, _("No such channel defined.\n"));
00620   return;
00621       }
00622     } else
00623       match = chname;
00624     if (p)
00625       free_null(p);
00626   }
00627 
00628   /* don't return here, we want to show global exempts even if no chan */
00629   if (!chan && !(chan = findchan_by_dname(dcc[idx].u.chat->con_chan))
00630       && !(chan = chanset))
00631     chan = NULL;
00632 
00633   if (chan && show_inact)
00634     dprintf(idx, "%s:   (! = %s %s)\n", _("Global exempts"),
00635       _("not active on"), chan->dname);
00636   else
00637     dprintf(idx, _("Global exempts:\n"));
00638   for (u = global_exempts; u; u = u->next) {
00639     if (match[0]) {
00640       if ((wild_match(match, u->mask)) ||
00641     (wild_match(match, u->desc)) ||
00642     (wild_match(match, u->user)))
00643   display_exempt(idx, k, u, chan, 1);
00644       k++;
00645     } else
00646       display_exempt(idx, k++, u, chan, show_inact);
00647   }
00648   if (chan) {
00649     if (show_inact)
00650       dprintf(idx, "%s %s:   (! = %s, * = %s)\n",
00651         _("Channel exempts for"), chan->dname,
00652         _("not active"),
00653         _("not placed by bot"));
00654     else
00655       dprintf(idx, "%s %s:  (* = %s)\n",
00656         _("Channel exempts for"), chan->dname,
00657         _("not placed by bot"));
00658     for (u = chan->exempts; u; u = u->next) {
00659       if (match[0]) {
00660   if ((wild_match(match, u->mask)) ||
00661       (wild_match(match, u->desc)) ||
00662       (wild_match(match, u->user)))
00663     display_exempt(idx, k, u, chan, 1);
00664   k++;
00665       } else
00666   display_exempt(idx, k++, u, chan, show_inact);
00667     }
00668     if (chan->status & CHAN_ACTIVE) {
00669       masklist *e;
00670       /* FIXME: possible buffer overflow in fill[] */
00671       char buf[UHOSTLEN], *nick, *uhost, fill[UHOSTLEN * 2];
00672       int min, sec;
00673 
00674       for (e = chan->channel.exempt; e && e->mask[0]; e = e->next) {
00675   if ((!u_equals_mask(global_exempts,e->mask)) &&
00676       (!u_equals_mask(chan->exempts, e->mask))) {
00677     strlcpy(buf, e->who, sizeof buf);
00678     nick = strtok(buf, "!");
00679     uhost = strtok(NULL, "!");
00680     if (nick)
00681       sprintf(fill, "%s (%s!%s)", e->mask, nick, uhost);
00682     else
00683       sprintf(fill, "%s (server %s)", e->mask, uhost);
00684     if (e->timer != 0) {
00685       min = (now - e->timer) / 60;
00686       sec = (now - e->timer) - (min * 60);
00687       sprintf(buf, " (active %02d:%02d)", min, sec);
00688       strcat(fill, buf);
00689     }
00690     if ((!match[0]) || (wild_match(match, e->mask)))
00691       dprintf(idx, "* [%3d] %s\n", k, fill);
00692     k++;
00693   }
00694       }
00695     }
00696   }
00697   if (k == 1)
00698     dprintf(idx, "(There are no ban exempts, permanent or otherwise.)\n");
00699   if ((!show_inact) && (!match[0]))
00700     dprintf(idx, "%s.\n", _("Use .exempts all to see the total list"));
00701 }

static void tell_invites ( int  idx,
int  show_inact,
char *  match 
) [static]

Definition at line 703 of file userchan.c.

References _, display_invite(), now, NULL, u_equals_mask, and wild_match().

Referenced by cmd_invites().

00704 {
00705   char *p = NULL, *chname;
00706   int k = 1;
00707   struct chanset_t *chan = NULL;
00708   maskrec *u;
00709 
00710   /* Was a channel given? */
00711   if (match[0]) {
00712     p = strdup(match);
00713     chname = strtok(p, " ");
00714     if (chname && (strchr(CHANMETA, chname[0]))) {
00715       chan = findchan_by_dname(chname);
00716       if (!chan) {
00717   dprintf(idx, "%s.\n", _("No such channel defined"));
00718   return;
00719       }
00720     } else
00721       match = chname;
00722     if (p)
00723       free_null(p);
00724   }
00725 
00726   /* don't return here, we want to show global invites even if no chan */
00727   if (!chan && !(chan = findchan_by_dname(dcc[idx].u.chat->con_chan))
00728       && !(chan = chanset))
00729     chan = NULL;
00730 
00731   if (chan && show_inact)
00732     dprintf(idx, "%s:   (! = %s %s)\n", _("Global invites"),
00733       _("not active on"), chan->dname);
00734   else
00735     dprintf(idx, "%s:\n", _("Global invites"));
00736   for (u = global_invites; u; u = u->next) {
00737     if (match[0]) {
00738       if ((wild_match(match, u->mask)) ||
00739     (wild_match(match, u->desc)) ||
00740     (wild_match(match, u->user)))
00741   display_invite(idx, k, u, chan, 1);
00742       k++;
00743     } else
00744       display_invite(idx, k++, u, chan, show_inact);
00745   }
00746   if (chan) {
00747     if (show_inact)
00748       dprintf(idx, "%s %s:   (! = %s, * = %s)\n",
00749         _("Channel invites for"), chan->dname,
00750         _("not active"),
00751         _("not placed by bot"));
00752     else
00753       dprintf(idx, "%s %s:  (* = %s)\n",
00754         _("Channel invites for"), chan->dname,
00755         _("not placed by bot"));
00756     for (u = chan->invites; u; u = u->next) {
00757       if (match[0]) {
00758   if ((wild_match(match, u->mask)) ||
00759       (wild_match(match, u->desc)) ||
00760       (wild_match(match, u->user)))
00761     display_invite(idx, k, u, chan, 1);
00762   k++;
00763       } else
00764   display_invite(idx, k++, u, chan, show_inact);
00765     }
00766     if (chan->status & CHAN_ACTIVE) {
00767       masklist *i;
00768       /* FIXME: possible buffer overflow in fill[] */
00769       char buf[UHOSTLEN], *nick, *uhost, fill[UHOSTLEN * 2];
00770       int min, sec;
00771 
00772       for (i = chan->channel.invite; i && i->mask[0]; i = i->next) {
00773   if ((!u_equals_mask(global_invites,i->mask)) &&
00774       (!u_equals_mask(chan->invites, i->mask))) {
00775     strlcpy(buf, i->who, sizeof buf);
00776     nick = strtok(buf, "!");
00777     uhost = strtok(NULL, "!");
00778     if (nick)
00779       sprintf(fill, "%s (%s!%s)", i->mask, nick, uhost);
00780     else
00781       sprintf(fill, "%s (server %s)", i->mask, uhost);
00782     if (i->timer != 0) {
00783       min = (now - i->timer) / 60;
00784       sec = (now - i->timer) - (min * 60);
00785       sprintf(buf, " (active %02d:%02d)", min, sec);
00786       strcat(fill, buf);
00787     }
00788     if ((!match[0]) || (wild_match(match, i->mask)))
00789       dprintf(idx, "* [%3d] %s\n", k, fill);
00790     k++;
00791   }
00792       }
00793     }
00794   }
00795   if (k == 1)
00796     dprintf(idx, "(There are no invites, permanent or otherwise.)\n");
00797   if ((!show_inact) && (!match[0]))
00798     dprintf(idx, "%s.\n", _("Use .invites all to see the total list"));
00799 }

static int u_addmask ( char  type,
struct chanset_t *  chan,
char *  who,
char *  from,
char *  note,
time_t  expire_time,
int  flags 
) [static]

Definition at line 290 of file userchan.c.

References _, irccmp(), LOG_MISC, now, NULL, putlog(), and wild_match().

00292 {
00293   char host[1024], s[1024];
00294   maskrec *p = NULL, *l, **u = NULL;
00295   module_entry *me;
00296 
00297   if (type == 'b')
00298     u = chan ? &chan->bans : &global_bans;
00299   if (type == 'e')
00300     u = chan ? &chan->exempts : &global_exempts;
00301   if (type == 'I')
00302     u = chan ? &chan->invites : &global_invites;
00303 
00304   strlcpy(host, who, sizeof host);
00305 
00306   /* Choke check: fix broken bans (must have '!' and '@') */
00307   if ((strchr(host, '!') == NULL) && (strchr(host, '@') == NULL))
00308     strcat(host, "!*@*");
00309   else if (strchr(host, '@') == NULL)
00310     strcat(host, "@*");
00311   else if (strchr(host, '!') == NULL) {
00312     char *i = strchr(host, '@');
00313 
00314     strcpy(s, i);
00315     *i = 0;
00316     strcat(host, "!*");
00317     strcat(host, s);
00318   }
00319   if ((me = module_find("server", 0, 0)) && me->funcs)
00320     simple_sprintf(s, "%s!%s", me->funcs[SERVER_BOTNAME],
00321        me->funcs[SERVER_BOTUSERHOST]);
00322   else
00323     s[0] = 0;
00324   if (s[0] && type == 'b' && wild_match(host, s)) {
00325     putlog(LOG_MISC, "*", _("Wanted to ban myself--deflected."));
00326     return 0;
00327   }
00328   if (expire_time == now)
00329     return 1;
00330 
00331   for (l = *u; l; l = l->next)
00332     if (!irccmp(l->mask, host)) {
00333       p = l;
00334       break;
00335     }
00336       
00337   /* It shouldn't expire and be sticky also */
00338   if (note[0] == '*') {
00339     flags |= MASKREC_STICKY;
00340     note++;
00341   }
00342   if ((expire_time == 0L) || (flags & MASKREC_PERM)) {
00343     flags |= MASKREC_PERM;
00344     expire_time = 0L;
00345   }
00346 
00347   if (p == NULL) {
00348     p = malloc(sizeof(maskrec));
00349     p->next = *u;
00350     *u = p;
00351   } else {
00352     free(p->mask);
00353     free(p->user);
00354     free(p->desc);
00355   }
00356   p->expire = expire_time;
00357   p->added = now;
00358   p->lastactive = 0;
00359   p->flags = flags;
00360   p->mask = strdup(host);
00361   p->user = strdup(from);
00362   p->desc = strdup(note);
00363   return 1;
00364 }

static int u_delmask ( char  type,
struct chanset_t *  c,
char *  who,
int  doit 
) [static]

Definition at line 241 of file userchan.c.

References irccmp(), and NULL.

00242 {
00243   int j, i = 0;
00244   maskrec **u = NULL, *t;
00245   char temp[256];
00246 
00247   if (type == 'b')
00248     u = c ? &c->bans : &global_bans;
00249   if (type == 'e')
00250     u = c ? &c->exempts : &global_exempts;
00251   if (type == 'I')
00252     u = c ? &c->invites : &global_invites;
00253 
00254   if (!strchr(who, '!') && (j = atoi(who))) {
00255     j--;
00256     for (; (*u) && j; u = &((*u)->next), j--);
00257     if (*u) {
00258       strlcpy(temp, (*u)->mask, sizeof temp);
00259       i = 1;
00260     } else
00261       return -j - 1;
00262   } else {
00263     /* Find matching host, if there is one */
00264     for (; *u && !i; u = &((*u)->next))
00265       if (!irccmp((*u)->mask, who)) {
00266         strlcpy(temp, who, sizeof temp);
00267   i = 1;
00268   break;
00269       }
00270     if (!*u)
00271       return 0;
00272   }
00273   if (i && doit) {
00274     if (lastdeletedmask)
00275       free(lastdeletedmask);
00276     lastdeletedmask = (*u)->mask;
00277     if ((*u)->desc)
00278       free((*u)->desc);
00279     if ((*u)->user)
00280       free((*u)->user);
00281     t = *u;
00282     *u = (*u)->next;
00283     free(t);
00284   }
00285   return i;
00286 }

static int u_equals_mask ( maskrec *  u,
char *  mask 
) [static]

Definition at line 221 of file userchan.c.

References irccmp().

00222 {
00223   for (; u; u = u->next)
00224     if (!irccmp(u->mask, mask)) {
00225       if (u->flags & MASKREC_PERM)
00226         return 2;
00227       else
00228         return 1;
00229     }
00230   return 0;
00231 }

static int u_match_mask ( maskrec *  rec,
char *  mask 
) [static]

Definition at line 233 of file userchan.c.

References wild_match().

00234 {
00235   for (; rec; rec = rec->next)
00236     if (wild_match(rec->mask, mask))
00237       return 1;
00238   return 0;
00239 }

static int u_setsticky_mask ( int  type,
struct chanset_t *  chan,
char *  uhost,
int  sticky 
) [static]

Definition at line 163 of file userchan.c.

References irccmp().

00165 {
00166   int j;
00167   maskrec *u;
00168   char *botcmd;
00169 
00170   if (type == 'b') {
00171     if (chan) u = chan->bans;
00172     else u = global_bans;
00173     botcmd = "s";
00174   }
00175   else if (type == 'I') {
00176     if (chan) u = chan->invites;
00177     else u = global_invites;
00178     botcmd = "sInv";
00179   }
00180   else if (type == 'e') {
00181     if (chan) u = chan->exempts;
00182     else u = global_exempts;
00183     botcmd = "se";
00184   }
00185   else return(-1);
00186 
00187   j = atoi(uhost);
00188   if (!j)
00189     j = (-1);
00190   while(u) {
00191     if (j >= 0)
00192       j--;
00193 
00194     if (!j || ((j < 0) && !irccmp(u->mask, uhost))) {
00195       if (sticky > 0)
00196   u->flags |= MASKREC_STICKY;
00197       else if (!sticky)
00198   u->flags &= ~MASKREC_STICKY;
00199       else  /* We don't actually want to change, just skip over */
00200   return 0;
00201       if (!j)
00202   strcpy(uhost, u->mask);
00203       return 1;
00204     }
00205 
00206     u = u->next;
00207   }
00208   if (j >= 0)
00209     return -j;
00210 
00211   return 0;
00212 }

static int u_sticky_mask ( maskrec *  u,
char *  uhost 
) [static]

Definition at line 153 of file userchan.c.

References irccmp().

00154 {
00155   for (; u; u = u->next)
00156     if (!irccmp(u->mask, uhost))
00157       return (u->flags & MASKREC_STICKY);
00158   return 0;
00159 }

static int write_bans ( FILE *  f,
int  idx 
) [static]

Definition at line 802 of file userchan.c.

00803 {
00804   struct chanset_t *chan;
00805   maskrec *b;
00806   char  *mask;
00807 
00808   if (global_bans)
00809     if (fprintf(f, BAN_NAME " - -\n") == EOF) /* Daemus */
00810       return 0;
00811   for (b = global_bans; b; b = b->next) {
00812     mask = str_escape(b->mask, ':', '\\');
00813     if (!mask ||
00814   fprintf(f, "- %s:%s%lu%s:+%lu:%lu:%s:%s\n", mask,
00815     (b->flags & MASKREC_PERM) ? "+" : "", b->expire,
00816     (b->flags & MASKREC_STICKY) ? "*" : "", b->added,
00817     b->lastactive, b->user ? b->user : myname,
00818     b->desc ? b->desc : "requested") == EOF) {
00819       if (mask)
00820   free(mask);
00821       return 0;
00822     }
00823     free(mask);
00824   }
00825   for (chan = chanset; chan; chan = chan->next)
00826     if (idx < 0) {
00827       struct flag_record fr = {FR_CHAN | FR_GLOBAL | FR_BOT, 0, 0, 0, 0, 0};
00828 
00829       if (idx >= 0)
00830   get_user_flagrec(dcc[idx].user, &fr, chan->dname);
00831     }
00832   return 1;
00833 }

static int write_exempts ( FILE *  f,
int  idx 
) [static]

Definition at line 837 of file userchan.c.

00838 {
00839   struct chanset_t *chan;
00840   maskrec *e;
00841   char  *mask;
00842 
00843   if (global_exempts)
00844     if (fprintf(f, EXEMPT_NAME " - -\n") == EOF) /* Daemus */
00845       return 0;
00846   for (e = global_exempts; e; e = e->next) {
00847     mask = str_escape(e->mask, ':', '\\');
00848     if (!mask ||
00849   fprintf(f, "%s %s:%s%lu%s:+%lu:%lu:%s:%s\n", "%", e->mask,
00850     (e->flags & MASKREC_PERM) ? "+" : "", e->expire,
00851     (e->flags & MASKREC_STICKY) ? "*" : "", e->added,
00852     e->lastactive, e->user ? e->user : myname,
00853     e->desc ? e->desc : "requested") == EOF) {
00854       if (mask)
00855   free(mask);
00856       return 0;
00857     }
00858     free(mask);
00859   }
00860   for (chan = chanset;chan;chan=chan->next)
00861     if (idx < 0) {
00862       struct flag_record fr = {FR_CHAN | FR_GLOBAL | FR_BOT, 0, 0, 0, 0, 0};
00863 
00864       if (idx >= 0)
00865   get_user_flagrec(dcc[idx].user,&fr,chan->dname);
00866     }
00867   return 1;
00868 }

static int write_invites ( FILE *  f,
int  idx 
) [static]

Definition at line 872 of file userchan.c.

00873 {
00874   struct chanset_t *chan;
00875   maskrec *ir;
00876   char  *mask;
00877 
00878   if (global_invites)
00879     if (fprintf(f, INVITE_NAME " - -\n") == EOF) /* Daemus */
00880       return 0;
00881   for (ir = global_invites; ir; ir = ir->next)  {
00882     mask = str_escape(ir->mask, ':', '\\');
00883     if (!mask ||
00884   fprintf(f,"@ %s:%s%lu%s:+%lu:%lu:%s:%s\n",ir->mask,
00885     (ir->flags & MASKREC_PERM) ? "+" : "", ir->expire,
00886     (ir->flags & MASKREC_STICKY) ? "*" : "", ir->added,
00887     ir->lastactive, ir->user ? ir->user : myname,
00888     ir->desc ? ir->desc : "requested") == EOF) {
00889       if (mask)
00890   free(mask);
00891       return 0;
00892     }
00893     free(mask);
00894   }
00895   for (chan = chanset; chan; chan = chan->next)
00896     if (idx < 0) {
00897       struct flag_record fr = {FR_CHAN | FR_GLOBAL | FR_BOT, 0, 0, 0, 0, 0};
00898 
00899       if (idx >= 0)
00900   get_user_flagrec(dcc[idx].user,&fr,chan->dname);
00901     }
00902   return 1;
00903 }


Generated on Sun Nov 30 18:43:35 2008 for eggdrop1.9 by  doxygen 1.5.6