summaryrefslogtreecommitdiff
path: root/src/chanserv.c
diff options
context:
space:
mode:
authorAdam- <Adam-@5417fbe8-f217-4b02-8779-1006273d7864>2010-01-14 21:29:08 +0000
committerAdam- <Adam-@5417fbe8-f217-4b02-8779-1006273d7864>2010-01-14 21:29:08 +0000
commit711787b54d8b57ace877b09587f368cee5553b70 (patch)
treef5093aeeec5c1f4155e31f72488ae4040e37f551 /src/chanserv.c
parentf2c44c67b59bd4f6a5a01412f2dc5df59010b1da (diff)
Burned do_sjoin and rewrote it to be sane. This changes how Anope handles new channel creations drasitcally as we now truely track it all instead of hack around it by not initially tracking user joins to new channels
git-svn-id: http://anope.svn.sourceforge.net/svnroot/anope/trunk@2755 5417fbe8-f217-4b02-8779-1006273d7864
Diffstat (limited to 'src/chanserv.c')
-rw-r--r--src/chanserv.c79
1 files changed, 45 insertions, 34 deletions
diff --git a/src/chanserv.c b/src/chanserv.c
index 8c74d1c6a..af458e42b 100644
--- a/src/chanserv.c
+++ b/src/chanserv.c
@@ -119,26 +119,41 @@ void moduleAddChanServCmds() {
/* *INDENT-ON* */
/*************************************************************************/
+/** A timer used to keep the BotServ bot/ChanServ in the channel
+ * after kicking the last user in a channel
+ */
class ChanServTimer : public Timer
{
- private:
- std::string channel;
+ private:
+ Channel *c;
- public:
- ChanServTimer(long delay, const std::string &chan) : Timer(delay), channel(chan)
- {
- }
+ public:
+ ChanServTimer(Channel *chan) : Timer(Config.CSInhabit), c(chan)
+ {
+ if (c->ci)
+ c->ci->SetFlag(CI_INHABIT);
+ }
- void Tick(time_t ctime)
- {
- ChannelInfo *ci = cs_findchan(channel);
+ void Tick(time_t)
+ {
+ if (!c->ci)
+ return;
- if (ci)
- ci->UnsetFlag(CI_INHABIT);
+ c->ci->UnsetFlag(CI_INHABIT);
- if (ci->c)
- ircdproto->SendPart(findbot(Config.s_ChanServ), ci->c, NULL);
- }
+ /* If the channel has users again, don't part it and halt */
+ if (c->usercount)
+ return;
+
+ if (c->ci->bi)
+ ircdproto->SendPart(c->ci->bi, c, NULL);
+ else
+ ircdproto->SendPart(findbot(Config.s_ChanServ), c, NULL);
+
+ /* Now delete the channel as it is empty */
+ if (!c->HasFlag(CH_PERSIST) && !c->ci->HasFlag(CI_PERSIST))
+ delete c;
+ }
};
/*************************************************************************/
@@ -611,9 +626,8 @@ bool ChannelInfo::CheckKick(User *user)
NickCore *nc;
char mask[BUFSIZE];
const char *reason;
- ChanServTimer *t;
- if (!user)
+ if (!user || !this->c)
return false;
if (user->isSuperAdmin == 1)
@@ -680,18 +694,12 @@ bool ChannelInfo::CheckKick(User *user)
alog("debug: channel: AutoKicking %s!%s@%s from %s", user->nick.c_str(),
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
- * on it (before SJOIN would have created the channel structure, while
- * 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 ((!this->c || this->c->usercount == 0) && !this->HasFlag(CI_INHABIT))
+ /* If the channel doesnt have any users and if a bot isn't already in the channel, join it
+ * NOTE: we use usercount == 1 here as there is one user, but they are about to be destroyed
+ */
+ if (this->c->usercount == 1 && !this->HasFlag(CI_INHABIT))
{
- 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
- */
+ /* If channel was forbidden, etc, set it +si to prevent rejoin */
if (set_modes)
{
c->SetMode(NULL, CMODE_NOEXTERNAL);
@@ -700,15 +708,18 @@ bool ChannelInfo::CheckKick(User *user)
c->SetMode(NULL, CMODE_INVITE);
}
- t = new ChanServTimer(Config.CSInhabit, this->name.c_str());
- this->SetFlag(CI_INHABIT);
+ /* This channel has no bot assigned to it, join ChanServ */
+ if (!this->bi)
+ {
+ ircdproto->SendJoin(findbot(Config.s_ChanServ), this->name.c_str(), this->c->creation_time);
+ }
+
+ /* Set a timer for this channel to part the bots later */
+ new ChanServTimer(this->c);
}
- if (c)
- {
- c->SetMode(NULL, CMODE_BAN, mask);
- ircdproto->SendKick(whosends(this), c, user, "%s", reason);
- }
+ this->c->SetMode(NULL, CMODE_BAN, mask);
+ this->c->Kick(NULL, user, "%s", reason);
return true;
}