diff options
Diffstat (limited to 'src/bots.cpp')
-rw-r--r-- | src/bots.cpp | 292 |
1 files changed, 161 insertions, 131 deletions
diff --git a/src/bots.cpp b/src/bots.cpp index a9933e336..35b390ed4 100644 --- a/src/bots.cpp +++ b/src/bots.cpp @@ -1,9 +1,21 @@ /* + * Anope IRC Services * - * (C) 2008-2011 Robin Burchell <w00t@inspircd.org> - * (C) 2008-2017 Anope Team <team@anope.org> + * Copyright (C) 2008-2011 Robin Burchell <w00t@inspircd.org> + * Copyright (C) 2008-2017 Anope Team <team@anope.org> * - * Please read COPYING and README for further details. + * This file is part of Anope. Anope is free software; you can + * redistribute it and/or modify it under the terms of the GNU + * General Public License as published by the Free Software + * Foundation, version 2. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, see see <http://www.gnu.org/licenses/>. */ #include "services.h" @@ -12,25 +24,22 @@ #include "servers.h" #include "protocol.h" #include "xline.h" -#include "regchannel.h" #include "channels.h" #include "config.h" #include "language.h" #include "serialize.h" +#include "event.h" +#include "modules/chanserv.h" -Serialize::Checker<botinfo_map> BotListByNick("BotInfo"), BotListByUID("BotInfo"); - -BotInfo::BotInfo(const Anope::string &nnick, const Anope::string &nuser, const Anope::string &nhost, const Anope::string &nreal, const Anope::string &bmodes) : User(nnick, nuser, nhost, "", "", Me, nreal, Anope::CurTime, "", IRCD ? IRCD->UID_Retrieve() : "", NULL), Serializable("BotInfo"), channels("ChannelInfo"), botmodes(bmodes) +ServiceBot::ServiceBot(const Anope::string &nnick, const Anope::string &nuser, const Anope::string &nhost, const Anope::string &nreal, const Anope::string &bmodes) + : LocalUser(nnick, nuser, nhost, "", "", Me, nreal, Anope::CurTime, "", IRCD ? IRCD->UID_Retrieve() : "", NULL) + , botmodes(bmodes) + , logger(this) { - this->lastmsg = this->created = Anope::CurTime; - this->introduced = false; - this->oper_only = this->conf = false; + this->type = UserType::BOT; + this->lastmsg = Anope::CurTime; - (*BotListByNick)[this->nick] = this; - if (!this->uid.empty()) - (*BotListByUID)[this->uid] = this; - - FOREACH_MOD(OnCreateBot, (this)); + EventManager::Get()->Dispatch(&Event::CreateBot::OnCreateBot, this); // If we're synchronised with the uplink already, send the bot. if (Me && Me->IsSynced()) @@ -39,191 +48,146 @@ BotInfo::BotInfo(const Anope::string &nnick, const Anope::string &nuser, const A if (!tmodes.empty()) this->SetModesInternal(this, tmodes.c_str()); - XLine x(this->nick, "Reserved for services"); - IRCD->SendSQLine(NULL, &x); - IRCD->SendClientIntroduction(this); + //XXX + //XLine x(this->nick, "Reserved for services"); + //IRCD->SendSQLine(NULL, &x); + IRCD->Send<messages::NickIntroduction>(this); this->introduced = true; } } -BotInfo::~BotInfo() +ServiceBot::~ServiceBot() { - UnsetExtensibles(); + if (bi != nullptr) + { + bi->bot = nullptr; + bi->Delete(); + } - FOREACH_MOD(OnDelBot, (this)); + EventManager::Get()->Dispatch(&Event::DelBot::OnDelBot, this); // If we're synchronised with the uplink already, send the bot. if (Me && Me->IsSynced()) { IRCD->SendQuit(this, ""); - FOREACH_MOD(OnUserQuit, (this, "")); + EventManager::Get()->Dispatch(&Event::UserQuit::OnUserQuit, this, ""); this->introduced = false; - XLine x(this->nick); - IRCD->SendSQLineDel(&x); - } - - for (std::set<ChannelInfo *>::iterator it = this->channels->begin(), it_end = this->channels->end(); it != it_end; ++it) - { - ChannelInfo *ci = *it; - this->UnAssign(NULL, ci); + // XXX ? + //XLine x(this->nick); + //IRCD->SendSQLineDel(&x); } - - BotListByNick->erase(this->nick); - if (!this->uid.empty()) - BotListByUID->erase(this->uid); } -void BotInfo::Serialize(Serialize::Data &data) const -{ - data["nick"] << this->nick; - data["user"] << this->ident; - data["host"] << this->host; - data["realname"] << this->realname; - data["created"] << this->created; - data["oper_only"] << this->oper_only; - - Extensible::ExtensibleSerialize(this, this, data); -} -Serializable* BotInfo::Unserialize(Serializable *obj, Serialize::Data &data) -{ - Anope::string nick, user, host, realname, flags; - - data["nick"] >> nick; - data["user"] >> user; - data["host"] >> host; - data["realname"] >> realname; - - BotInfo *bi; - if (obj) - bi = anope_dynamic_static_cast<BotInfo *>(obj); - else if (!(bi = BotInfo::Find(nick, true))) - bi = new BotInfo(nick, user, host, realname); - - data["created"] >> bi->created; - data["oper_only"] >> bi->oper_only; - - Extensible::ExtensibleUnserialize(bi, bi, data); - - return bi; -} - -void BotInfo::GenerateUID() +void ServiceBot::GenerateUID() { if (this->introduced) throw CoreException("Changing bot UID when it is introduced?"); if (!this->uid.empty()) - { - BotListByUID->erase(this->uid); UserListByUID.erase(this->uid); - } - this->uid = IRCD->UID_Retrieve(); - (*BotListByUID)[this->uid] = this; UserListByUID[this->uid] = this; } -void BotInfo::OnKill() +void ServiceBot::OnKill() { this->introduced = false; this->GenerateUID(); - IRCD->SendClientIntroduction(this); + IRCD->Send<messages::NickIntroduction>(this); this->introduced = true; for (User::ChanUserList::const_iterator cit = this->chans.begin(), cit_end = this->chans.end(); cit != cit_end; ++cit) - IRCD->SendJoin(this, cit->second->chan, &cit->second->status); + IRCD->Send<messages::Join>(this, cit->second->chan, &cit->second->status); } -void BotInfo::SetNewNick(const Anope::string &newnick) +void ServiceBot::SetNewNick(const Anope::string &newnick) { UserListByNick.erase(this->nick); - BotListByNick->erase(this->nick); + if (bi != nullptr) + bi->SetNick(newnick); this->nick = newnick; UserListByNick[this->nick] = this; - (*BotListByNick)[this->nick] = this; } -const std::set<ChannelInfo *> &BotInfo::GetChannels() const +std::vector<ChanServ::Channel *> ServiceBot::GetChannels() const { - return this->channels; + return bi != nullptr ? bi->GetRefs<ChanServ::Channel *>() : std::vector<ChanServ::Channel *>(); } -void BotInfo::Assign(User *u, ChannelInfo *ci) +void ServiceBot::Assign(User *u, ChanServ::Channel *ci) { EventReturn MOD_RESULT; - FOREACH_RESULT(OnPreBotAssign, MOD_RESULT, (u, ci, this)); + MOD_RESULT = EventManager::Get()->Dispatch(&Event::PreBotAssign::OnPreBotAssign, u, ci, this); if (MOD_RESULT == EVENT_STOP) return; - if (ci->bi) - ci->bi->UnAssign(u, ci); - - ci->bi = this; - this->channels->insert(ci); + if (ci->GetBot()) + ci->GetBot()->UnAssign(u, ci); - FOREACH_MOD(OnBotAssign, (u, ci, this)); + ci->SetBot(this); + + EventManager::Get()->Dispatch(&Event::BotAssign::OnBotAssign, u, ci, this); } -void BotInfo::UnAssign(User *u, ChannelInfo *ci) +void ServiceBot::UnAssign(User *u, ChanServ::Channel *ci) { EventReturn MOD_RESULT; - FOREACH_RESULT(OnBotUnAssign, MOD_RESULT, (u, ci)); + MOD_RESULT = EventManager::Get()->Dispatch(&Event::BotUnAssign::OnBotUnAssign, u, ci); if (MOD_RESULT == EVENT_STOP) return; - if (ci->c && ci->c->FindUser(ci->bi)) + if (ci->c && ci->c->FindUser(ci->GetBot())) { if (u) - ci->bi->Part(ci->c, "UNASSIGN from " + u->nick); + ci->GetBot()->Part(ci->c, "UNASSIGN from " + u->nick); else - ci->bi->Part(ci->c); + ci->GetBot()->Part(ci->c); } - ci->bi = NULL; - this->channels->erase(ci); + ci->SetBot(nullptr); } -unsigned BotInfo::GetChannelCount() const +unsigned ServiceBot::GetChannelCount() const { - return this->channels->size(); + return GetChannels().size(); } -void BotInfo::Join(Channel *c, ChannelStatus *status) +void ServiceBot::Join(Channel *c, ChannelStatus *status) { if (c->FindUser(this) != NULL) return; c->JoinUser(this, status); if (IRCD) - IRCD->SendJoin(this, c, status); + IRCD->Send<messages::Join>(this, c, status); - FOREACH_MOD(OnJoinChannel, (this, c)); + EventManager::Get()->Dispatch(&Event::JoinChannel::OnJoinChannel, this, c); } -void BotInfo::Join(const Anope::string &chname, ChannelStatus *status) +void ServiceBot::Join(const Anope::string &chname, ChannelStatus *status) { bool c; return this->Join(Channel::FindOrCreate(chname, c), status); } -void BotInfo::Part(Channel *c, const Anope::string &reason) +void ServiceBot::Part(Channel *c, const Anope::string &reason) { if (c->FindUser(this) == NULL) return; - FOREACH_MOD(OnPrePartChannel, (this, c)); + EventManager::Get()->Dispatch(&Event::PrePartChannel::OnPrePartChannel, this, c); - IRCD->SendPart(this, c, "%s", !reason.empty() ? reason.c_str() : ""); + IRCD->SendPart(this, c, reason); c->DeleteUser(this); - FOREACH_MOD(OnPartChannel, (this, c, c->name, reason)); + EventManager::Get()->Dispatch(&Event::PartChannel::OnPartChannel, this, c, c->name, reason); } -void BotInfo::OnMessage(User *u, const Anope::string &message) +void ServiceBot::OnMessage(User *u, const Anope::string &message) { if (this->commands.empty()) return; @@ -232,16 +196,16 @@ void BotInfo::OnMessage(User *u, const Anope::string &message) Command::Run(source, message); } -CommandInfo& BotInfo::SetCommand(const Anope::string &cname, const Anope::string &sname, const Anope::string &permission) +CommandInfo& ServiceBot::SetCommand(const Anope::string &cname, const Anope::string &sname, const Anope::string &permission) { - CommandInfo ci; + CommandInfo &ci = this->commands[cname]; ci.name = sname; + ci.cname = cname; ci.permission = permission; - this->commands[cname] = ci; - return this->commands[cname]; + return ci; } -CommandInfo *BotInfo::GetCommand(const Anope::string &cname) +CommandInfo *ServiceBot::GetCommand(const Anope::string &cname) { CommandInfo::map::iterator it = this->commands.find(cname); if (it != this->commands.end()) @@ -249,30 +213,96 @@ CommandInfo *BotInfo::GetCommand(const Anope::string &cname) return NULL; } -BotInfo* BotInfo::Find(const Anope::string &nick, bool nick_only) +CommandInfo *ServiceBot::FindCommand(const Anope::string &service) { - if (!nick_only && IRCD != NULL && IRCD->RequiresID) + for (auto& it : commands) { - botinfo_map::iterator it = BotListByUID->find(nick); - if (it != BotListByUID->end()) - { - BotInfo *bi = it->second; - bi->QueueUpdate(); - return bi; - } - - if (IRCD->AmbiguousID) - return NULL; + CommandInfo &ci = it.second; + + if (ci.name == service) + return &ci; } - botinfo_map::iterator it = BotListByNick->find(nick); - if (it != BotListByNick->end()) + return nullptr; +} + +ServiceBot* ServiceBot::Find(const Anope::string &nick, bool nick_only) +{ + User *u = User::Find(nick, nick_only); + if (u && u->type == UserType::BOT) + return anope_dynamic_static_cast<ServiceBot *>(u); + return nullptr; +} + +void BotInfo::Delete() +{ + if (bot) { - BotInfo *bi = it->second; - bi->QueueUpdate(); - return bi; + ServiceBot *b = bot; + bot = nullptr; + delete b; } - return NULL; + return Serialize::Object::Delete(); +} + +void BotInfo::SetCreated(const time_t &t) +{ + Set(&BotInfoType::created, t); +} + +time_t BotInfo::GetCreated() +{ + return Get(&BotInfoType::created); +} + +void BotInfo::SetOperOnly(const bool &b) +{ + Set(&BotInfoType::operonly, b); +} + +bool BotInfo::GetOperOnly() +{ + return Get(&BotInfoType::operonly); +} + +void BotInfo::SetNick(const Anope::string &n) +{ + Set(&BotInfoType::nick, n); +} + +Anope::string BotInfo::GetNick() +{ + return Get(&BotInfoType::nick); +} + +void BotInfo::SetUser(const Anope::string &u) +{ + Set(&BotInfoType::user, u); +} + +Anope::string BotInfo::GetUser() +{ + return Get(&BotInfoType::user); +} + +void BotInfo::SetHost(const Anope::string &h) +{ + Set(&BotInfoType::host, h); +} + +Anope::string BotInfo::GetHost() +{ + return Get(&BotInfoType::host); +} + +void BotInfo::SetRealName(const Anope::string &r) +{ + Set(&BotInfoType::realname, r); +} + +Anope::string BotInfo::GetRealName() +{ + return Get(&BotInfoType::realname); } |