summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/extern.h1
-rw-r--r--include/modules.h8
-rw-r--r--include/regchannel.h6
-rw-r--r--include/services.h15
-rw-r--r--src/actions.c7
-rw-r--r--src/botserv.c58
-rw-r--r--src/channels.c157
-rw-r--r--src/chanserv.c81
-rw-r--r--src/core/bs_kick.c2
-rw-r--r--src/core/cs_akick.c13
-rw-r--r--src/core/cs_ban.c14
-rw-r--r--src/core/cs_clear.c14
-rw-r--r--src/core/cs_forbid.c6
-rw-r--r--src/core/cs_kick.c15
-rw-r--r--src/core/cs_suspend.c7
-rw-r--r--src/core/os_kick.c10
-rw-r--r--src/modules/cs_enforce.c13
17 files changed, 180 insertions, 247 deletions
diff --git a/include/extern.h b/include/extern.h
index 0ca8d4d3c..6d00c347c 100644
--- a/include/extern.h
+++ b/include/extern.h
@@ -141,7 +141,6 @@ E int check_should_voice(User * user, char *chan);
E int check_should_halfop(User * user, char *chan);
E int check_should_owner(User * user, char *chan);
E int check_should_protect(User * user, char *chan);
-E int check_kick(User * user, const char *chan, time_t chants);
E void record_topic(const char *chan);
E void restore_topic(const char *chan);
E int check_topiclock(Channel * c, time_t topic_time);
diff --git a/include/modules.h b/include/modules.h
index a15657608..67aafc580 100644
--- a/include/modules.h
+++ b/include/modules.h
@@ -619,12 +619,14 @@ class CoreExport Module
*/
virtual void OnBotPreLoad(BotInfo *bi) { }
- /** Called when a bot kicks a user
+ /** Called before a bot kicks a user
+ * @param bi The bot sending the kick
+ * @param c The channel the user is being kicked on
* @param u The user being kicked
- * @param ci The channel
* @param reason The reason
+ * @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to halt the command and not process it
*/
- virtual void OnBotKick(User *u, ChannelInfo *ci, const std::string &reason) { }
+ virtual EventReturn OnBotKick(BotInfo *bi, Channel *c, User *u, const std::string &reason) { return EVENT_CONTINUE; }
/** Called before a user parts a channel
* @param u The user
diff --git a/include/regchannel.h b/include/regchannel.h
index a6275db1d..2304467de 100644
--- a/include/regchannel.h
+++ b/include/regchannel.h
@@ -289,4 +289,10 @@ class CoreExport ChannelInfo : public Extensible, public Flags<ChannelInfoFlag>
/** Clear all the params from the channel
*/
void ClearParams();
+
+ /** Check whether a user is permitted to be on this channel
+ * @param u The user
+ * @return true if they are allowed, false if they aren't and were kicked
+ */
+ bool CheckKick(User *user);
};
diff --git a/include/services.h b/include/services.h
index a2a328eb5..0a92a7c8e 100644
--- a/include/services.h
+++ b/include/services.h
@@ -989,6 +989,21 @@ class CoreExport Channel : public Extensible, public Flags<ChannelFlags>
* @param cmodes The modes to set
*/
void SetModes(BotInfo *bi, bool EnforceMLock, const char *cmodes, ...);
+
+ /** Kick a user from a channel internally
+ * @param source The sender of the kick
+ * @param nick The nick being kicked
+ * @param reason The reason for the kick
+ */
+ void KickInternal(const std::string &source, const std::string &nick, const std::string &reason);
+
+ /** Kick a user from the channel
+ * @param bi The sender, can be NULL for the service bot for this channel
+ * @param u The user being kicked
+ * @param reason The reason for the kick
+ * @return true if the kick was scucessful, false if a module blocked the kick
+ */
+ bool Kick(BotInfo *bi, User *u, const char *reason = NULL, ...);
};
/** Channelban type flags
diff --git a/src/actions.c b/src/actions.c
index 0e15f2cf4..fa9db5f4c 100644
--- a/src/actions.c
+++ b/src/actions.c
@@ -75,7 +75,6 @@ void sqline(const std::string &mask, const std::string &reason)
{
int i;
Channel *c, *next;
- const char *av[3];
struct c_userlist *cu, *cunext;
if (ircd->chansqline)
@@ -97,11 +96,7 @@ void sqline(const std::string &mask, const std::string &reason)
cunext = cu->next;
if (is_oper(cu->user))
continue;
- av[0] = c->name.c_str();
- av[1] = cu->user->nick.c_str();
- av[2] = reason.c_str();
- ircdproto->SendKick(findbot(Config.s_OperServ), c, cu->user, "Q-Lined: %s", av[2]);
- do_kick(Config.s_ChanServ, 3, av);
+ c->Kick(NULL, cu->user, "%s", reason.c_str());
}
}
}
diff --git a/src/botserv.c b/src/botserv.c
index faf6bf3b8..c3884e463 100644
--- a/src/botserv.c
+++ b/src/botserv.c
@@ -696,7 +696,6 @@ static void bot_kick(ChannelInfo * ci, User * u, int message, ...)
va_list args;
char buf[1024];
const char *fmt;
- const char *av[3];
if (!ci || !ci->bi || !ci->c || !u)
return;
@@ -708,22 +707,15 @@ static void bot_kick(ChannelInfo * ci, User * u, int message, ...)
vsnprintf(buf, sizeof(buf), fmt, args);
va_end(args);
- av[0] = ci->name.c_str();
- av[1] = u->nick.c_str();
- av[2] = buf;
- ircdproto->SendKick(ci->bi, ci->c, u, "%s", av[2]);
- do_kick(ci->bi->nick, 3, av);
- FOREACH_MOD(I_OnBotKick, OnBotKick(u, ci, buf));
+ ci->c->Kick(ci->bi, u, "%s", buf);
}
/*************************************************************************/
/* Makes a simple ban and kicks the target */
-void bot_raw_ban(User * requester, ChannelInfo * ci, char *nick,
- const char *reason)
+void bot_raw_ban(User * requester, ChannelInfo * ci, char *nick, const char *reason)
{
- const char *kav[4]; // seperate as not everything is constified XXX -- w00t
char mask[BUFSIZE];
User *u = finduser(nick);
@@ -753,35 +745,19 @@ void bot_raw_ban(User * requester, ChannelInfo * ci, char *nick,
ci->c->SetMode(NULL, CMODE_BAN, mask);
- kav[0] = ci->name.c_str();
- kav[1] = nick;
-
- if (!reason) {
- kav[2] = ci->bi->nick.c_str();
- } else {
- if (strlen(reason) > 200)
- (*const_cast<char **>(&reason))[200] = '\0'; // Unsafe cast -- will review later -- CyberBotX
- kav[2] = reason;
- }
-
/* Check if we need to do a signkick or not -GD */
- if ((ci->HasFlag(CI_SIGNKICK) || ci->HasFlag(CI_SIGNKICK_LEVEL)) && !check_access(requester, ci, CA_SIGNKICK))
- ircdproto->SendKick(ci->bi, ci->c, u, "%s (%s)", kav[2], requester->nick.c_str());
+ if (ci->HasFlag(CI_SIGNKICK) || ci->HasFlag(CI_SIGNKICK_LEVEL) && !check_access(requester, ci, CA_SIGNKICK))
+ ci->c->Kick(ci->bi, u, "%s (%s)", reason ? reason : ci->bi->nick.c_str(), requester->nick.c_str());
else
- ircdproto->SendKick(ci->bi, ci->c, u, "%s", kav[2]);
-
- do_kick(ci->bi->nick, 3, kav);
- FOREACH_MOD(I_OnBotKick, OnBotKick(u, ci, kav[2]));
+ ci->c->Kick(ci->bi, u, "%s", reason ? reason : ci->bi->nick.c_str());
}
/*************************************************************************/
/* Makes a kick with a "dynamic" reason ;) */
-void bot_raw_kick(User * requester, ChannelInfo * ci, char *nick,
- const char *reason)
+void bot_raw_kick(User * requester, ChannelInfo * ci, char *nick, const char *reason)
{
- const char *av[3];
User *u = finduser(nick);
if (!u || !is_on_chan(ci->c, u))
@@ -798,31 +774,17 @@ void bot_raw_kick(User * requester, ChannelInfo * ci, char *nick,
if (ci->HasFlag(CI_PEACE) && stricmp(requester->nick.c_str(), nick) && (get_access(u, ci) >= get_access(requester, ci)))
return;
- av[0] = ci->name.c_str();
- av[1] = nick;
-
- if (!reason) {
- av[2] = ci->bi->nick.c_str();
- } else {
- if (strlen(reason) > 200)
- (*const_cast<char **>(&reason))[200] = '\0'; // Unsafe cast -- will review later -- CyberBotX
- av[2] = reason;
- }
-
- if (ci->HasFlag(CI_SIGNKICK) || ((ci->HasFlag(CI_SIGNKICK_LEVEL)) && !check_access(requester, ci, CA_SIGNKICK)))
- ircdproto->SendKick(ci->bi, ci->c, u, "%s (%s)", av[2], requester->nick.c_str());
+ if (ci->HasFlag(CI_SIGNKICK) || (ci->HasFlag(CI_SIGNKICK_LEVEL) && !check_access(requester, ci, CA_SIGNKICK)))
+ ci->c->Kick(ci->bi, u, "%s (%s)", reason ? reason : ci->bi->nick.c_str(), requester->nick.c_str());
else
- ircdproto->SendKick(ci->bi, ci->c, u, "%s", av[2]);
- do_kick(ci->bi->nick, 3, av);
- FOREACH_MOD(I_OnBotKick, OnBotKick(u, ci, av[2]));
+ ci->c->Kick(ci->bi, u, "%s", reason ? reason : ci->bi->nick.c_str());
}
/*************************************************************************/
/* Makes a mode operation on a channel for a nick */
-void bot_raw_mode(User * requester, ChannelInfo * ci, const char *mode,
- char *nick)
+void bot_raw_mode(User * requester, ChannelInfo * ci, const char *mode, char *nick)
{
char buf[BUFSIZE];
User *u;
diff --git a/src/channels.c b/src/channels.c
index 1730dcf7c..6a449dc89 100644
--- a/src/channels.c
+++ b/src/channels.c
@@ -715,6 +715,75 @@ void ChanSetInternalModes(Channel *c, int ac, const char **av)
}
}
+/** Kick a user from a channel internally
+ * @param source The sender of the kick
+ * @param nick The nick being kicked
+ * @param reason The reason for the kick
+ */
+void Channel::KickInternal(const std::string &source, const std::string &nick, const std::string &reason)
+{
+ /* If it is the bot that is being kicked, we make it rejoin the
+ * channel and stop immediately.
+ * --lara
+ */
+ if (Config.s_BotServ && this->ci && findbot(nick))
+ {
+ bot_join(this->ci);
+ return;
+ }
+
+ User *user = finduser(nick);
+ if (!user)
+ {
+ if (debug)
+ alog("debug: Channel::KickInternal got a nonexistent user %s on %s: %s", nick.c_str(), this->name.c_str(), reason.c_str());
+ return;
+ }
+
+ if (debug)
+ alog("debug: Channel::KickInternal kicking %s from %s", user->nick.c_str(), this->name.c_str());
+
+ struct u_chanlist *c;
+ for (c = user->chans; c && this != c->chan; c = c->next);
+ if (c)
+ {
+ FOREACH_MOD(I_OnUserKicked, OnUserKicked(c->chan, user, source, reason));
+ chan_deluser(user, c->chan);
+ if (c->next)
+ c->next->prev = c->prev;
+ if (c->prev)
+ c->prev->next = c->next;
+ else
+ user->chans = c->next;
+ delete c;
+ }
+ else if (debug)
+ alog("debug: Channel::KickInternal got kick for user %s who isn't on channel %s ?", user->nick.c_str(), this->name.c_str());
+}
+
+/** Kick a user from the channel
+ * @param bi The sender, can be NULL for the service bot for this channel
+ * @param u The user being kicked
+ * @param reason The reason for the kick
+ * @return true if the kick was scucessful, false if a module blocked the kick
+ */
+bool Channel::Kick(BotInfo *bi, User *u, const char *reason, ...)
+{
+ va_list args;
+ char buf[BUFSIZE] = "";
+ va_start(args, reason);
+ vsnprintf(buf, BUFSIZE - 1, reason, args);
+ va_end(args);
+
+ EventReturn MOD_RESULT;
+ FOREACH_RESULT(I_OnBotKick, OnBotKick(bi, this, u, buf));
+ if (MOD_RESULT == EVENT_STOP)
+ return false;
+ ircdproto->SendKick(bi ? bi : whosends(this->ci), this, u, "%s", buf);
+ this->KickInternal(bi ? bi->nick : whosends(this->ci)->nick, u->nick, buf);
+ return true;
+}
+
/*************************************************************************/
void chan_deluser(User * user, Channel * c)
@@ -1065,7 +1134,6 @@ void do_join(const char *source, int ac, const char **av)
char *s, *t;
struct u_chanlist *c, *nextc;
char *channame;
- time_t ts = time(NULL);
if (ircd->ts6) {
user = find_byuid(source);
@@ -1113,9 +1181,10 @@ void do_join(const char *source, int ac, const char **av)
* don't get to see things like channel keys. */
/* If channel already exists, check_kick() will use correct TS.
* Otherwise, we lose. */
- if (check_kick(user, s, ts))
+ if (chan && chan->ci && chan->ci->CheckKick(user))
continue;
+ time_t ts = time(NULL);
if (ac == 2) {
ts = strtoul(av[1], NULL, 10);
if (debug) {
@@ -1133,67 +1202,26 @@ void do_join(const char *source, int ac, const char **av)
/*************************************************************************/
-/* Handle a KICK command.
- * av[0] = channel
- * av[1] = nick(s) being kicked
- * av[2] = reason
+/** Handle a KICK command.
+ * @param source The source of the kick
+ * @param ac number of args
+ * @param av The channel, nick(s) being kicked, and reason
*/
-
void do_kick(const std::string &source, int ac, const char **av)
{
- BotInfo *bi;
- ChannelInfo *ci;
- User *user;
- char *s, *t;
- struct u_chanlist *c;
-
- t = const_cast<char *>(av[1]); // XXX unsafe cast, this needs reviewing -- w00t
- while (*(s = t)) {
- t = s + strcspn(s, ",");
- if (*t)
- *t++ = 0;
-
- /* If it is the bot that is being kicked, we make it rejoin the
- * channel and stop immediately.
- * --lara
- */
- if (Config.s_BotServ && (bi = findbot(s)) && (ci = cs_findchan(av[0]))) {
- bot_join(ci);
- continue;
- }
+ Channel *c = findchan(av[0]);
+ if (!c)
+ {
+ if (debug)
+ alog("Recieved kick for nonexistant channel %s", av[0]);
+ return;
+ }
- if (ircd->ts6) {
- user = find_byuid(s);
- if (!user) {
- user = finduser(s);
- }
- } else {
- user = finduser(s);
- }
- if (!user) {
- if (debug) {
- alog("debug: KICK for nonexistent user %s on %s: %s", s,
- av[0], merge_args(ac - 2, av + 2));
- }
- continue;
- }
- if (debug) {
- alog("debug: kicking %s from %s", user->nick.c_str(), av[0]);
- }
- for (c = user->chans; c && stricmp(av[0], c->chan->name.c_str()) != 0;
- c = c->next);
- if (c)
- {
- FOREACH_MOD(I_OnUserKicked, OnUserKicked(c->chan, user, source, merge_args(ac - 2, av + 2)));
- chan_deluser(user, c->chan);
- if (c->next)
- c->next->prev = c->prev;
- if (c->prev)
- c->prev->next = c->next;
- else
- user->chans = c->next;
- delete c;
- }
+ std::string buf;
+ commasepstream sep(av[1]);
+ while (sep.GetToken(buf))
+ {
+ c->KickInternal(source, buf, av[2]);
}
}
@@ -1440,7 +1468,8 @@ void do_sjoin(const char *source, int ac, const char **av)
if (is_sqlined && !is_oper(user)) {
ircdproto->SendKick(findbot(Config.s_OperServ), c, user, "Q-Lined");
} else {
- if (!check_kick(user, av[1], ts)) {
+ if (!c || !c->ci || !c->ci->CheckKick(user))
+ {
FOREACH_MOD(I_OnPreJoinChannel, OnPreJoinChannel(user, av[1]));
/* Make the user join; if the channel does not exist it
@@ -1526,7 +1555,8 @@ void do_sjoin(const char *source, int ac, const char **av)
if (is_sqlined && !is_oper(user)) {
ircdproto->SendKick(findbot(Config.s_OperServ), c, user, "Q-Lined");
} else {
- if (!check_kick(user, av[1], ts)) {
+ if (!c || !c->ci || !c->ci->CheckKick(user))
+ {
FOREACH_MOD(I_OnPreJoinChannel, OnPreJoinChannel(user, av[1]));
/* Make the user join; if the channel does not exist it
@@ -1601,7 +1631,8 @@ void do_sjoin(const char *source, int ac, const char **av)
if (is_sqlined && !is_oper(user)) {
ircdproto->SendKick(findbot(Config.s_OperServ), c, user, "Q-Lined");
} else {
- if (!check_kick(user, av[1], ts)) {
+ if (!c || !c->ci || !c->ci->CheckKick(user))
+ {
FOREACH_MOD(I_OnPreJoinChannel, OnPreJoinChannel(user, av[1]));
/* Make the user join; if the channel does not exist it
@@ -1648,7 +1679,7 @@ void do_sjoin(const char *source, int ac, const char **av)
return;
}
- if (check_kick(user, av[1], ts))
+ if (c && c->ci && c->ci->CheckKick(user))
return;
if (ircd->chansqline) {
diff --git a/src/chanserv.c b/src/chanserv.c
index 5fcfee37f..1057e01cf 100644
--- a/src/chanserv.c
+++ b/src/chanserv.c
@@ -600,45 +600,39 @@ int check_should_protect(User * user, char *chan)
/*************************************************************************/
-/* Check whether a user is permitted to be on a channel. If so, return 0;
- * else, kickban the user with an appropriate message (could be either
- * AKICK or restricted access) and return 1. Note that this is called
- * _before_ the user is added to internal channel lists (so do_kick() is
- * not called). The channel TS must be given for a new channel.
+/** Check whether a user is permitted to be on this channel
+ * @param u The user
+ * @return true if they were banned, false if they are allowed
*/
-
-int check_kick(User * user, const char *chan, time_t chants)
+bool ChannelInfo::CheckKick(User *user)
{
- ChannelInfo *ci = cs_findchan(chan);
- Channel *c;
AutoKick *akick;
- bool set_modes = false;
+ bool set_modes = false, do_kick = false;
NickCore *nc;
char mask[BUFSIZE];
const char *reason;
ChanServTimer *t;
- if (!ci)
- return 0;
+ if (!user)
+ return false;
if (user->isSuperAdmin == 1)
- return 0;
+ return true;
/* We don't enforce services restrictions on clients on ulined services
* as this will likely lead to kick/rejoin floods. ~ Viper */
- if (is_ulined(user->server->name)) {
- return 0;
- }
+ if (is_ulined(user->server->name))
+ return true;
- if (ci->HasFlag(CI_SUSPENDED) || ci->HasFlag(CI_FORBIDDEN))
+ if (this->HasFlag(CI_SUSPENDED) || this->HasFlag(CI_FORBIDDEN))
{
if (is_oper(user))
return 0;
- get_idealban(ci, user, mask, sizeof(mask));
- reason = ci->forbidreason ? ci->forbidreason : getstring(user, CHAN_MAY_NOT_BE_USED);
+ get_idealban(this, user, mask, sizeof(mask));
+ reason = this->forbidreason ? this->forbidreason : getstring(user, CHAN_MAY_NOT_BE_USED);
set_modes = true;
- goto kick;
+ do_kick = true;
}
if (user->nc || user->IsRecognized())
@@ -646,22 +640,14 @@ int check_kick(User * user, const char *chan, time_t chants)
else
nc = NULL;
- /*
- * Before we go through akick lists, see if they're excepted FIRST
- * We cannot kick excempted users that are akicked or not on the channel access list
- * as that will start services <-> server wars which ends up as a DoS against services.
- *
- * UltimateIRCd 3.x at least informs channel staff when a joining user is matching an exempt.
- */
- if (ModeManager::FindChannelModeByName(CMODE_EXCEPT) && is_excepted(ci, user) == 1) {
- return 0;
- }
+ if (!do_kick && ModeManager::FindChannelModeByName(CMODE_EXCEPT) && is_excepted(this, user) == 1)
+ return true;
- for (unsigned j = 0; j < ci->GetAkickCount(); ++j)
+ for (unsigned j = 0; j < this->GetAkickCount(); ++j)
{
- akick = ci->GetAkick(j);
+ akick = this->GetAkick(j);
- if (!akick->InUse)
+ if (!akick->InUse || do_kick)
continue;
if ((akick->HasFlag(AK_ISNICK) && akick->nc == nc)
@@ -671,27 +657,28 @@ int check_kick(User * user, const char *chan, time_t chants)
if (debug >= 2)
alog("debug: %s matched akick %s", user->nick.c_str(), akick->HasFlag(AK_ISNICK) ? akick->nc->display : akick->mask.c_str());
if (akick->HasFlag(AK_ISNICK))
- get_idealban(ci, user, mask, sizeof(mask));
+ get_idealban(this, user, mask, sizeof(mask));
else
strlcpy(mask, akick->mask.c_str(), sizeof(mask));
reason = !akick->reason.empty() ? akick->reason.c_str() : Config.CSAutokickReason;
- goto kick;
+ do_kick = true;
}
}
- if (check_access(user, ci, CA_NOJOIN)) {
- get_idealban(ci, user, mask, sizeof(mask));
+ if (!do_kick && check_access(user, this, CA_NOJOIN))
+ {
+ get_idealban(this, user, mask, sizeof(mask));
reason = getstring(user, CHAN_NOT_ALLOWED_TO_JOIN);
- goto kick;
+ do_kick = true;
}
- return 0;
+ if (!do_kick)
+ return false;
- kick:
if (debug)
alog("debug: channel: AutoKicking %s!%s@%s from %s", user->nick.c_str(),
- user->GetIdent().c_str(), user->host, chan);
+ user->GetIdent().c_str(), user->host, this->name.c_str());
/* Remember that the user has not been added to our channel user list
* yet, so we check whether the channel does not exist OR has no user
@@ -699,9 +686,9 @@ int check_kick(User * user, const char *chan, time_t chants)
* JOIN would not). */
/* Don't check for CI_INHABIT before for the Channel record cos else
* c may be NULL even if it exists */
- if ((!(c = findchan(chan)) || c->usercount == 0) && !ci->HasFlag(CI_INHABIT))
+ if ((!this->c || this->c->usercount == 0) && !this->HasFlag(CI_INHABIT))
{
- ircdproto->SendJoin(findbot(Config.s_ChanServ), chan, (c ? c->creation_time : chants));
+ ircdproto->SendJoin(findbot(Config.s_ChanServ), this->name.c_str(), (this->c ? this->c->creation_time : time(NULL)));
/*
* If channel was forbidden, etc, set it +si to prevent rejoin
*/
@@ -713,17 +700,17 @@ int check_kick(User * user, const char *chan, time_t chants)
c->SetMode(NULL, CMODE_INVITE);
}
- t = new ChanServTimer(Config.CSInhabit, chan);
- ci->SetFlag(CI_INHABIT);
+ t = new ChanServTimer(Config.CSInhabit, this->name.c_str());
+ this->SetFlag(CI_INHABIT);
}
if (c)
{
c->SetMode(NULL, CMODE_BAN, mask);
- ircdproto->SendKick(whosends(ci), c, user, "%s", reason);
+ ircdproto->SendKick(whosends(this), c, user, "%s", reason);
}
- return 1;
+ return true;
}
/*************************************************************************/
diff --git a/src/core/bs_kick.c b/src/core/bs_kick.c
index daf09350a..dbff0e788 100644
--- a/src/core/bs_kick.c
+++ b/src/core/bs_kick.c
@@ -15,8 +15,6 @@
#include "module.h"
-int do_kickcmd(User * u);
-
class CommandBSKick : public Command
{
public:
diff --git a/src/core/cs_akick.c b/src/core/cs_akick.c
index 881cd01ec..d07e820a8 100644
--- a/src/core/cs_akick.c
+++ b/src/core/cs_akick.c
@@ -482,7 +482,6 @@ class CommandCSAKick : public Command
Channel *c = ci->c;
c_userlist *cu, *unext;
int count = 0;
- const char *argv[3];
if (!c)
{
@@ -495,17 +494,9 @@ class CommandCSAKick : public Command
while (cu)
{
unext = cu->next;
- if (check_kick(cu->user, c->name.c_str(), c->creation_time))
+ if (ci->CheckKick(cu->user))
{
- argv[0] = sstrdup(c->name.c_str());
- argv[1] = sstrdup(cu->user->nick.c_str());
- argv[2] = sstrdup(Config.CSAutokickReason);
-
- do_kick(Config.s_ChanServ, 3, argv);
-
- delete [] argv[2];
- delete [] argv[1];
- delete [] argv[0];
+ c->Kick(NULL, cu->user, "%s", Config.CSAutokickReason);
count++;
}
cu = unext;
diff --git a/src/core/cs_ban.c b/src/core/cs_ban.c
index aaf36ac27..68248e02b 100644
--- a/src/core/cs_ban.c
+++ b/src/core/cs_ban.c
@@ -75,18 +75,10 @@ class CommandCSBan : public Command
if (!is_on_chan(c, u2))
return MOD_CONT;
- if ((ci->HasFlag(CI_SIGNKICK))
- || ((ci->HasFlag(CI_SIGNKICK_LEVEL))
- && !check_access(u, ci, CA_SIGNKICK)))
- ircdproto->SendKick(whosends(ci), ci->c, u2, "%s (%s)", reason, u->nick.c_str());
+ if (ci->HasFlag(CI_SIGNKICK) || (ci->HasFlag(CI_SIGNKICK_LEVEL) && !check_access(u, ci, CA_SIGNKICK)))
+ c->Kick(whosends(ci), u2, "%s (%s)", reason, u->nick.c_str());
else
- ircdproto->SendKick(whosends(ci), ci->c, u2, "%s", reason);
-
- const char *kav[4];
- kav[0] = ci->name.c_str();
- kav[1] = target;
- kav[2] = reason;
- do_kick(Config.s_ChanServ, 3, kav);
+ c->Kick(whosends(ci), u2, "%s", reason);
}
return MOD_CONT;
diff --git a/src/core/cs_clear.c b/src/core/cs_clear.c
index 1de6ca1ff..9f2f1cce5 100644
--- a/src/core/cs_clear.c
+++ b/src/core/cs_clear.c
@@ -148,22 +148,12 @@ class CommandCSClear : public Command
notice_lang(Config.s_ChanServ, u, CHAN_CLEARED_VOICES, chan);
} else if (what == "users") {
- const char *av[3];
struct c_userlist *cu, *bnext;
- char buf[256];
-
- snprintf(buf, sizeof(buf), "CLEAR USERS command from %s", u->nick.c_str());
+ std::string buf = "CLEAR USERS command from " + u->nick;
for (cu = c->users; cu; cu = bnext) {
bnext = cu->next;
- av[0] = sstrdup(chan);
- av[1] = sstrdup(cu->user->nick.c_str());
- av[2] = sstrdup(buf);
- ircdproto->SendKick(whosends(ci), c, cu->user, av[2]);
- do_kick(Config.s_ChanServ, 3, av);
- delete [] av[2];
- delete [] av[1];
- delete [] av[0];
+ c->Kick(NULL, cu->user, buf.c_str());
}
notice_lang(Config.s_ChanServ, u, CHAN_CLEARED_USERS, chan);
} else {
diff --git a/src/core/cs_forbid.c b/src/core/cs_forbid.c
index 82b045b48..7abf355ac 100644
--- a/src/core/cs_forbid.c
+++ b/src/core/cs_forbid.c
@@ -82,11 +82,7 @@ class CommandCSForbid : public Command
if (is_oper(cu->user))
continue;
- av[0] = c->name.c_str();
- av[1] = cu->user->nick.c_str();
- av[2] = reason ? reason : getstring(cu->user->nc, CHAN_FORBID_REASON);
- ircdproto->SendKick(findbot(Config.s_ChanServ), c, cu->user, av[2]);
- do_kick(Config.s_ChanServ, 3, av);
+ c->Kick(findbot(Config.s_ChanServ), cu->user, "%s", reason ? reason : getstring(cu->user->nc, CHAN_FORBID_REASON));
}
}
diff --git a/src/core/cs_kick.c b/src/core/cs_kick.c
index 898fb898b..1cda01867 100644
--- a/src/core/cs_kick.c
+++ b/src/core/cs_kick.c
@@ -63,19 +63,10 @@ class CommandCSKick : public Command
} else if (is_protected(u2)) {
notice_lang(Config.s_ChanServ, u, ACCESS_DENIED);
} else {
- const char *av[3];
-
- if ((ci->HasFlag(CI_SIGNKICK))
- || ((ci->HasFlag(CI_SIGNKICK_LEVEL))
- && !check_access(u, ci, CA_SIGNKICK)))
- ircdproto->SendKick(whosends(ci), ci->c, u2, "%s (%s)",
- reason, u->nick.c_str());
+ if (ci->HasFlag(CI_SIGNKICK) || (ci->HasFlag(CI_SIGNKICK_LEVEL) && !check_access(u, ci, CA_SIGNKICK)))
+ ci->c->Kick(whosends(ci), u2, "%s (%s)", reason, u->nick.c_str());
else
- ircdproto->SendKick(whosends(ci), ci->c, u2, "%s", reason);
- av[0] = ci->name.c_str();
- av[1] = target;
- av[2] = reason;
- do_kick(Config.s_ChanServ, 3, av);
+ ci->c->Kick(whosends(ci), u2, "%s", reason);
}
return MOD_CONT;
}
diff --git a/src/core/cs_suspend.c b/src/core/cs_suspend.c
index fdd40c796..4a47091eb 100644
--- a/src/core/cs_suspend.c
+++ b/src/core/cs_suspend.c
@@ -63,7 +63,6 @@ class CommandCSSuspend : public Command
if ((c = findchan(ci->name.c_str())))
{
struct c_userlist *cu, *nextu;
- const char *av[3];
for (cu = c->users; cu; cu = nextu)
{
@@ -72,11 +71,7 @@ class CommandCSSuspend : public Command
if (is_oper(cu->user))
continue;
- av[0] = c->name.c_str();
- av[1] = cu->user->nick.c_str();
- av[2] = reason ? reason : getstring(cu->user->nc, CHAN_SUSPEND_REASON);
- ircdproto->SendKick(findbot(Config.s_ChanServ), c, cu->user, av[2]);
- do_kick(Config.s_ChanServ, 3, av);
+ c->Kick(NULL, cu->user, "%s", reason ? reason : getstring(cu->user->nc, CHAN_SUSPEND_REASON));
}
}
diff --git a/src/core/os_kick.c b/src/core/os_kick.c
index 096e81c4c..678934fbb 100644
--- a/src/core/os_kick.c
+++ b/src/core/os_kick.c
@@ -24,7 +24,6 @@ class CommandOSKick : public Command
CommandReturn Execute(User *u, const std::vector<ci::string> &params)
{
- const char *argv[3];
const char *chan = params[0].c_str(), *nick = params[1].c_str(), *s = params[2].c_str();
Channel *c;
User *u2;
@@ -45,16 +44,9 @@ class CommandOSKick : public Command
return MOD_CONT;
}
- ircdproto->SendKick(findbot(Config.s_OperServ), c, u2, "%s (%s)", u->nick.c_str(), s);
+ c->Kick(findbot(Config.s_OperServ), u2, "%s (%s)", u->nick.c_str(), s);
if (Config.WallOSKick)
ircdproto->SendGlobops(findbot(Config.s_OperServ), "%s used KICK on %s/%s", u->nick.c_str(), u2->nick.c_str(), chan);
- argv[0] = sstrdup(chan);
- argv[1] = sstrdup(u2->nick.c_str());
- argv[2] = sstrdup(s);
- do_kick(Config.s_OperServ, 3, argv);
- delete [] argv[2];
- delete [] argv[1];
- delete [] argv[0];
return MOD_CONT;
}
diff --git a/src/modules/cs_enforce.c b/src/modules/cs_enforce.c
index 32f2c85c2..56ac4cc9b 100644
--- a/src/modules/cs_enforce.c
+++ b/src/modules/cs_enforce.c
@@ -121,11 +121,7 @@ class CommandCSEnforce : public Command
get_idealban(ci, u, mask, sizeof(mask));
reason = getstring(u, CHAN_NOT_ALLOWED_TO_JOIN);
c->SetMode(NULL, CMODE_BAN, mask);
- ircdproto->SendKick(whosends(ci), ci->c, u, "%s", reason);
- av[0] = ci->name.c_str();
- av[1] = u->nick.c_str();
- av[2] = reason;
- do_kick(Config.s_ChanServ, 3, av);
+ c->Kick(NULL, u, "%s", reason);
}
user = next;
} while (user);
@@ -140,7 +136,6 @@ class CommandCSEnforce : public Command
ChannelInfo *ci;
char mask[BUFSIZE];
const char *reason;
- const char *av[3];
User *u;
if (!(ci = c->ci))
@@ -162,11 +157,7 @@ class CommandCSEnforce : public Command
{
c->SetMode(NULL, CMODE_BAN, mask);
}
- ircdproto->SendKick(whosends(ci), ci->c, u, "%s", reason);
- av[0] = ci->name.c_str();
- av[1] = u->nick.c_str();
- av[2] = reason;
- do_kick(Config.s_ChanServ, 3, av);
+ c->Kick(NULL, u, "%s", reason);
}
user = next;
} while (user);