Esempio n. 1
0
/* Flush the modes for EVERY channel.
 */
static void flush_modes()
{
    struct chanset_t *chan;
    memberlist *m;

    if (modesperline > MODES_PER_LINE_MAX)
        modesperline = MODES_PER_LINE_MAX;

    for (chan = chanset; chan; chan = chan->next) {
        for (m = chan->channel.member; m && m->nick[0]; m = m->next) {
            if (m->delay && m->delay <= now) {
                m->delay = 0L;
                m->flags &= ~FULL_DELAY;
                if (chan_sentop(m)) {
                    m->flags &= ~SENTOP;
                    add_mode(chan, '+', 'o', m->nick);
                }
                if (chan_senthalfop(m)) {
                    m->flags &= ~SENTHALFOP;
                    add_mode(chan, '+', 'h', m->nick);
                }
                if (chan_sentvoice(m)) {
                    m->flags &= ~SENTVOICE;
                    add_mode(chan, '+', 'v', m->nick);
                }
            }
        }
        flush_mode(chan, NORMAL);
    }
}
Esempio n. 2
0
static void got_invite(struct chanset_t *chan, char *nick, char *from,
                       char *who, char *ch, struct userrec *u)
{
  char s[UHOSTLEN];

  simple_sprintf(s, "%s!%s", nick, from);
  newinvite(chan, who, s);
  check_tcl_mode(nick, from, u, chan->dname, "+I", who);
  if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
    return;

  if (channel_pending(chan) || HALFOP_CANTDOMODE('I'))
    return;

  if (!match_my_nick(nick)) {
    if (nick[0] && channel_nouserinvites(chan) && !glob_bot(user) &&
        !glob_master(user) && !chan_master(user)) {
      add_mode(chan, '-', 'I', who);
      return;
    }
    if ((!nick[0]) && (bounce_modes))
      reversing = 1;
  }
  if (reversing || (bounce_invites && (!nick[0]) &&
      (!u_equals_mask(global_invites, who) ||
      !u_equals_mask(chan->invites, who))))
    add_mode(chan, '-', 'I', who);
}
Esempio n. 3
0
static int script_newsomething(void *type, char *chan_name, char *mask, char *creator, char *comment, char *lifetime, char *options)
{
	time_t expire_time;
	struct chanset_t *chan = NULL;
	int sticky = 0;
	int r;
	module_entry *me;

	if (chan_name[0]) {
		chan = findchan_by_dname(chan_name);
		if (!chan) return(-1);
	}

	if (lifetime) {
		expire_time = atoi(lifetime);
		if (expire_time) expire_time = expire_time * 60 + now;
	}
	expire_time = now + (60 * (((int) type == 'b') ?
			    ((chan->ban_time == 0) ? 0L : chan->ban_time) :
			    (((int) type == 'e') ? ((chan->exempt_time == 0) ?
			    0L : chan->exempt_time) :
			    ((chan->invite_time == 0) ?
			    0L : chan->invite_time))));

	if (options && !strcasecmp(options, "sticky")) sticky = 1;

	r = u_addmask((int) type, chan, mask, creator, comment, expire_time, sticky);
	if (chan && !r) return(-1);

	if ((int) type == 'b') {
		me = module_find("irc", 0, 0);
		if (me) {
			if (chan) (me->funcs[IRC_CHECK_THIS_BAN])(chan, mask, sticky);
			else for (chan = chanset; chan; chan = chan->next) {
				(me->funcs[IRC_CHECK_THIS_BAN])(chan, mask, sticky);
			}
		}
		return(0);
	}

	if (chan) add_mode(chan, '+', (int) type, mask);
	else {
		for (chan = chanset; chan; chan = chan->next) {
			add_mode(chan, '+', (int) type, mask);
		}
	}
	return(0);
}
Esempio n. 4
0
static void cmd_down(int idx, char *par)
{
  char *chname = NULL, buf2[201] = "";
  struct chanset_t *chan = NULL;

  putlog(LOG_CMDS, "*", "#%s# down %s", dcc[idx].nick, par);

  if (!par[0]) {
    dprintf(idx, "Usage: down [%s]<channel>\n", CHANMETA);
    return;
  }

  chname = newsplit(&par);
  chan = findchan_by_dname(chname);
  if (!chan) {
    dprintf(idx, "%s is not a valid channel.\n", chname);
    return;
  }
  
  simple_snprintf(buf2, sizeof(buf2), "down %s", chan->dname);
  putallbots(buf2);
  if (!conf.bot->hub) {
    add_mode(chan, '-', 'o', botname);
    chan->channel.no_op = (now + 10);
  }
}
Esempio n. 5
0
/*
 * A special insert used as the undo of delete char (C-d or DEL)
 * this is where the char is inserted at the point and the cursor
 * is NOT moved on 1 char.  This MUST be a seperate function so that
 *   INSERT + BACKSPACE are matching undo pairs
 *   INSERT_AT + DELETE are matching undo pairs
 * Note: This function is only ever called by execute_undo to undo a DEL.
 */
void insert_at()
{
	char_t the_char[2]; /* the inserted char plus a null */
	assert(curbp->b_gap <= curbp->b_egap);

	if (curbp->b_gap == curbp->b_egap && !growgap(curbp, CHUNK))
		return;
	curbp->b_point = movegap(curbp, curbp->b_point);


	/* overwrite if mid line, not EOL or EOF, CR will insert as normal */
	if ((curbp->b_flags & B_OVERWRITE) && *input != '\r' && *(ptr(curbp, curbp->b_point)) != '\n' && curbp->b_point < pos(curbp,curbp->b_ebuf) ) {
		*(ptr(curbp, curbp->b_point)) = *input;
		if (curbp->b_point < pos(curbp, curbp->b_ebuf))
			++curbp->b_point;
		/* FIXME - overwite mode not handled properly for undo yet */
	} else {
		the_char[0] = *input == '\r' ? '\n' : *input;
		the_char[1] = '\0'; /* null terminate */
		*curbp->b_gap++ = the_char[0];
		curbp->b_point = pos(curbp, curbp->b_egap);
		curbp->b_point--; /* move point back to where it was before, should always be safe */
		/* the point is set so that and undo will DELETE the char */
		add_undo(curbp, UNDO_T_INSAT, curbp->b_point, the_char, NULL);
	}

	add_mode(curbp, B_MODIFIED);
}
Esempio n. 6
0
static void got_unban(struct chanset_t *chan, char *nick, char *from,
                      char *who, char *ch, struct userrec *u)
{
  masklist *b, *old;

  old = NULL;
  for (b = chan->channel.ban; b->mask[0] && rfc_casecmp(b->mask, who);
       old = b, b = b->next);
  if (b->mask[0]) {
    if (old)
      old->next = b->next;
    else
      chan->channel.ban = b->next;
    nfree(b->mask);
    nfree(b->who);
    nfree(b);
  }
  check_tcl_mode(nick, from, u, chan->dname, "-b", who);
  if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
    return;

  if (channel_pending(chan))
    return;

  if ((u_sticky_mask(chan->bans, who) || u_sticky_mask(global_bans, who)) ||
      ((u_equals_mask(global_bans, who) || u_equals_mask(chan->bans, who)) &&
      !channel_dynamicbans(chan) && ((!glob_bot(user) ||
      !(bot_flags(u) & BOT_SHARE)) && ((!glob_op(user) || chan_deop(user)) &&
      !chan_op(user)) && ((!glob_halfop(user) || chan_dehalfop(user)) &&
      !chan_halfop(user)))))
    add_mode(chan, '+', 'b', who);
}
Esempio n. 7
0
static void got_unexempt(struct chanset_t *chan, char *nick, char *from,
                         char *who, char *ch, struct userrec *u)
{
  masklist *e = chan->channel.exempt, *old = NULL;
  masklist *b;
  int match = 0;

  while (e && e->mask[0] && rfc_casecmp(e->mask, who)) {
    old = e;
    e = e->next;
  }
  if (e && e->mask[0]) {
    if (old)
      old->next = e->next;
    else
      chan->channel.exempt = e->next;
    nfree(e->mask);
    nfree(e->who);
    nfree(e);
  }
  check_tcl_mode(nick, from, u, chan->dname, "-e", who);
  if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
    return;

  if (channel_pending(chan))
    return;

  if (u_sticky_mask(chan->exempts, who) || u_sticky_mask(global_exempts, who))
    add_mode(chan, '+', 'e', who);

  /* If exempt was removed by master then leave it else check for bans */
  if (!nick[0] && glob_bot(user) && !glob_master(user) && !chan_master(user)) {
    b = chan->channel.ban;
    while (b->mask[0] && !match) {
      if (mask_match(b->mask, who)) {
        add_mode(chan, '+', 'e', who);
        match = 1;
      } else
        b = b->next;
    }
  }
  if ((u_equals_mask(global_exempts, who) ||
      u_equals_mask(chan->exempts, who)) && me_op(chan) &&
      !channel_dynamicexempts(chan) && (!glob_bot(user) ||
      !(bot_flags(u) & BOT_SHARE)))
    add_mode(chan, '+', 'e', who);
}
Esempio n. 8
0
static void got_key(struct chanset_t *chan, char *nick, char *from, char *key)
{
  if (!nick[0] && bounce_modes)
    reversing = 1;

  if (!(glob_master(user) || glob_bot(user) || chan_master(user)) &&
      !match_my_nick(nick)) {
    if ((reversing && !chan->key_prot[0]) || (chan->mode_mns_prot & CHANKEY)) {
      if (strlen(key) != 0)
        add_mode(chan, '-', 'k', key);
      else
        add_mode(chan, '-', 'k', "");
    }
    if ((chan->mode_pls_prot & CHANKEY) && (chan->key_prot[0] != 0) &&
        strcmp(key, chan->key_prot)) {
      add_mode(chan, '+', 'k', chan->key_prot);
    }
  }
}
Esempio n. 9
0
/* Check for expired timed-invites.
 */
static void check_expired_invites(void)
{
  maskrec *u, *u2;
  struct chanset_t *chan;
  masklist *b;

  if (!use_invites)
    return;
  for (u = global_invites; u; u = u2) {
    u2 = u->next;
    if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
      putlog(LOG_MISC, "*", "%s %s (%s)", INVITES_NOLONGER,
             u->mask, MISC_EXPIRED);
      for (chan = chanset; chan; chan = chan->next)
        if (!(chan->channel.mode & CHANINV))
          for (b = chan->channel.invite; b->mask[0]; b = b->next)
            if (!rfc_casecmp(b->mask, u->mask) &&
                expired_mask(chan, b->who) && b->timer != now) {
              add_mode(chan, '-', 'I', u->mask);
              b->timer = now;
            }
      u_delinvite(NULL, u->mask, 1);
    }
  }
  /* Check for specific channel-domain invites expiring */
  for (chan = chanset; chan; chan = chan->next) {
    for (u = chan->invites; u; u = u2) {
      u2 = u->next;
      if (!(u->flags & MASKREC_PERM) && (now >= u->expire)) {
        putlog(LOG_MISC, "*", "%s %s %s %s (%s)", INVITES_NOLONGER,
               u->mask, MISC_ONLOCALE, chan->dname, MISC_EXPIRED);
        if (!(chan->channel.mode & CHANINV))
          for (b = chan->channel.invite; b->mask[0]; b = b->next)
            if (!rfc_casecmp(b->mask, u->mask) &&
                expired_mask(chan, b->who) && b->timer != now) {
              add_mode(chan, '-', 'I', u->mask);
              b->timer = now;
            }
        u_delinvite(chan, u->mask, 1);
      }
    }
  }
}
Esempio n. 10
0
/* Kill a ban/exempt/invite either globally or from a channel. */
static int script_killsomething(void *type, char *chan_name, char *mask)
{
	struct chanset_t *chan = NULL;

	if (chan_name && chan_name[0]) {
		chan = findchan_by_dname(chan_name);
		if (!chan) return(-1);
	}

	if (u_delmask((int) type, chan, mask, 1) > 0) {
		if (!chan) {
			for (chan = chanset; chan; chan = chan->next) {
				add_mode(chan, '-', (int) type, mask);
			}
		}
		else add_mode(chan, '-', (int) type, mask);
	}
	return(0);
}
Esempio n. 11
0
// Add standard list of windowed modes for given color depth
static void add_window_modes(video_depth depth)
{
#if 0
	add_mode(512, 384, 0x80, TrivialBytesPerRow(512, depth), depth);
	add_mode(640, 480, 0x81, TrivialBytesPerRow(640, depth), depth);
	add_mode(800, 600, 0x82, TrivialBytesPerRow(800, depth), depth);
	add_mode(1024, 768, 0x83, TrivialBytesPerRow(1024, depth), depth);
	add_mode(1152, 870, 0x84, TrivialBytesPerRow(1152, depth), depth);
	add_mode(1280, 1024, 0x85, TrivialBytesPerRow(1280, depth), depth);
	add_mode(1600, 1200, 0x86, TrivialBytesPerRow(1600, depth), depth);
#endif
}
Esempio n. 12
0
static void got_down(char *botnick, char *code, char *par)
{
  if (!par[0])
   return;

  char *chname = newsplit(&par);
  struct chanset_t *chan = NULL;

  if (!(chan = findchan_by_dname(chname)))
   return;
 
  chan->channel.no_op = (now + 10);
  add_mode(chan, '-', 'o', botname);
}
Esempio n. 13
0
void check_hack(char *nick, ChannelList *channel, NickList *ThisNick, char *from)
{
#ifdef WANT_USERLIST
UserList *userptr = NULL;
ShitList *shitptr = NULL;
#endif
WhowasList *check_op = NULL;

int	flag;

	if (from && *from && !strchr(from, '.'))
		return;

	if (!channel || !are_you_opped(channel->channel) || !nick || !ThisNick || wild_match(nick, get_server_nickname(from_server)))
		return;
	if (!(flag = get_cset_int_var(channel->csets, HACKING_CSET)))
		return;
	if ((ThisNick->sent_deop) && (now - ThisNick->sent_deop_time < 10))
		return;

#ifdef WANT_USERLIST
	userptr = ThisNick->userlist;
	shitptr = ThisNick->shitlist;
#endif
	check_op = check_whosplitin_buffer(nick, ThisNick->host, channel->channel, 0);
	if (check_op && check_op->has_ops)
		return;
		
#ifdef WANT_USERLIST
	if ( !userptr || (userptr && !check_channel_match(userptr->channels, channel->channel)) ||
		(shitptr && check_channel_match(shitptr->channels, channel->channel)))
#endif
	{
		switch(flag)
		{
			case 1:
			case 3:
				if (is_chanop(channel->channel, nick))
					add_mode(channel, "o", 0, nick, NULL, get_int_var(NUM_OPMODES_VAR));
				ThisNick->sent_deop++;
				ThisNick->sent_deop_time = now;
			case 2:
				if (flag != 1)
					bitchsay("NetHack detected on %s by %s!%s", channel->channel, nick, ThisNick->host); 
			case 0:
			default:
				break;
		}
	}
}
Esempio n. 14
0
static void got_uninvite(struct chanset_t *chan, char *nick, char *from,
                         char *who, char *ch, struct userrec *u)
{
  masklist *inv = chan->channel.invite, *old = NULL;

  while (inv->mask[0] && rfc_casecmp(inv->mask, who)) {
    old = inv;
    inv = inv->next;
  }
  if (inv->mask[0]) {
    if (old)
      old->next = inv->next;
    else
      chan->channel.invite = inv->next;
    nfree(inv->mask);
    nfree(inv->who);
    nfree(inv);
  }
  check_tcl_mode(nick, from, u, chan->dname, "-I", who);
  if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
    return;

  if (channel_pending(chan))
    return;

  if (u_sticky_mask(chan->invites, who) || u_sticky_mask(global_invites, who))
    add_mode(chan, '+', 'I', who);
  if (!nick[0] && glob_bot(user) && !glob_master(user) && !chan_master(user) &&
      (chan->channel.mode & CHANINV))
    add_mode(chan, '+', 'I', who);
  if ((u_equals_mask(global_invites, who) ||
      u_equals_mask(chan->invites, who)) && me_op(chan) &&
      !channel_dynamicinvites(chan) && (!glob_bot(user) ||
      !(bot_flags(u) & BOT_SHARE)))
    add_mode(chan, '+', 'I', who);
}
Esempio n. 15
0
void check_shit(ChannelList *chan)
{
ShitList *Bans;
	if (!chan || !chan->chop || !shitlist_list || chan->server <= -1 || !get_cset_int_var(chan->csets, SHITLIST_CSET))
		return;
	if (!check_channel_match(get_string_var(PROTECT_CHANNELS_VAR), chan->channel))
		return;
	for (Bans = shitlist_list; Bans; Bans = Bans->next)
	{
		/* this is a permanent ban */
		if (!check_channel_match(Bans->channels, chan->channel))
			continue;
		if ((Bans->level == 4) && !ban_is_on_channel(Bans->filter, chan) && !eban_is_on_channel(Bans->filter, chan))
			add_mode(chan, "b", 1, Bans->filter, NULL, get_int_var(NUM_BANMODES_VAR));
	}
	flush_mode_all(chan);
}
Esempio n. 16
0
void backspace()
{
	char_t the_char[7]; /* the deleted char, allow 6 unsigned chars plus a null */
	int n = prev_utf8_char_size();

	curbp->b_point = movegap(curbp, curbp->b_point);

	if (curbp->b_buf < (curbp->b_gap - (n - 1)) ) {
		curbp->b_gap -= n; /* increase start of gap by size of char */
		add_mode(curbp, B_MODIFIED);

		/* record the backspaced chars in the undo structure */
		memcpy(the_char, curbp->b_gap, n);
		the_char[n] = '\0'; /* null terminate, the backspaced char(s) */
		curbp->b_point = pos(curbp, curbp->b_egap);
		//debug("point after bs = %ld\n", curbp->b_point);
		add_undo(curbp, UNDO_T_BACKSPACE, curbp->b_point, the_char, NULL);
	}

	curbp->b_point = pos(curbp, curbp->b_egap);
}
Esempio n. 17
0
void sync_shitlist(ShitList *added, int type)
{
ChannelList *chan;
NickList *nick;
int i;
char tmp[BIG_BUFFER_SIZE+1];
char *check;
	
	for (i = 0; i < server_list_size(); i ++)
	{
		for (chan = get_server_channels(i); chan; chan = chan->next)
		{
			for (nick = next_nicklist(chan, NULL); nick; nick = next_nicklist(chan, nick))
			{
				check = clear_server_flags(nick->host);
				sprintf(tmp, "%s!%s", nick->nick, check);
				if (wild_match(added->filter, tmp))
				{
					if (type) 
					{
						nick->shitlist = added;
						check_auto(chan->channel, nick, chan);
					}
					else
					{
						BanList *b = NULL;
						nick->shitlist = NULL;
						if ((b = ban_is_on_channel(tmp, chan)) && !eban_is_on_channel(tmp, chan))
							add_mode(chan, "b", 0, b->ban, NULL, get_int_var(NUM_BANMODES_VAR));
					}
				}
			}
			flush_mode_all(chan);
		}
	}
}
Esempio n. 18
0
static void setup_modi ( void )
{
    const char *const sep     = ",";
    char              *savept = NULL;
    // Make a copy, as strtok will modify it.
    char              *switcher_str = g_strdup ( config.modi );
    // Split token on ','. This modifies switcher_str.
    for ( char *token = strtok_r ( switcher_str, sep, &savept ); token != NULL; token = strtok_r ( NULL, sep, &savept ) ) {
        add_mode ( token );
    }
    // Free string that was modified by strtok_r
    g_free ( switcher_str );
    // We cannot do this in main loop, as we create pointer to string,
    // and re-alloc moves that pointer.
    mode_set_config ( &ssh_mode );
    mode_set_config ( &run_mode );
    mode_set_config ( &drun_mode );

#ifdef WINDOW_MODE
    mode_set_config ( &window_mode );
    mode_set_config ( &window_mode_cd );
#endif // WINDOW_MODE
    mode_set_config ( &combi_mode );
}
Esempio n. 19
0
void userhost_unban(UserhostItem *stuff, char *nick1, char *args)
{
char *tmp;
ChannelList *chan;
char *channel = NULL;
BanList *bans;

char *host = NULL;
char *ip_str = NULL;
WhowasList *whowas = NULL;
NickList *n = NULL;
int count = 0;
int old_server = from_server;

	
	if (!stuff || !stuff->nick || !nick1 || 
		!strcmp(stuff->user, "<UNKNOWN>") || 
		my_stricmp(stuff->nick, nick1))
	{
		if (nick1 && (whowas = check_whowas_nick_buffer(nick1, args, 0)))
		{
			malloc_sprintf(&host, "%s!%s", whowas->nicklist->nick, whowas->nicklist->host);
			bitchsay("Using WhoWas info for unban of %s ", nick1);
			n = whowas->nicklist;
		}
		else if (nick1)
		{
			bitchsay("No match for the unban of %s on %s", nick1, args);
			return;
		}
		if (!nick1)
			return;
	}
	else
	{
		tmp = clear_server_flags(stuff->user);
		malloc_sprintf(&host, "%s!%s@%s",stuff->nick, tmp, stuff->host); 
	}

	channel = next_arg(args, &args);
	if (args && *args)
		from_server = atoi(args);
	if (!(chan = prepare_command(&from_server, channel, NEED_OP)))
	{
		new_free(&host);
		return;
	}
	if (!n)
		n = find_nicklist_in_channellist(stuff->nick, chan, 0);

	if (n && n->ip)
	{
		size_t len = strlen(n->nick)+strlen(n->host)+strlen(n->ip)+10;
		ip_str = alloca(len); 
		*ip_str = 0;
		strmopencat(ip_str, len, stuff->nick, "!", stuff->user, "@", n->ip, NULL);
	}
	for (bans = chan->bans; bans; bans = bans->next)
	{
		if (!bans->sent_unban && (wild_match(bans->ban, host) || (ip_str && wild_match(bans->ban, ip_str))) )
		{
			add_mode(chan, "b", 0, bans->ban, NULL, get_int_var(NUM_BANMODES_VAR));
			bans->sent_unban++;
			count++;
		}			
	}	

	flush_mode_all(chan);
	if (!count)
		bitchsay("No match for Unban of %s on %s", nick1, args);
	new_free(&host);
	from_server = old_server;
}
Esempio n. 20
0
static void check_expired_chanstuff()
{
    masklist *b, *e;
    memberlist *m, *n;
    char *key, s[UHOSTLEN];
    struct chanset_t *chan;
    struct flag_record fr = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 };

    if (!server_online)
        return;
    for (chan = chanset; chan; chan = chan->next) {
        if (channel_active(chan)) {
            if (me_op(chan) || me_halfop(chan)) {
                if (channel_dynamicbans(chan) && chan->ban_time)
                    for (b = chan->channel.ban; b->mask[0]; b = b->next)
                        if (now - b->timer > 60 * chan->ban_time &&
                                !u_sticky_mask(chan->bans, b->mask) &&
                                !u_sticky_mask(global_bans, b->mask) &&
                                expired_mask(chan, b->who)) {
                            putlog(LOG_MODES, chan->dname,
                                   "(%s) Channel ban on %s expired.", chan->dname, b->mask);
                            add_mode(chan, '-', 'b', b->mask);
                            b->timer = now;
                        }

                if (use_exempts && channel_dynamicexempts(chan) && chan->exempt_time)
                    for (e = chan->channel.exempt; e->mask[0]; e = e->next)
                        if (now - e->timer > 60 * chan->exempt_time &&
                                !u_sticky_mask(chan->exempts, e->mask) &&
                                !u_sticky_mask(global_exempts, e->mask) &&
                                expired_mask(chan, e->who)) {
                            /* Check to see if it matches a ban */
                            int match = 0;

                            for (b = chan->channel.ban; b->mask[0]; b = b->next)
                                if (mask_match(b->mask, e->mask)) {
                                    match = 1;
                                    break;
                                }
                            /* Leave this extra logging in for now. Can be removed later
                             * Jason
                             */
                            if (match) {
                                putlog(LOG_MODES, chan->dname,
                                       "(%s) Channel exemption %s NOT expired. Exempt still set!",
                                       chan->dname, e->mask);
                            } else {
                                putlog(LOG_MODES, chan->dname,
                                       "(%s) Channel exemption on %s expired.",
                                       chan->dname, e->mask);
                                add_mode(chan, '-', 'e', e->mask);
                            }
                            e->timer = now;
                        }

                if (use_invites && channel_dynamicinvites(chan) &&
                        chan->invite_time && !(chan->channel.mode & CHANINV))
                    for (b = chan->channel.invite; b->mask[0]; b = b->next)
                        if (now - b->timer > 60 * chan->invite_time &&
                                !u_sticky_mask(chan->invites, b->mask) &&
                                !u_sticky_mask(global_invites, b->mask) &&
                                expired_mask(chan, b->who)) {
                            putlog(LOG_MODES, chan->dname,
                                   "(%s) Channel invitation on %s expired.",
                                   chan->dname, b->mask);
                            add_mode(chan, '-', 'I', b->mask);
                            b->timer = now;
                        }

                if (chan->idle_kick)
                    for (m = chan->channel.member; m && m->nick[0]; m = m->next)
                        if (now - m->last >= chan->idle_kick * 60 &&
                                !match_my_nick(m->nick) && !chan_issplit(m)) {
                            sprintf(s, "%s!%s", m->nick, m->userhost);
                            get_user_flagrec(m->user ? m->user : get_user_by_host(s),
                                             &fr, chan->dname);
                            if ((!(glob_bot(fr) || glob_friend(fr) || (glob_op(fr) &&
                                    !chan_deop(fr)) || chan_friend(fr) || chan_op(fr))) &&
                                    (me_op(chan) || (me_halfop(chan) && !chan_hasop(m)))) {
                                dprintf(DP_SERVER, "KICK %s %s :idle %d min\n", chan->name,
                                        m->nick, chan->idle_kick);
                                m->flags |= SENTKICK;
                            }
                        }
            }
            for (m = chan->channel.member; m && m->nick[0]; m = n) {
                n = m->next;
                if (m->split && now - m->split > wait_split) {
                    sprintf(s, "%s!%s", m->nick, m->userhost);
                    check_tcl_sign(m->nick, m->userhost,
                                   m->user ? m->user : get_user_by_host(s),
                                   chan->dname, "lost in the netsplit");
                    putlog(LOG_JOIN, chan->dname,
                           "%s (%s) got lost in the net-split.", m->nick, m->userhost);
                    killmember(chan, m->nick);
                }
                m = n;
            }
            check_lonely_channel(chan);
        } else if (!channel_inactive(chan) && !channel_pending(chan)) {

            key = chan->channel.key[0] ? chan->channel.key : chan->key_prot;
            if (key[0])
                dprintf(DP_SERVER, "JOIN %s %s\n",
                        chan->name[0] ? chan->name : chan->dname, key);
            else
                dprintf(DP_SERVER, "JOIN %s\n",
                        chan->name[0] ? chan->name : chan->dname);
        }
    }
}
Esempio n. 21
0
/* Dependant on revenge_mode, punish the offender.
 */
static void punish_badguy(struct chanset_t *chan, char *whobad,
                          struct userrec *u, char *badnick, char *victim,
                          int mevictim, int type)
{
    char reason[1024], ct[81], *kick_msg;
    memberlist *m;
    struct flag_record fr = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 };

    m = ismember(chan, badnick);
    if (!m)
        return;
    get_user_flagrec(u, &fr, chan->dname);

    /* Get current time into a string */
    egg_strftime(ct, 7, "%d %b", localtime(&now));

    /* Put together log and kick messages */
    reason[0] = 0;
    switch (type) {
    case REVENGE_KICK:
        kick_msg = IRC_KICK_PROTECT;
        simple_sprintf(reason, "kicked %s off %s", victim, chan->dname);
        break;
    case REVENGE_DEOP:
        simple_sprintf(reason, "deopped %s on %s", victim, chan->dname);
        kick_msg = IRC_DEOP_PROTECT;
        break;
    default:
        kick_msg = "revenge!";
    }
    putlog(LOG_MISC, chan->dname, "Punishing %s (%s)", badnick, reason);

    /* Set the offender +d */
    if ((chan->revenge_mode > 0) && !(chan_deop(fr) || glob_deop(fr))) {
        char s[UHOSTLEN], s1[UHOSTLEN];
        memberlist *mx = NULL;

        /* Removing op */
        if (chan_op(fr) || (glob_op(fr) && !chan_deop(fr))) {
            fr.match = FR_CHAN;
            if (chan_op(fr))
                fr.chan &= ~USER_OP;
            else
                fr.chan |= USER_DEOP;
            set_user_flagrec(u, &fr, chan->dname);
            putlog(LOG_MISC, "*", "No longer opping %s[%s] (%s)", u->handle, whobad,
                   reason);
        }
        /* ... or just setting to deop */
        else if (u) {
            /* In the user list already, cool :) */
            fr.match = FR_CHAN;
            fr.chan |= USER_DEOP;
            set_user_flagrec(u, &fr, chan->dname);
            simple_sprintf(s, "(%s) %s", ct, reason);
            putlog(LOG_MISC, "*", "Now deopping %s[%s] (%s)", u->handle, whobad, s);
        }
        /* ... or creating new user and setting that to deop */
        else {
            strcpy(s1, whobad);
            maskaddr(s1, s, chan->ban_type);
            strcpy(s1, badnick);
            /* If that handle exists use "badX" (where X is an increasing number)
             * instead.
             */
            while (get_user_by_handle(userlist, s1)) {
                if (!strncmp(s1, "bad", 3)) {
                    int i;

                    i = atoi(s1 + 3);
                    simple_sprintf(s1 + 3, "%d", i + 1);
                } else
                    strcpy(s1, "bad1");   /* Start with '1' */
            }
            userlist = adduser(userlist, s1, s, "-", 0);
            fr.match = FR_CHAN;
            fr.chan = USER_DEOP;
            fr.udef_chan = 0;
            u = get_user_by_handle(userlist, s1);
            if ((mx = ismember(chan, badnick)))
                mx->user = u;
            set_user_flagrec(u, &fr, chan->dname);
            simple_sprintf(s, "(%s) %s (%s)", ct, reason, whobad);
            set_user(&USERENTRY_COMMENT, u, (void *) s);
            putlog(LOG_MISC, "*", "Now deopping %s (%s)", whobad, reason);
        }
    }

    /* Always try to deop the offender */
    if (!mevictim)
        add_mode(chan, '-', 'o', badnick);
    /* Ban. Should be done before kicking. */
    if (chan->revenge_mode > 2) {
        char s[UHOSTLEN], s1[UHOSTLEN];

        splitnick(&whobad);
        maskaddr(whobad, s1, chan->ban_type);
        simple_sprintf(s, "(%s) %s", ct, reason);
        u_addban(chan, s1, botnetnick, s, now + (60 * chan->ban_time), 0);
        if (!mevictim && HALFOP_CANDOMODE('b')) {
            add_mode(chan, '+', 'b', s1);
            flush_mode(chan, QUICK);
        }
    }
    /* Kick the offender */
    if (!mevictim && (chan->revenge_mode > 1) && (!channel_dontkickops(chan) ||
            (!chan_op(fr) && (!glob_op(fr) || chan_deop(fr)))) &&
            !chan_sentkick(m) && (me_op(chan) || (me_halfop(chan) &&
                                  !chan_hasop(m) && (strchr(NOHALFOPS_MODES, 'b') == NULL)))) {
        dprintf(DP_MODE, "KICK %s %s :%s\n", chan->name, badnick, kick_msg);
        m->flags |= SENTKICK;
    }
}
Esempio n. 22
0
static void got_dehalfop(struct chanset_t *chan, char *nick, char *from,
                         char *who, struct userrec *opu)
{
  memberlist *m;
  char ch[sizeof chan->name];
  char s[UHOSTLEN], s1[UHOSTLEN];
  struct userrec *u;
  int had_halfop;

  m = ismember(chan, who);
  if (!m) {
    if (channel_pending(chan))
      return;
    putlog(LOG_MISC, chan->dname, CHAN_BADCHANMODE, chan->dname, who);
    chan->status |= CHAN_PEND;
    refresh_who_chan(chan->name);
    return;
  }

  strcpy(ch, chan->name);
  simple_sprintf(s, "%s!%s", m->nick, m->userhost);
  simple_sprintf(s1, "%s!%s", nick, from);
  u = get_user_by_host(s);
  get_user_flagrec(u, &victim, chan->dname);

  had_halfop = chan_hasop(m);
  /* Flags need to be set correctly right from the beginning now, so that
   * add_mode() doesn't get irritated.
   */
  m->flags &= ~(CHANHALFOP | SENTDEHALFOP | FAKEHALFOP);
  check_tcl_mode(nick, from, opu, chan->dname, "-h", who);
  if (!(chan = modebind_refresh(ch, from, &user, s, &victim)) ||
      !(m = ismember(chan, who)))
    return;
  /* Check comments in got_op()  (drummer) */
  m->flags &= ~WASHALFOP;

  if (channel_pending(chan))
    return;

  /* Dehalfop'd someone on my oplist? */
  if (HALFOP_CANDOMODE('h')) {
    int ok = 1;

    if (!glob_dehalfop(victim) && !chan_dehalfop(victim)) {
      if (channel_protecthalfops(chan) && (glob_master(victim) ||
          chan_master(victim) || glob_halfop(victim) || chan_halfop(victim)))
        ok = 0;
      else if (channel_protectfriends(chan) && (glob_friend(victim) ||
               chan_friend(victim)))
        ok = 0;
    }
    if ((reversing || !ok) && had_halfop && !match_my_nick(nick) &&
        rfc_casecmp(who, nick) && !match_my_nick(who) && !glob_master(user) &&
        !chan_master(user) && !glob_bot(user) && ((chan_halfop(victim) ||
        (glob_halfop(victim) && !chan_dehalfop(victim))) ||
        !channel_bitch(chan)))
      add_mode(chan, '+', 'h', who);
  }

  if (!nick[0])
    putlog(LOG_MODES, chan->dname, "TS resync (%s): %s deopped by %s",
           chan->dname, who, from);
  if (!(m->flags & (CHANVOICE | STOPWHO))) {
    chan->status |= CHAN_PEND;
    refresh_who_chan(chan->name);
    m->flags |= STOPWHO;
  }
}
Esempio n. 23
0
static void got_halfop(struct chanset_t *chan, char *nick, char *from,
                       char *who, struct userrec *opu,
                       struct flag_record *opper)
{
  memberlist *m;
  char s[UHOSTLEN];
  char ch[sizeof chan->name];
  struct userrec *u;
  int check_chan = 0;
  int snm = chan->stopnethack_mode;

  m = ismember(chan, who);
  if (!m) {
    if (channel_pending(chan))
      return;
    putlog(LOG_MISC, chan->dname, CHAN_BADCHANMODE, chan->dname, who);
    chan->status |= CHAN_PEND;
    refresh_who_chan(chan->name);
    return;
  }

  /* Did *I* just get halfopped? */
  if (!me_op(chan) && !me_halfop(chan) && match_my_nick(who))
    check_chan = 1;

  strcpy(ch, chan->name);
  simple_sprintf(s, "%s!%s", m->nick, m->userhost);
  if (!m->user)
    u = get_user_by_host(s);
  else
    u = m->user;

  get_user_flagrec(u, &victim, chan->dname);
  /* Flags need to be set correctly right from the beginning now, so that
   * add_mode() doesn't get irritated.
   */
  m->flags |= CHANHALFOP;
  check_tcl_mode(nick, from, opu, chan->dname, "+h", who);
  if (!(chan = modebind_refresh(ch, from, opper, s, &victim)) ||
      !(m = ismember(chan, who)))
    return;
  m->flags &= ~SENTHALFOP;

  if (channel_pending(chan))
    return;

  if (nick[0] && HALFOP_CANDOMODE('h') && !match_my_nick(who) &&
      !match_my_nick(nick)) {
    if (channel_bitch(chan) && !(glob_master(*opper) || glob_bot(*opper)) &&
        !chan_master(*opper) && !(glob_halfop(victim) || glob_op(victim) ||
        glob_bot(victim)) && !chan_op(victim) && !chan_halfop(victim))
      add_mode(chan, '-', 'h', who);
    else if ((chan_dehalfop(victim) || (glob_dehalfop(victim) &&
             !chan_halfop(victim))) && !glob_master(*opper) &&
             !chan_master(*opper))
      add_mode(chan, '-', 'h', who);
    else if (reversing)
      add_mode(chan, '-', 'h', who);
  } else if (reversing && HALFOP_CANDOMODE('h') && !match_my_nick(who) &&
             !match_my_nick(nick))
    add_mode(chan, '-', 'h', who);
  if (!nick[0] && HALFOP_CANDOMODE('h') && !match_my_nick(who)) {
    if (chan_dehalfop(victim) || (glob_dehalfop(victim) &&
        !chan_halfop(victim))) {
      m->flags |= FAKEHALFOP;
      add_mode(chan, '-', 'h', who);
    } else if (snm > 0 && snm < 7 && !((channel_autohalfop(chan) ||
             glob_autohalfop(victim) || chan_autohalfop(victim)) &&
             (chan_halfop(victim) || (glob_halfop(victim) &&
             !chan_dehalfop(victim)))) && !glob_exempt(victim) &&
             !chan_exempt(victim)) {
      if (snm == 5)
        snm = channel_bitch(chan) ? 1 : 3;
      if (snm == 6)
        snm = channel_bitch(chan) ? 4 : 2;
      if (chan_washalfoptest(victim) || glob_washalfoptest(victim) || snm == 2) {
        if (!chan_washalfop(m)) {
          m->flags |= FAKEHALFOP;
          add_mode(chan, '-', 'h', who);
        }
      } else if (!(chan_halfop(victim) || (glob_halfop(victim) &&
               !chan_dehalfop(victim)))) {
        if (snm == 1 || snm == 4 || (snm == 3 && !chan_washalfop(m))) {
          add_mode(chan, '-', 'h', who);
          m->flags |= FAKEHALFOP;
        }
      } else if (snm == 4 && !chan_washalfop(m)) {
        add_mode(chan, '-', 'h', who);
        m->flags |= FAKEHALFOP;
      }
    }
  }
  m->flags |= WASHALFOP;
  if (check_chan)
    recheck_channel(chan, 1);
}
Esempio n. 24
0
static void cmd_pls_mask(const char type, int idx, char *par)
{
  const char *cmd = (type == 'b' ? "ban" : type == 'e' ? "exempt" : "invite");

  if (!par[0]) {
usage:
    dprintf(idx, "Usage: +%s <hostmask> [channel] [%%<XdXhXm>] [reason]\n", cmd);
    return;
  }

  char *chname = NULL, *who = NULL, s[UHOSTLEN] = "", s1[UHOSTLEN] = "", *p = NULL, *p_expire = NULL;
  unsigned long int expire_time = 0, expire_foo;
  int sticky = 0;
  struct chanset_t *chan = NULL;

  who = newsplit(&par);
  if (par[0] && strchr(CHANMETA, par[0]))
    chname = newsplit(&par);

  /* Did they mix up the two params? */
  if (!chname && strchr(CHANMETA, who[0])) {
    if (par[0]) {
      chname = who;
      who = newsplit(&par);
    } else {
      goto usage;
    }
  }

  if (chname || !(dcc[idx].user->flags & USER_MASTER)) {
    if (!chname)
      chname = dcc[idx].u.chat->con_chan;
    get_user_flagrec(dcc[idx].user, &user, chname);
    chan = findchan_by_dname(chname);
    /* *shrug* ??? (guppy:10Feb1999) */
    if (!chan || (chan && privchan(user, chan, PRIV_OP))) {
      dprintf(idx, "No such channel.\n");
      return;
    } else if (!chk_op(user, chan)) {
      dprintf(idx, "You don't have access to set %ss on %s.\n", cmd, chname);
      return;
    }
  } else
    chan = 0;
  /* Added by Q and Solal -- Requested by Arty2, special thanx :) */
  if (par[0] == '%') {
    p = newsplit(&par);
    p_expire = p + 1;
    while (*(++p) != 0) {
      switch (tolower(*p)) {
	case 'd':
	  *p = 0;
	  expire_foo = strtol(p_expire, NULL, 10);
	  if (expire_foo > 365)
	    expire_foo = 365;
	  expire_time += 86400 * expire_foo;
	  p_expire = p + 1;
	  break;
	case 'h':
	  *p = 0;
	  expire_foo = strtol(p_expire, NULL, 10);
	  if (expire_foo > 8760)
	    expire_foo = 8760;
	  expire_time += 3600 * expire_foo;
	  p_expire = p + 1;
	  break;
	case 'm':
	  *p = 0;
	  expire_foo = strtol(p_expire, NULL, 10);
	  if (expire_foo > 525600)
	    expire_foo = 525600;
	  expire_time += 60 * expire_foo;
	  p_expire = p + 1;
	}
    }
  }
  if (!par[0])
    par = "requested";
  else if (strlen(par) > MASKREASON_MAX)
    par[MASKREASON_MAX] = 0;
  if (strlen(who) > UHOSTMAX - 4)
    who[UHOSTMAX - 4] = 0;
  /* Fix missing ! or @ BEFORE checking against myself */
  if (!strchr(who, '!')) {
    if (!strchr(who, '@'))
      simple_snprintf(s, sizeof s, "%s!*@*", who);	/* Lame nick ban */
    else
      simple_snprintf(s, sizeof s, "*!%s", who);
  } else if (!strchr(who, '@'))
    simple_snprintf(s, sizeof s, "%s@*", who);	/* brain-dead? */
  else
    strlcpy(s, who, sizeof s);
    if (conf.bot->hub)
      simple_snprintf(s1, sizeof s1, "%s!%s@%s", origbotname, botuser, conf.bot->net.host);
    else
      simple_snprintf(s1, sizeof s1, "%s!%s", botname, botuserhost);
  if (type == 'b' && s1[0] && wild_match(s, s1)) {
    dprintf(idx, "I'm not going to ban myself.\n");
    putlog(LOG_CMDS, "*", "#%s# attempted +ban %s", dcc[idx].nick, s);
    return;
  }
  /* IRC can't understand bans longer than 70 characters */
  if (strlen(s) > 70) {
    s[69] = '*';
    s[70] = 0;
  }
  if (chan) {
    u_addmask(type, chan, s, dcc[idx].nick, par, expire_time ? now + expire_time : 0, 0);
    if (par[0] == '*') {
      sticky = 1;
      par++;
      putlog(LOG_CMDS, "*", "#%s# (%s) +%s %s %s (%s) (sticky)", dcc[idx].nick, dcc[idx].u.chat->con_chan, cmd, s, chan->dname, par);
      dprintf(idx, "New %s sticky %s: %s (%s)\n", chan->dname, cmd, s, par);
    } else {
      putlog(LOG_CMDS, "*", "#%s# (%s) +%s %s %s (%s)", dcc[idx].nick, dcc[idx].u.chat->con_chan, cmd, s, chan->dname, par);
      dprintf(idx, "New %s %s: %s (%s)\n", chan->dname, cmd, s, par);
    }
    if (!conf.bot->hub) {
      if (type == 'e' || type == 'I')
        add_mode(chan, '+', type, s);
      /* Avoid unnesessary modes if you got +dynamicbans
       */
      else
        check_this_ban(chan, s, sticky);
    } else
      write_userfile(idx);
  } else {
    u_addmask(type, NULL, s, dcc[idx].nick, par, expire_time ? now + expire_time : 0, 0);
    if (par[0] == '*') {
      sticky = 1;
      par++;
      putlog(LOG_CMDS, "*", "#%s# (GLOBAL) +%s %s (%s) (sticky)", dcc[idx].nick, cmd, s, par);
      dprintf(idx, "New sticky %s: %s (%s)\n", cmd, s, par);
    } else {
      putlog(LOG_CMDS, "*", "#%s# (GLOBAL) +%s %s (%s)", dcc[idx].nick, cmd, s, par);
      dprintf(idx, "New %s: %s (%s)\n", cmd, s, par);
    }
    if (!conf.bot->hub) {
      for (chan = chanset; chan != NULL; chan = chan->next) {
        if (type == 'b')
          check_this_ban(chan, s, sticky);
        else
          add_mode(chan, '+', type, s);
      }
    } else
      write_userfile(idx);
  }
}
Esempio n. 25
0
static void cmd_mns_mask(const char type, int idx, char *par)
{
  const char *cmd = (type == 'b' ? "ban" : type == 'e' ? "exempt" : "invite");

  if (!par[0]) {
usage:
    dprintf(idx, "Usage: -%s <hostmask> [channel]\n", cmd);
    return;
  }

  int i = 0, j;
  struct chanset_t *chan = NULL;
  char s[UHOSTLEN] = "", *who = NULL, *chname = NULL, *mask = NULL;
  masklist *m = NULL;

  who = newsplit(&par);
  if (par[0] && strchr(CHANMETA, par[0]))
    chname = newsplit(&par);

  /* Did they mix up the two params? */
  if (!chname && strchr(CHANMETA, who[0])) {
    if (par[0]) {
      chname = who;
      who = newsplit(&par);
    } else {
      goto usage;
    }
  }

  if (!chname)
    chname = dcc[idx].u.chat->con_chan;

  if (chname || !(dcc[idx].user->flags & USER_MASTER)) {
    if (!chname)
      chname = dcc[idx].u.chat->con_chan;
    get_user_flagrec(dcc[idx].user, &user, chname);

    if (strchr(CHANMETA, chname[0]) && privchan(user, findchan_by_dname(chname), PRIV_OP)) {
      dprintf(idx, "No such channel.\n");
      return;
    }
    if (!chk_op(user, findchan_by_dname(chname)))
      return;
  }
  strlcpy(s, who, sizeof s);
  i = u_delmask(type, NULL, s, (dcc[idx].user->flags & USER_MASTER));
  if (i > 0) {
    if (lastdeletedmask)
      mask = lastdeletedmask;
    else
      mask = s;
    putlog(LOG_CMDS, "*", "#%s# -%s %s", dcc[idx].nick, cmd, mask);
    dprintf(idx, "%s %s: %s\n", "Removed", cmd, s);
    if (!conf.bot->hub) {
      for (chan = chanset; chan != NULL; chan = chan->next)
        add_mode(chan, '-', type, mask);
    } else
      write_userfile(idx);
    return;
  }
  /* Channel-specific ban? */
  if (chname)
    chan = findchan_by_dname(chname);
  if (chan) {
    m = type == 'b' ? chan->channel.ban : type == 'e' ? chan->channel.exempt : chan->channel.invite;
    if (str_isdigit(who) && (i = atoi(who)) > 0) {
      simple_snprintf(s, sizeof s, "%d", i);
      j = u_delmask(type, chan, s, 1);
      if (j > 0) {
        if (lastdeletedmask)
          mask = lastdeletedmask;
        else
          mask = s;
	putlog(LOG_CMDS, "*", "#%s# (%s) -%s %s", dcc[idx].nick, chan->dname, cmd, mask);
	dprintf(idx, "Removed %s channel %s: %s\n", chan->dname, cmd, mask);
        if (!conf.bot->hub)
          add_mode(chan, '-', type, mask);
        else
          write_userfile(idx);
	return;
      }
      i = 0;
      for (; m && m->mask && m->mask[0]; m = m->next) {
	if ((!u_equals_mask(type == 'b' ? global_bans : type == 'e' ? global_exempts :
	      global_invites, m->mask)) &&
	    (!u_equals_mask(type == 'b' ? chan->bans : type == 'e' ? chan->exempts :
	      chan->invites, m->mask))) {
	  i++;
	  if (i == -j) {
	    dprintf(idx, "%s %s '%s' on %s.\n", "Removed", cmd, m->mask, chan->dname);
	    putlog(LOG_CMDS, "*", "#%s# (%s) -%s %s [on channel]", dcc[idx].nick, chan->dname, cmd, who);

            if (!conf.bot->hub)
              add_mode(chan, '-', type, m->mask);
            else
              write_userfile(idx);
	    return;
	  }
	}
      }
    } else {
      j = u_delmask(type, chan, who, 1);
      if (j > 0) {
	putlog(LOG_CMDS, "*", "#%s# (%s) -%s %s", dcc[idx].nick, dcc[idx].u.chat->con_chan, cmd, who);
	dprintf(idx, "Removed %s channel %s: %s\n", chname, cmd, who);
        if (!conf.bot->hub)
          add_mode(chan, '-', type, who);
        else
          write_userfile(idx);
	return;
      }
      for (; m && m->mask && m->mask[0]; m = m->next) {
	if (!rfc_casecmp(m->mask, who)) {
	  dprintf(idx, "%s %s '%s' on %s.\n", "Removed", cmd, m->mask, chan->dname);
	  putlog(LOG_CMDS, "*", "#%s# (%s) -%s %s [on channel]", dcc[idx].nick, chan->dname, cmd, who);
          if (!conf.bot->hub)
            add_mode(chan, '-', type, m->mask);
          else
            write_userfile(idx);
	  return;
	}
      }
    }
  }
  dprintf(idx, "No such %s.\n", cmd);
}
Esempio n. 26
0
static void got_deop(struct chanset_t *chan, char *nick, char *from,
                     char *who, struct userrec *opu)
{
  memberlist *m;
  char ch[sizeof chan->name];
  char s[UHOSTLEN], s1[UHOSTLEN];
  struct userrec *u;
  int had_halfop;

  m = ismember(chan, who);
  if (!m) {
    if (channel_pending(chan))
      return;
    putlog(LOG_MISC, chan->dname, CHAN_BADCHANMODE, chan->dname, who);
    chan->status |= CHAN_PEND;
    refresh_who_chan(chan->name);
    return;
  }

  strcpy(ch, chan->name);
  simple_sprintf(s, "%s!%s", m->nick, m->userhost);
  simple_sprintf(s1, "%s!%s", nick, from);
  u = get_user_by_host(s);
  get_user_flagrec(u, &victim, chan->dname);

  had_halfop = chan_hasop(m);
  /* Flags need to be set correctly right from the beginning now, so that
   * add_mode() doesn't get irritated.
   */
  m->flags &= ~(CHANOP | SENTDEOP | FAKEOP);
  check_tcl_mode(nick, from, opu, chan->dname, "-o", who);
  if (!(chan = modebind_refresh(ch, from, &user, s, &victim)) ||
      !(m = ismember(chan, who)))
    return;
  m->flags &= ~WASOP;

  if (channel_pending(chan))
    return;

  if (HALFOP_CANDOMODE('o')) {
    int ok = 1;

    if (!glob_deop(victim) && !chan_deop(victim)) {
      if (channel_protectops(chan) && (glob_master(victim) ||
          chan_master(victim) || glob_op(victim) || chan_op(victim)))
        ok = 0;
      else if (channel_protectfriends(chan) && (glob_friend(victim) ||
               chan_friend(victim)))
        ok = 0;
    }
    if ((reversing || !ok) && had_halfop && !match_my_nick(nick) &&
        rfc_casecmp(who, nick) && !match_my_nick(who) && !glob_master(user) &&
        !chan_master(user) && !glob_bot(user) && ((chan_op(victim) ||
        (glob_op(victim) && !chan_deop(victim))) || !channel_bitch(chan)))
      add_mode(chan, '+', 'o', who);
  }

  if (!nick[0])
    putlog(LOG_MODES, chan->dname, "TS resync (%s): %s deopped by %s",
           chan->dname, who, from);

  /* Check for mass deop */
  if (nick[0])
    detect_chan_flood(nick, from, s1, chan, FLOOD_DEOP, who, 0);

  /* Having op hides your +v and +h status -- so now that someone's lost ops,
   * check to see if they have +v or +h
   */
  if (!(m->flags & (CHANVOICE | CHANHALFOP | STOPWHO))) {
    chan->status |= CHAN_PEND;
    refresh_who_chan(chan->name);
    m->flags |= STOPWHO;
  }

  /* Was the bot deopped? */
  if (match_my_nick(who)) {
    /* Cancel any pending kicks and modes */
    memberlist *m2;

    for (m2 = chan->channel.member; m2 && m2->nick[0]; m2 = m2->next)
      m2->flags &= ~(SENTKICK | SENTDEOP | SENTOP | SENTVOICE | SENTDEVOICE);

    check_tcl_need(chan->dname, "op");
    if (chan->need_op[0])
      do_tcl("need-op", chan->need_op);
    if (!nick[0])
      putlog(LOG_MODES, chan->dname, "TS resync deopped me on %s :(",
             chan->dname);
  }
  if (nick[0])
    maybe_revenge(chan, s1, s, REVENGE_DEOP);
}
Esempio n. 27
0
static gboolean startup ( G_GNUC_UNUSED gpointer data )
{
    TICK_N ( "Startup" );
    // flags to run immediately and exit
    char *sname = NULL;
    char *msg   = NULL;
    //
    // Sanity check
    if ( config_sanity_check ( ) ) {
        return G_SOURCE_REMOVE;
    }
    TICK_N ( "Config sanity check" );
    // Parse the keybindings.
    if ( !parse_keys_abe () ) {
        // Error dialog
        return G_SOURCE_REMOVE;
    }
    TICK_N ( "Parse ABE" );
    // Dmenu mode.
    if ( dmenu_mode == TRUE ) {
        // force off sidebar mode:
        config.sidebar_mode = FALSE;
        int retv = run_dmenu ();
        if ( retv ) {
            rofi_set_return_code ( EXIT_SUCCESS );
            // Directly exit.
            g_main_loop_quit ( main_loop );
        }
    }
    else if ( find_arg_str (  "-e", &( msg ) ) ) {
        int markup = FALSE;
        if ( find_arg ( "-markup" ) >= 0 ) {
            markup = TRUE;
        }
        if (  !show_error_message ( msg, markup ) ) {
            g_main_loop_quit ( main_loop );
        }
    }
    else if ( find_arg_str ( "-show", &sname ) == TRUE ) {
        int index = switcher_get ( sname );
        if ( index < 0 ) {
            // Add it to the list
            index = add_mode ( sname );
            // Complain
            if ( index >= 0 ) {
                fprintf ( stdout, "Mode %s not enabled. Please add it to the list of enabled modi: %s\n",
                          sname, config.modi );
                fprintf ( stdout, "Adding mode: %s\n", sname );
            }
            // Run it anyway if found.
        }
        if ( index >= 0 ) {
            run_switcher ( index );
        }
        else {
            fprintf ( stderr, "The %s switcher has not been enabled\n", sname );
            return G_SOURCE_REMOVE;
        }
    }
    else{
        // Daemon mode
        fprintf ( stderr, "Rofi daemon mode is now removed.\n" );
        fprintf ( stderr, "Please use your window manager binding functionality or xbindkeys to replace it.\n" );
        g_main_loop_quit ( main_loop );
    }

    return G_SOURCE_REMOVE;
}
Esempio n. 28
0
static int gotmode(char *from, char *origmsg)
{
  char *nick, *ch, *op, *chg, *msg;
  char s[UHOSTLEN], buf[511];
  char ms2[3];
  int z;
  struct userrec *u;
  memberlist *m;
  struct chanset_t *chan;

  strncpy(buf, origmsg, 510);
  buf[510] = 0;
  msg = buf;
  /* Usermode changes? */
  if (msg[0] && (strchr(CHANMETA, msg[0]) != NULL)) {
    ch = newsplit(&msg);
    chg = newsplit(&msg);
    reversing = 0;
    chan = findchan(ch);
    if (!chan) {
      putlog(LOG_MISC, "*", CHAN_FORCEJOIN, ch);
      dprintf(DP_SERVER, "PART %s\n", ch);
    } else if (channel_active(chan) || channel_pending(chan)) {
      z = strlen(msg);
      if (msg[--z] == ' ')      /* I hate cosmetic bugs :P -poptix */
        msg[z] = 0;
      putlog(LOG_MODES, chan->dname, "%s: mode change '%s %s' by %s", ch, chg,
             msg, from);
      u = get_user_by_host(from);
      get_user_flagrec(u, &user, ch);
      nick = splitnick(&from);
      m = ismember(chan, nick);
      if (m)
        m->last = now;
      if (m && channel_active(chan) && (me_op(chan) || (me_halfop(chan) &&
          !chan_hasop(m))) && !(glob_friend(user) || chan_friend(user) ||
          (channel_dontkickops(chan) && (chan_op(user) || (glob_op(user) &&
          !chan_deop(user))))) && !match_my_nick(nick)) {
        if (chan_fakeop(m) || chan_fakehalfop(m)) {
          putlog(LOG_MODES, ch, CHAN_FAKEMODE, ch);
          dprintf(DP_MODE, "KICK %s %s :%s\n", ch, nick, CHAN_FAKEMODE_KICK);
          m->flags |= SENTKICK;
          reversing = 1;
        } else if (!chan_hasop(m) && !chan_hashalfop(m) &&
                 !channel_nodesynch(chan)) {
          putlog(LOG_MODES, ch, CHAN_DESYNCMODE, ch);
          dprintf(DP_MODE, "KICK %s %s :%s\n", ch, nick, CHAN_DESYNCMODE_KICK);
          m->flags |= SENTKICK;
          reversing = 1;
        }
      }
      ms2[0] = '+';
      ms2[2] = 0;
      while ((ms2[1] = *chg)) {
        int todo = 0;

        switch (*chg) {
        case '+':
          ms2[0] = '+';
          break;
        case '-':
          ms2[0] = '-';
          break;
        case 'i':
          todo = CHANINV;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'p':
          todo = CHANPRIV;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 's':
          todo = CHANSEC;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'm':
          todo = CHANMODER;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'c':
          todo = CHANNOCLR;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'C':
          todo = CHANNOCTCP;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'R':
          todo = CHANREGON;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'M':
          todo = CHANMODREG;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'r':
          todo = CHANLONLY;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'D':
          todo = CHANDELJN;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'u':
          todo = CHANSTRIP;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'N':
          todo = CHANNONOTC;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'T':
          todo = CHANNOAMSG;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'd':
          todo = CHANINVIS;
          break;
        case 't':
          todo = CHANTOPIC;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'n':
          todo = CHANNOMSG;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'a':
          todo = CHANANON;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'q':
          todo = CHANQUIET;
          if (!nick[0] && bounce_modes)
            reversing = 1;
          break;
        case 'l':
          if (!nick[0] && bounce_modes)
            reversing = 1;
          if (ms2[0] == '-') {
            check_tcl_mode(nick, from, u, chan->dname, ms2, "");
            /* The Tcl proc might have modified/removed the chan or user */
            if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
              return 0;
            if (channel_active(chan)) {
              if (reversing && (chan->channel.maxmembers != 0)) {
                simple_sprintf(s, "%d", chan->channel.maxmembers);
                add_mode(chan, '+', 'l', s);
              } else if ((chan->limit_prot != 0) && !glob_master(user) &&
                         !chan_master(user) && !match_my_nick(nick)) {
                simple_sprintf(s, "%d", chan->limit_prot);
                add_mode(chan, '+', 'l', s);
              }
            }
            chan->channel.maxmembers = 0;
          } else {
            op = newsplit(&msg);
            fixcolon(op);
            if (op == '\0')
              break;
            chan->channel.maxmembers = atoi(op);
            check_tcl_mode(nick, from, u, chan->dname, ms2,
                           int_to_base10(chan->channel.maxmembers));
            /* The Tcl proc might have modified/removed the chan or user */
            if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
              return 0;
            if (channel_pending(chan))
              break;
            if ((reversing && !(chan->mode_pls_prot & CHANLIMIT)) ||
                ((chan->mode_mns_prot & CHANLIMIT) && !glob_master(user) &&
                !chan_master(user)))
              add_mode(chan, '-', 'l', "");
            if ((chan->limit_prot != chan->channel.maxmembers) &&
                (chan->mode_pls_prot & CHANLIMIT) && (chan->limit_prot != 0) &&
                !glob_master(user) && !chan_master(user)) {
              simple_sprintf(s, "%d", chan->limit_prot);
              add_mode(chan, '+', 'l', s);
            }
          }
          break;
        case 'k':
          if (ms2[0] == '+')
            chan->channel.mode |= CHANKEY;
          else
            chan->channel.mode &= ~CHANKEY;
          op = newsplit(&msg);
          fixcolon(op);
          if (op == '\0') {
            break;
          }
          check_tcl_mode(nick, from, u, chan->dname, ms2, op);
          /* The Tcl proc might have modified/removed the chan or user */
          if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
            return 0;
          if (ms2[0] == '+') {
            set_key(chan, op);
            if (channel_active(chan))
              got_key(chan, nick, from, op);
          } else {
            if (channel_active(chan)) {
              if (reversing && chan->channel.key[0])
                add_mode(chan, '+', 'k', chan->channel.key);
              else if (chan->key_prot[0] && !glob_master(user) &&
                       !chan_master(user) && !match_my_nick(nick))
                add_mode(chan, '+', 'k', chan->key_prot);
            }
            set_key(chan, NULL);
          }
          break;
        case 'o':
          op = newsplit(&msg);
          fixcolon(op);
          if (ms2[0] == '+')
            got_op(chan, nick, from, op, u, &user);
          else
            got_deop(chan, nick, from, op, u);
          break;
        case 'h':
          op = newsplit(&msg);
          fixcolon(op);
          if (ms2[0] == '+')
            got_halfop(chan, nick, from, op, u, &user);
          else
            got_dehalfop(chan, nick, from, op, u);
          break;
        case 'v':
          op = newsplit(&msg);
          fixcolon(op);
          m = ismember(chan, op);
          if (!m) {
            if (channel_pending(chan))
              break;
            putlog(LOG_MISC, chan->dname, CHAN_BADCHANMODE, chan->dname, op);
            chan->status |= CHAN_PEND;
            refresh_who_chan(chan->name);
          } else {
            simple_sprintf(s, "%s!%s", m->nick, m->userhost);
            get_user_flagrec(m->user ? m->user : get_user_by_host(s),
                             &victim, chan->dname);
            if (ms2[0] == '+') {
              m->flags &= ~SENTVOICE;
              m->flags |= CHANVOICE;
              check_tcl_mode(nick, from, u, chan->dname, ms2, op);
              if (!(chan = modebind_refresh(ch, from, &user, s, &victim)))
                return 0;
              if (channel_active(chan) && !glob_master(user) &&
                  !chan_master(user) && !match_my_nick(nick)) {
                if (chan_quiet(victim) ||
                    (glob_quiet(victim) && !chan_voice(victim)))
                  add_mode(chan, '-', 'v', op);
                else if (reversing)
                  add_mode(chan, '-', 'v', op);
              }
            } else {
              m->flags &= ~SENTDEVOICE;
              m->flags &= ~CHANVOICE;
              check_tcl_mode(nick, from, u, chan->dname, ms2, op);
              if (!(chan = modebind_refresh(ch, from, &user, s, &victim)))
                return 0;
              if (channel_active(chan) && !glob_master(user) &&
                  !chan_master(user) && !match_my_nick(nick)) {
                if ((channel_autovoice(chan) && !chan_quiet(victim) &&
                    (chan_voice(victim) || glob_voice(victim))) ||
                    (!chan_quiet(victim) && (glob_gvoice(victim) ||
                    chan_gvoice(victim))))
                  add_mode(chan, '+', 'v', op);
                else if (reversing)
                  add_mode(chan, '+', 'v', op);
              }
            }
          }
          break;
        case 'b':
          op = newsplit(&msg);
          fixcolon(op);
          if (ms2[0] == '+')
            got_ban(chan, nick, from, op, ch, u);
          else
            got_unban(chan, nick, from, op, ch, u);
          break;
        case 'e':
          op = newsplit(&msg);
          fixcolon(op);
          if (ms2[0] == '+')
            got_exempt(chan, nick, from, op, ch, u);
          else
            got_unexempt(chan, nick, from, op, ch, u);
          break;
        case 'I':
          op = newsplit(&msg);
          fixcolon(op);
          if (ms2[0] == '+')
            got_invite(chan, nick, from, op, ch, u);
          else
            got_uninvite(chan, nick, from, op, ch, u);
          break;
        }
        if (todo) {
          check_tcl_mode(nick, from, u, chan->dname, ms2, "");
          if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
            return 0;
          if (ms2[0] == '+')
            chan->channel.mode |= todo;
          else
            chan->channel.mode &= ~todo;
          if (channel_active(chan)) {
            if ((((ms2[0] == '+') && (chan->mode_mns_prot & todo)) ||
                ((ms2[0] == '-') && (chan->mode_pls_prot & todo))) &&
                !glob_master(user) && !chan_master(user) &&
                !match_my_nick(nick))
              add_mode(chan, ms2[0] == '+' ? '-' : '+', *chg, "");
            else if (reversing && ((ms2[0] == '+') ||
                     (chan->mode_pls_prot & todo)) && ((ms2[0] == '-') ||
                     (chan->mode_mns_prot & todo)))
              add_mode(chan, ms2[0] == '+' ? '-' : '+', *chg, "");
          }
        }
        chg++;
      }
      if (!me_op(chan) && !nick[0])
        chan->status |= CHAN_ASKEDMODES;
    }
  }
  return 0;
}
Esempio n. 29
0
static int
setup_video_modes( void )
{
	char *vmodes_file = get_filename_res("fbdev_prefs");
	struct fb_var_screeninfo v;
	int modes_added = 0;
	char buf[160];
	FILE *f=NULL;

	if( !vmodes_file )
		printm("---> molrc resource 'video_modes' is missing!\n");
	if( vmodes_file && (f=fopen( vmodes_file, "r")) ){
		int line, done=0, err, i;		
		for( line=0; !done; ){
			while( !(done=!fgets( buf, sizeof(buf), f )) ) {
				line++;
				if( buf[0] != '#' )
					break;
			}
			if( done )
				break;
			memset( &v, 0, sizeof(v) );
			err = sscanf(buf, "%d %d %d %d %d %d %d %d %d %d %d %d %d %d %d", 
				     &v.xres, &v.yres, &v.xres_virtual, &v.yres_virtual, &v.xoffset, &v.yoffset,
				     &v.pixclock, &v.left_margin, &v.right_margin, &v.upper_margin, &v.lower_margin,
 				     &v.hsync_len, &v.vsync_len, &v.sync, &v.vmode ) != 15;
			v.xres_virtual = v.xres;
			v.yres_virtual = v.yres;
			v.xoffset = v.yoffset = 0;
			if( !err ) {
				int ndepths, depth, rowbytes, page_offs, refresh;
				line++;
				err = fscanf(f, "%d %d", &ndepths, &refresh ) != 2;
				for( i=0; i<3; i++ ) {
					if( !err )
						err = fscanf( f, "%d %d %d", &depth, &rowbytes, &page_offs ) != 3;
					if( !err && i < ndepths ) {
						modes_added++;
						add_mode( &v, depth, rowbytes, page_offs, refresh );
					}
				}
				if(fgets( buf, sizeof(buf),  f) == NULL) {
					err = 1;
					break;
				}
			}
			if( err )
				printm("Line %d in '%s' is malformed.\n", line, vmodes_file );
		}
		fclose( f );
	}
	if( vmodes_file && !f ) {
		printm("---> Could not open the video modes configuration file (%s)\n", vmodes_file );
	}
	
	if( !modes_added ) {
		if( cv->startup_mode_ok ){
			struct fb_fix_screeninfo *fix = &cv->startup_fix;
			v = cv->startup_var;
			add_mode( &v, v.bits_per_pixel, fix->line_length, (int)fix->smem_start & 0xfff, (75<<16) );
		}
	}
	return !fbdev_module.modes;
}
Esempio n. 30
0
static void got_ban(struct chanset_t *chan, char *nick, char *from, char *who,
                    char *ch, struct userrec *u)
{
  char me[UHOSTLEN], s[UHOSTLEN], s1[UHOSTLEN];
  memberlist *m;
  struct userrec *targ;

  egg_snprintf(me, sizeof me, "%s!%s", botname, botuserhost);
  egg_snprintf(s, sizeof s, "%s!%s", nick, from);
  newban(chan, who, s);
  check_tcl_mode(nick, from, u, chan->dname, "+b", who);
  if (!(chan = modebind_refresh(ch, from, &user, NULL, NULL)))
    return;

  if (channel_pending(chan) || HALFOP_CANTDOMODE('b'))
    return;

  if (match_addr(who, me) && !isexempted(chan, me)) {
    add_mode(chan, '-', 'b', who);
    reversing = 1;
    return;
  }
  if (!match_my_nick(nick)) {
    if (nick[0] && channel_nouserbans(chan) && !glob_bot(user) &&
        !glob_master(user) && !chan_master(user)) {
      add_mode(chan, '-', 'b', who);
      return;
    }
    for (m = chan->channel.member; m && m->nick[0]; m = m->next) {
      egg_snprintf(s1, sizeof s1, "%s!%s", m->nick, m->userhost);
      if (match_addr(who, s1)) {
        targ = get_user_by_host(s1);
        if (targ) {
          get_user_flagrec(targ, &victim, chan->dname);
          if ((glob_friend(victim) || (glob_op(victim) && !chan_deop(victim)) ||
               chan_friend(victim) || chan_op(victim)) && !glob_master(user) &&
              !glob_bot(user) && !chan_master(user) && !isexempted(chan, s1)) {
            add_mode(chan, '-', 'b', who);
            return;
          }
        }
      }
    }
  }
  refresh_exempt(chan, who);
  if (nick[0] && channel_enforcebans(chan)) {
    register maskrec *b;
    int cycle;
    char resn[512] = "";

    for (cycle = 0; cycle < 2; cycle++) {
      for (b = cycle ? chan->bans : global_bans; b; b = b->next) {
        if (match_addr(b->mask, who)) {
          if (b->desc && b->desc[0] != '@')
            egg_snprintf(resn, sizeof resn, "%s %s", IRC_PREBANNED, b->desc);
          else
            resn[0] = 0;
        }
      }
    }
    kick_all(chan, who, resn[0] ? resn : IRC_BANNED,
             match_my_nick(nick) ? 0 : 1);
  }
  if (!nick[0] && (bounce_bans || bounce_modes) &&
      (!u_equals_mask(global_bans, who) || !u_equals_mask(chan->bans, who)))
    add_mode(chan, '-', 'b', who);
}