diff options
Diffstat (limited to 'modules/core')
146 files changed, 0 insertions, 28601 deletions
diff --git a/modules/core/botserv.h b/modules/core/botserv.h deleted file mode 100644 index 5fa03f870..000000000 --- a/modules/core/botserv.h +++ /dev/null @@ -1,63 +0,0 @@ -#ifndef BOTSERV_H -#define BOTSERV_H - -struct UserData -{ - UserData() - { - this->Clear(); - } - - void Clear() - { - last_use = last_start = Anope::CurTime; - lines = times = 0; - lastline.clear(); - } - - /* Data validity */ - time_t last_use; - - /* for flood kicker */ - int16 lines; - time_t last_start; - - /* for repeat kicker */ - Anope::string lastline; - Anope::string lasttarget; - int16 times; -}; - -struct BanData -{ - Anope::string mask; - time_t last_use; - int16 ttb[TTB_SIZE]; - - BanData() - { - this->Clear(); - } - - void Clear() - { - last_use = 0; - for (int i = 0; i < TTB_SIZE; ++i) - this->ttb[i] = 0; - } -}; - -class BotServService : public Service -{ - public: - BotServService(Module *m) : Service(m, "BotServ") { } - - virtual UserData *GetUserData(User *u, Channel *c) = 0; - - virtual BanData *GetBanData(User *u, Channel *c) = 0; -}; - -static service_reference<BotServService> botserv("BotServ"); - -#endif // BOTSERV_H - diff --git a/modules/core/bs_assign.cpp b/modules/core/bs_assign.cpp deleted file mode 100644 index 803368994..000000000 --- a/modules/core/bs_assign.cpp +++ /dev/null @@ -1,168 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandBSAssign : public Command -{ - public: - CommandBSAssign(Module *creator) : Command(creator, "botserv/assign", 2, 2) - { - this->SetDesc(_("Assigns a bot to a channel")); - this->SetSyntax(_("\037channel\037 \037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &nick = params[1]; - - User *u = source.u; - - if (readonly) - { - source.Reply(BOT_ASSIGN_READONLY); - return; - } - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - BotInfo *bi = findbot(nick); - if (!bi) - { - source.Reply(BOT_DOES_NOT_EXIST, nick.c_str()); - return; - } - - if (ci->botflags.HasFlag(BS_NOBOT) || (!ci->HasPriv(u, CA_ASSIGN) && !u->HasPriv("botserv/administration"))) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (bi->HasFlag(BI_PRIVATE) && !u->HasCommand("botserv/botserv/assign/private")) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (ci->bi == bi) - { - source.Reply(_("Bot \002%s\002 is already assigned to channel \002%s\002."), ci->bi->nick.c_str(), chan.c_str()); - return; - } - - bool override = !ci->HasPriv(u, CA_ASSIGN); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "for " << bi->nick; - - bi->Assign(u, ci); - source.Reply(_("Bot \002%s\002 has been assigned to %s."), bi->nick.c_str(), ci->name.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Assigns a bot pointed out by nick to the channel chan. You\n" - "can then configure the bot for the channel so it fits\n" - "your needs.")); - return true; - } -}; - -class CommandBSUnassign : public Command -{ - public: - CommandBSUnassign(Module *creator) : Command(creator, "botserv/unassign", 1, 1) - { - this->SetDesc(_("Unassigns a bot from a channel")); - this->SetSyntax(_("\037channel\037 \037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - if (readonly) - { - source.Reply(BOT_ASSIGN_READONLY); - return; - } - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (!u->HasPriv("botserv/administration") && !ci->HasPriv(u, CA_ASSIGN)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (!ci->bi) - { - source.Reply(BOT_NOT_ASSIGNED); - return; - } - - if (ci->HasFlag(CI_PERSIST) && !ModeManager::FindChannelModeByName(CMODE_PERM)) - { - source.Reply(_("You can not unassign bots while persist is set on the channel.")); - return; - } - - bool override = !ci->HasPriv(u, CA_ASSIGN); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "for " << ci->bi->nick; - - ci->bi->UnAssign(u, ci); - source.Reply(_("There is no bot assigned to %s anymore."), ci->name.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Unassigns a bot from a channel. When you use this command,\n" - "the bot won't join the channel anymore. However, bot\n" - "configuration for the channel is kept, so you will always\n" - "be able to reassign a bot later without have to reconfigure\n" - "it entirely.")); - return true; - } -}; - -class BSAssign : public Module -{ - CommandBSAssign commandbsassign; - CommandBSUnassign commandbsunassign; - - public: - BSAssign(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbsassign(this), commandbsunassign(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbsassign); - ModuleManager::RegisterService(&commandbsunassign); - } -}; - -MODULE_INIT(BSAssign) diff --git a/modules/core/bs_badwords.cpp b/modules/core/bs_badwords.cpp deleted file mode 100644 index a27dca2d4..000000000 --- a/modules/core/bs_badwords.cpp +++ /dev/null @@ -1,331 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class BadwordsListCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - bool SentHeader; - public: - BadwordsListCallback(CommandSource &_source, ChannelInfo *_ci, const Anope::string &list) : NumberList(list, false), source(_source), ci(_ci), SentHeader(false) - { - } - - ~BadwordsListCallback() - { - if (!SentHeader) - source.Reply(_("No matching entries on %s bad words list."), ci->name.c_str()); - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetBadWordCount()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Bad words list for %s:\n" - " Num Word Type"), ci->name.c_str()); - } - - DoList(source, Number - 1, ci->GetBadWord(Number - 1)); - } - - static void DoList(CommandSource &source, unsigned Number, BadWord *bw) - { - source.Reply(_(" %3d %-30s %s"), Number + 1, bw->word.c_str(), bw->type == BW_SINGLE ? "(SINGLE)" : (bw->type == BW_START ? "(START)" : (bw->type == BW_END ? "(END)" : ""))); - } -}; - -class BadwordsDelCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - Command *c; - unsigned Deleted; - bool override; - public: - BadwordsDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, const Anope::string &list) : NumberList(list, true), source(_source), ci(_ci), c(_c), Deleted(0), override(false) - { - if (!ci->HasPriv(source.u, CA_BADWORDS) && source.u->HasPriv("botserv/administration")) - this->override = true; - } - - ~BadwordsDelCallback() - { - if (!Deleted) - source.Reply(_("No matching entries on %s bad words list."), ci->name.c_str()); - else if (Deleted == 1) - source.Reply(_("Deleted 1 entry from %s bad words list."), ci->name.c_str()); - else - source.Reply(_("Deleted %d entries from %s bad words list."), Deleted, ci->name.c_str()); - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetBadWordCount()) - return; - - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, c, ci) << "DEL " << ci->GetBadWord(Number - 1)->word; - ++Deleted; - ci->EraseBadWord(Number - 1); - } -}; - -class CommandBSBadwords : public Command -{ - private: - void DoList(CommandSource &source, ChannelInfo *ci, const Anope::string &word) - { - bool override = !ci->HasPriv(source.u, CA_BADWORDS); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, this, ci) << "LIST"; - - if (!ci->GetBadWordCount()) - source.Reply(_("%s bad words list is empty."), ci->name.c_str()); - else if (!word.empty() && word.find_first_not_of("1234567890,-") == Anope::string::npos) - { - BadwordsListCallback list(source, ci, word); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = ci->GetBadWordCount(); i < end; ++i) - { - BadWord *bw = ci->GetBadWord(i); - - if (!word.empty() && !Anope::Match(bw->word, word)) - continue; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Bad words list for %s:\n" - " Num Word Type"), ci->name.c_str()); - - } - - BadwordsListCallback::DoList(source, i, bw); - } - - if (!SentHeader) - source.Reply(_("No matching entries on %s bad words list."), ci->name.c_str()); - } - - return; - } - - void DoAdd(CommandSource &source, ChannelInfo *ci, const Anope::string &word) - { - size_t pos = word.rfind(' '); - BadWordType type = BW_ANY; - Anope::string realword = word; - - if (pos != Anope::string::npos) - { - Anope::string opt = word.substr(pos + 1); - if (!opt.empty()) - { - if (opt.equals_ci("SINGLE")) - type = BW_SINGLE; - else if (opt.equals_ci("START")) - type = BW_START; - else if (opt.equals_ci("END")) - type = BW_END; - } - realword = word.substr(0, pos); - } - - if (ci->GetBadWordCount() >= Config->BSBadWordsMax) - { - source.Reply(_("Sorry, you can only have %d bad words entries on a channel."), Config->BSBadWordsMax); - return; - } - - for (unsigned i = 0, end = ci->GetBadWordCount(); i < end; ++i) - { - BadWord *bw = ci->GetBadWord(i); - - if (!bw->word.empty() && ((Config->BSCaseSensitive && realword.equals_cs(bw->word)) || (!Config->BSCaseSensitive && realword.equals_ci(bw->word)))) - { - source.Reply(_("\002%s\002 already exists in %s bad words list."), bw->word.c_str(), ci->name.c_str()); - return; - } - } - - bool override = !ci->HasPriv(source.u, CA_BADWORDS); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, this, ci) << "ADD " << realword; - ci->AddBadWord(realword, type); - - source.Reply(_("\002%s\002 added to %s bad words list."), realword.c_str(), ci->name.c_str()); - - return; - } - - void DoDelete(CommandSource &source, ChannelInfo *ci, const Anope::string &word) - { - /* Special case: is it a number/list? Only do search if it isn't. */ - if (!word.empty() && isdigit(word[0]) && word.find_first_not_of("1234567890,-") == Anope::string::npos) - { - BadwordsDelCallback list(source, ci, this, word); - list.Process(); - } - else - { - unsigned i, end; - BadWord *badword; - - for (i = 0, end = ci->GetBadWordCount(); i < end; ++i) - { - badword = ci->GetBadWord(i); - - if (word.equals_ci(badword->word)) - break; - } - - if (i == end) - { - source.Reply(_("\002%s\002 not found on %s bad words list."), word.c_str(), ci->name.c_str()); - return; - } - - bool override = !ci->HasPriv(source.u, CA_BADWORDS); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, this, ci) << "DEL " << badword->word; - - source.Reply(_("\002%s\002 deleted from %s bad words list."), badword->word.c_str(), ci->name.c_str()); - - ci->EraseBadWord(i); - } - - return; - } - - void DoClear(CommandSource &source, ChannelInfo *ci) - { - bool override = !ci->HasPriv(source.u, CA_BADWORDS); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, this, ci) << "CLEAR"; - - ci->ClearBadWords(); - source.Reply(_("Bad words list is now empty.")); - return; - } - public: - CommandBSBadwords(Module *creator) : Command(creator, "botserv/badwords", 2, 3) - { - this->SetDesc(_("Maintains bad words list")); - this->SetSyntax(_("\037channel\037 ADD \037word\037 [\037SINGLE\037 | \037START\037 | \037END\037]")); - this->SetSyntax(_("\037channel\037 DEL {\037word\037 | \037entry-num\037 | \037list\037}")); - this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037list\037]")); - this->SetSyntax(_("\037channel\037 CLEAR")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[1]; - const Anope::string &word = params.size() > 2 ? params[2] : ""; - User *u = source.u; - bool need_args = cmd.equals_ci("LIST") || cmd.equals_ci("CLEAR"); - - if (!need_args && word.empty()) - { - this->OnSyntaxError(source, cmd); - return; - } - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - - if (!ci->HasPriv(u, CA_BADWORDS) && (!need_args || !u->HasPriv("botserv/administration"))) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (readonly) - { - source.Reply(_("Sorry, channel bad words list modification is temporarily disabled.")); - return; - } - - if (cmd.equals_ci("ADD")) - return this->DoAdd(source, ci, word); - else if (cmd.equals_ci("DEL")) - return this->DoDelete(source, ci, word); - else if (cmd.equals_ci("LIST")) - return this->DoList(source, ci, word); - else if (cmd.equals_ci("CLEAR")) - return this->DoClear(source, ci); - else - this->OnSyntaxError(source, ""); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002bad words list\002 for a channel. The bad\n" - "words list determines which words are to be kicked\n" - "when the bad words kicker is enabled. For more information,\n" - "type \002%s%s HELP KICK %s\002.\n" - " \n" - "The \002ADD\002 command adds the given word to the\n" - "badword list. If SINGLE is specified, a kick will be\n" - "done only if a user says the entire word. If START is \n" - "specified, a kick will be done if a user says a word\n" - "that starts with \037word\037. If END is specified, a kick\n" - "will be done if a user says a word that ends with\n" - "\037word\037. If you don't specify anything, a kick will\n" - "be issued every time \037word\037 is said by a user.\n" - " \n"), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), source.command.c_str()); - source.Reply(_("The \002DEL\002 command removes the given word from the\n" - "bad words list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - " \n" - "The \002LIST\002 command displays the bad words list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002#channel LIST 2-5,7-9\002\n" - " Lists bad words entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002CLEAR\002 command clears all entries of the\n" - "bad words list.")); - return true; - } -}; - -class BSBadwords : public Module -{ - CommandBSBadwords commandbsbadwords; - - public: - BSBadwords(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbsbadwords(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbsbadwords); - } -}; - -MODULE_INIT(BSBadwords) diff --git a/modules/core/bs_bot.cpp b/modules/core/bs_bot.cpp deleted file mode 100644 index 7500d1926..000000000 --- a/modules/core/bs_bot.cpp +++ /dev/null @@ -1,414 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandBSBot : public Command -{ - private: - void DoAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params[1]; - const Anope::string &user = params[2]; - const Anope::string &host = params[3]; - const Anope::string &real = params[4]; - BotInfo *bi; - - if (findbot(nick)) - { - source.Reply(_("Bot \002%s\002 already exists."), nick.c_str()); - return; - } - - if (nick.length() > Config->NickLen) - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - if (user.length() > Config->UserLen) - { - source.Reply(_("Bot Idents may only contain %d characters."), Config->UserLen); - return; - } - - if (host.length() > Config->HostLen) - { - source.Reply(_("Bot Hosts may only contain %d characters."), Config->HostLen); - return; - } - - /* Check the nick is valid re RFC 2812 */ - if (isdigit(nick[0]) || nick[0] == '-') - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - for (unsigned i = 0, end = nick.length(); i < end && i < Config->NickLen; ++i) - if (!isvalidnick(nick[i])) - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - /* check for hardcored ircd forbidden nicks */ - if (!ircdproto->IsNickValid(nick)) - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - /* Check the host is valid re RFC 2812 */ - if (!isValidHost(host, 3)) - { - source.Reply(_("Bot Hosts may only contain valid host characters.")); - return; - } - - for (unsigned i = 0, end = user.length(); i < end && i < Config->UserLen; ++i) - if (!isalnum(user[i])) - { - source.Reply(_("Bot Idents may only contain valid characters."), Config->UserLen); - return; - } - - /* We check whether the nick is registered, and inform the user - * if so. You need to drop the nick manually before you can use - * it as a bot nick from now on -GD - */ - if (findnick(nick)) - { - source.Reply(NICK_ALREADY_REGISTERED, nick.c_str()); - return; - } - - bi = new BotInfo(nick, user, host, real); - - Log(LOG_ADMIN, source.u, this) << "ADD " << bi->GetMask() << " " << bi->realname; - - source.Reply(_("%s!%s@%s (%s) added to the bot list."), bi->nick.c_str(), bi->GetIdent().c_str(), bi->host.c_str(), bi->realname.c_str()); - - FOREACH_MOD(I_OnBotCreate, OnBotCreate(bi)); - return; - } - - void DoChange(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &oldnick = params[1]; - const Anope::string &nick = params.size() > 2 ? params[2] : ""; - const Anope::string &user = params.size() > 3 ? params[3] : ""; - const Anope::string &host = params.size() > 4 ? params[4] : ""; - const Anope::string &real = params.size() > 5 ? params[5] : ""; - BotInfo *bi; - - if (oldnick.empty() || nick.empty()) - { - this->OnSyntaxError(source, "CHANGE"); - return; - } - - if (!(bi = findbot(oldnick))) - { - source.Reply(BOT_DOES_NOT_EXIST, oldnick.c_str()); - return; - } - - if (!oldnick.equals_ci(nick) && nickIsServices(oldnick, false)) - { - source.Reply(BOT_DOES_NOT_EXIST, oldnick.c_str()); - return; - } - - if (nick.length() > Config->NickLen) - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - if (!user.empty() && user.length() > Config->UserLen) - { - source.Reply(_("Bot Idents may only contain %d characters."), Config->UserLen); - return; - } - - if (!host.empty() && host.length() > Config->HostLen) - { - source.Reply(_("Bot Hosts may only contain %d characters."), Config->HostLen); - return; - } - - if (!oldnick.equals_ci(nick) && nickIsServices(nick, false)) - { - source.Reply(BOT_DOES_NOT_EXIST, oldnick.c_str()); - return; - } - - /* Checks whether there *are* changes. - * Case sensitive because we may want to change just the case. - * And we must finally check that the nick is not already - * taken by another bot. - */ - if (nick.equals_cs(bi->nick) && (!user.empty() ? user.equals_cs(bi->GetIdent()) : 1) && (!host.empty() ? host.equals_cs(bi->host) : 1) && (!real.empty() ? real.equals_cs(bi->realname) : 1)) - { - source.Reply(_("Old info is equal to the new one.")); - return; - } - - /* Check the nick is valid re RFC 2812 */ - if (isdigit(nick[0]) || nick[0] == '-') - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - for (unsigned i = 0, end = nick.length(); i < end && i < Config->NickLen; ++i) - if (!isvalidnick(nick[i])) - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - /* check for hardcored ircd forbidden nicks */ - if (!ircdproto->IsNickValid(nick)) - { - source.Reply(_("Bot Nicks may only contain valid nick characters.")); - return; - } - - if (!host.empty() && !isValidHost(host, 3)) - { - source.Reply(_("Bot Hosts may only contain valid host characters.")); - return; - } - - if (!user.empty()) - for (unsigned i = 0, end = user.length(); i < end && i < Config->UserLen; ++i) - if (!isalnum(user[i])) - { - source.Reply(_("Bot Idents may only contain valid characters."), Config->UserLen); - return; - } - - if (!nick.equals_ci(bi->nick) && findbot(nick)) - { - source.Reply(_("Bot \002%s\002 already exists."), nick.c_str()); - return; - } - - if (!nick.equals_ci(bi->nick)) - { - /* We check whether the nick is registered, and inform the user - * if so. You need to drop the nick manually before you can use - * it as a bot nick from now on -GD - */ - if (findnick(nick)) - { - source.Reply(NICK_ALREADY_REGISTERED, nick.c_str()); - return; - } - - /* The new nick is really different, so we remove the Q line for the old nick. */ - if (ircd->sqline) - { - XLine x(bi->nick); - ircdproto->SendSQLineDel(&x); - } - - /* Add a Q line for the new nick */ - XLine x(nick, "Reserved for services"); - ircdproto->SendSQLine(NULL, &x); - } - - if (!user.empty()) - ircdproto->SendQuit(bi, "Quit: Be right back"); - else - { - ircdproto->SendChangeBotNick(bi, nick); - } - - if (!nick.equals_cs(bi->nick)) - bi->SetNewNick(nick); - - if (!user.empty() && !user.equals_cs(bi->GetIdent())) - bi->SetIdent(user); - if (!host.empty() && !host.equals_cs(bi->host)) - bi->host = host; - if (!real.empty() && !real.equals_cs(bi->realname)) - bi->realname = real; - - if (!user.empty()) - { - ircdproto->SendClientIntroduction(bi, ircd->pseudoclient_mode); - bi->RejoinAll(); - } - - source.Reply(_("Bot \002%s\002 has been changed to %s!%s@%s (%s)"), oldnick.c_str(), bi->nick.c_str(), bi->GetIdent().c_str(), bi->host.c_str(), bi->realname.c_str()); - Log(LOG_ADMIN, source.u, this) << "CHANGE " << oldnick << " to " << bi->GetMask() << " " << bi->realname; - - FOREACH_MOD(I_OnBotChange, OnBotChange(bi)); - return; - } - - void DoDel(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params[1]; - BotInfo *bi; - - if (nick.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (!(bi = findbot(nick))) - { - source.Reply(BOT_DOES_NOT_EXIST, nick.c_str()); - return; - } - - if (nickIsServices(nick, false)) - { - source.Reply(BOT_DOES_NOT_EXIST, nick.c_str()); - return; - } - - FOREACH_MOD(I_OnBotDelete, OnBotDelete(bi)); - - Log(LOG_ADMIN, source.u, this) << "DEL " << bi->nick; - - source.Reply(_("Bot \002%s\002 has been deleted."), nick.c_str()); - delete bi; - return; - } - public: - CommandBSBot(Module *creator) : Command(creator, "botserv/bot", 1, 6) - { - this->SetDesc(_("Maintains network bot list")); - this->SetSyntax(_("\002ADD \037nick\037 \037user\037 \037host\037 \037real\037\002")); - this->SetSyntax(_("\002CHANGE \037oldnick\037 \037newnick\037 [\037user\037 [\037host\037 [\037real\037]]]\002")); - this->SetSyntax(_("\002DEL \037nick\037\002")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[0]; - User *u = source.u; - - if (readonly) - { - source.Reply(_("Sorry, bot modification is temporarily disabled.")); - return; - } - - if (cmd.equals_ci("ADD")) - { - // ADD nick user host real - 5 - if (!u->HasCommand("botserv/bot/add")) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params.size() < 5) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - std::vector<Anope::string> tempparams = params; - // ADD takes less params than CHANGE, so we need to take 6 if given and append it with a space to 5. - if (tempparams.size() >= 6) - tempparams[4] = tempparams[4] + " " + tempparams[5]; - - return this->DoAdd(source, tempparams); - } - else if (cmd.equals_ci("CHANGE")) - { - // CHANGE oldn newn user host real - 6 - // but only oldn and newn are required - if (!u->HasCommand("botserv/bot/change")) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params.size() < 3) - { - this->OnSyntaxError(source, "CHANGE"); - return; - } - - return this->DoChange(source, params); - } - else if (cmd.equals_ci("DEL")) - { - // DEL nick - if (!u->HasCommand("botserv/bot/del")) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params.size() < 1) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - return this->DoDel(source, params); - } - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services Operators to create, modify, and delete\n" - "bots that users will be able to use on their own\n" - "channels.\n" - " \n" - "\002BOT ADD\002 adds a bot with the given nickname, username,\n" - "hostname and realname. Since no integrity checks are done \n" - "for these settings, be really careful.\n" - "\002BOT CHANGE\002 allows to change nickname, username, hostname\n" - "or realname of a bot without actually delete it (and all\n" - "the data associated with it).\n" - "\002BOT DEL\002 removes the given bot from the bot list. \n" - " \n" - "\002Note\002: you cannot create a bot that has a nick that is\n" - "currently registered. If an unregistered user is currently\n" - "using the nick, they will be killed.")); - return true; - } -}; - -class BSBot : public Module -{ - CommandBSBot commandbsbot; - - public: - BSBot(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbsbot(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbsbot); - } -}; - -MODULE_INIT(BSBot) diff --git a/modules/core/bs_botlist.cpp b/modules/core/bs_botlist.cpp deleted file mode 100644 index ee7e4d2d8..000000000 --- a/modules/core/bs_botlist.cpp +++ /dev/null @@ -1,91 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandBSBotList : public Command -{ - public: - CommandBSBotList(Module *creator) : Command(creator, "botserv/botlist", 0, 0) - { - this->SetDesc(_("Lists available bots")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - unsigned count = 0; - - for (Anope::insensitive_map<BotInfo *>::const_iterator it = BotListByNick.begin(), it_end = BotListByNick.end(); it != it_end; ++it) - { - BotInfo *bi = it->second; - - if (!bi->HasFlag(BI_PRIVATE)) - { - if (!count) - source.Reply(_("Bot list:")); - ++count; - source.Reply(" %-15s (%s@%s)", bi->nick.c_str(), bi->GetIdent().c_str(), bi->host.c_str()); - } - } - - if (u->HasCommand("botserv/botserv/botlist") && count < BotListByNick.size()) - { - source.Reply(_("Bots reserved to IRC operators:")); - - for (Anope::insensitive_map<BotInfo *>::const_iterator it = BotListByNick.begin(), it_end = BotListByNick.end(); it != it_end; ++it) - { - BotInfo *bi = it->second; - - if (bi->HasFlag(BI_PRIVATE)) - { - source.Reply(" %-15s (%s@%s)", bi->nick.c_str(), bi->GetIdent().c_str(), bi->host.c_str()); - ++count; - } - } - } - - if (!count) - source.Reply(_("There are no bots available at this time.\n" - "Ask a Services Operator to create one!")); - else - source.Reply(_("%d bots available."), count); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all available bots on this network.")); - return true; - } -}; - -class BSBotList : public Module -{ - CommandBSBotList commandbsbotlist; - - public: - BSBotList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbsbotlist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbsbotlist); - } -}; - -MODULE_INIT(BSBotList) diff --git a/modules/core/bs_control.cpp b/modules/core/bs_control.cpp deleted file mode 100644 index 16a5b372a..000000000 --- a/modules/core/bs_control.cpp +++ /dev/null @@ -1,158 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandBSSay : public Command -{ - public: - CommandBSSay(Module *creator) : Command(creator, "botserv/say", 2, 2) - { - this->SetDesc(_("Makes the bot say the given text on the given channel")); - this->SetSyntax(_("\037channel\037 \037text\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &text = params[1]; - - User *u = source.u; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (!ci->HasPriv(u, CA_SAY)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (!ci->bi) - { - source.Reply(BOT_NOT_ASSIGNED); - return; - } - - if (!ci->c || !ci->c->FindUser(ci->bi)) - { - source.Reply(BOT_NOT_ON_CHANNEL, ci->name.c_str()); - return; - } - - if (text[0] == '\001') - { - this->OnSyntaxError(source, ""); - return; - } - - ircdproto->SendPrivmsg(ci->bi, ci->name, "%s", text.c_str()); - ci->bi->lastmsg = Anope::CurTime; - - // XXX need a way to find if someone is overriding this - Log(LOG_COMMAND, u, this, ci) << text; - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Makes the bot say the given text on the given channel.")); - return true; - } -}; - -class CommandBSAct : public Command -{ - public: - CommandBSAct(Module *creator) : Command(creator, "botserv/act", 2, 2) - { - this->SetDesc(_("Makes the bot do the equivalent of a \"/me\" command")); - this->SetSyntax(_("\037channel\037 \037text\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - Anope::string message = params[1]; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (!ci->HasPriv(u, CA_SAY)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (!ci->bi) - { - source.Reply(BOT_NOT_ASSIGNED); - return; - } - - if (!ci->c || !ci->c->FindUser(ci->bi)) - { - source.Reply(BOT_NOT_ON_CHANNEL, ci->name.c_str()); - return; - } - - size_t i = 0; - while ((i = message.find(1)) && i != Anope::string::npos) - message.erase(i, 1); - - ircdproto->SendAction(ci->bi, ci->name, "%s", message.c_str()); - ci->bi->lastmsg = Anope::CurTime; - - // XXX Need to be able to find if someone is overriding this. - Log(LOG_COMMAND, u, this, ci) << message; - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Makes the bot do the equivalent of a \"/me\" command\n" - "on the given channel using the given text.")); - return true; - } -}; - -class BSControl : public Module -{ - CommandBSSay commandbssay; - CommandBSAct commandbsact; - - public: - BSControl(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbssay(this), commandbsact(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbssay); - ModuleManager::RegisterService(&commandbsact); - } -}; - -MODULE_INIT(BSControl) diff --git a/modules/core/bs_info.cpp b/modules/core/bs_info.cpp deleted file mode 100644 index b48a0b296..000000000 --- a/modules/core/bs_info.cpp +++ /dev/null @@ -1,244 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * - */ -/*************************************************************************/ - -#include "module.h" - -class CommandBSInfo : public Command -{ - private: - void send_bot_channels(CommandSource &source, BotInfo *bi) - { - Anope::string buf; - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ++it) - { - ChannelInfo *ci = it->second; - - if (ci->bi == bi) - { - if (buf.length() + ci->name.length() > 300) - { - source.Reply("%s", buf.c_str()); - buf.clear(); - } - buf += " " + ci->name + " "; - } - } - - if (!buf.empty()) - source.Reply("%s", buf.c_str()); - return; - } - public: - CommandBSInfo(Module *creator) : Command(creator, "botserv/info", 1, 1) - { - this->SetDesc(_("Allows you to see BotServ information about a channel or a bot")); - this->SetSyntax(_("\002INFO {\037chan\037 | \037nick\037}\002")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &query = params[0]; - - bool need_comma = false; - char buf[BUFSIZE], *end; - - User *u = source.u; - BotInfo *bi = findbot(query); - ChannelInfo *ci; - if (bi) - { - source.Reply(_("Information for bot \002%s\002:"), bi->nick.c_str()); - source.Reply(_(" Mask : %s@%s"), bi->GetIdent().c_str(), bi->host.c_str()); - source.Reply(_(" Real name : %s"), bi->realname.c_str()); - source.Reply(_(" Created : %s"), do_strftime(bi->created).c_str()); - source.Reply(_(" Options : %s"), bi->HasFlag(BI_PRIVATE) ? _("Private") : _("None")); - source.Reply(_(" Used on : %d channel(s)"), bi->chancount); - - if (u->HasPriv("botserv/administration")) - this->send_bot_channels(source, bi); - } - else if ((ci = cs_findchan(query))) - { - if (!ci->HasPriv(u, CA_FOUNDER) && !u->HasPriv("botserv/administration")) - { - source.Reply(ACCESS_DENIED); - return; - } - - source.Reply(CHAN_INFO_HEADER, ci->name.c_str()); - if (ci->bi) - source.Reply(_(" Bot nick : %s"), ci->bi->nick.c_str()); - else - source.Reply(_(" Bot nick : not assigned yet.")); - - if (ci->botflags.HasFlag(BS_KICK_BADWORDS)) - { - if (ci->ttb[TTB_BADWORDS]) - source.Reply(_(" Bad words kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_BADWORDS]); - else - source.Reply(_(" Bad words kicker : %s"), ENABLED); - } - else - source.Reply(_(" Bad words kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_BOLDS)) - { - if (ci->ttb[TTB_BOLDS]) - source.Reply(_(" Bolds kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_BOLDS]); - else - source.Reply(_(" Bolds kicker : %s"), ENABLED); - } - else - source.Reply(_(" Bolds kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_CAPS)) - { - if (ci->ttb[TTB_CAPS]) - source.Reply(_(" Caps kicker : %s (%d kick(s) to ban; minimum %d/%d%%)"), ENABLED, ci->ttb[TTB_CAPS], ci->capsmin, ci->capspercent); - else - source.Reply(_(" Caps kicker : %s (minimum %d/%d%%)"), ENABLED, ci->capsmin, ci->capspercent); - } - else - source.Reply(_(" Caps kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_COLORS)) - { - if (ci->ttb[TTB_COLORS]) - source.Reply(_(" Colors kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_COLORS]); - else - source.Reply(_(" Colors kicker : %s"), ENABLED); - } - else - source.Reply(_(" Colors kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_FLOOD)) - { - if (ci->ttb[TTB_FLOOD]) - source.Reply(_(" Flood kicker : %s (%d kick(s) to ban; %d lines in %ds)"), ENABLED, ci->ttb[TTB_FLOOD], ci->floodlines, ci->floodsecs); - else - source.Reply(_(" Flood kicker : %s (%d lines in %ds)"), ENABLED, ci->floodlines, ci->floodsecs); - } - else - source.Reply(_(" Flood kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_REPEAT)) - { - if (ci->ttb[TTB_REPEAT]) - source.Reply(_(" Repeat kicker : %s (%d kick(s) to ban; %d times)"), ENABLED, ci->ttb[TTB_REPEAT], ci->repeattimes); - else - source.Reply(_(" Repeat kicker : %s (%d times)"), ENABLED, ci->repeattimes); - } - else - source.Reply(_(" Repeat kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_REVERSES)) - { - if (ci->ttb[TTB_REVERSES]) - source.Reply(_(" Reverses kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_REVERSES]); - else - source.Reply(_(" Reverses kicker : %s"), ENABLED); - } - else - source.Reply(_(" Reverses kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_UNDERLINES)) - { - if (ci->ttb[TTB_UNDERLINES]) - source.Reply(_(" Underlines kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_UNDERLINES]); - else - source.Reply(_(" Underlines kicker : %s"), ENABLED); - } - else - source.Reply(_(" Underlines kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_ITALICS)) - { - if (ci->ttb[TTB_ITALICS]) - source.Reply(_(" Italics kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_ITALICS]); - else - source.Reply(_(" Italics kicker : %s"), ENABLED); - } - else - source.Reply(_(" Italics kicker : %s"), DISABLED); - if (ci->botflags.HasFlag(BS_KICK_AMSGS)) - { - if (ci->ttb[TTB_AMSGS]) - source.Reply(_(" AMSG kicker : %s (%d kick(s) to ban)"), ENABLED, ci->ttb[TTB_AMSGS]); - else - source.Reply(_(" AMSG kicker : %s"), ENABLED); - } - else - source.Reply(_(" AMSG kicker : %s"), DISABLED); - - if (ci->botflags.HasFlag(BS_MSG_PRIVMSG)) - source.Reply(_(" Fantasy reply : %s"), "PRIVMSG"); - else if (ci->botflags.HasFlag(BS_MSG_NOTICE)) - source.Reply(_(" Fantasy reply : %s"), "NOTICE"); - else if (ci->botflags.HasFlag(BS_MSG_NOTICEOPS)) - source.Reply(_(" Fantasy reply : %s"), "NOTICEOPS"); - - end = buf; - *end = 0; - if (ci->botflags.HasFlag(BS_DONTKICKOPS)) - { - end += snprintf(end, sizeof(buf) - (end - buf), "%s", _("Ops protection")); - need_comma = true; - } - if (ci->botflags.HasFlag(BS_DONTKICKVOICES)) - { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", need_comma ? ", " : "", _("Voices protection")); - need_comma = true; - } - if (ci->botflags.HasFlag(BS_FANTASY)) - { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", need_comma ? ", " : "", _("Fantasy")); - need_comma = true; - } - if (ci->botflags.HasFlag(BS_GREET)) - { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", need_comma ? ", " : "", _("Greet")); - need_comma = true; - } - if (ci->botflags.HasFlag(BS_NOBOT)) - { - end += snprintf(end, sizeof(buf) - (end - buf), "%s%s", need_comma ? ", " : "", _("No bot")); - need_comma = true; - } - source.Reply(_(" Options : %s"), *buf ? buf : _("None")); - } - else - source.Reply(_("\002%s\002 is not a valid bot or registered channel."), query.c_str()); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to see %s information about a channel or a bot.\n" - "If the parameter is a channel, then you'll get information\n" - "such as enabled kickers. If the parameter is a nick,\n" - "you'll get information about a bot, such as creation\n" - "time or number of channels it is on."), source.owner->nick.c_str()); - return true; - } -}; - -class BSInfo : public Module -{ - CommandBSInfo commandbsinfo; - - public: - BSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbsinfo(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbsinfo); - } -}; - -MODULE_INIT(BSInfo) diff --git a/modules/core/bs_kick.cpp b/modules/core/bs_kick.cpp deleted file mode 100644 index 3f433f773..000000000 --- a/modules/core/bs_kick.cpp +++ /dev/null @@ -1,1011 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * - */ -/*************************************************************************/ - -#include "module.h" - -class CommandBSKick : public Command -{ - public: - CommandBSKick(Module *creator) : Command(creator, "botserv/kick", 3, 6) - { - this->SetDesc(_("Configures kickers")); - this->SetSyntax(_("\037channel\037 \037option\037 {\037ON|\037} [\037settings\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &option = params[1]; - const Anope::string &value = params[2]; - const Anope::string &ttb = params.size() > 3 ? params[3] : ""; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - - if (readonly) - source.Reply(_("Sorry, kicker configuration is temporarily disabled.")); - else if (ci == NULL) - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - else if (chan.empty() || option.empty() || value.empty()) - this->OnSyntaxError(source, ""); - else if (!value.equals_ci("ON") && !value.equals_ci("OFF")) - this->OnSyntaxError(source, ""); - else if (!ci->HasPriv(u, CA_SET) && !u->HasPriv("botserv/administration")) - source.Reply(ACCESS_DENIED); - else if (!ci->bi) - source.Reply(BOT_NOT_ASSIGNED); - else - { - bool override = !ci->HasPriv(u, CA_SET); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << option << " " << value; - - if (option.equals_ci("BADWORDS")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_BADWORDS] = convertTo<int16>(ttb); - if (ci->ttb[TTB_BADWORDS] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - /* reset the value back to 0 - TSL */ - ci->ttb[TTB_BADWORDS] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_BADWORDS] = 0; - - ci->botflags.SetFlag(BS_KICK_BADWORDS); - if (ci->ttb[TTB_BADWORDS]) - source.Reply(_("Bot will now kick \002bad words\002, and will place a ban after \n" - "%d kicks for the same user. Use the BADWORDS command\n" - "to add or remove a bad word."), ci->ttb[TTB_BADWORDS]); - else - source.Reply(_("Bot will now kick \002bad words\002. Use the BADWORDS command\n" - "to add or remove a bad word.")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_BADWORDS); - source.Reply(_("Bot won't kick \002bad words\002 anymore.")); - } - } - else if (option.equals_ci("BOLDS")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_BOLDS] = convertTo<int16>(ttb); - if (ci->ttb[TTB_BOLDS] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_BOLDS] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_BOLDS] = 0; - ci->botflags.SetFlag(BS_KICK_BOLDS); - if (ci->ttb[TTB_BOLDS]) - source.Reply(_("Bot will now kick \002bolds\002, and will place a ban after\n%d kicks to the same user."), ci->ttb[TTB_BOLDS]); - else - source.Reply(_("Bot will now kick \002bolds\002.")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_BOLDS); - source.Reply(_("Bot won't kick \002bolds\002 anymore.")); - } - } - else if (option.equals_ci("CAPS")) - { - if (value.equals_ci("ON")) - { - Anope::string min = params.size() > 4 ? params[4] : ""; - Anope::string percent = params.size() > 5 ? params[5] : ""; - - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_CAPS] = convertTo<int16>(ttb); - if (ci->ttb[TTB_CAPS] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_CAPS] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_CAPS] = 0; - - ci->capsmin = 10; - try - { - ci->capsmin = convertTo<int16>(min); - } - catch (const ConvertException &) { } - if (ci->capsmin < 1) - ci->capsmin = 10; - - ci->capspercent = 25; - try - { - ci->capspercent = convertTo<int16>(percent); - } - catch (const ConvertException &) { } - if (ci->capspercent < 1 || ci->capspercent > 100) - ci->capspercent = 25; - - ci->botflags.SetFlag(BS_KICK_CAPS); - if (ci->ttb[TTB_CAPS]) - source.Reply(_("Bot will now kick \002caps\002 (they must constitute at least\n" - "%d characters and %d%% of the entire message), and will \n" - "place a ban after %d kicks for the same user."), ci->capsmin, ci->capspercent, ci->ttb[TTB_CAPS]); - else - source.Reply(_("Bot will now kick \002caps\002 (they must constitute at least\n" - "%d characters and %d%% of the entire message)."), ci->capsmin, ci->capspercent); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_CAPS); - source.Reply(_("Bot won't kick \002caps\002 anymore.")); - } - } - else if (option.equals_ci("COLORS")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_COLORS] = convertTo<int16>(ttb); - if (ci->ttb[TTB_COLORS] < 1) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_COLORS] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_COLORS] = 0; - - ci->botflags.SetFlag(BS_KICK_COLORS); - if (ci->ttb[TTB_COLORS]) - source.Reply(_("Bot will now kick \002colors\002, and will place a ban after %d\nkicks for the same user."), ci->ttb[TTB_COLORS]); - else - source.Reply(_("Bot will now kick \002colors\002.")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_COLORS); - source.Reply(_("Bot won't kick \002colors\002 anymore.")); - } - } - else if (option.equals_ci("FLOOD")) - { - if (value.equals_ci("ON")) - { - Anope::string lines = params.size() > 4 ? params[4] : ""; - Anope::string secs = params.size() > 5 ? params[5] : ""; - - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_FLOOD] = convertTo<int16>(ttb); - if (ci->ttb[TTB_FLOOD] < 1) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_FLOOD] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_FLOOD] = 0; - - ci->floodlines = 6; - try - { - ci->floodlines = convertTo<int16>(lines); - } - catch (const ConvertException &) { } - if (ci->floodlines < 2) - ci->floodlines = 6; - - ci->floodsecs = 10; - try - { - ci->floodsecs = convertTo<int16>(secs); - } - catch (const ConvertException &) { } - if (ci->floodsecs < 1) - ci->floodsecs = 10; - if (ci->floodsecs > Config->BSKeepData) - ci->floodsecs = Config->BSKeepData; - - ci->botflags.SetFlag(BS_KICK_FLOOD); - if (ci->ttb[TTB_FLOOD]) - source.Reply(_("Bot will now kick \002flood\002 (%d lines in %d seconds and\nwill place a ban after %d kicks for the same user."), ci->floodlines, ci->floodsecs, ci->ttb[TTB_FLOOD]); - else - source.Reply(_("Bot will now kick \002flood\002 (%d lines in %d seconds)."), ci->floodlines, ci->floodsecs); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_FLOOD); - source.Reply(_("Bot won't kick \002flood\002 anymore.")); - } - } - else if (option.equals_ci("REPEAT")) - { - if (value.equals_ci("ON")) - { - Anope::string times = params.size() > 4 ? params[4] : ""; - - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_REPEAT] = convertTo<int16>(ttb); - if (ci->ttb[TTB_REPEAT] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_REPEAT] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_REPEAT] = 0; - - ci->repeattimes = 3; - try - { - ci->repeattimes = convertTo<int16>(times); - } - catch (const ConvertException &) { } - if (ci->repeattimes < 2) - ci->repeattimes = 3; - - ci->botflags.SetFlag(BS_KICK_REPEAT); - if (ci->ttb[TTB_REPEAT]) - source.Reply(_("Bot will now kick \002repeats\002 (users that say %d times\n" - "the same thing), and will place a ban after %d \n" - "kicks for the same user."), ci->repeattimes, ci->ttb[TTB_REPEAT]); - else - source.Reply(_("Bot will now kick \002repeats\002 (users that say %d times\n" - "the same thing)."), ci->repeattimes); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_REPEAT); - source.Reply(_("Bot won't kick \002repeats\002 anymore.")); - } - } - else if (option.equals_ci("REVERSES")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_REVERSES] = convertTo<int16>(ttb); - if (ci->ttb[TTB_REVERSES] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_REVERSES] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_REVERSES] = 0; - ci->botflags.SetFlag(BS_KICK_REVERSES); - if (ci->ttb[TTB_REVERSES]) - source.Reply(_("Bot will now kick \002reverses\002, and will place a ban after %d\nkicks for the same user."), ci->ttb[TTB_REVERSES]); - else - source.Reply(_("Bot will now kick \002reverses\002.")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_REVERSES); - source.Reply(_("Bot won't kick \002reverses\002 anymore.")); - } - } - else if (option.equals_ci("UNDERLINES")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_UNDERLINES] = convertTo<int16>(ttb); - if (ci->ttb[TTB_REVERSES] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_UNDERLINES] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_UNDERLINES] = 0; - - ci->botflags.SetFlag(BS_KICK_UNDERLINES); - if (ci->ttb[TTB_UNDERLINES]) - source.Reply(_("Bot will now kick \002underlines\002, and will place a ban after %d\nkicks for the same user."), ci->ttb[TTB_UNDERLINES]); - else - source.Reply(_("Bot will now kick \002underlines\002.")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_UNDERLINES); - source.Reply(_("Bot won't kick \002underlines\002 anymore.")); - } - } - else if (option.equals_ci("ITALICS")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_ITALICS] = convertTo<int16>(ttb); - if (ci->ttb[TTB_ITALICS] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_ITALICS] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_ITALICS] = 0; - - ci->botflags.SetFlag(BS_KICK_ITALICS); - if (ci->ttb[TTB_ITALICS]) - source.Reply(_("Bot will now kick \002italics\002, and will place a ban after\n%d kicks for the same user."), ci->ttb[TTB_ITALICS]); - else - source.Reply(_("Bot will now kick \002italics\002.")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_ITALICS); - source.Reply(_("Bot won't kick \002italics\002 anymore.")); - } - } - else if (option.equals_ci("AMSGS")) - { - if (value.equals_ci("ON")) - { - if (!ttb.empty()) - { - try - { - ci->ttb[TTB_AMSGS] = convertTo<int16>(ttb); - if (ci->ttb[TTB_AMSGS] < 0) - throw ConvertException(); - } - catch (const ConvertException &) - { - ci->ttb[TTB_AMSGS] = 0; - source.Reply(_("\002%s\002 cannot be taken as times to ban."), ttb.c_str()); - return; - } - } - else - ci->ttb[TTB_AMSGS] = 0; - - ci->botflags.SetFlag(BS_KICK_AMSGS); - if (ci->ttb[TTB_AMSGS]) - source.Reply(_("Bot will now kick for \002amsgs\002, and will place a ban after %d\nkicks for the same user."), ci->ttb[TTB_AMSGS]); - else - source.Reply(_("Bot will now kick for \002amsgs\002")); - } - else - { - ci->botflags.UnsetFlag(BS_KICK_AMSGS); - source.Reply(_("Bot won't kick for \002amsgs\002 anymore.")); - } - } - else - source.Reply(UNKNOWN_OPTION, Config->UseStrictPrivMsgString.c_str(), option.c_str(), this->name.c_str()); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - if (subcommand.empty()) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Configures bot kickers. \037option\037 can be one of:\n" - " \n" - " AMSGS Sets if the bot kicks for amsgs\n" - " BOLDS Sets if the bot kicks bolds\n" - " BADWORDS Sets if the bot kicks bad words\n" - " CAPS Sets if the bot kicks caps\n" - " COLORS Sets if the bot kicks colors\n" - " FLOOD Sets if the bot kicks flooding users\n" - " REPEAT Sets if the bot kicks users who repeat\n" - " themselves\n" - " REVERSES Sets if the bot kicks reverses\n" - " UNDERLINES Sets if the bot kicks underlines\n" - " ITALICS Sets if the bot kicks italics\n" - " \n" - "Type \002%s%s HELP KICK \037option\037\002 for more information\n" - "on a specific option.\n" - " \n" - "Note: access to this command is controlled by the\n" - "level SET."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - } - else if (subcommand.equals_ci("BADWORDS")) - source.Reply(_("Syntax: \002\037#channel\037 BADWORDS {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the bad words kicker on or off. When enabled, this\n" - "option tells the bot to kick users who say certain words\n" - "on the channels.\n" - "You can define bad words for your channel using the\n" - "\002BADWORDS\002 command. Type \002%s%s HELP BADWORDS\002 for\n" - "more information.\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - else if (subcommand.equals_ci("BOLDS")) - source.Reply(_("Syntax: \002\037channel\037 BOLDS {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the bolds kicker on or off. When enabled, this\n" - "option tells the bot to kick users who use bolds.\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("CAPS")) - source.Reply(_("Syntax: \002\037channel\037 CAPS {\037ON|OFF\037} [\037ttb\037 [\037min\037 [\037percent\037]]]\002\n" - "Sets the caps kicker on or off. When enabled, this\n" - "option tells the bot to kick users who are talking in\n" - "CAPS.\n" - "The bot kicks only if there are at least \002min\002 caps\n" - "and they constitute at least \002percent\002%% of the total \n" - "text line (if not given, it defaults to 10 characters\n" - "and 25%%).\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("COLORS")) - source.Reply(_("Syntax: \002\037channel\037 COLORS {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the colors kicker on or off. When enabled, this\n" - "option tells the bot to kick users who use colors.\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("FLOOD")) - source.Reply(_("Syntax: \002\037channel\037 FLOOD {\037ON|OFF\037} [\037ttb\037 [\037ln\037 [\037secs\037]]]\002\n" - "Sets the flood kicker on or off. When enabled, this\n" - "option tells the bot to kick users who are flooding\n" - "the channel using at least \002ln\002 lines in \002secs\002 seconds\n" - "(if not given, it defaults to 6 lines in 10 seconds).\n" - " \n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("REPEAT")) - source.Reply(_("Syntax: \002\037#channel\037 REPEAT {\037ON|OFF\037} [\037ttb\037 [\037num\037]]\002\n" - "Sets the repeat kicker on or off. When enabled, this\n" - "option tells the bot to kick users who are repeating\n" - "themselves \002num\002 times (if num is not given, it\n" - "defaults to 3).\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("REVERSES")) - source.Reply(_("Syntax: \002\037channel\037 REVERSES {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the reverses kicker on or off. When enabled, this\n" - "option tells the bot to kick users who use reverses.\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("UNDERLINES")) - source.Reply(_("Syntax: \002\037channel\037 UNDERLINES {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the underlines kicker on or off. When enabled, this\n" - "option tells the bot to kick users who use underlines.\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("ITALICS")) - source.Reply(_("Syntax: \002\037channel\037 ITALICS {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the italics kicker on or off. When enabled, this\n" - "option tells the bot to kick users who use italics.\n" - "ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else if (subcommand.equals_ci("AMSGS")) - source.Reply(_("Syntax: \002\037channel\037 AMSGS {\037ON|OFF\037} [\037ttb\037]\002\n" - "Sets the amsg kicker on or off. When enabled, the bot will\n" - "kick users who send the same message to multiple channels\n" - "where BotServ bots are.\n" - "Ttb is the number of times a user can be kicked\n" - "before it get banned. Don't give ttb to disable\n" - "the ban system once activated.")); - else - return false; - - return true; - } -}; - -struct BanData -{ - Anope::string mask; - time_t last_use; - int16 ttb[TTB_SIZE]; - - BanData() - { - this->Clear(); - } - - void Clear() - { - last_use = 0; - for (int i = 0; i < TTB_SIZE; ++i) - this->ttb[i] = 0; - } -}; - -struct UserData -{ - UserData() - { - this->Clear(); - } - - void Clear() - { - last_use = last_start = Anope::CurTime; - lines = times = 0; - lastline.clear(); - } - - /* Data validity */ - time_t last_use; - - /* for flood kicker */ - int16 lines; - time_t last_start; - - /* for repeat kicker */ - Anope::string lastline; - Anope::string lasttarget; - int16 times; -}; - - -class BanDataPurger : public CallBack -{ - public: - BanDataPurger(Module *owner) : CallBack(owner, 300, Anope::CurTime, true) { } - - void Tick(time_t) - { - Log(LOG_DEBUG) << "bs_main: Running bandata purger"; - - for (channel_map::iterator it = ChannelList.begin(), it_end = ChannelList.end(); it != it_end; ++it) - { - Channel *c = it->second; - - std::map<Anope::string, BanData> bandata; - if (c->GetExtRegular("bs_main_bandata", bandata)) - { - for (std::map<Anope::string, BanData>::iterator it2 = bandata.begin(), it2_end = bandata.end(); it2 != it2_end;) - { - const Anope::string &user = it->first; - BanData *bd = &it2->second; - ++it2; - - if (Anope::CurTime - bd->last_use > Config->BSKeepData) - { - bandata.erase(user); - continue; - } - } - - if (bandata.empty()) - c->Shrink("bs_main_bandata"); - } - } - } -}; - -class BSKick : public Module -{ - CommandBSKick commandbskick; - BanDataPurger purger; - - BanData *GetBanData(User *u, Channel *c) - { - std::map<Anope::string, BanData> bandatamap; - if (!c->GetExtRegular("bs_main_bandata", bandatamap)); - c->Extend("bs_main_bandata", new ExtensibleItemRegular<std::map<Anope::string, BanData> >(bandatamap)); - c->GetExtRegular("bs_main_bandata", bandatamap); - - BanData *bd = &bandatamap[u->GetMask()]; - if (bd->last_use && Anope::CurTime - bd->last_use > Config->BSKeepData) - bd->Clear(); - bd->last_use = Anope::CurTime; - return bd; - } - - UserData *GetUserData(User *u, Channel *c) - { - UserData *ud = NULL; - UserContainer *uc = c->FindUser(u); - if (uc != NULL && !uc->GetExtPointer("bs_main_userdata", ud)) - { - ud = new UserData(); - uc->Extend("bs_main_userdata", new ExtensibleItemPointer<UserData>(ud)); - } - return ud; - } - - void check_ban(ChannelInfo *ci, User *u, int ttbtype) - { - /* Don't ban ulines */ - if (u->server->IsULined()) - return; - - BanData *bd = this->GetBanData(u, ci->c); - - ++bd->ttb[ttbtype]; - if (ci->ttb[ttbtype] && bd->ttb[ttbtype] >= ci->ttb[ttbtype]) - { - /* Should not use == here because bd->ttb[ttbtype] could possibly be > ci->ttb[ttbtype] - * if the TTB was changed after it was not set (0) before and the user had already been - * kicked a few times. Bug #1056 - Adam */ - Anope::string mask; - - bd->ttb[ttbtype] = 0; - - get_idealban(ci, u, mask); - - if (ci->c) - ci->c->SetMode(NULL, CMODE_BAN, mask); - FOREACH_MOD(I_OnBotBan, OnBotBan(u, ci, mask)); - } - } - - void bot_kick(ChannelInfo *ci, User *u, const char *message, ...) - { - va_list args; - char buf[1024]; - - if (!ci || !ci->bi || !ci->c || !u || u->server->IsULined()) - return; - - Anope::string fmt = translate(u, message); - va_start(args, message); - vsnprintf(buf, sizeof(buf), fmt.c_str(), args); - va_end(args); - - ci->c->Kick(ci->bi, u, "%s", buf); - } - - public: - BSKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbskick(this), purger(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbskick); - - ModuleManager::Attach(I_OnPrivmsg, this); - } - - ~BSKick() - { - for (channel_map::const_iterator cit = ChannelList.begin(), cit_end = ChannelList.end(); cit != cit_end; ++cit) - { - cit->second->Shrink("bs_main_userdata"); - cit->second->Shrink("bs_main_bandata"); - } - } - - void OnPrivmsg(User *u, Channel *c, Anope::string &msg) - { - /* Now we can make kicker stuff. We try to order the checks - * from the fastest one to the slowest one, since there's - * no need to process other kickers if a user is kicked before - * the last kicker check. - * - * But FIRST we check whether the user is protected in any - * way. - */ - ChannelInfo *ci = c->ci; - if (ci == NULL) - return; - - bool Allow = true; - if (ci->HasPriv(u, CA_NOKICK)) - Allow = false; - else if (ci->botflags.HasFlag(BS_DONTKICKOPS) && (c->HasUserStatus(u, CMODE_HALFOP) || c->HasUserStatus(u, CMODE_OP) || c->HasUserStatus(u, CMODE_PROTECT) || c->HasUserStatus(u, CMODE_OWNER))) - Allow = false; - else if (ci->botflags.HasFlag(BS_DONTKICKVOICES) && c->HasUserStatus(u, CMODE_VOICE)) - Allow = false; - - if (Allow) - { - Anope::string realbuf = msg; - - /* If it's a /me, cut the CTCP part because the ACTION will cause - * problems with the caps or badwords kicker - */ - if (realbuf.substr(0, 8).equals_ci("\1ACTION ") && realbuf[realbuf.length() - 1] == '\1') - { - realbuf.erase(0, 8); - realbuf.erase(realbuf.length() - 1); - } - - if (realbuf.empty()) - return; - - /* Bolds kicker */ - if (ci->botflags.HasFlag(BS_KICK_BOLDS) && realbuf.find(2) != Anope::string::npos) - { - check_ban(ci, u, TTB_BOLDS); - bot_kick(ci, u, _("Don't use bolds on this channel!")); - return; - } - - /* Color kicker */ - if (ci->botflags.HasFlag(BS_KICK_COLORS) && realbuf.find(3) != Anope::string::npos) - { - check_ban(ci, u, TTB_COLORS); - bot_kick(ci, u, _("Don't use colors on this channel!")); - return; - } - - /* Reverses kicker */ - if (ci->botflags.HasFlag(BS_KICK_REVERSES) && realbuf.find(22) != Anope::string::npos) - { - check_ban(ci, u, TTB_REVERSES); - bot_kick(ci, u, _("Don't use reverses on this channel!")); - return; - } - - /* Italics kicker */ - if (ci->botflags.HasFlag(BS_KICK_ITALICS) && realbuf.find(29) != Anope::string::npos) - { - check_ban(ci, u, TTB_ITALICS); - bot_kick(ci, u, _("Don't use italics on this channel!")); - return; - } - - /* Underlines kicker */ - if (ci->botflags.HasFlag(BS_KICK_UNDERLINES) && realbuf.find(31) != Anope::string::npos) - { - check_ban(ci, u, TTB_UNDERLINES); - bot_kick(ci, u, _("Don't use underlines on this channel!")); - return; - } - - /* Caps kicker */ - if (ci->botflags.HasFlag(BS_KICK_CAPS) && realbuf.length() >= ci->capsmin) - { - int i = 0, l = 0; - - for (unsigned j = 0, end = realbuf.length(); j < end; ++j) - { - if (isupper(realbuf[j])) - ++i; - else if (islower(realbuf[j])) - ++l; - } - - /* i counts uppercase chars, l counts lowercase chars. Only - * alphabetic chars (so islower || isupper) qualify for the - * percentage of caps to kick for; the rest is ignored. -GD - */ - - if ((i || l) && i >= ci->capsmin && i * 100 / (i + l) >= ci->capspercent) - { - check_ban(ci, u, TTB_CAPS); - bot_kick(ci, u, _("Turn caps lock OFF!")); - return; - } - } - - /* Bad words kicker */ - if (ci->botflags.HasFlag(BS_KICK_BADWORDS)) - { - bool mustkick = false; - - /* Normalize the buffer */ - Anope::string nbuf = normalizeBuffer(realbuf); - - for (unsigned i = 0, end = ci->GetBadWordCount(); i < end; ++i) - { - BadWord *bw = ci->GetBadWord(i); - - if (bw->type == BW_ANY && ((Config->BSCaseSensitive && nbuf.find(bw->word) != Anope::string::npos) || (!Config->BSCaseSensitive && nbuf.find_ci(bw->word) != Anope::string::npos))) - mustkick = true; - else if (bw->type == BW_SINGLE) - { - size_t len = bw->word.length(); - - if ((Config->BSCaseSensitive && bw->word.equals_cs(nbuf)) || (!Config->BSCaseSensitive && bw->word.equals_ci(nbuf))) - mustkick = true; - else if (nbuf.find(' ') == len && ((Config->BSCaseSensitive && bw->word.equals_cs(nbuf)) || (!Config->BSCaseSensitive && bw->word.equals_ci(nbuf)))) - mustkick = true; - else - { - if (nbuf.rfind(' ') == nbuf.length() - len - 1 && ((Config->BSCaseSensitive && nbuf.find(bw->word) == nbuf.length() - len) || (!Config->BSCaseSensitive && nbuf.find_ci(bw->word) == nbuf.length() - len))) - mustkick = true; - else - { - Anope::string wordbuf = " " + bw->word + " "; - - if ((Config->BSCaseSensitive && nbuf.find(wordbuf) != Anope::string::npos) || (!Config->BSCaseSensitive && nbuf.find_ci(wordbuf) != Anope::string::npos)) - mustkick = true; - } - } - } - else if (bw->type == BW_START) - { - size_t len = bw->word.length(); - - if ((Config->BSCaseSensitive && nbuf.substr(0, len).equals_cs(bw->word)) || (!Config->BSCaseSensitive && nbuf.substr(0, len).equals_ci(bw->word))) - mustkick = true; - else - { - Anope::string wordbuf = " " + bw->word; - - if ((Config->BSCaseSensitive && nbuf.find(wordbuf) != Anope::string::npos) || (!Config->BSCaseSensitive && nbuf.find_ci(wordbuf) != Anope::string::npos)) - mustkick = true; - } - } - else if (bw->type == BW_END) - { - size_t len = bw->word.length(); - - if ((Config->BSCaseSensitive && nbuf.substr(nbuf.length() - len).equals_cs(bw->word)) || (!Config->BSCaseSensitive && nbuf.substr(nbuf.length() - len).equals_ci(bw->word))) - mustkick = true; - else - { - Anope::string wordbuf = bw->word + " "; - - if ((Config->BSCaseSensitive && nbuf.find(wordbuf) != Anope::string::npos) || (!Config->BSCaseSensitive && nbuf.find_ci(wordbuf) != Anope::string::npos)) - mustkick = true; - } - } - - if (mustkick) - { - check_ban(ci, u, TTB_BADWORDS); - if (Config->BSGentleBWReason) - bot_kick(ci, u, _("Watch your language!")); - else - bot_kick(ci, u, _("Don't use the word \"%s\" on this channel!"), bw->word.c_str()); - - return; - } - } - - UserData *ud = NULL; - - /* Flood kicker */ - if (ci->botflags.HasFlag(BS_KICK_FLOOD)) - { - ud = GetUserData(u, c); - if (ud) - { - if (Anope::CurTime - ud->last_start > ci->floodsecs) - { - ud->last_start = Anope::CurTime; - ud->lines = 0; - } - - ++ud->lines; - if (ud->lines >= ci->floodlines) - { - check_ban(ci, u, TTB_FLOOD); - bot_kick(ci, u, _("Stop flooding!")); - return; - } - } - } - - /* Repeat kicker */ - if (ci->botflags.HasFlag(BS_KICK_REPEAT)) - { - if (!ud) - ud = GetUserData(u, c); - if (ud) - { - - if (!ud->lastline.empty() && !ud->lastline.equals_ci(realbuf)) - { - ud->lastline = realbuf; - ud->times = 0; - } - else - { - if (ud->lastline.empty()) - ud->lastline = realbuf; - ++ud->times; - } - - if (ud->times >= ci->repeattimes) - { - check_ban(ci, u, TTB_REPEAT); - bot_kick(ci, u, _("Stop repeating yourself!")); - return; - } - } - } - - if (ud && ud->lastline.equals_ci(realbuf) && !ud->lasttarget.empty() && !ud->lasttarget.equals_ci(ci->name)) - { - for (UChannelList::iterator it = u->chans.begin(); it != u->chans.end();) - { - Channel *chan = (*it)->chan; - ++it; - - if (chan->ci != NULL && chan->ci->botflags.HasFlag(BS_KICK_AMSGS) && !chan->ci->HasPriv(u, CA_NOKICK)) - { - check_ban(chan->ci, u, TTB_AMSGS); - bot_kick(chan->ci, u, _("Don't use AMSGs!")); - } - } - } - - if (ud) - ud->lasttarget = ci->name; - } - } - } -}; - -MODULE_INIT(BSKick) diff --git a/modules/core/bs_main.cpp b/modules/core/bs_main.cpp deleted file mode 100644 index 69eab6040..000000000 --- a/modules/core/bs_main.cpp +++ /dev/null @@ -1,204 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class BotServCore : public Module -{ - Channel *fantasy_channel; - public: - BotServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), fantasy_channel(NULL) - { - this->SetAuthor("Anope"); - - BotInfo *BotServ = findbot(Config->BotServ); - if (BotServ == NULL) - throw ModuleException("No bot named " + Config->BotServ); - - Implementation i[] = { I_OnPrivmsg, I_OnPreCommand, I_OnJoinChannel, I_OnLeaveChannel, - I_OnPreHelp, I_OnPostHelp, I_OnChannelModeSet }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - } - - void OnPrivmsg(User *u, Channel *c, Anope::string &msg) - { - if (!u || !c || !c->ci || !c->ci->bi || msg.empty()) - return; - - /* Answer to ping if needed */ - if (msg.substr(0, 6).equals_ci("\1PING ") && msg[msg.length() - 1] == '\1') - { - Anope::string ctcp = msg; - ctcp.erase(ctcp.begin()); - ctcp.erase(ctcp.length() - 1); - ircdproto->SendCTCP(c->ci->bi, u->nick, "%s", ctcp.c_str()); - } - - - Anope::string realbuf = msg; - - bool was_action = false; - if (realbuf.substr(0, 8).equals_ci("\1ACTION ") && realbuf[realbuf.length() - 1] == '\1') - { - realbuf.erase(0, 8); - realbuf.erase(realbuf.length() - 1); - was_action = true; - } - - if (realbuf.empty()) - return; - - /* Fantaisist commands */ - if (c->ci->botflags.HasFlag(BS_FANTASY) && realbuf[0] == Config->BSFantasyCharacter[0] && !was_action) - { - /* Strip off the fantasy character */ - realbuf.erase(realbuf.begin()); - - size_t space = realbuf.find(' '); - Anope::string command, rest; - if (space == Anope::string::npos) - command = realbuf; - else - { - command = realbuf.substr(0, space); - rest = realbuf.substr(space + 1); - } - - BotInfo *bi = findbot(Config->ChanServ); - if (bi == NULL) - bi = findbot(Config->BotServ); - if (bi == NULL || !bi->commands.count(command)) - return; - - if (c->ci->HasPriv(u, CA_FANTASIA)) - { - - this->fantasy_channel = c; - bi->OnMessage(u, realbuf); - this->fantasy_channel = NULL; - - FOREACH_MOD(I_OnBotFantasy, OnBotFantasy(command, u, c->ci, rest)); - } - else - { - FOREACH_MOD(I_OnBotNoFantasyAccess, OnBotNoFantasyAccess(command, u, c->ci, rest)); - } - } - } - - EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector<Anope::string> ¶ms) - { - if (this->fantasy_channel != NULL) - { - if (!command->HasFlag(CFLAG_STRIP_CHANNEL)) - params.insert(params.begin(), this->fantasy_channel->name); - source.c = this->fantasy_channel; - } - - return EVENT_CONTINUE; - } - - void OnJoinChannel(User *user, Channel *c) - { - if (c->ci && c->ci->bi) - { - /** - * We let the bot join even if it was an ignored user, as if we don't, - * and the ignored user doesnt just leave, the bot will never - * make it into the channel, leaving the channel botless even for - * legit users - Rob - **/ - if (c->users.size() >= Config->BSMinUsers && !c->FindUser(c->ci->bi)) - c->ci->bi->Join(c, &Config->BotModeList); - /* Only display the greet if the main uplink we're connected - * to has synced, or we'll get greet-floods when the net - * recovers from a netsplit. -GD - */ - if (c->FindUser(c->ci->bi) && c->ci->botflags.HasFlag(BS_GREET) && user->Account() && !user->Account()->greet.empty() && c->ci->HasPriv(user, CA_GREET) && user->server->IsSynced()) - { - ircdproto->SendPrivmsg(c->ci->bi, c->name, "[%s] %s", user->Account()->display.c_str(), user->Account()->greet.c_str()); - c->ci->bi->lastmsg = Anope::CurTime; - } - } - } - - void OnLeaveChannel(User *u, Channel *c) - { - /* Channel is persistant, it shouldn't be deleted and the service bot should stay */ - if (c->HasFlag(CH_PERSIST) || (c->ci && c->ci->HasFlag(CI_PERSIST))) - return; - - /* Channel is syncing from a netburst, don't destroy it as more users are probably wanting to join immediatly - * We also don't part the bot here either, if necessary we will part it after the sync - */ - if (c->HasFlag(CH_SYNCING)) - return; - - /* Additionally, do not delete this channel if ChanServ/a BotServ bot is inhabiting it */ - if (c->HasFlag(CH_INHABIT)) - return; - - if (c->ci && c->ci->bi && c->users.size() - 1 <= Config->BSMinUsers && c->FindUser(c->ci->bi)) - { - bool persist = c->HasFlag(CH_PERSIST); - c->SetFlag(CH_PERSIST); - c->ci->bi->Part(c->ci->c); - if (!persist) - c->UnsetFlag(CH_PERSIST); - } - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->BotServ) - return; - source.Reply(_("\002%s\002 allows you to have a bot on your own channel.\n" - "It has been created for users that can't host or\n" - "configure a bot, or for use on networks that don't\n" - "allow user bots. Available commands are listed \n" - "below; to use them, type \002%s%s \037command\037\002. For\n" - "more information on a specific command, type\n" - "\002%s%s %s \037command\037\002.\n "), - Config->BotServ.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->BotServ.c_str(), - Config->UseStrictPrivMsgString.c_str(), Config->BotServ.c_str(), source.command.c_str()); - } - - void OnPostHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->BotServ) - return; - source.Reply(_(" \n" - "Bot will join a channel whenever there is at least\n" - "\002%d\002 user(s) on it. Additionally, all %s commands\n" - "can be used if fantasy is enabled by prefixing the command\n" - "name with a %c."), Config->BSMinUsers, Config->ChanServ.c_str(), Config->BSFantasyCharacter[0]); - } - - EventReturn OnChannelModeSet(Channel *c, ChannelModeName Name, const Anope::string ¶m) - { - if (Config->BSSmartJoin && Name == CMODE_BAN && c->ci && c->ci->bi && c->FindUser(c->ci->bi)) - { - BotInfo *bi = c->ci->bi; - - Entry ban(CMODE_BAN, param); - if (ban.Matches(bi)) - c->RemoveMode(bi, CMODE_BAN, param); - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(BotServCore) - diff --git a/modules/core/bs_set.cpp b/modules/core/bs_set.cpp deleted file mode 100644 index ccd1bb615..000000000 --- a/modules/core/bs_set.cpp +++ /dev/null @@ -1,307 +0,0 @@ -/* BotServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandBSSet : public Command -{ - public: - CommandBSSet(Module *creator) : Command(creator, "botserv/set", 3, 3) - { - this->SetDesc(_("Configures bot options")); - this->SetSyntax(_("\037(channel | bot)\037 \037option\037 \037settings\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &option = params[1]; - const Anope::string &value = params[2]; - - User *u = source.u; - ChannelInfo *ci; - - if (readonly) - source.Reply(_("Sorry, bot option setting is temporarily disabled.")); - else if (u->HasCommand("botserv/botserv/set/private") && option.equals_ci("PRIVATE")) - { - BotInfo *bi; - - if (!(bi = findbot(chan))) - { - source.Reply(BOT_DOES_NOT_EXIST, chan.c_str()); - return; - } - - if (value.equals_ci("ON")) - { - bi->SetFlag(BI_PRIVATE); - source.Reply(_("Private mode of bot %s is now \002on\002."), bi->nick.c_str()); - } - else if (value.equals_ci("OFF")) - { - bi->UnsetFlag(BI_PRIVATE); - source.Reply(_("Private mode of bot %s is now \002off\002."), bi->nick.c_str()); - } - else - this->OnSyntaxError(source, "PRIVATE"); - return; - } - else if (!(ci = cs_findchan(chan))) - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - else if (!u->HasPriv("botserv/administration") && !ci->HasPriv(u, CA_SET)) - source.Reply(ACCESS_DENIED); - else - { - bool override = !ci->HasPriv(u, CA_SET); - Log(override ? LOG_ADMIN : LOG_COMMAND, u, this, ci) << option << " " << value; - - if (option.equals_ci("DONTKICKOPS")) - { - if (value.equals_ci("ON")) - { - ci->botflags.SetFlag(BS_DONTKICKOPS); - source.Reply(_("Bot \002won't kick ops\002 on channel %s."), ci->name.c_str()); - } - else if (value.equals_ci("OFF")) - { - ci->botflags.UnsetFlag(BS_DONTKICKOPS); - source.Reply(_("Bot \002will kick ops\002 on channel %s."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "DONTKICKOPS"); - } - else if (option.equals_ci("DONTKICKVOICES")) - { - if (value.equals_ci("ON")) - { - ci->botflags.SetFlag(BS_DONTKICKVOICES); - source.Reply(_("Bot \002won't kick voices\002 on channel %s."), ci->name.c_str()); - } - else if (value.equals_ci("OFF")) - { - ci->botflags.UnsetFlag(BS_DONTKICKVOICES); - source.Reply(_("Bot \002will kick voices\002 on channel %s."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "DONTKICKVOICE"); - } - else if (option.equals_ci("FANTASY")) - { - if (value.equals_ci("ON")) - { - ci->botflags.SetFlag(BS_FANTASY); - source.Reply(_("Fantasy mode is now \002on\002 on channel %s."), ci->name.c_str()); - } - else if (value.equals_ci("OFF")) - { - ci->botflags.UnsetFlag(BS_FANTASY); - source.Reply(_("Fantasy mode is now \002off\002 on channel %s."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "FANTASY"); - } - else if (option.equals_ci("GREET")) - { - if (value.equals_ci("ON")) - { - ci->botflags.SetFlag(BS_GREET); - source.Reply(_("Greet mode is now \002on\002 on channel %s."), ci->name.c_str()); - } - else if (value.equals_ci("OFF")) - { - ci->botflags.UnsetFlag(BS_GREET); - source.Reply(_("Greet mode is now \002off\002 on channel %s."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "GREET"); - } - else if (u->HasCommand("botserv/botserv/set/nobot") && option.equals_ci("NOBOT")) - { - if (value.equals_ci("ON")) - { - ci->botflags.SetFlag(BS_NOBOT); - if (ci->bi) - ci->bi->UnAssign(u, ci); - source.Reply(_("No Bot mode is now \002on\002 on channel %s."), ci->name.c_str()); - } - else if (value.equals_ci("OFF")) - { - ci->botflags.UnsetFlag(BS_NOBOT); - source.Reply(_("No Bot mode is now \002off\002 on channel %s."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "NOBOT"); - } - else if (option.equals_ci("MSG")) - { - if (value.equals_ci("OFF")) - { - ci->botflags.UnsetFlag(BS_MSG_PRIVMSG); - ci->botflags.UnsetFlag(BS_MSG_NOTICE); - ci->botflags.UnsetFlag(BS_MSG_NOTICEOPS); - source.Reply(_("Fantasy replies will no longer be sent to %s."), ci->name.c_str()); - } - else if (value.equals_ci("PRIVMSG")) - { - ci->botflags.SetFlag(BS_MSG_PRIVMSG); - ci->botflags.UnsetFlag(BS_MSG_NOTICE); - ci->botflags.UnsetFlag(BS_MSG_NOTICEOPS); - source.Reply(_("Fantasy replies will be sent via PRIVMSG to %s."), ci->name.c_str()); - } - else if (value.equals_ci("NOTICE")) - { - ci->botflags.UnsetFlag(BS_MSG_PRIVMSG); - ci->botflags.SetFlag(BS_MSG_NOTICE); - ci->botflags.UnsetFlag(BS_MSG_NOTICEOPS); - source.Reply(_("Fantasy replies will be sent via NOTICE to %s."), ci->name.c_str()); - } - else if (value.equals_ci("NOTICEOPS")) - { - ci->botflags.UnsetFlag(BS_MSG_PRIVMSG); - ci->botflags.UnsetFlag(BS_MSG_NOTICE); - ci->botflags.SetFlag(BS_MSG_NOTICEOPS); - source.Reply(_("Fantasy replies will be sent via NOTICE to channel ops on %s."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "MSG"); - } - else - source.Reply(UNKNOWN_OPTION, option.c_str(), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), this->name.c_str()); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - if (subcommand.empty()) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Configures bot options. \037option\037 can be one of:\n" - " \n" - " DONTKICKOPS To protect ops against bot kicks\n" - " DONTKICKVOICES To protect voices against bot kicks\n" - " GREET Enable greet messages\n" - " FANTASY Enable fantaisist commands\n" - " MSG Configure how fantasy commands should be replied to\n" - " \n" - "Type \002%s%s HELP SET \037option\037\002 for more information\n" - "on a specific option.\n" - "Note: access to this command is controlled by the\n" - "level SET."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - User *u = source.u; - if (u->IsServicesOper()) - source.Reply(_("These options are reserved to Services Operators:\n" - " \n" - " NOBOT Prevent a bot from being assigned to \n" - " a channel\n" - " PRIVATE Prevent a bot from being assigned by\n" - " non IRC operators")); - } - else if (subcommand.equals_ci("DONTKICKOPS")) - source.Reply(_("Syntax: \002SET \037channel\037 DONTKICKOPS {\037ON|OFF\037}\n" - " \n" - "Enables or disables \002ops protection\002 mode on a channel.\n" - "When it is enabled, ops won't be kicked by the bot\n" - "even if they don't match the NOKICK level.")); - else if (subcommand.equals_ci("DONTKICKVOICES")) - source.Reply(_("Syntax: \002SET \037channel\037 DONTKICKVOICES {\037ON|OFF\037}\n" - " \n" - "Enables or disables \002voices protection\002 mode on a channel.\n" - "When it is enabled, voices won't be kicked by the bot\n" - "even if they don't match the NOKICK level.")); - else if (subcommand.equals_ci("FANTASY")) - source.Reply(_("Syntax: \002SET \037channel\037 FANTASY {\037ON|OFF\037}\n" - "Enables or disables \002fantasy\002 mode on a channel.\n" - "When it is enabled, users will be able to use\n" - "commands !op, !deop, !voice, !devoice,\n" - "!kick, !kb, !unban, !seen on a channel (find how \n" - "to use them; try with or without nick for each, \n" - "and with a reason for some?).\n" - " \n" - "Note that users wanting to use fantaisist\n" - "commands MUST have enough level for both\n" - "the FANTASIA and another level depending\n" - "of the command if required (for example, to use \n" - "!op, user must have enough access for the OPDEOP\n" - "level).")); - else if (subcommand.equals_ci("GREET")) - source.Reply(_("Syntax: \002SET \037channel\037 GREET {\037ON|OFF\037}\n" - " \n" - "Enables or disables \002greet\002 mode on a channel.\n" - "When it is enabled, the bot will display greet\n" - "messages of users joining the channel, provided\n" - "they have enough access to the channel.")); - else if (subcommand.equals_ci("NOBOT")) - source.Reply(_("Syntax: \002SET \037channel\037 NOBOT {\037ON|OFF\037}\002\n" - " \n" - "This option makes a channel be unassignable. If a bot \n" - "is already assigned to the channel, it is unassigned\n" - "automatically when you enable the option.")); - else if (subcommand.equals_ci("PRIVATE")) - source.Reply(_("Syntax: \002SET \037bot-nick\037 PRIVATE {\037ON|OFF\037}\002\n" - "This option prevents a bot from being assigned to a\n" - "channel by users that aren't IRC operators.")); - else if (subcommand.equals_ci("MSG")) - source.Reply(_("Syntax: \002SET \037channel\037 MSG {\037OFF|PRIVMSG|NOTICE|NOTICEOPS\037}\002\n" - " \n" - "Configures how fantasy commands should be returned to the channel. Off disables\n" - "fantasy from replying to the channel. Privmsg, notice, and noticeops message the\n" - "channel, notice the channel, and notice the channel ops respectively.\n" - " \n" - "Note that replies over one line will not use this setting to prevent spam, and will\n" - "go directly to the user who executed it.")); - else - return false; - - return true; - } - - void OnSyntaxError(CommandSource &source, const Anope::string &subcommand) - { - if (subcommand.empty()) - Command::OnSyntaxError(source, ""); - else if (subcommand.equals_ci("PRIVATE")) - this->SendSyntax(source, "\037botname\037 PRIVATE {\037ON|OFF\037}"); - else if (subcommand.equals_ci("DONTKICKOPS")) - this->SendSyntax(source, "\037channel\037 DONTKICKOPS {\037ON|OFF\037}"); - else if (subcommand.equals_ci("DONTKICKVOICES")) - this->SendSyntax(source, "\037channel\037 DONTKICKVOICES {\037ON|OFF\037}"); - else if (subcommand.equals_ci("FANTASY")) - this->SendSyntax(source, "\037channel\037 FANTASY {\037ON|OFF\037}"); - else if (subcommand.equals_ci("GREET")) - this->SendSyntax(source, "\037channel\037 GREET {\037ON|OFF\037}"); - else if (subcommand.equals_ci("MSG")) - this->SendSyntax(source, "\037botname\037 NOBOT {\037ON|OFF\037}"); - else if (subcommand.equals_ci("NOBOT")) - this->SendSyntax(source, "\037botname\037 NOBOT {\037ON|OFF\037}"); - } -}; - -class BSSet : public Module -{ - CommandBSSet commandbsset; - - public: - BSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandbsset(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandbsset); - } -}; - -MODULE_INIT(BSSet) diff --git a/modules/core/cs_access.cpp b/modules/core/cs_access.cpp deleted file mode 100644 index 777b0c176..000000000 --- a/modules/core/cs_access.cpp +++ /dev/null @@ -1,915 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -enum -{ - ACCESS_INVALID = -10000, - ACCESS_FOUNDER = 10001 -}; - -static struct AccessLevels -{ - ChannelAccess priv; - int default_level; - Anope::string config_name; - Anope::string name; - Anope::string desc; -} defaultLevels[] = { - { CA_ACCESS_CHANGE, 10, "level_change", "ACC-CHANGE", _("Allowed to modify the access list") }, - { CA_ACCESS_LIST, 1, "level_list", "ACC-LIST", _("Allowed to view the access list") }, - { CA_AKICK, 10, "level_akick", "AKICK", _("Allowed to use AKICK command") }, - { CA_ASSIGN, ACCESS_FOUNDER, "level_assign", "ASSIGN", _("Allowed to assign/unassign a bot") }, - { CA_AUTOHALFOP, 4, "level_autohalfop", "AUTOHALFOP", _("Automatic mode +h") }, - { CA_AUTOOP, 5, "level_autoop", "AUTOOP", _("Automatic channel operator status") }, - { CA_AUTOOWNER, 10000, "level_autoowner", "AUTOOWNER", _("Automatic mode +q") }, - { CA_AUTOPROTECT, 10, "level_autoprotect", "AUTOPROTECT", _("Automatic mode +a") }, - { CA_AUTOVOICE, 3, "level_autovoice", "AUTOVOICE", _("Automatic mode +v") }, - { CA_BADWORDS, 10, "level_badwords", "BADWORDS", _("Allowed to modify channel badwords list") }, - { CA_BAN, 4, "level_ban", "BAN", _("Allowed to use ban users") }, - { CA_FANTASIA, 3, "level_fantasia", "FANTASIA", _("Allowed to use fantaisist commands") }, - { CA_FOUNDER, ACCESS_FOUNDER, "level_founder", "FOUNDER", _("Allowed to issue commands restricted to channel founders") }, - { CA_GETKEY, 5, "level_getkey", "GETKEY", _("Allowed to use GETKEY command") }, - { CA_GREET, 5, "level_greet", "GREET", _("Greet message displayed") }, - { CA_HALFOP, 5, "level_halfop", "HALFOP", _("Allowed to (de)halfop users") }, - { CA_HALFOPME, 4, "level_halfopme", "HALFOPME", _("Allowed to (de)halfop him/herself") }, - { CA_INFO, 10000, "level_info", "INFO", _("Allowed to use INFO command with ALL option") }, - { CA_INVITE, 5, "level_invite", "INVITE", _("Allowed to use the INVITE command") }, - { CA_KICK, 4, "level_kick", "KICK", _("Allowed to use the KICK command") }, - { CA_MEMO, 10, "level_memo", "MEMO", _("Allowed to read channel memos") }, - { CA_MODE, 5, "level_mode", "MODE", _("Allowed to change channel modes") }, - { CA_NOKICK, 1, "level_nokick", "NOKICK", _("Never kicked by the bot's kickers") }, - { CA_OPDEOP, 5, "level_opdeop", "OPDEOP", _("Allowed to (de)op users") }, - { CA_OPDEOPME, 5, "level_opdeopme", "OPDEOPME", _("Allowed to (de)op him/herself") }, - { CA_OWNER, ACCESS_FOUNDER, "level_owner", "OWNER", _("Allowed to use (de)owner users") }, - { CA_OWNERME, 10000, "level_ownerme", "OWNERME", _("Allowed to (de)owner him/herself") }, - { CA_PROTECT, 10000, "level_protect", "PROTECT", _("Allowed to (de)protect users") }, - { CA_PROTECTME, 10, "level_protectme", "PROTECTME", _("Allowed to (de)protect him/herself"), }, - { CA_SAY, 5, "level_say", "SAY", _("Allowed to use SAY and ACT commands") }, - { CA_SIGNKICK, ACCESS_FOUNDER, "level_signkick", "SIGNKICK", _("No signed kick when SIGNKICK LEVEL is used") }, - { CA_SET, 10000, "level_set", "SET", _("Allowed to set channel settings") }, - { CA_TOPIC, 5, "level_topic", "TOPIC", _("Allowed to change channel topics") }, - { CA_UNBAN, 4, "level_unban", "UNBAN", _("Allowed to unban users") }, - { CA_VOICE, 4, "level_voice", "VOICE", _("Allowed to (de)voice users") }, - { CA_VOICEME, 3, "level_voiceme", "VOICEME", _("Allowed to (de)voice him/herself") }, - { CA_SIZE, -1, "", "", "" } -}; - -static void reset_levels(ChannelInfo *ci) -{ - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - ci->levels[defaultLevels[i].priv] = defaultLevels[i].default_level; -} - -class AccessChanAccess : public ChanAccess -{ - public: - int level; - - AccessChanAccess(AccessProvider *p) : ChanAccess(p) - { - } - - bool Matches(User *u, NickCore *nc) - { - if (u && (Anope::Match(u->nick, this->mask) || Anope::Match(u->GetMask(), this->mask))) - return true; - else if (nc && Anope::Match(nc->display, this->mask)) - return true; - return false; - } - - bool HasPriv(ChannelAccess priv) - { - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - if (defaultLevels[i].priv == priv) - return DetermineLevel(this) >= this->ci->levels[priv]; - return false; - } - - Anope::string Serialize() - { - return stringify(this->level); - } - - void Unserialize(const Anope::string &data) - { - this->level = convertTo<int>(data); - } - - static int DetermineLevel(ChanAccess *access) - { - if (access->provider->name == "access/access") - { - AccessChanAccess *aaccess = debug_cast<AccessChanAccess *>(access); - return aaccess->level; - } - else - { - int highest = 1; - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - if (access->ci->levels[defaultLevels[i].priv] > highest && access->HasPriv(defaultLevels[i].priv)) - highest = access->ci->levels[defaultLevels[i].priv]; - return highest; - } - } -}; - -class AccessAccessProvider : public AccessProvider -{ - public: - AccessAccessProvider(Module *o) : AccessProvider(o, "access/access") - { - } - - ChanAccess *Create() - { - return new AccessChanAccess(this); - } -}; - -class AccessListCallback : public NumberList -{ - protected: - CommandSource &source; - ChannelInfo *ci; - bool SentHeader; - public: - AccessListCallback(CommandSource &_source, ChannelInfo *_ci, const Anope::string &numlist) : NumberList(numlist, false), source(_source), ci(_ci), SentHeader(false) - { - } - - ~AccessListCallback() - { - if (SentHeader) - source.Reply(_("End of access list.")); - else - source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); - } - - virtual void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAccessCount()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(CHAN_ACCESS_LIST_HEADER, ci->name.c_str()); - } - - DoList(source, ci, Number - 1, ci->GetAccess(Number - 1)); - } - - static void DoList(CommandSource &source, ChannelInfo *ci, unsigned Number, ChanAccess *access) - { - source.Reply(_(" %3d %4d %s"), Number + 1, AccessChanAccess::DetermineLevel(access), access->mask.c_str()); - } -}; - -class AccessViewCallback : public AccessListCallback -{ - public: - AccessViewCallback(CommandSource &_source, ChannelInfo *_ci, const Anope::string &numlist) : AccessListCallback(_source, _ci, numlist) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAccessCount()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(CHAN_ACCESS_LIST_HEADER, ci->name.c_str()); - } - - DoList(source, ci, Number - 1, ci->GetAccess(Number - 1)); - } - - static void DoList(CommandSource &source, ChannelInfo *ci, unsigned Number, ChanAccess *access) - { - Anope::string timebuf; - if (ci->c) - for (CUserList::const_iterator cit = ci->c->users.begin(), cit_end = ci->c->users.end(); cit != cit_end; ++cit) - if (access->Matches((*cit)->user, (*cit)->user->Account())) - timebuf = "Now"; - if (timebuf.empty()) - { - if (access->last_seen == 0) - timebuf = "Never"; - else - timebuf = do_strftime(access->last_seen); - } - - source.Reply(CHAN_ACCESS_VIEW_AXS_FORMAT, Number + 1, AccessChanAccess::DetermineLevel(access), access->mask.c_str(), access->creator.c_str(), timebuf.c_str()); - } -}; - -class AccessDelCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - Command *c; - unsigned Deleted; - Anope::string Nicks; - bool Denied; - bool override; - public: - AccessDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, const Anope::string &numlist) : NumberList(numlist, true), source(_source), ci(_ci), c(_c), Deleted(0), Denied(false) - { - if (!ci->HasPriv(source.u, CA_ACCESS_CHANGE) && source.u->HasPriv("chanserv/access/modify")) - this->override = true; - } - - ~AccessDelCallback() - { - if (Denied && !Deleted) - source.Reply(ACCESS_DENIED); - else if (!Deleted) - source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); - else - { - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, c, ci) << "for user" << (Deleted == 1 ? " " : "s ") << Nicks; - - if (Deleted == 1) - source.Reply(_("Deleted 1 entry from %s access list."), ci->name.c_str()); - else - source.Reply(_("Deleted %d entries from %s access list."), Deleted, ci->name.c_str()); - } - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAccessCount()) - return; - - User *u = source.u; - - ChanAccess *access = ci->GetAccess(Number - 1); - - AccessGroup u_access = ci->AccessFor(u); - ChanAccess *u_highest = u_access.Highest(); - - if (u_highest ? AccessChanAccess::DetermineLevel(u_highest) : 0 <= AccessChanAccess::DetermineLevel(access) && !u->HasPriv("chanserv/access/modify")) - { - Denied = true; - return; - } - - ++Deleted; - if (!Nicks.empty()) - Nicks += ", " + access->mask; - else - Nicks = access->mask; - - FOREACH_MOD(I_OnAccessDel, OnAccessDel(ci, u, access)); - - ci->EraseAccess(Number - 1); - } -}; - -class CommandCSAccess : public Command -{ - void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string mask = params[2]; - int level = ACCESS_INVALID; - - try - { - level = convertTo<int>(params[3]); - } - catch (const ConvertException &) { } - - if (!level) - { - source.Reply(_("Access level must be non-zero.")); - return; - } - - AccessGroup u_access = ci->AccessFor(u); - ChanAccess *highest = u_access.Highest(); - int u_level = (highest ? AccessChanAccess::DetermineLevel(highest) : 0); - if (!ci->HasPriv(u, CA_FOUNDER) && level >= u_level && !u->HasPriv("chanserv/access/modify")) - { - source.Reply(ACCESS_DENIED); - return; - } - else if (level <= ACCESS_INVALID || level >= ACCESS_FOUNDER) - { - source.Reply(CHAN_ACCESS_LEVEL_RANGE, ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); - return; - } - - bool override = !ci->HasPriv(u, CA_ACCESS_CHANGE) || level >= u_level; - - for (unsigned i = ci->GetAccessCount(); i > 0; --i) - { - ChanAccess *access = ci->GetAccess(i - 1); - if (mask.equals_ci(access->mask)) - { - /* Don't allow lowering from a level >= u_level */ - if (AccessChanAccess::DetermineLevel(access) >= u_level && !u->HasPriv("chanserv/access/modify")) - { - source.Reply(ACCESS_DENIED); - return; - } - ci->EraseAccess(i - 1); - break; - } - } - - if (ci->GetAccessCount() >= Config->CSAccessMax) - { - source.Reply(_("Sorry, you can only have %d access entries on a channel."), Config->CSAccessMax); - return; - } - - if (mask.find_first_of("!*@") == Anope::string::npos && findnick(mask) == NULL) - mask += "!*@*"; - - service_reference<AccessProvider> provider("access/access"); - if (!provider) - return; - AccessChanAccess *access = debug_cast<AccessChanAccess *>(provider->Create()); - access->ci = ci; - access->mask = mask; - access->creator = u->nick; - access->level = level; - access->last_seen = 0; - access->created = Anope::CurTime; - ci->AddAccess(access); - - FOREACH_MOD(I_OnAccessAdd, OnAccessAdd(ci, u, access)); - - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "ADD " << mask << " (level: " << level << ") as level " << u_level; - source.Reply(_("\002%s\002 added to %s access list at level \002%d\002."), access->mask.c_str(), ci->name.c_str(), level); - - return; - } - - void DoDel(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &mask = params[2]; - - if (!ci->GetAccessCount()) - source.Reply(_("%s access list is empty."), ci->name.c_str()); - else if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AccessDelCallback list(source, ci, this, mask); - list.Process(); - } - else - { - AccessGroup u_access = ci->AccessFor(u); - ChanAccess *highest = u_access.Highest(); - int u_level = (highest ? AccessChanAccess::DetermineLevel(highest) : 0); - - for (unsigned i = ci->GetAccessCount(); i > 0; --i) - { - ChanAccess *access = ci->GetAccess(i - 1); - if (mask.equals_ci(access->mask)) - { - int access_level = AccessChanAccess::DetermineLevel(access); - if (!access->mask.equals_ci(u->Account()->display) && u_level <= access_level && !u->HasPriv("chanserv/access/modify")) - source.Reply(ACCESS_DENIED); - else - { - source.Reply(_("\002%s\002 deleted from %s access list."), access->mask.c_str(), ci->name.c_str()); - bool override = !ci->HasPriv(u, CA_ACCESS_CHANGE) && !access->mask.equals_ci(u->Account()->display); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "DEL " << access->mask; - - FOREACH_MOD(I_OnAccessDel, OnAccessDel(ci, u, access)); - ci->EraseAccess(access); - } - return; - } - } - - source.Reply(_("\002%s\002 not found on %s access list."), mask.c_str(), ci->name.c_str()); - } - - return; - } - - void DoList(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params.size() > 2 ? params[2] : ""; - - if (!ci->GetAccessCount()) - source.Reply(_("%s access list is empty."), ci->name.c_str()); - else if (!nick.empty() && nick.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AccessListCallback list(source, ci, nick); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) - { - ChanAccess *access = ci->GetAccess(i); - - if (!nick.empty() && !Anope::Match(access->mask, nick)) - continue; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(CHAN_ACCESS_LIST_HEADER, ci->name.c_str()); - } - - AccessListCallback::DoList(source, ci, i, access); - } - - if (SentHeader) - source.Reply(_("End of access list.")); - else - source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); - } - - return; - } - - void DoView(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params.size() > 2 ? params[2] : ""; - - if (!ci->GetAccessCount()) - source.Reply(_("%s access list is empty."), ci->name.c_str()); - else if (!nick.empty() && nick.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AccessViewCallback list(source, ci, nick); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) - { - ChanAccess *access = ci->GetAccess(i); - - if (!nick.empty() && !Anope::Match(access->mask, nick)) - continue; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(CHAN_ACCESS_LIST_HEADER, ci->name.c_str()); - } - - AccessViewCallback::DoList(source, ci, i, access); - } - - if (SentHeader) - source.Reply(_("End of access list.")); - else - source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); - } - - return; - } - - void DoClear(CommandSource &source, ChannelInfo *ci) - { - User *u = source.u; - - if (!IsFounder(u, ci) && !u->HasPriv("chanserv/access/modify")) - source.Reply(ACCESS_DENIED); - else - { - ci->ClearAccess(); - - FOREACH_MOD(I_OnAccessClear, OnAccessClear(ci, u)); - - source.Reply(_("Channel %s access list has been cleared."), ci->name.c_str()); - - bool override = !IsFounder(u, ci); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "CLEAR"; - } - - return; - } - - public: - CommandCSAccess(Module *creator) : Command(creator, "chanserv/access", 2, 4) - { - this->SetDesc(_("Modify the list of privileged users")); - this->SetSyntax(_("\037channel\037 ADD \037mask\037 \037level\037")); - this->SetSyntax(_("\037channel\037 DEL {\037mask\037 | \037entry-num\037 | \037list\037}")); - this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037list\037]")); - this->SetSyntax(_("\037channel\037 VIEW [\037mask\037 | \037list\037]")); - this->SetSyntax(_("\037channel\037 CLEAR\002")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[1]; - const Anope::string &nick = params.size() > 2 ? params[2] : ""; - const Anope::string &s = params.size() > 3 ? params[3] : ""; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - bool is_list = cmd.equals_ci("LIST") || cmd.equals_ci("VIEW"); - bool is_clear = cmd.equals_ci("CLEAR"); - bool is_del = cmd.equals_ci("DEL"); - - bool has_access = false; - if (u->HasPriv("chanserv/access/modify")) - has_access = true; - else if (is_list && ci->HasPriv(u, CA_ACCESS_LIST)) - has_access = true; - else if (ci->HasPriv(u, CA_ACCESS_CHANGE)) - has_access = true; - else if (is_del) - { - NickAlias *na = findnick(nick); - if (na && na->nc == u->Account()) - has_access = true; - } - - /* If LIST, we don't *require* any parameters, but we can take any. - * If DEL, we require a nick and no level. - * Else (ADD), we require a level (which implies a nick). */ - if (is_list || is_clear ? 0 : (cmd.equals_ci("DEL") ? (nick.empty() || !s.empty()) : s.empty())) - this->OnSyntaxError(source, cmd); - else if (!has_access) - source.Reply(ACCESS_DENIED); - else if (readonly && !is_list) - source.Reply(_("Sorry, channel access list modification is temporarily disabled.")); - else if (cmd.equals_ci("ADD")) - this->DoAdd(source, ci, params); - else if (cmd.equals_ci("DEL")) - this->DoDel(source, ci, params); - else if (cmd.equals_ci("LIST")) - this->DoList(source, ci, params); - else if (cmd.equals_ci("VIEW")) - this->DoView(source, ci, params); - else if (cmd.equals_ci("CLEAR")) - this->DoClear(source, ci); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002access list\002 for a channel. The access\n" - "list specifies which users are allowed chanop status or\n" - "access to %s commands on the channel. Different\n" - "user levels allow for access to different subsets of\n" - "privileges. Any nick not on the access list has\n" - "a user level of 0."), source.owner->nick.c_str()); - source.Reply(" "); - source.Reply(_("The \002ACCESS ADD\002 command adds the given mask to the\n" - "access list with the given user level; if the mask is\n" - "already present on the list, its access level is changed to\n" - "the level specified in the command. The \037level\037 specified\n" - "must be less than that of the user giving the command, and\n" - "if the \037mask\037 is already on the access list, the current\n" - "access level of that nick must be less than the access level\n" - "of the user giving the command. When a user joins the channel\n" - "the access they receive is from the highest level entry in the\n" - "access list.")); - source.Reply(" "); - source.Reply(_("The \002ACCESS DEL\002 command removes the given nick from the\n" - "access list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - "You may remove yourself from an access list, even if you\n" - "do not have access to modify that list otherwise.")); - source.Reply(" "); - source.Reply(_("The \002ACCESS LIST\002 command displays the access list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002ACCESS #channel LIST 2-5,7-9\002\n" - " Lists access entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002ACCESS VIEW\002 command displays the access list similar\n" - "to \002ACCESS LIST\002 but shows the creator and last used time.\n" - " \n" - "The \002ACCESS CLEAR\002 command clears all entries of the\n" - "access list.")); - source.Reply(_("\002User access levels\002\n" - " \n" - "By default, the following access levels are defined:\n" - " \n" - " \002Founder\002 Full access to %s functions; automatic\n" - " opping upon entering channel. Note\n" - " that only one person may have founder\n" - " status (it cannot be given using the\n" - " \002ACCESS\002 command).\n" - " \002 10\002 Access to AKICK command; automatic opping.\n" - " \002 5\002 Automatic opping.\n" - " \002 3\002 Automatic voicing.\n" - " \002 0\002 No special privileges; can be opped by other\n" - " ops (unless \002secure-ops\002 is set).\n" - " \002 <0\002 May not be opped.\n" - " \n" - "These levels may be changed, or new ones added, using the\n" - "\002LEVELS\002 command; type \002%s%s HELP LEVELS\002 for\n" - "information."), source.owner->nick.c_str(), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSLevels : public Command -{ - int levelinfo_maxwidth; - - void DoSet(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &what = params[2]; - const Anope::string &lev = params[3]; - - int level; - - if (lev.equals_ci("FOUNDER")) - level = ACCESS_FOUNDER; - else - { - try - { - level = convertTo<int>(lev); - } - catch (const ConvertException &) - { - this->OnSyntaxError(source, "SET"); - return; - } - } - - if (level <= ACCESS_INVALID || level > ACCESS_FOUNDER) - source.Reply(_("Level must be between %d and %d inclusive."), ACCESS_INVALID + 1, ACCESS_FOUNDER - 1); - else - { - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - - if (what.equals_ci(l.name)) - { - ci->levels[l.priv] = level; - FOREACH_MOD(I_OnLevelChange, OnLevelChange(u, ci, i, level)); - - bool override = !ci->HasPriv(u, CA_FOUNDER); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "SET " << l.name << " to " << level; - - if (level == ACCESS_FOUNDER) - source.Reply(_("Level for %s on channel %s changed to founder only."), l.name.c_str(), ci->name.c_str()); - else - source.Reply(_("Level for \002%s\002 on channel %s changed to \002%d\002."), l.name.c_str(), ci->name.c_str(), level); - return; - } - } - - source.Reply(_("Setting \002%s\002 not known. Type \002%s%s HELP LEVELS \002 for a list of valid settings."), what.c_str(), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - } - - return; - } - - void DoDisable(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &what = params[2]; - - /* Don't allow disabling of the founder level. It would be hard to change it back if you dont have access to use this command */ - if (!what.equals_ci("FOUNDER")) - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - - if (what.equals_ci(l.name)) - { - ci->levels[l.priv] = ACCESS_INVALID; - FOREACH_MOD(I_OnLevelChange, OnLevelChange(u, ci, i, l.priv)); - - bool override = !ci->HasPriv(u, CA_FOUNDER); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "DISABLE " << l.name; - - source.Reply(_("\002%s\002 disabled on channel %s."), l.name.c_str(), ci->name.c_str()); - return; - } - } - - source.Reply(_("Setting \002%s\002 not known. Type \002%s%s HELP LEVELS \002 for a list of valid settings."), what.c_str(), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - - return; - } - - void DoList(CommandSource &source, ChannelInfo *ci) - { - source.Reply(_("Access level settings for channel %s:"), ci->name.c_str()); - - if (!levelinfo_maxwidth) - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - - int len = l.name.length(); - if (len > levelinfo_maxwidth) - levelinfo_maxwidth = len; - } - - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - int j = ci->levels[l.priv]; - - if (j == ACCESS_INVALID) - source.Reply(_(" %-*s (disabled)"), levelinfo_maxwidth, l.name.c_str()); - else if (j == ACCESS_FOUNDER) - source.Reply(_(" %-*s (founder only)"), levelinfo_maxwidth, l.name.c_str()); - else - source.Reply(_(" %-*s %d"), levelinfo_maxwidth, l.name.c_str(), j); - } - - return; - } - - void DoReset(CommandSource &source, ChannelInfo *ci) - { - User *u = source.u; - - reset_levels(ci); - FOREACH_MOD(I_OnLevelChange, OnLevelChange(u, ci, -1, 0)); - - bool override = !ci->HasPriv(u, CA_FOUNDER); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "RESET"; - - source.Reply(_("Access levels for \002%s\002 reset to defaults."), ci->name.c_str()); - return; - } - - public: - CommandCSLevels(Module *creator) : Command(creator, "chanserv/levels", 2, 4), levelinfo_maxwidth(0) - { - this->SetDesc(_("Redefine the meanings of access levels")); - this->SetSyntax(_("\037channel\037 SET \037type\037 \037level\037")); - this->SetSyntax(_("\037channel\037 {DIS | DISABLE} \037type\037")); - this->SetSyntax(_("\037channel\037 LIST")); - this->SetSyntax(_("\037channel\037 RESET")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[1]; - const Anope::string &what = params.size() > 2 ? params[2] : ""; - const Anope::string &s = params.size() > 3 ? params[3] : ""; - - User *u = source.u; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - /* If SET, we want two extra parameters; if DIS[ABLE] or FOUNDER, we want only - * one; else, we want none. - */ - if (cmd.equals_ci("SET") ? s.empty() : (cmd.substr(0, 3).equals_ci("DIS") ? (what.empty() || !s.empty()) : !what.empty())) - this->OnSyntaxError(source, cmd); - else if (!ci->HasPriv(u, CA_FOUNDER) && !u->HasPriv("chanserv/access/modify")) - source.Reply(ACCESS_DENIED); - else if (cmd.equals_ci("SET")) - this->DoSet(source, ci, params); - else if (cmd.equals_ci("DIS") || cmd.equals_ci("DISABLE")) - this->DoDisable(source, ci, params); - else if (cmd.equals_ci("LIST")) - this->DoList(source, ci); - else if (cmd.equals_ci("RESET")) - this->DoReset(source, ci); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - if (subcommand.equals_ci("DESC")) - { - source.Reply(_("The following feature/function names are understood.")); - if (!levelinfo_maxwidth) - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - - int len = l.name.length(); - if (len > levelinfo_maxwidth) - levelinfo_maxwidth = len; - } - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - source.Reply(_(" %-*s %s"), levelinfo_maxwidth, l.name.c_str(), translate(source.u, l.desc.c_str())); - } - } - else - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("The \002LEVELS\002 command allows fine control over the meaning of\n" - "the numeric access levels used for channels. With this\n" - "command, you can define the access level required for most\n" - "of %s's functions. (The \002SET FOUNDER\002 and this command\n" - "are always restricted to the channel founder.)\n" - " \n" - "\002LEVELS SET\002 allows the access level for a function or group of\n" - "functions to be changed. \002LEVELS DISABLE\002 (or \002DIS\002 for short)\n" - "disables an automatic feature or disallows access to a\n" - "function by anyone, INCLUDING the founder (although, the founder\n" - "can always reenable it).\n" - " \n" - "\002LEVELS LIST\002 shows the current levels for each function or\n" - "group of functions. \002LEVELS RESET\002 resets the levels to the\n" - "default levels of a newly-created channel (see\n" - "\002HELP ACCESS LEVELS\002).\n" - " \n" - "For a list of the features and functions whose levels can be\n" - "set, see \002HELP LEVELS DESC\002."), source.owner->nick.c_str()); - } - return true; - } -}; - -class CSAccess : public Module -{ - AccessAccessProvider accessprovider; - CommandCSAccess commandcsaccess; - CommandCSLevels commandcslevels; - - public: - CSAccess(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - accessprovider(this), commandcsaccess(this), commandcslevels(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&accessprovider); - ModuleManager::RegisterService(&commandcsaccess); - ModuleManager::RegisterService(&commandcslevels); - - Implementation i[] = { I_OnReload, I_OnChanRegistered }; - ModuleManager::Attach(i, this, 2); - - this->OnReload(); - } - - void OnReload() - { - ConfigReader config; - - for (int i = 0; defaultLevels[i].priv != CA_SIZE; ++i) - { - AccessLevels &l = defaultLevels[i]; - - const Anope::string &value = config.ReadValue("chanserv", l.config_name, "", 0); - if (value.equals_ci("founder")) - l.default_level = ACCESS_FOUNDER; - else - l.default_level = config.ReadInteger("chanserv", l.config_name, 0, false); - } - } - - void OnChanRegistered(ChannelInfo *ci) - { - reset_levels(ci); - } -}; - -MODULE_INIT(CSAccess) diff --git a/modules/core/cs_akick.cpp b/modules/core/cs_akick.cpp deleted file mode 100644 index 437bf5572..000000000 --- a/modules/core/cs_akick.cpp +++ /dev/null @@ -1,564 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static void split_usermask(const Anope::string &mask, Anope::string &nick, Anope::string &user, Anope::string &host) -{ - size_t ex = mask.find('!'), at = mask.find('@', ex == Anope::string::npos ? 0 : ex + 1); - if (ex == Anope::string::npos) - { - if (at == Anope::string::npos) - { - nick = mask; - user = host = "*"; - } - else - { - nick = "*"; - user = mask.substr(0, at); - host = mask.substr(at + 1); - } - } - else - { - nick = mask.substr(0, ex); - if (at == Anope::string::npos) - { - user = mask.substr(ex + 1); - host = "*"; - } - else - { - user = mask.substr(ex + 1, at - ex - 1); - host = mask.substr(at + 1); - } - } -} - -class AkickListCallback : public NumberList -{ - protected: - CommandSource &source; - ChannelInfo *ci; - bool SentHeader; - public: - AkickListCallback(CommandSource &_source, ChannelInfo *_ci, const Anope::string &numlist) : NumberList(numlist, false), source(_source), ci(_ci), SentHeader(false) - { - } - - ~AkickListCallback() - { - if (!SentHeader) - source.Reply(_("No matching entries on %s autokick list."), ci->name.c_str()); - } - - virtual void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAkickCount()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Autokick list for %s:"), ci->name.c_str()); - } - - DoList(source, ci, Number - 1, ci->GetAkick(Number - 1)); - } - - static void DoList(CommandSource &source, ChannelInfo *ci, unsigned index, AutoKick *akick) - { - source.Reply(_(" %3d %s (%s)"), index + 1, akick->HasFlag(AK_ISNICK) ? akick->nc->display.c_str() : akick->mask.c_str(), !akick->reason.empty() ? akick->reason.c_str() : NO_REASON); - } -}; - -class AkickViewCallback : public AkickListCallback -{ - public: - AkickViewCallback(CommandSource &_source, ChannelInfo *_ci, const Anope::string &numlist) : AkickListCallback(_source, _ci, numlist) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAkickCount()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Autokick list for %s:"), ci->name.c_str()); - } - - DoList(source, ci, Number - 1, ci->GetAkick(Number - 1)); - } - - static void DoList(CommandSource &source, ChannelInfo *ci, unsigned index, AutoKick *akick) - { - Anope::string timebuf; - - if (akick->addtime) - timebuf = do_strftime(akick->addtime); - else - timebuf = UNKNOWN; - - source.Reply(CHAN_AKICK_VIEW_FORMAT, index + 1, akick->HasFlag(AK_ISNICK) ? akick->nc->display.c_str() : akick->mask.c_str(), !akick->creator.empty() ? akick->creator.c_str() : UNKNOWN, timebuf.c_str(), !akick->reason.empty() ? akick->reason.c_str() : _(NO_REASON)); - - if (akick->last_used) - source.Reply(_(" Last used %s"), do_strftime(akick->last_used).c_str()); - } -}; - -class AkickDelCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - Command *c; - unsigned Deleted; - public: - AkickDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, const Anope::string &list) : NumberList(list, true), source(_source), ci(_ci), c(_c), Deleted(0) - { - } - - ~AkickDelCallback() - { - User *u = source.u; - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, c, ci) << "DEL on " << Deleted << " users"; - - if (!Deleted) - source.Reply(_("No matching entries on %s autokick list."), ci->name.c_str()); - else if (Deleted == 1) - source.Reply(_("Deleted 1 entry from %s autokick list."), ci->name.c_str()); - else - source.Reply(_("Deleted %d entries from %s autokick list."), Deleted, ci->name.c_str()); - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAkickCount()) - return; - - ++Deleted; - ci->EraseAkick(Number - 1); - } -}; - -class CommandCSAKick : public Command -{ - void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string mask = params[2]; - Anope::string reason = params.size() > 3 ? params[3] : ""; - NickAlias *na = findnick(mask); - NickCore *nc = NULL; - AutoKick *akick; - - if (!na) - { - Anope::string nick, user, host; - - split_usermask(mask, nick, user, host); - mask = nick + "!" + user + "@" + host; - } - else - nc = na->nc; - - /* Check excepts BEFORE we get this far */ - if (ci->c) - { - std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> modes = ci->c->GetModeList(CMODE_EXCEPT); - for (; modes.first != modes.second; ++modes.first) - { - if (Anope::Match(modes.first->second, mask)) - { - source.Reply(CHAN_EXCEPTED, mask.c_str(), ci->name.c_str()); - return; - } - } - } - - /* Check whether target nick has equal/higher access - * or whether the mask matches a user with higher/equal access - Viper */ - if (ci->HasFlag(CI_PEACE) && nc) - { - AccessGroup nc_access = ci->AccessFor(nc), u_access = ci->AccessFor(u); - if (nc == ci->GetFounder() || nc_access >= u_access) - { - source.Reply(ACCESS_DENIED); - return; - } - } - else if (ci->HasFlag(CI_PEACE)) - { - /* Match against all currently online users with equal or - * higher access. - Viper */ - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(), it_end = UserListByNick.end(); it != it_end; ++it) - { - User *u2 = it->second; - - AccessGroup nc_access = ci->AccessFor(nc), u_access = ci->AccessFor(u); - Entry entry_mask(CMODE_BEGIN, mask); - - if ((ci->HasPriv(u2, CA_FOUNDER) || nc_access >= u_access) && entry_mask.Matches(u2)) - { - source.Reply(ACCESS_DENIED); - return; - } - } - - /* Match against the lastusermask of all nickalias's with equal - * or higher access. - Viper */ - for (nickalias_map::const_iterator it = NickAliasList.begin(), it_end = NickAliasList.end(); it != it_end; ++it) - { - na = it->second; - - AccessGroup nc_access = ci->AccessFor(na->nc), u_access = ci->AccessFor(u); - if (na->nc && (na->nc == ci->GetFounder() || nc_access >= u_access)) - { - Anope::string buf = na->nick + "!" + na->last_usermask; - if (Anope::Match(buf, mask)) - { - source.Reply(ACCESS_DENIED); - return; - } - } - } - } - - for (unsigned j = 0, end = ci->GetAkickCount(); j < end; ++j) - { - akick = ci->GetAkick(j); - if (akick->HasFlag(AK_ISNICK) ? akick->nc == nc : mask.equals_ci(akick->mask)) - { - source.Reply(_("\002%s\002 already exists on %s autokick list."), akick->HasFlag(AK_ISNICK) ? akick->nc->display.c_str() : akick->mask.c_str(), ci->name.c_str()); - return; - } - } - - if (ci->GetAkickCount() >= Config->CSAutokickMax) - { - source.Reply(_("Sorry, you can only have %d autokick masks on a channel."), Config->CSAutokickMax); - return; - } - - if (nc) - akick = ci->AddAkick(u->nick, nc, reason); - else - akick = ci->AddAkick(u->nick, mask, reason); - - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "ADD " << mask << ": " << reason; - - FOREACH_MOD(I_OnAkickAdd, OnAkickAdd(u, ci, akick)); - - source.Reply(_("\002%s\002 added to %s autokick list."), mask.c_str(), ci->name.c_str()); - - this->DoEnforce(source, ci); - } - - void DoDel(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &mask = params[2]; - AutoKick *akick; - unsigned i, end; - - if (!ci->GetAkickCount()) - { - source.Reply(_("%s autokick list is empty."), ci->name.c_str()); - return; - } - - /* Special case: is it a number/list? Only do search if it isn't. */ - if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AkickDelCallback list(source, ci, this, mask); - list.Process(); - } - else - { - NickAlias *na = findnick(mask); - NickCore *nc = na ? na->nc : NULL; - - for (i = 0, end = ci->GetAkickCount(); i < end; ++i) - { - akick = ci->GetAkick(i); - - if ((akick->HasFlag(AK_ISNICK) && akick->nc == nc) || (!akick->HasFlag(AK_ISNICK) && mask.equals_ci(akick->mask))) - break; - } - - if (i == ci->GetAkickCount()) - { - source.Reply(_("\002%s\002 not found on %s autokick list."), mask.c_str(), ci->name.c_str()); - return; - } - - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "DEL " << mask; - - ci->EraseAkick(i); - - source.Reply(_("\002%s\002 deleted from %s autokick list."), mask.c_str(), ci->name.c_str()); - } - } - - void DoList(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &mask = params.size() > 2 ? params[2] : ""; - - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "LIST"; - - if (!ci->GetAkickCount()) - { - source.Reply(_("%s autokick list is empty."), ci->name.c_str()); - return; - } - - if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AkickListCallback list(source, ci, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = ci->GetAkickCount(); i < end; ++i) - { - AutoKick *akick = ci->GetAkick(i); - - if (!mask.empty()) - { - if (!akick->HasFlag(AK_ISNICK) && !Anope::Match(akick->mask, mask)) - continue; - if (akick->HasFlag(AK_ISNICK) && !Anope::Match(akick->nc->display, mask)) - continue; - } - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Autokick list for %s:"), ci->name.c_str()); - } - - AkickListCallback::DoList(source, ci, i, akick); - } - - if (!SentHeader) - source.Reply(_("No matching entries on %s autokick list."), ci->name.c_str()); - } - } - - void DoView(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &mask = params.size() > 2 ? params[2] : ""; - - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "VIEW"; - - if (!ci->GetAkickCount()) - { - source.Reply(_("%s autokick list is empty."), ci->name.c_str()); - return; - } - - if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AkickViewCallback list(source, ci, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = ci->GetAkickCount(); i < end; ++i) - { - AutoKick *akick = ci->GetAkick(i); - - if (!mask.empty()) - { - if (!akick->HasFlag(AK_ISNICK) && !Anope::Match(akick->mask, mask)) - continue; - if (akick->HasFlag(AK_ISNICK) && !Anope::Match(akick->nc->display, mask)) - continue; - } - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Autokick list for %s:"), ci->name.c_str()); - } - - AkickViewCallback::DoList(source, ci, i, akick); - } - - if (!SentHeader) - source.Reply(_("No matching entries on %s autokick list."), ci->name.c_str()); - } - } - - void DoEnforce(CommandSource &source, ChannelInfo *ci) - { - User *u = source.u; - Channel *c = ci->c; - int count = 0; - - if (!c) - { - source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); - return; - } - - for (CUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ) - { - UserContainer *uc = *it++; - - if (ci->CheckKick(uc->user)) - ++count; - } - - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "ENFORCE, affects " << count << " users"; - - source.Reply(_("AKICK ENFORCE for \002%s\002 complete; \002%d\002 users were affected."), ci->name.c_str(), count); - } - - void DoClear(CommandSource &source, ChannelInfo *ci) - { - User *u = source.u; - bool override = !ci->HasPriv(u, CA_AKICK); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "CLEAR"; - - ci->ClearAkick(); - source.Reply(_("Channel %s akick list has been cleared."), ci->name.c_str()); - } - - public: - CommandCSAKick(Module *creator) : Command(creator, "chanserv/akick", 2, 4) - { - this->SetDesc(_("Maintain the AutoKick list")); - this->SetSyntax(_("\037channel\037 ADD {\037nick\037 | \037mask\037} [\037reason\037]")); - this->SetSyntax(_("\037channel\037 DEL {\037nick\037 | \037mask\037 | \037entry-num\037 | \037list\037}")); - this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | \037entry-num\037 | \037list\037]")); - this->SetSyntax(_("\002AKICK \037channel\037 VIEW [\037mask\037 | \037entry-num\037 | \037list\037]")); - this->SetSyntax(_("\037channel\037 ENFORCE")); - this->SetSyntax(_("\037channel\037 CLEAR")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - Anope::string chan = params[0]; - Anope::string cmd = params[1]; - Anope::string mask = params.size() > 2 ? params[2] : ""; - - User *u = source.u; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (mask.empty() && (cmd.equals_ci("ADD") || cmd.equals_ci("DEL"))) - this->OnSyntaxError(source, cmd); - else if (!ci->HasPriv(u, CA_AKICK) && !u->HasPriv("chanserv/access/modify")) - source.Reply(ACCESS_DENIED); - else if (!cmd.equals_ci("LIST") && !cmd.equals_ci("VIEW") && !cmd.equals_ci("ENFORCE") && readonly) - source.Reply(_("Sorry, channel autokick list modification is temporarily disabled.")); - else if (cmd.equals_ci("ADD")) - this->DoAdd(source, ci, params); - else if (cmd.equals_ci("DEL")) - this->DoDel(source, ci, params); - else if (cmd.equals_ci("LIST")) - this->DoList(source, ci, params); - else if (cmd.equals_ci("VIEW")) - this->DoView(source, ci, params); - else if (cmd.equals_ci("ENFORCE")) - this->DoEnforce(source, ci); - else if (cmd.equals_ci("CLEAR")) - this->DoClear(source, ci); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002AutoKick list\002 for a channel. If a user\n" - "on the AutoKick list attempts to join the channel,\n" - "%s will ban that user from the channel, then kick\n" - "the user.\n" - " \n" - "The \002AKICK ADD\002 command adds the given nick or usermask\n" - "to the AutoKick list. If a \037reason\037 is given with\n" - "the command, that reason will be used when the user is\n" - "kicked; if not, the default reason is \"You have been\n" - "banned from the channel\".\n" - "When akicking a \037registered nick\037 the nickserv account\n" - "will be added to the akick list instead of the mask.\n" - "All users within that nickgroup will then be akicked.\n"), - source.owner->nick.c_str()); - source.Reply(_( - " \n" - "The \002AKICK DEL\002 command removes the given nick or mask\n" - "from the AutoKick list. It does not, however, remove any\n" - "bans placed by an AutoKick; those must be removed\n" - "manually.\n" - " \n" - "The \002AKICK LIST\002 command displays the AutoKick list, or\n" - "optionally only those AutoKick entries which match the\n" - "given mask.\n" - " \n" - "The \002AKICK VIEW\002 command is a more verbose version of\n" - "\002AKICK LIST\002 command.\n" - " \n" - "The \002AKICK ENFORCE\002 command causes %s to enforce the\n" - "current AKICK list by removing those users who match an\n" - "AKICK mask.\n" - " \n" - "The \002AKICK CLEAR\002 command clears all entries of the\n" - "akick list."), source.owner->nick.c_str()); - return true; - } -}; - -class CSAKick : public Module -{ - CommandCSAKick commandcsakick; - - public: - CSAKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsakick(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsakick); - } -}; - -MODULE_INIT(CSAKick) diff --git a/modules/core/cs_ban.cpp b/modules/core/cs_ban.cpp deleted file mode 100644 index 759649662..000000000 --- a/modules/core/cs_ban.cpp +++ /dev/null @@ -1,109 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSBan : public Command -{ - public: - CommandCSBan(Module *creator) : Command(creator, "chanserv/ban", 2, 3) - { - this->SetDesc(_("Bans a selected nick on a channel")); - this->SetSyntax(_("\037#channel\037 \037nick\037 [\037reason\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &target = params[1]; - const Anope::string &reason = params.size() > 2 ? params[2] : "Requested"; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - User *u = source.u; - Channel *c = ci->c; - bool is_same = target.equals_ci(u->nick); - User *u2 = is_same ? u : finduser(target); - - AccessGroup u_access = ci->AccessFor(u), u2_access = ci->AccessFor(u2); - - if (!c) - source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); - else if (!u2) - source.Reply(NICK_X_NOT_IN_USE, target.c_str()); - else if (!ci->HasPriv(u, CA_BAN)) - source.Reply(ACCESS_DENIED); - else if (!is_same && ci->HasFlag(CI_PEACE) && u2_access >= u_access) - source.Reply(ACCESS_DENIED); - /* - * Dont ban/kick the user on channels where he is excepted - * to prevent services <-> server wars. - */ - else if (matches_list(ci->c, u2, CMODE_EXCEPT)) - source.Reply(CHAN_EXCEPTED, u2->nick.c_str(), ci->name.c_str()); - else if (u2->IsProtected()) - source.Reply(ACCESS_DENIED); - else - { - Anope::string mask; - get_idealban(ci, u2, mask); - - // XXX need a way to detect if someone is overriding - Log(LOG_COMMAND, u, this, ci) << "for " << mask; - - c->SetMode(NULL, CMODE_BAN, mask); - - /* We still allow host banning while not allowing to kick */ - if (!c->FindUser(u2)) - return; - - if (ci->HasFlag(CI_SIGNKICK) || (ci->HasFlag(CI_SIGNKICK_LEVEL) && !ci->HasPriv(u, CA_SIGNKICK))) - c->Kick(ci->WhoSends(), u2, "%s (%s)", reason.c_str(), u->nick.c_str()); - else - c->Kick(ci->WhoSends(), u2, "%s", reason.c_str()); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Bans a selected nick on a channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 access \n" - "and above on the channel.")); - return true; - } -}; - -class CSBan : public Module -{ - CommandCSBan commandcsban; - - public: - CSBan(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcsban(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsban); - } -}; - -MODULE_INIT(CSBan) diff --git a/modules/core/cs_clearusers.cpp b/modules/core/cs_clearusers.cpp deleted file mode 100644 index 18dc75479..000000000 --- a/modules/core/cs_clearusers.cpp +++ /dev/null @@ -1,83 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSClearUsers : public Command -{ - public: - CommandCSClearUsers(Module *creator) : Command(creator, "chanserv/clearusers", 1, 1) - { - this->SetDesc(_("Kicks all users on a channel")); - this->SetSyntax(_("\037channel\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - - User *u = source.u; - Channel *c = findchan(chan); - Anope::string modebuf; - - if (!c) - source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); - else if (!c->ci) - source.Reply(CHAN_X_NOT_REGISTERED, c->name.c_str()); - else if (!c->ci->HasPriv(u, CA_FOUNDER)) - { - source.Reply(ACCESS_DENIED); - return; - } - - Anope::string buf = "CLEARUSERS command from " + u->nick + " (" + u->Account()->display + ")"; - - for (CUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ) - { - UserContainer *uc = *it++; - - c->Kick(NULL, uc->user, "%s", buf.c_str()); - } - - source.Reply(_("All users have been kicked from \2%s\2."), chan.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Tells %s to clear (kick) all users certain settings on a channel." - " \n" - "By default, limited to those with founder access on the\n" - "channel."), source.owner->nick.c_str()); - return true; - } -}; - -class CSClearUsers : public Module -{ - CommandCSClearUsers commandcsclearusers; - - public: - CSClearUsers(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsclearusers(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsclearusers); - } -}; - -MODULE_INIT(CSClearUsers) diff --git a/modules/core/cs_clone.cpp b/modules/core/cs_clone.cpp deleted file mode 100644 index 5ede6a9e4..000000000 --- a/modules/core/cs_clone.cpp +++ /dev/null @@ -1,186 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSClone : public Command -{ -public: - CommandCSClone(Module *creator) : Command(creator, "chanserv/clone", 2, 3) - { - this->SetDesc(_("Copy all settings from one channel to another")); - this->SetSyntax(_("\037channel\037 \037target\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &channel = params[0]; - const Anope::string &target = params[1]; - Anope::string what = params.size() > 2 ? params[2] : ""; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (!ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - ChannelInfo *target_ci = cs_findchan(target); - if (!target_ci) - { - source.Reply(CHAN_X_NOT_REGISTERED, target.c_str()); - return; - } - if (!IsFounder(u, ci) || !IsFounder(u, target_ci)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (Config->CSMaxReg && u->Account()->channelcount >= Config->CSMaxReg && !u->HasPriv("chanserv/no-register-limit")) - { - source.Reply(u->Account()->channelcount > Config->CSMaxReg ? CHAN_EXCEEDED_CHANNEL_LIMIT : _(CHAN_REACHED_CHANNEL_LIMIT), Config->CSMaxReg); - return; - } - - if (what.equals_ci("ALL")) - what.clear(); - - if (what.empty()) - { - delete target_ci; - target_ci = new ChannelInfo(*ci); - target_ci->name = target; - RegisteredChannelList[target_ci->name] = target_ci; - target_ci->c = findchan(target_ci->name); - if (target_ci->c) - { - target_ci->c->ci = target_ci; - - check_modes(target_ci->c); - - ChannelMode *cm; - if (u->FindChannel(target_ci->c) != NULL) - { - /* On most ircds you do not receive the admin/owner mode till its registered */ - if ((cm = ModeManager::FindChannelModeByName(CMODE_OWNER))) - target_ci->c->SetMode(NULL, cm, u->nick); - else if ((cm = ModeManager::FindChannelModeByName(CMODE_PROTECT))) - target_ci->c->RemoveMode(NULL, cm, u->nick); - } - - /* Mark the channel as persistant */ - if (target_ci->c->HasMode(CMODE_PERM)) - target_ci->SetFlag(CI_PERSIST); - /* Persist may be in def cflags, set it here */ - else if (target_ci->HasFlag(CI_PERSIST) && (cm = ModeManager::FindChannelModeByName(CMODE_PERM))) - target_ci->c->SetMode(NULL, CMODE_PERM); - - if (target_ci->bi && target_ci->c->FindUser(target_ci->bi) == NULL) - target_ci->bi->Join(target_ci->c); - } - - if (target_ci->c && !target_ci->c->topic.empty()) - { - target_ci->last_topic = target_ci->c->topic; - target_ci->last_topic_setter = target_ci->c->topic_setter; - target_ci->last_topic_time = target_ci->c->topic_time; - } - else - target_ci->last_topic_setter = source.owner->nick; - - FOREACH_MOD(I_OnChanRegistered, OnChanRegistered(target_ci)); - - source.Reply(_("All settings from \002%s\002 have been transferred to \002%s\002"), channel.c_str(), target.c_str()); - } - else if (what.equals_ci("ACCESS")) - { - /*target_ci->ClearAccess(); - for (unsigned i = 0; i < ci->GetAccessCount(); ++i) - { - ChanAccess *access = ci->GetAccess(i); - target_ci->AddAccess(access->GetMask(), access->level, access->creator, access->last_seen); - } - - source.Reply(_("All access entries from \002%s\002 have been transferred to \002%s\002"), channel.c_str(), target.c_str()); - XXX - */ - } - else if (what.equals_ci("AKICK")) - { - target_ci->ClearAkick(); - for (unsigned i = 0; i < ci->GetAkickCount(); ++i) - { - AutoKick *akick = ci->GetAkick(i); - if (akick->HasFlag(AK_ISNICK)) - target_ci->AddAkick(akick->creator, akick->nc, akick->reason, akick->addtime, akick->last_used); - else - target_ci->AddAkick(akick->creator, akick->mask, akick->reason, akick->addtime, akick->last_used); - } - - source.Reply(_("All akick entries from \002%s\002 have been transferred to \002%s\002"), channel.c_str(), target.c_str()); - } - else if (what.equals_ci("BADWORDS")) - { - target_ci->ClearBadWords(); - for (unsigned i = 0; i < ci->GetBadWordCount(); ++i) - { - BadWord *bw = ci->GetBadWord(i); - target_ci->AddBadWord(bw->word, bw->type); - } - - source.Reply(_("All badword entries from \002%s\002 have been transferred to \002%s\002"), channel.c_str(), target.c_str()); - } - else - { - this->OnSyntaxError(source, ""); - return; - } - - Log(LOG_COMMAND, u, this, ci) << "to clone it to " << target_ci->name; - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Copies all settings, access, akicks, etc from channel to the\n" - "target channel. If access, akick, or badwords is specified then only\n" - "the respective settings are transferred. You must have founder level\n" - "access to \037channel\037 and \037target\037.")); - return true; - } -}; - -class CSClone : public Module -{ - CommandCSClone commandcsclone; - - public: - CSClone(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcsclone(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsclone); - } -}; - -MODULE_INIT(CSClone) diff --git a/modules/core/cs_drop.cpp b/modules/core/cs_drop.cpp deleted file mode 100644 index eb01875db..000000000 --- a/modules/core/cs_drop.cpp +++ /dev/null @@ -1,102 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSDrop : public Command -{ - public: - CommandCSDrop(Module *creator) : Command(creator, "chanserv/drop", 1, 1) - { - this->SetDesc(_("Cancel the registration of a channel")); - this->SetSyntax(_("\037channel\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - - User *u = source.u; - - if (readonly) - { - source.Reply(_("Sorry, channel de-registration is temporarily disabled.")); // XXX: READ_ONLY_MODE? - return; - } - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - ci = cs_findchan(chan); - - if (ci->HasFlag(CI_SUSPENDED) && !u->HasCommand("chanserv/chanserv/drop")) - { - source.Reply(CHAN_X_SUSPENDED, chan.c_str()); - return; - } - - if ((ci->HasFlag(CI_SECUREFOUNDER) ? !IsFounder(u, ci) : !ci->HasPriv(u, CA_FOUNDER)) && !u->HasCommand("chanserv/chanserv/drop")) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (ci->c && ModeManager::FindChannelModeByName(CMODE_REGISTERED)) - ci->c->RemoveMode(NULL, CMODE_REGISTERED, "", false); - - bool override = (ci->HasFlag(CI_SECUREFOUNDER) ? !IsFounder(u, ci) : !ci->HasPriv(u, CA_FOUNDER)); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "founder: " << (ci->GetFounder() ? ci->GetFounder()->display : "none"); - - delete ci; - - source.Reply(_("Channel \002%s\002 has been dropped."), chan.c_str()); - - FOREACH_MOD(I_OnChanDrop, OnChanDrop(chan)); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - User *u = source.u; - this->SendSyntax(source); - source.Reply(" "); - if (u->IsServicesOper()) - source.Reply(_("Unregisters the named channel. Only \002Services Operators\002\n" - "can drop a channel for which they have not identified.")); - else - source.Reply(_("Unregisters the named channel. Can only be used by\n" - "\002channel founder\002.")); - - return true; - } -}; - -class CSDrop : public Module -{ - CommandCSDrop commandcsdrop; - - public: - CSDrop(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcsdrop(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsdrop); - } -}; - -MODULE_INIT(CSDrop) diff --git a/modules/core/cs_flags.cpp b/modules/core/cs_flags.cpp deleted file mode 100644 index 48f1a22f1..000000000 --- a/modules/core/cs_flags.cpp +++ /dev/null @@ -1,455 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static struct FlagLevels -{ - ChannelAccess priv; - char default_char; - Anope::string config_name; - Anope::string desc; -} flagLevels[] = { - { CA_ACCESS_CHANGE, 'f', "flag_change", _("Allowed to modify the access list") }, - { CA_ACCESS_LIST, 'l', "flag_list", _("Allowed to view the access list") }, - { CA_AKICK, 'K', "flag_akick", _("Allowed to use AKICK command") }, - { CA_ASSIGN, 's', "flag_assign", _("Allowed to assign/unassign a bot") }, - { CA_AUTOHALFOP, 'H', "flag_autohalfop", _("Automatic mode +h") }, - { CA_AUTOOP, 'O', "flag_autoop", _("Automatic channel operator status") }, - { CA_AUTOOWNER, 'Q', "flag_autoowner", _("Automatic mode +q") }, - { CA_AUTOPROTECT, 'A', "flag_autoprotect", _("Automatic mode +a") }, - { CA_AUTOVOICE, 'V', "flag_autovoice", _("Automatic mode +v") }, - { CA_BADWORDS, 'k', "flag_badwords", _("Allowed to modify channel badwords list") }, - { CA_BAN, 'b', "flag_ban", _("Allowed to use ban users") }, - { CA_FANTASIA, 'c', "flag_fantasia", _("Allowed to use fantasy commands") }, - { CA_FOUNDER, 'F', "flag_founder", _("Allowed to issue commands restricted to channel founders") }, - { CA_GETKEY, 'G', "flag_getkey", _("Allowed to use GETKEY command") }, - { CA_GREET, 'g', "flag_greet", _("Greet message displayed") }, - { CA_HALFOP, 'h', "flag_halfop", _("Allowed to (de)halfop users") }, - { CA_HALFOPME, 'h', "flag_halfopme", _("Allowed to (de)halfop him/herself") }, - { CA_INFO, 'I', "flag_info", _("Allowed to use INFO command with ALL option") }, - { CA_INVITE, 'i', "flag_invite", _("Allowed to use the INVITE command") }, - { CA_KICK, 'k', "flag_kick", _("Allowed to use the KICK command") }, - { CA_MEMO, 'm', "flag_memo", _("Allowed to read channel memos") }, - { CA_MODE, 's', "flag_mode", _("Allowed to change channel modes") }, - { CA_NOKICK, 'N', "flag_nokick", _("Prevents users being kicked by Services") }, - { CA_OPDEOP, 'o', "flag_opdeop", _("Allowed to (de)op users") }, - { CA_OPDEOPME, 'o', "flag_opdeopme", _("Allowed to (de)op him/herself") }, - { CA_OWNER, 'q', "flag_owner", _("Allowed to use (de)owner users") }, - { CA_OWNERME, 'q', "flag_ownerme", _("Allowed to (de)owner him/herself") }, - { CA_PROTECT, 'a', "flag_protect", _("Allowed to (de)protect users") }, - { CA_PROTECTME, 'a', "flag_protectme", _("Allowed to (de)protect him/herself"), }, - { CA_SAY, 'B', "flag_say", _("Allowed to use SAY and ACT commands") }, - { CA_SET, 's', "flag_set", _("Allowed to set channel settings") }, - { CA_SIGNKICK, 'K', "flag_signkick", _("Prevents kicks from being signed") }, - { CA_TOPIC, 't', "flag_topic", _("Allowed to change channel topics") }, - { CA_UNBAN, 'u', "flag_unban", _("Allowed to unban users") }, - { CA_VOICE, 'v', "flag_voice", _("Allowed to (de)voice users") }, - { CA_VOICEME, 'v', "flag_voiceme", _("Allowed to (de)voice him/herself") }, - { CA_SIZE, -1, "", "" } -}; - -class FlagsChanAccess : public ChanAccess -{ - public: - std::set<char> flags; - - FlagsChanAccess(AccessProvider *p) : ChanAccess(p) - { - } - - bool Matches(User *u, NickCore *nc) - { - if (u && (Anope::Match(u->nick, this->mask) || Anope::Match(u->GetMask(), this->mask))) - return true; - else if (nc && Anope::Match(nc->display, this->mask)) - return true; - return false; - } - - bool HasPriv(ChannelAccess priv) - { - for (int i = 0; flagLevels[i].priv != CA_SIZE; ++i) - if (flagLevels[i].priv == priv) - return this->flags.count(flagLevels[i].default_char); - - return false; - } - - Anope::string Serialize() - { - return Anope::string(this->flags.begin(), this->flags.end()); - } - - void Unserialize(const Anope::string &data) - { - for (unsigned i = data.length(); i > 0; --i) - this->flags.insert(data[i - 1]); - } - - static Anope::string DetermineFlags(ChanAccess *access) - { - if (access->provider->name == "access/flags") - return access->Serialize(); - - std::set<char> buffer; - - for (int i = 0; flagLevels[i].priv != CA_SIZE; ++i) - { - FlagLevels &l = flagLevels[i]; - - if (access->HasPriv(l.priv)) - buffer.insert(l.default_char); - } - - return Anope::string(buffer.begin(), buffer.end()); - } -}; - -class FlagsAccessProvider : public AccessProvider -{ - public: - FlagsAccessProvider(Module *o) : AccessProvider(o, "access/flags") - { - } - - ChanAccess *Create() - { - return new FlagsChanAccess(this); - } -}; - -class CommandCSFlags : public Command -{ - void DoModify(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string mask = params.size() > 2 ? params[2] : ""; - Anope::string flags = params.size() > 3 ? params[3] : ""; - - if (flags.empty()) - { - this->OnSyntaxError(source, ""); - return; - } - - AccessGroup u_access = ci->AccessFor(u); - - if (mask.find_first_of("!*@") == Anope::string::npos && findnick(mask) == NULL) - mask += "!*@*"; - - ChanAccess *current = NULL; - std::set<char> current_flags; - for (unsigned i = ci->GetAccessCount(); i > 0; --i) - { - ChanAccess *access = ci->GetAccess(i - 1); - if (mask.equals_ci(access->mask)) - { - current = access; - Anope::string cur_flags = FlagsChanAccess::DetermineFlags(access); - for (unsigned j = cur_flags.length(); j > 0; --j) - current_flags.insert(cur_flags[j - 1]); - break; - } - } - - if (ci->GetAccessCount() >= Config->CSAccessMax) - { - source.Reply(_("Sorry, you can only have %d access entries on a channel."), Config->CSAccessMax); - return; - } - - bool override = false; - int add = -1; - for (size_t i = 0; i < flags.length(); ++i) - { - char f = flags[i]; - switch (f) - { - case '+': - add = 1; - break; - case '-': - add = 0; - break; - case '*': - if (add == -1) - break; - for (int j = 0; flagLevels[j].priv != CA_SIZE; ++j) - { - FlagLevels &l = flagLevels[j]; - if (!u_access.HasPriv(l.priv)) - { - if (u->HasPriv("chanserv/access/modify")) - override = true; - else - continue; - } - if (add == 1) - current_flags.insert(f); - else if (add == 0) - current_flags.erase(f); - } - break; - default: - if (add == -1) - break; - for (int j = 0; flagLevels[j].priv != CA_SIZE; ++j) - { - FlagLevels &l = flagLevels[j]; - if (f != l.default_char) - continue; - else if (!u_access.HasPriv(l.priv)) - { - if (u->HasPriv("chanserv/access/modify")) - override = true; - else - { - source.Reply(_("You can not set the \002%c\002 flag."), f); - continue; - } - } - if (add == 1) - current_flags.insert(f); - else if (add == 0) - current_flags.erase(f); - break; - } - } - } - if (current_flags.empty()) - { - if (current != NULL) - { - FOREACH_MOD(I_OnAccessDel, OnAccessDel(ci, u, current)); - ci->EraseAccess(current); - source.Reply(_("\002%s\002 removed from the %s access list."), mask.c_str(), ci->name.c_str()); - } - else - { - source.Reply(_("Insufficient flags given")); - } - return; - } - - service_reference<AccessProvider> provider("access/flags"); - if (!provider) - return; - FlagsChanAccess *access = debug_cast<FlagsChanAccess *>(provider->Create()); - access->ci = ci; - access->mask = mask; - access->creator = u->nick; - access->last_seen = current ? current->last_seen : 0; - access->created = Anope::CurTime; - access->flags = current_flags; - - if (current != NULL) - ci->EraseAccess(current); - - ci->AddAccess(access); - - FOREACH_MOD(I_OnAccessAdd, OnAccessAdd(ci, u, access)); - - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "MODIFY " << mask << " with flags " << access->Serialize(); - source.Reply(_("Access for \002%s\002 on %s set to +\002%s\002"), access->mask.c_str(), ci->name.c_str(), access->Serialize().c_str()); - - return; - } - - void DoList(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - const Anope::string &arg = params.size() > 2 ? params[2] : ""; - - if (!ci->GetAccessCount()) - source.Reply(_("%s access list is empty."), ci->name.c_str()); - else - { - unsigned total = 0; - - for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) - { - ChanAccess *access = ci->GetAccess(i); - const Anope::string &flags = FlagsChanAccess::DetermineFlags(access); - - if (!arg.empty()) - { - if (arg[0] == '+') - { - bool pass = true; - for (size_t j = 1; j < arg.length(); ++j) - if (flags.find(arg[j]) == Anope::string::npos) - pass = false; - if (pass == false) - continue; - } - else if (!Anope::Match(access->mask, arg)) - continue; - } - - if (++total == 1) - { - source.Reply(_("Flags list for %s"), ci->name.c_str()); - } - - source.Reply(_(" %3d %-10s +%-10s [last modified on %s by %s]"), i + 1, access->mask.c_str(), FlagsChanAccess::DetermineFlags(access).c_str(), do_strftime(access->created, source.u->Account(), true).c_str(), access->creator.c_str()); - } - - if (total == 0) - source.Reply(_("No matching entries on %s access list."), ci->name.c_str()); - else if (total == ci->GetAccessCount()) - source.Reply(_("End of access list.")); - else - source.Reply(_("End of access list - %d/%d entries shown."), total, ci->GetAccessCount()); - } - } - - void DoClear(CommandSource &source, ChannelInfo *ci) - { - User *u = source.u; - - if (!IsFounder(u, ci) && !u->HasPriv("chanserv/access/modify")) - source.Reply(ACCESS_DENIED); - else - { - ci->ClearAccess(); - - FOREACH_MOD(I_OnAccessClear, OnAccessClear(ci, u)); - - source.Reply(_("Channel %s access list has been cleared."), ci->name.c_str()); - - bool override = !IsFounder(u, ci); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "CLEAR"; - } - - return; - } - - public: - CommandCSFlags(Module *creator) : Command(creator, "chanserv/flags", 2, 4) - { - this->SetDesc(_("Modify the list of privileged users")); - this->SetSyntax(_("\037channel\037 MODIFY \037mask\037 \037changes\037")); - this->SetSyntax(_("\037channel\037 LIST [\037mask\037 | +\037flags\037]")); - this->SetSyntax(_("\037channel\037 CLEAR\002")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &cmd = params[1]; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(chan); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - return; - } - - bool is_list = cmd.equals_ci("LIST"); - bool has_access = false; - if (u->HasPriv("chanserv/access/modify")) - has_access = true; - else if (is_list && ci->HasPriv(u, CA_ACCESS_LIST)) - has_access = true; - else if (ci->HasPriv(u, CA_ACCESS_CHANGE)) - has_access = true; - - if (!has_access) - source.Reply(ACCESS_DENIED); - else if (readonly && !is_list) - source.Reply(_("Sorry, channel access list modification is temporarily disabled.")); - else if (cmd.equals_ci("MODIFY")) - this->DoModify(source, ci, params); - else if (cmd.equals_ci("LIST")) - this->DoList(source, ci, params); - else if (cmd.equals_ci("CLEAR")) - this->DoClear(source, ci); - else - this->OnSyntaxError(source, cmd); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("%s is another way to modify the channel access list, similar to\n" - "the XOP and ACCESS methods."), source.command.c_str()); - source.Reply(" "); - source.Reply(_("The MODIFY command allows you to modify the access list. If mask is\n" - "not already on the access list is it added, then the changes are applied.\n" - "If the mask has no more flags, then the mask is removed from the access list.\n" - "Additionally, you may use +* or -* to add or remove all flags, respectively. You are\n" - "only able to modify the access list if you have the proper permission on the channel,\n" - "and even then you can only give other people access to up what you already have.")); - source.Reply(" "); - source.Reply(_("The LIST command allows you to list existing entries on the channel access list.\n" - "If a mask is given, the mask is wildcard matched against all existing entries on the\n" - "access list, and only those entries are returned. If a set of flags is given, only those\n" - "on the access list with the specified flags are returned.")); - source.Reply(" "); - source.Reply(_("The CLEAR command clears the channel access list, which requires channel founder.")); - source.Reply(" "); - source.Reply(_("The available flags are:")); - - std::multimap<char, FlagLevels *, std::less<ci::string> > levels; - for (int i = 0; flagLevels[i].priv != CA_SIZE; ++i) - levels.insert(std::make_pair(flagLevels[i].default_char, &flagLevels[i])); - for (std::multimap<char, FlagLevels *, std::less<ci::string> >::iterator it = levels.begin(), it_end = levels.end(); it != it_end; ++it) - { - FlagLevels *l = it->second; - source.Reply(" %c - %s", l->default_char, translate(source.u->Account(), l->desc.c_str())); - } - - return true; - } -}; - -class CSFlags : public Module -{ - FlagsAccessProvider accessprovider; - CommandCSFlags commandcsflags; - - public: - CSFlags(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - accessprovider(this), commandcsflags(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&accessprovider); - ModuleManager::RegisterService(&commandcsflags); - - Implementation i[] = { I_OnReload }; - ModuleManager::Attach(i, this, 1); - - this->OnReload(); - } - - void OnReload() - { - ConfigReader config; - - for (int i = 0; flagLevels[i].priv != CA_SIZE; ++i) - { - FlagLevels &l = flagLevels[i]; - - const Anope::string &value = config.ReadValue("chanserv", l.config_name, "", 0); - if (value.empty()) - continue; - l.default_char = value[0]; - } - } -}; - -MODULE_INIT(CSFlags) diff --git a/modules/core/cs_getkey.cpp b/modules/core/cs_getkey.cpp deleted file mode 100644 index 4a6d62442..000000000 --- a/modules/core/cs_getkey.cpp +++ /dev/null @@ -1,80 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSGetKey : public Command -{ - public: - CommandCSGetKey(Module *creator) : Command(creator, "chanserv/getkey", 1, 1) - { - this->SetDesc(_("Returns the key of the given channel")); - this->SetSyntax(_("\037channel\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - - if (!ci->HasPriv(u, CA_GETKEY) && !u->HasCommand("chanserv/chanserv/getkey")) - { - source.Reply(ACCESS_DENIED); - return; - } - - Anope::string key; - if (!ci->c || !ci->c->GetParam(CMODE_KEY, key)) - { - source.Reply(_("The channel \002%s\002 has no key."), chan.c_str()); - return; - } - - bool override = !ci->HasPriv(u, CA_GETKEY); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci); - - source.Reply(_("Key for channel \002%s\002 is \002%s\002."), chan.c_str(), key.c_str()); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Returns the key of the given channel.")); - return true; - } -}; - -class CSGetKey : public Module -{ - CommandCSGetKey commandcsgetkey; - - public: - CSGetKey(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcsgetkey(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsgetkey); - } -}; - -MODULE_INIT(CSGetKey) diff --git a/modules/core/cs_info.cpp b/modules/core/cs_info.cpp deleted file mode 100644 index ef026563e..000000000 --- a/modules/core/cs_info.cpp +++ /dev/null @@ -1,142 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSInfo : public Command -{ - void CheckOptStr(Anope::string &buf, ChannelInfoFlag opt, const Anope::string &str, ChannelInfo *ci, const NickCore *nc) - { - if (ci->HasFlag(opt)) - { - if (!buf.empty()) - buf += ", "; - - buf += str; - } - } - - public: - CommandCSInfo(Module *creator) : Command(creator, "chanserv/info", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Lists information about the named registered channel")); - this->SetSyntax(_("\037channel\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - bool has_auspex = u->IsIdentified() && u->HasPriv("chanserv/auspex"); - bool show_all = false; - - /* Should we show all fields? Only for sadmins and identified users */ - if (has_auspex || ci->HasPriv(u, CA_INFO)) - show_all = true; - - source.Reply(CHAN_INFO_HEADER, chan.c_str()); - if (ci->GetFounder()) - source.Reply(_(" Founder: %s"), ci->GetFounder()->display.c_str()); - - if (show_all && ci->successor) - source.Reply(_(" Successor: %s"), ci->successor->display.c_str()); - - if (!ci->desc.empty()) - source.Reply(_(" Description: %s"), ci->desc.c_str()); - source.Reply(_(" Registered: %s"), do_strftime(ci->time_registered).c_str()); - source.Reply(_(" Last used: %s"), do_strftime(ci->last_used).c_str()); - - ModeLock *secret = ci->GetMLock(CMODE_SECRET); - if (!ci->last_topic.empty() && (show_all || ((!secret || secret->set == false) && (!ci->c || !ci->c->HasMode(CMODE_SECRET))))) - { - source.Reply(_(" Last topic: %s"), ci->last_topic.c_str()); - source.Reply(_(" Topic set by: %s"), ci->last_topic_setter.c_str()); - } - - if (show_all) - { - source.Reply(_(" Ban type: %d"), ci->bantype); - Anope::string optbuf; - - CheckOptStr(optbuf, CI_KEEPTOPIC, _("Topic Retention"), ci, u->Account()); - CheckOptStr(optbuf, CI_OPNOTICE, _("OP Notice"), ci, u->Account()); - CheckOptStr(optbuf, CI_PEACE, _("Peace"), ci, u->Account()); - CheckOptStr(optbuf, CI_PRIVATE, _("Private"), ci, u->Account()); - CheckOptStr(optbuf, CI_RESTRICTED, _("Restricted Access"), ci, u->Account()); - CheckOptStr(optbuf, CI_SECURE, _("Secure"), ci, u->Account()); - CheckOptStr(optbuf, CI_SECUREFOUNDER, _("Secure Founder"), ci, u->Account()); - CheckOptStr(optbuf, CI_SECUREOPS, _("Secure Ops"), ci, u->Account()); - if (ci->HasFlag(CI_SIGNKICK)) - CheckOptStr(optbuf, CI_SIGNKICK, _("Signed kicks"), ci, u->Account()); - else - CheckOptStr(optbuf, CI_SIGNKICK_LEVEL, _("Signed kicks"), ci, u->Account()); - CheckOptStr(optbuf, CI_TOPICLOCK, _("Topic Lock"), ci, u->Account()); - CheckOptStr(optbuf, CI_PERSIST, _("Persistant"), ci, u->Account()); - CheckOptStr(optbuf, CI_NO_EXPIRE, _("No expire"), ci, u->Account()); - - source.Reply(NICK_INFO_OPTIONS, optbuf.empty() ? _("None") : optbuf.c_str()); - source.Reply(_(" Mode lock: %s"), ci->GetMLockAsString(true).c_str()); - - if (!ci->HasFlag(CI_NO_EXPIRE)) - source.Reply(_(" Expires on: %s"), do_strftime(ci->last_used + Config->CSExpire).c_str()); - } - if (ci->HasFlag(CI_SUSPENDED)) - { - Anope::string by, reason; - ci->GetExtRegular("suspend_by", by); - ci->GetExtRegular("suspend_reason", reason); - source.Reply(_(" Suspended: [%s] %s"), by.c_str(), !reason.empty() ? reason.c_str() : NO_REASON); - } - - FOREACH_MOD(I_OnChanInfo, OnChanInfo(source, ci, show_all)); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists information about the named registered channel,\n" - "including its founder, time of registration, last time\n" - "used, description, and mode lock, if any. If \002ALL\002 is \n" - "specified, the entry message and successor will also \n" - "be displayed.")); - return true; - } -}; - -class CSInfo : public Module -{ - CommandCSInfo commandcsinfo; - - public: - CSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsinfo(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsinfo); - } -}; - -MODULE_INIT(CSInfo) diff --git a/modules/core/cs_invite.cpp b/modules/core/cs_invite.cpp deleted file mode 100644 index 27b4b03a3..000000000 --- a/modules/core/cs_invite.cpp +++ /dev/null @@ -1,102 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSInvite : public Command -{ - public: - CommandCSInvite(Module *creator) : Command(creator, "chanserv/invite", 1, 3) - { - this->SetDesc(_("Invites you into a channel")); - this->SetSyntax(_("\037channel\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - - User *u = source.u; - Channel *c = findchan(chan); - - if (!c) - { - source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); - return; - } - - ChannelInfo *ci = c->ci; - if (!ci) - { - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - return; - } - - if (!ci->HasPriv(u, CA_INVITE)) - { - source.Reply(ACCESS_DENIED); - return; - } - - User *u2; - if (params.size() == 1) - u2 = u; - else - { - if (!(u2 = finduser(params[1]))) - { - source.Reply(NICK_X_NOT_IN_USE, params[1].c_str()); - return; - } - } - - // XXX need a check for override... - Log(LOG_COMMAND, u, this, ci) << "for " << u2->nick; - - if (c->FindUser(u2)) - source.Reply(_("You are already in \002%s\002! "), c->name.c_str()); - else - { - ircdproto->SendInvite(ci->WhoSends(), chan, u2->nick); - source.Reply(_("\002%s\002 has been invited to \002%s\002."), u2->nick.c_str(), c->name.c_str()); - u2->SendMessage(ci->WhoSends(), _("You have been invited to \002%s\002."), c->name.c_str()); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Tells %s to invite you into the given channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 and above\n" - "on the channel."), source.owner->nick.c_str()); - return true; - } -}; - -class CSInvite : public Module -{ - CommandCSInvite commandcsinvite; - - public: - CSInvite(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcsinvite(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsinvite); - } -}; - -MODULE_INIT(CSInvite) diff --git a/modules/core/cs_kick.cpp b/modules/core/cs_kick.cpp deleted file mode 100644 index b98d0953d..000000000 --- a/modules/core/cs_kick.cpp +++ /dev/null @@ -1,91 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSKick : public Command -{ - public: - CommandCSKick(Module *creator) : Command(creator, "chanserv/kick", 2, 3) - { - this->SetDesc(_("Kicks a selected nick from a channel")); - this->SetSyntax(_("\037channel\037 \037nick\037 [\037reason\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &target = params[1]; - const Anope::string &reason = params.size() > 2 ? params[2] : "Requested"; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - Channel *c = findchan(params[0]); - bool is_same = target.equals_ci(u->nick); - User *u2 = is_same ? u : finduser(target); - - AccessGroup u_access = ci->AccessFor(u), u2_access = ci->AccessFor(u2); - - if (!c) - source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); - else if (!ci) - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - else if (!u2) - source.Reply(NICK_X_NOT_IN_USE, target.c_str()); - else if (!ci->HasPriv(u, CA_KICK)) - source.Reply(ACCESS_DENIED); - else if (!is_same && (ci->HasFlag(CI_PEACE)) && u2_access >= u_access) - source.Reply(ACCESS_DENIED); - else if (u2->IsProtected()) - source.Reply(ACCESS_DENIED); - else if (!c->FindUser(u2)) - source.Reply(NICK_X_NOT_ON_CHAN, u2->nick.c_str(), c->name.c_str()); - else - { - // XXX - Log(LOG_COMMAND, u, this, ci) << "for " << u2->nick; - - if (ci->HasFlag(CI_SIGNKICK) || (ci->HasFlag(CI_SIGNKICK_LEVEL) && !ci->HasPriv(u, CA_SIGNKICK))) - ci->c->Kick(ci->WhoSends(), u2, "%s (%s)", reason.c_str(), u->nick.c_str()); - else - ci->c->Kick(ci->WhoSends(), u2, "%s", reason.c_str()); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Kicks a selected nick on a channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 access \n" - "and above on the channel.")); - return true; - } -}; - -class CSKick : public Module -{ - CommandCSKick commandcskick; - - public: - CSKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcskick(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcskick); - } -}; - -MODULE_INIT(CSKick) diff --git a/modules/core/cs_list.cpp b/modules/core/cs_list.cpp deleted file mode 100644 index a79c047c4..000000000 --- a/modules/core/cs_list.cpp +++ /dev/null @@ -1,136 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSList : public Command -{ - public: - CommandCSList(Module *creator) : Command(creator, "chanserv/list", 1, 2) - { - this->SetFlag(CFLAG_STRIP_CHANNEL); - this->SetDesc(_("Lists all registered channels matching the given pattern")); - this->SetSyntax(_("\037pattern\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string pattern = params[0]; - unsigned nchans; - bool is_servadmin = u->HasCommand("chanserv/chanserv/list"); - int count = 0, from = 0, to = 0; - bool suspended = false, channoexpire = false; - - if (pattern[0] == '#') - { - Anope::string n1 = myStrGetToken(pattern.substr(1), '-', 0), /* Read FROM out */ - n2 = myStrGetTokenRemainder(pattern, '-', 1); - - try - { - from = convertTo<int>(n1); - to = convertTo<int>(n2); - } - catch (const ConvertException &) - { - source.Reply(LIST_INCORRECT_RANGE); - source.Reply(_("To search for channels starting with #, search for the channel\n" - "name without the #-sign prepended (\002anope\002 instead of \002#anope\002).")); - return; - } - - pattern = "*"; - } - - nchans = 0; - - if (is_servadmin && params.size() > 1) - { - Anope::string keyword; - spacesepstream keywords(params[1]); - while (keywords.GetToken(keyword)) - { - if (keyword.equals_ci("SUSPENDED")) - suspended = true; - if (keyword.equals_ci("NOEXPIRE")) - channoexpire = true; - } - } - - Anope::string spattern = "#" + pattern; - - source.Reply(LIST_HEADER, pattern.c_str()); - - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ++it) - { - ChannelInfo *ci = it->second; - - if (!is_servadmin && (ci->HasFlag(CI_PRIVATE) || ci->HasFlag(CI_SUSPENDED))) - continue; - else if (suspended && !ci->HasFlag(CI_SUSPENDED)) - continue; - else if (channoexpire && !ci->HasFlag(CI_NO_EXPIRE)) - continue; - - if (pattern.equals_ci(ci->name) || ci->name.equals_ci(spattern) || Anope::Match(ci->name, pattern) || Anope::Match(ci->name, spattern)) - { - if (((count + 1 >= from && count + 1 <= to) || (!from && !to)) && ++nchans <= Config->CSListMax) - { - char noexpire_char = ' '; - if (is_servadmin && (ci->HasFlag(CI_NO_EXPIRE))) - noexpire_char = '!'; - - Anope::string buf; - if (ci->HasFlag(CI_SUSPENDED)) - buf = Anope::printf("%-20s [Suspended]", ci->name.c_str()); - else - buf = Anope::printf("%-20s %s", ci->name.c_str(), !ci->desc.empty() ? ci->desc.c_str() : ""); - - source.Reply(" %c%s", noexpire_char, buf.c_str()); - } - ++count; - } - } - - source.Reply(_("End of list - %d/%d matches shown."), nchans > Config->CSListMax ? Config->CSListMax : nchans, nchans); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all registered channels matching the given pattern.\n" - "(Channels with the \002PRIVATE\002 option set are not listed.)\n" - "Note that a preceding '#' specifies a range, channel names\n" - "are to be written without '#'.")); - return true; - } -}; - -class CSList : public Module -{ - CommandCSList commandcslist; - - public: - CSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandcslist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcslist); - } -}; - -MODULE_INIT(CSList) diff --git a/modules/core/cs_main.cpp b/modules/core/cs_main.cpp deleted file mode 100644 index 5c490e4ff..000000000 --- a/modules/core/cs_main.cpp +++ /dev/null @@ -1,143 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class ChanServCore : public Module -{ - public: - ChanServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE) - { - this->SetAuthor("Anope"); - - BotInfo *ChanServ = findbot(Config->ChanServ); - if (ChanServ == NULL) - throw ModuleException("No bot named " + Config->ChanServ); - - Implementation i[] = { I_OnBotPrivmsg, I_OnDelCore, I_OnPreHelp, I_OnPostHelp }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) - { - if (Config->CSOpersOnly && !u->HasMode(UMODE_OPER) && bi->nick == Config->ChanServ) - { - u->SendMessage(bi, ACCESS_DENIED); - return EVENT_STOP; - } - - return EVENT_CONTINUE; - } - - void OnDelCore(NickCore *nc) - { - // XXX this is slightly inefficient - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end;) - { - ChannelInfo *ci = it->second; - ++it; - - if (ci->GetFounder() == nc) - { - NickCore *newowner = NULL; - if (ci->successor && (ci->successor->IsServicesOper() || !Config->CSMaxReg || ci->successor->channelcount < Config->CSMaxReg)) - newowner = ci->successor; - else - { - ChanAccess *highest = NULL; - for (unsigned j = 0; j < ci->GetAccessCount(); ++j) - { - ChanAccess *ca = ci->GetAccess(j); - NickCore *anc = findcore(ca->mask); - - if (!anc || (!anc->IsServicesOper() && Config->CSMaxReg && anc->channelcount >= Config->CSMaxReg) || (anc == nc)) - continue; - if (!highest || *ca > *highest) - highest = ca; - } - if (highest) - newowner = findcore(highest->mask); - } - - if (newowner) - { - Log(LOG_NORMAL, "chanserv/expire") << "Transferring foundership of " << ci->name << " from deleted nick " << nc->display << " to " << newowner->display; - ci->SetFounder(newowner); - ci->successor = NULL; - } - else - { - Log(LOG_NORMAL, "chanserv/expire") << "Deleting channel " << ci->name << " owned by deleted nick " << nc->display; - - delete ci; - continue; - } - } - - if (ci->successor == nc) - ci->successor = NULL; - - for (unsigned j = 0; j < ci->GetAccessCount(); ++j) - { - ChanAccess *ca = ci->GetAccess(j); - NickCore *anc = findcore(ca->mask); - - if (anc && anc == nc) - { - ci->EraseAccess(j); - break; - } - } - - for (unsigned j = ci->GetAkickCount(); j > 0; --j) - { - AutoKick *akick = ci->GetAkick(j - 1); - if (akick->HasFlag(AK_ISNICK) && akick->nc == nc) - ci->EraseAkick(j - 1); - } - } - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->ChanServ) - return; - source.Reply(_("\002%s\002 allows you to register and control various\n" - "aspects of channels. %s can often prevent\n" - "malicious users from \"taking over\" channels by limiting\n" - "who is allowed channel operator privileges. Available\n" - "commands are listed below; to use them, type\n" - "\002%s%s \037command\037\002. For more information on a\n" - "specific command, type \002%s%s HELP \037command\037\002.\n "), - Config->ChanServ.c_str(), Config->ChanServ.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->ChanServ.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->ChanServ.c_str(), Config->ChanServ.c_str(), source.command.c_str()); - } - - void OnPostHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->ChanServ) - return; - if (Config->CSExpire >= 86400) - source.Reply(_(" \n" - "Note that any channel which is not used for %d days\n" - "(i.e. which no user on the channel's access list enters\n" - "for that period of time) will be automatically dropped."), Config->CSExpire / 86400); - if (source.u->IsServicesOper()) - source.Reply(_(" \n" - "Services Operators can also drop any channel without needing\n" - "to identify via password, and may view the access, akick,\n" - "and level setting lists for any channel.")); - } -}; - -MODULE_INIT(ChanServCore) - diff --git a/modules/core/cs_mode.cpp b/modules/core/cs_mode.cpp deleted file mode 100644 index e67abd85a..000000000 --- a/modules/core/cs_mode.cpp +++ /dev/null @@ -1,364 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSMode : public Command -{ - bool CanSet(User *u, ChannelInfo *ci, ChannelModeName mode) - { - switch (mode) - { - case CMODE_OWNER: - return ci->HasPriv(u, CA_OWNER); - case CMODE_PROTECT: - return ci->HasPriv(u, CA_PROTECT); - case CMODE_OP: - return ci->HasPriv(u, CA_OPDEOP); - case CMODE_HALFOP: - return ci->HasPriv(u, CA_HALFOP); - case CMODE_VOICE: - return ci->HasPriv(u, CA_VOICE); - default: - break; - } - - return false; - } - - void DoLock(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &subcommand = params[2]; - const Anope::string ¶m = params.size() > 3 ? params[3] : ""; - - if (subcommand.equals_ci("ADD") && !param.empty()) - { - spacesepstream sep(param); - Anope::string modes; - - sep.GetToken(modes); - - int adding = -1; - for (size_t i = 0; i < modes.length(); ++i) - { - switch (modes[i]) - { - case '+': - adding = 1; - break; - case '-': - adding = 0; - break; - default: - if (adding == -1) - break; - ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); - if (!cm || !cm->CanSet(u)) - { - source.Reply(_("Unknown mode character %c ignored."), modes[i]); - break; - } - Anope::string mode_param; - if (((cm->Type == MODE_STATUS || cm->Type == MODE_LIST) && !sep.GetToken(mode_param)) || (cm->Type == MODE_PARAM && adding && !sep.GetToken(mode_param))) - source.Reply(_("Missing parameter for mode %c."), cm->ModeChar); - else - { - ci->SetMLock(cm, adding, mode_param, u->nick); - if (!mode_param.empty()) - mode_param = " " + mode_param; - source.Reply(_("%c%c%s locked on %s"), adding ? '+' : '-', cm->ModeChar, mode_param.c_str(), ci->name.c_str()); - } - } - } - - if (ci->c) - check_modes(ci->c); - } - else if (subcommand.equals_ci("DEL") && !param.empty()) - { - spacesepstream sep(param); - Anope::string modes; - - sep.GetToken(modes); - - int adding = -1; - for (size_t i = 0; i < modes.length(); ++i) - { - switch (modes[i]) - { - case '+': - adding = 1; - break; - case '-': - adding = 0; - break; - default: - if (adding == -1) - break; - ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); - if (!cm || !cm->CanSet(u)) - { - source.Reply(_("Unknown mode character %c ignored."), modes[i]); - break; - } - Anope::string mode_param; - if (!cm->Type == MODE_REGULAR && !sep.GetToken(mode_param)) - source.Reply(_("Missing parameter for mode %c."), cm->ModeChar); - else - { - if (ci->RemoveMLock(cm, mode_param)) - { - if (!mode_param.empty()) - mode_param = " " + mode_param; - source.Reply(_("%c%c%s has been unlocked from %s."), adding == 1 ? '+' : '-', cm->ModeChar, mode_param.c_str(), ci->name.c_str()); - } - else - source.Reply(_("%c is not locked on %s."), cm->ModeChar, ci->name.c_str()); - } - } - } - } - else if (subcommand.equals_ci("LIST")) - { - const std::multimap<ChannelModeName, ModeLock> &mlocks = ci->GetMLock(); - if (mlocks.empty()) - { - source.Reply(_("Channel %s has no mode locks."), ci->name.c_str()); - } - else - { - source.Reply(_("Mode locks for %s:"), ci->name.c_str()); - for (std::multimap<ChannelModeName, ModeLock>::const_iterator it = mlocks.begin(), it_end = mlocks.end(); it != it_end; ++it) - { - const ModeLock &ml = it->second; - ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name); - if (!cm) - continue; - - Anope::string modeparam = ml.param; - if (!modeparam.empty()) - modeparam = " " + modeparam; - source.Reply(_("%c%c%s, by %s on %s"), ml.set ? '+' : '-', cm->ModeChar, modeparam.c_str(), ml.setter.c_str(), do_strftime(ml.created).c_str()); - } - } - } - else - this->OnSyntaxError(source, subcommand); - } - - void DoSet(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - spacesepstream sep(params.size() > 3 ? params[3] : ""); - Anope::string modes = params[2], param; - - Log(LOG_COMMAND, u, this, ci) << "to set " << params[2]; - - int adding = -1; - for (size_t i = 0; i < modes.length(); ++i) - { - switch (modes[i]) - { - case '+': - adding = 1; - break; - case '-': - adding = 0; - break; - case '*': - if (adding == -1) - break; - for (unsigned j = 0; j < ModeManager::ChannelModes.size(); ++j) - { - ChannelMode *cm = ModeManager::ChannelModes[j]; - if (cm->CanSet(u)) - { - if (cm->Type == MODE_REGULAR || (!adding && cm->Type == MODE_PARAM)) - { - if (adding) - ci->c->SetMode(NULL, cm); - else - ci->c->RemoveMode(NULL, cm); - } - } - } - break; - default: - if (adding == -1) - break; - ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]); - if (!cm || !cm->CanSet(u)) - continue; - switch (cm->Type) - { - case MODE_REGULAR: - if (adding) - ci->c->SetMode(NULL, cm); - else - ci->c->RemoveMode(NULL, cm); - break; - case MODE_PARAM: - if (adding && !sep.GetToken(param)) - break; - if (adding) - ci->c->SetMode(NULL, cm, param); - else - ci->c->RemoveMode(NULL, cm); - break; - case MODE_STATUS: - { - if (!sep.GetToken(param)) - break; - - if (!this->CanSet(u, ci, cm->Name)) - { - source.Reply(_("You do not have access to set mode %c."), cm->ModeChar); - break; - } - - AccessGroup u_access = ci->AccessFor(u); - - if (str_is_wildcard(param)) - { - for (CUserList::const_iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) - { - UserContainer *uc = *it; - - AccessGroup targ_access = ci->AccessFor(uc->user); - - if (targ_access > u_access) - { - source.Reply(_("You do not have the access to change %s's modes."), uc->user->nick.c_str()); - continue; - } - - if (Anope::Match(uc->user->GetMask(), param)) - { - if (adding) - ci->c->SetMode(NULL, cm, uc->user->nick); - else - ci->c->RemoveMode(NULL, cm, uc->user->nick); - } - } - } - else - { - User *target = finduser(param); - if (target != NULL) - { - AccessGroup targ_access = ci->AccessFor(target); - if (targ_access > u_access) - { - source.Reply(_("You do not have the access to change %s's modes."), target->nick.c_str()); - break; - } - } - if (adding) - ci->c->SetMode(NULL, cm, param); - else - ci->c->RemoveMode(NULL, cm, param); - } - break; - } - case MODE_LIST: - if (!sep.GetToken(param)) - break; - if (adding) - ci->c->SetMode(NULL, cm, param); - else - { - std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> its = ci->c->GetModeList(cm->Name); - for (; its.first != its.second;) - { - const Anope::string &mask = its.first->second; - ++its.first; - - if (Anope::Match(mask, param)) - ci->c->RemoveMode(NULL, cm, mask); - } - } - } - } - } - } - - public: - CommandCSMode(Module *creator) : Command(creator, "chanserv/mode", 3, 4) - { - this->SetDesc(_("Control modes and mode locks on a channel")); - this->SetSyntax(_("\037channel\037 LOCK {ADD|DEL|LIST} [\037what\037]")); - this->SetSyntax(_("\037channel\037 SET \037modes\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &subcommand = params[1]; - - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - - if (!ci || !ci->c) - source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); - else if (!ci->HasPriv(u, CA_MODE) && !u->HasCommand("chanserv/chanserv/mode")) - source.Reply(ACCESS_DENIED); - else if (subcommand.equals_ci("LOCK")) - this->DoLock(source, ci, params); - else if (subcommand.equals_ci("SET")) - this->DoSet(source, ci, params); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Mainly controls mode locks and mode access (which is different from channel access)\n" - "on a channel.\n" - " \n" - "The \002MODE LOCK\002 command allows you to add, delete, and view mode locks on a channel.\n" - "If a mode is locked on or off, services will not allow that mode to be changed.\n" - "Example:\n" - " \002MODE #channel LOCK ADD +bmnt *!*@*aol*\002\n" - " \n" - "The \002MODE SET\002 command allows you to set modes through services. Wildcards * and ? may\n" - "be given as parameters for list and status modes.\n" - "Example:\n" - " \002MODE #channel SET +v *\002\n" - " Sets voice status to all users in the channel.\n" - " \n" - " \002MODE #channel SET -b ~c:*\n" - " Clears all extended bans that start with ~c:")); - return true; - } -}; - -class CSMode : public Module -{ - CommandCSMode commandcsmode; - - public: - CSMode(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsmode(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsmode); - } -}; - -MODULE_INIT(CSMode) diff --git a/modules/core/cs_modes.cpp b/modules/core/cs_modes.cpp deleted file mode 100644 index cee2f9460..000000000 --- a/modules/core/cs_modes.cpp +++ /dev/null @@ -1,431 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandModeBase : public Command -{ - void do_mode(CommandSource &source, Command *com, ChannelMode *cm, const Anope::string &chan, const Anope::string &nick, bool set, ChannelAccess level, ChannelAccess levelself, ChannelInfoFlag notice) - { - User *u = source.u; - User *u2 = finduser(nick); - Channel *c = findchan(chan); - ChannelInfo *ci = c ? c->ci : NULL; - - bool is_same = u == u2; - - AccessGroup u_access = ci ? ci->AccessFor(u) : AccessGroup(), u2_access = ci && u2 ? ci->AccessFor(u2) : AccessGroup(); - - if (!c) - source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); - else if (!ci) - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - else if (!u2) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (is_same ? !ci->HasPriv(u, levelself) : !ci->HasPriv(u, level)) - source.Reply(ACCESS_DENIED); - else if (!set && !is_same && ci->HasFlag(CI_PEACE) && u2_access >= u_access) - source.Reply(ACCESS_DENIED); - else if (!set && u2->IsProtected() && !is_same) - source.Reply(ACCESS_DENIED); - else if (!c->FindUser(u2)) - source.Reply(NICK_X_NOT_ON_CHAN, u2->nick.c_str(), c->name.c_str()); - else - { - if (set) - c->SetMode(NULL, cm, u2->nick); - else - c->RemoveMode(NULL, cm, u2->nick); - - Log(LOG_COMMAND, u, com, ci) << "for " << u2->nick; - if (notice && ci->HasFlag(notice)) - ircdproto->SendMessage(ci->WhoSends(), c->name, "%s command used for %s by %s", com->name.c_str(), u2->nick.c_str(), u->nick.c_str()); - } - } - - protected: - /** do_util: not a command, but does the job of others - * @param source The source of the command - * @param com The command calling this function - * @param cm A channel mode class - * @param chan The channel its being set on - * @param nick The nick the modes being set on - * @param set Is the mode being set or removed - * @param level The acecss level required to set this mode on someone else - * @param levelself The access level required to set this mode on yourself - * @param notice Flag required on a channel to send a notice - */ - void do_util(CommandSource &source, Command *com, ChannelMode *cm, const Anope::string &chan, const Anope::string &nick, bool set, ChannelAccess level, ChannelAccess levelself, ChannelInfoFlag notice) - { - User *u = source.u; - - if (chan.empty()) - for (UChannelList::iterator it = u->chans.begin(); it != u->chans.end(); ++it) - do_mode(source, com, cm, (*it)->chan->name, u->nick, set, level, levelself, notice); - else - do_mode(source, com, cm, chan, !nick.empty() ? nick : u->nick, set, level, levelself, notice); - - return; - } - - public: - CommandModeBase(Module *creator, const Anope::string &cname) : Command(creator, cname, 0, 2) - { - this->SetSyntax(_("[\037#channel\037] [\037nick\037]")); - } -}; - -class CommandCSOp : public CommandModeBase -{ - public: - CommandCSOp(Module *creator) : CommandModeBase(creator, "chanserv/op") - { - this->SetDesc(_("Gives Op status to a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_OP); - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", true, CA_OPDEOP, CA_OPDEOPME, CI_OPNOTICE); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Ops a selected nick on a channel. If nick is not given,\n" - "it will op you. If channel is not given, it will op you\n" - "on every channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 access \n" - "and above on the channel.")); - return true; - } -}; - -class CommandCSDeOp : public CommandModeBase -{ - public: - CommandCSDeOp(Module *creator) : CommandModeBase(creator, "chanserv/deop") - { - this->SetDesc(_("Deops a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_OP); - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", false, CA_OPDEOP, CA_OPDEOPME, CI_OPNOTICE); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply("Deops a selected nick on a channel. If nick is not given,\n" - "it will deop you. If channel is not given, it will deop\n" - "you on every channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 access \n" - "and above on the channel."); - return true; - } -}; - -class CommandCSVoice : public CommandModeBase -{ - public: - CommandCSVoice(Module *creator) : CommandModeBase(creator, "chanserv/voice") - { - this->SetDesc(_("Voices a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_VOICE); - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", true, CA_VOICE, CA_VOICEME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Voices a selected nick on a channel. If nick is not given,\n" - "it will voice you. If channel is not given, it will voice you\n" - "on every channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 access \n" - "and above on the channel, or to VOPs or those with level 3 \n" - "and above for self voicing.")); - return true; - } -}; - -class CommandCSDeVoice : public CommandModeBase -{ - public: - CommandCSDeVoice(Module *creator) : CommandModeBase(creator, "chanserv/devoice") - { - this->SetDesc(_("Devoices a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_VOICE); - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", false, CA_VOICE, CA_VOICEME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Devoices a selected nick on a channel. If nick is not given,\n" - "it will devoice you. If channel is not given, it will devoice\n" - "you on every channel.\n" - " \n" - "By default, limited to AOPs or those with level 5 access \n" - "and above on the channel, or to VOPs or those with level 3 \n" - "and above for self devoicing.")); - return true; - } -}; - -class CommandCSHalfOp : public CommandModeBase -{ - public: - CommandCSHalfOp(Module *creator) : CommandModeBase(creator, "chanserv/halfop") - { - this->SetDesc(_("Halfops a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_HALFOP); - - if (!cm) - return; - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", true, CA_HALFOP, CA_HALFOPME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Halfops a selected nick on a channel. If nick is not given,\n" - "it will halfop you. If channel is not given, it will halfop\n" - "you on every channel.\n" - " \n" - "By default, limited to AOPs and those with level 5 access \n" - "and above on the channel, or to HOPs or those with level 4 \n")); - return true; - } -}; - -class CommandCSDeHalfOp : public CommandModeBase -{ - public: - CommandCSDeHalfOp(Module *creator) : CommandModeBase(creator, "chanserv/dehalfop") - { - this->SetDesc(_("Dehalfops a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_HALFOP); - - if (!cm) - return; - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", false, CA_HALFOP, CA_HALFOPME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Dehalfops a selected nick on a channel. If nick is not given,\n" - "it will dehalfop you. If channel is not given, it will dehalfop\n" - "you on every channel.\n" - " \n" - "By default, limited to AOPs and those with level 5 access \n" - "and above on the channel, or to HOPs or those with level 4 \n" - "and above for self dehalfopping.")); - return true; - } -}; - -class CommandCSProtect : public CommandModeBase -{ - public: - CommandCSProtect(Module *creator) : CommandModeBase(creator, "chanserv/protect") - { - this->SetDesc(_("Protects a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_PROTECT); - - if (!cm) - return; - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", true, CA_PROTECT, CA_PROTECTME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Protects a selected nick on a channel. If nick is not given,\n" - "it will protect you. If channel is not given, it will protect\n" - "you on every channel.\n" - " \n" - "By default, limited to the founder, or to SOPs or those with \n" - "level 10 and above on the channel for self protecting.")); - return true; - } -}; - -class CommandCSDeProtect : public CommandModeBase -{ - public: - CommandCSDeProtect(Module *creator) : CommandModeBase(creator, "chanserv/deprotect") - { - this->SetDesc(_("Deprotects a selected nick on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_PROTECT); - - if (!cm) - return; - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", false, CA_PROTECT, CA_PROTECTME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Deprotects a selected nick on a channel. If nick is not given,\n" - "it will deprotect you. If channel is not given, it will deprotect\n" - "you on every channel.\n" - " \n" - "By default, limited to the founder, or to SOPs or those with \n")); - return true; - } -}; - -class CommandCSOwner : public CommandModeBase -{ - public: - CommandCSOwner(Module *creator) : CommandModeBase(module, "chanserv/owner") - { - this->SetDesc(_("Gives you owner status on channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_OWNER); - - if (!cm) - return; - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", true, CA_OWNER, CA_OWNERME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Gives the selected nick owner status on \002channel\002. If nick is not\n" - "given, it will give you owner. If channel is not given, it will\n" - "give you owner on every channel.\n" - " \n" - "Limited to those with founder access on the channel.")); - return true; - } -}; - -class CommandCSDeOwner : public CommandModeBase -{ - public: - CommandCSDeOwner(Module *creator) : CommandModeBase(creator, "chanserv/deowner") - { - this->SetDesc(_("Removes your owner status on a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_OWNER); - - if (!cm) - return; - - return do_util(source, this, cm, !params.empty() ? params[0] : "", params.size() > 1 ? params[1] : "", false, CA_OWNER, CA_OWNERME, CI_BEGIN); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Removes owner status from the selected nick on \002channel\002. If nick\n" - "is not given, it will deowner you. If channel is not given, it will\n" - "deowner you on every channel.\n" - " \n" - "Limited to those with founder access on the channel.")); - return true; - } -}; - -class CSModes : public Module -{ - CommandCSOwner commandcsowner; - CommandCSDeOwner commandcsdeowner; - CommandCSProtect commandcsprotect; - CommandCSDeProtect commandcsdeprotect; - CommandCSOp commandcsop; - CommandCSDeOp commandcsdeop; - CommandCSHalfOp commandcshalfop; - CommandCSDeHalfOp commandcsdehalfop; - CommandCSVoice commandcsvoice; - CommandCSDeVoice commandcsdevoice; - - public: - CSModes(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsowner(this), commandcsdeowner(this), commandcsprotect(this), commandcsdeprotect(this), - commandcsop(this), commandcsdeop(this), commandcshalfop(this), commandcsdehalfop(this), - commandcsvoice(this), commandcsdevoice(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsop); - ModuleManager::RegisterService(&commandcsdeop); - ModuleManager::RegisterService(&commandcsvoice); - ModuleManager::RegisterService(&commandcsdevoice); - - ModuleManager::RegisterService(&commandcsowner); - ModuleManager::RegisterService(&commandcsdeowner); - ModuleManager::RegisterService(&commandcsprotect); - ModuleManager::RegisterService(&commandcsdeprotect); - ModuleManager::RegisterService(&commandcshalfop); - ModuleManager::RegisterService(&commandcsdehalfop); - } -}; - -MODULE_INIT(CSModes) diff --git a/modules/core/cs_register.cpp b/modules/core/cs_register.cpp deleted file mode 100644 index 117212519..000000000 --- a/modules/core/cs_register.cpp +++ /dev/null @@ -1,193 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSRegister : public Command -{ - public: - CommandCSRegister(Module *creator) : Command(creator, "chanserv/register", 1, 2) - { - this->SetDesc(_("Register a channel")); - this->SetSyntax(_("\037channel\037 [\037description\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &chan = params[0]; - const Anope::string &chdesc = params.size() > 1 ? params[1] : ""; - - User *u = source.u; - Channel *c = findchan(params[0]); - ChannelInfo *ci = cs_findchan(params[0]); - - if (readonly) - source.Reply(_("Sorry, channel registration is temporarily disabled.")); - else if (u->Account()->HasFlag(NI_UNCONFIRMED)) - source.Reply(_("You must confirm your account before you can register a channel.")); - else if (chan[0] == '&') - source.Reply(_("Local channels cannot be registered.")); - else if (chan[0] != '#') - source.Reply(CHAN_SYMBOL_REQUIRED); - else if (!ircdproto->IsChannelValid(chan)) - source.Reply(CHAN_X_INVALID, chan.c_str()); - else if (ci) - source.Reply(_("Channel \002%s\002 is already registered!"), chan.c_str()); - else if (c && !c->HasUserStatus(u, CMODE_OP)) - source.Reply(_("You must be a channel operator to register the channel.")); - else if (Config->CSMaxReg && u->Account()->channelcount >= Config->CSMaxReg && !u->HasPriv("chanserv/no-register-limit")) - source.Reply(u->Account()->channelcount > Config->CSMaxReg ? CHAN_EXCEEDED_CHANNEL_LIMIT : _(CHAN_REACHED_CHANNEL_LIMIT), Config->CSMaxReg); - else - { - ci = new ChannelInfo(chan); - ci->SetFounder(u->Account()); - if (!chdesc.empty()) - ci->desc = chdesc; - - if (c && !c->topic.empty()) - { - ci->last_topic = c->topic; - ci->last_topic_setter = c->topic_setter; - ci->last_topic_time = c->topic_time; - } - else - ci->last_topic_setter = source.owner->nick; - - ci->bi = NULL; - Log(LOG_COMMAND, u, this, ci); - source.Reply(_("Channel \002%s\002 registered under your nickname: %s"), chan.c_str(), u->nick.c_str()); - - /* Implement new mode lock */ - if (c) - { - check_modes(c); - - ChannelMode *cm; - if (u->FindChannel(c) != NULL) - { - /* On most ircds you do not receive the admin/owner mode till its registered */ - if ((cm = ModeManager::FindChannelModeByName(CMODE_OWNER))) - c->SetMode(NULL, cm, u->nick); - else if ((cm = ModeManager::FindChannelModeByName(CMODE_PROTECT))) - c->RemoveMode(NULL, cm, u->nick); - } - - /* Mark the channel as persistant */ - if (c->HasMode(CMODE_PERM)) - ci->SetFlag(CI_PERSIST); - /* Persist may be in def cflags, set it here */ - else if (ci->HasFlag(CI_PERSIST) && (cm = ModeManager::FindChannelModeByName(CMODE_PERM))) - c->SetMode(NULL, CMODE_PERM); - } - - FOREACH_MOD(I_OnChanRegistered, OnChanRegistered(ci)); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Registers a channel in the %s database. In order\n" - "to use this command, you must first be a channel operator\n" - "on the channel you're trying to register.\n" - "The description, which is optional, is a\n" - "general description of the channel's purpose.\n" - " \n" - "When you register a channel, you are recorded as the\n" - "\"founder\" of the channel. The channel founder is allowed\n" - "to change all of the channel settings for the channel;\n" - "%s will also automatically give the founder\n" - "channel-operator privileges when s/he enters the channel.\n" - "See the \002ACCESS\002 command (\002%s%s HELP ACCESS\002) for\n" - "information on giving a subset of these privileges to\n" - "other channel users.\n" - " \n" - "NOTICE: In order to register a channel, you must have\n" - "first registered your nickname. If you haven't,\n" - "\002%s%s HELP\002 for information on how to do so."), - source.owner->nick.c_str(), source.owner->nick.c_str(), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class ExpireCallback : public CallBack -{ - public: - ExpireCallback(Module *owner) : CallBack(owner, Config->ExpireTimeout, Anope::CurTime, true) { } - - void Tick(time_t) - { - if (!Config->CSExpire || noexpire || readonly) - return; - - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ) - { - ChannelInfo *ci = it->second; - ++it; - - bool expire = false; - if (ci->HasFlag(CI_SUSPENDED)) - { - if (Config->CSSuspendExpire && Anope::CurTime - ci->last_used >= Config->CSSuspendExpire) - expire = true; - } - else if (!ci->c && Config->CSExpire && Anope::CurTime - ci->last_used >= Config->CSExpire) - expire = true; - - if (ci->HasFlag(CI_NO_EXPIRE)) - expire = false; - - if (expire) - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnPreChanExpire, OnPreChanExpire(ci)); - if (MOD_RESULT == EVENT_STOP) - continue; - - Anope::string extra; - if (ci->HasFlag(CI_SUSPENDED)) - extra = "suspended "; - - Log(LOG_NORMAL, "chanserv/expire") << "Expiring " << extra << "channel " << ci->name << " (founder: " << (ci->GetFounder() ? ci->GetFounder()->display : "(none)") << ")"; - FOREACH_MOD(I_OnChanExpire, OnChanExpire(ci)); - delete ci; - } - } - } -}; - -class CSRegister : public Module -{ - CommandCSRegister commandcsregister; - ExpireCallback ecb; - - public: - CSRegister(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsregister(this), ecb(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsregister); - ModuleManager::Attach(I_OnDelChan, this); - } - - void OnDelChan(ChannelInfo *ci) - { - if (ci->c && ci->c->HasMode(CMODE_REGISTERED)) - ci->c->RemoveMode(NULL, CMODE_REGISTERED, "", false); - } -}; - -MODULE_INIT(CSRegister) diff --git a/modules/core/cs_saset.cpp b/modules/core/cs_saset.cpp deleted file mode 100644 index 699c5bc2c..000000000 --- a/modules/core/cs_saset.cpp +++ /dev/null @@ -1,74 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSASet : public Command -{ - public: - CommandCSSASet(Module *creator) : Command(creator, "chanserv/saset", 2, 3) - { - this->SetDesc(_("Forcefully set channel options and information")); - this->SetSyntax(_("\037option\037 \037channel\037 \037parameters\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->OnSyntaxError(source, ""); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services Operators to forcefully change settings\n" - "on channels.\n" - " \n" - "Available options:")); - Anope::string this_name = source.command; - for (BotInfo::command_map::iterator it = source.owner->commands.begin(), it_end = source.owner->commands.end(); it != it_end; ++it) - { - const Anope::string &c_name = it->first; - CommandInfo &info = it->second; - if (c_name.find_ci(this_name + " ") == 0) - { - service_reference<Command> command(info.name); - if (command) - { - source.command = it->first; - command->OnServHelp(source); - } - } - } - source.Reply(_("Type \002%s%s HELP SASET \037option\037\002 for more information on a\n" - "particular option."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CSSASet : public Module -{ - CommandCSSASet commandcssaset; - - public: - CSSASet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssaset(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssaset); - } -}; - -MODULE_INIT(CSSASet) diff --git a/modules/core/cs_saset_noexpire.cpp b/modules/core/cs_saset_noexpire.cpp deleted file mode 100644 index 1e085496f..000000000 --- a/modules/core/cs_saset_noexpire.cpp +++ /dev/null @@ -1,81 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSASetNoexpire : public Command -{ - public: - CommandCSSASetNoexpire(Module *creator) : Command(creator, "chanserv/saset/noexpire", 2, 2) - { - this->SetDesc(_("Prevent the channel from expiring")); - this->SetDesc(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_NO_EXPIRE); - source.Reply(_("Channel %s \002will not\002 expire."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_NO_EXPIRE); - source.Reply(_("Channel %s \002will\002 expire."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "NOEXPIRE"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets whether the given channel will expire. Setting this\n" - "to ON prevents the channel from expiring.")); - return true; - } -}; - -class CSSetNoexpire : public Module -{ - CommandCSSASetNoexpire commandcssasetnoexpire; - - public: - CSSetNoexpire(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssasetnoexpire(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssasetnoexpire); - } -}; - -MODULE_INIT(CSSetNoexpire) diff --git a/modules/core/cs_set.cpp b/modules/core/cs_set.cpp deleted file mode 100644 index 65719ce91..000000000 --- a/modules/core/cs_set.cpp +++ /dev/null @@ -1,74 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSet : public Command -{ - public: - CommandCSSet(Module *creator) : Command(creator, "chanserv/set", 2, 3) - { - this->SetDesc(_("Set channel options and information")); - this->SetSyntax(_("\037option\037 \037channel\037 \037parameters\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->OnSyntaxError(source, ""); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows the channel founder to set various channel options\n" - "and other information.\n" - " \n" - "Available options:")); - Anope::string this_name = source.command; - for (BotInfo::command_map::iterator it = source.owner->commands.begin(), it_end = source.owner->commands.end(); it != it_end; ++it) - { - const Anope::string &c_name = it->first; - CommandInfo &info = it->second; - if (c_name.find_ci(this_name + " ") == 0) - { - service_reference<Command> command(info.name); - if (command) - { - source.command = it->first; - command->OnServHelp(source); - } - } - } - source.Reply(_("Type \002%s%s HELP SET \037option\037\002 for more information on a\n" - "particular option."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CSSet : public Module -{ - CommandCSSet commandcsset; - - public: - CSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsset(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsset); - } -}; - -MODULE_INIT(CSSet) diff --git a/modules/core/cs_set_bantype.cpp b/modules/core/cs_set_bantype.cpp deleted file mode 100644 index 94d2aa151..000000000 --- a/modules/core/cs_set_bantype.cpp +++ /dev/null @@ -1,98 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetBanType : public Command -{ - public: - CommandCSSetBanType(Module *creator, const Anope::string &cname = "chanserv/set/bantype") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Set how Services make bans on the channel")); - this->SetSyntax(_("\037channel\037 \037bantype\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - try - { - int16 new_type = convertTo<int16>(params[1]); - if (new_type < 0 || new_type > 3) - throw ConvertException("Invalid range"); - ci->bantype = new_type; - source.Reply(_("Ban type for channel %s is now #%d."), ci->name.c_str(), ci->bantype); - } - catch (const ConvertException &) - { - source.Reply(_("\002%s\002 is not a valid ban type."), params[1].c_str()); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets the ban type that will be used by services whenever\n" - "they need to ban someone from your channel.\n" - " \n" - "bantype is a number between 0 and 3 that means:\n" - " \n" - "0: ban in the form *!user@host\n" - "1: ban in the form *!*user@host\n" - "2: ban in the form *!*@host\n" - "3: ban in the form *!*user@*.domain"), this->name.c_str()); - return true; - } -}; - -class CommandCSSASetBanType : public CommandCSSetBanType -{ - public: - CommandCSSASetBanType(Module *creator) : CommandCSSetBanType(creator, "chanserv/saset/bantype") - { - } -}; - -class CSSetBanType : public Module -{ - CommandCSSetBanType commandcssetbantype; - CommandCSSASetBanType commandcssasetbantype; - - public: - CSSetBanType(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetbantype(this), commandcssasetbantype(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetbantype); - ModuleManager::RegisterService(&commandcssasetbantype); - } -}; - -MODULE_INIT(CSSetBanType) diff --git a/modules/core/cs_set_description.cpp b/modules/core/cs_set_description.cpp deleted file mode 100644 index 5c2cd447d..000000000 --- a/modules/core/cs_set_description.cpp +++ /dev/null @@ -1,89 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetDescription : public Command -{ - public: - CommandCSSetDescription(Module *creator, const Anope::string &cname = "chanserv/set/description") : Command(creator, cname, 1, 2) - { - this->SetDesc(_("Set the channel description")); - this->SetSyntax(_("\037channel\037 [\037description\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params.size() > 1) - { - ci->desc = params[1]; - source.Reply(_("Description of %s changed to \002%s\002."), ci->name.c_str(), ci->desc.c_str()); - } - else - { - ci->desc.clear(); - source.Reply(_("Description of %s unset."), ci->name.c_str()); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets the description for the channel, which shows up with\n" - "the \002LIST\002 and \002INFO\002 commands."), this->name.c_str()); - return true; - } -}; - -class CommandCSSASetDescription : public CommandCSSetDescription -{ - public: - CommandCSSASetDescription(Module *creator) : CommandCSSetDescription(creator, "chanserv/saset/description") - { - } -}; - -class CSSetDescription : public Module -{ - CommandCSSetDescription commandcssetdescription; - CommandCSSASetDescription commandcssasetdescription; - - public: - CSSetDescription(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetdescription(this), commandcssasetdescription(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetdescription); - ModuleManager::RegisterService(&commandcssasetdescription); - } -}; - -MODULE_INIT(CSSetDescription) diff --git a/modules/core/cs_set_founder.cpp b/modules/core/cs_set_founder.cpp deleted file mode 100644 index 2169af972..000000000 --- a/modules/core/cs_set_founder.cpp +++ /dev/null @@ -1,105 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetFounder : public Command -{ - public: - CommandCSSetFounder(Module *creator, const Anope::string &cname = "chanserv/set/founder") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Set the founder of a channel")); - this->SetSyntax(_("\037channel\037 \037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (source.permission.empty() && (ci->HasFlag(CI_SECUREFOUNDER) ? !IsFounder(u, ci) : !ci->HasPriv(u, CA_FOUNDER))) - { - source.Reply(ACCESS_DENIED); - return; - } - - NickAlias *na = findnick(params[1]); - - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, params[1].c_str()); - return; - } - - NickCore *nc = na->nc; - if (Config->CSMaxReg && nc->channelcount >= Config->CSMaxReg && !u->HasPriv("chanserv/no-register-limit")) - { - source.Reply(_("\002%s\002 has too many channels registered."), na->nick.c_str()); - return; - } - - Log(!source.permission.empty() ? LOG_ADMIN : LOG_COMMAND, u, this, ci) << "to change the founder to " << nc->display; - - ci->SetFounder(nc); - - source.Reply(_("Founder of %s changed to \002%s\002."), ci->name.c_str(), na->nick.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the founder of a channel. The new nickname must\n" - "be a registered one."), this->name.c_str()); - return true; - } -}; - -class CommandCSSASetFounder : public CommandCSSetFounder -{ - public: - CommandCSSASetFounder(Module *creator) : CommandCSSetFounder(creator, "chanserv/saset/founder") - { - } -}; - -class CSSetFounder : public Module -{ - CommandCSSetFounder commandcssetfounder; - CommandCSSASetFounder commandcssasetfounder; - - public: - CSSetFounder(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetfounder(this), commandcssasetfounder(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetfounder); - ModuleManager::RegisterService(&commandcssasetfounder); - } -}; - -MODULE_INIT(CSSetFounder) diff --git a/modules/core/cs_set_keeptopic.cpp b/modules/core/cs_set_keeptopic.cpp deleted file mode 100644 index 05578a2e5..000000000 --- a/modules/core/cs_set_keeptopic.cpp +++ /dev/null @@ -1,94 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetKeepTopic : public Command -{ - public: - CommandCSSetKeepTopic(Module *creator, const Anope::string &cname = "chanserv/set/keeptopic") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Retain topic when channel is not in use")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_KEEPTOPIC); - source.Reply(_("Topic retention option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_KEEPTOPIC); - source.Reply(_("Topic retention option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "KEEPTOPIC"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002topic retention\002 option for a \n" - "channel. When \002topic retention\002 is set, the topic for the\n" - "channel will be remembered by %s even after the\n" - "last user leaves the channel, and will be restored the\n" - "next time the channel is created."), this->name.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSSASetKeepTopic : public CommandCSSetKeepTopic -{ - public: - CommandCSSASetKeepTopic(Module *creator) : CommandCSSetKeepTopic(creator, "chanserv/saset/keeptopic") - { - } -}; - -class CSSetKeepTopic : public Module -{ - CommandCSSetKeepTopic commandcssetkeeptopic; - CommandCSSASetKeepTopic commandcssasetkeeptopic; - - public: - CSSetKeepTopic(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetkeeptopic(this), commandcssasetkeeptopic(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetkeeptopic); - ModuleManager::RegisterService(&commandcssasetkeeptopic); - } -}; - -MODULE_INIT(CSSetKeepTopic) diff --git a/modules/core/cs_set_opnotice.cpp b/modules/core/cs_set_opnotice.cpp deleted file mode 100644 index 018b89437..000000000 --- a/modules/core/cs_set_opnotice.cpp +++ /dev/null @@ -1,93 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetOpNotice : public Command -{ - public: - CommandCSSetOpNotice(Module *creator, const Anope::string &cname = "chanserv/set/notice") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Send a notice when OP/DEOP commands are used")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_OPNOTICE); - source.Reply(_("Op-notice option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_OPNOTICE); - source.Reply(_("Op-notice option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "OPNOTICE"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002op-notice\002 option for a channel.\n" - "When \002op-notice\002 is set, %s will send a notice to the\n" - "channel whenever the \002OP\002 or \002DEOP\002 commands are used for a user\n" - "in the channel."), this->name.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSSASetOpNotice : public CommandCSSetOpNotice -{ - public: - CommandCSSASetOpNotice(Module *creator) : CommandCSSetOpNotice(creator, "chanserv/saset/opnotice") - { - } -}; - -class CSSetOpNotice : public Module -{ - CommandCSSetOpNotice commandcssetopnotice; - CommandCSSASetOpNotice commandcssasetopnotice; - - public: - CSSetOpNotice(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetopnotice(this), commandcssasetopnotice(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetopnotice); - ModuleManager::RegisterService(&commandcssasetopnotice); - } -}; - -MODULE_INIT(CSSetOpNotice) diff --git a/modules/core/cs_set_peace.cpp b/modules/core/cs_set_peace.cpp deleted file mode 100644 index 3a045fc6d..000000000 --- a/modules/core/cs_set_peace.cpp +++ /dev/null @@ -1,93 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetPeace : public Command -{ - public: - CommandCSSetPeace(Module *creator, const Anope::string &cname = "chanserv/set/peace") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Regulate the use of critical commands")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_PEACE); - source.Reply(_("Peace option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_PEACE); - source.Reply(_("Peace option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "PEACE"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002peace\002 option for a channel.\n" - "When \002peace\002 is set, a user won't be able to kick,\n" - "ban or remove a channel status of a user that has\n" - "a level superior or equal to his via %s commands."), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSSASetPeace : public CommandCSSetPeace -{ - public: - CommandCSSASetPeace(Module *creator) : CommandCSSetPeace(creator, "chanserv/saset/peace") - { - } -}; - -class CSSetPeace : public Module -{ - CommandCSSetPeace commandcssetpeace; - CommandCSSASetPeace commandcssasetpeace; - - public: - CSSetPeace(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetpeace(this), commandcssasetpeace(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetpeace); - ModuleManager::RegisterService(&commandcssasetpeace); - } -}; - -MODULE_INIT(CSSetPeace) diff --git a/modules/core/cs_set_persist.cpp b/modules/core/cs_set_persist.cpp deleted file mode 100644 index 3cc9564c4..000000000 --- a/modules/core/cs_set_persist.cpp +++ /dev/null @@ -1,180 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetPersist : public Command -{ - public: - CommandCSSetPersist(Module *creator, const Anope::string &cname = "chanserv/set/persist") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Set the channel as permanent")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - ChannelMode *cm = ModeManager::FindChannelModeByName(CMODE_PERM); - - if (params[1].equals_ci("ON")) - { - if (!ci->HasFlag(CI_PERSIST)) - { - ci->SetFlag(CI_PERSIST); - if (ci->c) - ci->c->SetFlag(CH_PERSIST); - - /* Channel doesn't exist, create it */ - if (!ci->c) - { - Channel *c = new Channel(ci->name); - if (ci->bi) - ci->bi->Join(c); - } - - /* No botserv bot, no channel mode */ - /* Give them ChanServ - * Yes, this works fine with no Config->s_BotServ - */ - if (!ci->bi && !cm) - { - BotInfo *bi = findbot(Config->ChanServ); - if (!bi) - { - source.Reply(_("ChanServ is required to enable persist on this network.")); - return; - } - bi->Assign(NULL, ci); - if (!ci->c->FindUser(bi)) - bi->Join(ci->c); - } - - /* Set the perm mode */ - if (cm) - { - if (ci->c && !ci->c->HasMode(CMODE_PERM)) - ci->c->SetMode(NULL, cm); - /* Add it to the channels mlock */ - ci->SetMLock(cm, true); - } - } - - source.Reply(_("Channel \002%s\002 is now persistant."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - if (ci->HasFlag(CI_PERSIST)) - { - ci->UnsetFlag(CI_PERSIST); - if (ci->c) - ci->c->UnsetFlag(CH_PERSIST); - - /* Unset perm mode */ - if (cm) - { - if (ci->c && ci->c->HasMode(CMODE_PERM)) - ci->c->RemoveMode(NULL, cm); - /* Remove from mlock */ - ci->RemoveMLock(cm); - } - - /* No channel mode, no BotServ, but using ChanServ as the botserv bot - * which was assigned when persist was set on - */ - if (!cm && Config->BotServ.empty() && ci->bi) - { - BotInfo *bi = findbot(Config->ChanServ); - if (!bi) - { - source.Reply(_("ChanServ is required to enable persist on this network.")); - return; - } - /* Unassign bot */ - bi->UnAssign(NULL, ci); - } - } - - source.Reply(_("Channel \002%s\002 is no longer persistant."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "PERSIST"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the persistant channel setting.\n" - "When persistant is set, the service bot will remain\n" - "in the channel when it has emptied of users.\n" - " \n" - "If your IRCd does not a permanent (persistant) channel\n" - "mode you must have a service bot in your channel to\n" - "set persist on, and it can not be unassigned while persist\n" - "is on.\n" - " \n" - "If this network does not have BotServ enabled and does\n" - "not have a permanent channel mode, ChanServ will\n" - "join your channel when you set persist on (and leave when\n" - "it has been set off).\n" - " \n" - "If your IRCd has a permanent (persistant) channel mode\n" - "and is is set or unset (for any reason, including MLOCK),\n" - "persist is automatically set and unset for the channel aswell.\n" - "Additionally, services will set or unset this mode when you\n" - "set persist on or off.")); - return true; - } -}; - -class CommandCSSASetPersist : public CommandCSSetPersist -{ - public: - CommandCSSASetPersist(Module *creator) : CommandCSSetPersist(creator, "chanserv/saset/persist") - { - } -}; - -class CSSetPersist : public Module -{ - CommandCSSetPersist commandcssetpeace; - CommandCSSASetPersist commandcssasetpeace; - - public: - CSSetPersist(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetpeace(this), commandcssasetpeace(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetpeace); - ModuleManager::RegisterService(&commandcssasetpeace); - } -}; - -MODULE_INIT(CSSetPersist) diff --git a/modules/core/cs_set_private.cpp b/modules/core/cs_set_private.cpp deleted file mode 100644 index 108b11569..000000000 --- a/modules/core/cs_set_private.cpp +++ /dev/null @@ -1,93 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetPrivate : public Command -{ - public: - CommandCSSetPrivate(Module *creator, const Anope::string &cname = "chanserv/set/private") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Hide channel from LIST command")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_PRIVATE); - source.Reply(_("Private option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_PRIVATE); - source.Reply(_("Private option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "PRIVATE"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002private\002 option for a channel.\n" - "When \002private\002 is set, a \002%s%s LIST\002 will not\n" - "include the channel in any lists."), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSSASetPrivate : public CommandCSSetPrivate -{ - public: - CommandCSSASetPrivate(Module *creator) : CommandCSSetPrivate(creator, "chanserv/saset/private") - { - } -}; - -class CSSetPrivate : public Module -{ - CommandCSSetPrivate commandcssetprivate; - CommandCSSASetPrivate commandcssasetprivate; - - public: - CSSetPrivate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetprivate(this), commandcssasetprivate(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetprivate); - ModuleManager::RegisterService(&commandcssasetprivate); - } -}; - -MODULE_INIT(CSSetPrivate) diff --git a/modules/core/cs_set_restricted.cpp b/modules/core/cs_set_restricted.cpp deleted file mode 100644 index 5d675d2e7..000000000 --- a/modules/core/cs_set_restricted.cpp +++ /dev/null @@ -1,91 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetRestricted : public Command -{ - public: - CommandCSSetRestricted(Module *creator, const Anope::string &cname = "chanserv/set/restricted") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Restrict access to the channel")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_RESTRICTED); - source.Reply(_("Restricted access option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_RESTRICTED); - source.Reply(_("Restricted access option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "RESTRICTED"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002restricted access\002 option for a\n" - "channel. When \002restricted access\002 is set, users not on the access list will\n" - "instead be kicked and banned from the channel.")); - return true; - } -}; - -class CommandCSSASetRestricted : public CommandCSSetRestricted -{ - public: - CommandCSSASetRestricted(Module *creator) : CommandCSSetRestricted(creator, "chanserv/saset/restricted") - { - } -}; - -class CSSetRestricted : public Module -{ - CommandCSSetRestricted commandcssetrestricted; - CommandCSSASetRestricted commandcssasetrestricted; - - public: - CSSetRestricted(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetrestricted(this), commandcssasetrestricted(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetrestricted); - ModuleManager::RegisterService(&commandcssasetrestricted); - } -}; - -MODULE_INIT(CSSetRestricted) diff --git a/modules/core/cs_set_secure.cpp b/modules/core/cs_set_secure.cpp deleted file mode 100644 index 26e8c5768..000000000 --- a/modules/core/cs_set_secure.cpp +++ /dev/null @@ -1,94 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetSecure : public Command -{ - public: - CommandCSSetSecure(Module *creator, const Anope::string &cname = "chanserv/set/secure") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Activate security features")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_SECURE); - source.Reply(_("Secure option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_SECURE); - source.Reply(_("Secure option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "SECURE"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables security features for a\n" - "channel. When \002%s\002 is set, only users who have\n" - "registered their nicknames and IDENTIFY'd\n" - "with their password will be given access to the channel\n" - "as controlled by the access list."), this->name.c_str()); - return true; - } -}; - -class CommandCSSASetSecure : public CommandCSSetSecure -{ - public: - CommandCSSASetSecure(Module *creator) : CommandCSSetSecure(creator, "chanserv/saset/secure") - { - } -}; - -class CSSetSecure : public Module -{ - CommandCSSetSecure commandcssetsecure; - CommandCSSASetSecure commandcssasetsecure; - - public: - CSSetSecure(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetsecure(this), commandcssasetsecure(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetsecure); - ModuleManager::RegisterService(&commandcssasetsecure); - } -}; - -MODULE_INIT(CSSetSecure) diff --git a/modules/core/cs_set_securefounder.cpp b/modules/core/cs_set_securefounder.cpp deleted file mode 100644 index 7afc2e32d..000000000 --- a/modules/core/cs_set_securefounder.cpp +++ /dev/null @@ -1,95 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetSecureFounder : public Command -{ - public: - CommandCSSetSecureFounder(Module *creator, const Anope::string &cname = "chanserv/set/securefounder") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Stricter control of channel founder status")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - - if (source.permission.empty() && ci->HasFlag(CI_SECUREFOUNDER) ? !IsFounder(u, ci) : !ci->HasPriv(u, CA_FOUNDER)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_SECUREFOUNDER); - source.Reply(_("Secure founder option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_SECUREFOUNDER); - source.Reply(_("Secure founder option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "SECUREFOUNDER"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002secure founder\002 option for a channel.\n" - "When \002secure founder\002 is set, only the real founder will be\n" - "able to drop the channel, change its password, its founder and its\n" - "successor, and not those who have founder level access through\n" - "the access/qop command.")); - return true; - } -}; - -class CommandCSSASetSecureFounder : public CommandCSSetSecureFounder -{ - public: - CommandCSSASetSecureFounder(Module *creator) : CommandCSSetSecureFounder(creator, "chanserv/saset/securefounder") - { - } -}; - -class CSSetSecureFounder : public Module -{ - CommandCSSetSecureFounder commandcssetsecurefounder; - CommandCSSASetSecureFounder commandcssasetsecurefounder; - - public: - CSSetSecureFounder(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetsecurefounder(this), commandcssasetsecurefounder(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetsecurefounder); - ModuleManager::RegisterService(&commandcssasetsecurefounder); - } -}; - -MODULE_INIT(CSSetSecureFounder) diff --git a/modules/core/cs_set_secureops.cpp b/modules/core/cs_set_secureops.cpp deleted file mode 100644 index 4c3c54b05..000000000 --- a/modules/core/cs_set_secureops.cpp +++ /dev/null @@ -1,92 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetSecureOps : public Command -{ - public: - CommandCSSetSecureOps(Module *creator, const Anope::string &cname = "chanserv/set/secureops") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Stricter control of chanop status")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_SECUREOPS); - source.Reply(_("Secure ops option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_SECUREOPS); - source.Reply(_("Secure ops option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "SECUREOPS"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002secure ops\002 option for a channel.\n" - "When \002secure ops\002 is set, users who are not on the userlist\n" - "will not be allowed chanop status.")); - return true; - } -}; - -class CommandCSSASetSecureOps : public CommandCSSetSecureOps -{ - public: - CommandCSSASetSecureOps(Module *creator) : CommandCSSetSecureOps(creator, "chanserv/saset/secureops") - { - } -}; - -class CSSetSecureOps : public Module -{ - CommandCSSetSecureOps commandcssetsecureops; - CommandCSSASetSecureOps commandcssasetsecureops; - - public: - CSSetSecureOps(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetsecureops(this), commandcssasetsecureops(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetsecureops); - ModuleManager::RegisterService(&commandcssasetsecureops); - } -}; - -MODULE_INIT(CSSetSecureOps) diff --git a/modules/core/cs_set_signkick.cpp b/modules/core/cs_set_signkick.cpp deleted file mode 100644 index 0d421576d..000000000 --- a/modules/core/cs_set_signkick.cpp +++ /dev/null @@ -1,104 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetSignKick : public Command -{ - public: - CommandCSSetSignKick(Module *creator, const Anope::string &cname = "chanserv/set/signkick") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Sign kicks that are done with KICK command")); - this->SetSyntax(_("\037channel\037 SIGNKICK {ON | LEVEL | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_SIGNKICK); - ci->UnsetFlag(CI_SIGNKICK_LEVEL); - source.Reply(_("Signed kick option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("LEVEL")) - { - ci->SetFlag(CI_SIGNKICK_LEVEL); - ci->UnsetFlag(CI_SIGNKICK); - source.Reply(_("Signed kick option for %s is now \002ON\002, but depends of the\n" - "level of the user that is using the command."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_SIGNKICK); - ci->UnsetFlag(CI_SIGNKICK_LEVEL); - source.Reply(_("Signed kick option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "SIGNKICK"); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables signed kicks for a\n" - "channel. When \002SIGNKICK\002 is set, kicks issued with\n" - "KICK command will have the nick that used the\n" - "command in their reason.\n" - " \n" - "If you use \002LEVEL\002, those who have a level that is superior \n" - "or equal to the SIGNKICK level on the channel won't have their \n" - "kicks signed.")); - return true; - } -}; - -class CommandCSSASetSignKick : public CommandCSSetSignKick -{ - public: - CommandCSSASetSignKick(Module *creator) : CommandCSSetSignKick(creator, "chanserv/saset/signkick") - { - } -}; - -class CSSetSignKick : public Module -{ - CommandCSSetSignKick commandcssetsignkick; - CommandCSSASetSignKick commandcssasetsignkick; - - public: - CSSetSignKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetsignkick(this), commandcssasetsignkick(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetsignkick); - ModuleManager::RegisterService(&commandcssasetsignkick); - } -}; - -MODULE_INIT(CSSetSignKick) diff --git a/modules/core/cs_set_successor.cpp b/modules/core/cs_set_successor.cpp deleted file mode 100644 index f7ed8dba9..000000000 --- a/modules/core/cs_set_successor.cpp +++ /dev/null @@ -1,119 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetSuccessor : public Command -{ - public: - CommandCSSetSuccessor(Module *creator, const Anope::string &cname = "chanserv/set/successor") : Command(creator, cname, 1, 2) - { - this->SetDesc(_("Set the successor for a channel")); - this->SetSyntax(_("\037channel\037 \037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (source.permission.empty() && ci->HasFlag(CI_SECUREFOUNDER) ? !IsFounder(u, ci) : !ci->HasPriv(u, CA_FOUNDER)) - { - source.Reply(ACCESS_DENIED); - return; - } - - NickCore *nc; - - if (params.size() > 1) - { - NickAlias *na = findnick(params[1]); - - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, params[1].c_str()); - return; - } - if (na->nc == ci->GetFounder()) - { - source.Reply(_("%s cannot be the successor on channel %s they are the founder."), na->nick.c_str(), ci->name.c_str()); - return; - } - nc = na->nc; - } - else - nc = NULL; - - Log(!source.permission.empty() ? LOG_ADMIN : LOG_COMMAND, u, this, ci) << "to change the successor from " << (ci->successor ? ci->successor->display : "none") << " to " << (nc ? nc->display : "none"); - - ci->successor = nc; - - if (nc) - source.Reply(_("Successor for %s changed to \002%s\002."), ci->name.c_str(), nc->display.c_str()); - else - source.Reply(_("Successor for \002%s\002 unset."), ci->name.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the successor of a channel. If the founder's\n" - "nickname expires or is dropped while the channel is still\n" - "registered, the successor will become the new founder of the\n" - "channel. However, if the successor already has too many\n" - "channels registered (%d), the channel will be dropped\n" - "instead, just as if no successor had been set. The new\n" - "nickname must be a registered one."), Config->CSMaxReg); - return true; - } -}; - -class CommandCSSASetSuccessor : public CommandCSSetSuccessor -{ - public: - CommandCSSASetSuccessor(Module *creator) : CommandCSSetSuccessor(creator, "chanserv/saset/successor") - { - } -}; - -class CSSetSuccessor : public Module -{ - CommandCSSetSuccessor commandcssetsuccessor; - CommandCSSASetSuccessor commandcssasetsuccessor; - - public: - CSSetSuccessor(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssetsuccessor(this), commandcssasetsuccessor(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssetsuccessor); - ModuleManager::RegisterService(&commandcssasetsuccessor); - } -}; - -MODULE_INIT(CSSetSuccessor) diff --git a/modules/core/cs_set_topiclock.cpp b/modules/core/cs_set_topiclock.cpp deleted file mode 100644 index e670385ba..000000000 --- a/modules/core/cs_set_topiclock.cpp +++ /dev/null @@ -1,92 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSetTopicLock : public Command -{ - public: - CommandCSSetTopicLock(Module *creator, const Anope::string &cname = "chanserv/set/topiclock") : Command(creator, cname, 2, 2) - { - this->SetDesc(_("Topic can only be changed with TOPIC")); - this->SetSyntax(_("\037channel\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (source.permission.empty() && !ci->HasPriv(u, CA_SET)) - { - source.Reply(ACCESS_DENIED); - return; - } - - if (params[1].equals_ci("ON")) - { - ci->SetFlag(CI_TOPICLOCK); - source.Reply(_("Topic lock option for %s is now \002on\002."), ci->name.c_str()); - } - else if (params[1].equals_ci("OFF")) - { - ci->UnsetFlag(CI_TOPICLOCK); - source.Reply(_("Topic lock option for %s is now \002off\002."), ci->name.c_str()); - } - else - this->OnSyntaxError(source, "TOPICLOCK"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Enables or disables the \002topic lock\002 option for a channel.\n" - "When \002topic lock\002 is set, the channel topic will be unchangable\n" - " except via the \002TOPIC\002 command.")); - return true; - } -}; - -class CommandCSSASetTopicLock : public CommandCSSetTopicLock -{ - public: - CommandCSSASetTopicLock(Module *creator) : CommandCSSetTopicLock(creator, "chanserv/saset/topiclock") - { - } -}; - -class CSSetTopicLock : public Module -{ - CommandCSSetTopicLock commandcssettopiclock; - CommandCSSASetTopicLock commandcssasettopiclock; - - public: - CSSetTopicLock(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssettopiclock(this), commandcssasettopiclock(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssettopiclock); - ModuleManager::RegisterService(&commandcssasettopiclock); - } -}; - -MODULE_INIT(CSSetTopicLock) diff --git a/modules/core/cs_suspend.cpp b/modules/core/cs_suspend.cpp deleted file mode 100644 index d59ffb44b..000000000 --- a/modules/core/cs_suspend.cpp +++ /dev/null @@ -1,158 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSSuspend : public Command -{ - public: - CommandCSSuspend(Module *creator) : Command(creator, "chanserv/suspend", 1, 2) - { - this->SetDesc(_("Prevent a channel from being used preserving channel data and settings")); - this->SetSyntax(_("\037channel\037 [\037reason\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &reason = params.size() > 1 ? params[1] : ""; - - User *u = source.u; - - if (Config->ForceForbidReason && reason.empty()) - { - this->OnSyntaxError(source, ""); - return; - } - - if (readonly) - source.Reply(READ_ONLY_MODE); - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - ci->SetFlag(CI_SUSPENDED); - ci->Extend("suspend_by", new ExtensibleItemRegular<Anope::string>(u->nick)); - if (!reason.empty()) - ci->Extend("suspend_reason", new ExtensibleItemRegular<Anope::string>(u->nick)); - - if (ci->c) - { - for (CUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ) - { - UserContainer *uc = *it++; - - if (uc->user->HasMode(UMODE_OPER)) - continue; - - ci->c->Kick(NULL, uc->user, "%s", !reason.empty() ? reason.c_str() : translate(uc->user, _("This channel has been suspended."))); - } - } - - Log(LOG_ADMIN, u, this, ci) << (!reason.empty() ? reason : "No reason"); - source.Reply(_("Channel \002%s\002 is now suspended."), ci->name.c_str()); - - FOREACH_MOD(I_OnChanSuspend, OnChanSuspend(ci)); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Disallows anyone from using the given channel.\n" - "May be cancelled by using the UNSUSPEND\n" - "command to preserve all previous channel data/settings.\n" - " \n" - "Reason may be required on certain networks.")); - return true; - } -}; - -class CommandCSUnSuspend : public Command -{ - public: - CommandCSUnSuspend(Module *creator) : Command(creator, "chanserv/unsuspend", 1, 1) - { - this->SetDesc(_("Releases a suspended channel")); - this->SetSyntax(_("\037channel\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - if (readonly) - source.Reply(READ_ONLY_MODE); - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - /* Only UNSUSPEND already suspended channels */ - if (!ci->HasFlag(CI_SUSPENDED)) - { - source.Reply(_("Couldn't release channel \002%s\002!"), ci->name.c_str()); - return; - } - - Anope::string by, reason; - ci->GetExtRegular("suspend_by", by); - ci->GetExtRegular("suspend_reason", reason); - Log(LOG_ADMIN, u, this, ci) << " which was suspended by " << by << " for: " << (!reason.empty() ? reason : "No reason"); - - ci->UnsetFlag(CI_SUSPENDED); - ci->Shrink("suspend_by"); - ci->Shrink("suspend_reason"); - - source.Reply(_("Channel \002%s\002 is now released."), ci->name.c_str()); - - FOREACH_MOD(I_OnChanUnsuspend, OnChanUnsuspend(ci)); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Releases a suspended channel. All data and settings\n" - "are preserved from before the suspension.")); - return true; - } -}; - -class CSSuspend : public Module -{ - CommandCSSuspend commandcssuspend; - CommandCSUnSuspend commandcsunsuspend; - - public: - CSSuspend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcssuspend(this), commandcsunsuspend(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcssuspend); - ModuleManager::RegisterService(&commandcsunsuspend); - } -}; - -MODULE_INIT(CSSuspend) diff --git a/modules/core/cs_topic.cpp b/modules/core/cs_topic.cpp deleted file mode 100644 index 1b5de11c3..000000000 --- a/modules/core/cs_topic.cpp +++ /dev/null @@ -1,84 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSTopic : public Command -{ - public: - CommandCSTopic(Module *creator) : Command(creator, "chanserv/topic", 1, 2) - { - this->SetDesc(_("Manipulate the topic of the specified channel")); - this->SetSyntax(_("\037channel\037 [\037topic\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &topic = params.size() > 1 ? params[1] : ""; - - User *u = source.u; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (!ci->c) - source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); - else if (!ci->HasPriv(u, CA_TOPIC) && !u->HasCommand("chanserv/chanserv/topic")) - source.Reply(ACCESS_DENIED); - else - { - bool has_topiclock = ci->HasFlag(CI_TOPICLOCK); - ci->UnsetFlag(CI_TOPICLOCK); - ci->c->ChangeTopic(u->nick, topic, Anope::CurTime); - if (has_topiclock) - ci->SetFlag(CI_TOPICLOCK); - - bool override = !ci->HasPriv(u, CA_TOPIC); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "to change the topic to " << (!topic.empty() ? topic : "No topic"); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Causes %s to set the channel topic to the one\n" - "specified. If \002topic\002 is not given, then an empty topic\n" - "is set. This command is most useful in conjunction\n" - "with topic lock.\n" - "By default, limited to those with founder access on the\n" - "channel."), source.owner->nick.c_str()); - return true; - } -}; - -class CSTopic : public Module -{ - CommandCSTopic commandcstopic; - - public: - CSTopic(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcstopic(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcstopic); - } -}; - -MODULE_INIT(CSTopic) diff --git a/modules/core/cs_unban.cpp b/modules/core/cs_unban.cpp deleted file mode 100644 index cc3c68e91..000000000 --- a/modules/core/cs_unban.cpp +++ /dev/null @@ -1,94 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandCSUnban : public Command -{ - public: - CommandCSUnban(Module *creator) : Command(creator, "chanserv/unban", 1, 2) - { - this->SetDesc(_("Remove all bans preventing a user from entering a channel")); - this->SetSyntax(_("\037channel\037 [\037nick\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - if (ci->c == NULL) - { - source.Reply(CHAN_X_NOT_IN_USE, ci->name.c_str()); - return; - } - - if (!ci->HasPriv(u, CA_UNBAN)) - { - source.Reply(ACCESS_DENIED); - return; - } - - User *u2 = u; - if (params.size() > 1) - u2 = finduser(params[1]); - - if (!u2) - { - source.Reply(NICK_X_NOT_IN_USE, params[1].c_str()); - return; - } - - common_unban(ci, u2, u == u2); - if (u2 == u) - source.Reply(_("You have been unbanned from \002%s\002."), ci->c->name.c_str()); - else - source.Reply(_("\002%s\002 has been unbanned from \002%s\002."), u2->nick.c_str(), ci->c->name.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Tells %s to remove all bans preventing you or the given\n" - "user from entering the given channel. \n" - " \n" - "By default, limited to AOPs or those with level 5 and above\n" - "on the channel."), source.owner->nick.c_str()); - return true; - } -}; - -class CSUnban : public Module -{ - CommandCSUnban commandcsunban; - - public: - CSUnban(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandcsunban(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandcsunban); - } -}; - -MODULE_INIT(CSUnban) diff --git a/modules/core/cs_xop.cpp b/modules/core/cs_xop.cpp deleted file mode 100644 index 1b9348026..000000000 --- a/modules/core/cs_xop.cpp +++ /dev/null @@ -1,880 +0,0 @@ -/* ChanServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -enum XOPType -{ - XOP_QOP, - XOP_SOP, - XOP_AOP, - XOP_HOP, - XOP_VOP, - XOP_UNKNOWN -}; - -static struct XOPAccess -{ - XOPType type; - Anope::string name; - ChannelAccess access[CA_SIZE]; -} xopAccess[] = { - { XOP_QOP, "QOP", - { - CA_SIGNKICK, - CA_SET, - CA_AUTOOWNER, - CA_OWNERME, - CA_PROTECT, - CA_INFO, - CA_SIZE - } - }, - { XOP_SOP, "SOP", - { - CA_AUTOPROTECT, - CA_AKICK, - CA_BADWORDS, - CA_ASSIGN, - CA_MEMO, - CA_ACCESS_CHANGE, - CA_PROTECTME, - CA_OPDEOP, - CA_SIZE - } - }, - { XOP_AOP, "AOP", - { - CA_TOPIC, - CA_MODE, - CA_GETKEY, - CA_INVITE, - CA_UNBAN, - CA_AUTOOP, - CA_OPDEOPME, - CA_HALFOP, - CA_SAY, - CA_NOKICK, - CA_SIZE - } - }, - { XOP_HOP, "HOP", - { - CA_AUTOHALFOP, - CA_HALFOPME, - CA_KICK, - CA_BAN, - CA_FANTASIA, - CA_SIZE - } - }, - { XOP_VOP, "VOP", - { - CA_AUTOVOICE, - CA_VOICEME, - CA_ACCESS_LIST, - CA_SIZE - } - }, - { XOP_UNKNOWN, "", { } - } -}; - -class XOPChanAccess : public ChanAccess -{ - public: - XOPType type; - - XOPChanAccess(AccessProvider *p) : ChanAccess(p) - { - } - - bool Matches(User *u, NickCore *nc) - { - if (u && (Anope::Match(u->nick, this->mask) || Anope::Match(u->GetMask(), this->mask))) - return true; - else if (nc && Anope::Match(nc->display, this->mask)) - return true; - return false; - } - - bool HasPriv(ChannelAccess priv) - { - for (int i = 0; xopAccess[i].type != XOP_UNKNOWN; ++i) - { - XOPAccess &x = xopAccess[i]; - - if (this->type > x.type) - continue; - - for (int j = 0; x.access[j] != CA_SIZE; ++j) - if (x.access[j] == priv) - return true; - } - - return false; - } - - Anope::string Serialize() - { - for (int i = 0; xopAccess[i].type != XOP_UNKNOWN; ++i) - { - XOPAccess &x = xopAccess[i]; - - if (this->type == x.type) - return x.name; - } - - return ""; - } - - void Unserialize(const Anope::string &data) - { - for (int i = 0; xopAccess[i].type != XOP_UNKNOWN; ++i) - { - XOPAccess &x = xopAccess[i]; - - if (data == x.name) - { - this->type = x.type; - return; - } - } - - this->type = XOP_UNKNOWN; - } - - static XOPType DetermineLevel(ChanAccess *access) - { - if (access->provider->name == "access/xop") - { - XOPChanAccess *xaccess = debug_cast<XOPChanAccess *>(access); - return xaccess->type; - } - else - { - int count[XOP_UNKNOWN]; - for (int i = 0; i < XOP_UNKNOWN; ++i) - count[i] = 0; - - for (int i = 0; xopAccess[i].type != XOP_UNKNOWN; ++i) - { - XOPAccess &x = xopAccess[i]; - - for (int j = 0; x.access[j] != CA_SIZE; ++j) - if (access->HasPriv(x.access[j])) - ++count[x.type]; - } - - XOPType max = XOP_UNKNOWN; - int maxn = 0; - for (int i = 0; i < XOP_UNKNOWN; ++i) - if (count[i] > maxn) - { - max = static_cast<XOPType>(i); - maxn = count[i]; - } - - return max; - } - } -}; - -class XOPAccessProvider : public AccessProvider -{ - public: - XOPAccessProvider(Module *o) : AccessProvider(o, "access/xop") - { - } - - ChanAccess *Create() - { - return new XOPChanAccess(this); - } -}; - -class XOPListCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - XOPType type; - Command *c; - bool SentHeader; - public: - XOPListCallback(CommandSource &_source, ChannelInfo *_ci, const Anope::string &numlist, XOPType _type, Command *_c) : NumberList(numlist, false), source(_source), ci(_ci), type(_type), c(_c), SentHeader(false) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAccessCount()) - return; - - ChanAccess *access = ci->GetAccess(Number - 1); - - if (this->type != XOPChanAccess::DetermineLevel(access)) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("%s list for %s:\n Num Nick"), source.command.c_str(), ci->name.c_str()); - } - - DoList(source, access, Number - 1, this->type); - } - - static void DoList(CommandSource &source, ChanAccess *access, unsigned index, XOPType type) - { - source.Reply(_(" %3d %s"), index, access->mask.c_str()); - } -}; - -class XOPDelCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - Command *c; - unsigned Deleted; - Anope::string Nicks; - bool override; - XOPType type; - public: - XOPDelCallback(CommandSource &_source, ChannelInfo *_ci, Command *_c, bool _override, XOPType _type, const Anope::string &numlist) : NumberList(numlist, true), source(_source), ci(_ci), c(_c), Deleted(0), override(_override), type(_type) - { - } - - ~XOPDelCallback() - { - if (!Deleted) - source.Reply(_("No matching entries on %s %s list."), ci->name.c_str(), source.command.c_str()); - else - { - Log(override ? LOG_OVERRIDE : LOG_COMMAND, source.u, c, ci) << "deleted access of users " << Nicks; - - if (Deleted == 1) - source.Reply(_("Deleted one entry from %s %s list."), ci->name.c_str(), source.command.c_str()); - else - source.Reply(_("Deleted %d entries from %s %s list."), Deleted, ci->name.c_str(), source.command.c_str()); - } - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > ci->GetAccessCount()) - return; - - ChanAccess *access = ci->GetAccess(Number - 1); - - if (this->type != XOPChanAccess::DetermineLevel(access)) - return; - - ++Deleted; - if (!Nicks.empty()) - Nicks += ", " + access->mask; - else - Nicks = access->mask; - - FOREACH_MOD(I_OnAccessDel, OnAccessDel(ci, source.u, access)); - - ci->EraseAccess(Number - 1); - } -}; - -class XOPBase : public Command -{ - private: - void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms, XOPType level) - { - User *u = source.u; - - Anope::string mask = params.size() > 2 ? params[2] : ""; - - if (mask.empty()) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - if (readonly) - { - source.Reply(_("Sorry, channel %s list modification is temporarily disabled."), source.command.c_str()); - return; - } - - AccessGroup access = ci->AccessFor(u); - ChanAccess *highest = access.Highest(); - int u_level = (highest ? XOPChanAccess::DetermineLevel(highest) : 0); - - if (((access.HasPriv(CA_FOUNDER) || level >= u_level) || !access.HasPriv(CA_ACCESS_CHANGE)) && !u->HasPriv("chanserv/access/modify")) - { - source.Reply(ACCESS_DENIED); - return; - } - - for (unsigned i = 0; i < ci->GetAccessCount(); ++i) - { - ChanAccess *a = ci->GetAccess(i); - - if (a->mask.equals_ci(mask)) - { - if (XOPChanAccess::DetermineLevel(a) >= u_level && !u->HasPriv("chanserv/access/modify")) - { - source.Reply(ACCESS_DENIED); - return; - } - - ci->EraseAccess(i); - break; - } - } - - if (ci->GetAccessCount() >= Config->CSAccessMax) - { - source.Reply(_("Sorry, you can only have %d %s entries on a channel."), Config->CSAccessMax, source.command.c_str()); - return; - } - - if (mask.find_first_of("!*@") == Anope::string::npos && findnick(mask) == NULL) - mask += "!*@*"; - - service_reference<AccessProvider> provider("access/xop"); - if (!provider) - return; - XOPChanAccess *acc = debug_cast<XOPChanAccess *>(provider->Create()); - acc->ci = ci; - acc->mask = mask; - acc->creator = u->nick; - acc->type = level; - acc->last_seen = 0; - acc->created = Anope::CurTime; - ci->AddAccess(acc); - - bool override = level >= u_level || !access.HasPriv(CA_ACCESS_CHANGE); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "ADD " << mask << " as level " << level; - - FOREACH_MOD(I_OnAccessAdd, OnAccessAdd(ci, u, acc)); - source.Reply(("\002%s\002 added to %s %s list."), acc->mask.c_str(), ci->name.c_str(), source.command.c_str()); - } - - void DoDel(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms, XOPType level) - { - User *u = source.u; - - const Anope::string &mask = params.size() > 2 ? params[2] : ""; - - if (mask.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (readonly) - { - source.Reply(_("Sorry, channel %s list modification is temporarily disabled."), source.command.c_str()); - return; - } - - if (!ci->GetAccessCount()) - { - source.Reply(_("%s %s list is empty."), ci->name.c_str(), source.command.c_str()); - return; - } - - AccessGroup access = ci->AccessFor(u); - ChanAccess *highest = access.Highest(); - bool override = false; - if (!mask.equals_ci(u->Account()->display) && !access.HasPriv(CA_ACCESS_CHANGE) && (!highest || level >= XOPChanAccess::DetermineLevel(highest))) - { - if (u->HasPriv("chanserv/access/modify")) - override = true; - else - { - source.Reply(ACCESS_DENIED); - return; - } - } - - /* Special case: is it a number/list? Only do search if it isn't. */ - if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - XOPDelCallback list(source, ci, this, override, level, mask); - list.Process(); - } - else - { - for (unsigned i = 0; i < ci->GetAccessCount(); ++i) - { - ChanAccess *a = ci->GetAccess(i); - - if (a->mask.equals_ci(mask) && XOPChanAccess::DetermineLevel(a) == level) - { - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "DEL " << a->mask; - - source.Reply(_("\002%s\002 deleted from %s %s list."), a->mask.c_str(), ci->name.c_str(), source.command.c_str()); - - FOREACH_MOD(I_OnAccessDel, OnAccessDel(ci, u, a)); - ci->EraseAccess(a); - - return; - } - } - - source.Reply(_("\002%s\002 not found on %s %s list."), mask.c_str(), ci->name.c_str(), source.command.c_str()); - } - } - - void DoList(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms, XOPType level) - { - User *u = source.u; - - const Anope::string &nick = params.size() > 2 ? params[2] : ""; - - AccessGroup access = ci->AccessFor(u); - bool override = false; - - if (!access.HasPriv(CA_ACCESS_LIST)) - { - if (u->HasCommand("chanserv/access/list")) - override = true; - else - { - source.Reply(ACCESS_DENIED); - return; - } - } - - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci); - - if (!ci->GetAccessCount()) - { - source.Reply(_("%s %s list is empty."), ci->name.c_str(), source.command.c_str()); - return; - } - - if (!nick.empty() && nick.find_first_not_of("1234567890,-") == Anope::string::npos) - { - XOPListCallback list(source, ci, nick, level, this); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = ci->GetAccessCount(); i < end; ++i) - { - ChanAccess *a = ci->GetAccess(i); - - if (XOPChanAccess::DetermineLevel(a) != level) - continue; - else if (!nick.empty() && !Anope::Match(a->mask, nick)) - continue; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("%s list for %s:\n Num Nick"), source.command.c_str(), ci->name.c_str()); - } - - XOPListCallback::DoList(source, a, i + 1, level); - } - - if (!SentHeader) - source.Reply(_("No matching entries on %s %s list."), ci->name.c_str(), source.command.c_str()); - } - - return; - } - - void DoClear(CommandSource &source, ChannelInfo *ci, XOPType level) - { - User *u = source.u; - - if (readonly) - { - source.Reply(_("Sorry, channel %s list modification is temporarily disabled."), source.command.c_str()); - return; - } - - if (!ci->GetAccessCount()) - { - source.Reply(_("%s %s list is empty."), ci->name.c_str(), source.command.c_str()); - return; - } - - if (!ci->HasPriv(u, CA_FOUNDER) && !u->HasPriv("chanserv/access/modify")) - { - source.Reply(ACCESS_DENIED); - return; - } - - bool override = !ci->HasPriv(u, CA_FOUNDER); - Log(override ? LOG_OVERRIDE : LOG_COMMAND, u, this, ci) << "CLEAR level " << level; - - for (unsigned i = ci->GetAccessCount(); i > 0; --i) - { - ChanAccess *access = ci->GetAccess(i - 1); - if (XOPChanAccess::DetermineLevel(access) == level) - ci->EraseAccess(i - 1); - } - - FOREACH_MOD(I_OnAccessClear, OnAccessClear(ci, u)); - - source.Reply(_("Channel %s %s list has been cleared."), ci->name.c_str(), source.command.c_str()); - - return; - } - - protected: - void DoXop(CommandSource &source, const std::vector<Anope::string> ¶ms, XOPType level) - { - ChannelInfo *ci = cs_findchan(params[0]); - if (ci == NULL) - { - source.Reply(CHAN_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - const Anope::string &cmd = params[1]; - - if (cmd.equals_ci("ADD")) - return this->DoAdd(source, ci, params, level); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, ci, params, level); - else if (cmd.equals_ci("LIST")) - return this->DoList(source, ci, params, level); - else if (cmd.equals_ci("CLEAR")) - return this->DoClear(source, ci, level); - else - this->OnSyntaxError(source, ""); - - return; - } - public: - XOPBase(Module *modname, const Anope::string &command) : Command(modname, command, 2, 4) - { - this->SetSyntax("\037channel\037 ADD \037mask\037"); - this->SetSyntax("\037channel\037 DEL {\037mask\037 | \037entry-num\037 | \037list\037}"); - this->SetSyntax("\037channel\037 LIST [\037mask\037 | \037list\037]"); - this->SetSyntax("\037channel\037 CLEAR"); - } - - virtual ~XOPBase() - { - } - - virtual void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) = 0; - - virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand) = 0; -}; - -class CommandCSQOP : public XOPBase -{ - public: - CommandCSQOP(Module *creator) : XOPBase(creator, "chanserv/qop") - { - this->SetDesc(_("Modify the list of QOP users")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoXop(source, params, XOP_QOP); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002QOP\002 (AutoOwner) \002list\002 for a channel. The QOP \n" - "list gives users the right to be auto-owner on your channel,\n" - "which gives them almost (or potentially, total) access.\n" - " \n" - "The \002QOP ADD\002 command adds the given nickname to the\n" - "QOP list.\n" - " \n" - "The \002QOP DEL\002 command removes the given nick from the\n" - "QOP list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - " \n" - "The \002QOP LIST\002 command displays the QOP list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002QOP #channel LIST 2-5,7-9\002\n" - " Lists QOP entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002QOP CLEAR\002 command clears all entries of the\n" - "QOP list.\n")); - source.Reply(_(" \n" - "The \002QOP\002 commands are limited to\n" - "founders (unless SECUREOPS is off). However, any user on the\n" - "QOP list may use the \002QOP LIST\002 command.\n" - " \n")); - source.Reply(_("This command may have been disabled for your channel, and\n" - "in that case you need to use the access list. See \n" - "\002%s%s HELP ACCESS\002 for information about the access list,\n" - "and \002%s%s HELP SET XOP\002 to know how to toggle between \n" - "the access list and xOP list systems."), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSAOP : public XOPBase -{ - public: - CommandCSAOP(Module *creator) : XOPBase(creator, "chanserv/aop") - { - this->SetDesc(_("Modify the list of AOP users")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoXop(source, params, XOP_AOP); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002AOP\002 (AutoOP) \002list\002 for a channel. The AOP \n" - "list gives users the right to be auto-opped on your channel,\n" - "to unban or invite themselves if needed, to have their\n" - "greet message showed on join, and so on.\n" - " \n" - "The \002AOP ADD\002 command adds the given nickname to the\n" - "AOP list.\n" - " \n" - "The \002AOP DEL\002 command removes the given nick from the\n" - "AOP list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - " \n" - "The \002AOP LIST\002 command displays the AOP list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002AOP #channel LIST 2-5,7-9\002\n" - " Lists AOP entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002AOP CLEAR\002 command clears all entries of the\n" - "AOP list.\n")); - source.Reply(_(" \n" - "The \002AOP ADD\002 and \002AOP DEL\002 commands are limited to\n" - "SOPs or above, while the \002AOP CLEAR\002 command can only\n" - "be used by the channel founder. However, any user on the\n" - "AOP list may use the \002AOP LIST\002 command.\n" - " \n")); - source.Reply(_("This command may have been disabled for your channel, and\n" - "in that case you need to use the access list. See \n" - "\002%s%s HELP ACCESS\002 for information about the access list,\n" - "and \002%s%s HELP SET XOP\002 to know how to toggle between \n" - "the access list and xOP list systems."), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSHOP : public XOPBase -{ - public: - CommandCSHOP(Module *creator) : XOPBase(creator, "chanserv/hop") - { - this->SetDesc(_("Maintains the HOP (HalfOP) list for a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoXop(source, params, XOP_HOP); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002HOP\002 (HalfOP) \002list\002 for a channel. The HOP \n" - "list gives users the right to be auto-halfopped on your \n" - "channel.\n" - " \n" - "The \002HOP ADD\002 command adds the given nickname to the\n" - "HOP list.\n" - " \n" - "The \002HOP DEL\002 command removes the given nick from the\n" - "HOP list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - " \n" - "The \002HOP LIST\002 command displays the HOP list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002HOP #channel LIST 2-5,7-9\002\n" - " Lists HOP entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002HOP CLEAR\002 command clears all entries of the\n" - "HOP list.\n")); - source.Reply(_(" \n" - "The \002HOP ADD\002, \002HOP DEL\002 and \002HOP LIST\002 commands are \n" - "limited to AOPs or above, while the \002HOP CLEAR\002 command \n" - "can only be used by the channel founder.\n" - " \n")); - source.Reply(_("This command may have been disabled for your channel, and\n" - "in that case you need to use the access list. See \n" - "\002%s%s HELP ACCESS\002 for information about the access list,\n" - "and \002%s%s HELP SET XOP\002 to know how to toggle between \n" - "the access list and xOP list systems."), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSSOP : public XOPBase -{ - public: - CommandCSSOP(Module *creator) : XOPBase(creator, "chanserv/sop") - { - this->SetDesc(_("Modify the list of SOP users")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoXop(source, params, XOP_SOP); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002SOP\002 (SuperOP) \002list\002 for a channel. The SOP \n" - "list gives users all rights given by the AOP list, and adds\n" - "those needed to use the AutoKick and the BadWords lists, \n" - "to send and read channel memos, and so on.\n" - " \n" - "The \002SOP ADD\002 command adds the given nickname to the\n" - "SOP list.\n" - " \n" - "The \002SOP DEL\002 command removes the given nick from the\n" - "SOP list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - " \n" - "The \002SOP LIST\002 command displays the SOP list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002SOP #channel LIST 2-5,7-9\002\n" - " Lists AOP entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002SOP CLEAR\002 command clears all entries of the\n" - "SOP list.\n")); - source.Reply(_( - " \n" - "The \002SOP ADD\002, \002SOP DEL\002 and \002SOP CLEAR\002 commands are \n" - "limited to the channel founder. However, any user on the\n" - "AOP list may use the \002SOP LIST\002 command.\n" - " \n")); - source.Reply(_("This command may have been disabled for your channel, and\n" - "in that case you need to use the access list. See \n" - "\002%s%s HELP ACCESS\002 for information about the access list,\n" - "and \002%s%s HELP SET XOP\002 to know how to toggle between \n" - "the access list and xOP list systems."), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CommandCSVOP : public XOPBase -{ - public: - CommandCSVOP(Module *creator) : XOPBase(creator, "chanserv/vop") - { - this->SetDesc(_("Maintains the VOP (VOicePeople) list for a channel")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoXop(source, params, XOP_VOP); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Maintains the \002VOP\002 (VOicePeople) \002list\002 for a channel. \n" - "The VOP list allows users to be auto-voiced and to voice \n" - "themselves if they aren't.\n" - " \n" - "The \002VOP ADD\002 command adds the given nickname to the\n" - "VOP list.\n" - " \n" - "The \002VOP DEL\002 command removes the given nick from the\n" - "VOP list. If a list of entry numbers is given, those\n" - "entries are deleted. (See the example for LIST below.)\n" - " \n" - "The \002VOP LIST\002 command displays the VOP list. If\n" - "a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002VOP #channel LIST 2-5,7-9\002\n" - " Lists VOP entries numbered 2 through 5 and\n" - " 7 through 9.\n" - " \n" - "The \002VOP CLEAR\002 command clears all entries of the\n" - "VOP list.\n")); - source.Reply(_( - " \n" - "The \002VOP ADD\002, \002VOP DEL\002 and \002VOP LIST\002 commands are \n" - "limited to AOPs or above, while the \002VOP CLEAR\002 command \n" - "can only be used by the channel founder.\n" - " \n")); - source.Reply(_("This command may have been disabled for your channel, and\n" - "in that case you need to use the access list. See \n" - "\002%s%s HELP ACCESS\002 for information about the access list,\n" - "and \002%s%s HELP SET XOP\002 to know how to toggle between \n" - "the access list and xOP list systems."), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), - Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str()); - return true; - } -}; - -class CSXOP : public Module -{ - XOPAccessProvider accessprovider; - CommandCSQOP commandcsqop; - CommandCSSOP commandcssop; - CommandCSAOP commandcsaop; - CommandCSHOP commandcshop; - CommandCSVOP commandcsvop; - - public: - CSXOP(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - accessprovider(this), commandcsqop(this), commandcssop(this), commandcsaop(this), commandcshop(this), commandcsvop(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&accessprovider); - ModuleManager::RegisterService(&commandcssop); - ModuleManager::RegisterService(&commandcsaop); - ModuleManager::RegisterService(&commandcsqop); - ModuleManager::RegisterService(&commandcsvop); - ModuleManager::RegisterService(&commandcshop); - } -}; - -MODULE_INIT(CSXOP) diff --git a/modules/core/db_mysql.cpp b/modules/core/db_mysql.cpp deleted file mode 100644 index 4e6a7de4f..000000000 --- a/modules/core/db_mysql.cpp +++ /dev/null @@ -1,1566 +0,0 @@ -#include "module.h" -#include "../extra/sql.h" -#include "os_session.h" - -static Anope::string ToString(const std::vector<Anope::string> &strings) -{ - Anope::string ret; - - for (unsigned i = 0; i < strings.size(); ++i) - ret += " " + strings[i]; - - if (!ret.empty()) - ret.erase(ret.begin()); - - return ret; -} - -static std::vector<Anope::string> MakeVector(const Anope::string &buf) -{ - Anope::string s; - spacesepstream sep(buf); - std::vector<Anope::string> params; - - while (sep.GetToken(s)) - { - if (s[0] == ':') - { - s.erase(s.begin()); - if (!s.empty() && !sep.StreamEnd()) - params.push_back(s + " " + sep.GetRemaining()); - else if (!s.empty()) - params.push_back(s); - } - else - params.push_back(s); - } - - return params; -} - -static NickAlias *CurNick = NULL; -static NickCore *CurCore = NULL; -static ChannelInfo *CurChannel = NULL; -static BotInfo *CurBot = NULL; - -static void Write(const Anope::string &data); -static void WriteNickMetadata(const Anope::string &key, const Anope::string &data); -static void WriteCoreMetadata(const Anope::string &key, const Anope::string &data); -static void WriteChannelMetadata(const Anope::string &key, const Anope::string &data); -static void WriteBotMetadata(const Anope::string &key, const Anope::string &data); - -class CommandSQLSync : public Command -{ - public: - CommandSQLSync(Module *creator) : Command(creator, "SQLSYNC", 0, 0) - { - this->SetDesc(_("Import your databases to SQL")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms); - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command syncs your databases with SQL. You should\n" - "only have to execute this command once, when you initially\n" - "import your databases into SQL.")); - return true; - } -}; - -class MySQLInterface : public SQLInterface -{ - public: - MySQLInterface(Module *o) : SQLInterface(o) { } - - void OnResult(const SQLResult &r); - - void OnError(const SQLResult &r); -}; - -class DBMySQL; -static DBMySQL *me; -class DBMySQL : public Module -{ - private: - CommandSQLSync commandsqlsync; - MySQLInterface sqlinterface; - service_reference<SQLProvider> SQL; - - public: - service_reference<SessionService> SessionInterface; - time_t lastwarn; - bool ro; - - void RunQuery(const SQLQuery &query) - { - if (SQL) - { - if (readonly && this->ro) - { - readonly = this->ro = false; - BotInfo *bi = findbot(Config->OperServ); - if (bi) - ircdproto->SendGlobops(bi, "Found SQL again, going out of readonly mode..."); - } - - SQL->Run(&sqlinterface, query); - } - else - { - if (Anope::CurTime - Config->UpdateTimeout > lastwarn) - { - BotInfo *bi = findbot(Config->OperServ); - if (bi) - ircdproto->SendGlobops(bi, "Unable to locate SQL reference, is m_mysql loaded? Going to readonly..."); - readonly = this->ro = true; - this->lastwarn = Anope::CurTime; - } - } - } - - DBMySQL(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE), commandsqlsync(this), sqlinterface(this), SQL("mysql/main"), SessionInterface("session") - { - me = this; - - this->lastwarn = 0; - this->ro = false; - - Implementation i[] = { - I_OnLoadDatabase, I_OnServerConnect - }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&commandsqlsync); - - if (CurrentUplink) - OnServerConnect(); - } - - void OnServerConnect() - { - Implementation i[] = { - /* Misc */ - I_OnSaveDatabase, I_OnPostCommand, - /* NickServ */ - I_OnNickAddAccess, I_OnNickEraseAccess, I_OnNickClearAccess, - I_OnDelCore, I_OnNickForbidden, I_OnNickGroup, - I_OnNickRegister, I_OnChangeCoreDisplay, - I_OnNickSuspended, I_OnDelNick, - /* ChanServ */ - I_OnAccessAdd, I_OnAccessDel, I_OnAccessClear, I_OnLevelChange, - I_OnChanForbidden, I_OnDelChan, I_OnChanRegistered, I_OnChanSuspend, - I_OnAkickAdd, I_OnAkickDel, I_OnMLock, I_OnUnMLock, - /* BotServ */ - I_OnBotCreate, I_OnBotChange, I_OnBotDelete, - I_OnBotAssign, I_OnBotUnAssign, - I_OnBadWordAdd, I_OnBadWordDel, - /* MemoServ */ - I_OnMemoSend, I_OnMemoDel, - /* OperServ */ - I_OnExceptionAdd, I_OnExceptionDel, - I_OnAddXLine, I_OnDelXLine, - /* HostServ */ - I_OnSetVhost, I_OnDeleteVhost - }; - ModuleManager::Attach(i, this, 40); - } - - EventReturn OnLoadDatabase() - { - if (!SQL) - { - Log() << "Error, unable to find service reference for SQL, is m_mysql loaded and configured properly?"; - return EVENT_CONTINUE; - } - - SQLQuery query; - - query = "SELECT * FROM `anope_ns_core`"; - SQLResult r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickCore *nc = new NickCore(r.Get(i, "display")); - nc->pass = r.Get(i, "pass"); - nc->email = r.Get(i, "email"); - nc->greet = r.Get(i, "greet"); - - spacesepstream sep(r.Get(i, "flags")); - Anope::string buf; - std::vector<Anope::string> flags; - while (sep.GetToken(buf)) - flags.push_back(buf); - nc->FromString(flags); - - nc->language = r.Get(i, "language"); - nc->memos.memomax = r.Get(i, "memomax").is_number_only() ? convertTo<int16>(r.Get(i, "memomax")) : 20; - } - - query = "SELECT * FROM `anope_ns_access`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickCore *nc = findcore(r.Get(i, "display")); - if (!nc) - { - Log() << "MySQL: Got NickCore access entry for nonexistant core " << r.Get(i, "display"); - continue; - } - - nc->AddAccess(r.Get(i, "access")); - } - - query = "SELECT * FROM `anope_ns_core_metadata`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickCore *nc = findcore(r.Get(i, "display")); - if (!nc) - { - Log() << "MySQL: Got NickCore access entry for nonexistant core " << r.Get(i, "display"); - continue; - } - - EventReturn MOD_RESULT;; - std::vector<Anope::string> Params = MakeVector(r.Get(i, "value")); - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(nc, r.Get(i, "name"), Params)); - } - - query = "SELECT * FROM `anope_ns_alias`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickCore *nc = findcore(r.Get(i, "display")); - if (!nc) - { - Log() << "MySQL: Got NickAlias for nick " << r.Get(i, "nick") << " with nonexistant core " << r.Get(i, "display"); - continue; - } - - NickAlias *na = new NickAlias(r.Get(i, "nick"), nc); - na->last_quit = r.Get(i, "last_quit"); - na->last_realname = r.Get(i, "last_realname"); - na->last_usermask = r.Get(i, "last_usermask"); - na->time_registered = r.Get(i, "time_registered").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "time_registered")) : Anope::CurTime; - na->last_seen = r.Get(i, "last_seen").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "last_seen")) : Anope::CurTime; - - spacesepstream sep(r.Get(i, "flags")); - Anope::string buf; - std::vector<Anope::string> flags; - while (sep.GetToken(buf)) - flags.push_back(buf); - - na->FromString(flags); - } - - query = "SELECT * FROM `anope_ns_alias_metadata`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickAlias *na = findnick(r.Get(i, "nick")); - if (!na) - { - Log() << "MySQL: Got metadata for nonexistant nick " << r.Get(i, "nick"); - continue; - } - - EventReturn MOD_RESULT; - std::vector<Anope::string> Params = MakeVector(r.Get(i, "value")); - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(na, na->nick, Params)); - } - - query = "SELECT * FROM `anope_hs_core`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickAlias *na = findnick(r.Get(i, "nick")); - if (!na) - { - Log() << "MySQL: Got vhost entry for nonexistant nick " << r.Get(i, "nick"); - continue; - } - - time_t creation = r.Get(i, "time").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "time")) : Anope::CurTime; - na->hostinfo.SetVhost(r.Get(i, "vident"), r.Get(i, "vhost"), r.Get(i, "creator"), creation); - } - - query = "SELECT * FROM `anope_bs_core`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - BotInfo *bi = findbot(r.Get(i, "nick")); - if (!bi) - bi = new BotInfo(r.Get(i, "nick"), r.Get(i, "user"), r.Get(i, "host")); - bi->realname = r.Get(i, "rname"); - bi->created = r.Get(i, "created").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "created")) : Anope::CurTime; - - spacesepstream sep(r.Get(i, "flags")); - Anope::string buf; - std::vector<Anope::string> flags; - while (sep.GetToken(buf)) - flags.push_back(buf); - - bi->FromString(flags); - } - - query = "SELECT * FROM `anope_bs_info_metadata`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - BotInfo *bi = findbot(r.Get(i, "botname")); - if (!bi) - { - Log() << "MySQL: BotInfo metadata for nonexistant bot " << r.Get(i, "botname"); - continue; - } - - EventReturn MOD_RESULT; - std::vector<Anope::string> Params = MakeVector(r.Get(i, "value")); - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(bi, bi->nick, Params)); - } - - query = "SELECT * FROM `anope_cs_info`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickCore *nc = NULL; - - if (!r.Get(i, "founder").empty()) - { - nc = findcore(r.Get(i, "founder")); - if (!nc) - { - Log() << "MySQL: Channel " << r.Get(i, "name") << " with nonexistant founder " << r.Get(i, "founder"); - continue; - } - - ChannelInfo *ci = new ChannelInfo(r.Get(i, "name")); - ci->SetFounder(nc); - if (!r.Get(i, "successor").empty()) - ci->successor = findcore(r.Get(i, "successor")); - ci->desc = r.Get(i, "descr"); - ci->time_registered = r.Get(i, "time_registered").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "time_registered")) : Anope::CurTime; - ci->last_used = r.Get(i, "last_used").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "last_used")) : Anope::CurTime; - ci->last_topic = r.Get(i, "last_topic"); - ci->last_topic_setter = r.Get(i, "last_topic_setter"); - ci->last_topic_time = r.Get(i, "last_topic_time").is_number_only() ? convertTo<int>(r.Get(i, "last_topic_time")) : Anope::CurTime; - ci->bantype = r.Get(i, "bantype").is_number_only() ? convertTo<int>(r.Get(i, "bantype")) : 2; - ci->memos.memomax = r.Get(i, "memomax").is_number_only() ? convertTo<int16>(r.Get(i, "memomax")) : 20; - ci->capsmin = r.Get(i, "capsmin").is_number_only() ? convertTo<int>(r.Get(i, "capsmin")) : 0; - ci->capspercent = r.Get(i, "capspercent").is_number_only() ? convertTo<int>(r.Get(i, "capspercent")) : 0; - ci->floodlines = r.Get(i, "floodlines").is_number_only() ? convertTo<int>(r.Get(i, "floodlines")) : 0; - ci->floodsecs = r.Get(i, "floodsecs").is_number_only() ? convertTo<int>(r.Get(i, "floodsecs")) : 0; - ci->repeattimes = r.Get(i, "repeattimes").is_number_only() ? convertTo<int>(r.Get(i, "repeattimes")) : 0; - ci->bi = findbot(r.Get(i, "botnick")); - if (ci->bi && !r.Get(i, "botflags").empty()) - { - spacesepstream sep(r.Get(i, "botflags")); - Anope::string buf; - std::vector<Anope::string> flags; - while (sep.GetToken(buf)) - flags.push_back(buf); - - ci->botflags.FromString(flags); - } - - if (!r.Get(i, "flags").empty()) - { - spacesepstream sep(r.Get(i, "flags")); - Anope::string buf; - std::vector<Anope::string> flags; - while (sep.GetToken(buf)) - flags.push_back(buf); - - ci->FromString(flags); - } - } - } - - query = "SELECT * FROM `anope_cs_ttb`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel ttb for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - ci->ttb[atoi(r.Get(i, "ttb_id").c_str())] = atoi(r.Get(i, "value").c_str()); - } - - query = "SELECT * FROM `anope_bs_badwords`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel badwords entry for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - BadWordType BWTYPE = BW_ANY; - if (r.Get(i, "type").equals_cs("SINGLE")) - BWTYPE = BW_SINGLE; - else if (r.Get(i, "type").equals_cs("START")) - BWTYPE = BW_START; - else if (r.Get(i, "type").equals_cs("END")) - BWTYPE = BW_END; - ci->AddBadWord(r.Get(i, "word"), BWTYPE); - } - - query = "SELECT * FROM `anope_cs_access`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel access entry for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - const Anope::string &provider = r.Get(i, "provider"), &data = r.Get(i, "data"); - service_reference<AccessProvider> ap(provider); - if (!ap) - { - Log() << "MySQL: Access entry for " << ci->name << " using nonexistant provider " << provider; - continue; - } - - ChanAccess *access = ap->Create(); - access->ci = ci; - access->mask = r.Get(i, "mask"); - access->creator = r.Get(i, "creator"); - access->last_seen = r.Get(i, "last_seen").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "last_seen")) : Anope::CurTime; - access->created = r.Get(i, "created").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "created")) : Anope::CurTime; - access->Unserialize(data); - ci->AddAccess(access); - } - - query = "SELECT * FROM `anope_cs_akick`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel access entry for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - NickCore *nc = NULL; - spacesepstream sep(r.Get(i, "flags")); - Anope::string flag, mask; - while (sep.GetToken(flag)) - { - if (flag.equals_cs("ISNICK")) - nc = findcore(r.Get(i, "mask")); - - AutoKick *ak; - if (nc) - ak = ci->AddAkick(r.Get(i, "creator"), nc, r.Get(i, "reason"), atol(r.Get(i, "created").c_str()), atol(r.Get(i, "last_used").c_str())); - else - ak = ci->AddAkick(r.Get(i, "creator"), r.Get(i, "mask"), r.Get(i, "reason"), atol(r.Get(i, "created").c_str()), atol(r.Get(i, "last_used").c_str())); - if (nc) - ak->SetFlag(AK_ISNICK); - } - } - - query = "SELECT * FROM `anope_cs_levels`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel level entry for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - ci->levels[atoi(r.Get(i, "position").c_str())] = atoi(r.Get(i, "level").c_str()); - } - - query = "SELECT * FROM `anope_cs_info_metadata`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel metadata for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - EventReturn MOD_RESULT; - std::vector<Anope::string> Params = MakeVector(r.Get(i, "value")); - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(ci, ci->name, Params)); - } - - query = "SELECT * FROM `anope_cs_mlock`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - { - Log() << "MySQL: Channel mlock for nonexistant channel " << r.Get(i, "channel"); - continue; - } - - std::vector<Anope::string> mlocks; - ci->GetExtRegular("db_mlock", mlocks); - - Anope::string modestring = r.Get(i, "status") + " " + r.Get(i, "mode") + " " + r.Get(i, "setter") + " " + r.Get(i, "created") + " " + r.Get(i, "param"); - - mlocks.push_back(modestring); - - ci->Extend("db_mlock", new ExtensibleItemRegular<std::vector<Anope::string> >(mlocks)); - } - - query = "SELECT * FROM `anope_ms_info`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - MemoInfo *mi = NULL; - if (r.Get(i, "serv").equals_cs("NICK")) - { - NickCore *nc = findcore(r.Get(i, "receiver")); - if (nc) - mi = &nc->memos; - } - else if (r.Get(i, "serv").equals_cs("CHAN")) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "receiver")); - if (ci) - mi = &ci->memos; - } - if (mi) - { - Memo *m = new Memo(); - mi->memos.push_back(m); - m->sender = r.Get(i, "sender"); - m->time = r.Get(i, "time").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "time")) : Anope::CurTime; - m->text = r.Get(i, "text"); - - if (!r.Get(i, "flags").empty()) - { - spacesepstream sep(r.Get(i, "flags")); - Anope::string buf; - std::vector<Anope::string> flags; - while (sep.GetToken(buf)) - flags.push_back(buf); - - m->FromString(flags); - } - } - } - - for (std::list<XLineManager *>::iterator it = XLineManager::XLineManagers.begin(), it_end = XLineManager::XLineManagers.end(); it != it_end; ++it) - { - XLineManager *xm = *it; - - query = "SELECT * FROM `anope_os_xlines` WHERE `type` = @type"; - query.setValue("type", Anope::string(xm->Type())); - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - Anope::string user = r.Get(i, "user"); - Anope::string host = r.Get(i, "host"); - Anope::string by = r.Get(i, "xby"); - Anope::string reason = r.Get(i, "reason"); - time_t seton = r.Get(i, "seton").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "seton")) : Anope::CurTime; - time_t expires = r.Get(i, "expires").is_pos_number_only() ? convertTo<time_t>(r.Get(i, "expires")) : Anope::CurTime; - - XLine *x = xm->Add(user + "@" + host, by, expires, reason); - if (x) - x->Created = seton; - } - } - - query = "SELECT * FROM `anope_os_exceptions`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - Anope::string mask = r.Get(i, "mask"); - unsigned limit = convertTo<unsigned>(r.Get(i, "slimit")); - Anope::string creator = r.Get(i, "who"); - Anope::string reason = r.Get(i, "reason"); - time_t expires = convertTo<time_t>(r.Get(i, "expires")); - - if (SessionInterface) - { - Exception *e = new Exception(); - e->mask = mask; - e->limit = limit; - e->who = creator; - e->reason = reason; - e->time = expires; - SessionInterface->AddException(e); - } - } - - query = "SELECT * FROM `anope_extra`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - std::vector<Anope::string> params = MakeVector(r.Get(i, "data")); - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnDatabaseRead, OnDatabaseRead(params)); - } - - query = "SELECT * FROM `anope_ns_core_metadata`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - NickCore *nc = findcore(r.Get(i, "nick")); - if (!nc) - continue; - if (r.Get(i, "name") == "MEMO_IGNORE") - nc->memos.ignores.push_back(r.Get(i, "value").ci_str()); - } - - query = "SELECT * FROM `anope_cs_info_metadata`"; - r = SQL->RunQuery(query); - for (int i = 0; i < r.Rows(); ++i) - { - ChannelInfo *ci = cs_findchan(r.Get(i, "channel")); - if (!ci) - continue; - if (r.Get(i, "name") == "MEMO_IGNORE") - ci->memos.ignores.push_back(r.Get(i, "value").ci_str()); - } - - return EVENT_STOP; - } - - EventReturn OnSaveDatabase() - { - SQLQuery query; - - query = "TRUNCATE TABLE `anope_os_core`"; - this->RunQuery(query); - - query = "INSERT INTO `anope_os_core` (maxusercnt, maxusertime, akills_count, snlines_count, sqlines_count, szlines_count) VALUES(@maxusercnt, @maxusertime, @akills_count, @snlines_count, @sqlines_count, @szlines_count)"; - query.setValue("maxusercnt", maxusercnt); - query.setValue("maxusertime", maxusertime); - this->RunQuery(query); - - for (nickcore_map::const_iterator it = NickCoreList.begin(), it_end = NickCoreList.end(); it != it_end; ++it) - { - CurCore = it->second; - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteCoreMetadata, CurCore)); - } - - for (nickalias_map::const_iterator it = NickAliasList.begin(), it_end = NickAliasList.end(); it != it_end; ++it) - { - CurNick = it->second; - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteNickMetadata, CurNick)); - } - - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ++it) - { - CurChannel = it->second; - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteChannelMetadata, CurChannel)); - } - - for (Anope::insensitive_map<BotInfo *>::const_iterator it = BotListByNick.begin(), it_end = BotListByNick.end(); it != it_end; ++it) - { - if (it->second->HasFlag(BI_CONF)) - continue; - - CurBot = it->second; - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteBotMetadata, CurBot)); - - query = "INSERT INTO `anope_bs_core` (nick, user, host, rname, flags, created, chancount) VALUES(@nick, @user, @host, @rname, @flags, @created, @chancount) ON DUPLICATE KEY UPDATE nick=VALUES(nick), user=VALUES(user), host=VALUES(host), rname=VALUES(rname), flags=VALUES(flags), created=VALUES(created), chancount=VALUES(chancount)"; - query.setValue("nick", CurBot->nick); - query.setValue("user", CurBot->GetIdent()); - query.setValue("host", CurBot->host); - query.setValue("rname", CurBot->realname); - query.setValue("flags", ToString(CurBot->ToString())); - query.setValue("created", CurBot->created); - query.setValue("chancount", CurBot->chancount); - this->RunQuery(query); - } - - query = "TRUNCATE TABLE `anope_extra`"; - this->RunQuery(query); - FOREACH_MOD(I_OnDatabaseWrite, OnDatabaseWrite(Write)); - - return EVENT_CONTINUE; - } - - void OnPostCommand(CommandSource &source, Command *command, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - if (command->name.find("nickserv/set/") == 0 || command->name.find("nickserv/saset/") == 0) - { - NickAlias *na = findnick(command->name.find("nickserv/set/") == 0 ? source.u->nick : params[1]); - if (!na) - return; - - if (command->name == "nickserv/set/password" || command->name == "nickserv/saset/password") - { - SQLQuery query("UPDATE `anope_ns_core` SET `pass` = @pass WHERE `display` = @display"); - query.setValue("pass", na->nc->pass); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - else if (command->name == "nickserv/set/language" || command->name == "nickserv/saset/language") - { - SQLQuery query("UPDATE `anope_ns_core` SET `language` = @language WHERE `display` = @display"); - query.setValue("language", na->nc->language); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - else if (command->name == "nickserv/set/email" || command->name == "nickserv/saset/email") - { - SQLQuery query("UPDATE `anope_ns_core` SET `email` = @email WHERE `display` = @display"); - query.setValue("email", na->nc->email); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - else if (command->name == "nickserv/set/greet" || command->name == "nickserv/saset/greet") - { - SQLQuery query("UPDATE `anope_ns_core` SET `greet` = @greet WHERE `display` = @display"); - query.setValue("greet", na->nc->greet); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - else - { - SQLQuery query("UPDATE `anope_ns_core` SET `flags` = @flags WHERE `display` = @display"); - query.setValue("flags", ToString(na->nc->ToString())); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - } - else if (command->name.find("chanserv/set") == 0 || command->name.find("chanserv/saset") == 0) - { - ChannelInfo *ci = params.size() > 0 ? cs_findchan(params[0]) : NULL; - if (!ci) - return; - - if (command->name == "chanserv/set/founder" || command->name == "chanserv/saset/founder") - { - SQLQuery query("UPDATE `anope_cs_info` SET `founder` = @founder WHERE `name` = @name"); - query.setValue("founder", ci->GetFounder() ? ci->GetFounder()->display : ""); - query.setValue("name", ci->name); - this->RunQuery(query); - } - else if (command->name == "chanserv/set/successor" || command->name == "chanserv/saset/successor") - { - SQLQuery query("UPDATE `anope_cs_info` SET `successor` = @successor WHERE `name` = @name"); - query.setValue("successor", ci->successor ? ci->successor->display : ""); - query.setValue("name", ci->name); - this->RunQuery(query); - } - else if (command->name == "chanserv/set/desc" || command->name == "chanserv/saset/desc") - { - SQLQuery query("UPDATE `anope_cs_info` SET `descr` = @descr WHERE `name` = @name"); - query.setValue("descr", ci->desc); - query.setValue("name", ci->name); - this->RunQuery(query); - } - else if (command->name == "chanserv/set/bantype" || command->name == "chanserv/saset/bantype") - { - SQLQuery query("UPDATE `anope_cs_info` SET `bantype` = @bantype WHERE `name` = @name"); - query.setValue("bantype", ci->bantype); - query.setValue("name", ci->name); - this->RunQuery(query); - } - else - { - SQLQuery query("UPDATE `anope_cs_info` SET `flags` = @flags WHERE `name` = @name"); - query.setValue("flags", ToString(ci->ToString())); - query.setValue("name", ci->name); - this->RunQuery(query); - } - } - else if (command->name == "botserv/kick" && params.size() > 2) - { - ChannelInfo *ci = cs_findchan(params[0]); - if (!ci) - return; - if (!ci->HasPriv(u, CA_SET) && !u->HasPriv("botserv/administration")) - return; - if (params[1].equals_ci("BADWORDS") || params[1].equals_ci("BOLDS") || params[1].equals_ci("CAPS") || params[1].equals_ci("COLORS") || params[1].equals_ci("FLOOD") || params[1].equals_ci("REPEAT") || params[1].equals_ci("REVERSES") || params[1].equals_ci("UNDERLINES")) - { - if (params[2].equals_ci("ON") || params[2].equals_ci("OFF")) - { - for (int i = 0; i < TTB_SIZE; ++i) - { - SQLQuery query("INSERT INTO `anope_cs_ttb` (channel, ttb_id, value) VALUES(@channel, @ttb_id, @value) ON DUPLICATE KEY UPDATE channel=VALUES(channel), ttb_id=VALUES(ttb_id), value=VALUES(value)"); - query.setValue("channel", ci->name); - query.setValue("ttb_id", i); - query.setValue("value", ci->ttb[i]); - this->RunQuery(query); - } - - { - SQLQuery query("UPDATE `anope_cs_info` SET `botflags` = @botflags WHERE `name` = @name"); - query.setValue("botflags", ToString(ci->botflags.ToString())); - query.setValue("name", ci->name); - this->RunQuery(query); - } - - if (params[1].equals_ci("CAPS")) - { - SQLQuery query("UPDATE `anope_cs_info` SET `capsmin` = @capsmin, `capspercent` = @capspercent WHERE `name` = @name"); - query.setValue("capsmin", ci->capsmin); - query.setValue("capspercent", ci->capspercent); - query.setValue("name", ci->name); - this->RunQuery(query); - } - else if (params[1].equals_ci("FLOOD")) - { - SQLQuery query("UPDATE `anope_cs_info` SET `floodlines` = @floodlines, `floodsecs` = @floodsecs WHERE `name` = @name"); - query.setValue("floodlines", ci->floodlines); - query.setValue("floodsecs", ci->floodsecs); - query.setValue("name", ci->name); - this->RunQuery(query); - } - else if (params[1].equals_ci("REPEAT")) - { - SQLQuery query("UPDATE `anope_cs_info` SET `repeattimes` = @ WHERE `name` = @"); - query.setValue("repeattimes", ci->repeattimes); - query.setValue("name", ci->name); - this->RunQuery(query); - } - } - } - } - else if (command->name == "botserv/set" && params.size() > 1) - { - ChannelInfo *ci = cs_findchan(params[0]); - if (ci && !ci->HasPriv(u, CA_SET) && !u->HasPriv("botserv/administration")) - return; - BotInfo *bi = NULL; - if (!ci) - bi = findbot(params[0]); - if (bi && params[1].equals_ci("PRIVATE") && u->HasPriv("botserv/set/private")) - { - SQLQuery query("UPDATE `anope_bs_core` SET `flags` = @ WHERE `nick` = @"); - query.setValue("flags", ToString(bi->ToString())); - query.setValue("nick", bi->nick); - this->RunQuery(query); - } - else if (!ci) - return; - else if (params[1].equals_ci("DONTKICKOPS") || params[1].equals_ci("DONTKICKVOICES") || params[1].equals_ci("FANTASY") || params[1].equals_ci("GREET") || params[1].equals_ci("SYMBIOSIS") || params[1].equals_ci("NOBOT")) - { - SQLQuery query("UPDATE `anope_cs_info` SET `botflags` = @ WHERE `name` = @"); - query.setValue("botflags", ToString(ci->botflags.ToString())); - query.setValue("name", ci->name); - this->RunQuery(query); - } - } - else if (command->name == "memoserv/ignore" && params.size() > 0) - { - Anope::string target = params[0]; - NickCore *nc = NULL; - ChannelInfo *ci = NULL; - if (target[0] != '#') - { - target = u->nick; - nc = u->Account(); - if (!nc) - return; - } - else - { - ci = cs_findchan(target); - if (!ci || !ci->HasPriv(u, CA_MEMO)) - return; - } - - MemoInfo *mi = ci ? &ci->memos : &nc->memos; - Anope::string table = ci ? "anope_cs_info_metadata" : "anope_ns_core_metadata"; - Anope::string ename = ci ? "channel" : "nick"; - - SQLQuery query("DELETE FROM `" + table + "` WHERE `" + ename + "` = @target AND `name` = 'MEMO_IGNORE'"); - query.setValue("target", target); - this->RunQuery(query); - - query = "INSERT INTO `" + table + "` VALUES(" + ename + ", name, value) (@target, 'MEMO_IGNORE, @ignore)"; - query.setValue("target", target); - for (unsigned j = 0; j < mi->ignores.size(); ++j) - { - query.setValue("ignore", mi->ignores[j]); - this->RunQuery(query); - } - } - } - - void OnNickAddAccess(NickCore *nc, const Anope::string &entry) - { - SQLQuery query("INSERT INTO `anope_ns_access` (display, access) VALUES(@display, @access)"); - query.setValue("display", nc->display); - query.setValue("access", entry); - this->RunQuery(query); - } - - void OnNickEraseAccess(NickCore *nc, const Anope::string &entry) - { - SQLQuery query("DELETE FROM `anope_ns_access` WHERE `display` = @display AND `access` = @access"); - query.setValue("display", nc->display); - query.setValue("access", entry); - this->RunQuery(query); - } - - void OnNickClearAccess(NickCore *nc) - { - SQLQuery query("DELETE FROM `anope_ns_access` WHERE `display` = @display"); - query.setValue("display", nc->display); - this->RunQuery(query); - } - - void OnDelCore(NickCore *nc) - { - SQLQuery query("DELETE FROM `anope_ns_core` WHERE `display` = @display"); - query.setValue("display", nc->display); - this->RunQuery(query); - } - - void OnNickForbidden(NickAlias *na) - { - SQLQuery query("UPDATE `anope_ns_alias` SET `flags` = @flags WHERE `nick` = @nick"); - query.setValue("flags", ToString(na->ToString())); - query.setValue("nick", na->nick); - this->RunQuery(query); - } - - void OnNickGroup(User *u, NickAlias *) - { - OnNickRegister(findnick(u->nick)); - } - - void InsertAlias(NickAlias *na) - { - SQLQuery query("INSERT INTO `anope_ns_alias` (nick, last_quit, last_realname, last_usermask, time_registered, last_seen, flags, display) VALUES(@nick, @last_quit, @last_realname, @last_usermask, @time_registered, @last_seen, @flags, @display) ON DUPLICATE KEY UPDATE last_quit=VALUES(last_quit), last_realname=VALUES(last_realname), last_usermask=VALUES(last_usermask), time_registered=VALUES(time_registered), last_seen=VALUES(last_seen), flags=VALUES(flags), display=VALUES(display)"); - query.setValue("nick", na->nick); - query.setValue("last_quit", na->last_quit); - query.setValue("last_realname", na->last_realname); - query.setValue("last_usermask", na->last_usermask); - query.setValue("time_registered", na->time_registered); - query.setValue("last_seen", na->last_seen); - query.setValue("flags", ToString(na->ToString())); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - - void InsertCore(NickCore *nc) - { - SQLQuery query("INSERT INTO `anope_ns_core` (display, pass, email, greet, flags, language, memomax) VALUES(@display, @pass, @email, @greet, @flags, @language, @memomax) ON DUPLICATE KEY UPDATE pass=VALUES(pass), email=VALUES(email), greet=VALUES(greet), flags=VALUES(flags), language=VALUES(language), memomax=VALUES(memomax)"); - query.setValue("display", nc->display); - query.setValue("pass", nc->pass); - query.setValue("email", nc->email); - query.setValue("greet", nc->greet); - query.setValue("flags", ToString(nc->ToString())); - query.setValue("language", nc->language); - query.setValue("memomax", nc->memos.memomax); - this->RunQuery(query); - } - - void OnNickRegister(NickAlias *na) - { - this->InsertCore(na->nc); - this->InsertAlias(na); - } - - void OnChangeCoreDisplay(NickCore *nc, const Anope::string &newdisplay) - { - SQLQuery query("UPDATE `anope_ns_core` SET `display` = @newdisplay WHERE `display` = @olddisplay"); - query.setValue("newdisplay", newdisplay); - query.setValue("olddisplay", nc->display); - this->RunQuery(query); - } - - void OnNickSuspend(NickAlias *na) - { - SQLQuery query("UPDATE `anope_ns_core` SET `flags` = @flags WHERE `display` = @display"); - query.setValue("flags", ToString(na->nc->ToString())); - query.setValue("display", na->nc->display); - this->RunQuery(query); - } - - void OnDelNick(NickAlias *na) - { - SQLQuery query("DELETE FROM `anope_ns_alias` WHERE `nick` = @nick"); - query.setValue("nick", na->nick); - this->RunQuery(query); - } - - void OnAccessAdd(ChannelInfo *ci, User *, ChanAccess *access) - { - SQLQuery query("INSERT INTO `anope_cs_access` (provider, data, mask, channel, last_seen, creator) VALUES (@provider, @data, @mask, @channel, @last_seen, @creator) ON DUPLICATE KEY UPDATE level=VALUES(level), display=VALUES(display), channel=VALUES(channel), last_seen=VALUES(last_seen), creator=VALUES(creator)"); - query.setValue("provider", access->provider->name); - query.setValue("data", access->Serialize()); - query.setValue("mask", access->mask); - query.setValue("channel", ci->name); - query.setValue("last_seen", access->last_seen); - query.setValue("creator", access->creator); - this->RunQuery(query); - } - - void OnAccessDel(ChannelInfo *ci, User *u, ChanAccess *access) - { - SQLQuery query("DELETE FROM `anope_cs_access` WHERE `mask` = @mask AND `channel` = @channel"); - query.setValue("mask", access->mask); - query.setValue("channel", ci->name); - this->RunQuery(query); - } - - void OnAccessClear(ChannelInfo *ci, User *u) - { - SQLQuery query("DELETE FROM `anope_cs_access` WHERE `channel` = @channel"); - query.setValue("channel", ci->name); - this->RunQuery(query); - } - - void OnLevelChange(User *u, ChannelInfo *ci, int pos, int what) - { - SQLQuery query("UPDATE `anope_cs_levels` SET `level` = @level WHERE `channel` = @channel AND `position` = @pos ON DUPLICATE KEY UPDATE level=VALUES(level), position=VALUES(position)"); - if (pos >= 0) - { - query.setValue("level", what); - query.setValue("channel", ci->name); - query.setValue("pos", pos); - this->RunQuery(query); - } - else - { - query.setValue("channel", ci->name); - for (int i = 0; i < CA_SIZE; ++i) - { - query.setValue("level", ci->levels[i]); - query.setValue("pos", i); - this->RunQuery(query); - } - } - } - - void OnChanForbidden(ChannelInfo *ci) - { - SQLQuery query("INSERT INTO `anope_cs_info` (name, time_registered, last_used, flags) VALUES (@name, @time_registered, @last_used, @flags)"); - query.setValue("name", ci->name); - query.setValue("time_registered", ci->time_registered); - query.setValue("last_used", ci->last_used); - query.setValue("flags", ToString(ci->ToString())); - this->RunQuery(query); - } - - void OnDelChan(ChannelInfo *ci) - { - SQLQuery query("DELETE FROM `anope_cs_info` WHERE `name` = @name"); - query.setValue("name", ci->name); - this->RunQuery(query); - } - - void OnChanRegistered(ChannelInfo *ci) - { - SQLQuery query("INSERT INTO `anope_cs_info` (name, founder, successor, descr, time_registered, last_used, last_topic, last_topic_setter, last_topic_time, flags, bantype, memomax, botnick, botflags, capsmin, capspercent, floodlines, floodsecs, repeattimes) VALUES(@name, @founder, @successor, @descr, @time_registered, @last_used, @last_topic_text, @last_topic_setter, @last_topic_time, @flags, @bantype, @memomax, @botnick, @botflags, @capsmin, @capspercent, @floodlines, @floodsecs, @repeattimes) ON DUPLICATE KEY UPDATE founder=VALUES(founder), successor=VALUES(successor), descr=VALUES(descr), time_registered=VALUES(time_registered), last_used=VALUES(last_used), last_topic=VALUES(last_topic), last_topic_setter=VALUES(last_topic_setter), last_topic_time=VALUES(last_topic_time), flags=VALUES(flags), bantype=VALUES(bantype), memomax=VALUES(memomax), botnick=VALUES(botnick), botflags=VALUES(botflags), capsmin=VALUES(capsmin), capspercent=VALUES(capspercent), floodlines=VALUES(floodlines), floodsecs=VALUES(floodsecs), repeattimes=VALUES(repeattimes)"); - query.setValue("name", ci->name); - query.setValue("founder", ci->GetFounder() ? ci->GetFounder()->display : ""); - query.setValue("successor", ci->successor ? ci->successor->display : ""); - query.setValue("descr", ci->desc); - query.setValue("time_registered", ci->time_registered); - query.setValue("last_used", ci->last_used); - query.setValue("last_topic_text", ci->last_topic); - query.setValue("last_topic_setter", ci->last_topic_setter); - query.setValue("last_topic_time", ci->last_topic_time); - query.setValue("flags", ToString(ci->ToString())); - query.setValue("bantype", ci->bantype); - query.setValue("memomax", ci->memos.memomax); - query.setValue("botnick", ci->bi ? ci->bi->nick : ""); - query.setValue("botflags", ToString(ci->botflags.ToString())); - query.setValue("capsmin", ci->capsmin); - query.setValue("capspercent", ci->capspercent); - query.setValue("floodlines", ci->floodlines); - query.setValue("floodsecs", ci->floodsecs); - query.setValue("repeattimes", ci->repeattimes); - this->RunQuery(query); - - query = "DELETE from `anope_cs_mlock` WHERE `channel` = @name"; - query.setValue("name", ci->name); - this->RunQuery(query); - for (std::multimap<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it) - { - const ModeLock &ml = it->second; - ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name); - - if (cm != NULL) - { - query = "INSERT INTO `anope_cs_mlock` (channel, mode, status, setter, created, param) VALUES(@channel, @mode, @status, @setter, @created, @param)"; - query.setValue("channel", ci->name); - query.setValue("mode", cm->NameAsString()); - query.setValue("status", ml.set ? 1 : 0); - query.setValue("setter", ml.setter); - query.setValue("created", ml.created); - query.setValue("param", ml.param); - this->RunQuery(query); - } - } - } - - void OnChanSuspend(ChannelInfo *ci) - { - SQLQuery query("UPDATE `anope_cs_info` SET `flags` = @flags WHERE `name` = @name"); - query.setValue("flags", ToString(ci->ToString())); - query.setValue("name", ci->name); - this->RunQuery(query); - } - - void OnAkickAdd(ChannelInfo *ci, AutoKick *ak) - { - SQLQuery query("INSERT INTO `anope_cs_akick` (channel, flags, mask, reason, creator, created, last_used) VALUES(@channel, @flags, @mask, @reason, @creator, @created, @last_used)"); - query.setValue("channel", ci->name); - query.setValue("flags", ak->HasFlag(AK_ISNICK) ? "ISNICK" : ""); - query.setValue("mask", ak->HasFlag(AK_ISNICK) ? ak->nc->display : ak->mask); - query.setValue("reason", ak->reason); - query.setValue("creator", ak->creator); - query.setValue("created", ak->addtime); - query.setValue("last_used", ak->last_used); - this->RunQuery(query); - } - - void OnAkickDel(ChannelInfo *ci, AutoKick *ak) - { - SQLQuery query("DELETE FROM `anope_cs_akick` WHERE `channel`= @mask AND `mask` = @mask"); - query.setValue("channel", ci->name); - query.setValue("mask", ak->HasFlag(AK_ISNICK) ? ak->nc->display : ak->mask); - this->RunQuery(query); - } - - EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(lock->name); - if (cm != NULL) - { - SQLQuery query("INSERT INTO `anope_cs_mlock` (channel, mode, status, setter, created, param) VALUES(@channel, @mode, @status, @setter, @created, @param)"); - query.setValue("channel", ci->name); - query.setValue("mode", cm->NameAsString()); - query.setValue("status", lock->set ? 1 : 0); - query.setValue("setter", lock->setter); - query.setValue("created", lock->created); - query.setValue("param", lock->param); - this->RunQuery(query); - } - return EVENT_CONTINUE; - } - - EventReturn OnUnMLock(ChannelInfo *ci, ChannelMode *mode, const Anope::string ¶m) - { - ChannelMode *cm = ModeManager::FindChannelModeByName(mode->Name); - if (cm != NULL) - { - SQLQuery query("DELETE FROM `anope_cs_mlock` WHERE `channel` = @channel AND `mode` = @mode AND `param` = @param"); - query.setValue("channel", ci->name); - query.setValue("mode", mode->NameAsString()); - query.setValue("param", param); - this->RunQuery(query); - } - return EVENT_CONTINUE; - } - - void OnBotCreate(BotInfo *bi) - { - SQLQuery query("INSERT INTO `anope_bs_core` (nick, user, host, rname, flags, created, chancount) VALUES(@nick, @user, @host, @rname, @flags, @created, @chancuont) ON DUPLICATE KEY UPDATE nick=VALUES(nick), user=VALUES(user), host=VALUES(host), rname=VALUES(rname), flags=VALUES(flags), created=VALUES(created), chancount=VALUES(chancount)"); - query.setValue("nick", bi->nick); - query.setValue("user", bi->GetIdent()); - query.setValue("host", bi->host); - query.setValue("rname", bi->realname); - query.setValue("flags", ToString(bi->ToString())); - query.setValue("created", bi->created); - query.setValue("chancount", bi->chancount); - this->RunQuery(query); - } - - void OnBotChange(BotInfo *bi) - { - OnBotCreate(bi); - } - - void OnBotDelete(BotInfo *bi) - { - SQLQuery query("UPDATE `anope_cs_info` SET `botnick` = '' WHERE `botnick` = @botnick"); - query.setValue("botnick", bi->nick); - this->RunQuery(query); - } - - EventReturn OnBotAssign(User *sender, ChannelInfo *ci, BotInfo *bi) - { - SQLQuery query("UPDATE `anope_cs_info` SET `botnick` = @botnick WHERE `name` = @channel"); - query.setValue("botnick", bi->nick); - query.setValue("channel", ci->name); - this->RunQuery(query); - return EVENT_CONTINUE; - } - - EventReturn OnBotUnAssign(User *sender, ChannelInfo *ci) - { - SQLQuery query("UPDATE `anope_cs_info` SET `botnick` = '' WHERE `name` = @channel"); - query.setValue("channel", ci->name); - this->RunQuery(query); - return EVENT_CONTINUE; - } - - void OnBadWordAdd(ChannelInfo *ci, BadWord *bw) - { - SQLQuery query("INSERT INTO `anope_bs_badwords` (channel, word, type) VALUES(@channel, @word, @type) ON DUPLICATE KEY UPDATE channel=VALUES(channel), word=VALUES(word), type=VALUES(type)"); - query.setValue("channel", ci->name); - query.setValue("word", bw->word); - switch (bw->type) - { - case BW_SINGLE: - query.setValue("type", "SINGLE"); - break; - case BW_START: - query.setValue("type", "START"); - break; - case BW_END: - query.setValue("type", "END"); - break; - default: - query.setValue("type", "ANY"); - } - this->RunQuery(query); - } - - void OnBadWordDel(ChannelInfo *ci, BadWord *bw) - { - SQLQuery query("DELETE FROM `anope_bs_badwords` WHERE `channel` = @channel AND `word` = @word AND `type` = @type"); - query.setValue("channel", ci->name); - query.setValue("word", bw->word); - switch (bw->type) - { - case BW_SINGLE: - query.setValue("type", "SINGLE"); - break; - case BW_START: - query.setValue("type", "START"); - break; - case BW_END: - query.setValue("type", "END"); - break; - default: - query.setValue("type", "ANY"); - } - this->RunQuery(query); - } - - void OnMemoSend(const Anope::string &source, const Anope::string &target, MemoInfo *mi, Memo *m) - { - const Anope::string &mtype = (!target.empty() && target[0] == '#' ? "CHAN" : "NICK"); - SQLQuery query("INSERT INTO `anope_ms_info` (receiver, flags, time, sender, text, serv) VALUES(@receiver, @flags, @time, @sender, @text, @serv)"); - query.setValue("receiver", target); - query.setValue("flags", ToString(m->ToString())); - query.setValue("time", m->time); - query.setValue("sender", source); - query.setValue("text", m->text); - query.setValue("serv", mtype); - this->RunQuery(query); - } - - void OnMemoDel(const NickCore *nc, MemoInfo *mi, Memo *m) - { - SQLQuery query; - - if (m) - { - query = "DELETE FROM `anope_ms_info` WHERE `receiver` = @receiver AND `time` = @time"; - query.setValue("receiver", nc->display); - query.setValue("time", m->time); - } - else - { - query = "DELETE FROM `anope_ms_info` WHERE `receiver` = @receiver"; - query.setValue("receiver", nc->display); - } - - this->RunQuery(query); - } - - void OnMemoDel(ChannelInfo *ci, MemoInfo *mi, Memo *m) - { - SQLQuery query; - - if (m) - { - query = "DELETE FROM `anope_ms_info` WHERE `receiver` = @receiver AND `time` = @time"; - query.setValue("receiver", ci->name); - query.setValue("time", m->time); - } - else - { - query = "DELETE FROM `anope_ms_info` WHERE `receiver` = @receiver"; - query.setValue("receiver", ci->name); - } - - this->RunQuery(query); - } - - EventReturn OnExceptionAdd(Exception *ex) - { - SQLQuery query("INSERT INTO `anope_os_exceptions` (mask, slimit, who, reason, time, expires) VALUES(@mask, @slimit, @who, @reason, @time, @expires)"); - query.setValue("mask", ex->mask); - query.setValue("slimit", ex->limit); - query.setValue("who", ex->who); - query.setValue("reason", ex->reason); - query.setValue("time", ex->time); - query.setValue("expires", ex->expires); - return EVENT_CONTINUE; - } - - void OnExceptionDel(User *, Exception *ex) - { - SQLQuery query("DELETE FROM `anope_os_exceptions` WHERE `mask` = @mask"); - query.setValue("mask", ex->mask); - this->RunQuery(query); - } - - EventReturn OnAddXLine(XLine *x, XLineManager *xlm) - { - SQLQuery query("INSERT INTO `anope_os_xlines` (type, mask, xby, reason, seton, expire) VALUES(@type, @mask, @xby, @reason, @seton, @expire)"); - query.setValue("type", Anope::string(xlm->Type())); - query.setValue("mask", x->Mask); - query.setValue("xby", x->By); - query.setValue("reason", x->Reason); - query.setValue("seton", x->Created); - query.setValue("expire", x->Expires); - this->RunQuery(query); - return EVENT_CONTINUE; - } - - void OnDelXLine(User *, XLine *x, XLineManager *xlm) - { - SQLQuery query; - - if (x) - { - query = "DELETE FROM `anope_os_xlines` WHERE `mask` = @mask AND `type` = @type"; - query.setValue("mask", x->Mask); - query.setValue("type", Anope::string(xlm->Type())); - } - else - { - query = "DELETE FROM `anope_os_xlines` WHERE `type` = @type"; - query.setValue("type", Anope::string(xlm->Type())); - } - - this->RunQuery(query); - } - - void OnDeleteVhost(NickAlias *na) - { - SQLQuery query("DELETE FROM `anope_hs_core` WHERE `nick` = @nick"); - query.setValue("nick", na->nick); - this->RunQuery(query); - } - - void OnSetVhost(NickAlias *na) - { - SQLQuery query("INSERT INTO `anope_hs_core` (nick, vident, vhost, creator, time) VALUES(@nick, @vident, @vhost, @creator, @time)"); - query.setValue("nick", na->nick); - query.setValue("vident", na->hostinfo.GetIdent()); - query.setValue("vhost", na->hostinfo.GetHost()); - query.setValue("creator", na->hostinfo.GetCreator()); - query.setValue("time", na->hostinfo.GetTime()); - this->RunQuery(query); - } -}; - -void MySQLInterface::OnResult(const SQLResult &r) -{ - Log(LOG_DEBUG) << "MySQL successfully executed query: " << r.finished_query; -} - -void MySQLInterface::OnError(const SQLResult &r) -{ - if (!r.GetQuery().query.empty()) - Log(LOG_DEBUG) << "Error executing query " << r.finished_query << ": " << r.GetError(); - else - Log(LOG_DEBUG) << "Error executing query: " << r.GetError(); -} - - -static void Write(const Anope::string &data) -{ - SQLQuery query("INSERT INTO `anope_extra` (data) VALUES(@data)"); - query.setValue("data", data); - me->RunQuery(data); -} - -static void WriteNickMetadata(const Anope::string &key, const Anope::string &data) -{ - if (!CurNick) - throw CoreException("WriteNickMetadata without a nick to write"); - - SQLQuery query("INSERT INTO `anope_ns_alias_metadata` (nick, name, value) VALUES(@nick, @name, @value)"); - query.setValue("nick", CurNick->nick); - query.setValue("name", key); - query.setValue("value", data); - me->RunQuery(query); -} - -static void WriteCoreMetadata(const Anope::string &key, const Anope::string &data) -{ - if (!CurCore) - throw CoreException("WritCoreMetadata without a core to write"); - - SQLQuery query("INSERT INTO `anope_ns_core_metadata` (nick, name, value) VALUES(@nick, @name, @value)"); - query.setValue("nick", CurCore->display); - query.setValue("name", key); - query.setValue("value", data); - me->RunQuery(query); -} - -static void WriteChannelMetadata(const Anope::string &key, const Anope::string &data) -{ - if (!CurChannel) - throw CoreException("WriteChannelMetadata without a channel to write"); - - SQLQuery query("INSERT INTO `anope_cs_info_metadata` (channel, name, value) VALUES(@channel, @name, @value)"); - query.setValue("channel", CurChannel->name); - query.setValue("name", key); - query.setValue("value", data); - me->RunQuery(query); -} - -static void WriteBotMetadata(const Anope::string &key, const Anope::string &data) -{ - if (!CurBot) - throw CoreException("WriteBotMetadata without a bot to write"); - - SQLQuery query("INSERT INTO `anope_bs_info_metadata` (botname, name, value) VALUES(@botname, @name, @value)"); - query.setValue("botname", CurBot->nick); - query.setValue("name", key); - query.setValue("value", data); - me->RunQuery(query); -} - -static void SaveDatabases() -{ - SQLQuery query; - - query = "TRUNCATE TABLE `anope_ns_core`"; - me->RunQuery(query); - - query = "TRUNCATE TABLE `anope_ms_info`"; - me->RunQuery(query); - - query = "TRUNCATE TABLE `anope_ns_alias`"; - me->RunQuery(query); - - for (nickcore_map::const_iterator nit = NickCoreList.begin(), nit_end = NickCoreList.end(); nit != nit_end; ++nit) - { - NickCore *nc = nit->second; - - me->InsertCore(nc); - - for (std::list<NickAlias *>::iterator it = nc->aliases.begin(), it_end = nc->aliases.end(); it != it_end; ++it) - { - me->InsertAlias(*it); - if ((*it)->hostinfo.HasVhost()) - me->OnSetVhost(*it); - } - - for (std::vector<Anope::string>::iterator it = nc->access.begin(), it_end = nc->access.end(); it != it_end; ++it) - { - query = "INSERT INTO `anope_ns_access` (display, access) VALUES(@display, @access)"; - query.setValue("display", nc->display); - query.setValue("access", *it); - me->RunQuery(query); - } - - for (unsigned j = 0, end = nc->memos.memos.size(); j < end; ++j) - { - Memo *m = nc->memos.memos[j]; - - me->OnMemoSend(m->sender, nc->display, &nc->memos, m); - } - } - - query = "TRUNCATE TABLE `anope_bs_core`"; - me->RunQuery(query); - - for (Anope::insensitive_map<BotInfo *>::const_iterator it = BotListByNick.begin(), it_end = BotListByNick.end(); it != it_end; ++it) - me->OnBotCreate(it->second); - - query = "TRUNCATE TABLE `anope_cs_info`"; - me->RunQuery(query); - - query = "TRUNCATE TABLE `anope_bs_badwords`"; - me->RunQuery(query); - - query = "TRUNCATE TABLE `anope_cs_access`"; - me->RunQuery(query); - - query = "TRUNCATE TABLE `anope_cs_akick`"; - me->RunQuery(query); - - query = "TRUNCATE TABLE `anope_cs_levels`"; - me->RunQuery(query); - - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ++it) - { - ChannelInfo *ci = it->second; - - me->OnChanRegistered(ci); - - for (unsigned j = 0, end = ci->GetBadWordCount(); j < end; ++j) - { - BadWord *bw = ci->GetBadWord(j); - - me->OnBadWordAdd(ci, bw); - } - - for (unsigned j = 0, end = ci->GetAccessCount(); j < end; ++j) - { - ChanAccess *access = ci->GetAccess(j); - - me->OnAccessAdd(ci, NULL, access); - } - - for (unsigned j = 0, end = ci->GetAkickCount(); j < end; ++j) - { - AutoKick *ak = ci->GetAkick(j); - - me->OnAkickAdd(ci, ak); - } - - for (int k = 0; k < CA_SIZE; ++k) - me->OnLevelChange(NULL, ci, -1, -1); - - for (unsigned j = 0, end = ci->memos.memos.size(); j < end; ++j) - { - Memo *m = ci->memos.memos[j]; - - me->OnMemoSend(m->sender, ci->name, &ci->memos, m); - } - } - - for (std::list<XLineManager *>::iterator it = XLineManager::XLineManagers.begin(), it_end = XLineManager::XLineManagers.end(); it != it_end; ++it) - for (unsigned i = 0, end = (*it)->GetCount(); i < end; ++i) - me->OnAddXLine((*it)->GetEntry(i), *it); - - if (me->SessionInterface) - for (SessionService::ExceptionVector::iterator it = me->SessionInterface->GetExceptions().begin(); it != me->SessionInterface->GetExceptions().end(); ++it) - me->OnExceptionAdd(*it); -} - -void CommandSQLSync::Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) -{ - SaveDatabases(); - source.Reply(_("Updating MySQL.")); - return; -} - -MODULE_INIT(DBMySQL) - diff --git a/modules/core/db_mysql_live.cpp b/modules/core/db_mysql_live.cpp deleted file mode 100644 index ecfdc70d1..000000000 --- a/modules/core/db_mysql_live.cpp +++ /dev/null @@ -1,287 +0,0 @@ -#include "module.h" -#include "../extra/async_commands.h" -#include "../extra/sql.h" - -class SQLCache : public Timer -{ - typedef std::map<Anope::string, time_t, std::less<ci::string> > cache_map; - cache_map cache; - public: - - SQLCache() : Timer(300, Anope::CurTime, true) { } - - bool Check(const Anope::string &item) - { - cache_map::iterator it = this->cache.find(item); - if (it != this->cache.end() && Anope::CurTime - it->second < 5) - return true; - - this->cache[item] = Anope::CurTime; - return false; - } - - void Tick(time_t) - { - for (cache_map::iterator it = this->cache.begin(), next_it; it != this->cache.end(); it = next_it) - { - next_it = it; - ++next_it; - - if (Anope::CurTime - it->second > 5) - this->cache.erase(it); - } - } -}; - -static void ChanInfoUpdate(const SQLResult &res) -{ - try - { - ChannelInfo *ci = cs_findchan(res.Get(0, "name")); - if (!ci) - ci = new ChannelInfo(res.Get(0, "name")); - ci->SetFounder(findcore(res.Get(0, "founder"))); - ci->successor = findcore(res.Get(0, "successor")); - ci->desc = res.Get(0, "descr"); - ci->time_registered = convertTo<time_t>(res.Get(0, "time_registered")); - ci->ClearFlags(); - ci->FromString(BuildStringVector(res.Get(0, "flags"))); - ci->bantype = convertTo<int>(res.Get(0, "bantype")); - ci->memos.memomax = convertTo<unsigned>(res.Get(0, "memomax")); - - if (res.Get(0, "botnick").equals_cs(ci->bi ? ci->bi->nick : "") == false) - { - if (ci->bi) - ci->bi->UnAssign(NULL, ci); - BotInfo *bi = findbot(res.Get(0, "botnick")); - if (bi) - bi->Assign(NULL, ci); - } - - ci->capsmin = convertTo<int16>(res.Get(0, "capsmin")); - ci->capspercent = convertTo<int16>(res.Get(0, "capspercent")); - ci->floodlines = convertTo<int16>(res.Get(0, "floodlines")); - ci->floodsecs = convertTo<int16>(res.Get(0, "floodsecs")); - ci->repeattimes = convertTo<int16>(res.Get(0, "repeattimes")); - - if (ci->c) - check_modes(ci->c); - } - catch (const SQLException &ex) - { - Log(LOG_DEBUG) << ex.GetReason(); - } - catch (const ConvertException &) { } -} - -static void NickInfoUpdate(const SQLResult &res) -{ - try - { - NickCore *nc = findcore(res.Get(0, "display")); - if (!nc) - return; - NickAlias *na = findnick(res.Get(0, "nick")); - if (!na) - na = new NickAlias(res.Get(0, "nick"), nc); - - na->last_quit = res.Get(0, "last_quit"); - na->last_realname = res.Get(0, "last_realname"); - na->last_usermask = res.Get(0, "last_usermask"); - na->time_registered = convertTo<time_t>(res.Get(0, "time_registered")); - na->last_seen = convertTo<time_t>(res.Get(0, "last_seen")); - na->ClearFlags(); - na->FromString(BuildStringVector(res.Get(0, "flags"))); - - if (na->nc != nc) - { - std::list<NickAlias *>::iterator it = std::find(na->nc->aliases.begin(), na->nc->aliases.end(), na); - if (it != na->nc->aliases.end()) - na->nc->aliases.erase(it); - - na->nc = nc; - na->nc->aliases.push_back(na); - } - } - catch (const SQLException &ex) - { - Log(LOG_DEBUG) << ex.GetReason(); - } - catch (const ConvertException &) { } -} - -static void NickCoreUpdate(const SQLResult &res) -{ - try - { - NickCore *nc = findcore(res.Get(0, "display")); - if (!nc) - nc = new NickCore(res.Get(0, "display")); - - nc->pass = res.Get(0, "pass"); - nc->email = res.Get(0, "email"); - nc->greet = res.Get(0, "greet"); - nc->ClearFlags(); - nc->FromString(BuildStringVector(res.Get(0, "flags"))); - nc->language = res.Get(0, "language"); - } - catch (const SQLException &ex) - { - Log(LOG_DEBUG) << ex.GetReason(); - } - catch (const ConvertException &) { } -} - -class MySQLLiveModule : public Module -{ - service_reference<SQLProvider> SQL; - service_reference<AsynchCommandsService> ACS; - - SQLCache chan_cache, nick_cache, core_cache; - - SQLResult RunQuery(const SQLQuery &query) - { - if (!this->SQL) - throw SQLException("Unable to locate SQL reference, is m_mysql loaded and configured correctly?"); - - SQLResult res = SQL->RunQuery(query); - if (!res.GetError().empty()) - throw SQLException(res.GetError()); - return res; - } - - CommandMutex *CurrentCommand() - { - if (this->ACS) - return this->ACS->CurrentCommand(); - return NULL; - } - - public: - MySQLLiveModule(const Anope::string &modname, const Anope::string &creator) : - Module(modname, creator, DATABASE), SQL("mysql/main"), ACS("asynch_commands") - { - Implementation i[] = { I_OnFindChan, I_OnFindNick, I_OnFindCore, I_OnShutdown }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - void OnShutdown() - { - Implementation i[] = { I_OnFindChan, I_OnFindNick, I_OnFindCore }; - for (size_t j = 0; j < 3; ++j) - ModuleManager::Detach(i[j], this); - } - - void OnFindChan(const Anope::string &chname) - { - if (chan_cache.Check(chname)) - return; - - try - { - SQLQuery query("SELECT * FROM `anope_cs_info` WHERE `name` = @name"); - query.setValue("name", chname); - CommandMutex *current_command = this->CurrentCommand(); - if (current_command) - { - current_command->Unlock(); - try - { - SQLResult res = this->RunQuery(query); - current_command->Lock(); - ChanInfoUpdate(res); - } - catch (const SQLException &) - { - current_command->Lock(); - throw; - } - } - else - { - SQLResult res = this->RunQuery(query); - ChanInfoUpdate(res); - } - } - catch (const SQLException &ex) - { - Log(LOG_DEBUG) << "OnFindChan: " << ex.GetReason(); - } - } - - void OnFindNick(const Anope::string &nick) - { - if (nick_cache.Check(nick)) - return; - - try - { - SQLQuery query("SELECT * FROM `anope_ns_alias` WHERE `nick` = @nick"); - query.setValue("nick", nick); - CommandMutex *current_command = this->CurrentCommand(); - if (current_command) - { - current_command->Unlock(); - try - { - SQLResult res = this->RunQuery(query); - current_command->Lock(); - NickInfoUpdate(res); - } - catch (const SQLException &) - { - current_command->Lock(); - throw; - } - } - else - { - SQLResult res = this->RunQuery(query); - NickInfoUpdate(res); - } - } - catch (const SQLException &ex) - { - Log(LOG_DEBUG) << "OnFindNick: " << ex.GetReason(); - } - } - - void OnFindCore(const Anope::string &nick) - { - if (core_cache.Check(nick)) - return; - - try - { - SQLQuery query("SELECT * FROM `anope_ns_core` WHERE `display` = @display"); - query.setValue("display", nick); - CommandMutex *current_command = this->CurrentCommand(); - if (current_command) - { - current_command->Unlock(); - try - { - SQLResult res = this->RunQuery(query); - current_command->Lock(); - NickCoreUpdate(res); - } - catch (const SQLException &) - { - current_command->Lock(); - throw; - } - } - else - { - SQLResult res = this->RunQuery(query); - NickCoreUpdate(res); - } - } - catch (const SQLException &ex) - { - Log(LOG_DEBUG) << "OnFindCore: " << ex.GetReason(); - } - } -}; - -MODULE_INIT(MySQLLiveModule) diff --git a/modules/core/db_plain.cpp b/modules/core/db_plain.cpp deleted file mode 100644 index c41cea2d2..000000000 --- a/modules/core/db_plain.cpp +++ /dev/null @@ -1,908 +0,0 @@ -/* - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "os_session.h" - -Anope::string DatabaseFile; -std::stringstream db_buffer; -service_reference<SessionService> SessionInterface("session"); - -/** Enum used for what METADATA type we are reading - */ -enum MDType -{ - MD_NONE, - MD_NC, - MD_NA, - MD_BI, - MD_CH -}; - -/* Character for newlines, in my research I have concluded it is significantly faster - * to use \n instead of std::endl because std::endl also flushes the buffer, which - * is not necessary here - */ -static const char endl = '\n'; - -/** Read from the database and call the events - * @param m If specified it only calls the read events for the specific module - */ -static void ReadDatabase(Module *m = NULL) -{ - EventReturn MOD_RESULT; - MDType Type = MD_NONE; - - std::fstream db; - db.open(DatabaseFile.c_str(), std::ios_base::in); - - if (!db.is_open()) - { - Log() << "Unable to open " << DatabaseFile << " for reading!"; - return; - } - - NickCore *nc = NULL; - NickAlias *na = NULL; - BotInfo *bi = NULL; - ChannelInfo *ci = NULL; - - Anope::string buf; - while (std::getline(db, buf.str())) - { - if (buf.empty()) - continue; - - spacesepstream sep(buf); - std::vector<Anope::string> params; - while (sep.GetToken(buf)) - { - if (buf[0] == ':') - { - buf.erase(buf.begin()); - if (!buf.empty() && !sep.StreamEnd()) - params.push_back(buf + " " + sep.GetRemaining()); - else if (!sep.StreamEnd()) - params.push_back(sep.GetRemaining()); - else if (!buf.empty()) - params.push_back(buf); - break; - } - else - params.push_back(buf); - } - - if (m) - MOD_RESULT = m->OnDatabaseRead(params); - else - FOREACH_RESULT(I_OnDatabaseRead, OnDatabaseRead(params)); - if (MOD_RESULT == EVENT_STOP) - continue; - - if (!params.empty()) - { - if (params[0].equals_ci("NC")) - { - nc = findcore(params[1]); - Type = MD_NC; - } - else if (params[0].equals_ci("NA")) - { - na = findnick(params[2]); - Type = MD_NA; - } - else if (params[0].equals_ci("BI")) - { - bi = findbot(params[1]); - Type = MD_BI; - } - else if (params[0].equals_ci("CH")) - { - ci = cs_findchan(params[1]); - Type = MD_CH; - } - else if (params[0].equals_ci("MD")) - { - Anope::string key = params[1]; - params.erase(params.begin()); - params.erase(params.begin()); - - if (Type == MD_NC && nc) - { - try - { - if (m) - m->OnDatabaseReadMetadata(nc, key, params); - else - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(nc, key, params)); - } - catch (const DatabaseException &ex) - { - Log() << "[db_plain]: " << ex.GetReason(); - } - } - else if (Type == MD_NA && na) - { - try - { - if (m) - m->OnDatabaseReadMetadata(na, key, params); - else - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(na, key, params)); - } - catch (const DatabaseException &ex) - { - Log() << "[db_plain]: " << ex.GetReason(); - } - } - else if (Type == MD_BI && bi) - { - try - { - if (m) - m->OnDatabaseReadMetadata(bi, key, params); - else - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(bi, key, params)); - } - catch (const DatabaseException &ex) - { - Log() << "[db_plain]: " << ex.GetReason(); - } - } - else if (Type == MD_CH && ci) - { - try - { - if (m) - m->OnDatabaseReadMetadata(ci, key, params); - else - FOREACH_RESULT(I_OnDatabaseReadMetadata, OnDatabaseReadMetadata(ci, key, params)); - } - catch (const DatabaseException &ex) - { - Log() << "[db_plain]: " << ex.GetReason(); - } - } - } - } - } - - db.close(); -} - -struct ChannelLevel -{ - ChannelAccess Level; - Anope::string Name; -}; - -ChannelLevel ChannelLevels[] = { - { CA_ACCESS_LIST, "ACCESS_LIST" }, - { CA_NOKICK, "NOKICK" }, - { CA_FANTASIA, "FANTASIA" }, - { CA_GREET, "GREET" }, - { CA_AUTOVOICE, "AUTOVOICE" }, - { CA_VOICEME, "VOICEME" }, - { CA_VOICE, "VOICE" }, - { CA_INFO, "INFO" }, - { CA_SAY, "SAY" }, - { CA_AUTOHALFOP, "AUTOHALFOP" }, - { CA_HALFOPME, "HALFOPME" }, - { CA_HALFOP, "HALFOP" }, - { CA_KICK, "KICK" }, - { CA_SIGNKICK, "SIGNKICK" }, - { CA_BAN, "BAN" }, - { CA_TOPIC, "TOPIC" }, - { CA_MODE, "MODE" }, - { CA_GETKEY, "GETKEY" }, - { CA_INVITE, "INVITE" }, - { CA_UNBAN, "UNBAN" }, - { CA_AUTOOP, "AUTOOP" }, - { CA_OPDEOPME, "OPDEOPME" }, - { CA_OPDEOP, "OPDEOP" }, - { CA_AUTOPROTECT, "AUTOPROTECT" }, - { CA_AKICK, "AKICK" }, - { CA_BADWORDS, "BADWORDS" }, - { CA_ASSIGN, "ASSIGN" }, - { CA_MEMO, "MEMO" }, - { CA_ACCESS_CHANGE, "ACCESS_CHANGE" }, - { CA_PROTECTME, "PROTECTME" }, - { CA_PROTECT, "PROTECT" }, - { CA_SET, "SET" }, - { CA_AUTOOWNER, "AUTOPROTECT" }, - { CA_OWNERME, "OWNERME" }, - { CA_OWNER, "OWNER" }, - { CA_FOUNDER, "FOUNDER" }, - { CA_SIZE, "" } -}; - -static Anope::string ToString(const std::vector<Anope::string> &strings) -{ - Anope::string ret; - - for (unsigned i = 0; i < strings.size(); ++i) - ret += " " + strings[i]; - - if (!ret.empty()) - ret.erase(ret.begin()); - - return ret; -} - -static void LoadNickCore(const std::vector<Anope::string> ¶ms) -{ - NickCore *nc = new NickCore(params[0]); - /* Clear default flags */ - nc->ClearFlags(); - - nc->pass = params.size() > 1 ? params[1] : ""; - - Log(LOG_DEBUG_2) << "[db_plain]: Loaded NickCore " << nc->display; -} - -static void LoadNickAlias(const std::vector<Anope::string> ¶ms) -{ - NickCore *nc = findcore(params[0]); - if (!nc) - { - Log() << "[db_plain]: Unable to find core " << params[0]; - return; - } - - NickAlias *na = new NickAlias(params[1], nc); - - na->time_registered = params[2].is_pos_number_only() ? convertTo<time_t>(params[2]) : 0; - - na->last_seen = params[3].is_pos_number_only() ? convertTo<time_t>(params[3]) : 0; - - Log(LOG_DEBUG_2) << "[db_plain}: Loaded nickalias for " << na->nick; -} - -static void LoadBotInfo(const std::vector<Anope::string> ¶ms) -{ - BotInfo *bi = findbot(params[0]); - if (!bi) - bi = new BotInfo(params[0], params[1], params[2]); - - bi->created = params[3].is_pos_number_only() ? convertTo<time_t>(params[3]) : 0; - bi->chancount = params[4].is_pos_number_only() ? convertTo<uint32>(params[4]) : 0; - bi->realname = params[5]; - - Log(LOG_DEBUG_2) << "[db_plain]: Loaded botinfo for " << bi->nick; -} - -static void LoadChanInfo(const std::vector<Anope::string> ¶ms) -{ - ChannelInfo *ci = new ChannelInfo(params[0]); - /* CLear default mlock */ - ci->ClearMLock(); - /* Remove default channel flags */ - ci->ClearFlags(); - ci->botflags.ClearFlags(); - - ci->time_registered = params[1].is_pos_number_only() ? convertTo<time_t>(params[1]) : 0; - - ci->last_used = params[2].is_pos_number_only() ? convertTo<time_t>(params[2]) : 0; - - Log(LOG_DEBUG_2) << "[db_plain]: loaded channel " << ci->name; -} - -static void LoadOperInfo(const std::vector<Anope::string> ¶ms) -{ - if (params[0].equals_ci("STATS")) - { - maxusercnt = params[1].is_pos_number_only() ? convertTo<uint32>(params[1]) : 0; - maxusertime = params[2].is_pos_number_only() ? convertTo<time_t>(params[2]) : 0; - } - else if (params[0].equals_ci("SXLINE")) - { - char type = params[1][0]; - for (std::list<XLineManager *>::iterator it = XLineManager::XLineManagers.begin(), it_end = XLineManager::XLineManagers.end(); it != it_end; ++it) - { - XLineManager *xl = *it; - if (xl->Type() == type) - { - Anope::string mask = params[2]; - Anope::string by = params[3]; - time_t seton = params[4].is_pos_number_only() ? convertTo<time_t>(params[4]) : 0; - time_t expires = params[5].is_pos_number_only() ? convertTo<time_t>(params[5]) : 0; - Anope::string reason = params[6]; - - XLine *x = xl->Add(mask, by, expires, reason); - if (x) - x->Created = seton; - break; - } - } - } - else if (params[0].equals_ci("EXCEPTION") && SessionInterface) - { - Exception *exception = new Exception(); - exception->mask = params[1]; - exception->limit = params[2].is_pos_number_only() ? convertTo<int>(params[2]) : 1; - exception->who = params[3]; - exception->time = params[4].is_pos_number_only() ? convertTo<time_t>(params[4]) : 0; - exception->expires = params[5].is_pos_number_only() ? convertTo<time_t>(params[5]) : 0; - exception->reason = params[6]; - SessionInterface->AddException(exception); - } -} - -void Write(const Anope::string &buf) -{ - db_buffer << buf << endl; -} - -void WriteMetadata(const Anope::string &key, const Anope::string &data) -{ - Write("MD " + key + " " + data); -} - -class DBPlain : public Module -{ - /* Day the last backup was on */ - int LastDay; - /* Backup file names */ - std::list<Anope::string> Backups; - public: - DBPlain(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, DATABASE) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnReload, I_OnDatabaseRead, I_OnLoadDatabase, I_OnDatabaseReadMetadata, I_OnSaveDatabase, I_OnModuleLoad }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - OnReload(); - - LastDay = 0; - } - - ~DBPlain() - { - } - - void BackupDatabase() - { - /* Do not backup a database that doesn't exist */ - if (!IsFile(DatabaseFile)) - return; - - time_t now = Anope::CurTime; - tm *tm = localtime(&now); - - if (tm->tm_mday != LastDay) - { - LastDay = tm->tm_mday; - Anope::string newname = "backups/" + DatabaseFile + "." + stringify(tm->tm_year) + stringify(tm->tm_mon) + stringify(tm->tm_mday); - - /* Backup already exists */ - if (IsFile(newname)) - return; - - Log(LOG_DEBUG) << "db_plain: Attemping to rename " << DatabaseFile << " to " << newname; - if (rename(DatabaseFile.c_str(), newname.c_str())) - { - Log() << "Unable to back up database!"; - - if (!Config->NoBackupOkay) - quitting = true; - - return; - } - - Backups.push_back(newname); - - unsigned KeepBackups = Config->KeepBackups; - if (KeepBackups && Backups.size() > KeepBackups) - { - DeleteFile(Backups.front().c_str()); - Backups.pop_front(); - } - } - } - - void OnReload() - { - ConfigReader config; - DatabaseFile = config.ReadValue("db_plain", "database", "anope.db", 0); - } - - EventReturn OnDatabaseRead(const std::vector<Anope::string> ¶ms) - { - Anope::string key = params[0]; - std::vector<Anope::string> otherparams = params; - otherparams.erase(otherparams.begin()); - - if (key.equals_ci("NC")) - LoadNickCore(otherparams); - else if (key.equals_ci("NA")) - LoadNickAlias(otherparams); - else if (key.equals_ci("BI")) - LoadBotInfo(otherparams); - else if (key.equals_ci("CH")) - LoadChanInfo(otherparams); - else if (key.equals_ci("OS")) - LoadOperInfo(otherparams); - - return EVENT_CONTINUE; - } - - EventReturn OnLoadDatabase() - { - ReadDatabase(); - - /* No need to ever reload this again, although this should never be trigged again */ - ModuleManager::Detach(I_OnLoadDatabase, this); - ModuleManager::Detach(I_OnDatabaseReadMetadata, this); - - return EVENT_STOP; - } - - EventReturn OnDatabaseReadMetadata(NickCore *nc, const Anope::string &key, const std::vector<Anope::string> ¶ms) - { - try - { - if (key.equals_ci("LANGUAGE")) - nc->language = params[0]; - else if (key.equals_ci("MEMOMAX")) - nc->memos.memomax = params[0].is_pos_number_only() ? convertTo<int16>(params[0]) : -1; - else if (key.equals_ci("EMAIL")) - nc->email = params[0]; - else if (key.equals_ci("GREET")) - nc->greet = params[0]; - else if (key.equals_ci("ACCESS")) - nc->AddAccess(params[0]); - else if (key.equals_ci("CERT")) - nc->AddCert(params[0]); - else if (key.equals_ci("FLAGS")) - nc->FromString(params); - else if (key.equals_ci("MI")) - { - Memo *m = new Memo; - m->time = params[0].is_pos_number_only() ? convertTo<time_t>(params[0]) : 0; - m->sender = params[1]; - for (unsigned j = 2; params[j].equals_ci("UNREAD") || params[j].equals_ci("RECEIPT"); ++j) - { - if (params[j].equals_ci("UNREAD")) - m->SetFlag(MF_UNREAD); - else if (params[j].equals_ci("RECEIPT")) - m->SetFlag(MF_RECEIPT); - } - m->text = params[params.size() - 1]; - nc->memos.memos.push_back(m); - } - else if (key.equals_ci("MIG")) - nc->memos.ignores.push_back(params[0].ci_str()); - } - catch (const ConvertException &ex) - { - throw DatabaseException(ex.GetReason()); - } - - return EVENT_CONTINUE; - } - - EventReturn OnDatabaseReadMetadata(NickAlias *na, const Anope::string &key, const std::vector<Anope::string> ¶ms) - { - if (key.equals_ci("LAST_USERMASK")) - na->last_usermask = params[0]; - else if (key.equals_ci("LAST_REALNAME")) - na->last_realname = params[0]; - else if (key.equals_ci("LAST_QUIT")) - na->last_quit = params[0]; - else if (key.equals_ci("FLAGS")) - na->FromString(params); - else if (key.equals_ci("VHOST")) - na->hostinfo.SetVhost(params.size() > 3 ? params[3] : "", params[2], params[0], params[1].is_pos_number_only() ? convertTo<time_t>(params[1]) : 0); - - return EVENT_CONTINUE; - } - - EventReturn OnDatabaseReadMetadata(BotInfo *bi, const Anope::string &key, const std::vector<Anope::string> ¶ms) - { - if (key.equals_ci("FLAGS")) - bi->FromString(params); - - return EVENT_CONTINUE; - } - - EventReturn OnDatabaseReadMetadata(ChannelInfo *ci, const Anope::string &key, const std::vector<Anope::string> ¶ms) - { - try - { - if (key.equals_ci("BANTYPE")) - ci->bantype = params[0].is_pos_number_only() ? convertTo<int16>(params[0]) : Config->CSDefBantype; - else if (key.equals_ci("MEMOMAX")) - ci->memos.memomax = params[0].is_pos_number_only() ? convertTo<int16>(params[0]) : -1; - else if (key.equals_ci("FOUNDER")) - ci->SetFounder(findcore(params[0])); - else if (key.equals_ci("SUCCESSOR")) - ci->successor = findcore(params[0]); - else if (key.equals_ci("LEVELS")) - { - for (unsigned j = 0, end = params.size(); j < end; j += 2) - for (int i = 0; ChannelLevels[i].Level != CA_SIZE; ++i) - if (params[j].equals_ci(ChannelLevels[i].Name)) - ci->levels[ChannelLevels[i].Level] = params[j + 1].is_number_only() ? convertTo<int16>(params[j + 1]) : 0; - } - else if (key.equals_ci("FLAGS")) - ci->FromString(params); - else if (key.equals_ci("DESC")) - ci->desc = params[0]; - else if (key.equals_ci("TOPIC")) - { - ci->last_topic_setter = params[0]; - ci->last_topic_time = params[1].is_pos_number_only() ? convertTo<time_t>(params[1]) : 0; - ci->last_topic = params[2]; - } - else if (key.equals_ci("SUSPEND")) - { - ci->Extend("suspend_by", new ExtensibleItemRegular<Anope::string>(params[0])); - ci->Extend("suspend_reason", new ExtensibleItemRegular<Anope::string>(params[1])); - } - else if (key.equals_ci("ACCESS")) - { - service_reference<AccessProvider> provider(params[0]); - if (!provider) - throw DatabaseException("Access entry for nonexistant provider " + params[0]); - - ChanAccess *access = provider->Create(); - access->ci = ci; - access->mask = params[1]; - access->Unserialize(params[2]); - access->last_seen = params[3].is_pos_number_only() ? convertTo<time_t>(params[3]) : 0; - access->creator = params[4]; - access->created = params.size() > 5 && params[5].is_pos_number_only() ? convertTo<time_t>(params[5]) : Anope::CurTime; - - ci->AddAccess(access); - } - else if (key.equals_ci("AKICK")) - { - // 0 is the old stuck - bool Nick = params[1].equals_ci("NICK"); - NickCore *nc = NULL; - if (Nick) - { - nc = findcore(params[2]); - if (!nc) - throw DatabaseException("Akick for nonexistant core " + params[2] + " on " + ci->name); - } - - AutoKick *ak; - if (Nick) - ak = ci->AddAkick(params[3], nc, params.size() > 6 ? params[6] : "", params[4].is_pos_number_only() ? convertTo<time_t>(params[4]) : 0, params[5].is_pos_number_only() ? convertTo<time_t>(params[5]) : 0); - else - ak = ci->AddAkick(params[3], params[2], params.size() > 6 ? params[6] : "", params[4].is_pos_number_only() ? convertTo<time_t>(params[4]) : 0, params[5].is_pos_number_only() ? convertTo<time_t>(params[5]) : 0); - if (Nick) - ak->SetFlag(AK_ISNICK); - - } - else if (key.equals_ci("MLOCK")) - { - std::vector<Anope::string> mlocks; - ci->GetExtRegular("db_mlock", mlocks); - - Anope::string mlock_string = params[0] + " " + params[1] + " " + params[2] + " " + params[3]; - if (params.size() > 4) - mlock_string += " " + params[4]; - - mlocks.push_back(mlock_string); - ci->Extend("db_mlock", new ExtensibleItemRegular<std::vector<Anope::string> >(mlocks)); - } - else if (key.equals_ci("MI")) - { - Memo *m = new Memo; - m->time = params[0].is_pos_number_only() ? convertTo<time_t>(params[0]) : 0; - m->sender = params[1]; - for (unsigned j = 2; params[j].equals_ci("UNREAD") || params[j].equals_ci("RECEIPT"); ++j) - { - if (params[j].equals_ci("UNREAD")) - m->SetFlag(MF_UNREAD); - else if (params[j].equals_ci("RECEIPT")) - m->SetFlag(MF_RECEIPT); - } - m->text = params[params.size() - 1]; - ci->memos.memos.push_back(m); - } - else if (key.equals_ci("MIG")) - ci->memos.ignores.push_back(params[0].ci_str()); - else if (key.equals_ci("BI")) - { - if (params[0].equals_ci("NAME")) - ci->bi = findbot(params[1]); - else if (params[0].equals_ci("FLAGS")) - ci->botflags.FromString(params); - else if (params[0].equals_ci("TTB")) - { - for (unsigned j = 1, end = params.size(); j < end; j += 2) - { - if (params[j].equals_ci("BOLDS")) - ci->ttb[0] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("COLORS")) - ci->ttb[1] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("REVERSES")) - ci->ttb[2] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("UNDERLINES")) - ci->ttb[3] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("BADWORDS")) - ci->ttb[4] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("CAPS")) - ci->ttb[5] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("FLOOD")) - ci->ttb[6] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("REPEAT")) - ci->ttb[7] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("ITALICS")) - ci->ttb[8] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - else if (params[j].equals_ci("AMSGS")) - ci->ttb[9] = params[j + 1].is_pos_number_only() ? convertTo<int16>(params[j + 1]) : 0; - } - } - else if (params[0].equals_ci("CAPSMIN")) - ci->capsmin = params[1].is_pos_number_only() ? convertTo<int16>(params[1]) : 0; - else if (params[0].equals_ci("CAPSPERCENT")) - ci->capspercent = params[1].is_pos_number_only() ? convertTo<int16>(params[1]) : 0; - else if (params[0].equals_ci("FLOODLINES")) - ci->floodlines = params[1].is_pos_number_only() ? convertTo<int16>(params[1]) : 0; - else if (params[0].equals_ci("FLOODSECS")) - ci->floodsecs = params[1].is_pos_number_only() ? convertTo<int16>(params[1]) : 0; - else if (params[0].equals_ci("REPEATTIMES")) - ci->repeattimes = params[1].is_pos_number_only() ? convertTo<int16>(params[1]) : 0; - else if (params[0].equals_ci("BADWORD")) - { - BadWordType Type; - if (params[1].equals_ci("SINGLE")) - Type = BW_SINGLE; - else if (params[1].equals_ci("START")) - Type = BW_START; - else if (params[1].equals_ci("END")) - Type = BW_END; - else - Type = BW_ANY; - ci->AddBadWord(params[2], Type); - } - } - } - catch (const ConvertException &ex) - { - throw DatabaseException(ex.GetReason()); - } - - return EVENT_CONTINUE; - } - - EventReturn OnSaveDatabase() - { - BackupDatabase(); - - db_buffer << "VER 2" << endl; - - for (nickcore_map::const_iterator nit = NickCoreList.begin(), nit_end = NickCoreList.end(); nit != nit_end; ++nit) - { - NickCore *nc = nit->second; - - db_buffer << "NC " << nc->display << " " << nc->pass << endl; - - db_buffer << "MD MEMOMAX " << nc->memos.memomax << endl; - - if (!nc->language.empty()) - db_buffer << "MD LANGUAGE " << nc->language << endl; - if (!nc->email.empty()) - db_buffer << "MD EMAIL " << nc->email << endl; - if (!nc->greet.empty()) - db_buffer << "MD GREET :" << nc->greet << endl; - - if (!nc->access.empty()) - { - for (std::vector<Anope::string>::iterator it = nc->access.begin(), it_end = nc->access.end(); it != it_end; ++it) - db_buffer << "MD ACCESS " << *it << endl; - } - if (!nc->cert.empty()) - { - for (std::vector<Anope::string>::iterator it = nc->cert.begin(), it_end = nc->cert.end(); it != it_end; ++it) - db_buffer << "MD CERT " << *it << endl; - } - if (nc->FlagCount()) - db_buffer << "MD FLAGS " << ToString(nc->ToString()) << endl; - MemoInfo *mi = &nc->memos; - for (unsigned k = 0, end = mi->memos.size(); k < end; ++k) - { - db_buffer << "MD MI " << mi->memos[k]->time << " " << mi->memos[k]->sender; - if (mi->memos[k]->HasFlag(MF_UNREAD)) - db_buffer << " UNREAD"; - if (mi->memos[k]->HasFlag(MF_RECEIPT)) - db_buffer << " RECEIPT"; - db_buffer << " :" << mi->memos[k]->text << endl; - } - for (unsigned k = 0, end = mi->ignores.size(); k < end; ++k) - db_buffer << "MD MIG " << Anope::string(mi->ignores[k]) << endl; - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteMetadata, nc)); - } - - for (nickalias_map::const_iterator it = NickAliasList.begin(), it_end = NickAliasList.end(); it != it_end; ++it) - { - NickAlias *na = it->second; - - db_buffer << "NA " << na->nc->display << " " << na->nick << " " << na->time_registered << " " << na->last_seen << endl; - if (!na->last_usermask.empty()) - db_buffer << "MD LAST_USERMASK " << na->last_usermask << endl; - if (!na->last_realname.empty()) - db_buffer << "MD LAST_REALNAME :" << na->last_realname << endl; - if (!na->last_quit.empty()) - db_buffer << "MD LAST_QUIT :" << na->last_quit << endl; - if (na->FlagCount()) - db_buffer << "MD FLAGS " << ToString(na->ToString()) << endl; - if (na->hostinfo.HasVhost()) - db_buffer << "MD VHOST " << na->hostinfo.GetCreator() << " " << na->hostinfo.GetTime() << " " << na->hostinfo.GetHost() << " :" << na->hostinfo.GetIdent() << endl; - - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteMetadata, na)); - } - - for (Anope::insensitive_map<BotInfo *>::const_iterator it = BotListByNick.begin(), it_end = BotListByNick.end(); it != it_end; ++it) - { - BotInfo *bi = it->second; - - if (bi->HasFlag(BI_CONF)) - continue; - - db_buffer << "BI " << bi->nick << " " << bi->GetIdent() << " " << bi->host << " " << bi->created << " " << bi->chancount << " :" << bi->realname << endl; - if (bi->FlagCount()) - db_buffer << "MD FLAGS " << ToString(bi->ToString()) << endl; - } - - for (registered_channel_map::const_iterator cit = RegisteredChannelList.begin(), cit_end = RegisteredChannelList.end(); cit != cit_end; ++cit) - { - ChannelInfo *ci = cit->second; - - db_buffer << "CH " << ci->name << " " << ci->time_registered << " " << ci->last_used << endl; - db_buffer << "MD BANTYPE " << ci->bantype << endl; - db_buffer << "MD MEMOMAX " << ci->memos.memomax << endl; - if (ci->GetFounder()) - db_buffer << "MD FOUNDER " << ci->GetFounder()->display << endl; - if (ci->successor) - db_buffer << "MD SUCCESSOR " << ci->successor->display << endl; - if (!ci->desc.empty()) - db_buffer << "MD DESC :" << ci->desc << endl; - if (!ci->last_topic.empty()) - db_buffer << "MD TOPIC " << ci->last_topic_setter << " " << ci->last_topic_time << " :" << ci->last_topic << endl; - db_buffer << "MD LEVELS"; - for (int j = 0; ChannelLevels[j].Level != CA_SIZE; ++j) - db_buffer << " " << ChannelLevels[j].Name << " " << ci->levels[ChannelLevels[j].Level]; - db_buffer << endl; - if (ci->FlagCount()) - db_buffer << "MD FLAGS " << ToString(ci->ToString()) << endl; - if (ci->HasFlag(CI_SUSPENDED)) - { - Anope::string by, reason; - ci->GetExtRegular("suspend_by", by); - ci->GetExtRegular("suspend_reason", reason); - db_buffer << "MD SUSPEND " << by << " :" << reason << endl; - } - for (unsigned k = 0, end = ci->GetAccessCount(); k < end; ++k) - { - ChanAccess *access = ci->GetAccess(k); - db_buffer << "MD ACCESS " << access->provider->name << " " << access->mask << " " << access->Serialize() << " " << access->last_seen << " " << access->creator << " " << access->created << endl; - } - for (unsigned k = 0, end = ci->GetAkickCount(); k < end; ++k) - { - db_buffer << "MD AKICK 0 " << (ci->GetAkick(k)->HasFlag(AK_ISNICK) ? "NICK " : "MASK ") << - (ci->GetAkick(k)->HasFlag(AK_ISNICK) ? ci->GetAkick(k)->nc->display : ci->GetAkick(k)->mask) << " " << ci->GetAkick(k)->creator << " " << ci->GetAkick(k)->addtime << " " << ci->last_used << " :"; - if (!ci->GetAkick(k)->reason.empty()) - db_buffer << ci->GetAkick(k)->reason; - db_buffer << endl; - } - { - std::vector<Anope::string> mlocks; - if (ci->GetExtRegular("db_mlock", mlocks)) - for (unsigned i = 0; i < mlocks.size(); ++i) - db_buffer << mlocks[i] << endl; - else - { - for (std::multimap<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it) - { - const ModeLock &ml = it->second; - ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name); - if (cm != NULL) - db_buffer << "MD MLOCK " << (ml.set ? 1 : 0) << " " << cm->NameAsString() << " " << ml.setter << " " << ml.created << " " << ml.param << endl; - } - } - } - MemoInfo *memos = &ci->memos; - for (unsigned k = 0, end = memos->memos.size(); k < end; ++k) - { - db_buffer << "MD MI " << memos->memos[k]->time << " " << memos->memos[k]->sender; - if (memos->memos[k]->HasFlag(MF_UNREAD)) - db_buffer << " UNREAD"; - if (memos->memos[k]->HasFlag(MF_RECEIPT)) - db_buffer << " RECEIPT"; - db_buffer << " :" << memos->memos[k]->text << endl; - } - for (unsigned k = 0, end = memos->ignores.size(); k < end; ++k) - db_buffer << "MD MIG " << Anope::string(memos->ignores[k]) << endl; - if (ci->bi) - db_buffer << "MD BI NAME " << ci->bi->nick << endl; - if (ci->botflags.FlagCount()) - db_buffer << "MD BI FLAGS " << ToString(ci->botflags.ToString()) << endl; - db_buffer << "MD BI TTB BOLDS " << ci->ttb[0] << " COLORS " << ci->ttb[1] << " REVERSES " << ci->ttb[2] << " UNDERLINES " << ci->ttb[3] << " BADWORDS " << ci->ttb[4] << " CAPS " << ci->ttb[5] << " FLOOD " << ci->ttb[6] << " REPEAT " << ci->ttb[7] << " ITALICS " << ci->ttb[8] << " AMSGS " << ci->ttb[9] << endl; - if (ci->capsmin) - db_buffer << "MD BI CAPSMIN " << ci->capsmin << endl; - if (ci->capspercent) - db_buffer << "MD BI CAPSPERCENT " << ci->capspercent << endl; - if (ci->floodlines) - db_buffer << "MD BI FLOODLINES " << ci->floodlines << endl; - if (ci->floodsecs) - db_buffer << "MD BI FLOODSECS " << ci->floodsecs << endl; - if (ci->repeattimes) - db_buffer << "MD BI REPEATTIMES " << ci->repeattimes << endl; - for (unsigned k = 0, end = ci->GetBadWordCount(); k < end; ++k) - db_buffer << "MD BI BADWORD " << (ci->GetBadWord(k)->type == BW_ANY ? "ANY " : "") << (ci->GetBadWord(k)->type == BW_SINGLE ? "SINGLE " : "") << (ci->GetBadWord(k)->type == BW_START ? "START " : "") << - (ci->GetBadWord(k)->type == BW_END ? "END " : "") << ":" << ci->GetBadWord(k)->word << endl; - - FOREACH_MOD(I_OnDatabaseWriteMetadata, OnDatabaseWriteMetadata(WriteMetadata, ci)); - } - - db_buffer << "OS STATS " << maxusercnt << " " << maxusertime << endl; - - for (std::list<XLineManager *>::iterator it = XLineManager::XLineManagers.begin(), it_end = XLineManager::XLineManagers.end(); it != it_end; ++it) - { - XLineManager *xl = *it; - for (unsigned i = 0, end = xl->GetCount(); i < end; ++i) - { - XLine *x = xl->GetEntry(i); - db_buffer << "OS SXLINE " << xl->Type() << " " << x->GetUser() << " " << x->GetHost() << " " << x->By << " " << x->Created << " " << x->Expires << " :" << x->Reason << endl; - } - } - - if (SessionInterface) - for (SessionService::ExceptionVector::iterator it = SessionInterface->GetExceptions().begin(); it != SessionInterface->GetExceptions().end(); ++it) - { - Exception *e = *it; - db_buffer << "OS EXCEPTION " << e->mask << " " << e->limit << " " << e->who << " " << e->time << " " << e->expires << " " << e->reason << endl; - } - - FOREACH_MOD(I_OnDatabaseWrite, OnDatabaseWrite(Write)); - - std::fstream db; - db.open(DatabaseFile.c_str(), std::ios_base::out | std::ios_base::trunc); - - if (!db.is_open()) - { - ircdproto->SendGlobops(NULL, "Unable to open %s for writing!", DatabaseFile.c_str()); - return EVENT_CONTINUE; - } - - db << db_buffer.str(); - db_buffer.str(""); - - db.close(); - - return EVENT_CONTINUE; - } - - void OnModuleLoad(User *u, Module *m) - { - if (!u) - return; - - Implementation events[] = {I_OnDatabaseRead, I_OnDatabaseReadMetadata}; - for (int i = 0; i < 2; ++i) - { - std::vector<Module *>::iterator it = std::find(ModuleManager::EventHandlers[events[i]].begin(), ModuleManager::EventHandlers[events[i]].end(), m); - /* This module wants to read from the database */ - if (it != ModuleManager::EventHandlers[events[i]].end()) - /* Loop over the database and call the events it would on a normal startup */ - ReadDatabase(m); - } - } -}; - -MODULE_INIT(DBPlain) diff --git a/modules/core/enc_md5.cpp b/modules/core/enc_md5.cpp deleted file mode 100644 index 109f31dfc..000000000 --- a/modules/core/enc_md5.cpp +++ /dev/null @@ -1,372 +0,0 @@ -/* Module for encryption using MD5. - * - * Modified for Anope. - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Taken from IRC Services and is copyright (c) 1996-2002 Andrew Church. - * E-mail: <achurch@achurch.org> - * Parts written by Andrew Kempe and others. - * This program is free but copyrighted software; see the file COPYING for - * details. - */ - -#include "module.h" - -/*************************************************************************/ - -/* Copyright (C) 1991-2, RSA Data Security, Inc. Created 1991. All -rights reserved. - -License to copy and use this software is granted provided that it -is identified as the "RSA Data Security, Inc. MD5 Message-Digest -Algorithm" in all material mentioning or referencing this software -or this function. - -License is also granted to make and use derivative works provided -that such works are identified as "derived from the RSA Data -Security, Inc. MD5 Message-Digest Algorithm" in all material -mentioning or referencing the derived work. - -RSA Data Security, Inc. makes no representations concerning either -the merchantability of this software or the suitability of this -software for any particular purpose. It is provided "as is" -without express or implied warranty of any kind. - -These notices must be retained in any copies of any part of this -documentation and/or software. - */ - -/* MD5 context. */ -struct MD5_CTX -{ - unsigned state[4]; /* state (ABCD) */ - unsigned count[2]; /* number of bits, modulo 2^64 (lsb first) */ - unsigned char buffer[64]; /* input buffer */ -}; - -/* MD5C.C - RSA Data Security, Inc., MD5 message-digest algorithm - */ - -/* Constants for MD5Transform routine. - */ -enum -{ - S11 = 7, - S12 = 12, - S13 = 17, - S14 = 22, - S21 = 5, - S22 = 9, - S23 = 14, - S24 = 20, - S31 = 4, - S32 = 11, - S33 = 16, - S34 = 23, - S41 = 6, - S42 = 10, - S43 = 15, - S44 = 21 -}; - -void MD5Transform(unsigned [4], const unsigned char [64]); -void Encode(unsigned char *, unsigned *, unsigned); -void Decode(unsigned *, const unsigned char *, unsigned); - -static unsigned char PADDING[64] = { - 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 -}; - -/* F, G, H and I are basic MD5 functions. - */ -inline static unsigned F(unsigned x, unsigned y, unsigned z) { return (x & y) | (~x & z); } -inline static unsigned G(unsigned x, unsigned y, unsigned z) { return (x & z) | (y & ~z); } -inline static unsigned H(unsigned x, unsigned y, unsigned z) { return x ^ y ^ z; } -inline static unsigned I(unsigned x, unsigned y, unsigned z) { return y ^ (x | ~z); } - -/* ROTATE_LEFT rotates x left n bits. - */ -inline static unsigned ROTATE_LEFT(unsigned x, unsigned n) { return (x << n) | (x >> (32 - n)); } - -/* FF, GG, HH, and II transformations for rounds 1, 2, 3, and 4. - * Rotation is separate from addition to prevent recomputation. - */ -inline static void FF(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += F(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} -inline static void GG(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += G(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} -inline static void HH(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += H(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} -inline static void II(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += I(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} - -/* MD5 initialization. Begins an MD5 operation, writing a new context. - */ -void MD5Init(MD5_CTX *context) -{ - context->count[0] = context->count[1] = 0; - /* Load magic initialization constants. */ - context->state[0] = 0x67452301; - context->state[1] = 0xefcdab89; - context->state[2] = 0x98badcfe; - context->state[3] = 0x10325476; -} - -/* MD5 block update operation. Continues an MD5 message-digest - * operation, processing another message block, and updating the - * context. - */ -void MD5Update(MD5_CTX *context, const unsigned char *input, unsigned inputLen) -{ - unsigned i, index, partLen; - - /* Compute number of bytes mod 64 */ - index = (context->count[0] >> 3) & 0x3F; - - /* Update number of bits */ - if ((context->count[0] += inputLen << 3) < (inputLen << 3)) - ++context->count[1]; - context->count[1] += inputLen >> 29; - - partLen = 64 - index; - - /* Transform as many times as possible. */ - if (inputLen >= partLen) - { - memcpy(&context->buffer[index], input, partLen); - MD5Transform(context->state, context->buffer); - - for (i = partLen; i + 63 < inputLen; i += 64) - MD5Transform(context->state, &input[i]); - - index = 0; - } - else - i = 0; - - /* Buffer remaining input */ - memcpy(&context->buffer[index], &input[i], inputLen - i); -} - -/* MD5 finalization. Ends an MD5 message-digest operation, writing the - * the message digest and zeroizing the context. - */ -void MD5Final(unsigned char digest[17], MD5_CTX *context) -{ - unsigned char bits[8]; - unsigned index, padLen; - - /* Save number of bits */ - Encode(bits, context->count, 8); - - /* Pad out to 56 mod 64. */ - index = (context->count[0] >> 3) & 0x3f; - padLen = index < 56 ? 56 - index : 120 - index; - MD5Update(context, PADDING, padLen); - - /* Append length (before padding) */ - MD5Update(context, bits, 8); - /* Store state in digest */ - Encode(digest, context->state, 16); - - /* Zeroize sensitive information. */ - memset(context, 0, sizeof(*context)); -} - -/* MD5 basic transformation. Transforms state based on block. - */ -void MD5Transform(unsigned state[4], const unsigned char block[64]) -{ - unsigned a = state[0], b = state[1], c = state[2], d = state[3], x[16]; - - Decode(x, block, 64); - - /* Round 1 */ - FF(a, b, c, d, x[0], S11, 0xd76aa478); /* 1 */ - FF(d, a, b, c, x[1], S12, 0xe8c7b756); /* 2 */ - FF(c, d, a, b, x[2], S13, 0x242070db); /* 3 */ - FF(b, c, d, a, x[3], S14, 0xc1bdceee); /* 4 */ - FF(a, b, c, d, x[4], S11, 0xf57c0faf); /* 5 */ - FF(d, a, b, c, x[5], S12, 0x4787c62a); /* 6 */ - FF(c, d, a, b, x[6], S13, 0xa8304613); /* 7 */ - FF(b, c, d, a, x[7], S14, 0xfd469501); /* 8 */ - FF(a, b, c, d, x[8], S11, 0x698098d8); /* 9 */ - FF(d, a, b, c, x[9], S12, 0x8b44f7af); /* 10 */ - FF(c, d, a, b, x[10], S13, 0xffff5bb1); /* 11 */ - FF(b, c, d, a, x[11], S14, 0x895cd7be); /* 12 */ - FF(a, b, c, d, x[12], S11, 0x6b901122); /* 13 */ - FF(d, a, b, c, x[13], S12, 0xfd987193); /* 14 */ - FF(c, d, a, b, x[14], S13, 0xa679438e); /* 15 */ - FF(b, c, d, a, x[15], S14, 0x49b40821); /* 16 */ - - /* Round 2 */ - GG(a, b, c, d, x[1], S21, 0xf61e2562); /* 17 */ - GG(d, a, b, c, x[6], S22, 0xc040b340); /* 18 */ - GG(c, d, a, b, x[11], S23, 0x265e5a51); /* 19 */ - GG(b, c, d, a, x[0], S24, 0xe9b6c7aa); /* 20 */ - GG(a, b, c, d, x[5], S21, 0xd62f105d); /* 21 */ - GG(d, a, b, c, x[10], S22, 0x2441453); /* 22 */ - GG(c, d, a, b, x[15], S23, 0xd8a1e681); /* 23 */ - GG(b, c, d, a, x[4], S24, 0xe7d3fbc8); /* 24 */ - GG(a, b, c, d, x[9], S21, 0x21e1cde6); /* 25 */ - GG(d, a, b, c, x[14], S22, 0xc33707d6); /* 26 */ - GG(c, d, a, b, x[3], S23, 0xf4d50d87); /* 27 */ - GG(b, c, d, a, x[8], S24, 0x455a14ed); /* 28 */ - GG(a, b, c, d, x[13], S21, 0xa9e3e905); /* 29 */ - GG(d, a, b, c, x[2], S22, 0xfcefa3f8); /* 30 */ - GG(c, d, a, b, x[7], S23, 0x676f02d9); /* 31 */ - GG(b, c, d, a, x[12], S24, 0x8d2a4c8a); /* 32 */ - - /* Round 3 */ - HH(a, b, c, d, x[5], S31, 0xfffa3942); /* 33 */ - HH(d, a, b, c, x[8], S32, 0x8771f681); /* 34 */ - HH(c, d, a, b, x[11], S33, 0x6d9d6122); /* 35 */ - HH(b, c, d, a, x[14], S34, 0xfde5380c); /* 36 */ - HH(a, b, c, d, x[1], S31, 0xa4beea44); /* 37 */ - HH(d, a, b, c, x[4], S32, 0x4bdecfa9); /* 38 */ - HH(c, d, a, b, x[7], S33, 0xf6bb4b60); /* 39 */ - HH(b, c, d, a, x[10], S34, 0xbebfbc70); /* 40 */ - HH(a, b, c, d, x[13], S31, 0x289b7ec6); /* 41 */ - HH(d, a, b, c, x[0], S32, 0xeaa127fa); /* 42 */ - HH(c, d, a, b, x[3], S33, 0xd4ef3085); /* 43 */ - HH(b, c, d, a, x[6], S34, 0x4881d05); /* 44 */ - HH(a, b, c, d, x[9], S31, 0xd9d4d039); /* 45 */ - HH(d, a, b, c, x[12], S32, 0xe6db99e5); /* 46 */ - HH(c, d, a, b, x[15], S33, 0x1fa27cf8); /* 47 */ - HH(b, c, d, a, x[2], S34, 0xc4ac5665); /* 48 */ - - /* Round 4 */ - II(a, b, c, d, x[0], S41, 0xf4292244); /* 49 */ - II(d, a, b, c, x[7], S42, 0x432aff97); /* 50 */ - II(c, d, a, b, x[14], S43, 0xab9423a7); /* 51 */ - II(b, c, d, a, x[5], S44, 0xfc93a039); /* 52 */ - II(a, b, c, d, x[12], S41, 0x655b59c3); /* 53 */ - II(d, a, b, c, x[3], S42, 0x8f0ccc92); /* 54 */ - II(c, d, a, b, x[10], S43, 0xffeff47d); /* 55 */ - II(b, c, d, a, x[1], S44, 0x85845dd1); /* 56 */ - II(a, b, c, d, x[8], S41, 0x6fa87e4f); /* 57 */ - II(d, a, b, c, x[15], S42, 0xfe2ce6e0); /* 58 */ - II(c, d, a, b, x[6], S43, 0xa3014314); /* 59 */ - II(b, c, d, a, x[13], S44, 0x4e0811a1); /* 60 */ - II(a, b, c, d, x[4], S41, 0xf7537e82); /* 61 */ - II(d, a, b, c, x[11], S42, 0xbd3af235); /* 62 */ - II(c, d, a, b, x[2], S43, 0x2ad7d2bb); /* 63 */ - II(b, c, d, a, x[9], S44, 0xeb86d391); /* 64 */ - - state[0] += a; - state[1] += b; - state[2] += c; - state[3] += d; - - /* Zeroize sensitive information. */ - memset(x, 0, sizeof(x)); -} - -/* Encodes input (unsigned) into output (unsigned char). Assumes len is - * a multiple of 4. - */ -void Encode(unsigned char *output, unsigned *input, unsigned len) -{ - unsigned i, j; - - for (i = 0, j = 0; j < len; ++i, j += 4) - { - output[j] = static_cast<unsigned char>(input[i] & 0xff); - output[j + 1] = static_cast<unsigned char>((input[i] >> 8) & 0xff); - output[j + 2] = static_cast<unsigned char>((input[i] >> 16) & 0xff); - output[j + 3] = static_cast<unsigned char>((input[i] >> 24) & 0xff); - } -} - -/* Decodes input (unsigned char) into output (unsigned). Assumes len is - * a multiple of 4. - */ -void Decode(unsigned *output, const unsigned char *input, unsigned len) -{ - unsigned i, j; - - for (i = 0, j = 0; j < len; ++i, j += 4) - output[i] = static_cast<unsigned>(input[j]) | (static_cast<unsigned>(input[j + 1]) << 8) | (static_cast<unsigned>(input[j + 2]) << 16) | (static_cast<unsigned>(input[j + 3]) << 24); -} - -/*************************************************************************/ - -/* Module stuff. */ - -class EMD5 : public Module -{ - public: - EMD5(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnEncrypt, I_OnCheckAuthentication }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) - { - MD5_CTX context; - char digest[17] = ""; - Anope::string buf = "md5:"; - - MD5Init(&context); - MD5Update(&context, reinterpret_cast<const unsigned char *>(src.c_str()), src.length()); - MD5Final(reinterpret_cast<unsigned char *>(digest), &context); - - buf += Anope::Hex(digest, 16); - Log(LOG_DEBUG_2) << "(enc_md5) hashed password from [" << src << "] to [" << buf << "]"; - dest = buf; - return EVENT_ALLOW; - } - - EventReturn OnCheckAuthentication(Command *c, CommandSource *source, const std::vector<Anope::string> ¶ms, const Anope::string &account, const Anope::string &password) - { - NickAlias *na = findnick(account); - NickCore *nc = na ? na->nc : NULL; - if (na == NULL) - return EVENT_CONTINUE; - - size_t pos = nc->pass.find(':'); - if (pos == Anope::string::npos) - return EVENT_CONTINUE; - Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); - if (!hash_method.equals_cs("md5")) - return EVENT_CONTINUE; - - Anope::string buf; - this->OnEncrypt(password, buf); - if (nc->pass.equals_cs(buf)) - { - /* if we are NOT the first module in the list, - * we want to re-encrypt the pass with the new encryption - */ - if (ModuleManager::FindFirstOf(ENCRYPTION) != this) - enc_encrypt(password, nc->pass); - return EVENT_ALLOW; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(EMD5) diff --git a/modules/core/enc_none.cpp b/modules/core/enc_none.cpp deleted file mode 100644 index 180b431c2..000000000 --- a/modules/core/enc_none.cpp +++ /dev/null @@ -1,74 +0,0 @@ -/* Module for plain text encryption. - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * This program is free but copyrighted software; see the file COPYING for - * details. - */ - -#include "module.h" - -class ENone : public Module -{ - public: - ENone(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnEncrypt, I_OnDecrypt, I_OnCheckAuthentication }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) - { - Anope::string buf = "plain:"; - Anope::string cpass; - Anope::B64Encode(src, cpass); - buf += cpass; - Log(LOG_DEBUG_2) << "(enc_none) hashed password from [" << src << "] to [" << buf << "]"; - dest = buf; - return EVENT_ALLOW; - } - - EventReturn OnDecrypt(const Anope::string &hashm, const Anope::string &src, Anope::string &dest) - { - if (!hashm.equals_cs("plain")) - return EVENT_CONTINUE; - size_t pos = src.find(':'); - Anope::string buf = src.substr(pos + 1); - Anope::B64Decode(buf, dest); - return EVENT_ALLOW; - } - - EventReturn OnCheckAuthentication(Command *c, CommandSource *source, const std::vector<Anope::string> ¶ms, const Anope::string &account, const Anope::string &password) - { - NickAlias *na = findnick(account); - NickCore *nc = na ? na->nc : NULL; - if (na == NULL) - return EVENT_CONTINUE; - - size_t pos = nc->pass.find(':'); - if (pos == Anope::string::npos) - return EVENT_CONTINUE; - Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); - if (!hash_method.equals_cs("plain")) - return EVENT_CONTINUE; - - Anope::string buf; - this->OnEncrypt(password, buf); - if (nc->pass.equals_cs(buf)) - { - /* if we are NOT the first module in the list, - * we want to re-encrypt the pass with the new encryption - */ - if (ModuleManager::FindFirstOf(ENCRYPTION) != this) - enc_encrypt(password, nc->pass); - return EVENT_ALLOW; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(ENone) diff --git a/modules/core/enc_old.cpp b/modules/core/enc_old.cpp deleted file mode 100644 index e68887c49..000000000 --- a/modules/core/enc_old.cpp +++ /dev/null @@ -1,382 +0,0 @@ -/* Include file for high-level encryption routines. - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -#include "module.h" - -/******** Code specific to the type of encryption. ********/ - -/* Copyright (C) 1991-2, RSA Data Security, Inc. Created 1991. All -rights reserved. - -License to copy and use this software is granted provided that it -is identified as the "RSA Data Security, Inc. MD5 Message-Digest -Algorithm" in all material mentioning or referencing this software -or this function. - -License is also granted to make and use derivative works provided -that such works are identified as "derived from the RSA Data -Security, Inc. MD5 Message-Digest Algorithm" in all material -mentioning or referencing the derived work. - -RSA Data Security, Inc. makes no representations concerning either -the merchantability of this software or the suitability of this -software for any particular purpose. It is provided "as is" -without express or implied warranty of any kind. - -These notices must be retained in any copies of any part of this -documentation and/or software. - */ - -/* MD5 context. */ -struct MD5_CTX -{ - unsigned state[4]; /* state (ABCD) */ - unsigned count[2]; /* number of bits, modulo 2^64 (lsb first) */ - unsigned char buffer[64]; /* input buffer */ -}; - -/* MD5C.C - RSA Data Security, Inc., MD5 message-digest algorithm - */ - -/* Constants for MD5Transform routine. - */ -enum -{ - S11 = 7, - S12 = 12, - S13 = 17, - S14 = 22, - S21 = 5, - S22 = 9, - S23 = 14, - S24 = 20, - S31 = 4, - S32 = 11, - S33 = 16, - S34 = 23, - S41 = 6, - S42 = 10, - S43 = 15, - S44 = 21 -}; - -static void MD5Transform(unsigned [4], const unsigned char[64]); -static void Encode(unsigned char *, unsigned *, unsigned); -static void Decode(unsigned *, const unsigned char *, unsigned); - -static unsigned char PADDING[64] = { - 0x80, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 -}; - -/* F, G, H and I are basic MD5 functions. - */ -inline static unsigned F(unsigned x, unsigned y, unsigned z) { return (x & y) | (~x & z); } -inline static unsigned G(unsigned x, unsigned y, unsigned z) { return (x & z) | (y & ~z); } -inline static unsigned H(unsigned x, unsigned y, unsigned z) { return x ^ y ^ z; } -inline static unsigned MD5_I(unsigned x, unsigned y, unsigned z) { return y ^ (x | ~z); } - -/* ROTATE_LEFT rotates x left n bits. - */ -inline static unsigned ROTATE_LEFT(unsigned x, unsigned n) { return (x << n) | (x >> (32 - n)); } - -/* FF, GG, HH, and II transformations for rounds 1, 2, 3, and 4. - * Rotation is separate from addition to prevent recomputation. - */ -inline static void FF(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += F(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} -inline static void GG(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += G(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} -inline static void HH(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += H(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} -inline static void II(unsigned &a, unsigned b, unsigned c, unsigned d, unsigned x, unsigned s, unsigned ac) -{ - a += MD5_I(b, c, d) + x + ac; - a = ROTATE_LEFT(a, s); - a += b; -} - -/* MD5 initialization. Begins an MD5 operation, writing a new context. - */ -static void MD5Init(MD5_CTX *context) -{ - context->count[0] = context->count[1] = 0; - /* Load magic initialization constants. - */ - context->state[0] = 0x67452301; - context->state[1] = 0xefcdab89; - context->state[2] = 0x98badcfe; - context->state[3] = 0x10325476; -} - -/* MD5 block update operation. Continues an MD5 message-digest - * operation, processing another message block, and updating the - * context. - */ -static void MD5Update(MD5_CTX *context, const unsigned char *input, unsigned inputLen) -{ - unsigned i, index, partLen; - - /* Compute number of bytes mod 64 */ - index = (context->count[0] >> 3) & 0x3F; - - /* Update number of bits */ - if ((context->count[0] += inputLen << 3) < (inputLen << 3)) - ++context->count[1]; - context->count[1] += inputLen >> 29; - - partLen = 64 - index; - - /* Transform as many times as possible. - */ - if (inputLen >= partLen) - { - memcpy(&context->buffer[index], input, partLen); - MD5Transform(context->state, context->buffer); - - for (i = partLen; i + 63 < inputLen; i += 64) - MD5Transform(context->state, &input[i]); - - index = 0; - } - else - i = 0; - - /* Buffer remaining input */ - memcpy(&context->buffer[index], &input[i], inputLen - i); -} - -/* MD5 finalization. Ends an MD5 message-digest operation, writing the - * the message digest and zeroizing the context. - */ -static void MD5Final(unsigned char digest[17], MD5_CTX *context) -{ - unsigned char bits[8]; - unsigned index, padLen; - - /* Save number of bits */ - Encode(bits, context->count, 8); - - /* Pad out to 56 mod 64. - */ - index = (context->count[0] >> 3) & 0x3f; - padLen = index < 56 ? 56 - index : 120 - index; - MD5Update(context, PADDING, padLen); - - /* Append length (before padding) */ - MD5Update(context, bits, 8); - /* Store state in digest */ - Encode(digest, context->state, 16); - - /* Zeroize sensitive information. - */ - memset(context, 0, sizeof(*context)); -} - -/* MD5 basic transformation. Transforms state based on block. - */ -static void MD5Transform(unsigned state[4], const unsigned char block[64]) -{ - unsigned a = state[0], b = state[1], c = state[2], d = state[3], x[16]; - - Decode(x, block, 64); - - /* Round 1 */ - FF(a, b, c, d, x[0], S11, 0xd76aa478); /* 1 */ - FF(d, a, b, c, x[1], S12, 0xe8c7b756); /* 2 */ - FF(c, d, a, b, x[2], S13, 0x242070db); /* 3 */ - FF(b, c, d, a, x[3], S14, 0xc1bdceee); /* 4 */ - FF(a, b, c, d, x[4], S11, 0xf57c0faf); /* 5 */ - FF(d, a, b, c, x[5], S12, 0x4787c62a); /* 6 */ - FF(c, d, a, b, x[6], S13, 0xa8304613); /* 7 */ - FF(b, c, d, a, x[7], S14, 0xfd469501); /* 8 */ - FF(a, b, c, d, x[8], S11, 0x698098d8); /* 9 */ - FF(d, a, b, c, x[9], S12, 0x8b44f7af); /* 10 */ - FF(c, d, a, b, x[10], S13, 0xffff5bb1); /* 11 */ - FF(b, c, d, a, x[11], S14, 0x895cd7be); /* 12 */ - FF(a, b, c, d, x[12], S11, 0x6b901122); /* 13 */ - FF(d, a, b, c, x[13], S12, 0xfd987193); /* 14 */ - FF(c, d, a, b, x[14], S13, 0xa679438e); /* 15 */ - FF(b, c, d, a, x[15], S14, 0x49b40821); /* 16 */ - - /* Round 2 */ - GG(a, b, c, d, x[1], S21, 0xf61e2562); /* 17 */ - GG(d, a, b, c, x[6], S22, 0xc040b340); /* 18 */ - GG(c, d, a, b, x[11], S23, 0x265e5a51); /* 19 */ - GG(b, c, d, a, x[0], S24, 0xe9b6c7aa); /* 20 */ - GG(a, b, c, d, x[5], S21, 0xd62f105d); /* 21 */ - GG(d, a, b, c, x[10], S22, 0x2441453); /* 22 */ - GG(c, d, a, b, x[15], S23, 0xd8a1e681); /* 23 */ - GG(b, c, d, a, x[4], S24, 0xe7d3fbc8); /* 24 */ - GG(a, b, c, d, x[9], S21, 0x21e1cde6); /* 25 */ - GG(d, a, b, c, x[14], S22, 0xc33707d6); /* 26 */ - GG(c, d, a, b, x[3], S23, 0xf4d50d87); /* 27 */ - GG(b, c, d, a, x[8], S24, 0x455a14ed); /* 28 */ - GG(a, b, c, d, x[13], S21, 0xa9e3e905); /* 29 */ - GG(d, a, b, c, x[2], S22, 0xfcefa3f8); /* 30 */ - GG(c, d, a, b, x[7], S23, 0x676f02d9); /* 31 */ - GG(b, c, d, a, x[12], S24, 0x8d2a4c8a); /* 32 */ - - /* Round 3 */ - HH(a, b, c, d, x[5], S31, 0xfffa3942); /* 33 */ - HH(d, a, b, c, x[8], S32, 0x8771f681); /* 34 */ - HH(c, d, a, b, x[11], S33, 0x6d9d6122); /* 35 */ - HH(b, c, d, a, x[14], S34, 0xfde5380c); /* 36 */ - HH(a, b, c, d, x[1], S31, 0xa4beea44); /* 37 */ - HH(d, a, b, c, x[4], S32, 0x4bdecfa9); /* 38 */ - HH(c, d, a, b, x[7], S33, 0xf6bb4b60); /* 39 */ - HH(b, c, d, a, x[10], S34, 0xbebfbc70); /* 40 */ - HH(a, b, c, d, x[13], S31, 0x289b7ec6); /* 41 */ - HH(d, a, b, c, x[0], S32, 0xeaa127fa); /* 42 */ - HH(c, d, a, b, x[3], S33, 0xd4ef3085); /* 43 */ - HH(b, c, d, a, x[6], S34, 0x4881d05); /* 44 */ - HH(a, b, c, d, x[9], S31, 0xd9d4d039); /* 45 */ - HH(d, a, b, c, x[12], S32, 0xe6db99e5); /* 46 */ - HH(c, d, a, b, x[15], S33, 0x1fa27cf8); /* 47 */ - HH(b, c, d, a, x[2], S34, 0xc4ac5665); /* 48 */ - - /* Round 4 */ - II(a, b, c, d, x[0], S41, 0xf4292244); /* 49 */ - II(d, a, b, c, x[7], S42, 0x432aff97); /* 50 */ - II(c, d, a, b, x[14], S43, 0xab9423a7); /* 51 */ - II(b, c, d, a, x[5], S44, 0xfc93a039); /* 52 */ - II(a, b, c, d, x[12], S41, 0x655b59c3); /* 53 */ - II(d, a, b, c, x[3], S42, 0x8f0ccc92); /* 54 */ - II(c, d, a, b, x[10], S43, 0xffeff47d); /* 55 */ - II(b, c, d, a, x[1], S44, 0x85845dd1); /* 56 */ - II(a, b, c, d, x[8], S41, 0x6fa87e4f); /* 57 */ - II(d, a, b, c, x[15], S42, 0xfe2ce6e0); /* 58 */ - II(c, d, a, b, x[6], S43, 0xa3014314); /* 59 */ - II(b, c, d, a, x[13], S44, 0x4e0811a1); /* 60 */ - II(a, b, c, d, x[4], S41, 0xf7537e82); /* 61 */ - II(d, a, b, c, x[11], S42, 0xbd3af235); /* 62 */ - II(c, d, a, b, x[2], S43, 0x2ad7d2bb); /* 63 */ - II(b, c, d, a, x[9], S44, 0xeb86d391); /* 64 */ - - state[0] += a; - state[1] += b; - state[2] += c; - state[3] += d; - - /* Zeroize sensitive information. - */ - memset(x, 0, sizeof(x)); -} - -/* Encodes input (unsigned) into output (unsigned char). Assumes len is - * a multiple of 4. - */ -static void Encode(unsigned char *output, unsigned *input, unsigned len) -{ - unsigned i, j; - - for (i = 0, j = 0; j < len; ++i, j += 4) - { - output[j] = static_cast<unsigned char>(input[i] & 0xff); - output[j + 1] = static_cast<unsigned char>((input[i] >> 8) & 0xff); - output[j + 2] = static_cast<unsigned char>((input[i] >> 16) & 0xff); - output[j + 3] = static_cast<unsigned char>((input[i] >> 24) & 0xff); - } -} - -/* Decodes input (unsigned char) into output (unsigned). Assumes len is - * a multiple of 4. - */ -static void Decode(unsigned *output, const unsigned char *input, unsigned len) -{ - unsigned i, j; - - for (i = 0, j = 0; j < len; ++i, j += 4) - output[i] = static_cast<unsigned>(input[j]) | (static_cast<unsigned>(input[j + 1]) << 8) | (static_cast<unsigned>(input[j + 2]) << 16) | (static_cast<unsigned>(input[j + 3]) << 24); -} - -/*************************************************************************/ - -/******** Our own high-level routines. ********/ - -inline static char XTOI(char c) { return c > 9 ? c - 'A' + 10 : c - '0'; } - -class EOld : public Module -{ - public: - EOld(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnEncrypt, I_OnCheckAuthentication }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) - { - MD5_CTX context; - char digest[33] = "", digest2[17] = ""; - int i; - Anope::string buf = "oldmd5:"; - - memset(&context, 0, sizeof(context)); - - MD5Init(&context); - MD5Update(&context, reinterpret_cast<const unsigned char *>(src.c_str()), src.length()); - MD5Final(reinterpret_cast<unsigned char *>(digest), &context); - for (i = 0; i < 32; i += 2) - digest2[i / 2] = XTOI(digest[i]) << 4 | XTOI(digest[i + 1]); - - buf += Anope::Hex(digest2, 16); - Log(LOG_DEBUG_2) << "(enc_old) hashed password from [" << src << "] to [" << buf << "]"; - dest = buf; - return EVENT_ALLOW; - } - - EventReturn OnCheckAuthentication(Command *c, CommandSource *source, const std::vector<Anope::string> ¶ms, const Anope::string &account, const Anope::string &password) - { - NickAlias *na = findnick(account); - NickCore *nc = na ? na->nc : NULL; - if (na == NULL) - return EVENT_CONTINUE; - - size_t pos = nc->pass.find(':'); - if (pos == Anope::string::npos) - return EVENT_CONTINUE; - Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); - if (!hash_method.equals_cs("oldmd5")) - return EVENT_CONTINUE; - - Anope::string buf; - this->OnEncrypt(password, buf); - if (nc->pass.equals_cs(buf)) - { - /* if we are NOT the first module in the list, - * we want to re-encrypt the pass with the new encryption - */ - if (ModuleManager::FindFirstOf(ENCRYPTION) != this) - enc_encrypt(password, nc->pass); - return EVENT_ALLOW; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(EOld) diff --git a/modules/core/enc_sha1.cpp b/modules/core/enc_sha1.cpp deleted file mode 100644 index 4fe321bdc..000000000 --- a/modules/core/enc_sha1.cpp +++ /dev/null @@ -1,222 +0,0 @@ -/* -SHA-1 in C -By Steve Reid <steve@edmweb.com> -100% Public Domain - -Test Vectors (from FIPS PUB 180-1) -"abc" - A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D -"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq" - 84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1 -A million repetitions of "a" - 34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F -*/ - -/* #define LITTLE_ENDIAN * This should be #define'd if true. */ - -#include "module.h" - -struct SHA1_CTX -{ - uint32 state[5]; - uint32 count[2]; - unsigned char buffer[64]; -}; - -void SHA1Transform(uint32 state[5], const unsigned char buffer[64]); -void SHA1Init(SHA1_CTX *context); -void SHA1Update(SHA1_CTX *context, const unsigned char *data, uint32 len); -void SHA1Final(unsigned char digest[20], SHA1_CTX *context); - -inline static uint32 rol(uint32 value, uint32 bits) { return (value << bits) | (value >> (32 - bits)); } - -union CHAR64LONG16 -{ - unsigned char c[64]; - uint32 l[16]; -}; - -/* blk0() and blk() perform the initial expand. */ -/* I got the idea of expanding during the round function from SSLeay */ -inline static uint32 blk0(CHAR64LONG16 *block, uint32 i) -{ -#ifdef LITTLE_ENDIAN - return block->l[i] = (rol(block->l[i], 24) & 0xFF00FF00) | (rol(block->l[i], 8) & 0x00FF00FF); -#else - return block->l[i]; -#endif -} -inline static uint32 blk(CHAR64LONG16 *block, uint32 i) { return block->l[i & 15] = rol(block->l[(i + 13) & 15] ^ block->l[(i + 8) & 15] ^ block->l[(i + 2) & 15] ^ block->l[i & 15],1); } - -/* (R0+R1), R2, R3, R4 are the different operations used in SHA1 */ -inline static void R0(CHAR64LONG16 *block, uint32 v, uint32 &w, uint32 x, uint32 y, uint32 &z, uint32 i) { z += ((w & (x ^ y)) ^ y) + blk0(block, i) + 0x5A827999 + rol(v, 5); w = rol(w, 30); } -inline static void R1(CHAR64LONG16 *block, uint32 v, uint32 &w, uint32 x, uint32 y, uint32 &z, uint32 i) { z += ((w & (x ^ y)) ^ y) + blk(block, i) + 0x5A827999 + rol(v, 5); w = rol(w, 30); } -inline static void R2(CHAR64LONG16 *block, uint32 v, uint32 &w, uint32 x, uint32 y, uint32 &z, uint32 i) { z += (w ^ x ^ y) + blk(block, i) + 0x6ED9EBA1 + rol(v, 5); w = rol(w, 30); } -inline static void R3(CHAR64LONG16 *block, uint32 v, uint32 &w, uint32 x, uint32 y, uint32 &z, uint32 i) { z += (((w | x) & y) | (w & x)) + blk(block, i) + 0x8F1BBCDC + rol(v, 5); w = rol(w, 30); } -inline static void R4(CHAR64LONG16 *block, uint32 v, uint32 &w, uint32 x, uint32 y, uint32 &z, uint32 i) { z += (w ^ x ^ y) + blk(block, i) + 0xCA62C1D6 + rol(v, 5); w = rol(w, 30); } - -/* Hash a single 512-bit block. This is the core of the algorithm. */ - -void SHA1Transform(uint32 state[5], const unsigned char buffer[64]) -{ - uint32 a, b, c, d, e; - static unsigned char workspace[64]; - CHAR64LONG16 *block = reinterpret_cast<CHAR64LONG16 *>(workspace); - memcpy(block, buffer, 64); - /* Copy context->state[] to working vars */ - a = state[0]; - b = state[1]; - c = state[2]; - d = state[3]; - e = state[4]; - /* 4 rounds of 20 operations each. Loop unrolled. */ - R0(block, a, b, c, d, e, 0); R0(block, e, a, b, c, d, 1); R0(block, d, e, a, b, c, 2); R0(block, c, d, e, a, b, 3); - R0(block, b, c, d, e, a, 4); R0(block, a, b, c, d, e, 5); R0(block, e, a, b, c, d, 6); R0(block, d, e, a, b, c, 7); - R0(block, c, d, e, a, b, 8); R0(block, b, c, d, e, a, 9); R0(block, a, b, c, d, e, 10); R0(block, e, a, b, c, d, 11); - R0(block, d, e, a, b, c, 12); R0(block, c, d, e, a, b, 13); R0(block, b, c, d, e, a, 14); R0(block, a, b, c, d, e, 15); - R1(block, e, a, b, c, d, 16); R1(block, d, e, a, b, c, 17); R1(block, c, d, e, a, b, 18); R1(block, b, c, d, e, a, 19); - R2(block, a, b, c, d, e, 20); R2(block, e, a, b, c, d, 21); R2(block, d, e, a, b, c, 22); R2(block, c, d, e, a, b, 23); - R2(block, b, c, d, e, a, 24); R2(block, a, b, c, d, e, 25); R2(block, e, a, b, c, d, 26); R2(block, d, e, a, b, c, 27); - R2(block, c, d, e, a, b, 28); R2(block, b, c, d, e, a, 29); R2(block, a, b, c, d, e, 30); R2(block, e, a, b, c, d, 31); - R2(block, d, e, a, b, c, 32); R2(block, c, d, e, a, b, 33); R2(block, b, c, d, e, a, 34); R2(block, a, b, c, d, e, 35); - R2(block, e, a, b, c, d, 36); R2(block, d, e, a, b, c, 37); R2(block, c, d, e, a, b, 38); R2(block, b, c, d, e, a, 39); - R3(block, a, b, c, d, e, 40); R3(block, e, a, b, c, d, 41); R3(block, d, e, a, b, c, 42); R3(block, c, d, e, a, b, 43); - R3(block, b, c, d, e, a, 44); R3(block, a, b, c, d, e, 45); R3(block, e, a, b, c, d, 46); R3(block, d, e, a, b, c, 47); - R3(block, c, d, e, a, b, 48); R3(block, b, c, d, e, a, 49); R3(block, a, b, c, d, e, 50); R3(block, e, a, b, c, d, 51); - R3(block, d, e, a, b, c, 52); R3(block, c, d, e, a, b, 53); R3(block, b, c, d, e, a, 54); R3(block, a, b, c, d, e, 55); - R3(block, e, a, b, c, d, 56); R3(block, d, e, a, b, c, 57); R3(block, c, d, e, a, b, 58); R3(block, b, c, d, e, a, 59); - R4(block, a, b, c, d, e, 60); R4(block, e, a, b, c, d, 61); R4(block, d, e, a, b, c, 62); R4(block, c, d, e, a, b, 63); - R4(block, b, c, d, e, a, 64); R4(block, a, b, c, d, e, 65); R4(block, e, a, b, c, d, 66); R4(block, d, e, a, b, c, 67); - R4(block, c, d, e, a, b, 68); R4(block, b, c, d, e, a, 69); R4(block, a, b, c, d, e, 70); R4(block, e, a, b, c, d, 71); - R4(block, d, e, a, b, c, 72); R4(block, c, d, e, a, b, 73); R4(block, b, c, d, e, a, 74); R4(block, a, b, c, d, e, 75); - R4(block, e, a, b, c, d, 76); R4(block, d, e, a, b, c, 77); R4(block, c, d, e, a, b, 78); R4(block, b, c, d, e, a, 79); - /* Add the working vars back into context.state[] */ - state[0] += a; - state[1] += b; - state[2] += c; - state[3] += d; - state[4] += e; - /* Wipe variables */ - a = b = c = d = e = 0; -} - -/* SHA1Init - Initialize new context */ - -void SHA1Init(SHA1_CTX *context) -{ - /* SHA1 initialization constants */ - context->state[0] = 0x67452301; - context->state[1] = 0xEFCDAB89; - context->state[2] = 0x98BADCFE; - context->state[3] = 0x10325476; - context->state[4] = 0xC3D2E1F0; - context->count[0] = context->count[1] = 0; -} - -/* Run your data through this. */ - -void SHA1Update(SHA1_CTX *context, const unsigned char *data, uint32 len) -{ - uint32 i, j; - - j = (context->count[0] >> 3) & 63; - if ((context->count[0] += len << 3) < (len << 3)) - ++context->count[1]; - context->count[1] += len >> 29; - if (j + len > 63) - { - memcpy(&context->buffer[j], data, (i = 64 - j)); - SHA1Transform(context->state, context->buffer); - for (; i + 63 < len; i += 64) - SHA1Transform(context->state, &data[i]); - j = 0; - } - else - i = 0; - memcpy(&context->buffer[j], &data[i], len - i); -} - -/* Add padding and return the message digest. */ - -void SHA1Final(unsigned char digest[21], SHA1_CTX *context) -{ - uint32 i; - unsigned char finalcount[8]; - - for (i = 0; i < 8; ++i) - finalcount[i] = static_cast<unsigned char>((context->count[i >= 4 ? 0 : 1] >> ((3 - (i & 3)) * 8)) & 255); /* Endian independent */ - SHA1Update(context, reinterpret_cast<const unsigned char *>("\200"), 1); - while ((context->count[0] & 504) != 448) - SHA1Update(context, reinterpret_cast<const unsigned char *>("\0"), 1); - SHA1Update(context, finalcount, 8); /* Should cause a SHA1Transform() */ - for (i = 0; i < 20; ++i) - digest[i] = static_cast<unsigned char>((context->state[i>>2] >> ((3 - (i & 3)) * 8)) & 255); - /* Wipe variables */ - i = 0; - memset(context->buffer, 0, 64); - memset(context->state, 0, 20); - memset(context->count, 0, 8); - memset(&finalcount, 0, 8); - SHA1Transform(context->state, context->buffer); -} - -/*****************************************************************************/ -/*****************************************************************************/ - -/* Module stuff. */ - -class ESHA1 : public Module -{ - public: - ESHA1(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnEncrypt, I_OnCheckAuthentication }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) - { - SHA1_CTX context; - char digest[21] = ""; - Anope::string buf = "sha1:"; - - SHA1Init(&context); - SHA1Update(&context, reinterpret_cast<const unsigned char *>(src.c_str()), src.length()); - SHA1Final(reinterpret_cast<unsigned char *>(digest), &context); - - buf += Anope::Hex(digest, 20); - Log(LOG_DEBUG_2) << "(enc_sha1) hashed password from [" << src << "] to [" << buf << "]"; - dest = buf; - return EVENT_ALLOW; - } - - EventReturn OnCheckAuthentication(Command *c, CommandSource *source, const std::vector<Anope::string> ¶ms, const Anope::string &account, const Anope::string &password) - { - NickAlias *na = findnick(account); - NickCore *nc = na ? na->nc : NULL; - if (na == NULL) - return EVENT_CONTINUE; - - size_t pos = nc->pass.find(':'); - if (pos == Anope::string::npos) - return EVENT_CONTINUE; - Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); - if (!hash_method.equals_cs("sha1")) - return EVENT_CONTINUE; - - Anope::string buf; - this->OnEncrypt(password, buf); - if (nc->pass.equals_cs(buf)) - { - if (ModuleManager::FindFirstOf(ENCRYPTION) != this) - enc_encrypt(password, nc->pass); - return EVENT_ALLOW; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(ESHA1) diff --git a/modules/core/enc_sha256.cpp b/modules/core/enc_sha256.cpp deleted file mode 100644 index 3034f3731..000000000 --- a/modules/core/enc_sha256.cpp +++ /dev/null @@ -1,314 +0,0 @@ -/* This module generates and compares password hashes using SHA256 algorithms. - * To help reduce the risk of dictionary attacks, the code appends random bytes - * (so-called "salt") to the original plain text before generating hashes and - * stores this salt appended to the result. To verify another plain text value - * against the given hash, this module will retrieve the salt value from the - * password string and use it when computing a new hash of the plain text. - * - * If an intruder gets access to your system or uses a brute force attack, - * salt will not provide much value. - * IMPORTANT: DATA HASHES CANNOT BE "DECRYPTED" BACK TO PLAIN TEXT. - * - * Modified for Anope. - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Taken from InspIRCd ( www.inspircd.org ) - * see http://wiki.inspircd.org/Credits - * - * This program is free but copyrighted software; see - * the file COPYING for details. - */ - -/* FIPS 180-2 SHA-224/256/384/512 implementation - * Last update: 05/23/2005 - * Issue date: 04/30/2005 - * - * Copyright (C) 2005 Olivier Gay <olivier.gay@a3.epfl.ch> - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the project nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -#include "module.h" - -static const unsigned SHA256_DIGEST_SIZE = 256 / 8; -static const unsigned SHA256_BLOCK_SIZE = 512 / 8; - -/** An sha256 context - */ -class SHA256Context -{ - public: - unsigned tot_len; - unsigned len; - unsigned char block[2 * SHA256_BLOCK_SIZE]; - uint32 h[8]; -}; - -inline static uint32 SHFR(uint32 x, uint32 n) { return x >> n; } -inline static uint32 ROTR(uint32 x, uint32 n) { return (x >> n) | (x << ((sizeof(x) << 3) - n)); } -inline static uint32 ROTL(uint32 x, uint32 n) { return (x << n) | (x >> ((sizeof(x) << 3) - n)); } -inline static uint32 CH(uint32 x, uint32 y, uint32 z) { return (x & y) ^ (~x & z); } -inline static uint32 MAJ(uint32 x, uint32 y, uint32 z) { return (x & y) ^ (x & z) ^ (y & z); } - -inline static uint32 SHA256_F1(uint32 x) { return ROTR(x, 2) ^ ROTR(x, 13) ^ ROTR(x, 22); } -inline static uint32 SHA256_F2(uint32 x) { return ROTR(x, 6) ^ ROTR(x, 11) ^ ROTR(x, 25); } -inline static uint32 SHA256_F3(uint32 x) { return ROTR(x, 7) ^ ROTR(x, 18) ^ SHFR(x, 3); } -inline static uint32 SHA256_F4(uint32 x) { return ROTR(x, 17) ^ ROTR(x, 19) ^ SHFR(x, 10); } - -inline static void UNPACK32(unsigned x, unsigned char *str) -{ - str[3] = static_cast<uint8>(x); - str[2] = static_cast<uint8>(x >> 8); - str[1] = static_cast<uint8>(x >> 16); - str[0] = static_cast<uint8>(x >> 24); -} - -inline static void PACK32(unsigned char *str, uint32 &x) -{ - x = static_cast<uint32>(str[3]) | static_cast<uint32>(str[2]) << 8 | static_cast<uint32>(str[1]) << 16 | static_cast<uint32>(str[0]) << 24; -} - -/* Macros used for loops unrolling */ - -inline static void SHA256_SCR(uint32 w[64], int i) -{ - w[i] = SHA256_F4(w[i - 2]) + w[i - 7] + SHA256_F3(w[i - 15]) + w[i - 16]; -} - -uint32 sha256_k[64] = -{ - 0x428a2f98, 0x71374491, 0xb5c0fbcf, 0xe9b5dba5, - 0x3956c25b, 0x59f111f1, 0x923f82a4, 0xab1c5ed5, - 0xd807aa98, 0x12835b01, 0x243185be, 0x550c7dc3, - 0x72be5d74, 0x80deb1fe, 0x9bdc06a7, 0xc19bf174, - 0xe49b69c1, 0xefbe4786, 0x0fc19dc6, 0x240ca1cc, - 0x2de92c6f, 0x4a7484aa, 0x5cb0a9dc, 0x76f988da, - 0x983e5152, 0xa831c66d, 0xb00327c8, 0xbf597fc7, - 0xc6e00bf3, 0xd5a79147, 0x06ca6351, 0x14292967, - 0x27b70a85, 0x2e1b2138, 0x4d2c6dfc, 0x53380d13, - 0x650a7354, 0x766a0abb, 0x81c2c92e, 0x92722c85, - 0xa2bfe8a1, 0xa81a664b, 0xc24b8b70, 0xc76c51a3, - 0xd192e819, 0xd6990624, 0xf40e3585, 0x106aa070, - 0x19a4c116, 0x1e376c08, 0x2748774c, 0x34b0bcb5, - 0x391c0cb3, 0x4ed8aa4a, 0x5b9cca4f, 0x682e6ff3, - 0x748f82ee, 0x78a5636f, 0x84c87814, 0x8cc70208, - 0x90befffa, 0xa4506ceb, 0xbef9a3f7, 0xc67178f2 -}; - -class ESHA256 : public Module -{ - unsigned iv[8]; - bool use_iv; - - /* initializes the IV with a new random value */ - void NewRandomIV() - { - for (int i = 0; i < 8; ++i) - iv[i] = getrandom32(); - } - - /* returns the IV as base64-encrypted string */ - Anope::string GetIVString() - { - char buf[33]; - for (int i = 0; i < 8; ++i) - UNPACK32(iv[i], reinterpret_cast<unsigned char *>(&buf[i << 2])); - buf[32] = '\0'; - return Anope::Hex(buf, 32); - } - - /* splits the appended IV from the password string so it can be used for the next encryption */ - /* password format: <hashmethod>:<password_b64>:<iv_b64> */ - void GetIVFromPass(const Anope::string &password) - { - size_t pos = password.find(':'); - Anope::string buf = password.substr(password.find(':', pos + 1) + 1, password.length()); - char buf2[33]; - Anope::Unhex(buf, buf2); - for (int i = 0 ; i < 8; ++i) - PACK32(reinterpret_cast<unsigned char *>(&buf2[i << 2]), iv[i]); - } - - void SHA256Init(SHA256Context *ctx) - { - for (int i = 0; i < 8; ++i) - ctx->h[i] = iv[i]; - ctx->len = 0; - ctx->tot_len = 0; - } - - void SHA256Transform(SHA256Context *ctx, unsigned char *message, unsigned block_nb) - { - uint32 w[64], wv[8]; - unsigned char *sub_block; - for (unsigned i = 1; i <= block_nb; ++i) - { - int j; - sub_block = message + ((i - 1) << 6); - - for (j = 0; j < 16; ++j) - PACK32(&sub_block[j << 2], w[j]); - for (j = 16; j < 64; ++j) - SHA256_SCR(w, j); - for (j = 0; j < 8; ++j) - wv[j] = ctx->h[j]; - for (j = 0; j < 64; ++j) - { - uint32 t1 = wv[7] + SHA256_F2(wv[4]) + CH(wv[4], wv[5], wv[6]) + sha256_k[j] + w[j]; - uint32 t2 = SHA256_F1(wv[0]) + MAJ(wv[0], wv[1], wv[2]); - wv[7] = wv[6]; - wv[6] = wv[5]; - wv[5] = wv[4]; - wv[4] = wv[3] + t1; - wv[3] = wv[2]; - wv[2] = wv[1]; - wv[1] = wv[0]; - wv[0] = t1 + t2; - } - for (j = 0; j < 8; ++j) - ctx->h[j] += wv[j]; - } - } - - void SHA256Update(SHA256Context *ctx, const unsigned char *message, unsigned len) - { - /* - * XXX here be dragons! - * After many hours of pouring over this, I think I've found the problem. - * When Special created our module from the reference one, he used: - * - * unsigned rem_len = SHA256_BLOCK_SIZE - ctx->len; - * - * instead of the reference's version of: - * - * unsigned tmp_len = SHA256_BLOCK_SIZE - ctx->len; - * unsigned rem_len = len < tmp_len ? len : tmp_len; - * - * I've changed back to the reference version of this code, and it seems to work with no errors. - * So I'm inclined to believe this was the problem.. - * -- w00t (January 06, 2008) - */ - unsigned tmp_len = SHA256_BLOCK_SIZE - ctx->len, rem_len = len < tmp_len ? len : tmp_len; - - memcpy(&ctx->block[ctx->len], message, rem_len); - if (ctx->len + len < SHA256_BLOCK_SIZE) - { - ctx->len += len; - return; - } - unsigned new_len = len - rem_len, block_nb = new_len / SHA256_BLOCK_SIZE; - unsigned char *shifted_message = new unsigned char[len - rem_len]; - memcpy(shifted_message, message + rem_len, len - rem_len); - SHA256Transform(ctx, ctx->block, 1); - SHA256Transform(ctx, shifted_message, block_nb); - rem_len = new_len % SHA256_BLOCK_SIZE; - memcpy(ctx->block, &shifted_message[block_nb << 6], rem_len); - delete [] shifted_message; - ctx->len = rem_len; - ctx->tot_len += (block_nb + 1) << 6; - } - - void SHA256Final(SHA256Context *ctx, unsigned char *digest) - { - unsigned block_nb = 1 + ((SHA256_BLOCK_SIZE - 9) < (ctx->len % SHA256_BLOCK_SIZE)); - unsigned len_b = (ctx->tot_len + ctx->len) << 3; - unsigned pm_len = block_nb << 6; - memset(ctx->block + ctx->len, 0, pm_len - ctx->len); - ctx->block[ctx->len] = 0x80; - UNPACK32(len_b, ctx->block + pm_len - 4); - SHA256Transform(ctx, ctx->block, block_nb); - for (int i = 0 ; i < 8; ++i) - UNPACK32(ctx->h[i], &digest[i << 2]); - } - -/********** ANOPE ******/ - public: - ESHA256(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, ENCRYPTION) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnEncrypt, I_OnCheckAuthentication }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - use_iv = false; - } - - EventReturn OnEncrypt(const Anope::string &src, Anope::string &dest) - { - char digest[SHA256_DIGEST_SIZE + 1]; - SHA256Context ctx; - std::stringstream buf; - - if (!use_iv) - NewRandomIV(); - else - use_iv = false; - - SHA256Init(&ctx); - SHA256Update(&ctx, reinterpret_cast<const unsigned char *>(src.c_str()), src.length()); - SHA256Final(&ctx, reinterpret_cast<unsigned char *>(digest)); - digest[SHA256_DIGEST_SIZE] = '\0'; - buf << "sha256:" << Anope::Hex(digest, SHA256_DIGEST_SIZE) << ":" << GetIVString(); - Log(LOG_DEBUG_2) << "(enc_sha256) hashed password from [" << src << "] to [" << buf.str() << " ]"; - dest = buf.str(); - return EVENT_ALLOW; - } - - EventReturn OnCheckAuthentication(Command *c, CommandSource *source, const std::vector<Anope::string> ¶ms, const Anope::string &account, const Anope::string &password) - { - NickAlias *na = findnick(account); - NickCore *nc = na ? na->nc : NULL; - if (na == NULL) - return EVENT_CONTINUE; - - size_t pos = nc->pass.find(':'); - if (pos == Anope::string::npos) - return EVENT_CONTINUE; - Anope::string hash_method(nc->pass.begin(), nc->pass.begin() + pos); - if (!hash_method.equals_cs("sha256")) - return EVENT_CONTINUE; - - GetIVFromPass(nc->pass); - use_iv = true; - Anope::string buf; - this->OnEncrypt(password, buf); - - if (nc->pass.equals_cs(buf)) - { - /* if we are NOT the first module in the list, - * we want to re-encrypt the pass with the new encryption - */ - if (ModuleManager::FindFirstOf(ENCRYPTION) != this) - enc_encrypt(password, nc->pass); - return EVENT_ALLOW; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(ESHA256) diff --git a/modules/core/gl_global.cpp b/modules/core/gl_global.cpp deleted file mode 100644 index 80c42e017..000000000 --- a/modules/core/gl_global.cpp +++ /dev/null @@ -1,64 +0,0 @@ -/* Global core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "global.h" - -class CommandGLGlobal : public Command -{ - public: - CommandGLGlobal(Module *creator) : Command(creator, "global/global", 1, 1) - { - this->SetDesc(_("Send a message to all users")); - this->SetSyntax(_("\037message\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &msg = params[0]; - - if (!global) - source.Reply("No global reference, is gl_main loaded?"); - else - { - Log(LOG_ADMIN, u, this); - global->SendGlobal(findbot(Config->Global), u->nick, msg); - } - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Administrators to send messages to all users on the \n" - "network. The message will be sent from the nick \002%s\002."), source.owner->nick.c_str()); - return true; - } -}; - -class GLGlobal : public Module -{ - CommandGLGlobal commandglglobal; - - public: - GLGlobal(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandglglobal(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandglglobal); - } -}; - -MODULE_INIT(GLGlobal) diff --git a/modules/core/gl_main.cpp b/modules/core/gl_main.cpp deleted file mode 100644 index c7ccf9209..000000000 --- a/modules/core/gl_main.cpp +++ /dev/null @@ -1,93 +0,0 @@ -/* Global core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "global.h" - -class MyGlobalService : public GlobalService -{ - void ServerGlobal(Server *s, const Anope::string &message) - { - if (s != Me && !s->HasFlag(SERVER_JUPED)) - notice_server(Config->Global, s, "%s", message.c_str()); - for (unsigned i = 0, j = s->GetLinks().size(); i < j; ++i) - this->ServerGlobal(s->GetLinks()[i], message); - } - - public: - MyGlobalService(Module *m) : GlobalService(m) { } - - void SendGlobal(BotInfo *sender, const Anope::string &source, const Anope::string &message) - { - if (Me->GetLinks().empty()) - return; - - Anope::string rmessage; - - if (!source.empty() && !Config->AnonymousGlobal) - rmessage = "[" + source + "] " + message; - else - rmessage = message; - - this->ServerGlobal(Me->GetLinks().front(), rmessage); - } -}; - -class GlobalCore : public Module -{ - MyGlobalService myglobalservice; - - public: - GlobalCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - myglobalservice(this) - { - this->SetAuthor("Anope"); - - BotInfo *Global = findbot(Config->Global); - if (Global == NULL) - throw ModuleException("No bot named " + Config->Global); - - ModuleManager::RegisterService(&this->myglobalservice); - - Implementation i[] = { I_OnRestart, I_OnShutdown, I_OnNewServer, I_OnPreHelp }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - void OnRestart() - { - if (Config->GlobalOnCycle) - global->SendGlobal(findbot(Config->Global), "", Config->GlobalOnCycleMessage); - } - - void OnShutdown() - { - if (Config->GlobalOnCycle) - global->SendGlobal(findbot(Config->Global), "", Config->GlobalOnCycleMessage); - } - - void OnNewServer(Server *s) - { - if (Config->GlobalOnCycle && !Config->GlobalOnCycleUP.empty()) - notice_server(Config->Global, s, "%s", Config->GlobalOnCycleUP.c_str()); - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->Global) - return; - source.Reply(_("%s commands:\n"), Config->Global.c_str()); - } -}; - -MODULE_INIT(GlobalCore) - diff --git a/modules/core/global.h b/modules/core/global.h deleted file mode 100644 index 454e879c2..000000000 --- a/modules/core/global.h +++ /dev/null @@ -1,20 +0,0 @@ -#ifndef GLOBAL_H -#define GLOBAL_H - -class GlobalService : public Service -{ - public: - GlobalService(Module *m) : Service(m, "Global") { } - - /** Send out a global message to all users - * @param sender Our client which should send the global - * @param source The sender of the global - * @param message The message - */ - virtual void SendGlobal(BotInfo *sender, const Anope::string &source, const Anope::string &message) = 0; -}; - -static service_reference<GlobalService> global("Global"); - -#endif // GLOBAL_H - diff --git a/modules/core/help.cpp b/modules/core/help.cpp deleted file mode 100644 index 2a4f25b6c..000000000 --- a/modules/core/help.cpp +++ /dev/null @@ -1,130 +0,0 @@ -/* Core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHelp : public Command -{ - public: - CommandHelp(Module *creator) : Command(creator, "generic/help", 0) - { - this->SetDesc(_("Displays this list and give information about commands")); - this->SetFlag(CFLAG_STRIP_CHANNEL); - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - FOREACH_MOD(I_OnPreHelp, OnPreHelp(source, params)); - - User *u = source.u; - BotInfo *bi = source.owner; - - if (params.empty()) - { - for (BotInfo::command_map::iterator it = bi->commands.begin(), it_end = bi->commands.end(); it != it_end; ++it) - { - const Anope::string &c_name = it->first; - CommandInfo &info = it->second; - - // Smaller command exists - Anope::string cmd = myStrGetToken(c_name, ' ', 0); - if (cmd != it->first && bi->commands.count(cmd)) - continue; - - service_reference<Command> c(info.name); - if (!c) - continue; - if (!Config->HidePrivilegedCommands || info.permission.empty() || u->HasCommand(info.permission)) - { - source.command = c_name; - c->OnServHelp(source); - } - } - } - else - { - bool helped = false; - for (unsigned max = params.size(); max > 0; --max) - { - Anope::string full_command; - for (unsigned i = 0; i < max; ++i) - full_command += " " + params[i]; - full_command.erase(full_command.begin()); - - BotInfo::command_map::iterator it = bi->commands.find(full_command); - if (it == bi->commands.end()) - continue; - - CommandInfo &info = it->second; - - service_reference<Command> c(info.name); - if (!c) - continue; - - if (Config->HidePrivilegedCommands && !info.permission.empty() && !u->HasCommand(info.permission)) - continue; - - const Anope::string &subcommand = params.size() > max ? params[max] : ""; - source.command = full_command; - if (!c->OnHelp(source, subcommand)) - continue; - - helped = true; - - /* Inform the user what permission is required to use the command */ - if (!info.permission.empty()) - { - source.Reply(" "); - source.Reply(_("Access to this command requires the permission \002%s\002 to be present in your opertype."), info.permission.c_str()); - } - if (!c->HasFlag(CFLAG_ALLOW_UNREGISTERED) && !u->IsIdentified()) - { - if (info.permission.empty()) - source.Reply(" "); - source.Reply( _("You need to be identified to use this command.")); - } - /* User doesn't have the proper permission to use this command */ - else if (!info.permission.empty() && !u->HasCommand(info.permission)) - { - source.Reply(_("You cannot use this command.")); - } - - break; - } - - if (helped == false) - source.Reply(_("No help available for \002%s\002."), params[0].c_str()); - } - - FOREACH_MOD(I_OnPostHelp, OnPostHelp(source, params)); - - return; - } -}; - -class Help : public Module -{ - CommandHelp commandhelp; - - public: - Help(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandhelp(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhelp); - } -}; - -MODULE_INIT(Help) diff --git a/modules/core/hs_del.cpp b/modules/core/hs_del.cpp deleted file mode 100644 index 541986aff..000000000 --- a/modules/core/hs_del.cpp +++ /dev/null @@ -1,107 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHSDel : public Command -{ - public: - CommandHSDel(Module *creator) : Command(creator, "hostserv/del", 1, 1) - { - this->SetDesc(_("Delete the vhost of another user")); - this->SetSyntax(_("\037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - NickAlias *na = findnick(nick); - if (na) - { - Log(LOG_ADMIN, u, this) << "for user " << na->nick; - FOREACH_MOD(I_OnDeleteVhost, OnDeleteVhost(na)); - na->hostinfo.RemoveVhost(); - source.Reply(_("Vhost for \002%s\002 removed."), nick.c_str()); - } - else - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Deletes the vhost assigned to the given nick from the\n" - "database.")); - return true; - } -}; - -class CommandHSDelAll : public Command -{ - public: - CommandHSDelAll(Module *creator) : Command(creator, "hostserv/delall", 1, 1) - { - this->SetDesc(_("Delete the vhost for all nicks in a group")); - this->SetSyntax(_("\037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params[0]; - User *u = source.u; - NickAlias *na = findnick(nick); - if (na) - { - FOREACH_MOD(I_OnDeleteVhost, OnDeleteVhost(na)); - NickCore *nc = na->nc; - for (std::list<NickAlias *>::iterator it = nc->aliases.begin(), it_end = nc->aliases.end(); it != it_end; ++it) - { - na = *it; - na->hostinfo.RemoveVhost(); - } - Log(LOG_ADMIN, u, this) << "for all nicks in group " << nc->display; - source.Reply(_("vhosts for group \002%s\002 have been removed."), nc->display.c_str()); - } - else - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Deletes the vhost for all nicks in the same group as\n" - "that of the given nick.")); - return true; - } -}; - -class HSDel : public Module -{ - CommandHSDel commandhsdel; - CommandHSDelAll commandhsdelall; - - public: - HSDel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandhsdel(this), commandhsdelall(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhsdel); - ModuleManager::RegisterService(&commandhsdelall); - } -}; - -MODULE_INIT(HSDel) diff --git a/modules/core/hs_group.cpp b/modules/core/hs_group.cpp deleted file mode 100644 index 8d6fbd630..000000000 --- a/modules/core/hs_group.cpp +++ /dev/null @@ -1,80 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHSGroup : public Command -{ - void Sync(NickAlias *na) - { - if (!na || !na->hostinfo.HasVhost()) - return; - - for (std::list<NickAlias *>::iterator it = na->nc->aliases.begin(), it_end = na->nc->aliases.end(); it != it_end; ++it) - { - NickAlias *nick = *it; - nick->hostinfo.SetVhost(na->hostinfo.GetIdent(), na->hostinfo.GetHost(), na->hostinfo.GetCreator()); - } - } - - public: - CommandHSGroup(Module *creator) : Command(creator, "hostserv/group", 0, 0) - { - this->SetDesc(_("Syncs the vhost for all nicks in a group")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na = findnick(u->nick); - if (na && u->Account() == na->nc && na->hostinfo.HasVhost()) - { - this->Sync(na); - if (!na->hostinfo.GetIdent().empty()) - source.Reply(_("All vhost's in the group \002%s\002 have been set to \002%s\002@\002%s\002"), u->Account()->display.c_str(), na->hostinfo.GetIdent().c_str(), na->hostinfo.GetHost().c_str()); - else - source.Reply(_("All vhost's in the group \002%s\002 have been set to \002%s\002"), u->Account()->display.c_str(), na->hostinfo.GetHost().c_str()); - } - else - source.Reply(HOST_NOT_ASSIGNED); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command allows users to set the vhost of their\n" - "CURRENT nick to be the vhost for all nicks in the same\n" - "group.")); - return true; - } -}; - -class HSGroup : public Module -{ - CommandHSGroup commandhsgroup; - - public: - HSGroup(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandhsgroup(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhsgroup); - } -}; - -MODULE_INIT(HSGroup) diff --git a/modules/core/hs_list.cpp b/modules/core/hs_list.cpp deleted file mode 100644 index 589eef3e1..000000000 --- a/modules/core/hs_list.cpp +++ /dev/null @@ -1,137 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHSList : public Command -{ - public: - CommandHSList(Module *creator) : Command(creator, "hostserv/list", 0, 1) - { - this->SetDesc(_("Displays one or more vhost entries.")); - this->SetSyntax(_("\002[<key>|<#X-Y>]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &key = !params.empty() ? params[0] : ""; - int from = 0, to = 0, counter = 1; - unsigned display_counter = 0; - - /** - * Do a check for a range here, then in the next loop - * we'll only display what has been requested.. - **/ - if (!key.empty() && key[0] == '#') - { - size_t tmp = key.find('-'); - if (tmp == Anope::string::npos || tmp == key.length() || tmp == 1) - { - source.Reply(LIST_INCORRECT_RANGE); - return; - } - for (unsigned i = 1, end = key.length(); i < end; ++i) - { - if (!isdigit(key[i]) && i != tmp) - { - source.Reply(LIST_INCORRECT_RANGE); - return; - } - try - { - from = convertTo<int>(key.substr(1, tmp - 1)); - to = convertTo<int>(key.substr(tmp + 1)); - } - catch (const ConvertException &) { } - } - } - - for (nickalias_map::const_iterator it = NickAliasList.begin(), it_end = NickAliasList.end(); it != it_end; ++it) - { - NickAlias *na = it->second; - - if (!na->hostinfo.HasVhost()) - continue; - - if (!key.empty() && key[0] != '#') - { - if ((Anope::Match(na->nick, key) || Anope::Match(na->hostinfo.GetHost(), key)) && display_counter < Config->NSListMax) - { - ++display_counter; - if (!na->hostinfo.GetIdent().empty()) - source.Reply(_("#%d Nick:\002%s\002, vhost:\002%s\002@\002%s\002 (%s - %s)"), counter, na->nick.c_str(), na->hostinfo.GetIdent().c_str(), na->hostinfo.GetHost().c_str(), na->hostinfo.GetCreator().c_str(), do_strftime(na->hostinfo.GetTime()).c_str()); - else - source.Reply(_("#%d Nick:\002%s\002, vhost:\002%s\002 (%s - %s)"), counter, na->nick.c_str(), na->hostinfo.GetHost().c_str(), na->hostinfo.GetCreator().c_str(), do_strftime(na->hostinfo.GetTime()).c_str()); - } - } - else - { - /** - * List the host if its in the display range, and not more - * than NSListMax records have been displayed... - **/ - if (((counter >= from && counter <= to) || (!from && !to)) && display_counter < Config->NSListMax) - { - ++display_counter; - if (!na->hostinfo.GetIdent().empty()) - source.Reply(_("#%d Nick:\002%s\002, vhost:\002%s\002@\002%s\002 (%s - %s)"), counter, na->nick.c_str(), na->hostinfo.GetIdent().c_str(), na->hostinfo.GetHost().c_str(), na->hostinfo.GetCreator().c_str(), do_strftime(na->hostinfo.GetTime()).c_str()); - else - source.Reply(_("#%d Nick:\002%s\002, vhost:\002%s\002 (%s - %s)"), counter, na->nick.c_str(), na->hostinfo.GetHost().c_str(), na->hostinfo.GetCreator().c_str(), do_strftime(na->hostinfo.GetTime()).c_str()); - } - } - ++counter; - } - if (!key.empty()) - source.Reply(_("Displayed records matching key \002%s\002 (Count: \002%d\002)"), key.c_str(), display_counter); - else - { - if (from) - source.Reply(_("Displayed records from \002%d\002 to \002%d\002"), from, to); - else - source.Reply(_("Displayed all records (Count: \002%d\002)"), display_counter); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command lists registered vhosts to the operator\n" - "if a Key is specified, only entries whos nick or vhost match\n" - "the pattern given in <key> are displayed e.g. Rob* for all\n" - "entries beginning with \"Rob\"\n" - "If a #X-Y style is used, only entries between the range of X\n" - "and Y will be displayed, e.g. #1-3 will display the first 3\n" - "nick/vhost entries.\n" - "The list uses the value of NSListMax as a hard limit for the\n" - "number of items to display to a operator at any 1 time.")); - return true; - } -}; - -class HSList : public Module -{ - CommandHSList commandhslist; - - public: - HSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandhslist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhslist); - } -}; - -MODULE_INIT(HSList) diff --git a/modules/core/hs_main.cpp b/modules/core/hs_main.cpp deleted file mode 100644 index a6cc6bbb7..000000000 --- a/modules/core/hs_main.cpp +++ /dev/null @@ -1,85 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class HostServCore : public Module -{ - public: - HostServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE) - { - this->SetAuthor("Anope"); - - if (!ircd || !ircd->vhost) - throw ModuleException("Your IRCd does not suppor vhosts"); - - BotInfo *HostServ = findbot(Config->HostServ); - if (HostServ == NULL) - throw ModuleException("No bot named " + Config->HostServ); - - Implementation i[] = { I_OnNickIdentify, I_OnNickUpdate, I_OnPreHelp }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - void OnNickIdentify(User *u) - { - HostInfo *ho = NULL; - NickAlias *na = findnick(u->nick); - if (na && na->hostinfo.HasVhost()) - ho = &na->hostinfo; - else - { - na = findnick(u->Account()->display); - if (na && na->hostinfo.HasVhost()) - ho = &na->hostinfo; - } - if (ho == NULL) - return; - - if (u->vhost.empty() || !u->vhost.equals_cs(na->hostinfo.GetHost()) || (!na->hostinfo.GetIdent().empty() && !u->GetVIdent().equals_cs(na->hostinfo.GetIdent()))) - { - ircdproto->SendVhost(u, na->hostinfo.GetIdent(), na->hostinfo.GetHost()); - if (ircd->vhost) - { - u->vhost = na->hostinfo.GetHost(); - u->UpdateHost(); - } - if (ircd->vident && !na->hostinfo.GetIdent().empty()) - u->SetVIdent(na->hostinfo.GetIdent()); - - BotInfo *bi = findbot(Config->HostServ); - if (bi) - { - if (!na->hostinfo.GetIdent().empty()) - u->SendMessage(bi, _("Your vhost of \002%s\002@\002%s\002 is now activated."), na->hostinfo.GetIdent().c_str(), na->hostinfo.GetHost().c_str()); - else - u->SendMessage(bi, _("Your vhost of \002%s\002 is now activated."), na->hostinfo.GetHost().c_str()); - } - } - } - - void OnNickUpdate(User *u) - { - this->OnNickIdentify(u); - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->HostServ) - return; - source.Reply(_("%s commands:\n"), Config->HostServ.c_str()); - } -}; - -MODULE_INIT(HostServCore) - diff --git a/modules/core/hs_off.cpp b/modules/core/hs_off.cpp deleted file mode 100644 index a3f11c2bd..000000000 --- a/modules/core/hs_off.cpp +++ /dev/null @@ -1,67 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHSOff : public Command -{ - public: - CommandHSOff(Module *creator) : Command(creator, "hostserv/off", 0, 0) - { - this->SetDesc(_("Deactivates your assigned vhost")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na = findnick(u->nick); - - if (!na || !na->hostinfo.HasVhost()) - source.Reply(HOST_NOT_ASSIGNED); - else - { - ircdproto->SendVhostDel(u); - Log(LOG_COMMAND, u, this) << "to disable their vhost"; - source.Reply(_("Your vhost was removed and the normal cloaking restored.")); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Deactivates the vhost currently assigned to the nick in use.\n" - "When you use this command any user who performs a /whois\n" - "on you will see your real IP address.")); - return true; - } -}; - -class HSOff : public Module -{ - CommandHSOff commandhsoff; - - public: - HSOff(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandhsoff(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhsoff); - } -}; - -MODULE_INIT(HSOff) diff --git a/modules/core/hs_on.cpp b/modules/core/hs_on.cpp deleted file mode 100644 index 0ba124ba1..000000000 --- a/modules/core/hs_on.cpp +++ /dev/null @@ -1,77 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHSOn : public Command -{ - public: - CommandHSOn(Module *creator) : Command(creator, "hostserv/on", 0, 0) - { - this->SetDesc(_("Activates your assigned vhost")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na = findnick(u->nick); - if (na && u->Account() == na->nc && na->hostinfo.HasVhost()) - { - if (!na->hostinfo.GetIdent().empty()) - source.Reply(_("Your vhost of \002%s\002@\002%s\002 is now activated."), na->hostinfo.GetIdent().c_str(), na->hostinfo.GetHost().c_str()); - else - source.Reply(_("Your vhost of \002%s\002 is now activated."), na->hostinfo.GetHost().c_str()); - Log(LOG_COMMAND, u, this) << "to enable their vhost of " << (!na->hostinfo.GetIdent().empty() ? na->hostinfo.GetIdent() + "@" : "") << na->hostinfo.GetHost(); - ircdproto->SendVhost(u, na->hostinfo.GetIdent(), na->hostinfo.GetHost()); - if (ircd->vhost) - u->vhost = na->hostinfo.GetHost(); - if (ircd->vident) - { - if (!na->hostinfo.GetIdent().empty()) - u->SetVIdent(na->hostinfo.GetIdent()); - } - u->UpdateHost(); - } - else - source.Reply(HOST_NOT_ASSIGNED); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Activates the vhost currently assigned to the nick in use.\n" - "When you use this command any user who performs a /whois\n" - "on you will see the vhost instead of your real IP address.")); - return true; - } -}; - -class HSOn : public Module -{ - CommandHSOn commandhson; - - public: - HSOn(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandhson(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhson); - } -}; - -MODULE_INIT(HSOn) diff --git a/modules/core/hs_set.cpp b/modules/core/hs_set.cpp deleted file mode 100644 index 4711022db..000000000 --- a/modules/core/hs_set.cpp +++ /dev/null @@ -1,236 +0,0 @@ -/* HostServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandHSSet : public Command -{ - public: - CommandHSSet(Module *creator) : Command(creator, "hostserv/set", 2, 2) - { - this->SetDesc(_("Set the vhost of another user")); - this->SetSyntax(_("\037nick\037 \037hostmask\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params[0]; - - NickAlias *na = findnick(nick); - if (na == NULL) - { - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - return; - } - - Anope::string rawhostmask = params[1]; - - Anope::string user, host; - size_t a = rawhostmask.find('@'); - - if (a == Anope::string::npos) - host = rawhostmask; - else - { - user = rawhostmask.substr(0, a); - host = rawhostmask.substr(a + 1); - } - - if (host.empty()) - { - this->OnSyntaxError(source, ""); - return; - } - - if (!user.empty()) - { - if (user.length() > Config->UserLen) - { - source.Reply(HOST_SET_IDENTTOOLONG, Config->UserLen); - return; - } - else if (!ircd->vident) - { - source.Reply(HOST_NO_VIDENT); - return; - } - for (Anope::string::iterator s = user.begin(), s_end = user.end(); s != s_end; ++s) - if (!isvalidchar(*s)) - { - source.Reply(HOST_SET_IDENT_ERROR); - return; - } - } - - if (host.length() > Config->HostLen) - { - source.Reply(HOST_SET_TOOLONG, Config->HostLen); - return; - } - - if (!isValidHost(host, 3)) - { - source.Reply(HOST_SET_ERROR); - return; - } - - Log(LOG_ADMIN, u, this) << "to set the vhost of " << na->nick << " to " << (!user.empty() ? user + "@" : "") << host; - - na->hostinfo.SetVhost(user, host, u->nick); - FOREACH_MOD(I_OnSetVhost, OnSetVhost(na)); - if (!user.empty()) - source.Reply(_("VHost for \002%s\002 set to \002%s\002@\002%s\002."), nick.c_str(), user.c_str(), host.c_str()); - else - source.Reply(_("VHost for \002%s\002 set to \002%s\002."), nick.c_str(), host.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets the vhost for the given nick to that of the given\n" - "hostmask. If your IRCD supports vIdents, then using\n" - "SET <nick> <ident>@<hostmask> set idents for users as \n" - "well as vhosts.")); - return true; - } -}; - -class CommandHSSetAll : public Command -{ - void Sync(NickAlias *na) - { - if (!na || !na->hostinfo.HasVhost()) - return; - - for (std::list<NickAlias *>::iterator it = na->nc->aliases.begin(), it_end = na->nc->aliases.end(); it != it_end; ++it) - { - NickAlias *nick = *it; - nick->hostinfo.SetVhost(na->hostinfo.GetIdent(), na->hostinfo.GetHost(), na->hostinfo.GetCreator()); - } - } - - public: - CommandHSSetAll(Module *creator) : Command(creator, "hostserv/setall", 2, 2) - { - this->SetDesc(_("Set the vhost for all nicks in a group")); - this->SetSyntax(_("\037nick\037 \037hostmask>\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string nick = params[0]; - - NickAlias *na = findnick(nick); - if (na == NULL) - { - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - return; - } - - Anope::string rawhostmask = params[1]; - - Anope::string user, host; - size_t a = rawhostmask.find('@'); - - if (a == Anope::string::npos) - host = rawhostmask; - else - { - user = rawhostmask.substr(0, a); - host = rawhostmask.substr(a + 1); - } - - if (host.empty()) - { - this->OnSyntaxError(source, ""); - return; - } - - if (!user.empty()) - { - if (user.length() > Config->UserLen) - { - source.Reply(HOST_SET_IDENTTOOLONG, Config->UserLen); - return; - } - else if (!ircd->vident) - { - source.Reply(HOST_NO_VIDENT); - return; - } - for (Anope::string::iterator s = user.begin(), s_end = user.end(); s != s_end; ++s) - if (!isvalidchar(*s)) - { - source.Reply(HOST_SET_IDENT_ERROR); - return; - } - } - - if (host.length() > Config->HostLen) - { - source.Reply(HOST_SET_TOOLONG, Config->HostLen); - return; - } - - if (!isValidHost(host, 3)) - { - source.Reply(HOST_SET_ERROR); - return; - } - - Log(LOG_ADMIN, u, this) << "to set the vhost of " << na->nick << " to " << (!user.empty() ? user + "@" : "") << host; - - na->hostinfo.SetVhost(user, host, u->nick); - this->Sync(na); - FOREACH_MOD(I_OnSetVhost, OnSetVhost(na)); - if (!user.empty()) - source.Reply(_("VHost for group \002%s\002 set to \002%s\002@\002%s\002."), nick.c_str(), user.c_str(), host.c_str()); - else - source.Reply(_("VHost for group \002%s\002 set to \002%s\002."), nick.c_str(), host.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets the vhost for all nicks in the same group as that\n" - "of the given nick. If your IRCD supports vIdents, then\n" - "using SETALL <nick> <ident>@<hostmask> will set idents\n" - "for users as well as vhosts.\n" - "* NOTE, this will not update the vhost for any nicks\n" - "added to the group after this command was used.")); - return true; - } -}; - -class HSSet : public Module -{ - CommandHSSet commandhsset; - CommandHSSetAll commandhssetall; - - public: - HSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), commandhsset(this), commandhssetall(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandhsset); - ModuleManager::RegisterService(&commandhssetall); - } -}; - -MODULE_INIT(HSSet) diff --git a/modules/core/memoserv.h b/modules/core/memoserv.h deleted file mode 100644 index 0bf0c79ca..000000000 --- a/modules/core/memoserv.h +++ /dev/null @@ -1,41 +0,0 @@ -#ifndef MEMOSERV_H -#define MEMOSERV_H - -class MemoServService : public Service -{ - public: - enum MemoResult - { - MEMO_SUCCESS, - MEMO_INVALID_TARGET, - MEMO_TOO_FAST, - MEMO_TARGET_FULL - }; - - MemoServService(Module *m) : Service(m, "MemoServ") { } - - /** Retrieve the memo info for a nick or channel - * @param target Target - * @param ischan Set to true if target is a channel - * @return A memoinfo structure or NULL - */ - virtual MemoInfo *GetMemoInfo(const Anope::string &target, bool &ischan) = 0; - - /** Sends a memo. - * @param source The source of the memo, can be anythin. - * @param target The target of the memo, nick or channel. - * @param message Memo text - * @param force true to force the memo, restrictions/delays etc are not checked - */ - virtual MemoResult Send(const Anope::string &source, const Anope::string &target, const Anope::string &message, bool force = false) = 0; - - /** Check for new memos and notify the user if there are any - * @param u The user - */ - virtual void Check(User *u) = 0; -}; - -static service_reference<MemoServService> memoserv("MemoServ"); - -#endif // MEMOSERV_H - diff --git a/modules/core/ms_cancel.cpp b/modules/core/ms_cancel.cpp deleted file mode 100644 index e5beffa10..000000000 --- a/modules/core/ms_cancel.cpp +++ /dev/null @@ -1,77 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -class CommandMSCancel : public Command -{ - public: - CommandMSCancel(Module *creator) : Command(creator, "memoserv/cancel", 1, 1) - { - this->SetDesc(_("Cancel the last memo you sent")); - this->SetSyntax(_("{\037nick\037 | \037channel\037}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nname = params[0]; - - bool ischan; - MemoInfo *mi = memoserv->GetMemoInfo(nname, ischan); - - if (mi == NULL) - source.Reply(ischan ? CHAN_X_NOT_REGISTERED : _(NICK_X_NOT_REGISTERED), nname.c_str()); - else - { - for (int i = mi->memos.size() - 1; i >= 0; --i) - if (mi->memos[i]->HasFlag(MF_UNREAD) && u->Account()->display.equals_ci(mi->memos[i]->sender)) - { - FOREACH_MOD(I_OnMemoDel, OnMemoDel(findnick(nname)->nc, mi, mi->memos[i])); - mi->Del(mi->memos[i]); - source.Reply(_("Last memo to \002%s\002 has been cancelled."), nname.c_str()); - return; - } - - source.Reply(_("No memo was cancelable.")); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Cancels the last memo you sent to the given nick or channel,\n" - "provided it has not been read at the time you use the command.")); - return true; - } -}; - -class MSCancel : public Module -{ - CommandMSCancel commandmscancel; - - public: - MSCancel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmscancel(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmscancel); - } -}; - -MODULE_INIT(MSCancel) diff --git a/modules/core/ms_check.cpp b/modules/core/ms_check.cpp deleted file mode 100644 index 3019e270f..000000000 --- a/modules/core/ms_check.cpp +++ /dev/null @@ -1,89 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandMSCheck : public Command -{ - public: - CommandMSCheck(Module *creator) : Command(creator, "memoserv/check", 1, 1) - { - this->SetDesc(_("Checks if last memo to a nick was read")); - this->SetSyntax(_("\037nick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &recipient = params[0]; - - bool found = false; - - NickAlias *na = findnick(recipient); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, recipient.c_str()); - return; - } - - MemoInfo *mi = &na->nc->memos; - - /* Okay, I know this looks strange but we wanna get the LAST memo, so we - have to loop backwards */ - - for (int i = mi->memos.size() - 1; i >= 0; --i) - { - if (u->Account()->display.equals_ci(mi->memos[i]->sender)) - { - found = true; /* Yes, we've found the memo */ - - if (mi->memos[i]->HasFlag(MF_UNREAD)) - source.Reply(_("The last memo you sent to %s (sent on %s) has not yet been read."), na->nick.c_str(), do_strftime(mi->memos[i]->time).c_str()); - else - source.Reply(_("The last memo you sent to %s (sent on %s) has been read."), na->nick.c_str(), do_strftime(mi->memos[i]->time).c_str()); - break; - } - } - - if (!found) - source.Reply(_("Nick %s doesn't have a memo from you."), na->nick.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Checks whether the _last_ memo you sent to \037nick\037 has been read\n" - "or not. Note that this does only work with nicks, not with chans.")); - return true; - } -}; - -class MSCheck : public Module -{ - CommandMSCheck commandmscheck; - - public: - MSCheck(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmscheck(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmscheck); - } -}; - -MODULE_INIT(MSCheck) diff --git a/modules/core/ms_del.cpp b/modules/core/ms_del.cpp deleted file mode 100644 index 991adff2b..000000000 --- a/modules/core/ms_del.cpp +++ /dev/null @@ -1,163 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class MemoDelCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - MemoInfo *mi; - public: - MemoDelCallback(CommandSource &_source, ChannelInfo *_ci, MemoInfo *_mi, const Anope::string &list) : NumberList(list, true), source(_source), ci(_ci), mi(_mi) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > mi->memos.size()) - return; - - if (ci) - FOREACH_MOD(I_OnMemoDel, OnMemoDel(ci, mi, mi->memos[Number - 1])); - else - FOREACH_MOD(I_OnMemoDel, OnMemoDel(source.u->Account(), mi, mi->memos[Number - 1])); - - mi->Del(Number - 1); - source.Reply(_("Memo %d has been deleted."), Number); - } -}; - -class CommandMSDel : public Command -{ - public: - CommandMSDel(Module *creator) : Command(creator, "memoserv/del", 0, 2) - { - this->SetDesc(_("Delete a memo or memos")); - this->SetSyntax(_("[\037channel\037] {\037num\037 | \037list\037 | LAST | ALL}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - MemoInfo *mi; - ChannelInfo *ci = NULL; - Anope::string numstr = !params.empty() ? params[0] : "", chan; - - if (!numstr.empty() && numstr[0] == '#') - { - chan = numstr; - numstr = params.size() > 1 ? params[1] : ""; - - if (!(ci = cs_findchan(chan))) - { - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - return; - } - else if (readonly) - { - source.Reply(READ_ONLY_MODE); - return; - } - else if (!ci->HasPriv(u, CA_MEMO)) - { - source.Reply(ACCESS_DENIED); - return; - } - mi = &ci->memos; - } - else - mi = &u->Account()->memos; - if (numstr.empty() || (!isdigit(numstr[0]) && !numstr.equals_ci("ALL") && !numstr.equals_ci("LAST"))) - this->OnSyntaxError(source, numstr); - else if (mi->memos.empty()) - { - if (!chan.empty()) - source.Reply(MEMO_X_HAS_NO_MEMOS, chan.c_str()); - else - source.Reply(MEMO_HAVE_NO_MEMOS); - } - else - { - if (isdigit(numstr[0])) - { - MemoDelCallback list(source, ci, mi, numstr); - list.Process(); - } - else if (numstr.equals_ci("LAST")) - { - /* Delete last memo. */ - if (ci) - FOREACH_MOD(I_OnMemoDel, OnMemoDel(ci, mi, mi->memos[mi->memos.size() - 1])); - else - FOREACH_MOD(I_OnMemoDel, OnMemoDel(u->Account(), mi, mi->memos[mi->memos.size() - 1])); - mi->Del(mi->memos[mi->memos.size() - 1]); - source.Reply(_("Memo %d has been deleted."), mi->memos.size() + 1); - } - else - { - if (ci) - FOREACH_MOD(I_OnMemoDel, OnMemoDel(ci, mi, NULL)); - else - FOREACH_MOD(I_OnMemoDel, OnMemoDel(u->Account(), mi, NULL)); - /* Delete all memos. */ - for (unsigned i = 0, end = mi->memos.size(); i < end; ++i) - delete mi->memos[i]; - mi->memos.clear(); - if (!chan.empty()) - source.Reply(_("All memos for channel %s have been deleted."), chan.c_str()); - else - source.Reply(_("All of your memos have been deleted.")); - } - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Deletes the specified memo or memos. You can supply\n" - "multiple memo numbers or ranges of numbers instead of a\n" - "single number, as in the second example below.\n" - " \n" - "If \002LAST\002 is given, the last memo will be deleted.\n" - "If \002ALL\002 is given, deletes all of your memos.\n" - " \n" - "Examples:\n" - " \n" - " \002DEL 1\002\n" - " Deletes your first memo.\n" - " \n" - " \002DEL 2-5,7-9\002\n" - " Deletes memos numbered 2 through 5 and 7 through 9.")); - return true; - } -}; - -class MSDel : public Module -{ - CommandMSDel commandmsdel; - - public: - MSDel(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsdel(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmsdel); - } -}; - -MODULE_INIT(MSDel) diff --git a/modules/core/ms_ignore.cpp b/modules/core/ms_ignore.cpp deleted file mode 100644 index c8b9c19e6..000000000 --- a/modules/core/ms_ignore.cpp +++ /dev/null @@ -1,110 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -class CommandMSIgnore : public Command -{ - public: - CommandMSIgnore(Module *creator) : Command(creator, "memoserv/ignore", 1, 3) - { - this->SetDesc(_("Manage your memo ignore list")); - this->SetSyntax(_("[\037channel\037] {\002ADD|DEL|LIST\002} [\037entry\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string channel = params[0]; - Anope::string command = (params.size() > 1 ? params[1] : ""); - Anope::string param = (params.size() > 2 ? params[2] : ""); - - if (channel[0] != '#') - { - param = command; - command = channel; - channel = u->nick; - } - - bool ischan; - MemoInfo *mi = memoserv->GetMemoInfo(channel, ischan); - if (!mi) - source.Reply(ischan ? CHAN_X_NOT_REGISTERED : _(NICK_X_NOT_REGISTERED), channel.c_str()); - else if (ischan && !cs_findchan(channel)->HasPriv(u, CA_MEMO)) - source.Reply(ACCESS_DENIED); - else if (command.equals_ci("ADD") && !param.empty()) - { - if (std::find(mi->ignores.begin(), mi->ignores.end(), param.ci_str()) == mi->ignores.end()) - { - mi->ignores.push_back(param.ci_str()); - source.Reply(_("\002%s\002 added to your ignore list."), param.c_str()); - } - else - source.Reply(_("\002%s\002 is already on your ignore list."), param.c_str()); - } - else if (command.equals_ci("DEL") && !param.empty()) - { - std::vector<Anope::string>::iterator it = std::find(mi->ignores.begin(), mi->ignores.end(), param.ci_str()); - - if (it != mi->ignores.end()) - { - mi->ignores.erase(it); - source.Reply(_("\002%s\002 removed from your ignore list."), param.c_str()); - } - else - source.Reply(_("\002%s\002 is not on your ignore list."), param.c_str()); - } - else if (command.equals_ci("LIST")) - { - if (mi->ignores.empty()) - source.Reply(_("Your memo ignore list is empty.")); - else - { - source.Reply(_("Ignore list:")); - for (unsigned i = 0; i < mi->ignores.size(); ++i) - source.Reply(" %s", mi->ignores[i].c_str()); - } - } - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to ignore users by nick or host from memoing you. If someone on your\n" - "memo ignore list tries to memo you, they will not be told that you have them ignored.")); - return true; - } -}; - -class MSIgnore : public Module -{ - CommandMSIgnore commandmsignore; - - public: - MSIgnore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsignore(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmsignore); - } -}; - -MODULE_INIT(MSIgnore) diff --git a/modules/core/ms_info.cpp b/modules/core/ms_info.cpp deleted file mode 100644 index 9fdb467c9..000000000 --- a/modules/core/ms_info.cpp +++ /dev/null @@ -1,219 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandMSInfo : public Command -{ - public: - CommandMSInfo(Module *creator) : Command(creator, "memoserv/info", 0, 1) - { - this->SetDesc(_("Displays information about your memos")); - this->SetSyntax(_("[\037nick\037 | \037channel\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const MemoInfo *mi; - NickAlias *na = NULL; - ChannelInfo *ci = NULL; - const Anope::string &nname = !params.empty() ? params[0] : ""; - int hardmax = 0; - - if (!nname.empty() && nname[0] != '#' && u->HasPriv("memoserv/info")) - { - na = findnick(nname); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, nname.c_str()); - return; - } - mi = &na->nc->memos; - hardmax = na->nc->HasFlag(NI_MEMO_HARDMAX) ? 1 : 0; - } - else if (!nname.empty() && nname[0] == '#') - { - if (!(ci = cs_findchan(nname))) - { - source.Reply(CHAN_X_NOT_REGISTERED, nname.c_str()); - return; - } - else if (!ci->HasPriv(u, CA_MEMO)) - { - source.Reply(ACCESS_DENIED); - return; - } - mi = &ci->memos; - hardmax = ci->HasFlag(CI_MEMO_HARDMAX) ? 1 : 0; - } - else if (!nname.empty()) /* It's not a chan and we aren't services admin */ - { - source.Reply(ACCESS_DENIED); - return; - } - else - { - mi = &u->Account()->memos; - hardmax = u->Account()->HasFlag(NI_MEMO_HARDMAX) ? 1 : 0; - } - - if (!nname.empty() && (ci || na->nc != u->Account())) - { - if (mi->memos.empty()) - source.Reply(_("%s currently has no memos."), nname.c_str()); - else if (mi->memos.size() == 1) - { - if (mi->memos[0]->HasFlag(MF_UNREAD)) - source.Reply(_("%s currently has \0021\002 memo, and it has not yet been read."), nname.c_str()); - else - source.Reply(_("%s currently has \0021\002 memo."), nname.c_str()); - } - else - { - unsigned count = 0, i, end; - for (i = 0, end = mi->memos.size(); i < end; ++i) - if (mi->memos[i]->HasFlag(MF_UNREAD)) - ++count; - if (count == mi->memos.size()) - source.Reply(_("%s currently has \002%d\002 memos; all of them are unread."), nname.c_str(), count); - else if (!count) - source.Reply(_("%s currently has \002%d\002 memos."), nname.c_str(), mi->memos.size()); - else if (count == 1) - source.Reply(_("%s currently has \002%d\002 memos, of which \0021\002 is unread."), nname.c_str(), mi->memos.size()); - else - source.Reply(_("%s currently has \002%d\002 memos, of which \002%d\002 are unread."), nname.c_str(), mi->memos.size(), count); - } - if (!mi->memomax) - { - if (hardmax) - source.Reply(_("%s's memo limit is \002%d\002, and may not be changed."), nname.c_str(), mi->memomax); - else - source.Reply(_("%s's memo limit is \002%d\002."), nname.c_str(), mi->memomax); - } - else if (mi->memomax > 0) - { - if (hardmax) - source.Reply(_("%s's memo limit is \002%d\002, and may not be changed."), nname.c_str(), mi->memomax); - else - source.Reply(_("%s's memo limit is \002%d\002."), nname.c_str(), mi->memomax); - } - else - source.Reply(_("%s has no memo limit."), nname.c_str()); - - /* I ripped this code out of ircservices 4.4.5, since I didn't want - to rewrite the whole thing (it pisses me off). */ - if (na) - { - if (na->nc->HasFlag(NI_MEMO_RECEIVE) && na->nc->HasFlag(NI_MEMO_SIGNON)) - source.Reply(_("%s is notified of new memos at logon and when they arrive."), nname.c_str()); - else if (na->nc->HasFlag(NI_MEMO_RECEIVE)) - source.Reply(_("%s is notified when new memos arrive."), nname.c_str()); - else if (na->nc->HasFlag(NI_MEMO_SIGNON)) - source.Reply(_("%s is notified of news memos at logon."), nname.c_str()); - else - source.Reply(_("%s is not notified of new memos."), nname.c_str()); - } - } - else /* !nname || (!ci || na->nc == u->Account()) */ - { - if (mi->memos.empty()) - source.Reply(_("You currently have no memos.")); - else if (mi->memos.size() == 1) - { - if (mi->memos[0]->HasFlag(MF_UNREAD)) - source.Reply(_("You currently have \0021\002 memo, and it has not yet been read.")); - else - source.Reply(_("You currently have \0021\002 memo.")); - } - else - { - unsigned count = 0, i, end; - for (i = 0, end = mi->memos.size(); i < end; ++i) - if (mi->memos[i]->HasFlag(MF_UNREAD)) - ++count; - if (count == mi->memos.size()) - source.Reply(_("You currently have \002%d\002 memos; all of them are unread."), count); - else if (!count) - source.Reply(_("You currently have \002%d\002 memos."), mi->memos.size()); - else if (count == 1) - source.Reply(_("You currently have \002%d\002 memos, of which \0021\002 is unread."), mi->memos.size()); - else - source.Reply(_("You currently have \002%d\002 memos, of which \002%d\002 are unread."), mi->memos.size(), count); - } - - if (!mi->memomax) - { - if (!u->IsServicesOper() && hardmax) - source.Reply(_("Your memo limit is \0020\002; you will not receive any new memos. You cannot change this limit.")); - else - source.Reply(_("Your memo limit is \0020\002; you will not receive any new memos.")); - } - else if (mi->memomax > 0) - { - if (!u->IsServicesOper() && hardmax) - source.Reply(_("Your memo limit is \002%d\002, and may not be changed."), mi->memomax); - else - source.Reply(_("Your memo limit is \002%d\002."), mi->memomax); - } - else - source.Reply(_("You have no limit on the number of memos you may keep.")); - - /* Ripped too. But differently because of a seg fault (loughs) */ - if (u->Account()->HasFlag(NI_MEMO_RECEIVE) && u->Account()->HasFlag(NI_MEMO_SIGNON)) - source.Reply(_("You will be notified of new memos at logon and when they arrive.")); - else if (u->Account()->HasFlag(NI_MEMO_RECEIVE)) - source.Reply(_("You will be notified when new memos arrive.")); - else if (u->Account()->HasFlag(NI_MEMO_SIGNON)) - source.Reply(_("You will be notified of new memos at logon.")); - else - source.Reply(_("You will not be notified of new memos.")); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Without a parameter, displays information on the number of\n" - "memos you have, how many of them are unread, and how many\n" - "total memos you can receive.\n" - " \n" - "With a channel parameter, displays the same information for\n" - "the given channel.\n" - " \n" - "With a nickname parameter, displays the same information\n" - "for the given nickname. This use limited to \002Services\n" - "Operators\002.")); - - return true; - } -}; - -class MSInfo : public Module -{ - CommandMSInfo commandmsinfo; - - public: - MSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsinfo(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmsinfo); - } -}; - -MODULE_INIT(MSInfo) diff --git a/modules/core/ms_list.cpp b/modules/core/ms_list.cpp deleted file mode 100644 index 26821a413..000000000 --- a/modules/core/ms_list.cpp +++ /dev/null @@ -1,168 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class MemoListCallback : public NumberList -{ - CommandSource &source; - ChannelInfo *ci; - const MemoInfo *mi; - bool SentHeader; - public: - MemoListCallback(CommandSource &_source, ChannelInfo *_ci, const MemoInfo *_mi, const Anope::string &list) : NumberList(list, false), source(_source), ci(_ci), mi(_mi), SentHeader(false) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > mi->memos.size()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Memos for %s:"), ci ? ci->name.c_str() : source.u->nick.c_str()); - source.Reply(_(" Num Sender Date/Time")); - } - - DoList(source, mi, Number - 1); - } - - static void DoList(CommandSource &source, const MemoInfo *mi, unsigned index) - { - Memo *m = mi->memos[index]; - source.Reply(_("%c%3d %-16s %s"), (m->HasFlag(MF_UNREAD)) ? '*' : ' ', index + 1, m->sender.c_str(), do_strftime(m->time).c_str()); - } -}; - -class CommandMSList : public Command -{ - public: - CommandMSList(Module *creator) : Command(creator, "memoserv/list", 0, 2) - { - this->SetDesc(_("List your memos")); - this->SetSyntax(_("[\037channel\037] [\037list\037 | NEW]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string param = !params.empty() ? params[0] : "", chan; - ChannelInfo *ci = NULL; - const MemoInfo *mi; - int i, end; - - if (!param.empty() && param[0] == '#') - { - chan = param; - param = params.size() > 1 ? params[1] : ""; - - if (!(ci = cs_findchan(chan))) - { - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - return; - } - else if (!ci->HasPriv(u, CA_MEMO)) - { - source.Reply(ACCESS_DENIED); - return; - } - mi = &ci->memos; - } - else - mi = &u->Account()->memos; - if (!param.empty() && !isdigit(param[0]) && !param.equals_ci("NEW")) - this->OnSyntaxError(source, param); - else if (!mi->memos.size()) - { - if (!chan.empty()) - source.Reply(MEMO_X_HAS_NO_MEMOS, chan.c_str()); - else - source.Reply(MEMO_HAVE_NO_MEMOS); - } - else - { - if (!param.empty() && isdigit(param[0])) - { - MemoListCallback list(source, ci, mi, param); - list.Process(); - } - else - { - if (!param.empty()) - { - for (i = 0, end = mi->memos.size(); i < end; ++i) - if (mi->memos[i]->HasFlag(MF_UNREAD)) - break; - if (i == end) - { - if (!chan.empty()) - source.Reply(MEMO_X_HAS_NO_NEW_MEMOS, chan.c_str()); - else - source.Reply(MEMO_HAVE_NO_NEW_MEMOS); - return; - } - } - - bool SentHeader = false; - - for (i = 0, end = mi->memos.size(); i < end; ++i) - { - if (!param.empty() && !mi->memos[i]->HasFlag(MF_UNREAD)) - continue; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("New memo for %s."), ci ? ci->name.c_str() : u->nick.c_str()); - source.Reply(_(" Num Sender Date/Time")); - } - - MemoListCallback::DoList(source, mi, i); - } - } - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists any memos you currently have. With \002NEW\002, lists only\n" - "new (unread) memos. Unread memos are marked with a \"*\"\n" - "to the left of the memo number. You can also specify a list\n" - "of numbers, as in the example below:\n" - " \002LIST 2-5,7-9\002\n" - " Lists memos numbered 2 through 5 and 7 through 9.")); - return true; - } -}; - -class MSList : public Module -{ - CommandMSList commandmslist; - - public: - MSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmslist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmslist); - } -}; - -MODULE_INIT(MSList) diff --git a/modules/core/ms_main.cpp b/modules/core/ms_main.cpp deleted file mode 100644 index bb6d7847e..000000000 --- a/modules/core/ms_main.cpp +++ /dev/null @@ -1,228 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -static BotInfo *MemoServ; - -static bool SendMemoMail(NickCore *nc, MemoInfo *mi, Memo *m) -{ - Anope::string message = Anope::printf(translate(nc, _( - "Hi %s\n" - " \n" - "You've just received a new memo from %s. This is memo number %d.\n" - " \n" - "Memo text:\n" - " \n" - "%s")), nc->display.c_str(), m->sender.c_str(), mi->GetIndex(m), m->text.c_str()); - - return Mail(nc, translate(nc, _("New memo")), message); -} - -class MyMemoServService : public MemoServService -{ - public: - MyMemoServService(Module *m) : MemoServService(m) { } - - MemoInfo *GetMemoInfo(const Anope::string &target, bool &ischan) - { - if (!target.empty() && target[0] == '#') - { - ischan = true; - ChannelInfo *ci = cs_findchan(target); - if (ci != NULL) - return &ci->memos; - } - else - { - ischan = false; - NickAlias *na = findnick(target); - if (na != NULL) - return &na->nc->memos; - } - - return NULL; - } - - MemoResult Send(const Anope::string &source, const Anope::string &target, const Anope::string &message, bool force) - { - bool ischan; - MemoInfo *mi = this->GetMemoInfo(target, ischan); - - if (mi == NULL) - return MEMO_INVALID_TARGET; - - User *sender = finduser(source); - if (sender != NULL && !sender->HasPriv("memoserv/no-limit") && !force) - { - if (Config->MSSendDelay > 0 && sender->lastmemosend + Config->MSSendDelay > Anope::CurTime) - return MEMO_TOO_FAST; - else if (!mi->memomax) - return MEMO_TARGET_FULL; - else if (mi->memomax > 0 && mi->memos.size() >= mi->memomax) - return MEMO_TARGET_FULL; - else if (mi->HasIgnore(sender)) - return MEMO_SUCCESS; - } - - if (sender != NULL) - sender->lastmemosend = Anope::CurTime; - - Memo *m = new Memo(); - mi->memos.push_back(m); - m->sender = source; - m->time = Anope::CurTime; - m->text = message; - m->SetFlag(MF_UNREAD); - - FOREACH_MOD(I_OnMemoSend, OnMemoSend(source, target, mi, m)); - - if (ischan) - { - ChannelInfo *ci = cs_findchan(target); - - if (ci->c) - { - for (CUserList::iterator it = ci->c->users.begin(), it_end = ci->c->users.end(); it != it_end; ++it) - { - UserContainer *cu = *it; - - if (ci->HasPriv(cu->user, CA_MEMO)) - { - if (cu->user->Account() && cu->user->Account()->HasFlag(NI_MEMO_RECEIVE)) - cu->user->SendMessage(MemoServ, MEMO_NEW_X_MEMO_ARRIVED, ci->name.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->MemoServ.c_str(), ci->name.c_str(), mi->memos.size()); - } - } - } - } - else - { - NickCore *nc = findnick(target)->nc; - - if (nc->HasFlag(NI_MEMO_RECEIVE)) - { - for (std::list<NickAlias *>::iterator it = nc->aliases.begin(), it_end = nc->aliases.end(); it != it_end; ++it) - { - NickAlias *na = *it; - User *user = finduser(na->nick); - if (user && user->IsIdentified()) - user->SendMessage(MemoServ, MEMO_NEW_MEMO_ARRIVED, source.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->MemoServ.c_str(), mi->memos.size()); - } - } - - /* let's get out the mail if set in the nickcore - certus */ - if (nc->HasFlag(NI_MEMO_MAIL)) - SendMemoMail(nc, mi, m); - } - - return MEMO_SUCCESS; - } - - void Check(User *u) - { - NickCore *nc = u->Account(); - if (!nc) - return; - - unsigned i = 0, end = nc->memos.memos.size(), newcnt = 0; - for (; i < end; ++i) - { - if (nc->memos.memos[i]->HasFlag(MF_UNREAD)) - ++newcnt; - } - if (newcnt > 0) - u->SendMessage(MemoServ, newcnt == 1 ? _("You have 1 new memo.") : _("You have %d new memos."), newcnt); - if (nc->memos.memomax > 0 && nc->memos.memos.size() >= nc->memos.memomax) - { - if (nc->memos.memos.size() > nc->memos.memomax) - u->SendMessage(MemoServ, _("You are over your maximum number of memos (%d). You will be unable to receive any new memos until you delete some of your current ones."), nc->memos.memomax); - else - u->SendMessage(MemoServ, _("You have reached your maximum number of memos (%d). You will be unable to receive any new memos until you delete some of your current ones."), nc->memos.memomax); - } - } -}; - -class MemoServCore : public Module -{ - MyMemoServService mymemoserv; - public: - MemoServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - mymemoserv(this) - { - this->SetAuthor("Anope"); - - MemoServ = findbot(Config->MemoServ); - if (MemoServ == NULL) - throw ModuleException("No bot named " + Config->MemoServ); - - Implementation i[] = { I_OnNickIdentify, I_OnJoinChannel, I_OnUserAway, I_OnNickUpdate, I_OnPreHelp, I_OnPostHelp }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&this->mymemoserv); - } - - void OnNickIdentify(User *u) - { - this->mymemoserv.Check(u); - } - - void OnJoinChannel(User *u, Channel *c) - { - if (c->ci && c->ci->HasPriv(u, CA_MEMO) && c->ci->memos.memos.size() > 0) - { - if (c->ci->memos.memos.size() == 1) - u->SendMessage(MemoServ, _("There is \002%d\002 memo on channel %s."), c->ci->memos.memos.size(), c->ci->name.c_str()); - else - u->SendMessage(MemoServ, _("There are \002%d\002 memos on channel %s."), c->ci->memos.memos.size(), c->ci->name.c_str()); - } - } - - void OnUserAway(User *u, const Anope::string &message) - { - if (message.empty()) - this->mymemoserv.Check(u); - } - - void OnNickUpdate(User *u) - { - this->mymemoserv.Check(u); - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->MemoServ) - return; - source.Reply(_("\002%s\002 is a utility allowing IRC users to send short\n" - "messages to other IRC users, whether they are online at\n" - "the time or not, or to channels(*). Both the sender's\n" - "nickname and the target nickname or channel must be\n" - "registered in order to send a memo.\n" - "%s's commands include:"), Config->MemoServ.c_str(), Config->MemoServ.c_str()); - } - - void OnPostHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->MemoServ) - return; - source.Reply(_(" \n" - "Type \002%s%s HELP \037command\037\002 for help on any of the\n" - "above commands.\n" - "(*) By default, any user with at least level 10 access on a\n" - " channel can read that channel's memos. This can be\n" - " changed with the %s \002LEVELS\002 command."), Config->UseStrictPrivMsgString.c_str(), Config->MemoServ.c_str(), Config->ChanServ.c_str()); - } -}; - -MODULE_INIT(MemoServCore) - diff --git a/modules/core/ms_read.cpp b/modules/core/ms_read.cpp deleted file mode 100644 index f275f8d7d..000000000 --- a/modules/core/ms_read.cpp +++ /dev/null @@ -1,195 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -void rsend_notify(CommandSource &source, MemoInfo *mi, Memo *m, const Anope::string &targ) -{ - /* Only send receipt if memos are allowed */ - if (memoserv && !readonly) - { - /* Get nick alias for sender */ - NickAlias *na = findnick(m->sender); - - if (!na) - return; - - /* Get nick core for sender */ - NickCore *nc = na->nc; - - if (!nc) - return; - - /* Text of the memo varies if the recepient was a - nick or channel */ - Anope::string text = Anope::printf(translate(na->nc, _("\002[auto-memo]\002 The memo you sent to %s has been viewed.")), targ.c_str()); - - /* Send notification */ - memoserv->Send(source.u->nick, m->sender, text, true); - - /* Notify recepient of the memo that a notification has - been sent to the sender */ - source.Reply(_("A notification memo has been sent to %s informing him/her you have\n" - "read his/her memo."), nc->display.c_str()); - } - - /* Remove receipt flag from the original memo */ - m->UnsetFlag(MF_RECEIPT); -} - -class MemoListCallback : public NumberList -{ - CommandSource &source; - MemoInfo *mi; - public: - MemoListCallback(CommandSource &_source, MemoInfo *_mi, const Anope::string &numlist) : NumberList(numlist, false), source(_source), mi(_mi) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > mi->memos.size()) - return; - - MemoListCallback::DoRead(source, mi, NULL, Number - 1); - } - - static void DoRead(CommandSource &source, MemoInfo *mi, ChannelInfo *ci, unsigned index) - { - Memo *m = mi->memos[index]; - if (ci) - source.Reply(_("Memo %d from %s (%s). To delete, type: \002%s%s DEL %s %d\002"), index + 1, m->sender.c_str(), do_strftime(m->time).c_str(), Config->UseStrictPrivMsgString.c_str(), Config->MemoServ.c_str(), ci->name.c_str(), index + 1); - else - source.Reply(_("Memo %d from %s (%s). To delete, type: \002%s%s DEL %d\002"), index + 1, m->sender.c_str(), do_strftime(m->time).c_str(), Config->UseStrictPrivMsgString.c_str(), Config->MemoServ.c_str(), index + 1); - source.Reply("%s", m->text.c_str()); - m->UnsetFlag(MF_UNREAD); - - /* Check if a receipt notification was requested */ - if (m->HasFlag(MF_RECEIPT)) - rsend_notify(source, mi, m, ci ? ci->name : source.u->nick); - } -}; - -class CommandMSRead : public Command -{ - public: - CommandMSRead(Module *creator) : Command(creator, "memoserv/read", 1, 2) - { - this->SetDesc(_("Read a memo or memos")); - this->SetSyntax(_("[\037channel\037] {\037num\037 | \037list\037 | LAST | NEW}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - MemoInfo *mi; - ChannelInfo *ci = NULL; - Anope::string numstr = params[0], chan; - - if (!numstr.empty() && numstr[0] == '#') - { - chan = numstr; - numstr = params.size() > 1 ? params[1] : ""; - - if (!(ci = cs_findchan(chan))) - { - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - return; - } - else if (!ci->HasPriv(u, CA_MEMO)) - { - source.Reply(ACCESS_DENIED); - return; - } - mi = &ci->memos; - } - else - mi = &u->Account()->memos; - - if (numstr.empty() || (!numstr.equals_ci("LAST") && !numstr.equals_ci("NEW") && !numstr.is_number_only())) - this->OnSyntaxError(source, numstr); - else if (mi->memos.empty()) - { - if (!chan.empty()) - source.Reply(MEMO_X_HAS_NO_MEMOS, chan.c_str()); - else - source.Reply(MEMO_HAVE_NO_MEMOS); - } - else - { - int i, end; - - if (numstr.equals_ci("NEW")) - { - int readcount = 0; - for (i = 0, end = mi->memos.size(); i < end; ++i) - if (mi->memos[i]->HasFlag(MF_UNREAD)) - { - MemoListCallback::DoRead(source, mi, ci, i); - ++readcount; - } - if (!readcount) - { - if (!chan.empty()) - source.Reply(MEMO_X_HAS_NO_NEW_MEMOS, chan.c_str()); - else - source.Reply(MEMO_HAVE_NO_NEW_MEMOS); - } - } - else if (numstr.equals_ci("LAST")) - { - for (i = 0, end = mi->memos.size() - 1; i < end; ++i); - MemoListCallback::DoRead(source, mi, ci, i); - } - else /* number[s] */ - { - MemoListCallback list(source, mi, numstr); - list.Process(); - } - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sends you the text of the memos specified. If LAST is\n" - "given, sends you the memo you most recently received. If\n" - "NEW is given, sends you all of your new memos. Otherwise,\n" - "sends you memo number \037num\037. You can also give a list of\n" - "numbers, as in this example:\n" - " \n" - " \002READ 2-5,7-9\002\n" - " Displays memos numbered 2 through 5 and 7 through 9.")); - return true; - } -}; - -class MSRead : public Module -{ - CommandMSRead commandmsread; - - public: - MSRead(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsread(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmsread); - } -}; - -MODULE_INIT(MSRead) diff --git a/modules/core/ms_rsend.cpp b/modules/core/ms_rsend.cpp deleted file mode 100644 index 37c633e02..000000000 --- a/modules/core/ms_rsend.cpp +++ /dev/null @@ -1,106 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -class CommandMSRSend : public Command -{ - public: - CommandMSRSend(Module *creator) : Command(creator, "memoserv/rsend", 2, 2) - { - this->SetDesc(_("Sends a memo and requests a read receipt")); - this->SetSyntax(_("{\037nick\037 | \037channel\037} \037memo-text\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params[0]; - const Anope::string &text = params[1]; - NickAlias *na = NULL; - - /* prevent user from rsend to themselves */ - if ((na = findnick(nick)) && na->nc == u->Account()) - { - source.Reply(_("You can not request a receipt when sending a memo to yourself.")); - return; - } - - if (Config->MSMemoReceipt == 1 && !u->IsServicesOper()) - source.Reply(ACCESS_DENIED); - else if (Config->MSMemoReceipt > 2 || Config->MSMemoReceipt == 0) - { - Log() << "MSMemoReceipt is set misconfigured to " << Config->MSMemoReceipt; - source.Reply(_("Sorry, RSEND has been disabled on this network.")); - } - else - { - MemoServService::MemoResult result = memoserv->Send(u->nick, nick, text); - if (result == MemoServService::MEMO_INVALID_TARGET) - source.Reply(_("\002%s\002 is not a registered unforbidden nick or channel."), nick.c_str()); - else if (result == MemoServService::MEMO_TOO_FAST) - source.Reply(_("Please wait %d seconds before using the SEND command again."), Config->MSSendDelay); - else if (result == MemoServService::MEMO_TARGET_FULL) - source.Reply(_("%s currently has too many memos and cannot receive more."), nick.c_str()); - else - { - source.Reply(_("Memo sent to \002%s\002."), name.c_str()); - - bool ischan; - MemoInfo *mi = memoserv->GetMemoInfo(nick, ischan); - if (mi == NULL) - throw CoreException("NULL mi in ms_rsend"); - Memo *m = (mi->memos.size() ? mi->memos[mi->memos.size() - 1] : NULL); - if (m != NULL) - m->SetFlag(MF_RECEIPT); - } - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sends the named \037nick\037 or \037channel\037 a memo containing\n" - "\037memo-text\037. When sending to a nickname, the recipient will\n" - "receive a notice that he/she has a new memo. The target\n" - "nickname/channel must be registered.\n" - "Once the memo is read by its recipient, an automatic notification\n" - "memo will be sent to the sender informing him/her that the memo\n" - "has been read.")); - return true; - } -}; - -class MSRSend : public Module -{ - CommandMSRSend commandmsrsend; - - public: - MSRSend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsrsend(this) - { - this->SetAuthor("Anope"); - - if (!Config->MSMemoReceipt) - throw ModuleException("Invalid value for memoreceipt"); - - ModuleManager::RegisterService(&commandmsrsend); - } -}; - -MODULE_INIT(MSRSend) diff --git a/modules/core/ms_send.cpp b/modules/core/ms_send.cpp deleted file mode 100644 index 9397e7ad7..000000000 --- a/modules/core/ms_send.cpp +++ /dev/null @@ -1,70 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -class CommandMSSend : public Command -{ - public: - CommandMSSend(Module *creator) : Command(creator, "memoserv/send", 2, 2) - { - this->SetDesc(_("Send a memo to a nick or channel")); - this->SetSyntax(_("{\037nick\037 | \037channel\037} \037memo-text\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params[0]; - const Anope::string &text = params[1]; - - MemoServService::MemoResult result = memoserv->Send(source.u->nick, nick, text); - if (result == MemoServService::MEMO_SUCCESS) - source.Reply(_("Memo sent to \002%s\002."), nick.c_str()); - else if (result == MemoServService::MEMO_INVALID_TARGET) - source.Reply(_("\002%s\002 is not a registered unforbidden nick or channel."), nick.c_str()); - else if (result == MemoServService::MEMO_TOO_FAST) - source.Reply(_("Please wait %d seconds before using the SEND command again."), Config->MSSendDelay); - else if (result == MemoServService::MEMO_TARGET_FULL) - source.Reply(_("%s currently has too many memos and cannot receive more."), nick.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sends the named \037nick\037 or \037channel\037 a memo containing\n" - "\037memo-text\037. When sending to a nickname, the recipient will\n" - "receive a notice that he/she has a new memo. The target\n" - "nickname/channel must be registered.")); - return true; - } -}; - -class MSSend : public Module -{ - CommandMSSend commandmssend; - - public: - MSSend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmssend(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmssend); - } -}; - -MODULE_INIT(MSSend) diff --git a/modules/core/ms_sendall.cpp b/modules/core/ms_sendall.cpp deleted file mode 100644 index 7af5ac7af..000000000 --- a/modules/core/ms_sendall.cpp +++ /dev/null @@ -1,74 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -class CommandMSSendAll : public Command -{ - public: - CommandMSSendAll(Module *creator) : Command(creator, "memoserv/sendall", 1, 1) - { - this->SetDesc(_("Send a memo to all registered users")); - this->SetSyntax(_("\037memo-text\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &text = params[0]; - - if (readonly) - { - source.Reply(MEMO_SEND_DISABLED); - return; - } - - NickAlias *na = findnick(u->nick); - - for (nickcore_map::const_iterator it = NickCoreList.begin(), it_end = NickCoreList.end(); it != it_end; ++it) - { - NickCore *nc = it->second; - - if ((na && na->nc == nc) || !nc->display.equals_ci(u->nick)) - memoserv->Send(u->nick, nc->display, text); - } - - source.Reply(_("A massmemo has been sent to all registered users.")); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sends all registered users a memo containing \037memo-text\037.")); - return true; - } -}; - -class MSSendAll : public Module -{ - CommandMSSendAll commandmssendall; - - public: - MSSendAll(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmssendall(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmssendall); - } -}; - -MODULE_INIT(MSSendAll) diff --git a/modules/core/ms_set.cpp b/modules/core/ms_set.cpp deleted file mode 100644 index 1aa3f469d..000000000 --- a/modules/core/ms_set.cpp +++ /dev/null @@ -1,313 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandMSSet : public Command -{ - private: - void DoNotify(CommandSource &source, const std::vector<Anope::string> ¶ms, MemoInfo *mi) - { - User *u = source.u; - const Anope::string ¶m = params[1]; - - if (param.equals_ci("ON")) - { - u->Account()->SetFlag(NI_MEMO_SIGNON); - u->Account()->SetFlag(NI_MEMO_RECEIVE); - source.Reply(_("%s will now notify you of memos when you log on and when they are sent to you."), Config->MemoServ.c_str()); - } - else if (param.equals_ci("LOGON")) - { - u->Account()->SetFlag(NI_MEMO_SIGNON); - u->Account()->UnsetFlag(NI_MEMO_RECEIVE); - source.Reply(_("%s will now notify you of memos when you log on or unset /AWAY."), Config->MemoServ.c_str()); - } - else if (param.equals_ci("NEW")) - { - u->Account()->UnsetFlag(NI_MEMO_SIGNON); - u->Account()->SetFlag(NI_MEMO_RECEIVE); - source.Reply(_("%s will now notify you of memos when they are sent to you."), Config->MemoServ.c_str()); - } - else if (param.equals_ci("MAIL")) - { - if (!u->Account()->email.empty()) - { - u->Account()->SetFlag(NI_MEMO_MAIL); - source.Reply(_("You will now be informed about new memos via email.")); - } - else - source.Reply(_("There's no email address set for your nick.")); - } - else if (param.equals_ci("NOMAIL")) - { - u->Account()->UnsetFlag(NI_MEMO_MAIL); - source.Reply(_("You will no longer be informed via email.")); - } - else if (param.equals_ci("OFF")) - { - u->Account()->UnsetFlag(NI_MEMO_SIGNON); - u->Account()->UnsetFlag(NI_MEMO_RECEIVE); - u->Account()->UnsetFlag(NI_MEMO_MAIL); - source.Reply(_("%s will not send you any notification of memos."), Config->MemoServ.c_str()); - } - else - this->OnSyntaxError(source, param); - - return; - } - - void DoLimit(CommandSource &source, const std::vector<Anope::string> ¶ms, MemoInfo *mi) - { - User *u = source.u; - - Anope::string p1 = params[1]; - Anope::string p2 = params.size() > 2 ? params[2] : ""; - Anope::string p3 = params.size() > 3 ? params[3] : ""; - Anope::string user, chan; - int16 limit; - NickCore *nc = u->Account(); - ChannelInfo *ci = NULL; - bool is_servadmin = u->HasPriv("memoserv/set-limit"); - - if (p1[0] == '#') - { - chan = p1; - p1 = p2; - p2 = p3; - p3 = params.size() > 4 ? params[4] : ""; - if (!(ci = cs_findchan(chan))) - { - source.Reply(CHAN_X_NOT_REGISTERED, chan.c_str()); - return; - } - else if (!is_servadmin && !ci->HasPriv(u, CA_MEMO)) - { - source.Reply(ACCESS_DENIED); - return; - } - mi = &ci->memos; - } - if (is_servadmin) - { - if (!p2.empty() && !p2.equals_ci("HARD") && chan.empty()) - { - NickAlias *na; - if (!(na = findnick(p1))) - { - source.Reply(NICK_X_NOT_REGISTERED, p1.c_str()); - return; - } - user = p1; - mi = &na->nc->memos; - nc = na->nc; - p1 = p2; - p2 = p3; - } - else if (p1.empty() || (!p1.is_pos_number_only() && !p1.equals_ci("NONE")) || (!p2.empty() && !p2.equals_ci("HARD"))) - { - this->OnSyntaxError(source, ""); - return; - } - if (!chan.empty()) - { - if (!p2.empty()) - ci->SetFlag(CI_MEMO_HARDMAX); - else - ci->UnsetFlag(CI_MEMO_HARDMAX); - } - else - { - if (!p2.empty()) - nc->SetFlag(NI_MEMO_HARDMAX); - else - nc->UnsetFlag(NI_MEMO_HARDMAX); - } - limit = -1; - try - { - limit = convertTo<int16>(p1); - } - catch (const ConvertException &) { } - } - else - { - if (p1.empty() || !p2.empty() || !isdigit(p1[0])) - { - this->OnSyntaxError(source, ""); - return; - } - if (!chan.empty() && ci->HasFlag(CI_MEMO_HARDMAX)) - { - source.Reply(_("The memo limit for %s may not be changed."), chan.c_str()); - return; - } - else if (chan.empty() && nc->HasFlag(NI_MEMO_HARDMAX)) - { - source.Reply(_("You are not permitted to change your memo limit.")); - return; - } - limit = -1; - try - { - limit = convertTo<int16>(p1); - } - catch (const ConvertException &) { } - /* The first character is a digit, but we could still go negative - * from overflow... watch out! */ - if (limit < 0 || (Config->MSMaxMemos > 0 && static_cast<unsigned>(limit) > Config->MSMaxMemos)) - { - if (!chan.empty()) - source.Reply(_("You cannot set the memo limit for %s higher than %d."), chan.c_str(), Config->MSMaxMemos); - else - source.Reply(_("You cannot set your memo limit higher than %d."), Config->MSMaxMemos); - return; - } - } - mi->memomax = limit; - if (limit > 0) - { - if (chan.empty() && nc == u->Account()) - source.Reply(_("Your memo limit has been set to \002%d\002."), limit); - else - source.Reply(_("Memo limit for %s set to \002%d\002."), !chan.empty() ? chan.c_str() : user.c_str(), limit); - } - else if (!limit) - { - if (chan.empty() && nc == u->Account()) - source.Reply(_("You will no longer be able to receive memos.")); - else - source.Reply(_("Memo limit for %s set to \0020\002."), !chan.empty() ? chan.c_str() : user.c_str()); - } - else - { - if (chan.empty() && nc == u->Account()) - source.Reply(_("Your memo limit has been disabled.")); - else - source.Reply(_("Memo limit \002disabled\002 for %s."), !chan.empty() ? chan.c_str() : user.c_str()); - } - return; - } - public: - CommandMSSet(Module *creator) : Command(creator, "memoserv/set", 2, 5) - { - this->SetDesc(_("Set options related to memos")); - this->SetSyntax(_("\037option\037 \037parameters\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &cmd = params[0]; - MemoInfo *mi = &u->Account()->memos; - - if (readonly) - source.Reply(_("Sorry, memo option setting is temporarily disabled.")); - else if (cmd.equals_ci("NOTIFY")) - return this->DoNotify(source, params, mi); - else if (cmd.equals_ci("LIMIT")) - return this->DoLimit(source, params, mi); - else - { - source.Reply(NICK_SET_UNKNOWN_OPTION, Config->UseStrictPrivMsgString.c_str(), cmd.c_str()); - source.Reply(MORE_INFO, Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), "SET"); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - if (subcommand.empty()) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets various memo options. \037option\037 can be one of:\n" - " \n" - " NOTIFY Changes when you will be notified about\n" - " new memos (only for nicknames)\n" - " LIMIT Sets the maximum number of memos you can\n" - " receive\n" - " \n" - "Type \002%s%s HELP %s \037option\037\002 for more information\n" - "on a specific option."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), source.command.c_str()); - } - else if (subcommand.equals_ci("NOTIFY")) - source.Reply(_("Syntax: \002NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\002\n" - "Changes when you will be notified about new memos:\n" - " \n" - " ON You will be notified of memos when you log on,\n" - " when you unset /AWAY, and when they are sent\n" - " to you.\n" - " LOGON You will only be notified of memos when you log\n" - " on or when you unset /AWAY.\n" - " NEW You will only be notified of memos when they\n" - " are sent to you.\n" - " MAIL You will be notified of memos by email aswell as\n" - " any other settings you have.\n" - " NOMAIL You will not be notified of memos by email.\n" - " OFF You will not receive any notification of memos.\n" - " \n" - "\002ON\002 is essentially \002LOGON\002 and \002NEW\002 combined.")); - else if (subcommand.equals_ci("LIMIT")) - { - User *u = source.u; - if (u->IsServicesOper()) - source.Reply(_("Syntax: \002LIMIT [\037user\037 | \037channel\037] {\037limit\037 | NONE} [HARD]\002\n" - " \n" - "Sets the maximum number of memos a user or channel is\n" - "allowed to have. Setting the limit to 0 prevents the user\n" - "from receiving any memos; setting it to \002NONE\002 allows the\n" - "user to receive and keep as many memos as they want. If\n" - "you do not give a nickname or channel, your own limit is\n" - "set.\n" - " \n" - "Adding \002HARD\002 prevents the user from changing the limit. Not\n" - "adding \002HARD\002 has the opposite effect, allowing the user to\n" - "change the limit (even if a previous limit was set with\n" - "\002HARD\002).\n" - "This use of the \002SET LIMIT\002 command is limited to \002Services\002\n" - "\002admins\002. Other users may only enter a limit for themselves\n" - "or a channel on which they have such privileges, may not\n" - "remove their limit, may not set a limit above %d, and may\n" - "not set a hard limit."), Config->MSMaxMemos); - else - source.Reply(_("Syntax: \002LIMIT [\037channel\037] \037limit\037\002\n" - " \n" - "Sets the maximum number of memos you (or the given channel)\n" - "are allowed to have. If you set this to 0, no one will be\n" - "able to send any memos to you. However, you cannot set\n" - "this any higher than %d."), Config->MSMaxMemos); - } - else - return false; - - return true; - } -}; - -class MSSet : public Module -{ - CommandMSSet commandmsset; - - public: - MSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsset(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmsset); - } -}; - -MODULE_INIT(MSSet) diff --git a/modules/core/ms_staff.cpp b/modules/core/ms_staff.cpp deleted file mode 100644 index 6264dbea4..000000000 --- a/modules/core/ms_staff.cpp +++ /dev/null @@ -1,71 +0,0 @@ -/* MemoServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "memoserv.h" - -class CommandMSStaff : public Command -{ - public: - CommandMSStaff(Module *creator) : Command(creator, "memoserv/staff", 1, 1) - { - this->SetDesc(_("Send a memo to all opers/admins")); - this->SetSyntax(_("\037memo-text\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &text = params[0]; - - if (readonly) - { - source.Reply(MEMO_SEND_DISABLED); - return; - } - - for (nickcore_map::const_iterator it = NickCoreList.begin(), it_end = NickCoreList.end(); it != it_end; ++it) - { - NickCore *nc = it->second; - - if (nc->IsServicesOper()) - memoserv->Send(source.u->nick, nc->display, text, true); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sends all services staff a memo containing \037memo-text\037.")); - - return true; - } -}; - -class MSStaff : public Module -{ - CommandMSStaff commandmsstaff; - - public: - MSStaff(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandmsstaff(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandmsstaff); - } -}; - -MODULE_INIT(MSStaff) diff --git a/modules/core/nickserv.h b/modules/core/nickserv.h deleted file mode 100644 index b58dbd65f..000000000 --- a/modules/core/nickserv.h +++ /dev/null @@ -1,15 +0,0 @@ -#ifndef NICKSERV_H -#define NICKSERV_H - -class NickServService : public Service -{ - public: - NickServService(Module *m) : Service(m, "NickServ") { } - - virtual void Validate(User *u) = 0; -}; - -static service_reference<NickServService> nickserv("NickServ"); - -#endif // NICKSERV_H - diff --git a/modules/core/ns_access.cpp b/modules/core/ns_access.cpp deleted file mode 100644 index df9ae6eed..000000000 --- a/modules/core/ns_access.cpp +++ /dev/null @@ -1,195 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSAccess : public Command -{ - private: - void DoServAdminList(CommandSource &source, const std::vector<Anope::string> ¶ms, NickCore *nc) - { - Anope::string mask = params.size() > 2 ? params[2] : ""; - unsigned i, end; - - if (nc->access.empty()) - { - source.Reply(_("Access list for \002%s\002 is empty."), nc->display.c_str()); - return; - } - - if (nc->HasFlag(NI_SUSPENDED)) - { - source.Reply(NICK_X_SUSPENDED, nc->display.c_str()); - return; - } - - source.Reply(_("Access list for \002%s\002:"), params[1].c_str()); - for (i = 0, end = nc->access.size(); i < end; ++i) - { - Anope::string access = nc->GetAccess(i); - if (!mask.empty() && !Anope::Match(access, mask)) - continue; - source.Reply(" %s", access.c_str()); - } - - return; - } - - void DoAdd(CommandSource &source, NickCore *nc, const Anope::string &mask) - { - - if (mask.empty()) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - if (nc->access.size() >= Config->NSAccessMax) - { - source.Reply(_("Sorry, you can only have %d access entries for a nickname."), Config->NSAccessMax); - return; - } - - if (nc->FindAccess(mask)) - { - source.Reply(_("Mask \002%s\002 already present on your access list."), mask.c_str()); - return; - } - - nc->AddAccess(mask); - source.Reply(_("\002%s\002 added to your access list."), mask.c_str()); - - return; - } - - void DoDel(CommandSource &source, NickCore *nc, const Anope::string &mask) - { - if (mask.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (!nc->FindAccess(mask)) - { - source.Reply(_("\002%s\002 not found on your access list."), mask.c_str()); - return; - } - - source.Reply(_("\002%s\002 deleted from your access list."), mask.c_str()); - nc->EraseAccess(mask); - - return; - } - - void DoList(CommandSource &source, NickCore *nc, const Anope::string &mask) - { - User *u = source.u; - unsigned i, end; - - if (nc->access.empty()) - { - source.Reply(_("Your access list is empty."), u->nick.c_str()); - return; - } - - source.Reply(_("Access list:")); - for (i = 0, end = nc->access.size(); i < end; ++i) - { - Anope::string access = nc->GetAccess(i); - if (!mask.empty() && !Anope::Match(access, mask)) - continue; - source.Reply(" %s", access.c_str()); - } - - return; - } - public: - CommandNSAccess(Module *creator) : Command(creator, "nickserv/access", 1, 3) - { - this->SetDesc(_("Modify the list of authorized addresses")); - this->SetSyntax(_("ADD \037mask\037")); - this->SetSyntax(_("DEL \037mask\037")); - this->SetSyntax(_("LIST")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &cmd = params[0]; - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - NickAlias *na; - if (cmd.equals_ci("LIST") && u->IsServicesOper() && !mask.empty() && (na = findnick(params[1]))) - return this->DoServAdminList(source, params, na->nc); - - if (!mask.empty() && mask.find('@') == Anope::string::npos) - { - source.Reply(BAD_USERHOST_MASK); - source.Reply(MORE_INFO, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), this->name.c_str()); - } - else if (u->Account()->HasFlag(NI_SUSPENDED)) - source.Reply(NICK_X_SUSPENDED, u->Account()->display.c_str()); - else if (cmd.equals_ci("ADD")) - return this->DoAdd(source, u->Account(), mask); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, u->Account(), mask); - else if (cmd.equals_ci("LIST")) - return this->DoList(source, u->Account(), mask); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Modifies or displays the access list for your nick. This\n" - "is the list of addresses which will be automatically\n" - "recognized by %s as allowed to use the nick. If\n" - "you want to use the nick from a different address, you\n" - "need to send an \002IDENTIFY\002 command to make %s\n" - "recognize you.\n" - " \n" - "Examples:\n" - " \n" - " \002ACCESS ADD anyone@*.bepeg.com\002\n" - " Allows access to user \002anyone\002 from any machine in\n" - " the \002bepeg.com\002 domain.\n" - " \n" - " \002ACCESS DEL anyone@*.bepeg.com\002\n" - " Reverses the previous command.\n" - " \n" - " \002ACCESS LIST\002\n" - " Displays the current access list."), Config->NickServ.c_str(), Config->NickServ.c_str()); - return true; - } -}; - -class NSAccess : public Module -{ - CommandNSAccess commandnsaccess; - - public: - NSAccess(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsaccess(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsaccess); - } -}; - -MODULE_INIT(NSAccess) diff --git a/modules/core/ns_ajoin.cpp b/modules/core/ns_ajoin.cpp deleted file mode 100644 index 4f35f28b8..000000000 --- a/modules/core/ns_ajoin.cpp +++ /dev/null @@ -1,239 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSAJoin : public Command -{ - void DoList(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - std::vector<std::pair<Anope::string, Anope::string> > channels; - source.u->Account()->GetExtRegular("ns_ajoin_channels", channels); - - if (channels.empty()) - source.Reply(_("Your auto join list is empty.")); - else - { - source.Reply(_("Your auto join list:\n" - " Num Channel Key")); - for (unsigned i = 0; i < channels.size(); ++i) - source.Reply(" %3d %-12s %s", i + 1, channels[i].first.c_str(), channels[i].second.c_str()); - } - } - - void DoAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - std::vector<std::pair<Anope::string, Anope::string> > channels; - source.u->Account()->GetExtRegular("ns_ajoin_channels", channels); - - if (channels.size() >= Config->AJoinMax) - source.Reply(_("Your auto join list is full.")); - else if (ircdproto->IsChannelValid(params[1]) == false) - source.Reply(CHAN_X_INVALID, params[1].c_str()); - else - { - channels.push_back(std::make_pair(params[1], params.size() > 2 ? params[2] : "")); - source.Reply(_("Added %s to your auto join list."), params[1].c_str()); - source.u->Account()->Extend("ns_ajoin_channels", new ExtensibleItemRegular<std::vector< - std::pair<Anope::string, Anope::string> > >(channels)); - } - } - - void DoDel(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - std::vector<std::pair<Anope::string, Anope::string> > channels; - source.u->Account()->GetExtRegular("ns_ajoin_channels", channels); - - unsigned i; - for (i = 0; i < channels.size(); ++i) - if (channels[i].first.equals_ci(params[1])) - break; - - if (i == channels.size()) - source.Reply(_("%s was not found on your auto join list."), params[1].c_str()); - else - { - channels.erase(channels.begin() + i); - source.u->Account()->Extend("ns_ajoin_channels", new ExtensibleItemRegular<std::vector< - std::pair<Anope::string, Anope::string> > >(channels)); - source.Reply(_("%s was removed from your auto join list."), params[1].c_str()); - } - } - - public: - CommandNSAJoin(Module *creator) : Command(creator, "nickserv/ajoin", 1, 3) - { - this->SetDesc(_("Manage your auto join list")); - this->SetSyntax(_("{ADD | DEL | LIST} [\037channel\037] [\037key\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (params[0].equals_ci("LIST")) - this->DoList(source, params); - else if (params.size() < 2) - this->OnSyntaxError(source, ""); - else if (params[0].equals_ci("ADD")) - this->DoAdd(source, params); - else if (params[0].equals_ci("DEL")) - this->DoDel(source, params); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command manages your auto join list. When you identify\n" - "you will automatically join the channels on your auto join list")); - return true; - } -}; - -class NSAJoin : public Module -{ - CommandNSAJoin commandnsajoin; - - public: - NSAJoin(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsajoin(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsajoin); - - Implementation i[] = { I_OnNickIdentify, I_OnDatabaseWriteMetadata, I_OnDatabaseReadMetadata }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - } - - void OnNickIdentify(User *u) - { - std::vector<std::pair<Anope::string, Anope::string> > channels; - u->Account()->GetExtRegular("ns_ajoin_channels", channels); - - for (unsigned i = 0; i < channels.size(); ++i) - { - Channel *c = findchan(channels[i].first); - ChannelInfo *ci = c != NULL ? c->ci : cs_findchan(channels[i].first); - if (c == NULL && ci != NULL) - c = ci->c; - - bool need_invite = false; - Anope::string key = channels[i].second; - - if (ci != NULL) - { - if (ci->HasFlag(CI_SUSPENDED)) - continue; - } - if (c != NULL) - { - if (c->FindUser(u) != NULL) - continue; - else if (c->HasMode(CMODE_OPERONLY) && !u->HasMode(UMODE_OPER)) - continue; - else if (c->HasMode(CMODE_ADMINONLY) && !u->HasMode(UMODE_ADMIN)) - continue; - else if (c->HasMode(CMODE_SSL) && !u->HasMode(UMODE_SSL)) - continue; - else if (matches_list(c, u, CMODE_BAN) == true && matches_list(c, u, CMODE_EXCEPT) == false) - need_invite = true; - else if (c->HasMode(CMODE_INVITE) && matches_list(c, u, CMODE_INVITEOVERRIDE) == false) - need_invite = true; - - if (c->HasMode(CMODE_KEY)) - { - Anope::string k; - if (c->GetParam(CMODE_KEY, k)) - { - if (ci->HasPriv(u, CA_GETKEY)) - key = k; - else if (key != k) - need_invite = true; - } - } - if (c->HasMode(CMODE_LIMIT)) - { - Anope::string l; - if (c->GetParam(CMODE_LIMIT, l)) - { - try - { - unsigned limit = convertTo<unsigned>(l); - if (c->users.size() >= limit) - need_invite = true; - } - catch (const ConvertException &) { } - } - } - } - - if (need_invite) - { - BotInfo *bi = findbot(Config->NickServ); - if (!bi || !ci->HasPriv(u, CA_INVITE)) - continue; - ircdproto->SendInvite(bi, channels[i].first, u->nick); - } - - ircdproto->SendSVSJoin(Config->NickServ, u->nick, channels[i].first, key); - } - } - - void OnDatabaseWriteMetadata(void (*WriteMetadata)(const Anope::string &, const Anope::string &), NickCore *nc) - { - std::vector<std::pair<Anope::string, Anope::string> > channels; - nc->GetExtRegular("ns_ajoin_channels", channels); - - Anope::string chans; - for (unsigned i = 0; i < channels.size(); ++i) - chans += " " + channels[i].first + "," + channels[i].second; - - if (!chans.empty()) - { - chans.erase(chans.begin()); - WriteMetadata("NS_AJOIN", chans); - } - } - - EventReturn OnDatabaseReadMetadata(NickCore *nc, const Anope::string &key, const std::vector<Anope::string> ¶ms) - { - if (key == "NS_AJOIN") - { - std::vector<std::pair<Anope::string, Anope::string> > channels; - nc->GetExtRegular("ns_ajoin_channels", channels); - - for (unsigned i = 0; i < params.size(); ++i) - { - Anope::string chan, chankey; - commasepstream sep(params[i]); - sep.GetToken(chan); - sep.GetToken(chankey); - - channels.push_back(std::make_pair(chan, chankey)); - } - - nc->Extend("ns_ajoin_channels", new ExtensibleItemRegular<std::vector< - std::pair<Anope::string, Anope::string> > >(channels)); - - return EVENT_STOP; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(NSAJoin) diff --git a/modules/core/ns_alist.cpp b/modules/core/ns_alist.cpp deleted file mode 100644 index f502b4344..000000000 --- a/modules/core/ns_alist.cpp +++ /dev/null @@ -1,96 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSAList : public Command -{ - public: - CommandNSAList(Module *creator) : Command(creator, "nickserv/alist", 0, 2) - { - this->SetDesc(_("List channels you have access on")); - this->SetSyntax(_("[\037nickname\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - Anope::string nick = u->Account()->display; - - if (params.size() && u->IsServicesOper()) - nick = params[0]; - - NickAlias *na = findnick(nick); - - if (!na) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else - { - int chan_count = 0; - - source.Reply(_("Channels that \002%s\002 has access on:\n" - " Num Channel Level"), na->nick.c_str()); - - for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ++it) - { - ChannelInfo *ci = it->second; - - AccessGroup access = ci->AccessFor(na->nc); - if (access.empty()) - continue; - - ++chan_count; - - if (access.size() > 1) - { - source.Reply(_(" %3d You match %d access entries on %c%s, they are"), chan_count, access.size(), ci->HasFlag(CI_NO_EXPIRE) ? '!' : ' ', ci->name.c_str()); - for (unsigned i = 0; i < access.size(); ++i) - source.Reply(_(" %3d %-8s"), i + 1, access[i]->Serialize().c_str()); - } - else - source.Reply(_(" %3d %c%-20s %-8s"), chan_count, ci->HasFlag(CI_NO_EXPIRE) ? '!' : ' ', ci->name.c_str(), access[0]->Serialize().c_str()); - } - - source.Reply(_("End of list - %d channels shown."), chan_count); - } - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all channels you have access on.\n" - " \n" - "Channels that have the \037NOEXPIRE\037 option set will be\n" - "prefixed by an exclamation mark. The nickname parameter is\n" - "limited to Services Operators")); - - return true; - } -}; - -class NSAList : public Module -{ - CommandNSAList commandnsalist; - - public: - NSAList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsalist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsalist); - } -}; - -MODULE_INIT(NSAList) diff --git a/modules/core/ns_cert.cpp b/modules/core/ns_cert.cpp deleted file mode 100644 index fbd75d597..000000000 --- a/modules/core/ns_cert.cpp +++ /dev/null @@ -1,231 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSCert : public Command -{ - private: - void DoServAdminList(CommandSource &source, NickCore *nc) - { - if (nc->cert.empty()) - { - source.Reply(_("Certificate list for \002%s\002 is empty."), nc->display.c_str()); - return; - } - - if (nc->HasFlag(NI_SUSPENDED)) - { - source.Reply(NICK_X_SUSPENDED, nc->display.c_str()); - return; - } - - source.Reply(_("Certificate list for \002%s\002:"), nc->display.c_str()); - for (unsigned i = 0, end = nc->cert.size(); i < end; ++i) - { - Anope::string fingerprint = nc->GetCert(i); - source.Reply(" %s", fingerprint.c_str()); - } - - return; - } - - void DoAdd(CommandSource &source, NickCore *nc, const Anope::string &mask) - { - - if (nc->cert.size() >= Config->NSAccessMax) - { - source.Reply(_("Sorry, you can only have %d certificate entries for a nickname."), Config->NSAccessMax); - return; - } - - if (!source.u->fingerprint.empty() && !nc->FindCert(source.u->fingerprint)) - { - nc->AddCert(source.u->fingerprint); - source.Reply(_("\002%s\002 added to your certificate list."), source.u->fingerprint.c_str()); - return; - } - - if (mask.empty()) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - if (nc->FindCert(mask)) - { - source.Reply(_("Fingerprint \002%s\002 already present on your certificate list."), mask.c_str()); - return; - } - - nc->AddCert(mask); - source.Reply(_("\002%s\002 added to your certificate list."), mask.c_str()); - return; - } - - void DoDel(CommandSource &source, NickCore *nc, const Anope::string &mask) - { - - if (!source.u->fingerprint.empty() && nc->FindCert(source.u->fingerprint)) - { - nc->EraseCert(source.u->fingerprint); - source.Reply(_("\002%s\002 deleted from your certificate list."), source.u->fingerprint.c_str()); - return; - } - - if (mask.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (!nc->FindCert(mask)) - { - source.Reply(_("\002%s\002 not found on your certificate list."), mask.c_str()); - return; - } - - source.Reply(_("\002%s\002 deleted from your certificate list."), mask.c_str()); - nc->EraseCert(mask); - - return; - } - - void DoList(CommandSource &source, NickCore *nc) - { - User *u = source.u; - - if (nc->cert.empty()) - { - source.Reply(_("Your certificate list is empty."), u->nick.c_str()); - return; - } - - source.Reply(_("Cert list:")); - for (unsigned i = 0, end = nc->cert.size(); i < end; ++i) - { - Anope::string fingerprint = nc->GetCert(i); - source.Reply(" %s", fingerprint.c_str()); - } - - return; - } - - public: - CommandNSCert(Module *creator) : Command(creator, "nickserv/cert", 1, 2) - { - this->SetDesc("Modify the nickname client certificate list"); - this->SetSyntax("ADD \037fingerprint\037"); - this->SetSyntax("DEL \037fingerprint\037"); - this->SetSyntax("LIST"); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &cmd = params[0]; - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - NickAlias *na; - if (cmd.equals_ci("LIST") && u->IsServicesOper() && !mask.empty() && (na = findnick(mask))) - return this->DoServAdminList(source, na->nc); - - if (u->Account()->HasFlag(NI_SUSPENDED)) - source.Reply(NICK_X_SUSPENDED, u->Account()->display.c_str()); - else if (cmd.equals_ci("ADD")) - return this->DoAdd(source, u->Account(), mask); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, u->Account(), mask); - else if (cmd.equals_ci("LIST")) - return this->DoList(source, u->Account()); - else - this->OnSyntaxError(source, cmd); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Modifies or displays the certificate list for your nick.\n" - "If you connect to IRC and provide a client certificate with a\n" - "matching fingerprint in the cert list, your nick will be\n" - "automatically identified to %s.\n" - " \n"), Config->NickServ.c_str(), Config->NickServ.c_str()); - source.Reply(_("Examples:\n" - " \n" - " \002CERT ADD <fingerprint>\002\n" - " Adds this fingerprint to the certificate list and\n" - " automatically identifies you when you connect to IRC\n" - " using this certificate.\n" - " \n" - " \002CERT DEL <fingerprint>\002\n" - " Reverses the previous command.\n" - " \n" - " \002CERT LIST\002\n" - " Displays the current certificate list."), Config->NickServ.c_str()); - return true; - } -}; - -class NSCert : public Module -{ - CommandNSCert commandnscert; - - void DoAutoIdentify(User *u) - { - BotInfo *bi = findbot(Config->NickServ); - NickAlias *na = findnick(u->nick); - if (!bi || !na) - return; - if (u->IsIdentified() && u->Account() == na->nc) - return; - if (na->nc->HasFlag(NI_SUSPENDED)) - return; - if (!na->nc->FindCert(u->fingerprint)) - return; - - u->Identify(na); - u->SendMessage(bi, _("SSL Fingerprint accepted. You are now identified.")); - return; - } - - public: - NSCert(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnscert(this) - { - this->SetAuthor("Anope"); - - if (!ircd || !ircd->certfp) - throw ModuleException("Your IRCd does not support ssl client certificates"); - - Implementation i[] = { I_OnUserNickChange, I_OnFingerprint }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&commandnscert); - } - - void OnFingerprint(User *u) - { - DoAutoIdentify(u); - } - - void OnUserNickChange(User *u, const Anope::string &oldnick) - { - if (!u->fingerprint.empty()) - DoAutoIdentify(u); - } -}; - -MODULE_INIT(NSCert) diff --git a/modules/core/ns_drop.cpp b/modules/core/ns_drop.cpp deleted file mode 100644 index 7960652ff..000000000 --- a/modules/core/ns_drop.cpp +++ /dev/null @@ -1,130 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSDrop : public Command -{ - public: - CommandNSDrop(Module *creator) : Command(creator, "nickserv/drop", 0, 1) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Cancel the registration of a nickname")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - Anope::string nick = !params.empty() ? params[0] : ""; - - if (readonly) - { - source.Reply(_("Sorry, nickname de-registration is temporarily disabled.")); - return; - } - - NickAlias *na = findnick((u->Account() && !nick.empty() ? nick : u->nick)); - if (!na) - { - source.Reply(NICK_NOT_REGISTERED); - return; - } - - if (!u->Account()) - { - source.Reply(NICK_IDENTIFY_REQUIRED, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - return; - } - - bool is_mine = u->Account() == na->nc; - Anope::string my_nick; - if (is_mine && nick.empty()) - my_nick = na->nick; - - if (!is_mine && !u->HasPriv("nickserv/drop")) - source.Reply(ACCESS_DENIED); - else if (Config->NSSecureAdmins && !is_mine && na->nc->IsServicesOper()) - source.Reply(ACCESS_DENIED); - else - { - if (readonly) - source.Reply(READ_ONLY_MODE); - - FOREACH_MOD(I_OnNickDrop, OnNickDrop(u, na)); - - Log(!is_mine ? LOG_OVERRIDE : LOG_COMMAND, u, this) << "to drop nickname " << na->nick << " (group: " << na->nc->display << ") (email: " << (!na->nc->email.empty() ? na->nc->email : "none") << ")"; - delete na; - - if (!is_mine) - { - source.Reply(_("Nickname \002%s\002 has been dropped."), nick.c_str()); - } - else - { - if (!nick.empty()) - source.Reply(_("Nickname \002%s\002 has been dropped."), nick.c_str()); - else - source.Reply(_("Your nickname has been dropped.")); - } - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - User *u = source.u; - if (u->Account() && u->HasPriv("nickserv/drop")) - source.Reply(_("Syntax: \002%s [\037nickname\037]\002\n" - " \n" - "Without a parameter, deletes your nickname.\n" - " \n" - "With a parameter, drops the named nick from the database.\n" - "You may drop any nick within your group without any \n" - "special privileges. Dropping any nick is limited to \n" - "\002Services Operators\002."), source.command.c_str()); - else - source.Reply(_("Syntax: \002%s [\037nickname\037 | \037password\037]\002\n" - " \n" - "Deltes your nickname. A nick\n" - "that has been dropped is free for anyone to re-register.\n" - " \n" - "You may drop a nick within your group by passing it\n" - "as the \002nick\002 parameter.\n" - " \n" - "If you have a nickname registration pending but can not confirm\n" - "it for any reason, you can cancel your registration by passing\n" - "your password as the \002password\002 parameter.\n" - " \n" - "In order to use this command, you must first identify\n" - "with your password."), source.command.c_str()); - - return true; - } -}; - -class NSDrop : public Module -{ - CommandNSDrop commandnsdrop; - - public: - NSDrop(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsdrop(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsdrop); - } -}; - -MODULE_INIT(NSDrop) diff --git a/modules/core/ns_getemail.cpp b/modules/core/ns_getemail.cpp deleted file mode 100644 index fa27e5174..000000000 --- a/modules/core/ns_getemail.cpp +++ /dev/null @@ -1,82 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * A simple call to check for all emails that a user may have registered - * with. It returns the nicks that match the email you provide. Wild - * Cards are not excepted. Must use user@email-host. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSGetEMail : public Command -{ - public: - CommandNSGetEMail(Module *creator) : Command(creator, "nickserv/getemail", 1, 1) - { - this->SetDesc(_("Matches and returns all users that registered using given email")); - this->SetSyntax(_("\037user@email-host\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &email = params[0]; - int j = 0; - - Log(LOG_ADMIN, u, this) << "on " << email; - - for (nickcore_map::const_iterator it = NickCoreList.begin(), it_end = NickCoreList.end(); it != it_end; ++it) - { - NickCore *nc = it->second; - - if (!nc->email.empty() && nc->email.equals_ci(email)) - { - ++j; - source.Reply(_("Emails Match \002%s\002 to \002%s\002."), nc->display.c_str(), email.c_str()); - } - } - - if (j <= 0) - { - source.Reply(_("No Emails listed for \002%s\002."), email.c_str()); - return; - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Returns the matching nicks that used given email. \002Note\002 that\n" - "you can not use wildcards for either user or emailhost. Whenever\n" - "this command is used, a message including the person who issued\n" - "the command and the email it was used on will be logged.")); - return true; - } -}; - -class NSGetEMail : public Module -{ - CommandNSGetEMail commandnsgetemail; - public: - NSGetEMail(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsgetemail(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsgetemail); - } -}; - -MODULE_INIT(NSGetEMail) diff --git a/modules/core/ns_getpass.cpp b/modules/core/ns_getpass.cpp deleted file mode 100644 index 9ebea5263..000000000 --- a/modules/core/ns_getpass.cpp +++ /dev/null @@ -1,79 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSGetPass : public Command -{ - public: - CommandNSGetPass(Module *creator) : Command(creator, "nickserv/getpass", 1, 1) - { - this->SetDesc(_("Retrieve the password for a nickname")); - this->SetSyntax(_("\037nickname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - Anope::string tmp_pass; - NickAlias *na; - - if (!(na = findnick(nick))) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else if (Config->NSSecureAdmins && na->nc->IsServicesOper()) - source.Reply(ACCESS_DENIED); - else - { - if (enc_decrypt(na->nc->pass, tmp_pass) == 1) - { - Log(LOG_ADMIN, u, this) << "for " << nick; - source.Reply(_("Password for %s is \002%s\002."), nick.c_str(), tmp_pass.c_str()); - } - else - source.Reply(_("GETPASS command unavailable because encryption is in use.")); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Returns the password for the given nickname. \002Note\002 that\n" - "whenever this command is used, a message including the\n" - "person who issued the command and the nickname it was used\n" - "on will be logged and sent out as a WALLOPS/GLOBOPS.")); - return true; - } -}; - -class NSGetPass : public Module -{ - CommandNSGetPass commandnsgetpass; - - public: - NSGetPass(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsgetpass(this) - { - this->SetAuthor("Anope"); - - Anope::string tmp_pass = "plain:tmp"; - if (enc_decrypt(tmp_pass, tmp_pass) == -1) - throw ModuleException("Incompatible with the encryption module being used"); - - ModuleManager::RegisterService(&commandnsgetpass); - } -}; - -MODULE_INIT(NSGetPass) diff --git a/modules/core/ns_ghost.cpp b/modules/core/ns_ghost.cpp deleted file mode 100644 index 37dcef9c7..000000000 --- a/modules/core/ns_ghost.cpp +++ /dev/null @@ -1,122 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSGhost : public Command -{ - public: - CommandNSGhost(Module *creator) : Command(creator, "nickserv/ghost", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Disconnects a \"ghost\" IRC session using your nick")); - this->SetSyntax("\037nickname\037 [\037password\037]"); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &nick = params[0]; - const Anope::string &pass = params.size() > 1 ? params[1] : ""; - - User *u = source.u; - User *user = finduser(nick); - NickAlias *na = findnick(nick); - - if (!user) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (!na) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else if (na->nc->HasFlag(NI_SUSPENDED)) - source.Reply(NICK_X_SUSPENDED, na->nick.c_str()); - else if (nick.equals_ci(u->nick)) - source.Reply(_("You can't ghost yourself!")); - else - { - bool ok = false; - if (u->Account() == na->nc) - ok = true; - else if (!na->nc->HasFlag(NI_SECURE) && is_on_access(u, na->nc)) - ok = true; - else if (!u->fingerprint.empty() && na->nc->FindCert(u->fingerprint)) - ok = true; - else if (!pass.empty()) - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnCheckAuthentication, OnCheckAuthentication(this, &source, params, na->nc->display, pass)); - if (MOD_RESULT == EVENT_STOP) - return; - else if (MOD_RESULT == EVENT_ALLOW) - ok = true; - } - - if (ok) - { - if (!user->IsIdentified()) - source.Reply(_("You may not ghost an unidentified user, use RECOVER instead.")); - else - { - Log(LOG_COMMAND, u, this) << "for " << nick; - Anope::string buf = "GHOST command used by " + u->nick; - user->Kill(Config->NickServ, buf); - source.Reply(_("Ghost with your nick has been killed."), nick.c_str()); - } - } - else - { - source.Reply(ACCESS_DENIED); - if (!pass.empty()) - { - Log(LOG_COMMAND, u, this) << "with an invalid password for " << nick; - bad_password(u); - } - } - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("itermminates a \"ghost\" IRC session using your nick. A\n" - "ghost\" session is one which is not actually connected,\n" - "but which the IRC server believes is still online for one\n" - "reason or another. Typically, this happens if your\n" - "computer crashes or your Internet or modem connection\n" - "goes down while you're on IRC.\n" - " \n" - "In order to use the \002GHOST\002 command for a nick, your\n" - "current address as shown in /WHOIS must be on that nick's\n" - "access list, you must be identified and in the group of\n" - "that nick, or you must supply the correct password for\n" - "the nickname.")); - return true; - } -}; - -class NSGhost : public Module -{ - CommandNSGhost commandnsghost; - - public: - NSGhost(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsghost(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsghost); - } -}; - -MODULE_INIT(NSGhost) diff --git a/modules/core/ns_group.cpp b/modules/core/ns_group.cpp deleted file mode 100644 index 2e23e1f51..000000000 --- a/modules/core/ns_group.cpp +++ /dev/null @@ -1,305 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSGroup : public Command -{ - public: - CommandNSGroup(Module *creator) : Command(creator, "nickserv/group", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Join a group")); - this->SetSyntax(_("\037target\037 \037password\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params[0]; - const Anope::string &pass = params.size() > 1 ? params[1] : ""; - - if (readonly) - { - source.Reply(_("Sorry, nickname grouping is temporarily disabled.")); - return; - } - - if (Config->RestrictOperNicks) - for (unsigned i = 0; i < Config->Opers.size(); ++i) - { - Oper *o = Config->Opers[i]; - - if (!u->HasMode(UMODE_OPER) && u->nick.find_ci(o->name) != Anope::string::npos) - { - source.Reply(NICK_CANNOT_BE_REGISTERED, u->nick.c_str()); - return; - } - } - - NickAlias *target, *na = findnick(u->nick); - if (!(target = findnick(nick))) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else if (Anope::CurTime < u->lastnickreg + Config->NSRegDelay) - source.Reply(_("Please wait %d seconds before using the GROUP command again."), (Config->NSRegDelay + u->lastnickreg) - Anope::CurTime); - else if (target && target->nc->HasFlag(NI_SUSPENDED)) - { - Log(LOG_COMMAND, u, this) << "tried to use GROUP for SUSPENDED nick " << target->nick; - source.Reply(NICK_X_SUSPENDED, target->nick.c_str()); - } - else if (na && target->nc == na->nc) - source.Reply(_("You are already a member of the group of \002%s\002."), target->nick.c_str()); - else if (na && na->nc != u->Account()) - source.Reply(NICK_IDENTIFY_REQUIRED, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - else if (na && Config->NSNoGroupChange) - source.Reply(_("Your nick is already registered.")); - else if (Config->NSMaxAliases && (target->nc->aliases.size() >= Config->NSMaxAliases) && !target->nc->IsServicesOper()) - source.Reply(_("There are too many nicks in %s's group.")); - else - { - bool ok = false; - if (!na && u->Account()) - ok = true; - else if (!u->fingerprint.empty() && target->nc->FindCert(u->fingerprint)) - ok = true; - else if (!pass.empty()) - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnCheckAuthentication, OnCheckAuthentication(this, &source, params, target->nc->display, pass)); - if (MOD_RESULT == EVENT_STOP) - return; - else if (MOD_RESULT == EVENT_ALLOW) - ok = true; - } - if (ok) - { - /* If the nick is already registered, drop it. - * If not, check that it is valid. - */ - if (na) - delete na; - else - { - size_t prefixlen = Config->NSGuestNickPrefix.length(); - size_t nicklen = u->nick.length(); - - if (nicklen <= prefixlen + 7 && nicklen >= prefixlen + 1 && !u->nick.find_ci(Config->NSGuestNickPrefix) && !u->nick.substr(prefixlen).find_first_not_of("1234567890")) - { - source.Reply(NICK_CANNOT_BE_REGISTERED, u->nick.c_str()); - return; - } - } - - na = new NickAlias(u->nick, target->nc); - - Anope::string last_usermask = u->GetIdent() + "@" + u->GetDisplayedHost(); - na->last_usermask = last_usermask; - na->last_realname = u->realname; - na->time_registered = na->last_seen = Anope::CurTime; - - u->Login(na->nc); - FOREACH_MOD(I_OnNickGroup, OnNickGroup(u, target)); - if (target->nc->HasFlag(NI_UNCONFIRMED) == false) - ircdproto->SendAccountLogin(u, u->Account()); - ircdproto->SetAutoIdentificationToken(u); - - Log(LOG_COMMAND, u, this) << "makes " << u->nick << " join group of " << target->nick << " (" << target->nc->display << ") (email: " << (!target->nc->email.empty() ? target->nc->email : "none") << ")"; - source.Reply(_("You are now in the group of \002%s\002."), target->nick.c_str()); - - u->lastnickreg = Anope::CurTime; - } - else - { - Log(LOG_COMMAND, u, this) << "failed group for " << target->nick; - source.Reply(PASSWORD_INCORRECT); - bad_password(u); - } - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command makes your nickname join the \037target\037 nickname's \n" - "group. \037password\037 is the password of the target nickname.\n" - " \n" - "Joining a group will allow you to share your configuration,\n" - "memos, and channel privileges with all the nicknames in the\n" - "group, and much more!\n" - " \n" - "A group exists as long as it is useful. This means that even\n" - "if a nick of the group is dropped, you won't lose the\n" - "shared things described above, as long as there is at\n" - "least one nick remaining in the group.\n" - " \n" - "You may be able to use this command even if you have not registered\n" - "your nick yet. If your nick is already registered, you'll\n" - "need to identify yourself before using this command.\n" - " \n" - "It is recommended to use this command with a non-registered\n" - "nick because it will be registered automatically when \n" - "using this command. You may use it with a registered nick (to \n" - "change your group) only if your network administrators allowed \n" - "it.\n" - " \n" - "You can only be in one group at a time. Group merging is\n" - "not possible.\n" - " \n" - "\037Note\037: all the nicknames of a group have the same password.")); - return true; - } -}; - -class CommandNSUngroup : public Command -{ - public: - CommandNSUngroup(Module *creator) : Command(creator, "nickserv/ungroup", 0, 1) - { - this->SetDesc(_("Remove a nick from a group")); - this->SetSyntax(_("[\037nick\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - Anope::string nick = !params.empty() ? params[0] : ""; - NickAlias *na = findnick(!nick.empty() ? nick : u->nick); - - if (u->Account()->aliases.size() == 1) - source.Reply(_("Your nick is not grouped to anything, you can't ungroup it.")); - else if (!na) - source.Reply(NICK_X_NOT_REGISTERED, !nick.empty() ? nick.c_str() : u->nick.c_str()); - else if (na->nc != u->Account()) - source.Reply(_("The nick %s is not in your group."), na->nick.c_str()); - else - { - NickCore *oldcore = na->nc; - - std::list<NickAlias *>::iterator it = std::find(oldcore->aliases.begin(), oldcore->aliases.end(), na); - if (it != oldcore->aliases.end()) - oldcore->aliases.erase(it); - - if (na->nick.equals_ci(oldcore->display)) - change_core_display(oldcore); - - na->nc = new NickCore(na->nick); - na->nc->aliases.push_back(na); - - na->nc->pass = oldcore->pass; - if (!oldcore->email.empty()) - na->nc->email = oldcore->email; - if (!oldcore->greet.empty()) - na->nc->greet = oldcore->greet; - na->nc->language = oldcore->language; - - source.Reply(_("Nick %s has been ungrouped from %s."), na->nick.c_str(), oldcore->display.c_str()); - - User *user = finduser(na->nick); - if (user) - /* The user on the nick who was ungrouped may be identified to the old group, set -r */ - user->RemoveMode(findbot(Config->NickServ), UMODE_REGISTERED); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command ungroups your nick, or if given, the specificed nick,\n" - "from the group it is in. The ungrouped nick keeps its registration\n" - "time, password, email, greet, language, url, and icq. Everything\n" - "else is reset. You may not ungroup yourself if there is only one\n" - "nick in your group.")); - return true; - } -}; - -class CommandNSGList : public Command -{ - public: - CommandNSGList(Module *creator) : Command(creator, "nickserv/glist", 0, 1) - { - this->SetDesc(_("Lists all nicknames in your group")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - Anope::string nick = !params.empty() ? params[0] : ""; - - const NickCore *nc = u->Account(); - - if (!nick.empty() && (!nick.equals_ci(u->nick) && !u->IsServicesOper())) - source.Reply(ACCESS_DENIED, Config->NickServ.c_str()); - else if (!nick.empty() && (!findnick(nick) || !(nc = findnick(nick)->nc))) - source.Reply(nick.empty() ? NICK_NOT_REGISTERED : _(NICK_X_NOT_REGISTERED), nick.c_str()); - else - { - source.Reply(!nick.empty() ? _("List of nicknames in the group of \002%s\002:") : _("List of nicknames in your group:"), nc->display.c_str()); - for (std::list<NickAlias *>::const_iterator it = nc->aliases.begin(), it_end = nc->aliases.end(); it != it_end; ++it) - { - NickAlias *na2 = *it; - - source.Reply(na2->HasFlag(NS_NO_EXPIRE) || !Config->NSExpire ? _(" %s (does not expire)") : _(" %s (expires in %s)"), na2->nick.c_str(), do_strftime(na2->last_seen + Config->NSExpire).c_str()); - } - source.Reply(_("%d nicknames in the group."), nc->aliases.size()); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - User *u = source.u; - if (u->IsServicesOper()) - source.Reply(_("Syntax: \002%s [\037nickname\037]\002\n" - " \n" - "Without a parameter, lists all nicknames that are in\n" - "your group.\n" - " \n" - "With a parameter, lists all nicknames that are in the\n" - "group of the given nick.\n" - "This use limited to \002Services Operators\002."), - source.command.c_str()); - else - source.Reply(_("Syntax: \002%s\002\n" - " \n" - "Lists all nicks in your group."), source.command.c_str()); - - return true; - } -}; - -class NSGroup : public Module -{ - CommandNSGroup commandnsgroup; - CommandNSUngroup commandnsungroup; - CommandNSGList commandnsglist; - - public: - NSGroup(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsgroup(this), commandnsungroup(this), commandnsglist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsgroup); - ModuleManager::RegisterService(&commandnsungroup); - ModuleManager::RegisterService(&commandnsglist); - } -}; - -MODULE_INIT(NSGroup) diff --git a/modules/core/ns_identify.cpp b/modules/core/ns_identify.cpp deleted file mode 100644 index b0a375cd2..000000000 --- a/modules/core/ns_identify.cpp +++ /dev/null @@ -1,93 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSIdentify : public Command -{ - public: - CommandNSIdentify(Module *creator) : Command(creator, "nickserv/identify", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Identify yourself with your password")); - this->SetSyntax(_("[\037account\037] \037password\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params.size() == 2 ? params[0] : u->nick; - Anope::string pass = params[params.size() - 1]; - - NickAlias *na = findnick(nick); - if (na && na->nc->HasFlag(NI_SUSPENDED)) - source.Reply(NICK_X_SUSPENDED, na->nick.c_str()); - else if (u->Account() && na && u->Account() == na->nc) - source.Reply(_("You are already identified.")); - else - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnCheckAuthentication, OnCheckAuthentication(this, &source, params, na ? na->nc->display : nick, pass)); - if (MOD_RESULT == EVENT_STOP) - return; - - if (!na) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else if (MOD_RESULT != EVENT_ALLOW) - { - Log(LOG_COMMAND, u, this) << "and failed to identify"; - source.Reply(PASSWORD_INCORRECT); - bad_password(u); - } - else - { - if (u->IsIdentified()) - Log(LOG_COMMAND, u, this) << "to log out of account " << u->Account()->display; - - Log(LOG_COMMAND, u, this) << "and identified for account " << na->nc->display; - source.Reply(_("Password accepted - you are now recognized.")); - u->Identify(na); - } - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Tells %s that you are really the owner of this\n" - "nick. Many commands require you to authenticate yourself\n" - "with this command before you use them. The password\n" - "should be the same one you sent with the \002REGISTER\002\n" - "command."), source.owner->nick.c_str()); - return true; - } -}; - -class NSIdentify : public Module -{ - CommandNSIdentify commandnsidentify; - - public: - NSIdentify(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsidentify(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsidentify); - } -}; - -MODULE_INIT(NSIdentify) diff --git a/modules/core/ns_info.cpp b/modules/core/ns_info.cpp deleted file mode 100644 index 5a6d9dc0c..000000000 --- a/modules/core/ns_info.cpp +++ /dev/null @@ -1,173 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSInfo : public Command -{ - private: - // cannot be const, as it is modified - void CheckOptStr(Anope::string &buf, NickCoreFlag opt, const Anope::string &str, NickCore *nc, bool reverse_logic = false) - { - if (reverse_logic ? !nc->HasFlag(opt) : nc->HasFlag(opt)) - { - if (!buf.empty()) - buf += ", "; - - buf += str; - } - } - public: - CommandNSInfo(Module *creator) : Command(creator, "nickserv/info", 0, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Displays information about a given nickname")); - this->SetSyntax(_("[\037nickname\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params.size() ? params[0] : (u->Account() ? u->Account()->display : u->nick); - NickAlias *na = findnick(nick); - bool has_auspex = u->IsIdentified() && u->HasPriv("nickserv/auspex"); - - if (!na) - { - if (nickIsServices(nick, true)) - source.Reply(_("Nick \002%s\002 is part of this Network's Services."), nick.c_str()); - else - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - } - else - { - bool nick_online = false, show_hidden = false; - - /* Is the real owner of the nick we're looking up online? -TheShadow */ - User *u2 = finduser(na->nick); - if (u2 && u2->Account() == na->nc) - nick_online = true; - - if (has_auspex || (u->Account() && na->nc == u->Account())) - show_hidden = true; - - source.Reply(_("%s is %s"), na->nick.c_str(), na->last_realname.c_str()); - - if (na->nc->IsServicesOper() && (show_hidden || !na->nc->HasFlag(NI_HIDE_STATUS))) - source.Reply(_("%s is a services operator of type %s."), na->nick.c_str(), na->nc->o->ot->GetName().c_str()); - - if (nick_online) - { - if (show_hidden || !na->nc->HasFlag(NI_HIDE_MASK)) - source.Reply(_(" Is online from: %s"), na->last_usermask.c_str()); - else - source.Reply(_("%s is currently online."), na->nick.c_str()); - } - else - { - if (show_hidden || !na->nc->HasFlag(NI_HIDE_MASK)) - source.Reply(_("Last seen address: %s"), na->last_usermask.c_str()); - } - - source.Reply(_(" Time registered: %s"), do_strftime(na->time_registered).c_str()); - - if (!nick_online) - { - source.Reply(_(" Last seen time: %s"), do_strftime(na->last_seen).c_str()); - } - - if (!na->last_quit.empty() && (show_hidden || !na->nc->HasFlag(NI_HIDE_QUIT))) - source.Reply(_("Last quit message: %s"), na->last_quit.c_str()); - - if (!na->nc->email.empty() && (show_hidden || !na->nc->HasFlag(NI_HIDE_EMAIL))) - source.Reply(_(" E-mail address: %s"), na->nc->email.c_str()); - - if (show_hidden) - { - if (na->hostinfo.HasVhost()) - { - if (ircd->vident && !na->hostinfo.GetIdent().empty()) - source.Reply(_(" vhost: %s@%s"), na->hostinfo.GetIdent().c_str(), na->hostinfo.GetHost().c_str()); - else - source.Reply(_(" vhost: %s"), na->hostinfo.GetHost().c_str()); - } - if (!na->nc->greet.empty()) - source.Reply(_(" Greet message: %s"), na->nc->greet.c_str()); - - Anope::string optbuf; - - CheckOptStr(optbuf, NI_KILLPROTECT, _("Protection"), na->nc); - CheckOptStr(optbuf, NI_SECURE, _("Security"), na->nc); - CheckOptStr(optbuf, NI_PRIVATE, _("Private"), na->nc); - CheckOptStr(optbuf, NI_MSG, _("Message mode"), na->nc); - CheckOptStr(optbuf, NI_AUTOOP, _("Auto-op"), na->nc); - - source.Reply(NICK_INFO_OPTIONS, optbuf.empty() ? _("None") : optbuf.c_str()); - - if (na->nc->HasFlag(NI_SUSPENDED)) - { - if (!na->last_quit.empty()) - source.Reply(_("This nickname is currently suspended, reason: %s"), na->last_quit.c_str()); - else - source.Reply(_("This nickname is currently suspended")); - } - - if (na->nc->HasFlag(NI_UNCONFIRMED) == false) - { - if (na->HasFlag(NS_NO_EXPIRE) || !Config->NSExpire) - source.Reply(_("This nickname will not expire.")); - else - source.Reply(_("Expires on: %s"), do_strftime(na->last_seen + Config->NSExpire).c_str()); - } - else - source.Reply(_("Expires on: %s"), do_strftime(na->time_registered + Config->NSUnconfirmedExpire).c_str()); - } - - FOREACH_MOD(I_OnNickInfo, OnNickInfo(source, na, show_hidden)); - - if (na->nc->HasFlag(NI_UNCONFIRMED)) - source.Reply(_("This nickname is unconfirmed.")); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Displays information about the given nickname, such as\n" - "the nick's owner, last seen address and time, and nick\n" - "options. If no nick is given, and you are identified,\n" - "your account name is used, else your current nickname is\n" - "used.")); - - return true; - } -}; - -class NSInfo : public Module -{ - CommandNSInfo commandnsinfo; - - public: - NSInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsinfo(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsinfo); - } -}; - -MODULE_INIT(NSInfo) diff --git a/modules/core/ns_list.cpp b/modules/core/ns_list.cpp deleted file mode 100644 index 96049ba02..000000000 --- a/modules/core/ns_list.cpp +++ /dev/null @@ -1,169 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSList : public Command -{ - public: - CommandNSList(Module *creator) : Command(creator, "nickserv/list", 1, 2) - { - this->SetDesc(_("List all registered nicknames that match a given pattern")); - this->SetSyntax(_("\037pattern\037 [SUSPENDED] [NOEXPIRE] [UNCONFIRMED]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - Anope::string pattern = params[0]; - const NickCore *mync; - unsigned nnicks; - bool is_servadmin = u->IsServicesOper(); - char noexpire_char = ' '; - int count = 0, from = 0, to = 0; - bool suspended, nsnoexpire, unconfirmed; - - suspended = nsnoexpire = unconfirmed = false; - - if (pattern[0] == '#') - { - Anope::string n1 = myStrGetToken(pattern.substr(1), '-', 0), /* Read FROM out */ - n2 = myStrGetToken(pattern, '-', 1); - - try - { - from = convertTo<int>(n1); - to = convertTo<int>(n2); - } - catch (const ConvertException &) - { - source.Reply(LIST_INCORRECT_RANGE); - return; - } - - pattern = "*"; - } - - nnicks = 0; - - if (is_servadmin && params.size() > 1) - { - Anope::string keyword; - spacesepstream keywords(params[1]); - while (keywords.GetToken(keyword)) - { - if (keyword.equals_ci("NOEXPIRE")) - nsnoexpire = true; - if (keyword.equals_ci("SUSPENDED")) - suspended = true; - if (keyword.equals_ci("UNCONFIRMED")) - unconfirmed = true; - } - } - - mync = u->Account(); - - source.Reply(LIST_HEADER, pattern.c_str()); - for (nickalias_map::const_iterator it = NickAliasList.begin(), it_end = NickAliasList.end(); it != it_end; ++it) - { - NickAlias *na = it->second; - - /* Don't show private nicks to non-services admins. */ - if (na->nc->HasFlag(NI_PRIVATE) && !is_servadmin && na->nc != mync) - continue; - else if (nsnoexpire && !na->HasFlag(NS_NO_EXPIRE)) - continue; - else if (suspended && !na->nc->HasFlag(NI_SUSPENDED)) - continue; - else if (unconfirmed && !na->nc->HasFlag(NI_UNCONFIRMED)) - continue; - - /* We no longer compare the pattern against the output buffer. - * Instead we build a nice nick!user@host buffer to compare. - * The output is then generated separately. -TheShadow */ - Anope::string buf = Anope::printf("%s!%s", na->nick.c_str(), !na->last_usermask.empty() ? na->last_usermask.c_str() : "*@*"); - if (na->nick.equals_ci(pattern) || Anope::Match(buf, pattern)) - { - if (((count + 1 >= from && count + 1 <= to) || (!from && !to)) && ++nnicks <= Config->NSListMax) - { - if (is_servadmin && na->HasFlag(NS_NO_EXPIRE)) - noexpire_char = '!'; - else - noexpire_char = ' '; - if (na->nc->HasFlag(NI_HIDE_MASK) && !is_servadmin && na->nc != mync) - buf = Anope::printf("%-20s [Hostname Hidden]", na->nick.c_str()); - else if (na->nc->HasFlag(NI_SUSPENDED)) - buf = Anope::printf("%-20s [Suspended]", na->nick.c_str()); - else if (na->nc->HasFlag(NI_UNCONFIRMED)) - buf = Anope::printf("%-20s [Unconfirmed]", na->nick.c_str()); - else - buf = Anope::printf("%-20s %s", na->nick.c_str(), na->last_usermask.c_str()); - source.Reply(" %c%s", noexpire_char, buf.c_str()); - } - ++count; - } - } - - - source.Reply(_("End of list - %d/%d matches shown."), nnicks > Config->NSListMax ? Config->NSListMax : nnicks, nnicks); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all registered nicknames which match the given\n" - "pattern, in \037nick!user@host\037 format. Nicks with the \002PRIVATE\002\n" - "option set will only be displayed to Services Operators. Nicks\n" - "with the \002NOEXPIRE\002 option set will have a \002!\002 appended to\n" - "the nickname for Services Operators.\n" - " \n" - "If the SUSPENDED, NOEXPIRE or UNCONFIRMED options are given, only\n" - "nicks which, respectively, are SUSPENDED, UNCONFIRMED or have the\n" - "NOEXPIRE flag set will be displayed. If multiple options are\n" - "given, all nicks matching at least one option will be displayed.\n" - "These options are limited to \037Services Operators\037. \n" - "\n" - "Examples:\n" - " \n" - " \002LIST *!joeuser@foo.com\002\n" - " Lists all registered nicks owned by joeuser@foo.com.\n" - " \n" - " \002LIST *Bot*!*@*\002\n" - " Lists all registered nicks with \002Bot\002 in their\n" - " names (case insensitive).\n" - " \n" - " \002LIST * NOEXPIRE\002\n" - " Lists all registered nicks which have been set to not expire.\n")); - - return true; - } -}; - -class NSList : public Module -{ - CommandNSList commandnslist; - - public: - NSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnslist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnslist); - } -}; - -MODULE_INIT(NSList) diff --git a/modules/core/ns_logout.cpp b/modules/core/ns_logout.cpp deleted file mode 100644 index 476330a11..000000000 --- a/modules/core/ns_logout.cpp +++ /dev/null @@ -1,97 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "nickserv.h" - -class CommandNSLogout : public Command -{ - public: - CommandNSLogout(Module *creator) : Command(creator, "nickserv/logout", 0, 2) - { - this->SetDesc(_("Reverses the effect of the IDENTIFY command")); - this->SetSyntax(_("[\037nickname\037 [REVALIDATE]]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = !params.empty() ? params[0] : ""; - const Anope::string ¶m = params.size() > 1 ? params[1] : ""; - - User *u2; - if (!u->IsServicesOper() && !nick.empty()) - this->OnSyntaxError(source, ""); - else if (!(u2 = (!nick.empty() ? finduser(nick) : u))) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (!nick.empty() && !u2->IsServicesOper()) - source.Reply(_("You can't logout %s because they are a Services Operator."), nick.c_str()); - else - { - if (!nick.empty() && !param.empty() && param.equals_ci("REVALIDATE") && nickserv) - nickserv->Validate(u2); - - u2->isSuperAdmin = 0; /* Dont let people logout and remain a SuperAdmin */ - Log(LOG_COMMAND, u, this) << "to logout " << u2->nick; - - /* Remove founder status from this user in all channels */ - if (!nick.empty()) - source.Reply(_("Nick %s has been logged out."), nick.c_str()); - else - source.Reply(_("Your nick has been logged out.")); - - ircdproto->SendAccountLogout(u2, u2->Account()); - u2->RemoveMode(source.owner, UMODE_REGISTERED); - ircdproto->SendUnregisteredNick(u2); - - u2->Logout(); - - /* Send out an event */ - FOREACH_MOD(I_OnNickLogout, OnNickLogout(u2)); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Without a parameter, reverses the effect of the \002IDENTIFY\002 \n" - "command, i.e. make you not recognized as the real owner of the nick\n" - "anymore. Note, however, that you won't be asked to reidentify\n" - "yourself.\n" - " \n" - "With a parameter, does the same for the given nick. If you \n" - "specify REVALIDATE as well, Services will ask the given nick\n" - "to re-identify. This use limited to \002Services Operators\002.")); - - return true; - } -}; - -class NSLogout : public Module -{ - CommandNSLogout commandnslogout; - - public: - NSLogout(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnslogout(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnslogout); - } -}; - -MODULE_INIT(NSLogout) diff --git a/modules/core/ns_main.cpp b/modules/core/ns_main.cpp deleted file mode 100644 index 57323d0a5..000000000 --- a/modules/core/ns_main.cpp +++ /dev/null @@ -1,307 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "nickserv.h" - -static BotInfo *NickServ; - -class MyNickServService : public NickServService -{ - public: - MyNickServService(Module *m) : NickServService(m) { } - - void Validate(User *u) - { - NickAlias *na = findnick(u->nick); - if (!na) - return; - - if (na->nc->HasFlag(NI_SUSPENDED)) - { - u->SendMessage(NickServ, NICK_X_SUSPENDED, u->nick.c_str()); - u->Collide(na); - return; - } - - if (!u->IsIdentified() && !u->fingerprint.empty() && na->nc->FindCert(u->fingerprint)) - { - u->SendMessage(NickServ, _("SSL Fingerprint accepted, you are now identified.")); - u->Identify(na); - return; - } - - if (!na->nc->HasFlag(NI_SECURE) && u->IsRecognized()) - { - na->last_seen = Anope::CurTime; - Anope::string last_usermask = u->GetIdent() + "@" + u->GetDisplayedHost(); - na->last_usermask = last_usermask; - na->last_realname = u->realname; - return; - } - - if (u->IsRecognized() || !na->nc->HasFlag(NI_KILL_IMMED)) - { - if (na->nc->HasFlag(NI_SECURE)) - u->SendMessage(NickServ, NICK_IS_SECURE, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - else - u->SendMessage(NickServ, NICK_IS_REGISTERED, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - } - - if (na->nc->HasFlag(NI_KILLPROTECT) && !u->IsRecognized()) - { - if (na->nc->HasFlag(NI_KILL_IMMED)) - { - u->SendMessage(NickServ, FORCENICKCHANGE_NOW); - u->Collide(na); - } - else if (na->nc->HasFlag(NI_KILL_QUICK)) - { - u->SendMessage(NickServ, _("If you do not change within 20 seconds, I will change your nick.")); - new NickServCollide(u, 20); - } - else - { - u->SendMessage(NickServ, _("If you do not change within one minute, I will change your nick.")); - new NickServCollide(u, 60); - } - } - - } -}; - -class ExpireCallback : public CallBack -{ - public: - ExpireCallback(Module *owner) : CallBack(owner, Config->ExpireTimeout, Anope::CurTime, true) { } - - void Tick(time_t) - { - if (noexpire || readonly) - return; - - for (nickalias_map::const_iterator it = NickAliasList.begin(), it_end = NickAliasList.end(); it != it_end; ) - { - NickAlias *na = it->second; - ++it; - - User *u = finduser(na->nick); - if (u && (na->nc->HasFlag(NI_SECURE) ? u->IsIdentified(true) : u->IsRecognized(true))) - na->last_seen = Anope::CurTime; - - bool expire = false; - - if (na->nc->HasFlag(NI_UNCONFIRMED)) - if (Config->NSUnconfirmedExpire && Anope::CurTime - na->time_registered >= Config->NSUnconfirmedExpire) - expire = true; - if (na->nc->HasFlag(NI_SUSPENDED)) - { - if (Config->NSSuspendExpire && Anope::CurTime - na->last_seen >= Config->NSSuspendExpire) - expire = true; - } - else if (Config->NSExpire && Anope::CurTime - na->last_seen >= Config->NSExpire) - expire = true; - if (na->HasFlag(NS_NO_EXPIRE)) - expire = false; - - if (expire) - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnPreNickExpire, OnPreNickExpire(na)); - if (MOD_RESULT == EVENT_STOP) - continue; - Anope::string extra; - if (na->nc->HasFlag(NI_SUSPENDED)) - extra = "suspended "; - Log(LOG_NORMAL, "expire") << "Expiring " << extra << "nickname " << na->nick << " (group: " << na->nc->display << ") (e-mail: " << (na->nc->email.empty() ? "none" : na->nc->email) << ")"; - FOREACH_MOD(I_OnNickExpire, OnNickExpire(na)); - delete na; - } - } - } -}; - -class NickServCore : public Module -{ - MyNickServService mynickserv; - ExpireCallback expires; - - public: - NickServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), mynickserv(this), expires(this) - { - this->SetAuthor("Anope"); - - NickServ = findbot(Config->NickServ); - if (NickServ == NULL) - throw ModuleException("No bot named " + Config->NickServ); - - Implementation i[] = { I_OnDelNick, I_OnDelCore, I_OnChangeCoreDisplay, I_OnNickIdentify, I_OnNickGroup, - I_OnNickUpdate, I_OnUserNickChange, I_OnPreHelp, I_OnPostHelp }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&this->mynickserv); - } - - void OnDelNick(NickAlias *na) - { - User *u = finduser(na->nick); - if (u && u->Account() == na->nc) - { - u->RemoveMode(NickServ, UMODE_REGISTERED); - ircdproto->SendAccountLogout(u, u->Account()); - ircdproto->SendUnregisteredNick(u); - u->Logout(); - } - } - - void OnDelCore(NickCore *nc) - { - Log(NickServ, "nick") << "deleting nickname group " << nc->display; - - /* Clean up this nick core from any users online using it - * (ones that /nick but remain unidentified) - */ - for (std::list<User *>::iterator it = nc->Users.begin(); it != nc->Users.end();) - { - User *user = *it++; - ircdproto->SendAccountLogout(user, user->Account()); - user->RemoveMode(NickServ, UMODE_REGISTERED); - ircdproto->SendUnregisteredNick(user); - user->Logout(); - FOREACH_MOD(I_OnNickLogout, OnNickLogout(user)); - } - nc->Users.clear(); - } - - void OnChangeCoreDisplay(NickCore *nc, const Anope::string &newdisplay) - { - Log(LOG_NORMAL, "nick", NickServ) << "Changing " << nc->display << " nickname group display to " << newdisplay; - } - - void OnNickIdentify(User *u) - { - NickAlias *this_na = findnick(u->nick); - if (this_na && this_na->nc == u->Account() && u->Account()->HasFlag(NI_UNCONFIRMED) == false) - u->SetMode(NickServ, UMODE_REGISTERED); - - if (Config->NSModeOnID) - for (UChannelList::iterator it = u->chans.begin(), it_end = u->chans.end(); it != it_end; ++it) - { - ChannelContainer *cc = *it; - Channel *c = cc->chan; - if (c) - chan_set_correct_modes(u, c, 1); - } - - if (Config->NSForceEmail && u->Account()->email.empty()) - { - u->SendMessage(NickServ, _("You must now supply an e-mail for your nick.\n" - "This e-mail will allow you to retrieve your password in\n" - "case you forget it.")); - u->SendMessage(NickServ, _("Type \002%s%s SET EMAIL \037e-mail\037\002 in order to set your e-mail.\n" - "Your privacy is respected; this e-mail won't be given to\n" - "any third-party person."), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - } - - if (u->Account()->HasFlag(NI_UNCONFIRMED)) - { - u->SendMessage(NickServ, _("Your email address is not confirmed. To confirm it, follow the instructions that were emailed to you when you registered.")); - this_na = findnick(u->Account()->display); - time_t time_registered = Anope::CurTime - this_na->time_registered; - if (Config->NSUnconfirmedExpire > time_registered) - u->SendMessage(NickServ, _("Your account will expire, if not confirmed, in %s"), duration(Config->NSUnconfirmedExpire - time_registered).c_str()); - } - } - - void OnNickGroup(User *u, NickAlias *target) - { - if (target->nc->HasFlag(NI_UNCONFIRMED) == false) - u->SetMode(NickServ, UMODE_REGISTERED); - } - - void OnNickUpdate(User *u) - { - for (UChannelList::iterator it = u->chans.begin(), it_end = u->chans.end(); it != it_end; ++it) - { - ChannelContainer *cc = *it; - Channel *c = cc->chan; - if (c) - chan_set_correct_modes(u, c, 1); - } - } - - void OnUserNickChange(User *u, const Anope::string &oldnick) - { - NickAlias *na = findnick(u->nick); - /* If the new nick isnt registerd or its registerd and not yours */ - if (!na || na->nc != u->Account()) - { - u->RemoveMode(NickServ, UMODE_REGISTERED); - ircdproto->SendUnregisteredNick(u); - - this->mynickserv.Validate(u); - } - else - { - if (na->nc->HasFlag(NI_UNCONFIRMED) == false) - { - u->SetMode(NickServ, UMODE_REGISTERED); - ircdproto->SetAutoIdentificationToken(u); - } - Log(NickServ) << u->GetMask() << " automatically identified for group " << u->Account()->display; - } - } - - void OnUserModeSet(User *u, UserModeName Name) - { - if (Name == UMODE_REGISTERED && !u->IsIdentified()) - u->RemoveMode(NickServ, Name); - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->NickServ) - return; - source.Reply(_("\002%s\002 allows you to \"register\" a nickname and\n" - "prevent others from using it. The following\n" - "commands allow for registration and maintenance of\n" - "nicknames; to use them, type \002%s%s \037command\037\002.\n" - "For more information on a specific command, type\n" - "\002%s%s %s \037command\037\002.\n "), Config->NickServ.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), source.command.c_str()); - } - - void OnPostHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->NickServ) - return; - if (source.u->IsServicesOper()) - source.Reply(_(" \n" - "Services Operators can also drop any nickname without needing\n" - "to identify for the nick, and may view the access list for\n" - "any nickname.")); - if (Config->NSExpire >= 86400) - source.Reply(_("Nicknames that are not used anymore are subject to \n" - "the automatic expiration, i.e. they will be deleted\n" - "after %d days if not used."), Config->NSExpire / 86400); - source.Reply(_(" \n" - "\002NOTICE:\002 This service is intended to provide a way for\n" - "IRC users to ensure their identity is not compromised.\n" - "It is \002NOT\002 intended to facilitate \"stealing\" of\n" - "nicknames or other malicious actions. Abuse of %s\n" - "will result in, at minimum, loss of the abused\n" - "nickname(s)."), Config->NickServ.c_str()); - } -}; - -MODULE_INIT(NickServCore) - diff --git a/modules/core/ns_recover.cpp b/modules/core/ns_recover.cpp deleted file mode 100644 index 5e45aab9a..000000000 --- a/modules/core/ns_recover.cpp +++ /dev/null @@ -1,132 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSRecover : public Command -{ - public: - CommandNSRecover(Module *creator) : Command(creator, "nickserv/recover", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Kill another user who has taken your nick")); - this->SetSyntax(_("\037nickname\037 [\037password\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params[0]; - const Anope::string &pass = params.size() > 1 ? params[1] : ""; - - NickAlias *na; - User *u2; - if (!(u2 = finduser(nick))) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (!(na = findnick(u2->nick))) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else if (na->nc->HasFlag(NI_SUSPENDED)) - source.Reply(NICK_X_SUSPENDED, na->nick.c_str()); - else if (nick.equals_ci(u->nick)) - source.Reply(_("You can't recover yourself!")); - else if (!pass.empty()) - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnCheckAuthentication, OnCheckAuthentication(this, &source, params, na->nc->display, pass)); - if (MOD_RESULT == EVENT_STOP) - return; - - if (MOD_RESULT == EVENT_ALLOW) - { - u2->SendMessage(source.owner, FORCENICKCHANGE_NOW); - u2->Collide(na); - - /* Convert Config->NSReleaseTimeout seconds to string format */ - Anope::string relstr = duration(Config->NSReleaseTimeout); - - source.Reply(NICK_RECOVERED, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), nick.c_str(), relstr.c_str()); - } - else - { - source.Reply(ACCESS_DENIED); - Log(LOG_COMMAND, u, this) << "with invalid password for " << nick; - bad_password(u); - } - } - else - { - if (u->Account() == na->nc || (!na->nc->HasFlag(NI_SECURE) && is_on_access(u, na->nc)) || - (!u->fingerprint.empty() && na->nc->FindCert(u->fingerprint))) - { - u2->SendMessage(source.owner, FORCENICKCHANGE_NOW); - u2->Collide(na); - - /* Convert Config->NSReleaseTimeout seconds to string format */ - Anope::string relstr = duration(Config->NSReleaseTimeout); - - source.Reply(NICK_RECOVERED, Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), nick.c_str(), relstr.c_str()); - } - else - source.Reply(ACCESS_DENIED); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - /* Convert Config->NSReleaseTimeout seconds to string format */ - Anope::string relstr = duration(Config->NSReleaseTimeout); - - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to recover your nickname if someone else has\n" - "taken it; this does the same thing that %s does\n" - "automatically if someone tries to use a kill-protected\n" - "nick.\n" - " \n" - "When you give this command, %s will bring a fake\n" - "user online with the same nickname as the user you're\n" - "trying to recover your nick from. This causes the IRC\n" - "servers to disconnect the other user. This fake user will\n" - "remain online for %s to ensure that the other\n" - "user does not immediately reconnect; after that time, you\n" - "can reclaim your nick. Alternatively, use the \002RELEASE\002\n" - "command (\002%s%s HELP RELEASE\002) to get the nick\n" - "back sooner.\n" - " \n" - "In order to use the \002RECOVER\002 command for a nick, your\n" - "current address as shown in /WHOIS must be on that nick's\n" - "access list, you must be identified and in the group of\n" - "that nick, or you must supply the correct password for\n" - "the nickname."), Config->NickServ.c_str(), Config->NickServ.c_str(), relstr.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - - return true; - } -}; - -class NSRecover : public Module -{ - CommandNSRecover commandnsrecover; - - public: - NSRecover(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsrecover(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsrecover); - } -}; - -MODULE_INIT(NSRecover) diff --git a/modules/core/ns_register.cpp b/modules/core/ns_register.cpp deleted file mode 100644 index 552551994..000000000 --- a/modules/core/ns_register.cpp +++ /dev/null @@ -1,355 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static bool SendRegmail(User *u, NickAlias *na, BotInfo *bi); - -class CommandNSConfirm : public Command -{ - public: - CommandNSConfirm(Module *creator) : Command(creator, "nickserv/confirm", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Confirm an auth code")); - this->SetSyntax(_("\037passcode\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &passcode = params[0]; - - if (u->Account() && u->HasPriv("nickserv/confirm")) - { - NickAlias *na = findnick(passcode); - if (na == NULL) - source.Reply(NICK_X_NOT_REGISTERED, passcode.c_str()); - else if (na->nc->HasFlag(NI_UNCONFIRMED) == false) - source.Reply(_("Nick \002%s\002 is already confirmed."), na->nick.c_str()); - else - { - na->nc->UnsetFlag(NI_UNCONFIRMED); - Log(LOG_ADMIN, u, this) << "to confirm nick " << na->nick << " (" << na->nc->display << ")"; - source.Reply(_("Nick \002%s\002 has been confirmed."), na->nick.c_str()); - } - } - else if (u->Account()) - { - Anope::string code; - if (u->Account()->GetExtRegular<Anope::string>("ns_register_passcode", code) && code == passcode) - { - u->Account()->Shrink("ns_register_passcode"); - Log(LOG_COMMAND, u, this) << "to confirm their email"; - source.Reply(_("Your email address of \002%s\002 has been confirmed."), u->Account()->email.c_str()); - u->Account()->UnsetFlag(NI_UNCONFIRMED); - ircdproto->SendAccountLogin(u, u->Account()); - NickAlias *na = findnick(u->nick); - if (na && na->nc == u->Account()) - u->SetMode(findbot(Config->NickServ), UMODE_REGISTERED); - } - else - source.Reply(_("Invalid passcode.")); - } - else - source.Reply(_("Invalid passcode.")); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - User *u = source.u; - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command is used by several commands as a way to confirm\n" - "changes made to your account.\n" - " \n" - "This is most commonly used to confirm your email address once\n" - "you register or change it.\n" - " \n" - "This is also used after the RESETPASS command has been used to\n" - "force identify you to your nick so you may change your password.")); - if (u->Account() && u->HasPriv("nickserv/confirm")) - source.Reply(_("Additionally, Services Operators with the \037nickserv/confirm\037 permission can\n" - "replace \037passcode\037 with a users nick to force validate them.")); - return true; - } - - void OnSyntaxError(CommandSource &source, const Anope::string &subcommand) - { - source.Reply(NICK_CONFIRM_INVALID); - } -}; - -class CommandNSRegister : public Command -{ - public: - CommandNSRegister(Module *creator) : Command(creator, "nickserv/register", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Register a nickname")); - if (Config->NSForceEmail) - this->SetSyntax(_("\037password\037 \037email\037")); - else - this->SetSyntax(_("\037password\037 \037[email]\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na; - size_t prefixlen = Config->NSGuestNickPrefix.length(); - size_t nicklen = u->nick.length(); - Anope::string pass = params[0]; - Anope::string email = params.size() > 1 ? params[1] : ""; - - if (readonly) - { - source.Reply(_("Sorry, nickname registration is temporarily disabled.")); - return; - } - - if (!u->HasMode(UMODE_OPER) && Config->NickRegDelay && Anope::CurTime - u->my_signon < Config->NickRegDelay) - { - source.Reply(_("You must have been using this nick for at least %d seconds to register."), Config->NickRegDelay); - return; - } - - /* Prevent "Guest" nicks from being registered. -TheShadow */ - - /* Guest nick can now have a series of between 1 and 7 digits. - * --lara - */ - if (nicklen <= prefixlen + 7 && nicklen >= prefixlen + 1 && !u->nick.find_ci(Config->NSGuestNickPrefix) && u->nick.substr(prefixlen).find_first_not_of("1234567890") == Anope::string::npos) - { - source.Reply(NICK_CANNOT_BE_REGISTERED, u->nick.c_str()); - return; - } - - if (Config->RestrictOperNicks) - for (unsigned i = 0; i < Config->Opers.size(); ++i) - { - Oper *o = Config->Opers[i]; - - if (!u->HasMode(UMODE_OPER) && u->nick.find_ci(o->name) != Anope::string::npos) - { - source.Reply(NICK_CANNOT_BE_REGISTERED, u->nick.c_str()); - return; - } - } - - if (Config->NSForceEmail && email.empty()) - this->OnSyntaxError(source, ""); - else if (Anope::CurTime < u->lastnickreg + Config->NSRegDelay) - source.Reply(_("Please wait %d seconds before using the REGISTER command again."), (u->lastnickreg + Config->NSRegDelay) - Anope::CurTime); - else if ((na = findnick(u->nick))) - source.Reply(NICK_ALREADY_REGISTERED, u->nick.c_str()); - else if (pass.equals_ci(u->nick) || (Config->StrictPasswords && pass.length() < 5)) - source.Reply(MORE_OBSCURE_PASSWORD); - else if (pass.length() > Config->PassLen) - source.Reply(PASSWORD_TOO_LONG); - else if (!email.empty() && !MailValidate(email)) - source.Reply(MAIL_X_INVALID, email.c_str()); - else - { - na = new NickAlias(u->nick, new NickCore(u->nick)); - enc_encrypt(pass, na->nc->pass); - if (!email.empty()) - na->nc->email = email; - - Anope::string last_usermask = u->GetIdent() + "@" + u->GetDisplayedHost(); - na->last_usermask = last_usermask; - na->last_realname = u->realname; - if (Config->NSAddAccessOnReg) - na->nc->AddAccess(create_mask(u)); - - u->Login(na->nc); - - Log(LOG_COMMAND, u, this) << "to register " << na->nick << " (email: " << (!na->nc->email.empty() ? na->nc->email : "none") << ")"; - - FOREACH_MOD(I_OnNickRegister, OnNickRegister(na)); - - if (Config->NSAddAccessOnReg) - source.Reply(_("Nickname \002%s\002 registered under your account: %s"), u->nick.c_str(), na->nc->GetAccess(0).c_str()); - else - source.Reply(_("Nickname \002%s\002 registered."), u->nick.c_str()); - - Anope::string tmp_pass; - if (enc_decrypt(na->nc->pass, tmp_pass) == 1) - source.Reply(_("Your password is \002%s\002 - remember this for later use."), tmp_pass.c_str()); - - if (Config->NSEmailReg) - { - na->nc->SetFlag(NI_UNCONFIRMED); - if (SendRegmail(u, na, source.owner)) - { - source.Reply(_("A passcode has been sent to %s, please type %s%s confirm <passcode> to confirm your email address."), email.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - source.Reply(_("If you do not confirm your email address within %s your account will expire."), duration(Config->NSUnconfirmedExpire).c_str()); - } - } - else - ircdproto->SendAccountLogin(u, u->Account()); - ircdproto->SetAutoIdentificationToken(u); - - u->lastnickreg = Anope::CurTime; - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply("\n"); - source.Reply(_("Registers your nickname in the %s database. Once\n" - "your nick is registered, you can use the \002SET\002 and \002ACCESS\002\n" - "commands to configure your nick's settings as you like\n" - "them. Make sure you remember the password you use when\n" - "registering - you'll need it to make changes to your nick\n" - "later. (Note that \002case matters!\002 \037ANOPE\037, \037Anope\037, and \n" - "\037anope\037 are all different passwords!)\n" - " \n" - "Guidelines on choosing passwords:\n" - " \n" - "Passwords should not be easily guessable. For example,\n" - "using your real name as a password is a bad idea. Using\n" - "your nickname as a password is a much worse idea ;) and,\n" - "in fact, %s will not allow it. Also, short\n" - "passwords are vulnerable to trial-and-error searches, so\n" - "you should choose a password at least 5 characters long.\n" - "Finally, the space character cannot be used in passwords.\n"), - Config->NickServ.c_str(), Config->NickServ.c_str()); - - if (!Config->NSForceEmail) - source.Reply(_(" \n" - "The parameter \037email\037 is optional and will set the email\n" - "for your nick immediately.\n" - "Your privacy is respected; this e-mail won't be given to\n" - "any third-party person.\n" - " \n")); - - source.Reply(_("This command also creates a new group for your nickname,\n" - "that will allow you to register other nicks later sharing\n" - "the same configuration, the same set of memos and the\n" - "same channel privileges.")); - return true; - } -}; - -class CommandNSResend : public Command -{ - public: - CommandNSResend(Module *creator) : Command(creator, "nickserv/resend", 0, 0) - { - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!Config->NSEmailReg) - return; - - User *u = source.u; - NickAlias *na = findnick(u->nick); - - if (na == NULL) - source.Reply(NICK_NOT_REGISTERED); - else if (na->nc != u->Account() || u->Account()->HasFlag(NI_UNCONFIRMED) == false) - source.Reply(_("Your account is already confirmed.")); - else - { - if (Anope::CurTime < u->Account()->lastmail + Config->NSResendDelay) - source.Reply(_("Cannot send mail now; please retry a little later.")); - else if (!SendRegmail(u, na, source.owner)) - { - na->nc->lastmail = Anope::CurTime; - source.Reply(_("Your passcode has been re-sent to %s."), na->nc->email.c_str()); - Log(LOG_COMMAND, u, this) << "to resend registration verification code"; - } - else - Log() << "Unable to resend registration verification code for " << u->nick; - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - if (!Config->NSEmailReg) - return false; - - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command will re-send the auth code (also called passcode)\n" - "to the e-mail address of the user whom is performing it.")); - return true; - } - - void OnServHelp(CommandSource &source) - { - if (Config->NSEmailReg) - source.Reply(" %-14s %s", this->name.c_str(),_("Resend the registration passcode")); - } -}; - -class NSRegister : public Module -{ - CommandNSRegister commandnsregister; - CommandNSConfirm commandnsconfirm; - CommandNSResend commandnsrsend; - - public: - NSRegister(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsregister(this), commandnsconfirm(this), commandnsrsend(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsregister); - ModuleManager::RegisterService(&commandnsconfirm); - ModuleManager::RegisterService(&commandnsrsend); - } -}; - -static bool SendRegmail(User *u, NickAlias *na, BotInfo *bi) -{ - Anope::string code; - if (na->nc->GetExtRegular<Anope::string>("ns_register_passcode", code) == false) - { - int chars[] = { - ' ', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', - 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', - 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', - 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', - 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' - }; - int idx, min = 1, max = 62; - for (idx = 0; idx < 9; ++idx) - code += chars[1 + static_cast<int>((static_cast<float>(max - min)) * getrandom16() / 65536.0) + min]; - na->nc->Extend("ns_register_passcode", new ExtensibleItemRegular<Anope::string>(code)); - } - - Anope::string subject = Anope::printf(_("Nickname Registration (%s)"), na->nick.c_str()); - Anope::string message = Anope::printf(_("Hi,\n" - " \n" - "You have requested to register the nickname %s on %s.\n" - "Please type \" %s%s confirm %s \" to complete registration.\n" - " \n" - "If you don't know why this mail was sent to you, please ignore it silently.\n" - " \n" - "%s administrators."), na->nick.c_str(), Config->NetworkName.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), code.c_str(), Config->NetworkName.c_str()); - - return Mail(u, na->nc, bi, subject, message); -} - -MODULE_INIT(NSRegister) diff --git a/modules/core/ns_release.cpp b/modules/core/ns_release.cpp deleted file mode 100644 index 20a3e295c..000000000 --- a/modules/core/ns_release.cpp +++ /dev/null @@ -1,110 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSRelease : public Command -{ - public: - CommandNSRelease(Module *creator) : Command(creator, "nickserv/release", 1, 2) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Regain custody of your nick after RECOVER")); - this->SetSyntax(_("\037nickname\037 [\037password\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - Anope::string pass = params.size() > 1 ? params[1] : ""; - NickAlias *na; - - if (!(na = findnick(nick))) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else if (na->nc->HasFlag(NI_SUSPENDED)) - source.Reply(NICK_X_SUSPENDED, na->nick.c_str()); - else if (!na->HasFlag(NS_HELD)) - source.Reply(_("Nick \002%s\002 isn't being held."), nick.c_str()); - else if (!pass.empty()) - { - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnCheckAuthentication, OnCheckAuthentication(this, &source, params, na->nc->display, pass)); - if (MOD_RESULT == EVENT_STOP) - return; - - if (MOD_RESULT == EVENT_ALLOW) - { - Log(LOG_COMMAND, u, this) << "released " << na->nick; - na->Release(); - source.Reply(_("Services' hold on your nick has been released.")); - } - else - { - source.Reply(ACCESS_DENIED); - Log(LOG_COMMAND, u, this) << "invalid password for " << nick; - bad_password(u); - } - } - else - { - if (u->Account() == na->nc || (!na->nc->HasFlag(NI_SECURE) && is_on_access(u, na->nc)) || - (!u->fingerprint.empty() && na->nc->FindCert(u->fingerprint))) - { - na->Release(); - source.Reply(_("Services' hold on your nick has been released.")); - } - else - source.Reply(ACCESS_DENIED); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - /* Convert Config->NSReleaseTimeout seconds to string format */ - Anope::string relstr = duration(Config->NSReleaseTimeout); - - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Instructs %s to remove any hold on your nickname\n" - "caused by automatic kill protection or use of the \002RECOVER\002\n" - "command. This holds lasts for %s;\n" - "This command gets rid of them sooner.\n" - " \n" - "In order to use the \002RELEASE\002 command for a nick, your\n" - "current address as shown in /WHOIS must be on that nick's\n" - "access list, you must be identified and in the group of\n" - "that nick, or you must supply the correct password for\n" - "the nickname."), Config->NickServ.c_str(), relstr.c_str()); - - - return true; - } -}; - -class NSRelease : public Module -{ - CommandNSRelease commandnsrelease; - - public: - NSRelease(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsrelease(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsrelease); - } -}; - -MODULE_INIT(NSRelease) diff --git a/modules/core/ns_resetpass.cpp b/modules/core/ns_resetpass.cpp deleted file mode 100644 index b0d40226f..000000000 --- a/modules/core/ns_resetpass.cpp +++ /dev/null @@ -1,152 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static bool SendResetEmail(User *u, NickAlias *na, BotInfo *bi); - -class CommandNSResetPass : public Command -{ - public: - CommandNSResetPass(Module *creator) : Command(creator, "nickserv/resetpass", 1, 1) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Helps you reset lost passwords")); - this->SetSyntax(_("\037nickname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na; - - if (Config->RestrictMail && (!u->Account() || !u->HasCommand("nickserv/nickserv/resetpass"))) - source.Reply(ACCESS_DENIED); - else if (!(na = findnick(params[0]))) - source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); - else - { - if (SendResetEmail(u, na, source.owner)) - { - Log(LOG_COMMAND, u, this) << "for " << na->nick << " (group: " << na->nc->display << ")"; - source.Reply(_("Password reset email for \002%s\002 has been sent."), na->nick.c_str()); - } - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sends a code key to the nickname with instructions on how to\n" - "reset their password.")); - return true; - } -}; - -class NSResetPass : public Module -{ - CommandNSResetPass commandnsresetpass; - - public: - NSResetPass(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsresetpass(this) - { - this->SetAuthor("Anope"); - - if (!Config->UseMail) - throw ModuleException("Not using mail."); - - ModuleManager::RegisterService(&commandnsresetpass); - - ModuleManager::Attach(I_OnPreCommand, this); - } - - EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector<Anope::string> ¶ms) - { - if (command->name == "nickserv/confirm" && params.size() > 1) - { - User *u = source.u; - NickAlias *na = findnick(params[0]); - - time_t t; - Anope::string c; - if (na && na->nc->GetExtRegular("ns_resetpass_code", c) && na->nc->GetExtRegular("ns_resetpass_time", t)) - { - const Anope::string &passcode = params[1]; - if (t < Anope::CurTime - 3600) - { - na->nc->Shrink("ns_resetpass_code"); - na->nc->Shrink("ns_resetpass_time"); - source.Reply(_("Your password reset request has expired.")); - } - else if (passcode.equals_cs(c)) - { - na->nc->Shrink("ns_resetpass_code"); - na->nc->Shrink("ns_resetpass_time"); - - Log(LOG_COMMAND, u, &commandnsresetpass) << "confirmed RESETPASS to forcefully identify to " << na->nick; - - na->nc->UnsetFlag(NI_UNCONFIRMED); - u->Identify(na); - - source.Reply(_("You are now identified for your nick. Change your passwor now.")); - - } - else - return EVENT_CONTINUE; - - return EVENT_STOP; - } - } - - return EVENT_CONTINUE; - } -}; - -static bool SendResetEmail(User *u, NickAlias *na, BotInfo *bi) -{ - int min = 1, max = 62; - int chars[] = { - ' ', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', - 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', - 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', - 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', - 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' - }; - - Anope::string passcode; - int idx; - for (idx = 0; idx < 20; ++idx) - passcode += chars[1 + static_cast<int>((static_cast<float>(max - min)) * getrandom16() / 65536.0) + min]; - - Anope::string subject = Anope::printf(translate(na->nc, _("Reset password request for %s")), na->nick.c_str()); - Anope::string message = Anope::printf(translate(na->nc, _( - "Hi,\n" - " \n" - "You have requested to have the password for %s reset.\n" - "To reset your password, type %s%s CONFIRM %s %s\n" - " \n" - "If you don't know why this mail was sent to you, please ignore it silently.\n" - " \n" - "%s administrators.")), na->nick.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), na->nick.c_str(), passcode.c_str(), Config->NetworkName.c_str()); - - na->nc->Extend("ns_resetpass_code", new ExtensibleItemRegular<Anope::string>(passcode)); - na->nc->Extend("ns_resetpass_time", new ExtensibleItemRegular<time_t>(Anope::CurTime)); - - return Mail(u, na->nc, bi, subject, message); -} - -MODULE_INIT(NSResetPass) diff --git a/modules/core/ns_saset.cpp b/modules/core/ns_saset.cpp deleted file mode 100644 index a4aa2f422..000000000 --- a/modules/core/ns_saset.cpp +++ /dev/null @@ -1,173 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSASet : public Command -{ - public: - CommandNSSASet(Module *creator) : Command(creator, "nickserv/saset", 2, 4) - { - this->SetDesc(_("Set SET-options on another nickname")); - this->SetSyntax(_("\037option\037 \037nickname\037 \037parameters\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->OnSyntaxError(source, ""); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(_("Sets various nickname options. \037option\037 can be one of:")); - Anope::string this_name = source.command; - for (BotInfo::command_map::iterator it = source.owner->commands.begin(), it_end = source.owner->commands.end(); it != it_end; ++it) - { - const Anope::string &c_name = it->first; - CommandInfo &info = it->second; - - if (c_name.find_ci(this_name + " ") == 0) - { - service_reference<Command> command(info.name); - if (command) - { - source.command = c_name; - command->OnServHelp(source); - } - } - } - source.Reply(_("Type \002%s%s HELP SASET \037option\037\002 for more information\n" - "on a specific option. The options will be set on the given\n" - "\037nickname\037."), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str()); - return true; - } -}; - -class CommandNSSASetDisplay : public Command -{ - public: - CommandNSSASetDisplay(Module *creator) : Command(creator, "nickserv/saset/display", 2, 2) - { - this->SetDesc(_("Set the display of the group in Services")); - this->SetSyntax(_("\037nickname\037 \037new-display\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - NickAlias *setter_na = findnick(params[0]); - if (setter_na == NULL) - { - source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); - return; - } - NickCore *nc = setter_na->nc; - - NickAlias *na = findnick(params[1]); - if (!na || na->nc != nc) - { - source.Reply(_("The new display for \002%s\002 MUST be a nickname of the nickname group!"), nc->display.c_str()); - return; - } - - change_core_display(nc, params[1]); - source.Reply(NICK_SET_DISPLAY_CHANGED, nc->display.c_str()); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(_("Changes the display used to refer to the nickname group in \n" - "Services. The new display MUST be a nick of the group.")); - return true; - } -}; - -class CommandNSSASetPassword : public Command -{ - public: - CommandNSSASetPassword(Module *creator) : Command(creator, "nickserv/saset/password", 2, 2) - { - this->SetDesc(_("Set the nickname password")); - this->SetSyntax(_("\037nickname\037 \037new-password\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *setter_na = findnick(params[0]); - if (setter_na == NULL) - { - source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); - return; - } - NickCore *nc = setter_na->nc; - - size_t len = params[1].length(); - - if (Config->NSSecureAdmins && u->Account() != nc && nc->IsServicesOper()) - { - source.Reply(ACCESS_DENIED); - return; - } - else if (nc->display.equals_ci(params[1]) || (Config->StrictPasswords && len < 5)) - { - source.Reply(MORE_OBSCURE_PASSWORD); - return; - } - else if (len > Config->PassLen) - { - source.Reply(PASSWORD_TOO_LONG); - return; - } - - enc_encrypt(params[1], nc->pass); - Anope::string tmp_pass; - if (enc_decrypt(nc->pass, tmp_pass) == 1) - source.Reply(_("Password for \002%s\002 changed to \002%s\002."), nc->display.c_str(), tmp_pass.c_str()); - else - source.Reply(_("Password for \002%s\002 changed."), nc->display.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the password used to identify as the nick's owner.")); - return true; - } -}; - -class NSSASet : public Module -{ - CommandNSSASet commandnssaset; - CommandNSSASetDisplay commandnssasetdisplay; - CommandNSSASetPassword commandnssasetpassword; - - public: - NSSASet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssaset(this), commandnssasetdisplay(this), commandnssasetpassword(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssaset); - ModuleManager::RegisterService(&commandnssasetdisplay); - ModuleManager::RegisterService(&commandnssasetpassword); - } -}; - -MODULE_INIT(NSSASet) diff --git a/modules/core/ns_saset_noexpire.cpp b/modules/core/ns_saset_noexpire.cpp deleted file mode 100644 index 1bff9b461..000000000 --- a/modules/core/ns_saset_noexpire.cpp +++ /dev/null @@ -1,76 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSASetNoexpire : public Command -{ - public: - CommandNSSASetNoexpire(Module *creator) : Command(creator, "nickserv/saset/noexpire", 1, 2) - { - this->SetDesc(_("Prevent the nickname from expiring")); - this->SetSyntax(_("\037nickname\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - NickAlias *na = findnick(params[0]); - if (na == NULL) - { - source.Reply(NICK_X_NOT_REGISTERED, params[0].c_str()); - return; - } - - Anope::string param = params.size() > 1 ? params[1] : ""; - - if (param.equals_ci("ON")) - { - na->SetFlag(NS_NO_EXPIRE); - source.Reply(_("Nick %s \002will not\002 expire."), na->nick.c_str()); - } - else if (param.equals_ci("OFF")) - { - na->UnsetFlag(NS_NO_EXPIRE); - source.Reply(_("Nick %s \002will\002 expire."), na->nick.c_str()); - } - else - this->OnSyntaxError(source, "NOEXPIRE"); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets whether the given nickname will expire. Setting this\n" - "to \002ON\002 prevents the nickname from expiring.")); - return true; - } -}; - -class NSSASetNoexpire : public Module -{ - CommandNSSASetNoexpire commandnssasetnoexpire; - - public: - NSSASetNoexpire(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssasetnoexpire(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssasetnoexpire); - } -}; - -MODULE_INIT(NSSASetNoexpire) diff --git a/modules/core/ns_sendpass.cpp b/modules/core/ns_sendpass.cpp deleted file mode 100644 index ca185c68b..000000000 --- a/modules/core/ns_sendpass.cpp +++ /dev/null @@ -1,108 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static bool SendPassMail(User *u, NickAlias *na, BotInfo *bi, const Anope::string &pass); - -class CommandNSSendPass : public Command -{ - public: - CommandNSSendPass(Module *creator) : Command(creator, "nickserv/sendpass", 1, 1) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Forgot your password? Try this")); - this->SetSyntax(_("\037nickname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - NickAlias *na; - - if (Config->RestrictMail && (!u->Account() || !u->HasCommand("nickserv/sendpass"))) - source.Reply(ACCESS_DENIED); - else if (!(na = findnick(nick))) - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - else - { - Anope::string tmp_pass; - if (enc_decrypt(na->nc->pass, tmp_pass) == 1) - { - if (SendPassMail(u, na, source.owner, tmp_pass)) - { - Log(Config->RestrictMail ? LOG_ADMIN : LOG_COMMAND, u, this) << "for " << na->nick; - source.Reply(_("Password of \002%s\002 has been sent."), nick.c_str()); - } - } - else - source.Reply(_("SENDPASS command unavailable because encryption is in use.")); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Send the password of the given nickname to the e-mail address\n" - "set in the nickname record. This command is really useful\n" - "to deal with lost passwords.\n" - " \n" - "May be limited to \002IRC operators\002 on certain networks.")); - return true; - } -}; - -class NSSendPass : public Module -{ - CommandNSSendPass commandnssendpass; - - public: - NSSendPass(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssendpass(this) - { - this->SetAuthor("Anope"); - - if (!Config->UseMail) - throw ModuleException("Not using mail."); - - Anope::string tmp_pass = "plain:tmp"; - if (enc_decrypt(tmp_pass, tmp_pass) == -1) - throw ModuleException("Incompatible with the encryption module being used"); - - ModuleManager::RegisterService(&commandnssendpass); - } -}; - -static bool SendPassMail(User *u, NickAlias *na, BotInfo *bi, const Anope::string &pass) -{ - char subject[BUFSIZE], message[BUFSIZE]; - - snprintf(subject, sizeof(subject), translate(na->nc, _("Nickname password (%s)")), na->nick.c_str()); - snprintf(message, sizeof(message), translate(na->nc, _( - "Hi,\n" - " \n" - "You have requested to receive the password of nickname %s by e-mail.\n" - "The password is %s. For security purposes, you should change it as soon as you receive this mail.\n" - " \n" - "If you don't know why this mail was sent to you, please ignore it silently.\n" - " \n" - "%s administrators.")), na->nick.c_str(), pass.c_str(), Config->NetworkName.c_str()); - - return Mail(u, na->nc, bi, subject, message); -} - -MODULE_INIT(NSSendPass) diff --git a/modules/core/ns_set.cpp b/modules/core/ns_set.cpp deleted file mode 100644 index ad7acb5a4..000000000 --- a/modules/core/ns_set.cpp +++ /dev/null @@ -1,158 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSet : public Command -{ - public: - CommandNSSet(Module *creator) : Command(creator, "nickserv/set", 1, 3) - { - this->SetDesc(_("Set options, including kill protection")); - this->SetSyntax(_("\037option\037 \037parameters\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->OnSyntaxError(source, ""); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets various nickname options. \037option\037 can be one of:")); - Anope::string this_name = source.command; - for (BotInfo::command_map::iterator it = source.owner->commands.begin(), it_end = source.owner->commands.end(); it != it_end; ++it) - { - const Anope::string &c_name = it->first; - CommandInfo &info = it->second; - - if (c_name.find_ci(this_name + " ") == 0) - { - service_reference<Command> command(info.name); - if (command) - { - source.command = c_name; - command->OnServHelp(source); - } - } - } - source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n" - "on a specific option."), Config->UseStrictPrivMsgString.c_str(), source.owner->nick.c_str(), source.command.c_str()); - return true; - } -}; - -class CommandNSSetDisplay : public Command -{ - public: - CommandNSSetDisplay(Module *creator) : Command(creator, "nickserv/set/display", 1) - { - this->SetDesc(_("Set the display of your group in Services")); - this->SetSyntax(_("\037new-display\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na = findnick(params[1]); - - if (!na || na->nc != u->Account()) - { - source.Reply(_("The new display MUST be a nickname of your nickname group!")); - return; - } - - change_core_display(u->Account(), params[1]); - source.Reply(NICK_SET_DISPLAY_CHANGED, u->Account()->display.c_str()); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the display used to refer to your nickname group in \n" - "Services. The new display MUST be a nick of your group.")); - return true; - } -}; - -class CommandNSSetPassword : public Command -{ - public: - CommandNSSetPassword(Module *creator) : Command(creator, "nickserv/set/password", 1) - { - this->SetDesc(_("Set your nickname password")); - this->SetSyntax(_("\037new-password\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string ¶m = params[1]; - unsigned len = param.length(); - - if (u->Account()->display.equals_ci(param) || (Config->StrictPasswords && len < 5)) - { - source.Reply(MORE_OBSCURE_PASSWORD); - return; - } - else if (len > Config->PassLen) - { - source.Reply(PASSWORD_TOO_LONG); - return; - } - - enc_encrypt(param, u->Account()->pass); - Anope::string tmp_pass; - if (enc_decrypt(u->Account()->pass, tmp_pass) == 1) - source.Reply(_("Password for \002%s\002 changed to \002%s\002."), u->Account()->display.c_str(), tmp_pass.c_str()); - else - source.Reply(_("Password for \002%s\002 changed."), u->Account()->display.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the password used to identify you as the nick's\n" - "owner.")); - return true; - } -}; - -class NSSet : public Module -{ - CommandNSSet commandnsset; - CommandNSSetDisplay commandnssetdisplay; - CommandNSSetPassword commandnssetpassword; - - public: - NSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsset(this), commandnssetdisplay(this), commandnssetpassword(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsset); - ModuleManager::RegisterService(&commandnssetdisplay); - ModuleManager::RegisterService(&commandnssetpassword); - } -}; - -MODULE_INIT(NSSet) diff --git a/modules/core/ns_set_autoop.cpp b/modules/core/ns_set_autoop.cpp deleted file mode 100644 index ff178141f..000000000 --- a/modules/core/ns_set_autoop.cpp +++ /dev/null @@ -1,107 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetAutoOp : public Command -{ - public: - CommandNSSetAutoOp(Module *creator, const Anope::string &sname = "nickserv/set/autoop", size_t min = 1) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Should services op you automatically.")); - this->SetSyntax(_("{ON | OFF}")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (na == NULL) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (param.equals_ci("ON")) - { - nc->SetFlag(NI_AUTOOP); - source.Reply(_("Services will now autoop %s in channels."), nc->display.c_str()); - } - else if (param.equals_ci("OFF")) - { - nc->UnsetFlag(NI_AUTOOP); - source.Reply(_("Services will no longer autoop %s in channels."), nc->display.c_str()); - } - else - this->OnSyntaxError(source, "AUTOOP"); - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params[0]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets whether you will be opped automatically. Set to ON to \n" - "allow ChanServ to op you automatically when entering channels.")); - return true; - } -}; - -class CommandNSSASetAutoOp : public CommandNSSetAutoOp -{ - public: - CommandNSSASetAutoOp(Module *creator) : CommandNSSetAutoOp(creator, "nickserv/saset/autoop", 2) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params[1]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets whether the given nickname will be opped automatically.\n" - "Set to \002ON\002 to allow ChanServ to op the given nickname \n" - "omatically when joining channels.")); - return true; - } -}; - -class NSSetAutoOp : public Module -{ - CommandNSSetAutoOp commandnssetautoop; - CommandNSSASetAutoOp commandnssasetautoop; - - public: - NSSetAutoOp(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetautoop(this), commandnssasetautoop(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetautoop); - ModuleManager::RegisterService(&commandnssasetautoop); - } -}; - -MODULE_INIT(NSSetAutoOp) diff --git a/modules/core/ns_set_email.cpp b/modules/core/ns_set_email.cpp deleted file mode 100644 index f0914eb51..000000000 --- a/modules/core/ns_set_email.cpp +++ /dev/null @@ -1,186 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static bool SendConfirmMail(User *u, BotInfo *bi) -{ - int chars[] = { - ' ', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', - 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', - 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', - 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', - 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' - }; - int idx, min = 1, max = 62; - Anope::string code; - for (idx = 0; idx < 9; ++idx) - code += chars[1 + static_cast<int>((static_cast<float>(max - min)) * getrandom16() / 65536.0) + min]; - u->Account()->Extend("ns_set_email_passcode", new ExtensibleItemRegular<Anope::string>(code)); - - Anope::string subject = _("Email confirmation"); - Anope::string message = Anope::printf(_("Hi,\n" - " \n" - "You have requested to change your email address to %s.\n" - "Please type \" %s%s confirm %s \" to confirm this change.\n" - " \n" - "If you don't know why this mail was sent to you, please ignore it silently.\n" - " \n" - "%s administrators."), u->Account()->email.c_str(), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str(), code.c_str(), Config->NetworkName.c_str()); - - return Mail(u, u->Account(), bi, subject, message); -} - -class CommandNSSetEmail : public Command -{ - public: - CommandNSSetEmail(Module *creator, const Anope::string &cname = "nickserv/set/email", size_t min = 0) : Command(creator, cname, min, min + 1) - { - this->SetDesc(_("Associate an E-mail address with your nickname")); - this->SetSyntax(_("\037address\037")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - User *u = source.u; - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (param.empty() && Config->NSForceEmail) - { - source.Reply(_("You cannot unset the e-mail on this network.")); - return; - } - else if (Config->NSSecureAdmins && u->Account() != nc && nc->IsServicesOper()) - { - source.Reply(ACCESS_DENIED); - return; - } - else if (!param.empty() && !MailValidate(param)) - { - source.Reply(MAIL_X_INVALID, param.c_str()); - return; - } - - if (!param.empty() && Config->NSConfirmEmailChanges && !u->IsServicesOper()) - { - u->Account()->Extend("ns_set_email", new ExtensibleItemRegular<Anope::string>(param)); - Anope::string old = u->Account()->email; - u->Account()->email = param; - if (SendConfirmMail(u, source.owner)) - source.Reply(_("A confirmation email has been sent to \002%s\002. Follow the instructions in it to change your email address."), param.c_str()); - u->Account()->email = old; - } - else - { - if (!param.empty()) - { - nc->email = param; - source.Reply(_("E-mail address for \002%s\002 changed to \002%s\002."), nc->display.c_str(), param.c_str()); - } - else - { - nc->email.clear(); - source.Reply(_("E-mail address for \002%s\002 unset."), nc->display.c_str()); - } - } - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params.size() ? params[0] : ""); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Associates the given E-mail address with your nickname.\n" - "This address will be displayed whenever someone requests\n" - "information on the nickname with the \002INFO\002 command.")); - return true; - } -}; - -class CommandNSSASetEmail : public CommandNSSetEmail -{ - public: - CommandNSSASetEmail(Module *creator) : CommandNSSetEmail(creator, "nickserv/saset/email", 2) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 \037address\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params.size() > 1 ? params[1] : ""); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Associates the given E-mail address with the nickname.")); - return true; - } -}; - -class NSSetEmail : public Module -{ - CommandNSSetEmail commandnssetemail; - CommandNSSASetEmail commandnssasetemail; - - public: - NSSetEmail(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetemail(this), commandnssasetemail(this) - { - this->SetAuthor("Anope"); - - ModuleManager::Attach(I_OnPreCommand, this); - - ModuleManager::RegisterService(&commandnssetemail); - ModuleManager::RegisterService(&commandnssasetemail); - } - - EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector<Anope::string> ¶ms) - { - User *u = source.u; - if (command->name == "nickserv/confirm" && !params.empty() && u->IsIdentified()) - { - Anope::string new_email, passcode; - if (u->Account()->GetExtRegular("ns_set_email", new_email) && u->Account()->GetExtRegular("ns_set_email_passcode", passcode)) - { - if (params[0] == passcode) - { - u->Account()->email = new_email; - Log(LOG_COMMAND, u, command) << "to confirm their email address change to " << u->Account()->email; - source.Reply(_("Your email address has been changed to \002%s\002."), u->Account()->email.c_str()); - u->Account()->Shrink("ns_set_email"); - u->Account()->Shrink("ns_set_email_passcode"); - return EVENT_STOP; - } - } - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(NSSetEmail) diff --git a/modules/core/ns_set_greet.cpp b/modules/core/ns_set_greet.cpp deleted file mode 100644 index 03bcd3834..000000000 --- a/modules/core/ns_set_greet.cpp +++ /dev/null @@ -1,108 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetGreet : public Command -{ - public: - CommandNSSetGreet(Module *creator, const Anope::string &sname = "nickserv/set/greet", size_t min = 0) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Associate a greet message with your nickname")); - this->SetSyntax(_("\037message\037")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (!param.empty()) - { - nc->greet = param; - source.Reply(_("Greet message for \002%s\002 changed to \002%s\002."), nc->display.c_str(), nc->greet.c_str()); - } - else - { - nc->greet.clear(); - source.Reply(_("Greet message for \002%s\002 unset."), nc->display.c_str()); - } - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params.size() > 0 ? params[0] : ""); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Makes the given message the greet of your nickname, that\n" - "will be displayed when joining a channel that has GREET\n" - "option enabled, provided that you have the necessary \n" - "access on it.")); - return true; - } -}; - -class CommandNSSASetGreet : public CommandNSSetGreet -{ - public: - CommandNSSASetGreet(Module *creator) : CommandNSSetGreet(creator, "nickserv/saset/greet", 1) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 \037message\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params.size() > 1 ? params[1] : ""); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Makes the given message the greet of the nickname, that\n" - "will be displayed when joining a channel that has GREET\n" - "option enabled, provided that the user has the necessary \n" - "access on it.")); - return true; - } -}; - -class NSSetGreet : public Module -{ - CommandNSSetGreet commandnssetgreet; - CommandNSSASetGreet commandnssasetgreet; - - public: - NSSetGreet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetgreet(this), commandnssasetgreet(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetgreet); - ModuleManager::RegisterService(&commandnssasetgreet); - } -}; - -MODULE_INIT(NSSetGreet) diff --git a/modules/core/ns_set_hide.cpp b/modules/core/ns_set_hide.cpp deleted file mode 100644 index e0fb0e85e..000000000 --- a/modules/core/ns_set_hide.cpp +++ /dev/null @@ -1,149 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetHide : public Command -{ - public: - CommandNSSetHide(Module *creator, const Anope::string &sname = "nickserv/set/hide", size_t min = 2) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Hide certain pieces of nickname information")); - this->SetSyntax(_("{EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m, const Anope::string &arg) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - Anope::string onmsg, offmsg; - NickCoreFlag flag; - - if (param.equals_ci("EMAIL")) - { - flag = NI_HIDE_EMAIL; - onmsg = _("The E-mail address of \002%s\002 will now be hidden from %s INFO displays."); - offmsg = _("The E-mail address of \002%s\002 will now be shown in %s INFO displays."); - } - else if (param.equals_ci("USERMASK")) - { - flag = NI_HIDE_MASK; - onmsg = _("The last seen user@host mask of \002%s\002 will now be hidden from %s INFO displays."); - offmsg = _("The last seen user@host mask of \002%s\002 will now be shown in %s INFO displays."); - } - else if (param.equals_ci("STATUS")) - { - flag = NI_HIDE_STATUS; - onmsg = _("The services access status of \002%s\002 will now be hidden from %s INFO displays."); - offmsg = _("The services access status of \002%s\002 will now be shown in %s INFO displays."); - } - else if (param.equals_ci("QUIT")) - { - flag = NI_HIDE_QUIT; - onmsg = _("The last quit message of \002%s\002 will now be hidden from %s INFO displays."); - offmsg = _("The last quit message of \002%s\002 will now be shown in %s INFO displays."); - } - else - { - this->OnSyntaxError(source, "HIDE"); - return; - } - - if (arg.equals_ci("ON")) - { - nc->SetFlag(flag); - source.Reply(onmsg.c_str(), nc->display.c_str(), Config->NickServ.c_str()); - } - else if (arg.equals_ci("OFF")) - { - nc->UnsetFlag(flag); - source.Reply(offmsg.c_str(), nc->display.c_str(), Config->NickServ.c_str()); - } - else - this->OnSyntaxError(source, "HIDE"); - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params[0], params[1]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to prevent certain pieces of information from\n" - "being displayed when someone does a %s \002INFO\002 on your\n" - "nick. You can hide your E-mail address (\002EMAIL\002), last seen\n" - "user@host mask (\002USERMASK\002), your services access status\n" - "(\002STATUS\002) and last quit message (\002QUIT\002).\n" - "The second parameter specifies whether the information should\n" - "be displayed (\002OFF\002) or hidden (\002ON\002)."), Config->NickServ.c_str()); - return true; - } -}; - -class CommandNSSASetHide : public CommandNSSetHide -{ - public: - CommandNSSASetHide(Module *creator) : CommandNSSetHide(creator, "nickserv/saset/hide", 3) - { - this->SetSyntax("\037nickname\037 {EMAIL | STATUS | USERMASK | QUIT} {ON | OFF}"); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->ClearSyntax(); - this->Run(source, params[0], params[1], params[2]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to prevent certain pieces of information from\n" - "being displayed when someone does a %s \002INFO\002 on the\n" - "nick. You can hide the E-mail address (\002EMAIL\002), last seen\n" - "user@host mask (\002USERMASK\002), the services access status\n" - "(\002STATUS\002) and last quit message (\002QUIT\002).\n" - "The second parameter specifies whether the information should\n" - "be displayed (\002OFF\002) or hidden (\002ON\002)."), Config->NickServ.c_str()); - return true; - } -}; - -class NSSetHide : public Module -{ - CommandNSSetHide commandnssethide; - CommandNSSASetHide commandnssasethide; - - public: - NSSetHide(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssethide(this), commandnssasethide(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssethide); - ModuleManager::RegisterService(&commandnssasethide); - } -}; - -MODULE_INIT(NSSetHide) diff --git a/modules/core/ns_set_kill.cpp b/modules/core/ns_set_kill.cpp deleted file mode 100644 index f57a93893..000000000 --- a/modules/core/ns_set_kill.cpp +++ /dev/null @@ -1,149 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetKill : public Command -{ - public: - CommandNSSetKill(Module *creator, const Anope::string &sname = "nickserv/set/kill", size_t min = 1) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Turn protection on or off")); - this->SetSyntax(_("{ON | QUICK | IMMED | OFF}")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (param.equals_ci("ON")) - { - nc->SetFlag(NI_KILLPROTECT); - nc->UnsetFlag(NI_KILL_QUICK); - nc->UnsetFlag(NI_KILL_IMMED); - source.Reply(_("Protection is now \002on\002 for \002%s\002."), nc->display.c_str()); - } - else if (param.equals_ci("QUICK")) - { - nc->SetFlag(NI_KILLPROTECT); - nc->SetFlag(NI_KILL_QUICK); - nc->UnsetFlag(NI_KILL_IMMED); - source.Reply(_("Protection is now \002on\002 for \002%s\002, with a reduced delay."), nc->display.c_str()); - } - else if (param.equals_ci("IMMED")) - { - if (Config->NSAllowKillImmed) - { - nc->SetFlag(NI_KILLPROTECT); - nc->SetFlag(NI_KILL_IMMED); - nc->UnsetFlag(NI_KILL_QUICK); - source.Reply(_("Protection is now \002on\002 for \002%s\002, with no delay."), nc->display.c_str()); - } - else - source.Reply(_("The \002IMMED\002 option is not available on this network.")); - } - else if (param.equals_ci("OFF")) - { - nc->UnsetFlag(NI_KILLPROTECT); - nc->UnsetFlag(NI_KILL_QUICK); - nc->UnsetFlag(NI_KILL_IMMED); - source.Reply(_("Protection is now \002off\002 for \002%s\002."), nc->display.c_str()); - } - else - this->OnSyntaxError(source, "KILL"); - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params[0]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Turns the automatic protection option for your nick\n" - "on or off. With protection on, if another user\n" - "tries to take your nick, they will be given one minute to\n" - "change to another nick, after which %s will forcibly change\n" - "their nick.\n" - " \n" - "If you select \002QUICK\002, the user will be given only 20 seconds\n" - "to change nicks instead of the usual 60. If you select\n" - "\002IMMED\002, user's nick will be changed immediately \037without\037 being\n" - "warned first or given a chance to change their nick; please\n" - "do not use this option unless necessary. Also, your\n" - "network's administrators may have disabled this option."), Config->NickServ.c_str()); - return true; - } -}; - -class CommandNSSASetKill : public CommandNSSetKill -{ - public: - CommandNSSASetKill(Module *creator) : CommandNSSetKill(creator, "nickserv/saset/kill", 2) - { - this->SetSyntax(_("\037nickname\037 {ON | QUICK | IMMED | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->ClearSyntax(); - this->Run(source, params[0], params[1]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Turns the automatic protection option for the nick\n" - "on or off. With protection on, if another user\n" - "tries to take the nick, they will be given one minute to\n" - "change to another nick, after which %s will forcibly change\n" - "their nick.\n" - " \n" - "If you select \002QUICK\002, the user will be given only 20 seconds\n" - "to change nicks instead of the usual 60. If you select\n" - "\002IMMED\002, the user's nick will be changed immediately \037without\037 being\n" - "warned first or given a chance to change their nick; please\n" - "do not use this option unless necessary. Also, your\n" - "network's administrators may have disabled this option."), Config->NickServ.c_str()); - return true; - } -}; - -class NSSetKill : public Module -{ - CommandNSSetKill commandnssetkill; - CommandNSSASetKill commandnssasetkill; - - public: - NSSetKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetkill(this), commandnssasetkill(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetkill); - ModuleManager::RegisterService(&commandnssasetkill); - } -}; - -MODULE_INIT(NSSetKill) diff --git a/modules/core/ns_set_language.cpp b/modules/core/ns_set_language.cpp deleted file mode 100644 index 3429ad688..000000000 --- a/modules/core/ns_set_language.cpp +++ /dev/null @@ -1,121 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetLanguage : public Command -{ - public: - CommandNSSetLanguage(Module *creator, const Anope::string &sname = "nickserv/set/language", size_t min = 1) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Set the language Services will use when messaging you")); - this->SetSyntax(_("\037language\037")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - for (unsigned j = 0; j < languages.size(); ++j) - { - if (param == "en" || languages[j] == param) - break; - else if (j + 1 == languages.size()) - { - this->OnSyntaxError(source, ""); - return; - } - } - - nc->language = param != "en" ? param : ""; - source.Reply(_("Language changed to \002English\002.")); - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶m) - { - this->Run(source, source.u->Account()->display, param[0]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the language Services uses when sending messages to\n" - "you (for example, when responding to a command you send).\n" - "\037language\037 should be chosen from the following list of\n" - "supported languages:")); - - source.Reply(" en (English)"); - for (unsigned j = 0; j < languages.size(); ++j) - { - const Anope::string &langname = anope_gettext(languages[j].c_str(), _("English")); - if (langname == "English") - continue; - source.Reply(" %s (%s)", languages[j].c_str(), langname.c_str()); - } - - return true; - } -}; - -class CommandNSSASetLanguage : public CommandNSSetLanguage -{ - public: - CommandNSSASetLanguage(Module *creator) : CommandNSSetLanguage(creator, "nickserv/saset/language", 2) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 \037language\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params[1]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Changes the language Services uses when sending messages to\n" - "you (for example, when responding to a command you send).\n" - "\037language\037 should be chosen from the following list of\n" - "supported languages:")); - return true; - } -}; - -class NSSetLanguage : public Module -{ - CommandNSSetLanguage commandnssetlanguage; - CommandNSSASetLanguage commandnssasetlanguage; - - public: - NSSetLanguage(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetlanguage(this), commandnssasetlanguage(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetlanguage); - ModuleManager::RegisterService(&commandnssasetlanguage); - } -}; - -MODULE_INIT(NSSetLanguage) diff --git a/modules/core/ns_set_message.cpp b/modules/core/ns_set_message.cpp deleted file mode 100644 index 677002c78..000000000 --- a/modules/core/ns_set_message.cpp +++ /dev/null @@ -1,114 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetMessage : public Command -{ - public: - CommandNSSetMessage(Module *creator, const Anope::string &sname = "nickserv/set/message", size_t min = 1) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Change the communication method of Services")); - this->SetSyntax(_("{ON | OFF}")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (!Config->UsePrivmsg) - { - source.Reply(_("Option \002%s\02 cannot be set on this network."), "MSG"); - return; - } - - if (param.equals_ci("ON")) - { - nc->SetFlag(NI_MSG); - source.Reply(_("Services will now reply to \002%s\002 with \002messages\002."), nc->display.c_str()); - } - else if (param.equals_ci("OFF")) - { - nc->UnsetFlag(NI_MSG); - source.Reply(_("Services will now reply to \002%s\002 with \002notices\002."), nc->display.c_str()); - } - else - this->OnSyntaxError(source, "MSG"); - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params[0]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to choose the way Services are communicating with \n" - "you. With \002MSG\002 set, Services will use messages, else they'll \n" - "use notices.")); - return true; - } -}; - -class CommandNSSASetMessage : public CommandNSSetMessage -{ - public: - CommandNSSASetMessage(Module *creator) : CommandNSSetMessage(creator, "nickserv/saset/message", 2) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 {ON | OFF}")); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to choose the way Services are communicating with \n" - "the given user. With \002MSG\002 set, Services will use messages,\n" - "else they'll use notices.")); - return true; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params[1]); - } -}; - -class NSSetMessage : public Module -{ - CommandNSSetMessage commandnssetmessage; - CommandNSSASetMessage commandnssasetmessage; - - public: - NSSetMessage(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetmessage(this), commandnssasetmessage(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetmessage); - ModuleManager::RegisterService(&commandnssasetmessage); - } -}; - -MODULE_INIT(NSSetMessage) diff --git a/modules/core/ns_set_private.cpp b/modules/core/ns_set_private.cpp deleted file mode 100644 index 63fec57d6..000000000 --- a/modules/core/ns_set_private.cpp +++ /dev/null @@ -1,114 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetPrivate : public Command -{ - public: - CommandNSSetPrivate(Module *creator, const Anope::string &sname = "nickserv/set/private", size_t min = 1) : Command(creator, sname, min, min + 1) - { - this->SetDesc(Anope::printf(_("Prevent the nickname from appearing in a \002%s%s LIST\002"), Config->UseStrictPrivMsgString.c_str(), Config->NickServ.c_str())); - this->SetSyntax(_("{ON | OFF}")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (param.equals_ci("ON")) - { - nc->SetFlag(NI_PRIVATE); - source.Reply(_("Private option is now \002on\002 for \002%s\002."), nc->display.c_str()); - } - else if (param.equals_ci("OFF")) - { - nc->UnsetFlag(NI_PRIVATE); - source.Reply(_("Private option is now \002off\002 for \002%s\002."), nc->display.c_str()); - } - else - this->OnSyntaxError(source, "PRIVATE"); - - return; - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params[0]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Turns %s's privacy option on or off for your nick.\n" - "With \002PRIVATE\002 set, your nickname will not appear in\n" - "nickname lists generated with %s's \002LIST\002 command.\n" - "(However, anyone who knows your nickname can still get\n" - "information on it using the \002INFO\002 command.)"), - Config->NickServ.c_str(), Config->NickServ.c_str()); - return true; - } -}; - -class CommandNSSASetPrivate : public CommandNSSetPrivate -{ - public: - CommandNSSASetPrivate(Module *creator) : CommandNSSetPrivate(creator, "nickserv/saset/private", 2) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params[1]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Turns %s's privacy option on or off for the nick.\n" - "With \002PRIVATE\002 set, the nickname will not appear in\n" - "nickname lists generated with %s's \002LIST\002 command.\n" - "(However, anyone who knows the nickname can still get\n" - "information on it using the \002INFO\002 command.)"), - Config->NickServ.c_str(), Config->NickServ.c_str()); - return true; - } -}; - -class NSSetPrivate : public Module -{ - CommandNSSetPrivate commandnssetprivate; - CommandNSSASetPrivate commandnssasetprivate; - - public: - NSSetPrivate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetprivate(this), commandnssasetprivate(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetprivate); - ModuleManager::RegisterService(&commandnssasetprivate); - } -}; - -MODULE_INIT(NSSetPrivate) diff --git a/modules/core/ns_set_secure.cpp b/modules/core/ns_set_secure.cpp deleted file mode 100644 index 31314a5a5..000000000 --- a/modules/core/ns_set_secure.cpp +++ /dev/null @@ -1,114 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSetSecure : public Command -{ - public: - CommandNSSetSecure(Module *creator, const Anope::string &sname = "nickserv/set/secure", size_t min = 1) : Command(creator, sname, min, min + 1) - { - this->SetDesc(_("Turn nickname security on or off")); - this->SetSyntax(_("{ON | OFF}")); - } - - void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m) - { - NickAlias *na = findnick(user); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, user.c_str()); - return; - } - NickCore *nc = na->nc; - - if (param.equals_ci("ON")) - { - nc->SetFlag(NI_SECURE); - source.Reply(_("Secure option is now \002on\002 for \002%s\002."), nc->display.c_str()); - } - else if (param.equals_ci("OFF")) - { - nc->UnsetFlag(NI_SECURE); - source.Reply(_("Secure option is now \002off\002 for \002%s\002."), nc->display.c_str()); - } - else - this->OnSyntaxError(source, "SECURE"); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, source.u->Account()->display, params[0]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Turns %s's security features on or off for your\n" - "nick. With \002SECURE\002 set, you must enter your password\n" - "before you will be recognized as the owner of the nick,\n" - "regardless of whether your address is on the access\n" - "list. However, if you are on the access list, %s\n" - "will not auto-kill you regardless of the setting of the\n" - "\002KILL\002 option."), Config->NickServ.c_str(), Config->NickServ.c_str()); - return true; - } -}; - -class CommandNSSASetSecure : public CommandNSSetSecure -{ - public: - CommandNSSASetSecure(Module *creator) : CommandNSSetSecure(creator, "nickserv/saset/secure", 2) - { - this->ClearSyntax(); - this->SetSyntax(_("\037nickname\037 {ON | OFF}")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - this->Run(source, params[0], params[1]); - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Turns %s's security features on or off for your\n" - "nick. With \002SECURE\002 set, you must enter your password\n" - "before you will be recognized as the owner of the nick,\n" - "regardless of whether your address is on the access\n" - "list. However, if you are on the access list, %s\n" - "will not auto-kill you regardless of the setting of the\n" - "\002KILL\002 option."), Config->NickServ.c_str(), Config->NickServ.c_str()); - return true; - } -}; - -class NSSetSecure : public Module -{ - CommandNSSetSecure commandnssetsecure; - CommandNSSASetSecure commandnssasetsecure; - - public: - NSSetSecure(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssetsecure(this), commandnssasetsecure(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssetsecure); - ModuleManager::RegisterService(&commandnssasetsecure); - } -}; - -MODULE_INIT(NSSetSecure) diff --git a/modules/core/ns_status.cpp b/modules/core/ns_status.cpp deleted file mode 100644 index 9d8b58fcb..000000000 --- a/modules/core/ns_status.cpp +++ /dev/null @@ -1,94 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSStatus : public Command -{ - public: - CommandNSStatus(Module *creator) : Command(creator, "nickserv/status", 0, 16) - { - this->SetFlag(CFLAG_ALLOW_UNREGISTERED); - this->SetDesc(_("Returns the owner status of the given nickname")); - this->SetSyntax(_("\037nickname\037...")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = !params.empty() ? params[0] : u->nick; - NickAlias *na = findnick(nick); - spacesepstream sep(nick); - Anope::string nickbuf; - - while (sep.GetToken(nickbuf)) - { - User *u2 = finduser(nickbuf); - if (!u2) /* Nick is not online */ - source.Reply(_("STATUS %s %d %s"), nickbuf.c_str(), 0, ""); - else if (u2->IsIdentified() && na && na->nc == u2->Account()) /* Nick is identified */ - source.Reply(_("STATUS %s %d %s"), nickbuf.c_str(), 3, u2->Account()->display.c_str()); - else if (u2->IsRecognized()) /* Nick is recognised, but NOT identified */ - source.Reply(_("STATUS %s %d %s"), nickbuf.c_str(), 2, u2->Account() ? u2->Account()->display.c_str() : ""); - else if (!na) /* Nick is online, but NOT a registered */ - source.Reply(_("STATUS %s %d %s"), nickbuf.c_str(), 0, ""); - else - /* Nick is not identified for the nick, but they could be logged into an account, - * so we tell the user about it - */ - source.Reply(_("STATUS %s %d %s"), nickbuf.c_str(), 1, u2->Account() ? u2->Account()->display.c_str() : ""); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Returns whether the user using the given nickname is\n" - "recognized as the owner of the nickname. The response has\n" - "this format:\n" - " \n" - " \037nickname\037 \037status-code\037 \037account\037\n" - " \n" - "where \037nickname\037 is the nickname sent with the command,\n" - "\037status-code\037 is one of the following, and \037account\037\n" - "is the account they are logged in as.\n" - " \n" - " 0 - no such user online \002or\002 nickname not registered\n" - " 1 - user not recognized as nickname's owner\n" - " 2 - user recognized as owner via access list only\n" - " 3 - user recognized as owner via password identification\n" - " \n" - "Up to sixteen nicknames may be sent with each command; the\n" - "rest will be ignored. If no nickname is given, your status\n" - "will be returned.")); - return true; - } -}; - -class NSStatus : public Module -{ - CommandNSStatus commandnsstatus; - - public: - NSStatus(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsstatus(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsstatus); - } -}; - -MODULE_INIT(NSStatus) diff --git a/modules/core/ns_suspend.cpp b/modules/core/ns_suspend.cpp deleted file mode 100644 index 50cf039ce..000000000 --- a/modules/core/ns_suspend.cpp +++ /dev/null @@ -1,160 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSSuspend : public Command -{ - public: - CommandNSSuspend(Module *creator) : Command(creator, "nickserv/suspend", 2, 2) - { - this->SetDesc(_("Suspend a given nick")); - this->SetSyntax(_("\037nickname\037 \037reason\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - const Anope::string &nick = params[0]; - const Anope::string &reason = params[1]; - - if (readonly) - { - source.Reply(READ_ONLY_MODE); - return; - } - - NickAlias *na = findnick(nick); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - return; - } - - if (Config->NSSecureAdmins && na->nc->IsServicesOper()) - { - source.Reply(ACCESS_DENIED); - return; - } - - na->nc->SetFlag(NI_SUSPENDED); - na->nc->SetFlag(NI_SECURE); - na->nc->UnsetFlag(NI_KILLPROTECT); - na->nc->UnsetFlag(NI_KILL_QUICK); - na->nc->UnsetFlag(NI_KILL_IMMED); - - for (std::list<NickAlias *>::iterator it = na->nc->aliases.begin(), it_end = na->nc->aliases.end(); it != it_end; ++it) - { - NickAlias *na2 = *it; - - if (na2->nc == na->nc) - { - na2->last_quit = reason; - - User *u2 = finduser(na2->nick); - if (u2) - { - u2->Logout(); - u2->Collide(na2); - } - } - } - - Log(LOG_ADMIN, u, this) << "for " << nick << " (" << (!reason.empty() ? reason : "No reason") << ")"; - source.Reply(_("Nick %s is now suspended."), nick.c_str()); - - FOREACH_MOD(I_OnNickSuspended, OnNickSuspend(na)); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Suspends a registered nickname, which prevents from being used\n" - "while keeping all the data for that nick.")); - return true; - } -}; - -class CommandNSUnSuspend : public Command -{ - public: - CommandNSUnSuspend(Module *creator) : Command(creator, "nickserv/unsuspend", 1, 1) - { - this->SetDesc(_("Unsuspend a given nick")); - this->SetSyntax(_("\037nickname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - - if (readonly) - { - source.Reply(READ_ONLY_MODE); - return; - } - - NickAlias *na = findnick(nick); - if (!na) - { - source.Reply(NICK_X_NOT_REGISTERED, nick.c_str()); - return; - } - - if (Config->NSSecureAdmins && na->nc->IsServicesOper()) - { - source.Reply(ACCESS_DENIED); - return; - } - - na->nc->UnsetFlag(NI_SUSPENDED); - - Log(LOG_ADMIN, u, this) << "for " << na->nick; - source.Reply(_("Nick %s is now released."), nick.c_str()); - - FOREACH_MOD(I_OnNickUnsuspended, OnNickUnsuspended(na)); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Unsuspends a nickname which allows it to be used again.")); - return true; - } -}; - -class NSSuspend : public Module -{ - CommandNSSuspend commandnssuspend; - CommandNSUnSuspend commandnsunsuspend; - - public: - NSSuspend(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnssuspend(this), commandnsunsuspend(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnssuspend); - ModuleManager::RegisterService(&commandnsunsuspend); - } -}; - -MODULE_INIT(NSSuspend) diff --git a/modules/core/ns_update.cpp b/modules/core/ns_update.cpp deleted file mode 100644 index d870e3532..000000000 --- a/modules/core/ns_update.cpp +++ /dev/null @@ -1,70 +0,0 @@ -/* NickServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandNSUpdate : public Command -{ - public: - CommandNSUpdate(Module *creator) : Command(creator, "nickserv/update", 0, 0) - { - this->SetDesc(_("Updates your current status, i.e. it checks for new memos")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - NickAlias *na = findnick(u->nick); - - if (!na) - { - source.Reply(NICK_NOT_REGISTERED); - return; - } - - na->last_realname = u->realname; - na->last_seen = Anope::CurTime; - - FOREACH_MOD(I_OnNickUpdate, OnNickUpdate(u)); - - source.Reply(_("Status updated (memos, vhost, chmodes, flags)."), Config->NickServ.c_str()); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Updates your current status, i.e. it checks for new memos,\n" - "sets needed channel modes and updates your vhost and\n" - "your userflags (lastseentime, etc).")); - return true; - } -}; - -class NSUpdate : public Module -{ - CommandNSUpdate commandnsupdate; - - public: - NSUpdate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandnsupdate(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandnsupdate); - } -}; - -MODULE_INIT(NSUpdate) diff --git a/modules/core/os_akill.cpp b/modules/core/os_akill.cpp deleted file mode 100644 index 05602a746..000000000 --- a/modules/core/os_akill.cpp +++ /dev/null @@ -1,464 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static service_reference<XLineManager> akills("xlinemanager/sgline"); - -class AkillDelCallback : public NumberList -{ - CommandSource &source; - unsigned Deleted; - public: - AkillDelCallback(CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, true), source(_source), Deleted(0) - { - } - - ~AkillDelCallback() - { - if (!Deleted) - source.Reply(_("No matching entries on the AKILL list.")); - else if (Deleted == 1) - source.Reply(_("Deleted 1 entry from the AKILL list.")); - else - source.Reply(_("Deleted %d entries from the AKILL list."), Deleted); - } - - void HandleNumber(unsigned Number) - { - if (!Number) - return; - - XLine *x = akills->GetEntry(Number - 1); - - if (!x) - return; - - ++Deleted; - DoDel(source, x); - } - - static void DoDel(CommandSource &source, XLine *x) - { - akills->DelXLine(x); - } -}; - -class AkillListCallback : public NumberList -{ - protected: - CommandSource &source; - bool SentHeader; - public: - AkillListCallback(CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, false), source(_source), SentHeader(false) - { - } - - ~AkillListCallback() - { - if (!SentHeader) - source.Reply(_("No matching entries on the AKILL list.")); - else - source.Reply(END_OF_ANY_LIST, "Akill"); - } - - void HandleNumber(unsigned Number) - { - if (!Number) - return; - - XLine *x = akills->GetEntry(Number - 1); - - if (!x) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current AKILL list:\n" - " Num Mask Reason")); - } - - DoList(source, x, Number); - } - - static void DoList(CommandSource &source, XLine *x, unsigned Number) - { - source.Reply(OPER_LIST_FORMAT, Number + 1, x->Mask.c_str(), x->Reason.c_str()); - } -}; - -class AkillViewCallback : public AkillListCallback -{ - public: - AkillViewCallback(CommandSource &_source, const Anope::string &numlist) : AkillListCallback(_source, numlist) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number) - return; - - XLine *x = akills->GetEntry(Number - 1); - - if (!x) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current AKILL list:")); - } - - DoList(source, x, Number); - } - - static void DoList(CommandSource &source, XLine *x, unsigned Number) - { - source.Reply(OPER_VIEW_FORMAT, Number + 1, x->Mask.c_str(), x->By.c_str(), do_strftime(x->Created).c_str(), expire_left(source.u->Account(), x->Expires).c_str(), x->Reason.c_str()); - } -}; - -class CommandOSAKill : public Command -{ - private: - void DoAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - unsigned last_param = 2; - Anope::string expiry, mask; - time_t expires; - - mask = params.size() > 1 ? params[1] : ""; - if (!mask.empty() && mask[0] == '+') - { - expiry = mask; - mask = params.size() > 2 ? params[2] : ""; - last_param = 3; - } - - expires = !expiry.empty() ? dotime(expiry) : Config->AutokillExpiry; - /* If the expiry given does not contain a final letter, it's in days, - * said the doc. Ah well. - */ - if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) - expires *= 86400; - /* Do not allow less than a minute expiry time */ - if (expires && expires < 60) - { - source.Reply(BAD_EXPIRY_TIME); - return; - } - else if (expires > 0) - expires += Anope::CurTime; - - if (params.size() <= last_param) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - Anope::string reason = params[last_param]; - if (last_param == 2 && params.size() > 3) - reason += " " + params[3]; - if (!mask.empty() && !reason.empty()) - { - std::pair<int, XLine *> canAdd = akills->CanAdd(mask, expires); - if (mask.find('!') != Anope::string::npos) - source.Reply(_("\002Reminder\002: AKILL masks cannot contain nicknames; make sure you have \002not\002 included a nick portion in your mask.")); - else if (mask.find('@') == Anope::string::npos) - source.Reply(BAD_USERHOST_MASK); - else if (mask.find_first_not_of("~@.*?") == Anope::string::npos) - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - else if (canAdd.first == 1) - source.Reply(_("\002%s\002 already exists on the AKILL list."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 2) - source.Reply(_("Expiry time of \002%s\002 changed."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 3) - source.Reply(_("\002%s\002 is already covered by %s."), mask.c_str(), canAdd.second->Mask.c_str()); - else - { - User *user = finduser(mask); - if (user) - mask = "*@" + user->host; - unsigned int affected = 0; - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) - if (Anope::Match(it->second->GetIdent() + "@" + it->second->host, mask)) - ++affected; - float percent = static_cast<float>(affected) / static_cast<float>(UserListByNick.size()) * 100.0; - - if (percent > 95) - { - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - Log(LOG_ADMIN, u, this) << "tried to akill " << percent << "% of the network (" << affected << " users)"; - return; - } - - XLine *x = akills->Add(mask, u->nick, expires, reason); - - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnAddXLine, OnAddXLine(u, x, akills)); - if (MOD_RESULT == EVENT_STOP) - { - delete x; - return; - } - - source.Reply(_("\002%s\002 added to the AKILL list."), mask.c_str()); - - Log(LOG_ADMIN, u, this) << "on " << mask << " (" << reason << ") expires in " << (expires ? duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; - - if (readonly) - source.Reply(READ_ONLY_MODE); - } - } - else - this->OnSyntaxError(source, "ADD"); - - return; - } - - void DoDel(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (mask.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (akills->GetList().empty()) - { - source.Reply(_("AKILL list is empty.")); - return; - } - - if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AkillDelCallback list(source, mask); - list.Process(); - } - else - { - XLine *x = akills->HasEntry(mask); - - if (!x) - { - source.Reply(_("\002%s\002 not found on the AKILL list."), mask.c_str()); - return; - } - - FOREACH_MOD(I_OnDelXLine, OnDelXLine(u, x, akills)); - - AkillDelCallback::DoDel(source, x); - source.Reply(_("\002%s\002 deleted from the AKILL list."), mask.c_str()); - } - - if (readonly) - source.Reply(READ_ONLY_MODE); - - return; - } - - void DoList(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (akills->GetList().empty()) - { - source.Reply(_("AKILL list is empty.")); - return; - } - - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AkillListCallback list(source, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = akills->GetCount(); i < end; ++i) - { - XLine *x = akills->GetEntry(i); - - if (mask.empty() || mask.equals_ci(x->Mask) || Anope::Match(x->Mask, mask)) - { - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current AKILL list:\n" - " Num Mask Reason")); - } - - AkillListCallback::DoList(source, x, i); - } - } - - if (!SentHeader) - source.Reply(_("No matching entries on the AKILL list.")); - else - source.Reply(END_OF_ANY_LIST, "Akill"); - } - - return; - } - - void DoView(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (akills->GetList().empty()) - { - source.Reply(_("AKILL list is empty.")); - return; - } - - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - AkillViewCallback list(source, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = akills->GetCount(); i < end; ++i) - { - XLine *x = akills->GetEntry(i); - - if (mask.empty() || mask.equals_ci(x->Mask) || Anope::Match(x->Mask, mask)) - { - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current AKILL list:")); - } - - AkillViewCallback::DoList(source, x, i); - } - } - - if (!SentHeader) - source.Reply(_("No matching entries on the AKILL list.")); - } - - return; - } - - void DoClear(CommandSource &source) - { - User *u = source.u; - FOREACH_MOD(I_OnDelXLine, OnDelXLine(u, NULL, akills)); - akills->Clear(); - source.Reply(_("The AKILL list has been cleared.")); - - return; - } - public: - CommandOSAKill(Module *creator) : Command(creator, "operserv/akill", 1, 4) - { - this->SetDesc(_("Manipulate the AKILL list")); - this->SetSyntax(_("ADD [+\037expiry\037] \037mask\037 \037reason\037")); - this->SetSyntax(_("DEL {\037mask\037 | \037entry-num\037 | \037list\037}")); - this->SetSyntax(_("LIST [\037mask\037 | \037list\037]")); - this->SetSyntax(_("VIEW [\037mask\037 | \037list\037]")); - this->SetSyntax(_("CLEAR")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[0]; - - if (!akills) - return; - - if (cmd.equals_ci("ADD")) - return this->DoAdd(source, params); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, params); - else if (cmd.equals_ci("LIST")) - return this->DoList(source, params); - else if (cmd.equals_ci("VIEW")) - return this->DoView(source, params); - else if (cmd.equals_ci("CLEAR")) - return this->DoClear(source); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services operators to manipulate the AKILL list. If\n" - "a user matching an AKILL mask attempts to connect, Services\n" - "will issue a KILL for that user and, on supported server\n" - "types, will instruct all servers to add a ban (K-line) for\n" - "the mask which the user matched.\n" - " \n" - "\002AKILL ADD\002 adds the given nick or user@host/ip mask to the AKILL\n" - "list for the given reason (which \002must\002 be given).\n" - "\037expiry\037 is specified as an integer followed by one of \037d\037 \n" - "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as \n" - "\0371h30m\037) are not permitted. If a unit specifier is not \n" - "included, the default is days (so \037+30\037 by itself means 30 \n" - "days). To add an AKILL which does not expire, use \037+0\037. If the\n" - "usermask to be added starts with a \037+\037, an expiry time must\n" - "be given, even if it is the same as the default. The\n" - "current AKILL default expiry time can be found with the\n" - "\002STATS AKILL\002 command.\n" - " \n" - "The \002AKILL DEL\002 command removes the given mask from the\n" - "AKILL list if it is present. If a list of entry numbers is \n" - "given, those entries are deleted. (See the example for LIST \n" - "below.)\n" - " \n" - "The \002AKILL LIST\002 command displays the AKILL list. \n" - "If a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002AKILL LIST 2-5,7-9\002\n" - " Lists AKILL entries numbered 2 through 5 and 7 \n" - " through 9.\n" - " \n" - "\002AKILL VIEW\002 is a more verbose version of \002AKILL LIST\002, and \n" - "will show who added an AKILL, the date it was added, and when \n" - "it expires, as well as the user@host/ip mask and reason.\n" - " \n" - "\002AKILL CLEAR\002 clears all entries of the AKILL list.")); - return true; - } -}; - -class OSAKill : public Module -{ - CommandOSAKill commandosakill; - - public: - OSAKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosakill(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosakill); - } -}; - -MODULE_INIT(OSAKill) diff --git a/modules/core/os_chankill.cpp b/modules/core/os_chankill.cpp deleted file mode 100644 index 9ce895c59..000000000 --- a/modules/core/os_chankill.cpp +++ /dev/null @@ -1,120 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static service_reference<XLineManager> akills("xlinemanager/sgline"); - -class CommandOSChanKill : public Command -{ - public: - CommandOSChanKill(Module *creator) : Command(creator, "operserv/chankill", 2, 3) - { - this->SetDesc(_("AKILL all users on a specific channel")); - this->SetSyntax(_("[+\037expiry\037] \037channel\037 \037reason\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!akills) - return; - - User *u = source.u; - Anope::string expiry, channel; - time_t expires; - unsigned last_param = 1; - Channel *c; - - channel = params[0]; - if (!channel.empty() && channel[0] == '+') - { - expiry = channel; - channel = params[1]; - last_param = 2; - } - - expires = !expiry.empty() ? dotime(expiry) : Config->ChankillExpiry; - if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) - expires *= 86400; - if (expires && expires < 60) - { - source.Reply(BAD_EXPIRY_TIME); - return; - } - else if (expires > 0) - expires += Anope::CurTime; - - if (params.size() <= last_param) - { - this->OnSyntaxError(source, ""); - return; - } - - Anope::string reason = params[last_param]; - if (params.size() > last_param + 1) - reason += params[last_param + 1]; - if (!reason.empty()) - { - Anope::string realreason; - if (Config->AddAkiller) - realreason = "[" + u->nick + "] " + reason; - else - realreason = reason; - - if ((c = findchan(channel))) - { - for (CUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ) - { - UserContainer *uc = *it++; - - if (uc->user->HasMode(UMODE_OPER)) - continue; - - akills->Add("*@" + uc->user->host, u->nick, expires, realreason); - akills->Check(uc->user); - } - - Log(LOG_ADMIN, u, this) << "(" << realreason << ")"; - } - else - source.Reply(CHAN_X_NOT_IN_USE, channel.c_str()); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Puts an AKILL for every nick on the specified channel. It\n" - "uses the entire and complete real ident@host for every nick,\n" - "then enforces the AKILL.")); - return true; - } -}; - -class OSChanKill : public Module -{ - CommandOSChanKill commandoschankill; - - public: - OSChanKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandoschankill(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandoschankill); - } -}; - -MODULE_INIT(OSChanKill) diff --git a/modules/core/os_config.cpp b/modules/core/os_config.cpp deleted file mode 100644 index 1d1fead33..000000000 --- a/modules/core/os_config.cpp +++ /dev/null @@ -1,217 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSConfig : public Command -{ - void ChangeHash(ConfigDataHash &hash, const Anope::string &block, const Anope::string &iname, const Anope::string &value) - { - ConfigDataHash::iterator it = hash.find(block); - - KeyValList &list = it->second; - for (unsigned i = 0; i < list.size(); ++i) - { - const Anope::string &item = list[i].first; - if (item == iname) - { - list[i] = std::make_pair(item, value); - break; - } - } - } - - public: - CommandOSConfig(Module *creator) : Command(creator, "operserv/config", 1, 4) - { - this->SetDesc(_("View and change configuration file settings")); - this->SetSyntax(_("{\037MODIFY\037|\037VIEW\037} [\037block name\037 \037item name\037 \037item value\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &what = params[0]; - - if (what.equals_ci("MODIFY") && params.size() > 3) - { - ConfigItems configitems(Config); - - for (unsigned i = 0; !configitems.Values[i].tag.empty(); ++i) - { - ConfigItems::Item *v = &configitems.Values[i]; - if (v->tag.equals_cs(params[1]) && v->value.equals_cs(params[2])) - { - try - { - ValueItem vi(params[3]); - if (!v->validation_function(Config, v->tag, v->value, vi)) - throw ConfigException("Parameter failed to validate."); - - int dt = v->datatype; - - if (dt & DT_NORELOAD) - throw ConfigException("This item can not be changed while Anope is running."); - bool allow_wild = dt & DT_ALLOW_WILD; - dt &= ~(DT_ALLOW_NEWLINE | DT_ALLOW_WILD); - - /* Yay for *massive* copypaste from config.cpp */ - switch (dt) - { - case DT_NOSPACES: - { - ValueContainerString *vcs = debug_cast<ValueContainerString *>(v->val); - Config->ValidateNoSpaces(vi.GetValue(), v->tag, v->value); - vcs->Set(vi.GetValue()); - break; - } - case DT_HOSTNAME: - { - ValueContainerString *vcs = debug_cast<ValueContainerString *>(v->val); - Config->ValidateHostname(vi.GetValue(), v->tag, v->value); - vcs->Set(vi.GetValue()); - break; - } - case DT_IPADDRESS: - { - ValueContainerString *vcs = debug_cast<ValueContainerString *>(v->val); - Config->ValidateIP(vi.GetValue(), v->tag, v->value, allow_wild); - vcs->Set(vi.GetValue()); - break; - } - case DT_STRING: - { - ValueContainerString *vcs = debug_cast<ValueContainerString *>(v->val); - vcs->Set(vi.GetValue()); - break; - } - case DT_INTEGER: - { - int val = vi.GetInteger(); - ValueContainerInt *vci = debug_cast<ValueContainerInt *>(v->val); - vci->Set(&val, sizeof(int)); - break; - } - case DT_UINTEGER: - { - unsigned val = vi.GetInteger(); - ValueContainerUInt *vci = debug_cast<ValueContainerUInt *>(v->val); - vci->Set(&val, sizeof(unsigned)); - break; - } - case DT_LUINTEGER: - { - unsigned long val = vi.GetInteger(); - ValueContainerLUInt *vci = debug_cast<ValueContainerLUInt *>(v->val); - vci->Set(&val, sizeof(unsigned long)); - break; - } - case DT_TIME: - { - time_t time = dotime(vi.GetValue()); - ValueContainerTime *vci = debug_cast<ValueContainerTime *>(v->val); - vci->Set(&time, sizeof(time_t)); - break; - } - case DT_BOOLEAN: - { - bool val = vi.GetBool(); - ValueContainerBool *vcb = debug_cast<ValueContainerBool *>(v->val); - vcb->Set(&val, sizeof(bool)); - break; - } - default: - break; - } - } - catch (const ConfigException &ex) - { - source.Reply(_("Error changing configuration value: ") + ex.GetReason()); - return; - } - - ChangeHash(Config->config_data, params[1], params[2], params[3]); - - Log(LOG_ADMIN, source.u, this) << "to change the configuration value of " << params[1] << ":" << params[2] << " to " << params[3]; - source.Reply(_("Value of %s:%s changed to %s"), params[1].c_str(), params[2].c_str(), params[3].c_str()); - return; - } - } - - source.Reply("There is no configuration value named %s:%s", params[1].c_str(), params[2].c_str()); - } - else if (what.equals_ci("VIEW")) - { - /* Blocks we should show */ - const Anope::string show_blocks[] = { "botserv", "chanserv", "defcon", "global", "memoserv", "nickserv", "networkinfo", "operserv", "options", "" }; - - Log(LOG_ADMIN, source.u, this) << "VIEW"; - - for (ConfigDataHash::const_iterator it = Config->config_data.begin(), it_end = Config->config_data.end(); it != it_end; ++it) - { - const Anope::string &bname = it->first; - const KeyValList &list = it->second; - - bool ok = false; - for (unsigned i = 0; !show_blocks[i].empty(); ++i) - if (bname == show_blocks[i]) - ok = true; - if (ok == false) - continue; - - source.Reply(_("%s settings:"), bname.c_str()); - for (unsigned i = 0; i < list.size(); ++i) - { - const Anope::string &first = list[i].first, second = list[i].second; - - source.Reply(_(" Name: %-15s Value: %s"), first.c_str(), second.c_str()); - } - } - - source.Reply(_("End of configuration.")); - } - else - this->OnSyntaxError(source, what); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to change and view configuration settings.\n" - "Settings changed by this command are temporary and will not be reflected\n" - "back into the configuration file, and will be lost if Anope is shut down,\n" - "restarted, or the RELOAD command is used.\n" - " \n" - "Example:\n" - " \002MODIFY nickserv forcemail no\002")); - return true; - } -}; - -class OSConfig : public Module -{ - CommandOSConfig commandosconfig; - - public: - OSConfig(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosconfig(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosconfig); - } -}; - -MODULE_INIT(OSConfig) diff --git a/modules/core/os_forbid.cpp b/modules/core/os_forbid.cpp deleted file mode 100644 index d4b4c2b41..000000000 --- a/modules/core/os_forbid.cpp +++ /dev/null @@ -1,342 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "os_forbid.h" - -class MyForbidService : public ForbidService -{ - std::vector<ForbidData *> forbidData; - - public: - MyForbidService(Module *m) : ForbidService(m) { } - - void AddForbid(ForbidData *d) - { - this->forbidData.push_back(d); - } - - void RemoveForbid(ForbidData *d) - { - std::vector<ForbidData *>::iterator it = std::find(this->forbidData.begin(), this->forbidData.end(), d); - if (it != this->forbidData.end()) - this->forbidData.erase(it); - delete d; - } - - ForbidData *FindForbid(const Anope::string &mask, ForbidType type) - { - const std::vector<ForbidData *> &forbids = this->GetForbids(); - for (unsigned i = forbids.size(); i > 0; --i) - { - ForbidData *d = this->forbidData[i - 1]; - - if ((type == FT_NONE || type == d->type) && Anope::Match(mask, d->mask)) - return d; - } - return NULL; - } - - const std::vector<ForbidData *> &GetForbids() - { - for (unsigned i = this->forbidData.size(); i > 0; --i) - { - ForbidData *d = this->forbidData[i - 1]; - - if (d->expires && Anope::CurTime >= d->expires) - { - Anope::string type = "none"; - if (d->type == FT_NICK) - type = "nick"; - else if (d->type == FT_CHAN) - type = "chan"; - else if (d->type == FT_EMAIL) - type = "email"; - - Log(LOG_NORMAL, Config->OperServ + "/forbid") << "Expiring forbid for " << d->mask << " type " << type; - this->forbidData.erase(this->forbidData.begin() + i - 1); - delete d; - } - } - - return this->forbidData; - } -}; - -class CommandOSForbid : public Command -{ - service_reference<ForbidService> fs; - public: - CommandOSForbid(Module *creator) : Command(creator, "operserv/forbid", 1, 5), fs("forbid") - { - this->SetDesc(_("Forbid usage of nicknames, channels, and emails")); - this->SetSyntax(_("ADD {NICK|CHAN|EMAIL} [+\037expiry\037] \037entry\037\002 [\037reason\037]")); - this->SetSyntax(_("DEL {NICK|CHAN|EMAIL} \037entry\037")); - this->SetSyntax(_("LIST (NICK|CHAN|EMAIL)")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!this->fs) - return; - - const Anope::string &command = params[0]; - const Anope::string &subcommand = params.size() > 1 ? params[1] : ""; - - ForbidType type = FT_NONE; - if (subcommand.equals_ci("NICK")) - type = FT_NICK; - else if (subcommand.equals_ci("CHAN")) - type = FT_CHAN; - else if (subcommand.equals_ci("EMAIL")) - type = FT_EMAIL; - - if (command.equals_ci("ADD") && params.size() > 2 && type != FT_NONE) - { - const Anope::string &expiry = params[2][0] == '+' ? params[2] : ""; - const Anope::string &entry = params.size() > 3 && !expiry.empty() ? params[3] : params[2]; - Anope::string reason = !expiry.empty() && params.size() > 4 ? params[4] : (params.size() > 3 ? params[3] : ""); - - time_t expiryt = 0; - if (!expiry.empty()) - { - expiryt = dotime(expiry); - if (expiryt) - expiryt += Anope::CurTime; - } - - ForbidData *d = this->fs->FindForbid(entry, type); - bool created = false; - if (d == NULL) - { - d = new ForbidData(); - created = true; - } - - d->mask = entry; - d->creator = source.u->nick; - d->reason = reason; - d->created = Anope::CurTime; - d->expires = expiryt; - d->type = type; - if (created) - this->fs->AddForbid(d); - - Log(LOG_ADMIN, source.u, this) << "to add a forbid on " << entry << " of type " << subcommand; - source.Reply(_("Added a%s forbid on %s to expire on %s"), type == FT_CHAN ? "n" : "", entry.c_str(), d->expires ? do_strftime(d->expires).c_str() : "never"); - } - else if (command.equals_ci("DEL") && params.size() > 2 && type != FT_NONE) - { - const Anope::string &entry = params[2]; - - ForbidData *d = this->fs->FindForbid(entry, type); - if (d != NULL) - { - Log(LOG_ADMIN, source.u, this) << "to remove forbid " << d->mask << " of type " << subcommand; - source.Reply(_("%s deleted from the %s forbid list."), d->mask.c_str(), subcommand.c_str()); - } - else - source.Reply(_("Forbid on %s was not found."), entry.c_str()); - } - else if (command.equals_ci("LIST")) - { - const std::vector<ForbidData *> &forbids = this->fs->GetForbids(); - if (forbids.empty()) - source.Reply(_("Forbid list is empty.")); - else - { - source.Reply(_("Forbid list:")); - source.Reply(_("Mask Type Reason")); - - for (unsigned i = 0; i < forbids.size(); ++i) - { - ForbidData *d = forbids[i]; - - Anope::string ftype; - if (d->type == FT_NICK) - ftype = "NICK"; - else if (d->type == FT_CHAN) - ftype = "CHAN"; - else if (d->type == FT_EMAIL) - ftype = "EMAIL"; - else - continue; - - source.Reply("%-10s %-5s %s", d->mask.c_str(), ftype.c_str(), d->reason.c_str()); - source.Reply(_("By %s, expires on %s"), d->creator.c_str(), d->expires ? do_strftime(d->expires).c_str() : "never"); - } - - source.Reply(_("End of forbid list.")); - } - } - else - this->OnSyntaxError(source, command); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Forbid allows you to forbid usage of certain nicknames, channels,\n" - "and email addresses. Wildcards are accepted for all entries.")); - return true; - } -}; - -class OSForbid : public Module -{ - MyForbidService forbidService; - CommandOSForbid commandosforbid; - - public: - OSForbid(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - forbidService(this), commandosforbid(this) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnUserConnect, I_OnUserNickChange, I_OnJoinChannel, I_OnPreCommand, I_OnDatabaseWrite, I_OnDatabaseRead }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&this->forbidService); - - ModuleManager::RegisterService(&commandosforbid); - } - - void OnUserConnect(dynamic_reference<User> &u, bool &exempt) - { - if (!u || exempt) - return; - - this->OnUserNickChange(u, ""); - } - - void OnUserNickChange(User *u, const Anope::string &) - { - if (u->HasMode(UMODE_OPER)) - return; - - ForbidData *d = this->forbidService.FindForbid(u->nick, FT_NICK); - if (d != NULL) - { - BotInfo *bi = findbot(Config->OperServ); - if (bi) - { - if (d->reason.empty()) - u->SendMessage(bi, _("This nickname has been forbidden.")); - else - u->SendMessage(bi, _("This nickname has been forbidden: %s"), d->reason.c_str()); - } - u->Collide(NULL); - } - } - - void OnJoinChannel(User *u, Channel *c) - { - if (u->HasMode(UMODE_OPER)) - return; - - BotInfo *bi = findbot(Config->OperServ); - ForbidData *d = this->forbidService.FindForbid(c->name, FT_CHAN); - if (bi != NULL && d != NULL) - { - if (!c->HasFlag(CH_INHABIT)) - { - /* Join ChanServ and set a timer for this channel to part ChanServ later */ - new ChanServTimer(c); - - /* Set +si to prevent rejoin */ - c->SetMode(NULL, CMODE_NOEXTERNAL); - c->SetMode(NULL, CMODE_TOPIC); - c->SetMode(NULL, CMODE_SECRET); - c->SetMode(NULL, CMODE_INVITE); - } - - if (d->reason.empty()) - c->Kick(bi, u, _("This channel has been forbidden.")); - else - c->Kick(bi, u, _("This channel has been forbidden: %s"), d->reason.c_str()); - } - } - - EventReturn OnPreCommand(CommandSource &source, Command *command, std::vector<Anope::string> ¶ms) - { - if (source.u->HasMode(UMODE_OPER)) - return EVENT_CONTINUE; - else if (command->name == "nickserv/register" && params.size() > 1) - { - ForbidData *d = this->forbidService.FindForbid(params[1], FT_EMAIL); - if (d != NULL) - { - source.Reply("Your email address is not allowed, choose a different one."); - return EVENT_STOP; - } - } - else if (command->name == "nickserv/set/email" && params.size() > 0) - { - ForbidData *d = this->forbidService.FindForbid(params[0], FT_EMAIL); - if (d != NULL) - { - source.Reply("Your email address is not allowed, choose a different one."); - return EVENT_STOP; - } - } - - return EVENT_CONTINUE; - } - - void OnDatabaseWrite(void (*Write)(const Anope::string &)) - { - std::vector<ForbidData *> forbids = this->forbidService.GetForbids(); - for (unsigned i = 0; i < forbids.size(); ++i) - { - ForbidData *f = forbids[i]; - Anope::string ftype; - if (f->type == FT_NICK) - ftype = "NICK"; - else if (f->type == FT_CHAN) - ftype = "CHAN"; - else if (f->type == FT_EMAIL) - ftype = "EMAIL"; - Write("FORBID " + f->mask + " " + f->creator + " " + stringify(f->created) + " " + stringify(f->expires) + " " + ftype + " " + f->reason); - } - } - - EventReturn OnDatabaseRead(const std::vector<Anope::string> ¶ms) - { - if (params.size() > 5 && params[0] == "FORBID") - { - ForbidData *f = new ForbidData(); - f->mask = params[1]; - f->creator = params[2]; - f->created = convertTo<time_t>(params[3]); - f->expires = convertTo<time_t>(params[4]); - if (params[5] == "NICK") - f->type = FT_NICK; - else if (params[5] == "CHAN") - f->type = FT_CHAN; - else if (params[5] == "EMAIL") - f->type = FT_EMAIL; - else - f->type = FT_NONE; - f->reason = params.size() > 6 ? params[6] : ""; - - this->forbidService.AddForbid(f); - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(OSForbid) diff --git a/modules/core/os_forbid.h b/modules/core/os_forbid.h deleted file mode 100644 index b91aa3be8..000000000 --- a/modules/core/os_forbid.h +++ /dev/null @@ -1,37 +0,0 @@ -#ifndef OS_FORBID_H -#define OS_FORBID_H - -enum ForbidType -{ - FT_NONE, - FT_NICK, - FT_CHAN, - FT_EMAIL -}; - -struct ForbidData -{ - Anope::string mask; - Anope::string creator; - Anope::string reason; - time_t created; - time_t expires; - ForbidType type; -}; - -class ForbidService : public Service -{ - public: - ForbidService(Module *m) : Service(m, "forbid") { } - - virtual void AddForbid(ForbidData *d) = 0; - - virtual void RemoveForbid(ForbidData *d) = 0; - - virtual ForbidData *FindForbid(const Anope::string &mask, ForbidType type) = 0; - - virtual const std::vector<ForbidData *> &GetForbids() = 0; -}; - -#endif - diff --git a/modules/core/os_ignore.cpp b/modules/core/os_ignore.cpp deleted file mode 100644 index 9f50ec967..000000000 --- a/modules/core/os_ignore.cpp +++ /dev/null @@ -1,350 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "os_ignore.h" - -class OSIgnoreService : public IgnoreService -{ - public: - OSIgnoreService(Module *o, const Anope::string &n) : IgnoreService(o, n) { } - - void AddIgnore(const Anope::string &mask, const Anope::string &creator, const Anope::string &reason, time_t delta = Anope::CurTime) - { - /* If it s an existing user, we ignore the hostmask. */ - Anope::string realmask = mask; - size_t user, host; - - User *u = finduser(mask); - if (u) - realmask = "*!*@" + u->host; - /* Determine whether we get a nick or a mask. */ - else if ((host = mask.find('@')) != Anope::string::npos) - { - /* Check whether we have a nick too.. */ - if ((user = mask.find('!')) != Anope::string::npos) - { - /* this should never happen */ - if (user > host) - return; - } - else - /* We have user@host. Add nick wildcard. */ - realmask = "*!" + mask; - } - /* We only got a nick.. */ - else - realmask = mask + "!*@*"; - - /* Check if we already got an identical entry. */ - IgnoreData *ign = this->Find(realmask); - if (ign != NULL) - { - if (!delta) - ign->time = 0; - else - ign->time = Anope::CurTime + delta; - } - /* Create new entry.. */ - else - { - IgnoreData newign; - newign.mask = realmask; - newign.creator = creator; - newign.reason = reason; - newign.time = delta ? Anope::CurTime + delta : 0; - this->ignores.push_back(newign); - } - } - - bool DelIgnore(const Anope::string &mask) - { - for (std::list<IgnoreData>::iterator it = this->ignores.begin(), it_end = this->ignores.end(); it != it_end; ++it) - { - IgnoreData &idn = *it; - if (idn.mask.equals_ci(mask)) - { - this->ignores.erase(it); - return true; - } - } - - return false; - } - - IgnoreData *Find(const Anope::string &mask) - { - User *u = finduser(mask); - std::list<IgnoreData>::iterator ign = this->ignores.begin(), ign_end = this->ignores.end(); - - if (u) - { - for (; ign != ign_end; ++ign) - { - Entry ignore_mask(CMODE_BEGIN, ign->mask); - if (ignore_mask.Matches(u)) - break; - } - } - else - { - size_t user, host; - Anope::string tmp; - /* We didn't get a user.. generate a valid mask. */ - if ((host = mask.find('@')) != Anope::string::npos) - { - if ((user = mask.find('!')) != Anope::string::npos) - { - /* this should never happen */ - if (user > host) - return NULL; - tmp = mask; - } - else - /* We have user@host. Add nick wildcard. */ - tmp = "*!" + mask; - } - /* We only got a nick.. */ - else - tmp = mask + "!*@*"; - - for (; ign != ign_end; ++ign) - if (Anope::Match(tmp, ign->mask)) - break; - } - - /* Check whether the entry has timed out */ - if (ign != ign_end)// && (*ign)->time && (*ign)->time <= Anope::CurTime) - { - IgnoreData &id = *ign; - - if (id.time && id.time <= Anope::CurTime) - { - Log(LOG_DEBUG) << "Expiring ignore entry " << id.mask; - this->ignores.erase(ign); - } - else - return &id; - } - - return NULL; - } -}; - -class CommandOSIgnore : public Command -{ - private: - void DoAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - service_reference<IgnoreService> ignore_service("ignore"); - if (!ignore_service) - return; - - const Anope::string &time = params.size() > 1 ? params[1] : ""; - const Anope::string &nick = params.size() > 2 ? params[2] : ""; - const Anope::string &reason = params.size() > 3 ? params[3] : ""; - - if (time.empty() || nick.empty()) - { - this->OnSyntaxError(source, "ADD"); - return; - } - else - { - time_t t = dotime(time); - - if (t <= -1) - { - source.Reply(_("You have to enter a valid number as time.")); - return; - } - - ignore_service->AddIgnore(nick, source.u->nick, reason, t); - if (!t) - source.Reply(_("\002%s\002 will now permanently be ignored."), nick.c_str()); - else - source.Reply(_("\002%s\002 will now be ignored for \002%s\002."), nick.c_str(), time.c_str()); - } - - return; - } - - void DoList(CommandSource &source) - { - service_reference<IgnoreService> ignore_service("ignore"); - if (!ignore_service) - return; - - const std::list<IgnoreData> &ignores = ignore_service->GetIgnores(); - if (ignores.empty()) - source.Reply(_("Ignore list is empty.")); - else - { - source.Reply(_("Services ignore list:\n" - " Mask Creator Reason Expires")); - for (std::list<IgnoreData>::const_iterator ign = ignores.begin(), ign_end = ignores.end(); ign != ign_end; ++ign) - { - const IgnoreData &ignore = *ign; - - source.Reply(" %-11s %-11s %-11s %s", ignore.mask.c_str(), ignore.creator.c_str(), ignore.reason.c_str(), do_strftime(ignore.time).c_str()); - } - } - - return; - } - - void DoDel(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - service_reference<IgnoreService> ignore_service("ignore"); - if (!ignore_service) - return; - - const Anope::string nick = params.size() > 1 ? params[1] : ""; - if (nick.empty()) - this->OnSyntaxError(source, "DEL"); - else if (ignore_service->DelIgnore(nick)) - source.Reply(_("\002%s\002 will no longer be ignored."), nick.c_str()); - else - source.Reply(_("Nick \002%s\002 not found on ignore list."), nick.c_str()); - - return; - } - - void DoClear(CommandSource &source) - { - service_reference<IgnoreService> ignore_service("ignore"); - if (!ignore_service) - return; - - ignore_service->ClearIgnores(); - source.Reply(_("Ignore list has been cleared.")); - - return; - } - - public: - CommandOSIgnore(Module *creator) : Command(creator, "operserv/ignore", 1, 4) - { - this->SetDesc(_("Modify the Services ignore list")); - this->SetSyntax(_("ADD \037time\037 \037nick\037 \037reason\037")); - this->SetSyntax(_("DEL \037nick\037")); - this->SetSyntax(_("LIST")); - this->SetSyntax(_("CLEAR")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[0]; - - if (cmd.equals_ci("ADD")) - return this->DoAdd(source, params); - else if (cmd.equals_ci("LIST")) - return this->DoList(source); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, params); - else if (cmd.equals_ci("CLEAR")) - return this->DoClear(source); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services Operators to make Services ignore a nick or mask\n" - "for a certain time or until the next restart. The default\n" - "time format is seconds. You can specify it by using units.\n" - "Valid units are: \037s\037 for seconds, \037m\037 for minutes, \n" - "\037h\037 for hours and \037d\037 for days. \n" - "Combinations of these units are not permitted.\n" - "To make Services permanently ignore the user, type 0 as time.\n" - "When adding a \037mask\037, it should be in the format user@host\n" - "or nick!user@host, everything else will be considered a nick.\n" - "Wildcards are permitted.\n" - " \n" - "Ignores will not be enforced on IRC Operators.")); - return true; - } -}; - -class OSIgnore : public Module -{ - OSIgnoreService osignoreservice; - CommandOSIgnore commandosignore; - - public: - OSIgnore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - osignoreservice(this, "ignore"), commandosignore(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosignore); - - Implementation i[] = { I_OnDatabaseRead, I_OnDatabaseWrite, I_OnBotPrivmsg }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&this->osignoreservice); - } - - EventReturn OnDatabaseRead(const std::vector<Anope::string> ¶ms) - { - if (params.size() >= 4 && params[0].equals_ci("OS") && params[1].equals_ci("IGNORE")) - { - service_reference<IgnoreService> ignore_service("ignore"); - if (ignore_service) - { - const Anope::string &mask = params[2]; - time_t time = params[3].is_pos_number_only() ? convertTo<time_t>(params[3]) : 0; - const Anope::string &creator = params.size() > 4 ? params[4] : ""; - const Anope::string &reason = params.size() > 5 ? params[5] : ""; - ignore_service->AddIgnore(mask, creator, reason, time - Anope::CurTime); - - return EVENT_STOP; - } - } - - return EVENT_CONTINUE; - } - - void OnDatabaseWrite(void (*Write)(const Anope::string &)) - { - for (std::list<IgnoreData>::iterator ign = this->osignoreservice.GetIgnores().begin(), ign_end = this->osignoreservice.GetIgnores().end(); ign != ign_end; ) - { - if (ign->time && ign->time <= Anope::CurTime) - { - Log(LOG_DEBUG) << "[os_ignore] Expiring ignore entry " << ign->mask; - ign = this->osignoreservice.GetIgnores().erase(ign); - } - else - { - std::stringstream buf; - buf << "OS IGNORE " << ign->mask << " " << ign->time << " " << ign->creator << " :" << ign->reason; - Write(buf.str()); - ++ign; - } - } - } - - EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) - { - if (this->osignoreservice.Find(u->nick)) - return EVENT_STOP; - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(OSIgnore) diff --git a/modules/core/os_ignore.h b/modules/core/os_ignore.h deleted file mode 100644 index 056161a79..000000000 --- a/modules/core/os_ignore.h +++ /dev/null @@ -1,39 +0,0 @@ -/* OperServ ignore interface - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - - -struct IgnoreData -{ - Anope::string mask; - Anope::string creator; - Anope::string reason; - time_t time; /* When do we stop ignoring them? */ -}; - -class IgnoreService : public Service -{ - protected: - std::list<IgnoreData> ignores; - - IgnoreService(Module *c, const Anope::string &n) : Service(c, n) { } - - public: - virtual void AddIgnore(const Anope::string &mask, const Anope::string &creator, const Anope::string &reason, time_t delta = Anope::CurTime) = 0; - - virtual bool DelIgnore(const Anope::string &mask) = 0; - - inline void ClearIgnores() { this->ignores.clear(); } - - virtual IgnoreData *Find(const Anope::string &mask) = 0; - - inline std::list<IgnoreData> &GetIgnores() { return this->ignores; } -}; - diff --git a/modules/core/os_jupe.cpp b/modules/core/os_jupe.cpp deleted file mode 100644 index a689b33e2..000000000 --- a/modules/core/os_jupe.cpp +++ /dev/null @@ -1,79 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSJupe : public Command -{ - public: - CommandOSJupe(Module *creator) : Command(creator, "operserv/jupe", 1, 2) - { - this->SetDesc(_("\"Jupiter\" a server")); - this->SetSyntax(_("\037server\037 [\037reason\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &jserver = params[0]; - const Anope::string &reason = params.size() > 1 ? params[1] : ""; - Server *server = Server::Find(jserver); - - if (!isValidHost(jserver, 3)) - source.Reply(_("Please use a valid server name when juping")); - else if (server && (server == Me || server == Me->GetLinks().front())) - source.Reply(_("You can not jupe your services server or your uplink server.")); - else - { - Anope::string rbuf = "Juped by " + u->nick + (!reason.empty() ? ": " + reason : ""); - if (server) - ircdproto->SendSquit(jserver, rbuf); - Server *juped_server = new Server(Me, jserver, 1, rbuf, ircd->ts6 ? ts6_sid_retrieve() : "", SERVER_JUPED); - ircdproto->SendServer(juped_server); - - Log(LOG_ADMIN, u, this) << "on " << jserver << " (" << rbuf << ")"; - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Tells Services to jupiter a server -- that is, to create\n" - "a fake \"server\" connected to Services which prevents\n" - "the real server of that name from connecting. The jupe\n" - "may be removed using a standard \002SQUIT\002. If a reason is\n" - "given, it is placed in the server information field;\n" - "otherwise, the server information field will contain the\n" - "text \"Juped by <nick>\", showing the nickname of the\n" - "person who jupitered the server.")); - return true; - } -}; - -class OSJupe : public Module -{ - CommandOSJupe commandosjupe; - - public: - OSJupe(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosjupe(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosjupe); - } -}; - -MODULE_INIT(OSJupe) diff --git a/modules/core/os_kick.cpp b/modules/core/os_kick.cpp deleted file mode 100644 index 341ea1ee6..000000000 --- a/modules/core/os_kick.cpp +++ /dev/null @@ -1,83 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSKick : public Command -{ - public: - CommandOSKick(Module *creator) : Command(creator, "operserv/kick", 3, 3) - { - this->SetDesc(_("Kick a user from a channel")); - this->SetSyntax(_("\037channel\037 \037user\037 \037reason\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &chan = params[0]; - const Anope::string &nick = params[1]; - const Anope::string &s = params[2]; - Channel *c; - User *u2; - - if (!(c = findchan(chan))) - { - source.Reply(CHAN_X_NOT_IN_USE, chan.c_str()); - return; - } - else if (c->bouncy_modes) - { - source.Reply(_("Services is unable to change modes. Are your servers' U:lines configured correctly?")); - return; - } - else if (!(u2 = finduser(nick))) - { - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - return; - } - - c->Kick(source.owner, u2, "%s (%s)", u->nick.c_str(), s.c_str()); - Log(LOG_ADMIN, u, this) << "on " << u2->nick << " in " << c->name; - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows staff to kick a user from any channel.\n" - "Parameters are the same as for the standard /KICK\n" - "command. The kick message will have the nickname of the\n" - "IRCop sending the KICK command prepended; for example:\n" - " \n" - "*** SpamMan has been kicked off channel #my_channel by %s (Alcan (Flood))"), source.owner->nick.c_str()); - return true; - } -}; - -class OSKick : public Module -{ - CommandOSKick commandoskick; - - public: - OSKick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandoskick(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandoskick); - } -}; - -MODULE_INIT(OSKick) diff --git a/modules/core/os_kill.cpp b/modules/core/os_kill.cpp deleted file mode 100644 index 11a0636ef..000000000 --- a/modules/core/os_kill.cpp +++ /dev/null @@ -1,72 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSKill : public Command -{ - public: - CommandOSKill(Module *creator) : Command(creator, "operserv/kill", 1, 2) - { - this->SetDesc(_("Kill a user")); - this->SetSyntax(_("\037user\037 [\037reason\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - Anope::string reason = params.size() > 1 ? params[1] : ""; - - User *u2 = finduser(nick); - if (u2 == NULL) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (u2->IsProtected() || u2->server == Me) - source.Reply(ACCESS_DENIED); - else - { - if (reason.empty()) - reason = "No reason specified"; - if (Config->AddAkiller) - reason = "(" + u->nick + ") " + reason; - Log(LOG_ADMIN, u, this) << "on " << u2->nick << " for " << reason; - u2->Kill(Config->OperServ, reason); - } - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to kill a user from the network.\n" - "Parameters are the same as for the standard /KILL\n" - "command.")); - return true; - } -}; - -class OSKill : public Module -{ - CommandOSKill commandoskill; - - public: - OSKill(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandoskill(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandoskill); - } -}; - -MODULE_INIT(OSKill) diff --git a/modules/core/os_list.cpp b/modules/core/os_list.cpp deleted file mode 100644 index 9a582f97b..000000000 --- a/modules/core/os_list.cpp +++ /dev/null @@ -1,187 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSChanList : public Command -{ - public: - CommandOSChanList(Module *creator) : Command(creator, "operserv/chanlist", 0, 2) - { - this->SetDesc(_("Lists all channel records")); - this->SetSyntax(_("[{\037pattern\037 | \037nick\037} [\037SECRET\037]]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &pattern = !params.empty() ? params[0] : ""; - const Anope::string &opt = params.size() > 1 ? params[1] : ""; - std::list<ChannelModeName> Modes; - User *u2; - - if (!opt.empty() && opt.equals_ci("SECRET")) - { - Modes.push_back(CMODE_SECRET); - Modes.push_back(CMODE_PRIVATE); - } - - if (!pattern.empty() && (u2 = finduser(pattern))) - { - source.Reply(_("\002%s\002 channel list:\n" - "Name Users Modes Topic"), u2->nick.c_str()); - - for (UChannelList::iterator uit = u2->chans.begin(), uit_end = u2->chans.end(); uit != uit_end; ++uit) - { - ChannelContainer *cc = *uit; - - if (!Modes.empty()) - for (std::list<ChannelModeName>::iterator it = Modes.begin(), it_end = Modes.end(); it != it_end; ++it) - if (!cc->chan->HasMode(*it)) - continue; - - source.Reply(_("%-20s %4d +%-6s %s"), cc->chan->name.c_str(), cc->chan->users.size(), cc->chan->GetModes(true, true).c_str(), !cc->chan->topic.empty() ? cc->chan->topic.c_str() : ""); - } - } - else - { - source.Reply(_("Channel list:\n" - "Name Users Modes Topic")); - - for (channel_map::const_iterator cit = ChannelList.begin(), cit_end = ChannelList.end(); cit != cit_end; ++cit) - { - Channel *c = cit->second; - - if (!pattern.empty() && !Anope::Match(c->name, pattern)) - continue; - if (!Modes.empty()) - for (std::list<ChannelModeName>::iterator it = Modes.begin(), it_end = Modes.end(); it != it_end; ++it) - if (!c->HasMode(*it)) - continue; - - source.Reply(_("%-20s %4d +%-6s %s"), c->name.c_str(), c->users.size(), c->GetModes(true, true).c_str(), !c->topic.empty() ? c->topic.c_str() : ""); - } - } - - source.Reply(_("End of channel list.")); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all channels currently in use on the IRC network, whether they\n" - "are registered or not.\n" - "If \002pattern\002 is given, lists only channels that match it. If a nickname\n" - "is given, lists only the channels the user using it is on. If SECRET is\n" - "specified, lists only channels matching \002pattern\002 that have the +s or\n" - "+p mode.")); - return true; - } -}; - -class CommandOSUserList : public Command -{ - public: - CommandOSUserList(Module *creator) : Command(creator, "operserv/userlist", 0, 2) - { - this->SetDesc(_("Lists all user records")); - this->SetSyntax(_("[{\037pattern\037 | \037channel\037} [\037INVISIBLE\037]]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &pattern = !params.empty() ? params[0] : ""; - const Anope::string &opt = params.size() > 1 ? params[1] : ""; - Channel *c; - std::list<UserModeName> Modes; - - if (!opt.empty() && opt.equals_ci("INVISIBLE")) - Modes.push_back(UMODE_INVIS); - - if (!pattern.empty() && (c = findchan(pattern))) - { - source.Reply(_("\002%s\002 users list:\n" - "Nick Mask"), pattern.c_str()); - - for (CUserList::iterator cuit = c->users.begin(), cuit_end = c->users.end(); cuit != cuit_end; ++cuit) - { - UserContainer *uc = *cuit; - - if (!Modes.empty()) - for (std::list<UserModeName>::iterator it = Modes.begin(), it_end = Modes.end(); it != it_end; ++it) - if (!uc->user->HasMode(*it)) - continue; - - source.Reply(_("%-20s %s@%s"), uc->user->nick.c_str(), uc->user->GetIdent().c_str(), uc->user->GetDisplayedHost().c_str()); - } - } - else - { - source.Reply(_("Users list:\n" - "Nick Mask")); - - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) - { - User *u2 = it->second; - - if (!pattern.empty()) - { - Anope::string mask = u2->nick + "!" + u2->GetIdent() + "@" + u2->GetDisplayedHost(); - if (!Anope::Match(mask, pattern)) - continue; - if (!Modes.empty()) - for (std::list<UserModeName>::iterator mit = Modes.begin(), mit_end = Modes.end(); mit != mit_end; ++mit) - if (!u2->HasMode(*mit)) - continue; - } - source.Reply(_("%-20s %s@%s"), u2->nick.c_str(), u2->GetIdent().c_str(), u2->GetDisplayedHost().c_str()); - } - } - - source.Reply(_("End of users list.")); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all users currently online on the IRC network, whether their\n" - "nick is registered or not.\n" - " \n" - "If \002pattern\002 is given, lists only users that match it (it must be in\n" - "the format nick!user@host). If \002channel\002 is given, lists only users\n" - "that are on the given channel. If INVISIBLE is specified, only users\n" - "with the +i flag will be listed.")); - return true; - } -}; - -class OSList : public Module -{ - CommandOSChanList commandoschanlist; - CommandOSUserList commandosuserlist; - - public: - OSList(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandoschanlist(this), commandosuserlist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandoschanlist); - ModuleManager::RegisterService(&commandosuserlist); - } -}; - -MODULE_INIT(OSList) diff --git a/modules/core/os_login.cpp b/modules/core/os_login.cpp deleted file mode 100644 index 94a82e334..000000000 --- a/modules/core/os_login.cpp +++ /dev/null @@ -1,97 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - * - * - */ -/*************************************************************************/ - -#include "module.h" - -class CommandOSLogin : public Command -{ - public: - CommandOSLogin(Module *creator) : Command(creator, "operserv/login", 1, 1) - { - this->SetDesc(Anope::printf(_("Login to %s"), Config->OperServ.c_str())); - this->SetSyntax(_("\037password\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &password = params[0]; - - Oper *o = source.u->Account()->o; - if (o == NULL) - source.Reply(_("No oper block for your nick.")); - else if (o->password.empty()) - source.Reply(_("Your oper block doesn't require logging in.")); - else if (source.u->GetExt("os_login_password_correct")) - source.Reply(_("You are already identified.")); - else if (o->password != password) - { - source.Reply(PASSWORD_INCORRECT); - bad_password(source.u); - } - else - { - Log(LOG_ADMIN, source.u, this) << "and successfully identified to " << source.owner->nick; - source.u->Extend("os_login_password_correct"); - source.Reply(_("Password accepted.")); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Logs you in to %s so you gain Services Operator privileges.\n" - "This command may be unnecessary if your oper block is\n" - "configured without a password."), source.owner->nick.c_str()); - return true; - } -}; - -class OSLogin : public Module -{ - CommandOSLogin commandoslogin; - - public: - OSLogin(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandoslogin(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandoslogin); - - ModuleManager::Attach(I_IsServicesOper, this); - } - - ~OSLogin() - { - for (Anope::insensitive_map<User *>::const_iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) - it->second->Shrink("os_login_password_correct"); - } - - EventReturn IsServicesOper(User *u) - { - if (!u->Account()->o->password.empty()) - { - if (u->GetExt("os_login_password_correct")) - return EVENT_ALLOW; - return EVENT_STOP; - } - - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(OSLogin) diff --git a/modules/core/os_main.cpp b/modules/core/os_main.cpp deleted file mode 100644 index b555b9ede..000000000 --- a/modules/core/os_main.cpp +++ /dev/null @@ -1,371 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -static BotInfo *OperServ; - -class SGLineManager : public XLineManager -{ - public: - SGLineManager(Module *creator) : XLineManager(creator, "xlinemanager/sgline", 'G') { } - - XLine *Add(const Anope::string &mask, const Anope::string &creator, time_t expires, const Anope::string &reason) - { - Anope::string realreason = reason; - if (!creator.empty() && Config->AddAkiller) - realreason = "[" + creator + "] " + reason; - - XLine *x = new XLine(mask, creator, expires, realreason); - - this->AddXLine(x); - - if (UplinkSock && Config->AkillOnAdd) - this->Send(NULL, x); - - return x; - } - - void Del(XLine *x) - { - ircdproto->SendAkillDel(x); - } - - void OnMatch(User *u, XLine *x) - { - if (u) - u->Kill(Config->OperServ, x->Reason); - ircdproto->SendAkill(u, x); - } - - void OnExpire(XLine *x) - { - if (Config->WallAkillExpire) - ircdproto->SendGlobops(OperServ, "AKILL on %s has expired", x->Mask.c_str()); - } - - void Send(User *u, XLine *x) - { - ircdproto->SendAkill(u, x); - } -}; - -class SZLineManager : public XLineManager -{ - public: - SZLineManager(Module *creator) : XLineManager(creator, "xlinemanager/szline", 'Z') { } - - XLine *Add(const Anope::string &mask, const Anope::string &creator, time_t expires, const Anope::string &reason) - { - XLine *x = new XLine(mask, creator, expires, reason); - - this->AddXLine(x); - - if (UplinkSock) - this->Send(NULL, x); - - return x; - } - - void Del(XLine *x) - { - ircdproto->SendSZLineDel(x); - } - - void OnMatch(User *u, XLine *x) - { - if (u) - { - Anope::string reason = "Z-Lined: " + x->Reason; - u->Kill(Config->OperServ, reason); - } - - ircdproto->SendSZLine(u, x); - } - - void OnExpire(XLine *x) - { - if (Config->WallSZLineExpire) - ircdproto->SendGlobops(OperServ, "SZLINE on \2%s\2 has expired", x->Mask.c_str()); - } - - void Send(User *u, XLine *x) - { - ircdproto->SendSZLine(u, x); - } -}; - -class SQLineManager : public XLineManager -{ - public: - SQLineManager(Module *creator) : XLineManager(creator, "xlinemanager/sqline", 'Q') { } - - XLine *Add(const Anope::string &mask, const Anope::string &creator, time_t expires, const Anope::string &reason) - { - XLine *x = new XLine(mask, creator, expires, reason); - - this->AddXLine(x); - - if (Config->KillonSQline) - { - Anope::string rreason = "Q-Lined: " + reason; - - if (mask[0] == '#') - { - for (channel_map::const_iterator cit = ChannelList.begin(), cit_end = ChannelList.end(); cit != cit_end; ++cit) - { - Channel *c = cit->second; - - if (!Anope::Match(c->name, mask)) - continue; - for (CUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; ) - { - UserContainer *uc = *it; - ++it; - - if (uc->user->HasMode(UMODE_OPER) || uc->user->server == Me) - continue; - c->Kick(NULL, uc->user, "%s", reason.c_str()); - } - } - } - else - { - for (Anope::insensitive_map<User *>::const_iterator it = UserListByNick.begin(); it != UserListByNick.end();) - { - User *user = it->second; - ++it; - - if (!user->HasMode(UMODE_OPER) && user->server != Me && Anope::Match(user->nick, x->Mask)) - user->Kill(Config->ServerName, rreason); - } - } - } - - if (UplinkSock) - this->Send(NULL, x); - - return x; - } - - void Del(XLine *x) - { - ircdproto->SendSQLineDel(x); - } - - void OnMatch(User *u, XLine *x) - { - if (u) - { - Anope::string reason = "Q-Lined: " + x->Reason; - u->Kill(Config->OperServ, reason); - } - - this->Send(u, x); - } - - void OnExpire(XLine *x) - { - if (Config->WallSQLineExpire) - ircdproto->SendGlobops(OperServ, "SQLINE on \2%s\2 has expired", x->Mask.c_str()); - } - - void Send(User *u, XLine *x) - { - ircdproto->SendSQLine(u, x); - } - - bool CheckChannel(Channel *c) - { - if (ircd->chansqline) - for (std::vector<XLine *>::const_iterator it = this->GetList().begin(), it_end = this->GetList().end(); it != it_end; ++it) - if (Anope::Match(c->name, (*it)->Mask)) - return true; - return false; - } -}; - -class SNLineManager : public XLineManager -{ - public: - SNLineManager(Module *creator) : XLineManager(creator, "xlinemanager/snline", 'N') { } - - XLine *Add(const Anope::string &mask, const Anope::string &creator, time_t expires, const Anope::string &reason) - { - XLine *x = new XLine(mask, creator, expires, reason); - - this->AddXLine(x); - - if (Config->KillonSNline && !ircd->sglineenforce) - { - Anope::string rreason = "G-Lined: " + reason; - - for (Anope::insensitive_map<User *>::const_iterator it = UserListByNick.begin(); it != UserListByNick.end();) - { - User *user = it->second; - ++it; - - if (!user->HasMode(UMODE_OPER) && user->server != Me && Anope::Match(user->realname, x->Mask)) - user->Kill(Config->ServerName, rreason); - } - } - - return x; - } - - void Del(XLine *x) - { - ircdproto->SendSGLineDel(x); - } - - void OnMatch(User *u, XLine *x) - { - if (u) - { - Anope::string reason = "G-Lined: " + x->Reason; - u->Kill(Config->OperServ, reason); - } - this->Send(u, x); - } - - void OnExpire(XLine *x) - { - if (Config->WallSNLineExpire) - ircdproto->SendGlobops(OperServ, "SNLINE on \2%s\2 has expired", x->Mask.c_str()); - } - - void Send(User *u, XLine *x) - { - ircdproto->SendSGLine(u, x); - } - - XLine *Check(User *u) - { - for (unsigned i = this->XLines.size(); i > 0; --i) - { - XLine *x = this->XLines[i - 1]; - - if (x->Expires && x->Expires < Anope::CurTime) - { - this->OnExpire(x); - this->Del(x); - delete x; - this->XLines.erase(XLines.begin() + i - 1); - continue; - } - - if (Anope::Match(u->realname, x->Mask)) - { - this->OnMatch(u, x); - return x; - } - } - - return NULL; - } -}; - -class OperServCore : public Module -{ - SGLineManager sglines; - SZLineManager szlines; - SQLineManager sqlines; - SNLineManager snlines; - - public: - OperServCore(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - sglines(this), szlines(this), sqlines(this), snlines(this) - { - this->SetAuthor("Anope"); - - OperServ = findbot(Config->OperServ); - if (OperServ == NULL) - throw ModuleException("No bot named " + Config->OperServ); - - Implementation i[] = { I_OnBotPrivmsg, I_OnServerQuit, I_OnUserModeSet, I_OnUserModeUnset, I_OnUserConnect, I_OnUserNickChange, I_OnPreHelp }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&sglines); - ModuleManager::RegisterService(&szlines); - ModuleManager::RegisterService(&sqlines); - ModuleManager::RegisterService(&snlines); - - /* Yes, these are in this order for a reason. Most violent->least violent. */ - XLineManager::RegisterXLineManager(&sglines); - XLineManager::RegisterXLineManager(&szlines); - XLineManager::RegisterXLineManager(&sqlines); - XLineManager::RegisterXLineManager(&snlines); - } - - EventReturn OnBotPrivmsg(User *u, BotInfo *bi, Anope::string &message) - { - if (Config->OSOpersOnly && !u->HasMode(UMODE_OPER) && bi->nick == Config->OperServ) - { - u->SendMessage(bi, ACCESS_DENIED); - return EVENT_STOP; - } - - return EVENT_CONTINUE; - } - - void OnServerQuit(Server *server) - { - if (server->HasFlag(SERVER_JUPED)) - ircdproto->SendGlobops(OperServ, "Received SQUIT for juped server %s", server->GetName().c_str()); - } - - void OnUserModeSet(User *u, UserModeName Name) - { - if (Name == UMODE_OPER) - { - if (Config->WallOper) - ircdproto->SendGlobops(OperServ, "\2%s\2 is now an IRC operator.", u->nick.c_str()); - Log(OperServ) << u->nick << " is now an IRC operator"; - } - } - - void OnUserModeUnset(User *u, UserModeName Name) - { - if (Name == UMODE_OPER) - Log(OperServ) << u->nick << " is no longer an IRC operator"; - } - - void OnUserConnect(dynamic_reference<User> &u, bool &exempt) - { - if (u && !exempt) - XLineManager::CheckAll(u); - } - - void OnUserNickChange(User *u, const Anope::string &oldnick) - { - if (ircd->sqline && !u->HasMode(UMODE_OPER)) - this->sqlines.Check(u); - } - - EventReturn OnCheckKick(User *u, ChannelInfo *ci, bool &kick) - { - if (this->sqlines.CheckChannel(ci->c)) - kick = true; - return EVENT_CONTINUE; - } - - void OnPreHelp(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!params.empty() || source.owner->nick != Config->OperServ) - return; - source.Reply(_("%s commands:"), Config->OperServ.c_str()); - } -}; - -MODULE_INIT(OperServCore) - diff --git a/modules/core/os_mode.cpp b/modules/core/os_mode.cpp deleted file mode 100644 index b3e62ca25..000000000 --- a/modules/core/os_mode.cpp +++ /dev/null @@ -1,109 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSMode : public Command -{ - public: - CommandOSMode(Module *creator) : Command(creator, "operserv/mode", 2, 2) - { - this->SetDesc(_("Change channel modes")); - this->SetSyntax(_("\037channel\037 \037modes\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &target = params[0]; - const Anope::string &modes = params[1]; - - Channel *c = findchan(target); - if (!c) - source.Reply(CHAN_X_NOT_IN_USE, target.c_str()); - else if (c->bouncy_modes) - source.Reply(_("Services is unable to change modes. Are your servers' U:lines configured correctly?")); - else - { - c->SetModes(source.owner, false, modes.c_str()); - - Log(LOG_ADMIN, u, this) << modes << " on " << target; - } - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services operators to change modes for any channel.\n" - "Parameters are the same as for the standard /MODE command.")); - return true; - } -}; - -class CommandOSUMode : public Command -{ - public: - CommandOSUMode(Module *creator) : Command(creator, "operserv/umode", 2, 2) - { - this->SetDesc(_("Change channel or user modes")); - this->SetSyntax(_("\037user\037 \037modes\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &target = params[0]; - const Anope::string &modes = params[1]; - - User *u2 = finduser(target); - if (!u2) - source.Reply(NICK_X_NOT_IN_USE, target.c_str()); - else - { - u2->SetModes(source.owner, "%s", modes.c_str()); - source.Reply(_("Changed usermodes of \002%s\002 to %s."), u2->nick.c_str(), modes.c_str()); - - u2->SendMessage(source.owner, _("\002%s\002 changed your usermodes to %s."), u->nick.c_str(), modes.c_str()); - - Log(LOG_ADMIN, u, this) << modes << " on " << target; - } - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services operators to change modes for any user.\n" - "Parameters are the same as for the standard /MODE command.")); - return true; - } -}; - -class OSMode : public Module -{ - CommandOSMode commandosmode; - CommandOSUMode commandosumode; - - public: - OSMode(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosmode(this), commandosumode(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosmode); - ModuleManager::RegisterService(&commandosumode); - } -}; - -MODULE_INIT(OSMode) diff --git a/modules/core/os_modinfo.cpp b/modules/core/os_modinfo.cpp deleted file mode 100644 index 38d9cf905..000000000 --- a/modules/core/os_modinfo.cpp +++ /dev/null @@ -1,245 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSModInfo : public Command -{ - public: - CommandOSModInfo(Module *creator) : Command(creator, "operserv/modinfo", 1, 1) - { - this->SetDesc(_("Info about a loaded module")); - this->SetSyntax(_("\037modname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &file = params[0]; - - Module *m = ModuleManager::FindModule(file); - if (m) - { - source.Reply(_("Module: \002%s\002 Version: \002%s\002 Author: \002%s\002 loaded: \002%s\002"), m->name.c_str(), !m->version.empty() ? m->version.c_str() : "?", !m->author.empty() ? m->author.c_str() : "?", do_strftime(m->created).c_str()); - - std::vector<Anope::string> services = ModuleManager::GetServiceKeys(); - for (unsigned i = 0; i < services.size(); ++i) - { - Service *s = ModuleManager::GetService(services[i]); - if (!s || s->owner != m) - continue; - source.Reply(_(" Providing service: \002%s\002"), s->name.c_str()); - - for (botinfo_map::const_iterator it = BotListByNick.begin(), it_end = BotListByNick.end(); it != it_end; ++it) - { - BotInfo *bi = it->second; - - for (BotInfo::command_map::const_iterator cit = bi->commands.begin(), cit_end = bi->commands.end(); cit != cit_end; ++cit) - { - const Anope::string &c_name = cit->first; - const CommandInfo &info = cit->second; - if (info.name != s->name) - continue; - source.Reply(_(" Command \002%s\002 on \002%s\002 is linked to \002%s\002"), c_name.c_str(), bi->nick.c_str(), s->name.c_str()); - } - } - } - } - else - source.Reply(_("No information about module \002%s\002 is available"), file.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command lists information about the specified loaded module")); - return true; - } -}; - -class CommandOSModList : public Command -{ - public: - CommandOSModList(Module *creator) : Command(creator, "operserv/modlist", 0, 1) - { - this->SetDesc(_("List loaded modules")); - this->SetSyntax(_("[Core|3rd|protocol|encryption|supported]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string ¶m = !params.empty() ? params[0] : ""; - - int count = 0; - int showCore = 0; - int showThird = 1; - int showProto = 1; - int showEnc = 1; - int showSupported = 1; - int showDB = 1; - - char core[] = "Core"; - char third[] = "3rd"; - char proto[] = "Protocol"; - char enc[] = "Encryption"; - char supported[] = "Supported"; - char db[] = "Database"; - - if (!param.empty()) - { - if (param.equals_ci(core)) - { - showCore = 1; - showThird = 0; - showProto = 0; - showEnc = 0; - showSupported = 0; - showDB = 0; - } - else if (param.equals_ci(third)) - { - showCore = 0; - showThird = 1; - showSupported = 0; - showProto = 0; - showEnc = 0; - showDB = 0; - } - else if (param.equals_ci(proto)) - { - showCore = 0; - showThird = 0; - showProto = 1; - showEnc = 0; - showSupported = 0; - showDB = 0; - } - else if (param.equals_ci(supported)) - { - showCore = 0; - showThird = 0; - showProto = 0; - showSupported = 1; - showEnc = 0; - showDB = 0; - } - else if (param.equals_ci(enc)) - { - showCore = 0; - showThird = 0; - showProto = 0; - showSupported = 0; - showEnc = 1; - showDB = 0; - } - else if (param.equals_ci(db)) - { - showCore = 0; - showThird = 0; - showProto = 0; - showSupported = 0; - showEnc = 0; - showDB = 1; - } - } - - source.Reply(_("Current Module list:")); - - for (std::list<Module *>::iterator it = Modules.begin(), it_end = Modules.end(); it != it_end; ++it) - { - Module *m = *it; - - switch (m->type) - { - case CORE: - if (showCore) - { - source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), core); - ++count; - } - break; - case THIRD: - if (showThird) - { - source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), third); - ++count; - } - break; - case PROTOCOL: - if (showProto) - { - source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), proto); - ++count; - } - break; - case SUPPORTED: - if (showSupported) - { - source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), supported); - ++count; - } - break; - case ENCRYPTION: - if (showEnc) - { - source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), enc); - ++count; - } - break; - case DATABASE: - if (showDB) - { - source.Reply(_("Module: \002%s\002 [%s] [%s]"), m->name.c_str(), m->version.c_str(), db); - ++count; - } - break; - default: - break; - } - } - if (!count) - source.Reply(_("No modules currently loaded")); - else - source.Reply(_("%d Modules loaded."), count); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Lists all currently loaded modules.")); - return true; - } -}; - -class OSModInfo : public Module -{ - CommandOSModInfo commandosmodinfo; - CommandOSModList commandosmodlist; - - public: - OSModInfo(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosmodinfo(this), commandosmodlist(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosmodinfo); - ModuleManager::RegisterService(&commandosmodlist); - } -}; - -MODULE_INIT(OSModInfo) diff --git a/modules/core/os_module.cpp b/modules/core/os_module.cpp deleted file mode 100644 index 562e130aa..000000000 --- a/modules/core/os_module.cpp +++ /dev/null @@ -1,202 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSModLoad : public Command -{ - public: - CommandOSModLoad(Module *creator) : Command(creator, "operserv/modload", 1, 1) - { - this->SetDesc(_("Load a module")); - this->SetSyntax(_("\037modname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &mname = params[0]; - - ModuleReturn status = ModuleManager::LoadModule(mname, u); - if (status == MOD_ERR_OK) - { - ircdproto->SendGlobops(source.owner, "%s loaded module %s", u->nick.c_str(), mname.c_str()); - source.Reply(_("Module \002%s\002 loaded"), mname.c_str()); - - /* If a user is loading this module, then the core databases have already been loaded - * so trigger the event manually - */ - Module *m = ModuleManager::FindModule(mname); - if (m) - m->OnPostLoadDatabases(); - } - else if (status == MOD_ERR_EXISTS) - source.Reply(_("Module \002%s\002 is already loaded."), mname.c_str()); - else - source.Reply(_("Unable to load module \002%s\002"), mname.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command loads the module named FileName from the modules\n" - "directory.")); - return true; - } -}; - -class CommandOSModReLoad : public Command -{ - public: - CommandOSModReLoad(Module *creator) : Command(creator, "operserv/modreload", 1, 1) - { - this->SetDesc(_("Reload a module")); - this->SetSyntax(_("\037modname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &mname = params[0]; - - Module *m = ModuleManager::FindModule(mname); - if (!m) - { - source.Reply(_("Module \002%s\002 isn't loaded."), mname.c_str()); - return; - } - - if (!m->handle || m->GetPermanent()) - { - source.Reply(_("Unable to remove module \002%s\002"), m->name.c_str()); - return; - } - - /* Unrecoverable */ - bool fatal = m->type == PROTOCOL; - ModuleReturn status = ModuleManager::UnloadModule(m, u); - - if (status != MOD_ERR_OK) - { - source.Reply(_("Unable to remove module \002%s\002"), mname.c_str()); - return; - } - - status = ModuleManager::LoadModule(mname, u); - if (status == MOD_ERR_OK) - { - ircdproto->SendGlobops(source.owner, "%s reloaded module %s", u->nick.c_str(), mname.c_str()); - source.Reply(_("Module \002%s\002 reloaded"), mname.c_str()); - - /* If a user is loading this module, then the core databases have already been loaded - * so trigger the event manually - */ - m = ModuleManager::FindModule(mname); - if (m) - m->OnPostLoadDatabases(); - } - else - { - if (fatal) - throw FatalException("Unable to reload module " + mname); - else - source.Reply(_("Unable to load module \002%s\002"), mname.c_str()); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command reloads the module named FileName.")); - return true; - } -}; - -class CommandOSModUnLoad : public Command -{ - public: - CommandOSModUnLoad(Module *creator) : Command(creator, "operserv/modunload", 1, 1) - { - this->SetDesc(_("Un-Load a module")); - this->SetSyntax(_("\037modname\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &mname = params[0]; - - Module *m = ModuleManager::FindModule(mname); - if (!m) - { - source.Reply(_("Module \002%s\002 isn't loaded."), mname.c_str()); - return; - } - - if (!m->handle || m->GetPermanent() || m->type == PROTOCOL) - { - source.Reply(_("Unable to remove module \002%s\002"), m->name.c_str()); - return; - } - - Log() << "Trying to unload module [" << mname << "]"; - - ModuleReturn status = ModuleManager::UnloadModule(m, u); - - if (status == MOD_ERR_OK) - { - source.Reply(_("Module \002%s\002 unloaded"), mname.c_str()); - ircdproto->SendGlobops(source.owner, "%s unloaded module %s", u->nick.c_str(), mname.c_str()); - } - else - source.Reply(_("Unable to remove module \002%s\002"), mname.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("This command unloads the module named FileName from the modules\n" - "directory.")); - return true; - } -}; - -class OSModule : public Module -{ - CommandOSModLoad commandosmodload; - CommandOSModReLoad commandosmodreload; - CommandOSModUnLoad commandosmodunload; - - public: - OSModule(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosmodload(this), commandosmodreload(this), commandosmodunload(this) - { - this->SetAuthor("Anope"); - this->SetPermanent(true); - - ModuleManager::RegisterService(&commandosmodload); - ModuleManager::RegisterService(&commandosmodreload); - ModuleManager::RegisterService(&commandosmodunload); - } -}; - -MODULE_INIT(OSModule) diff --git a/modules/core/os_news.cpp b/modules/core/os_news.cpp deleted file mode 100644 index 9c9aae0a4..000000000 --- a/modules/core/os_news.cpp +++ /dev/null @@ -1,450 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at info@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "global.h" -#include "os_news.h" - -/* List of messages for each news type. This simplifies message sending. */ - -enum -{ - MSG_SYNTAX, - MSG_LIST_HEADER, - MSG_LIST_NONE, - MSG_ADDED, - MSG_DEL_NOT_FOUND, - MSG_DELETED, - MSG_DEL_NONE, - MSG_DELETED_ALL -}; - -struct NewsMessages msgarray[] = { - {NEWS_LOGON, "LOGON", - {_("LOGONNEWS {ADD|DEL|LIST} [\037text\037|\037num\037]\002"), - _("Logon news items:"), - _("There is no logon news."), - _("Added new logon news item."), - _("Logon news item #%s not found!"), - _("Logon news item #%d deleted."), - _("No logon news items to delete!"), - _("All logon news items deleted.")} - }, - {NEWS_OPER, "OPER", - {_("OPERNEWS {ADD|DEL|LIST} [\037text\037|\037num\037]\002"), - _("Oper news items:"), - _("There is no oper news."), - _("Added new oper news item."), - _("Oper news item #%s not found!"), - _("Oper news item #%d deleted."), - _("No oper news items to delete!"), - _("All oper news items deleted.")} - }, - {NEWS_RANDOM, "RANDOM", - {_("RANDOMNEWS {ADD|DEL|LIST} [\037text\037|\037num\037]\002"), - _("Random news items:"), - _("There is no random news."), - _("Added new random news item."), - _("Random news item #%s not found!"), - _("Random news item #%d deleted."), - _("No random news items to delete!"), - _("All random news items deleted.")} - } -}; - -class MyNewsService : public NewsService -{ - std::vector<NewsItem *> newsItems[3]; - public: - MyNewsService(Module *m) : NewsService(m) { } - - ~MyNewsService() - { - for (unsigned i = 0; i < 3; ++i) - for (unsigned j = 0; j < newsItems[i].size(); ++j) - delete newsItems[i][j]; - } - - void AddNewsItem(NewsItem *n) - { - this->newsItems[n->type].push_back(n); - } - - void DelNewsItem(NewsItem *n) - { - std::vector<NewsItem *> &list = this->GetNewsList(n->type); - std::vector<NewsItem *>::iterator it = std::find(list.begin(), list.end(), n); - if (it != list.end()) - list.erase(it); - delete n; - } - - std::vector<NewsItem *> &GetNewsList(NewsType t) - { - return this->newsItems[t]; - } -}; - -#define lenof(a) (sizeof(a) / sizeof(*(a))) -static const char **findmsgs(NewsType type) -{ - for (unsigned i = 0; i < lenof(msgarray); ++i) - if (msgarray[i].type == type) - return msgarray[i].msgs; - return NULL; -} - -class NewsBase : public Command -{ - service_reference<NewsService> ns; - - protected: - void DoList(CommandSource &source, NewsType type, const char **msgs) - { - std::vector<NewsItem *> &list = this->ns->GetNewsList(type); - if (list.empty()) - source.Reply(msgs[MSG_LIST_NONE]); - else - { - source.Reply(msgs[MSG_LIST_HEADER]); - for (unsigned i = 0, end = list.size(); i < end; ++i) - source.Reply(_("%5d (%s by %s)\n"" %s"), i + 1, do_strftime(list[i]->time).c_str(), !list[i]->who.empty() ? list[i]->who.c_str() : "<unknown>", list[i]->text.c_str()); - source.Reply(END_OF_ANY_LIST, "News"); - } - - return; - } - - void DoAdd(CommandSource &source, const std::vector<Anope::string> ¶ms, NewsType type, const char **msgs) - { - const Anope::string text = params.size() > 1 ? params[1] : ""; - - if (text.empty()) - this->OnSyntaxError(source, "ADD"); - else - { - if (readonly) - source.Reply(READ_ONLY_MODE); - - NewsItem *news = new NewsItem(); - news->type = type; - news->text = text; - news->time = Anope::CurTime; - news->who = source.u->nick; - - this->ns->AddNewsItem(news); - - source.Reply(msgs[MSG_ADDED]); - } - - return; - } - - void DoDel(CommandSource &source, const std::vector<Anope::string> ¶ms, NewsType type, const char **msgs) - { - const Anope::string &text = params.size() > 1 ? params[1] : ""; - - if (text.empty()) - this->OnSyntaxError(source, "DEL"); - else - { - std::vector<NewsItem *> &list = this->ns->GetNewsList(type); - if (list.empty()) - source.Reply(msgs[MSG_LIST_NONE]); - else - { - if (readonly) - source.Reply(READ_ONLY_MODE); - if (!text.equals_ci("ALL")) - { - try - { - unsigned num = convertTo<unsigned>(text); - if (num > 0 && num <= list.size()) - { - this->ns->DelNewsItem(list[num - 1]); - source.Reply(msgs[MSG_DELETED], num); - return; - } - } - catch (const ConvertException &) { } - - source.Reply(msgs[MSG_DEL_NOT_FOUND], text.c_str()); - } - else - { - for (unsigned i = list.size(); i > 0; --i) - this->ns->DelNewsItem(list[i - 1]); - source.Reply(msgs[MSG_DELETED_ALL]); - } - } - } - - return; - } - - void DoNews(CommandSource &source, const std::vector<Anope::string> ¶ms, NewsType type) - { - if (!this->ns) - return; - - const Anope::string &cmd = params[0]; - - const char **msgs = findmsgs(type); - if (!msgs) - throw CoreException("news: Invalid type to do_news()"); - - if (cmd.equals_ci("LIST")) - return this->DoList(source, type, msgs); - else if (cmd.equals_ci("ADD")) - return this->DoAdd(source, params, type, msgs); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, params, type, msgs); - else - this->OnSyntaxError(source, ""); - - return; - } - public: - NewsBase(Module *creator, const Anope::string &newstype) : Command(creator, newstype, 1, 2), ns("news") - { - this->SetSyntax(_("ADD \037text\037")); - this->SetSyntax(_("DEL {\037num\037 | ALL}")); - this->SetSyntax(_("LIST")); - } - - virtual ~NewsBase() - { - } - - virtual void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) = 0; - - virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand) = 0; -}; - -class CommandOSLogonNews : public NewsBase -{ - public: - CommandOSLogonNews(Module *creator) : NewsBase(creator, "operserv/logonnews") - { - this->SetDesc(_("Define messages to be shown to users at logon")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoNews(source, params, NEWS_LOGON); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Edits or displays the list of logon news messages. When a\n" - "user connects to the network, these messages will be sent\n" - "to them. (However, no more than \002%d\002 messages will be\n" - "sent in order to avoid flooding the user. If there are\n" - "more news messages, only the most recent will be sent.)\n" - "NewsCount can be configured in services.conf.\n" - " \n" - "LOGONNEWS may only be used by Services Operators."), Config->NewsCount); - return true; - } -}; - -class CommandOSOperNews : public NewsBase -{ - public: - CommandOSOperNews(Module *creator) : NewsBase(creator, "operserv/opernews") - { - this->SetDesc(_("Define messages to be shown to users who oper")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoNews(source, params, NEWS_OPER); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Edits or displays the list of oper news messages. When a\n" - "user opers up (with the /OPER command), these messages will\n" - "be sent to them. (However, no more than \002%d\002 messages will\n" - "be sent in order to avoid flooding the user. If there are\n" - "more news messages, only the most recent will be sent.)\n" - "NewsCount can be configured in services.conf.\n" - " \n" - "OPERNEWS may only be used by Services Operators."), Config->NewsCount); - return true; - } -}; - -class CommandOSRandomNews : public NewsBase -{ - public: - CommandOSRandomNews(Module *creator) : NewsBase(creator, "operserv/randomnews") - { - this->SetDesc(_("Define messages to be randomly shown to users at logon")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - return this->DoNews(source, params, NEWS_RANDOM); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Edits or displays the list of random news messages. When a\n" - "user connects to the network, one (and only one) of the\n" - "random news will be randomly chosen and sent to them.\n" - " \n" - "RANDOMNEWS may only be used by Services Operators.")); - return true; - } -}; - -class OSNews : public Module -{ - MyNewsService newsservice; - - CommandOSLogonNews commandoslogonnews; - CommandOSOperNews commandosopernews; - CommandOSRandomNews commandosrandomnews; - - void DisplayNews(User *u, NewsType Type) - { - std::vector<NewsItem *> &newsList = this->newsservice.GetNewsList(Type); - if (newsList.empty()) - return; - - Anope::string msg; - if (Type == NEWS_LOGON) - msg = _("[\002Logon News\002 - %s] %s"); - else if (Type == NEWS_OPER) - msg = _("[\002Oper News\002 - %s] %s"); - else if (Type == NEWS_RANDOM) - msg = _("[\002Random News\002 - %s] %s"); - - static unsigned cur_rand_news = 0; - unsigned displayed = 0; - for (unsigned i = 0, end = newsList.size(); i < end; ++i) - { - if (Type == NEWS_RANDOM && i != cur_rand_news) - continue; - - BotInfo *gl = findbot(Config->Global); - if (!gl && !BotListByNick.empty()) - gl = BotListByNick.begin()->second; - BotInfo *os = findbot(Config->OperServ); - if (!os) - os = gl; - if (gl) - u->SendMessage(Type != NEWS_OPER ? gl : os, msg.c_str(), do_strftime(newsList[i]->time).c_str(), newsList[i]->text.c_str()); - - ++displayed; - - if (Type == NEWS_RANDOM) - { - ++cur_rand_news; - break; - } - else if (displayed >= Config->NewsCount) - break; - } - - /* Reset to head of list to get first random news value */ - if (Type == NEWS_RANDOM && cur_rand_news >= newsList.size()) - cur_rand_news = 0; - } - - public: - OSNews(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - newsservice(this), commandoslogonnews(this), commandosopernews(this), commandosrandomnews(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandoslogonnews); - ModuleManager::RegisterService(&commandosopernews); - ModuleManager::RegisterService(&commandosrandomnews); - - Implementation i[] = { I_OnUserModeSet, I_OnUserConnect, I_OnDatabaseRead, I_OnDatabaseWrite }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&this->newsservice); - } - - void OnUserModeSet(User *u, UserModeName Name) - { - if (Name == UMODE_OPER) - DisplayNews(u, NEWS_OPER); - } - - void OnUserConnect(dynamic_reference<User> &user, bool &) - { - if (!user || !user->server->IsSynced()) - return; - - DisplayNews(user, NEWS_LOGON); - DisplayNews(user, NEWS_RANDOM); - } - - EventReturn OnDatabaseRead(const std::vector<Anope::string> ¶ms) - { - if (params[0].equals_ci("OS") && params.size() >= 7 && params[1].equals_ci("NEWS")) - { - NewsItem *n = new NewsItem(); - // params[2] was news number - n->time = params[3].is_number_only() ? convertTo<time_t>(params[3]) : 0; - n->who = params[4]; - if (params[5].equals_ci("LOGON")) - n->type = NEWS_LOGON; - else if (params[5].equals_ci("RANDOM")) - n->type = NEWS_RANDOM; - else if (params[5].equals_ci("OPER")) - n->type = NEWS_OPER; - n->text = params[6]; - - this->newsservice.AddNewsItem(n); - - return EVENT_STOP; - } - - return EVENT_CONTINUE; - } - - void OnDatabaseWrite(void (*Write)(const Anope::string &)) - { - for (unsigned i = 0; i < 3; ++i) - { - std::vector<NewsItem *> &list = this->newsservice.GetNewsList(static_cast<NewsType>(i)); - for (std::vector<NewsItem *>::iterator it = list.begin(); it != list.end(); ++it) - { - NewsItem *n = *it; - Anope::string ntype; - if (n->type == NEWS_LOGON) - ntype = "LOGON"; - else if (n->type == NEWS_RANDOM) - ntype = "RANDOM"; - else if (n->type == NEWS_OPER) - ntype = "OPER"; - Anope::string buf = "OS NEWS 0 " + stringify(n->time) + " " + n->who + " " + ntype + " :" + n->text; - Write(buf); - } - } - } -}; - -MODULE_INIT(OSNews) diff --git a/modules/core/os_news.h b/modules/core/os_news.h deleted file mode 100644 index c55f56d42..000000000 --- a/modules/core/os_news.h +++ /dev/null @@ -1,39 +0,0 @@ -#ifndef OS_NEWS -#define OS_NEWS - -enum NewsType -{ - NEWS_LOGON, - NEWS_RANDOM, - NEWS_OPER -}; - -struct NewsMessages -{ - NewsType type; - Anope::string name; - const char *msgs[10]; -}; - -struct NewsItem -{ - NewsType type; - Anope::string text; - Anope::string who; - time_t time; -}; - -class NewsService : public Service -{ - public: - NewsService(Module *m) : Service(m, "news") { } - - virtual void AddNewsItem(NewsItem *n) = 0; - - virtual void DelNewsItem(NewsItem *n) = 0; - - virtual std::vector<NewsItem *> &GetNewsList(NewsType t) = 0; -}; - -#endif // OS_NEWS - diff --git a/modules/core/os_noop.cpp b/modules/core/os_noop.cpp deleted file mode 100644 index 2eec522a3..000000000 --- a/modules/core/os_noop.cpp +++ /dev/null @@ -1,94 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSNOOP : public Command -{ - public: - CommandOSNOOP(Module *creator) : Command(creator, "operserv/noop", 2, 2) - { - this->SetDesc(_("Temporarily remove all O:lines of a server remotely")); - this->SetSyntax(_("SET \037server\037")); - this->SetSyntax(_("REVOKE \037server\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &cmd = params[0]; - const Anope::string &server = params[1]; - - Server *s = Server::Find(server); - if (s == NULL) - source.Reply(_("Server %s does not exist."), server.c_str()); - else if (cmd.equals_ci("SET")) - { - /* Remove the O:lines */ - ircdproto->SendSVSNOOP(s, true); - - Log(LOG_ADMIN, u, this) << "SET on " << s->GetName(); - source.Reply(_("All O:lines of \002%s\002 have been removed."), s->GetName().c_str()); - - Anope::string reason = "NOOP command used by " + u->nick; - /* Kill all the IRCops of the server */ - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(); it != UserListByNick.end();) - { - User *u2 = it->second; - ++it; - - if (u2 && u2->HasMode(UMODE_OPER) && u2->server == s) - u2->Kill(Config->OperServ, reason); - } - } - else if (cmd.equals_ci("REVOKE")) - { - Log(LOG_ADMIN, u, this) << "REVOKE on " << s->GetName(); - ircdproto->SendSVSNOOP(s, false); - source.Reply(_("All O:lines of \002%s\002 have been reset."), s->GetName().c_str()); - } - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("\002NOOP SET\002 remove all O:lines of the given\n" - "\002server\002 and kill all IRCops currently on it to\n" - "prevent them from rehashing the server (because this\n" - "would just cancel the effect).\n" - "\002NOOP REVOKE\002 makes all removed O:lines available again\n" - "on the given \002server\002.\n")); - return true; - } -}; - -class OSNOOP : public Module -{ - CommandOSNOOP commandosnoop; - - public: - OSNOOP(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosnoop(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosnoop); - } -}; - -MODULE_INIT(OSNOOP) diff --git a/modules/core/os_oline.cpp b/modules/core/os_oline.cpp deleted file mode 100644 index adebc52a1..000000000 --- a/modules/core/os_oline.cpp +++ /dev/null @@ -1,83 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSOLine : public Command -{ - public: - CommandOSOLine(Module *creator) : Command(creator, "operserv/oline", 2, 2) - { - this->SetDesc(_("Give Operflags to a certain user")); - this->SetSyntax(_("\037nick\037 \037flags\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - const Anope::string &flag = params[1]; - User *u2 = NULL; - - /* let's check whether the user is online */ - if (!(u2 = finduser(nick))) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (u2 && flag[0] == '+') - { - ircdproto->SendSVSO(Config->OperServ, nick, flag); - u2->SetMode(source.owner, UMODE_OPER); - u2->SendMessage(source.owner, _("You are now an IRC Operator.")); - source.Reply(_("Operflags \002%s\002 have been added for \002%s\002."), flag.c_str(), nick.c_str()); - ircdproto->SendGlobops(source.owner, "\2%s\2 used OLINE for %s", u->nick.c_str(), nick.c_str()); - } - else if (u2 && flag[0] == '-') - { - ircdproto->SendSVSO(Config->OperServ, nick, flag); - source.Reply(_("Operflags \002%s\002 have been added for \002%s\002."), flag.c_str(), nick.c_str()); - ircdproto->SendGlobops(source.owner, "\2%s\2 used OLINE for %s", u->nick.c_str(), nick.c_str()); - } - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services Opers to give Operflags to any user.\n" - "Flags have to be prefixed with a \"+\" or a \"-\". To\n" - "remove all flags simply type a \"-\" instead of any flags.")); - return true; - } -}; - -class OSOLine : public Module -{ - CommandOSOLine commandosoline; - - public: - OSOLine(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosoline(this) - { - this->SetAuthor("Anope"); - - if (!ircd || !ircd->omode) - throw ModuleException("Your IRCd does not support OMODE."); - - ModuleManager::RegisterService(&commandosoline); - } -}; - -MODULE_INIT(OSOLine) diff --git a/modules/core/os_oper.cpp b/modules/core/os_oper.cpp deleted file mode 100644 index 237c0b5bc..000000000 --- a/modules/core/os_oper.cpp +++ /dev/null @@ -1,219 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSOper : public Command -{ - public: - CommandOSOper(Module *creator) : Command(creator, "operserv/oper", 1, 3) - { - this->SetDesc(_("View and change services operators")); - this->SetSyntax(_("ADD \037oper\037 \037type\037")); - this->SetSyntax(_("DEL [\037oper\037]")); - this->SetSyntax(_("INFO [\037type\037]")); - this->SetSyntax(_("LIST")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &subcommand = params[0]; - - if (subcommand.equals_ci("ADD") && params.size() > 2) - { - const Anope::string &oper = params[1]; - const Anope::string &type = params[2]; - - NickAlias *na = findnick(oper); - if (na == NULL) - source.Reply(NICK_X_NOT_REGISTERED, oper.c_str()); - else - { - OperType *ot = OperType::Find(type); - if (ot == NULL) - source.Reply(_("Oper type \2%s\2 has not been configured."), type.c_str()); - else - { - if (na->nc->o) - delete na->nc->o; - na->nc->o = new Oper(na->nc->display, "", "", ot); - - Log(LOG_ADMIN, source.u, this) << "ADD " << na->nick << " as type " << ot->GetName(); - source.Reply("%s (%s) added to the \2%s\2 list.", na->nick.c_str(), na->nc->display.c_str(), ot->GetName().c_str()); - } - } - } - else if (subcommand.equals_ci("DEL") && params.size() > 1) - { - const Anope::string &oper = params[1]; - - NickAlias *na = findnick(oper); - if (na == NULL) - source.Reply(NICK_X_NOT_REGISTERED, oper.c_str()); - else if (!na->nc || !na->nc->o) - source.Reply(_("Nick \2%s\2 is not a services operator."), oper.c_str()); - else - { - delete na->nc->o; - na->nc->o = NULL; - - Log(LOG_ADMIN, source.u, this) << "DEL " << na->nick; - source.Reply(_("Oper privileges removed from %s (%s)."), na->nick.c_str(), na->nc->display.c_str()); - } - } - else if (subcommand.equals_ci("LIST")) - { - source.Reply(_("Name Type")); - for (nickcore_map::const_iterator it = NickCoreList.begin(), it_end = NickCoreList.end(); it != it_end; ++it) - { - NickCore *nc = it->second; - - if (!nc->o) - continue; - - source.Reply(_("%-8s %s"), nc->o->name.c_str(), nc->o->ot->GetName().c_str()); - for (std::list<NickAlias *>::const_iterator it2 = nc->aliases.begin(), it2_end = nc->aliases.end(); it2 != it2_end; ++it2) - if (Oper::Find((*it2)->nick) != NULL) - source.Reply(_(" This oper is configured in the configuration file as %s"), (*it2)->nick.c_str()); - for (std::list<User *>::iterator uit = nc->Users.begin(); uit != nc->Users.end(); ++uit) - { - User *u = *uit; - source.Reply(_(" %s is online using this oper block."), u->nick.c_str()); - } - } - } - else if (subcommand.equals_ci("INFO") && params.size() > 1) - { - Anope::string fulltype = params[1]; - if (params.size() > 2) - fulltype += " " + params[2]; - OperType *ot = OperType::Find(fulltype); - if (ot == NULL) - source.Reply(_("Oper type \2%s\2 has not been configured."), fulltype.c_str()); - else - { - if (ot->GetCommands().empty()) - source.Reply(_("Opertype \2%s\2 has no allowed commands."), ot->GetName().c_str()); - else - { - source.Reply(_("Available commands for \2%s\2:"), ot->GetName().c_str()); - Anope::string buf; - for (std::list<Anope::string>::const_iterator it = ot->GetCommands().begin(), it_end = ot->GetCommands().end(); it != it_end; ++it) - { - buf += *it + " "; - if (buf.length() > 400) - { - source.Reply("%s", buf.c_str()); - buf.clear(); - } - } - if (!buf.empty()) - { - source.Reply("%s", buf.c_str()); - buf.clear(); - } - } - if (ot->GetPrivs().empty()) - source.Reply(_("Opertype \2%s\2 has no allowed privileges."), ot->GetName().c_str()); - else - { - source.Reply(_("Available privileges for \2%s\2:"), ot->GetName().c_str()); - Anope::string buf; - for (std::list<Anope::string>::const_iterator it = ot->GetPrivs().begin(), it_end = ot->GetPrivs().end(); it != it_end; ++it) - { - buf += *it + " "; - if (buf.length() > 400) - { - source.Reply("%s", buf.c_str()); - buf.clear(); - } - } - if (!buf.empty()) - { - source.Reply("%s", buf.c_str()); - buf.clear(); - } - } - if (!ot->modes.empty()) - source.Reply(_("Opertype \2%s\2 receives modes \2%s\2 once identifying."), ot->GetName().c_str(), ot->modes.c_str()); - } - } - else - this->OnSyntaxError(source, subcommand); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows you to change and view services operators.\n" - "Note that operators removed by this command but are still set in\n" - "the configuration file are not permanently affected by this.")); - return true; - } -}; - -class OSOper : public Module -{ - CommandOSOper commandosoper; - - public: - OSOper(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosoper(this) - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnDatabaseWrite, I_OnDatabaseRead }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&commandosoper); - } - - void OnDatabaseWrite(void (*Write)(const Anope::string &)) - { - for (nickcore_map::const_iterator it = NickCoreList.begin(), it_end = NickCoreList.end(); it != it_end; ++it) - { - NickCore *nc = it->second; - if (!nc->o) - continue; - bool found = false; - for (std::list<NickAlias *>::const_iterator it2 = nc->aliases.begin(), it2_end = nc->aliases.end(); it2 != it2_end; ++it2) - if (Oper::Find((*it2)->nick) != NULL) - found = true; - if (found == false) - { - Write("OPER " + nc->display + " :" + nc->o->ot->GetName()); - } - } - } - - EventReturn OnDatabaseRead(const std::vector<Anope::string> ¶ms) - { - if (params[0] == "OPER" && params.size() > 2) - { - NickCore *nc = findcore(params[1]); - if (!nc || nc->o) - return EVENT_CONTINUE; - OperType *ot = OperType::Find(params[2]); - if (ot == NULL) - return EVENT_CONTINUE; - nc->o = new Oper(nc->display, "", "", ot); - Log(LOG_NORMAL, "operserv/oper") << "Tied oper " << nc->display << " to type " << ot->GetName(); - } - return EVENT_CONTINUE; - } -}; - -MODULE_INIT(OSOper) diff --git a/modules/core/os_reload.cpp b/modules/core/os_reload.cpp deleted file mode 100644 index d4d8eac7c..000000000 --- a/modules/core/os_reload.cpp +++ /dev/null @@ -1,72 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSReload : public Command -{ - public: - CommandOSReload(Module *creator) : Command(creator, "operserv/reload", 0, 0) - { - this->SetDesc(_("Reload services' configuration file")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - ServerConfig *old_config = Config; - - try - { - Config = new ServerConfig(); - FOREACH_MOD(I_OnReload, OnReload()); - delete old_config; - source.Reply(_("Services' configuration file has been reloaded.")); - } - catch (const ConfigException &ex) - { - Config = old_config; - Log() << "Error reloading configuration file: " << ex.GetReason(); - source.Reply(_("Error reloading confguration file: ") + ex.GetReason()); - } - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Causes Services to reload the configuration file. Note that\n" - "some directives still need the restart of the Services to\n" - "take effect (such as Services' nicknames, activation of the \n" - "session limitation, etc.)")); - return true; - } -}; - -class OSReload : public Module -{ - CommandOSReload commandosreload; - - public: - OSReload(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosreload(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosreload); - } -}; - -MODULE_INIT(OSReload) diff --git a/modules/core/os_session.cpp b/modules/core/os_session.cpp deleted file mode 100644 index 990cd1b4b..000000000 --- a/modules/core/os_session.cpp +++ /dev/null @@ -1,749 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" -#include "os_session.h" - -static service_reference<SessionService> sessionservice("session"); - -class MySessionService : public SessionService -{ - SessionMap Sessions; - ExceptionVector Exceptions; - public: - MySessionService(Module *m) : SessionService(m) { } - - void AddException(Exception *e) - { - this->Exceptions.push_back(e); - } - - void DelException(Exception *e) - { - ExceptionVector::iterator it = std::find(this->Exceptions.begin(), this->Exceptions.end(), e); - if (it != this->Exceptions.end()) - this->Exceptions.erase(it); - } - - Exception *FindException(User *u) - { - for (std::vector<Exception *>::const_iterator it = this->Exceptions.begin(), it_end = this->Exceptions.end(); it != it_end; ++it) - { - Exception *e = *it; - if (Anope::Match(u->host, e->mask) || (u->ip() && Anope::Match(u->ip.addr(), e->mask))) - return e; - } - return NULL; - } - - Exception *FindException(const Anope::string &host) - { - for (std::vector<Exception *>::const_iterator it = this->Exceptions.begin(), it_end = this->Exceptions.end(); it != it_end; ++it) - { - Exception *e = *it; - if (Anope::Match(host, e->mask)) - return e; - } - - return NULL; - } - - ExceptionVector &GetExceptions() - { - return this->Exceptions; - } - - void AddSession(Session *s) - { - this->Sessions[s->host] = s; - } - - void DelSession(Session *s) - { - this->Sessions.erase(s->host); - } - - Session *FindSession(const Anope::string &mask) - { - SessionMap::iterator it = this->Sessions.find(mask); - if (it != this->Sessions.end()) - return it->second; - return NULL; - } - - SessionMap &GetSessions() - { - return this->Sessions; - } -}; - -class ExpireTimer : public Timer -{ - public: - ExpireTimer() : Timer(Config->ExpireTimeout, Anope::CurTime, true) { } - - void Tick(time_t) - { - if (!sessionservice) - return; - for (unsigned i = sessionservice->GetExceptions().size(); i > 0; --i) - { - Exception *e = sessionservice->GetExceptions()[i - 1]; - - if (!e->expires || e->expires > Anope::CurTime) - continue; - BotInfo *bi = findbot(Config->OperServ); - if (Config->WallExceptionExpire && bi) - ircdproto->SendGlobops(bi, "Session exception for %s has expired.", e->mask.c_str()); - sessionservice->DelException(e); - delete e; - } - } -}; - -class ExceptionDelCallback : public NumberList -{ - protected: - CommandSource &source; - unsigned Deleted; - public: - ExceptionDelCallback(CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, true), source(_source), Deleted(0) - { - } - - ~ExceptionDelCallback() - { - if (!Deleted) - source.Reply(_("No matching entries on session-limit exception list.")); - else if (Deleted == 1) - source.Reply(_("Deleted 1 entry from session-limit exception list.")); - else - source.Reply(_("Deleted %d entries from session-limit exception list."), Deleted); - } - - virtual void HandleNumber(unsigned Number) - { - if (!Number || Number > sessionservice->GetExceptions().size()) - return; - - ++Deleted; - - DoDel(source, Number - 1); - } - - static void DoDel(CommandSource &source, unsigned index) - { - Exception *e = sessionservice->GetExceptions()[index]; - FOREACH_MOD(I_OnExceptionDel, OnExceptionDel(source.u, e)); - - sessionservice->DelException(e); - delete e; - } -}; - -class ExceptionListCallback : public NumberList -{ - protected: - CommandSource &source; - bool SentHeader; - public: - ExceptionListCallback(CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, false), source(_source), SentHeader(false) - { - } - - virtual void HandleNumber(unsigned Number) - { - if (!Number || Number > sessionservice->GetExceptions().size()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current Session Limit Exception list:")); - source.Reply(_("Num Limit Host")); - } - - DoList(source, Number - 1); - } - - static void DoList(CommandSource &source, unsigned index) - { - if (index >= sessionservice->GetExceptions().size()) - return; - - source.Reply(_("%3d %4d %s"), index + 1, sessionservice->GetExceptions()[index]->limit, sessionservice->GetExceptions()[index]->mask.c_str()); - } -}; - -class ExceptionViewCallback : public ExceptionListCallback -{ - public: - ExceptionViewCallback(CommandSource &_source, const Anope::string &numlist) : ExceptionListCallback(_source, numlist) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number || Number > sessionservice->GetExceptions().size()) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current Session Limit Exception list:")); - } - - DoList(source, Number - 1); - } - - static void DoList(CommandSource &source, unsigned index) - { - if (index >= sessionservice->GetExceptions().size()) - return; - - Anope::string expirebuf = expire_left(source.u->Account(), sessionservice->GetExceptions()[index]->expires); - - source.Reply(_("%3d. %s (by %s on %s; %s)\n " " Limit: %-4d - %s"), index + 1, sessionservice->GetExceptions()[index]->mask.c_str(), !sessionservice->GetExceptions()[index]->who.empty() ? sessionservice->GetExceptions()[index]->who.c_str() : "<unknown>", do_strftime((sessionservice->GetExceptions()[index]->time ? sessionservice->GetExceptions()[index]->time : Anope::CurTime)).c_str(), expirebuf.c_str(), sessionservice->GetExceptions()[index]->limit, sessionservice->GetExceptions()[index]->reason.c_str()); - } -}; - -class CommandOSSession : public Command -{ - private: - void DoList(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - Anope::string param = params[1]; - - unsigned mincount = 0; - try - { - mincount = convertTo<unsigned>(param); - } - catch (const ConvertException &) { } - - if (mincount <= 1) - source.Reply(_("Invalid threshold value. It must be a valid integer greater than 1.")); - else - { - source.Reply(_("Hosts with at least \002%d\002 sessions:"), mincount); - source.Reply(_("Sessions Host")); - - for (SessionService::SessionMap::iterator it = sessionservice->GetSessions().begin(), it_end = sessionservice->GetSessions().end(); it != it_end; ++it) - { - Session *session = it->second; - - if (session->count >= mincount) - source.Reply(_("%6d %s"), session->count, session->host.c_str()); - } - } - - return; - } - - void DoView(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - Anope::string param = params[1]; - Session *session = sessionservice->FindSession(param); - - if (!session) - source.Reply(_("\002%s\002 not found on session list."), param.c_str()); - else - { - Exception *exception = sessionservice->FindException(param); - source.Reply(_("The host \002%s\002 currently has \002%d\002 sessions with a limit of \002%d\002."), param.c_str(), session->count, exception ? exception-> limit : Config->DefSessionLimit); - } - - return; - } - public: - CommandOSSession(Module *creator) : Command(creator, "operserv/session", 2, 2) - { - this->SetDesc(_("View the list of host sessions")); - this->SetSyntax(_("LIST \037threshold\037")); - this->SetSyntax(_("VIEW \037host\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[0]; - - if (!Config->LimitSessions) - { - source.Reply(_("Session limiting is disabled.")); - return; - } - - if (cmd.equals_ci("LIST")) - return this->DoList(source, params); - else if (cmd.equals_ci("VIEW")) - return this->DoView(source, params); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services Operators to view the session list.\n" - "\002SESSION LIST\002 lists hosts with at least \037threshold\037 sessions.\n" - "The threshold must be a number greater than 1. This is to \n" - "prevent accidental listing of the large number of single \n" - "session hosts.\n" - "\002SESSION VIEW\002 displays detailed information about a specific\n" - "host - including the current session count and session limit.\n" - "The \037host\037 value may not include wildcards.\n" - "See the \002EXCEPTION\002 help for more information about session\n" - "limiting and how to set session limits specific to certain\n" - "hosts and groups thereof.")); - return true; - } -}; - -class CommandOSException : public Command -{ - private: - void DoAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - Anope::string mask, expiry, limitstr; - unsigned last_param = 3; - - mask = params.size() > 1 ? params[1] : ""; - if (!mask.empty() && mask[0] == '+') - { - expiry = mask; - mask = params.size() > 2 ? params[2] : ""; - last_param = 4; - } - - limitstr = params.size() > last_param - 1 ? params[last_param - 1] : ""; - - if (params.size() <= last_param) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - Anope::string reason = params[last_param]; - if (last_param == 3 && params.size() > 4) - reason += " " + params[4]; - if (reason.empty()) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - time_t expires = !expiry.empty() ? dotime(expiry) : Config->ExceptionExpiry; - if (expires < 0) - { - source.Reply(BAD_EXPIRY_TIME); - return; - } - else if (expires > 0) - expires += Anope::CurTime; - - int limit = -1; - try - { - limit = convertTo<int>(limitstr); - } - catch (const ConvertException &) { } - - if (limit < 0 || limit > static_cast<int>(Config->MaxSessionLimit)) - { - source.Reply(_("Invalid session limit. It must be a valid integer greater than or equal to zero and less than \002%d\002."), Config->MaxSessionLimit); - return; - } - else - { - if (mask.find('!') != Anope::string::npos || mask.find('@') != Anope::string::npos) - { - source.Reply(_("Invalid hostmask. Only real hostmasks are valid as sessionservice->GetExceptions() are not matched against nicks or usernames.")); - return; - } - - for (std::vector<Exception *>::iterator it = sessionservice->GetExceptions().begin(), it_end = sessionservice->GetExceptions().end(); it != it_end; ++it) - { - Exception *e = *it; - if (e->mask.equals_ci(mask)) - { - if (e->limit != limit) - { - e->limit = limit; - source.Reply(_("Exception for \002%s\002 has been updated to %d."), mask.c_str(), e->limit); - } - else - source.Reply(_("\002%s\002 already exists on the EXCEPTION list."), mask.c_str()); - } - } - - Exception *exception = new Exception(); - exception->mask = mask; - exception->limit = limit; - exception->reason = reason; - exception->time = Anope::CurTime; - exception->who = u->nick; - exception->expires = expires; - - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnExceptionAdd, OnExceptionAdd(exception)); - if (MOD_RESULT == EVENT_STOP) - delete exception; - else - { - sessionservice->AddException(exception); - source.Reply(_("Session limit for \002%s\002 set to \002%d\002."), mask.c_str(), limit); - if (readonly) - source.Reply(READ_ONLY_MODE); - } - } - - return; - } - - void DoDel(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (mask.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - ExceptionDelCallback list(source, mask); - list.Process(); - } - else - { - unsigned i = 0, end = sessionservice->GetExceptions().size(); - for (; i < end; ++i) - if (mask.equals_ci(sessionservice->GetExceptions()[i]->mask)) - { - ExceptionDelCallback::DoDel(source, i); - source.Reply(_("\002%s\002 deleted from session-limit exception list."), mask.c_str()); - break; - } - if (i == end) - source.Reply(_("\002%s\002 not found on session-limit exception list."), mask.c_str()); - } - - if (readonly) - source.Reply(READ_ONLY_MODE); - - return; - } - - void DoMove(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &n1str = params.size() > 1 ? params[1] : ""; /* From position */ - const Anope::string &n2str = params.size() > 2 ? params[2] : ""; /* To position */ - int n1, n2; - - if (n2str.empty()) - { - this->OnSyntaxError(source, "MOVE"); - return; - } - - n1 = n2 = -1; - try - { - n1 = convertTo<int>(n1str); - n2 = convertTo<int>(n2str); - } - catch (const ConvertException &) { } - - if (n1 >= 0 && n1 < sessionservice->GetExceptions().size() && n2 >= 0 && n2 < sessionservice->GetExceptions().size() && n1 != n2) - { - Exception *temp = sessionservice->GetExceptions()[n1]; - sessionservice->GetExceptions()[n1] = sessionservice->GetExceptions()[n2]; - sessionservice->GetExceptions()[n2] = temp; - - source.Reply(_("Exception for \002%s\002 (#%d) moved to position \002%d\002."), sessionservice->GetExceptions()[n1]->mask.c_str(), n1 + 1, n2 + 1); - - if (readonly) - source.Reply(READ_ONLY_MODE); - } - else - this->OnSyntaxError(source, "MOVE"); - - return; - } - - void DoList(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - Anope::string mask = params.size() > 1 ? params[1] : ""; - - if (!mask.empty() && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - ExceptionListCallback list(source, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = sessionservice->GetExceptions().size(); i < end; ++i) - if (mask.empty() || Anope::Match(sessionservice->GetExceptions()[i]->mask, mask)) - { - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current Session Limit Exception list:")); - source.Reply(_("Num Limit Host")); - } - - ExceptionListCallback::DoList(source, i); - } - - if (!SentHeader) - source.Reply(_("No matching entries on session-limit exception list.")); - } - - return; - } - - void DoView(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - Anope::string mask = params.size() > 1 ? params[1] : ""; - - if (!mask.empty() && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - ExceptionViewCallback list(source, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = sessionservice->GetExceptions().size(); i < end; ++i) - if (mask.empty() || Anope::Match(sessionservice->GetExceptions()[i]->mask, mask)) - { - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current Session Limit Exception list:")); - } - - ExceptionViewCallback::DoList(source, i); - } - - if (!SentHeader) - source.Reply(_("No matching entries on session-limit exception list.")); - } - - return; - } - - public: - CommandOSException(Module *creator) : Command(creator, "operserv/exception", 1, 5) - { - this->SetDesc(_("Modify the session-limit exception list")); - this->SetSyntax(_("ADD [\037+expiry\037] \037mask\037 \037limit\037 \037reason\037")); - this->SetSyntax(_("DEL {\037mask\037 | \037list\037}")); - this->SetSyntax(_("MOVE \037num\037 \037position\037")); - this->SetSyntax(_("LIST [\037mask\037 | \037list\037]")); - this->SetSyntax(_("VIEW [\037mask\037 | \037list\037]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[0]; - - if (!Config->LimitSessions) - { - source.Reply(_("Session limiting is disabled.")); - return; - } - - if (cmd.equals_ci("ADD")) - return this->DoAdd(source, params); - else if (cmd.equals_ci("DEL")) - return this->DoDel(source, params); - else if (cmd.equals_ci("MOVE")) - return this->DoMove(source, params); - else if (cmd.equals_ci("LIST")) - return this->DoList(source, params); - else if (cmd.equals_ci("VIEW")) - return this->DoView(source, params); - else - this->OnSyntaxError(source, ""); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services Operators to manipulate the list of hosts that\n" - "have specific session limits - allowing certain machines, \n" - "such as shell servers, to carry more than the default number\n" - "of clients at a time. Once a host reaches its session limit,\n" - "all clients attempting to connect from that host will be\n" - "killed. Before the user is killed, they are notified, via a\n" - "/NOTICE from %s, of a source of help regarding session\n" - "limiting. The content of this notice is a config setting.\n"), - Config->OperServ.c_str()); - source.Reply(" "); - source.Reply(_("\002EXCEPTION ADD\002 adds the given host mask to the exception list.\n" - "Note that \002nick!user@host\002 and \002user@host\002 masks are invalid!\n" - "Only real host masks, such as \002box.host.dom\002 and \002*.host.dom\002,\n" - "are allowed because sessions limiting does not take nick or\n" - "user names into account. \037limit\037 must be a number greater than\n" - "or equal to zero. This determines how many sessions this host\n" - "may carry at a time. A value of zero means the host has an\n" - "unlimited session limit. See the \002AKILL\002 help for details about\n" - "the format of the optional \037expiry\037 parameter.\n" - "\002EXCEPTION DEL\002 removes the given mask from the exception list.\n" - "\002EXCEPTION MOVE\002 moves exception \037num\037 to \037position\037. The\n" - "sessionservice->GetExceptions() inbetween will be shifted up or down to fill the gap.\n" - "\002EXCEPTION LIST\002 and \002EXCEPTION VIEW\002 show all current\n" - "sessionservice->GetExceptions(); if the optional mask is given, the list is limited\n" - "to those sessionservice->GetExceptions() matching the mask. The difference is that\n" - "\002EXCEPTION VIEW\002 is more verbose, displaying the name of the\n" - "person who added the exception, its session limit, reason, \n" - "host mask and the expiry date and time.\n" - " \n" - "Note that a connecting client will \"use\" the first exception\n" - "their host matches.")); - return true; - } -}; - -class OSSession : public Module -{ - MySessionService ss; - ExpireTimer expiretimer; - CommandOSSession commandossession; - CommandOSException commandosexception; - service_reference<XLineManager> akills; - - void AddSession(User *u, bool exempt) - { - Session *session = this->ss.FindSession(u->host); - - if (session) - { - bool kill = false; - if (Config->DefSessionLimit && session->count >= Config->DefSessionLimit) - { - kill = true; - Exception *exception = this->ss.FindException(u); - if (exception) - { - kill = false; - if (exception->limit && session->count >= exception->limit) - kill = true; - } - } - - /* Previously on IRCds that send a QUIT (InspIRCD) when a user is killed, the session for a host was - * decremented in do_quit, which caused problems and fixed here - * - * Now, we create the user struture before calling this to fix some user tracking issues, - * so we must increment this here no matter what because it will either be - * decremented in do_kill or in do_quit - Adam - */ - ++session->count; - - if (kill && !exempt) - { - BotInfo *bi = findbot(Config->OperServ); - if (bi) - { - if (!Config->SessionLimitExceeded.empty()) - u->SendMessage(bi, Config->SessionLimitExceeded.c_str(), u->host.c_str()); - if (!Config->SessionLimitDetailsLoc.empty()) - u->SendMessage(bi, "%s", Config->SessionLimitDetailsLoc.c_str()); - } - - u->Kill(Config->OperServ, "Session limit exceeded"); - - ++session->hits; - if (Config->MaxSessionKill && session->hits >= Config->MaxSessionKill && akills) - { - const Anope::string &akillmask = "*@" + u->host; - const Anope::string &akillreason = "Session limit exceeded for " + u->host; - akills->Add(akillmask, Config->OperServ, Anope::CurTime + Config->SessionAutoKillExpiry, akillreason); - if (bi) - ircdproto->SendGlobops(bi, "Added a temporary AKILL for \2%s\2 due to excessive connections", akillmask.c_str()); - } - } - } - else - { - session = new Session(); - session->host = u->host; - session->count = 1; - session->hits = 0; - - this->ss.AddSession(session); - } - } - - void DelSession(User *u) - { - Session *session = this->ss.FindSession(u->host); - if (!session) - { - if (debug) - Log() << "session: Tried to delete non-existant session: " << u->host; - return; - } - - if (session->count > 1) - { - --session->count; - return; - } - - this->ss.DelSession(session); - delete session; - } - - public: - OSSession(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - ss(this), commandossession(this), commandosexception(this), akills("xlinemanager/sgline") - { - this->SetAuthor("Anope"); - - Implementation i[] = { I_OnUserConnect, I_OnUserLogoff }; - ModuleManager::Attach(i, this, sizeof(i) / sizeof(Implementation)); - - ModuleManager::RegisterService(&commandossession); - ModuleManager::RegisterService(&commandosexception); - - ModuleManager::RegisterService(&this->ss); - } - - void OnUserConnect(dynamic_reference<User> &user, bool &exempt) - { - if (user && Config->LimitSessions) - this->AddSession(user, exempt); - } - - void OnUserLogoff(User *u) - { - if (Config->LimitSessions && (!u->server || !u->server->IsULined())) - this->DelSession(u); - } -}; - -MODULE_INIT(OSSession) diff --git a/modules/core/os_session.h b/modules/core/os_session.h deleted file mode 100644 index faab37934..000000000 --- a/modules/core/os_session.h +++ /dev/null @@ -1,32 +0,0 @@ -#ifndef OS_SESSION_H -#define OS_SESSION_H - -class SessionService : public Service -{ - public: - typedef Anope::map<Session *> SessionMap; - typedef std::vector<Exception *> ExceptionVector; - - SessionService(Module *m) : Service(m, "session") { } - - virtual void AddException(Exception *e) = 0; - - virtual void DelException(Exception *e) = 0; - - virtual Exception *FindException(User *u) = 0; - - virtual Exception *FindException(const Anope::string &host) = 0; - - virtual ExceptionVector &GetExceptions() = 0; - - virtual void AddSession(Session *s) = 0; - - virtual void DelSession(Session *s) = 0; - - virtual Session *FindSession(const Anope::string &mask) = 0; - - virtual SessionMap &GetSessions() = 0; -}; - -#endif - diff --git a/modules/core/os_set.cpp b/modules/core/os_set.cpp deleted file mode 100644 index 2a50f851c..000000000 --- a/modules/core/os_set.cpp +++ /dev/null @@ -1,261 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSSet : public Command -{ - private: - void DoList(CommandSource &source) - { - Log(LOG_ADMIN, source.u, this); - - Anope::string index; - - index = readonly ? _("%s is enabled") : _("%s is disabled"); - source.Reply(index.c_str(), "READONLY"); - index = debug ? _("%s is enabled") : _("%s is disabled"); - source.Reply(index.c_str(), "DEBUG"); - index = noexpire ? _("%s is enabled") : _("%s is disabled"); - source.Reply(index.c_str(), "NOEXPIRE"); - - return; - } - - void DoSetReadOnly(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &setting = params.size() > 1 ? params[1] : ""; - - if (setting.empty()) - { - this->OnSyntaxError(source, "READONLY"); - return; - } - - if (setting.equals_ci("ON")) - { - readonly = true; - Log(LOG_ADMIN, u, this) << "READONLY ON"; - source.Reply(_("Services are now in \002read-only\002 mode.")); - } - else if (setting.equals_ci("OFF")) - { - readonly = false; - Log(LOG_ADMIN, u, this) << "READONLY OFF"; - source.Reply(_("Services are now in \002read-write\002 mode.")); - } - else - source.Reply(_("Setting for READONLY must be \002on\002 or \002off\002.")); - - return; - } - - void DoSetSuperAdmin(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &setting = params.size() > 1 ? params[1] : ""; - - if (setting.empty()) - { - this->OnSyntaxError(source, "SUPERADMIN"); - return; - } - - /** - * Allow the user to turn super admin on/off - * - * Rob - **/ - if (!Config->SuperAdmin) - source.Reply(_("SuperAdmin setting not enabled in services.conf")); - else if (setting.equals_ci("ON")) - { - u->isSuperAdmin = 1; - source.Reply(_("You are now a SuperAdmin")); - Log(LOG_ADMIN, u, this) << "SUPERADMIN ON"; - ircdproto->SendGlobops(source.owner, _("%s is now a Super-Admin"), u->nick.c_str()); - } - else if (setting.equals_ci("OFF")) - { - u->isSuperAdmin = 0; - source.Reply(_("You are no longer a SuperAdmin")); - Log(LOG_ADMIN, u, this) << "SUPERADMIN OFF"; - ircdproto->SendGlobops(source.owner, _("%s is no longer a Super-Admin"), u->nick.c_str()); - } - else - source.Reply(_("Setting for SuperAdmin must be \002on\002 or \002off\002 (must be enabled in services.conf)")); - - return; - } - - void DoSetDebug(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &setting = params.size() > 1 ? params[1] : ""; - - if (setting.empty()) - { - this->OnSyntaxError(source, "DEBUG"); - return; - } - - if (setting.equals_ci("ON")) - { - debug = 1; - Log(LOG_ADMIN, u, this) << "DEBUG ON"; - source.Reply(_("Services are now in debug mode.")); - } - else if (setting.equals_ci("OFF") || (setting[0] == '0' && setting.is_number_only() && !convertTo<int>(setting))) - { - Log(LOG_ADMIN, u, this) << "DEBUG OFF"; - debug = 0; - source.Reply(_("Services are now in non-debug mode.")); - } - else - { - try - { - debug = convertTo<int>(setting); - Log(LOG_ADMIN, u, this) << "DEBUG " << debug; - source.Reply(_("Services are now in debug mode (level %d)."), debug); - return; - } - catch (const ConvertException &) { } - - source.Reply(_("Setting for DEBUG must be \002ON\002, \002OFF\002, or a positive number.")); - } - - return; - } - - void DoSetNoExpire(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &setting = params.size() > 1 ? params[1] : ""; - - if (setting.empty()) - { - this->OnSyntaxError(source, "NOEXPIRE"); - return; - } - - if (setting.equals_ci("ON")) - { - noexpire = true; - Log(LOG_ADMIN, u, this) << "NOEXPIRE ON"; - source.Reply(_("Services are now in \002no expire\002 mode.")); - } - else if (setting.equals_ci("OFF")) - { - noexpire = false; - Log(LOG_ADMIN, u, this) << "NOEXPIRE OFF"; - source.Reply(_("Services are now in \002expire\002 mode.")); - } - else - source.Reply(_("Setting for NOEXPIRE must be \002on\002 or \002off\002.")); - - return; - } - public: - CommandOSSet(Module *creator) : Command(creator, "operserv/set", 1, 2) - { - this->SetDesc(_("Set various global Services options")); - this->SetSyntax(_("\037option\037 \037setting\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &option = params[0]; - - if (option.equals_ci("LIST")) - return this->DoList(source); - else if (option.equals_ci("READONLY")) - return this->DoSetReadOnly(source, params); - else if (option.equals_ci("SUPERADMIN")) - return this->DoSetSuperAdmin(source, params); - else if (option.equals_ci("DEBUG")) - return this->DoSetDebug(source, params); - else if (option.equals_ci("NOEXPIRE")) - return this->DoSetNoExpire(source, params); - else - source.Reply(_("Unknown option \002%s\002."), option.c_str()); - - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - if (subcommand.empty()) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Sets various global Services options. Option names\n" - "currently defined are:\n" - " READONLY Set read-only or read-write mode\n" - " DEBUG Activate or deactivate debug mode\n" - " NOEXPIRE Activate or deactivate no expire mode\n" - " SUPERADMIN Activate or deactivate super-admin mode\n" - " LIST List the options")); - } - else if (subcommand.equals_ci("LIST")) - source.Reply(_("Syntax: \002LIST\n" - "Display the various %s settings"), Config->OperServ.c_str()); - else if (subcommand.equals_ci("READONLY")) - source.Reply(_("Syntax: \002READONLY {ON | OFF}\002\n" - " \n" - "Sets read-only mode on or off. In read-only mode, normal\n" - "users will not be allowed to modify any Services data,\n" - "including channel and nickname access lists, etc. IRCops\n" - "with sufficient Services privileges will be able to modify\n" - "Services' AKILL list and drop or forbid nicknames and\n" - "channels, but any such changes will not be saved unless\n" - "read-only mode is deactivated before Services is terminated\n" - "or restarted.\n" - " \n" - "This option is equivalent to the command-line option\n" - "\002-readonly\002.")); - else if (subcommand.equals_ci("NOEXPIRE")) - source.Reply(_("Syntax: \002NOEXPIRE {ON | OFF}\002\n" - "Sets no expire mode on or off. In no expire mode, nicks,\n" - "channels, akills and exceptions won't expire until the\n" - "option is unset.\n" - "This option is equivalent to the command-line option\n" - "\002-noexpire\002.")); - else if (subcommand.equals_ci("SUPERADMIN")) - source.Reply(_("Syntax: \002SUPERADMIN {ON | OFF}\002\n" - "Setting this will grant you extra privileges such as the\n" - "ability to be \"founder\" on all channel's etc...\n" - "This option is \002not\002 persistent, and should only be used when\n" - "needed, and set back to OFF when no longer needed.")); - else - return false; - return true; - } -}; - -class OSSet : public Module -{ - CommandOSSet commandosset; - - public: - OSSet(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosset(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosset); - } -}; - -MODULE_INIT(OSSet) diff --git a/modules/core/os_shutdown.cpp b/modules/core/os_shutdown.cpp deleted file mode 100644 index bc3a19353..000000000 --- a/modules/core/os_shutdown.cpp +++ /dev/null @@ -1,117 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSQuit : public Command -{ - public: - CommandOSQuit(Module *creator) : Command(creator, "operserv/quit", 0, 0) - { - this->SetDesc(_("Terminate Services WITHOUT saving")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - quitmsg = "QUIT command received from " + u->nick; - quitting = true; - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Causes Services to do an immediate shutdown; databases are\n" - "\002not\002 saved. This command should not be used unless\n" - "damage to the in-memory copies of the databases is feared\n" - "and they should not be saved.")); - return true; - } -}; - -class CommandOSRestart : public Command -{ - public: - CommandOSRestart(Module *creator) : Command(creator, "operserv/restart", 0, 0) - { - this->SetDesc(_("Save databases and restart Services")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - quitmsg = "RESTART command received from " + u->nick; - save_databases(); - quitting = restarting = true; - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(_("Causes Services to save all databases and then restart\n" - "(i.e. exit and immediately re-run the executable).")); - return true; - } -}; - -class CommandOSShutdown : public Command -{ - public: - CommandOSShutdown(Module *creator) : Command(creator, "operserv/shutdown", 0, 0) - { - this->SetDesc(_("Terminate services with save")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - quitmsg = source.command + " command received from " + u->nick; - save_databases(); - quitting = true; - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Causes Services to save all databases and then shut down.")); - return true; - } -}; - -class OSShutdown : public Module -{ - CommandOSQuit commandosquit; - CommandOSRestart commandosrestart; - CommandOSShutdown commandosshutdown; - - public: - OSShutdown(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosquit(this), commandosrestart(this), commandosshutdown(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosquit); - ModuleManager::RegisterService(&commandosrestart); - ModuleManager::RegisterService(&commandosshutdown); - } -}; - -MODULE_INIT(OSShutdown) diff --git a/modules/core/os_stats.cpp b/modules/core/os_stats.cpp deleted file mode 100644 index 2c20395d0..000000000 --- a/modules/core/os_stats.cpp +++ /dev/null @@ -1,224 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -/** - * Count servers connected to server s - * @param s The server to start counting from - * @return Amount of servers connected to server s - **/ -static int stats_count_servers(Server *s) -{ - if (!s) - return 0; - - int count = 1; - - if (!s->GetLinks().empty()) - for (unsigned i = 0, j = s->GetLinks().size(); i < j; ++i) - count += stats_count_servers(s->GetLinks()[i]); - - return count; -} - -class CommandOSStats : public Command -{ - service_reference<XLineManager> akills, snlines, sqlines, szlines; - private: - void DoStatsAkill(CommandSource &source) - { - int timeout; - if (akills) - { - /* AKILLs */ - source.Reply(_("Current number of AKILLs: \002%d\002"), akills->GetCount()); - timeout = Config->AutokillExpiry + 59; - if (timeout >= 172800) - source.Reply(_("Default AKILL expiry time: \002%d days\002"), timeout / 86400); - else if (timeout >= 86400) - source.Reply(_("Default AKILL expiry time: \0021 day\002")); - else if (timeout >= 7200) - source.Reply(_("Default AKILL expiry time: \002%d hours\002"), timeout / 3600); - else if (timeout >= 3600) - source.Reply(_("Default AKILL expiry time: \0021 hour\002")); - else if (timeout >= 120) - source.Reply(_("Default AKILL expiry time: \002%d minutes\002"), timeout / 60); - else if (timeout >= 60) - source.Reply(_("Default AKILL expiry time: \0021 minute\002")); - else - source.Reply(_("Default AKILL expiry time: \002No expiration\002")); - } - if (ircd->snline && snlines) - { - /* SNLINEs */ - source.Reply(_("Current number of SNLINEs: \002%d\002"), snlines->GetCount()); - timeout = Config->SNLineExpiry + 59; - if (timeout >= 172800) - source.Reply(_("Default SNLINE expiry time: \002%d days\002"), timeout / 86400); - else if (timeout >= 86400) - source.Reply(_("Default SNLINE expiry time: \0021 day\002")); - else if (timeout >= 7200) - source.Reply(_("Default SNLINE expiry time: \002%d hours\002"), timeout / 3600); - else if (timeout >= 3600) - source.Reply(_("Default SNLINE expiry time: \0021 hour\002")); - else if (timeout >= 120) - source.Reply(_("Default SNLINE expiry time: \002%d minutes\002"), timeout / 60); - else if (timeout >= 60) - source.Reply(_("Default SNLINE expiry time: \0021 minute\002")); - else - source.Reply(_("Default SNLINE expiry time: \002No expiration\002")); - } - if (ircd->sqline && sqlines) - { - /* SQLINEs */ - source.Reply(_("Current number of SQLINEs: \002%d\002"), sqlines->GetCount()); - timeout = Config->SQLineExpiry + 59; - if (timeout >= 172800) - source.Reply(_("Default SQLINE expiry time: \002%d days\002"), timeout / 86400); - else if (timeout >= 86400) - source.Reply(_("Default SQLINE expiry time: \0021 day\002")); - else if (timeout >= 7200) - source.Reply(_("Default SQLINE expiry time: \002%d hours\002"), timeout / 3600); - else if (timeout >= 3600) - source.Reply(_("Default SQLINE expiry time: \0021 hour\002")); - else if (timeout >= 120) - source.Reply(_("Default SQLINE expiry time: \002%d minutes\002"), timeout / 60); - else if (timeout >= 60) - source.Reply(_("Default SQLINE expiry time: \0021 minute\002")); - else - source.Reply(_("Default SQLINE expiry time: \002No expiration\002")); - } - if (ircd->szline && szlines) - { - /* SZLINEs */ - source.Reply(_("Current number of SZLINEs: \002%d\002"), szlines->GetCount()); - timeout = Config->SZLineExpiry + 59; - if (timeout >= 172800) - source.Reply(_("Default SZLINE expiry time: \002%d days\002"), timeout / 86400); - else if (timeout >= 86400) - source.Reply(_("Default SZLINE expiry time: \0021 day\002")); - else if (timeout >= 7200) - source.Reply(_("Default SZLINE expiry time: \002%d hours\002"), timeout / 3600); - else if (timeout >= 3600) - source.Reply(_("Default SZLINE expiry time: \0021 hour\002")); - else if (timeout >= 120) - source.Reply(_("Default SZLINE expiry time: \002%d minutes\002"), timeout / 60); - else if (timeout >= 60) - source.Reply(_("Default SZLINE expiry time: \0021 minute\002")); - else - source.Reply(_("Default SZLINE expiry time: \002No expiration\002")); - } - return; - } - - void DoStatsReset(CommandSource &source) - { - maxusercnt = usercnt; - source.Reply(_("Statistics reset.")); - return; - } - - void DoStatsUptime(CommandSource &source) - { - time_t uptime = Anope::CurTime - start_time; - source.Reply(_("Current users: \002%d\002 (\002%d\002 ops)"), usercnt, opcnt); - source.Reply(_("Maximum users: \002%d\002 (%s)"), maxusercnt, do_strftime(maxusertime).c_str()); - source.Reply(_("Services up %s"), duration(uptime).c_str()); - - return; - } - - void DoStatsUplink(CommandSource &source) - { - Anope::string buf; - - for (unsigned j = 0; !Capab_Info[j].Token.empty(); ++j) - if (Capab.HasFlag(Capab_Info[j].Flag)) - buf += " " + Capab_Info[j].Token; - - if (!buf.empty()) - buf.erase(buf.begin()); - - source.Reply(_("Uplink server: %s"), Me->GetLinks().front()->GetName().c_str()); - source.Reply(_("Uplink capab: %s"), buf.c_str()); - source.Reply(_("Servers found: %d"), stats_count_servers(Me->GetLinks().front())); - return; - } - - public: - CommandOSStats(Module *creator) : Command(creator, "operserv/stats", 0, 1), - akills("xlinemanager/sgline"), snlines("xlinemanager/snline"), sqlines("xlinemanager/sqline"), szlines("xlinemanager/szline") - { - this->SetDesc(_("Show status of Services and network")); - this->SetSyntax(_("[AKILL | ALL | RESET | UPLINK]")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - Anope::string extra = !params.empty() ? params[0] : ""; - - if (extra.equals_ci("RESET")) - return this->DoStatsReset(source); - - if (extra.equals_ci("ALL") || extra.equals_ci("AKILL")) - this->DoStatsAkill(source); - - if (extra.empty() || extra.equals_ci("ALL") || extra.equals_ci("UPTIME")) - this->DoStatsUptime(source); - - if (extra.equals_ci("ALL") || extra.equals_ci("UPLINK")) - this->DoStatsUplink(source); - - if (!extra.empty() && !extra.equals_ci("ALL") && !extra.equals_ci("AKILL") && !extra.equals_ci("UPLINK")) - source.Reply(_("Unknown STATS option \002%s\002."), extra.c_str()); - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Without any option, shows the current number of users online,\n" - "and the highest number of users online since Services was\n" - "started, and the length of time Services has been running.\n" - " \n" - "With the \002AKILL\002 option, displays the current size of the\n" - "AKILL list and the current default expiry time.\n" - " \n" - "The \002RESET\002 option currently resets the maximum user count\n" - "to the number of users currently present on the network.\n" - " \n" - "The \002UPLINK\002 option displays information about the current\n" - "server Anope uses as an uplink to the network.\n" - " \n" - "The \002ALL\002 displays the user and uptime statistics, and\n" - "everything you'd see with the \002UPLINK\002 option.")); - return true; - } -}; - -class OSStats : public Module -{ - CommandOSStats commandosstats; - - public: - OSStats(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosstats(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosstats); - } -}; - -MODULE_INIT(OSStats) diff --git a/modules/core/os_svsnick.cpp b/modules/core/os_svsnick.cpp deleted file mode 100644 index dc7c77a6c..000000000 --- a/modules/core/os_svsnick.cpp +++ /dev/null @@ -1,92 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSSVSNick : public Command -{ - public: - CommandOSSVSNick(Module *creator) : Command(creator, "operserv/svsnick", 2, 2) - { - this->SetDesc(_("Forcefully change a user's nickname")); - this->SetSyntax(_("\037nick\037 \037newnick\037")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - const Anope::string &nick = params[0]; - Anope::string newnick = params[1]; - User *u2; - - /* Truncate long nicknames to Config->NickLen characters */ - if (newnick.length() > Config->NickLen) - { - source.Reply(_("Nick \002%s\002 was truncated to %d characters."), newnick.c_str(), Config->NickLen, newnick.c_str()); - newnick = params[1].substr(0, Config->NickLen); - } - - /* Check for valid characters */ - if (newnick[0] == '-' || isdigit(newnick[0])) - { - source.Reply(_("Nick \002%s\002 is an illegal nickname and cannot be used."), newnick.c_str()); - return; - } - for (unsigned i = 0, end = newnick.length(); i < end; ++i) - if (!isvalidnick(newnick[i])) - { - source.Reply(_("Nick \002%s\002 is an illegal nickname and cannot be used."), newnick.c_str()); - return; - } - - /* Check for a nick in use or a forbidden/suspended nick */ - if (!(u2 = finduser(nick))) - source.Reply(NICK_X_NOT_IN_USE, nick.c_str()); - else if (finduser(newnick)) - source.Reply(_("Nick \002%s\002 is currently in use."), newnick.c_str()); - else - { - source.Reply(_("The nick \002%s\002 is now being changed to \002%s\002."), nick.c_str(), newnick.c_str()); - ircdproto->SendGlobops(source.owner, "%s used SVSNICK to change %s to %s", u->nick.c_str(), nick.c_str(), newnick.c_str()); - ircdproto->SendForceNickChange(u2, newnick, Anope::CurTime); - } - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Forcefully changes a user's nickname from nick to newnick.")); - return true; - } -}; - -class OSSVSNick : public Module -{ - CommandOSSVSNick commandossvsnick; - - public: - OSSVSNick(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandossvsnick(this) - { - this->SetAuthor("Anope"); - - if (!ircd || !ircd->svsnick) - throw ModuleException("Your IRCd does not support SVSNICK"); - - ModuleManager::RegisterService(&commandossvsnick); - } -}; - -MODULE_INIT(OSSVSNick) diff --git a/modules/core/os_sxline.cpp b/modules/core/os_sxline.cpp deleted file mode 100644 index f949cb7d2..000000000 --- a/modules/core/os_sxline.cpp +++ /dev/null @@ -1,807 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class SXLineDelCallback : public NumberList -{ - XLineManager *xlm; - Command *command; - CommandSource &source; - unsigned Deleted; - public: - SXLineDelCallback(XLineManager *x, Command *c, CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, true), xlm(x), command(c), source(_source), Deleted(0) - { - } - - ~SXLineDelCallback() - { - if (!Deleted) - source.Reply(_("No matching entries on the %s list."), this->command->name.c_str()); - else if (Deleted == 1) - source.Reply(_("Deleted 1 entry from the %s list."), this->command->name.c_str()); - else - source.Reply(_("Deleted %d entries from the %s list."), Deleted, this->command->name.c_str()); - } - - void HandleNumber(unsigned Number) - { - if (!Number) - return; - - XLine *x = this->xlm->GetEntry(Number - 1); - - if (!x) - return; - - ++Deleted; - DoDel(this->xlm, source, x); - } - - static void DoDel(XLineManager *xlm, CommandSource &source, XLine *x) - { - xlm->DelXLine(x); - } -}; - -class SXLineListCallback : public NumberList -{ - protected: - XLineManager *xlm; - Command *command; - CommandSource &source; - bool SentHeader; - public: - SXLineListCallback(XLineManager *x, Command *c, CommandSource &_source, const Anope::string &numlist) : NumberList(numlist, false), xlm(x), command(c), source(_source), SentHeader(false) - { - } - - ~SXLineListCallback() - { - if (!SentHeader) - source.Reply(_("No matching entries on the %s list."), this->command->name.c_str()); - } - - virtual void HandleNumber(unsigned Number) - { - if (!Number) - return; - - XLine *x = this->xlm->GetEntry(Number - 1); - - if (!x) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current %s list:\n Num Mask Reason"), this->command->name.c_str()); - } - - DoList(source, x, Number - 1); - } - - static void DoList(CommandSource &source, XLine *x, unsigned Number) - { - source.Reply(OPER_LIST_FORMAT, Number + 1, x->Mask.c_str(), x->Reason.c_str()); - } -}; - -class SXLineViewCallback : public SXLineListCallback -{ - public: - SXLineViewCallback(XLineManager *x, Command *c, CommandSource &_source, const Anope::string &numlist) : SXLineListCallback(x, c, _source, numlist) - { - } - - void HandleNumber(unsigned Number) - { - if (!Number) - return; - - XLine *x = this->xlm->GetEntry(Number - 1); - - if (!x) - return; - - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current %s list:"), this->command->name.c_str()); - } - - DoList(source, x, Number - 1); - } - - static void DoList(CommandSource &source, XLine *x, unsigned Number) - { - Anope::string expirebuf = expire_left(source.u->Account(), x->Expires); - source.Reply(OPER_VIEW_FORMAT, Number + 1, x->Mask.c_str(), x->By.c_str(), do_strftime(x->Created).c_str(), expirebuf.c_str(), x->Reason.c_str()); - } -}; - -class CommandOSSXLineBase : public Command -{ - private: - virtual XLineManager* xlm() = 0; - - virtual void OnAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) = 0; - - void OnDel(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - User *u = source.u; - - if (!this->xlm() || this->xlm()->GetList().empty()) - { - source.Reply(_("%s list is empty."), this->name.c_str()); - return; - } - - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (mask.empty()) - { - this->OnSyntaxError(source, "DEL"); - return; - } - - if (isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - SXLineDelCallback list(this->xlm(), this, source, mask); - list.Process(); - } - else - { - XLine *x = this->xlm()->HasEntry(mask); - - if (!x) - { - source.Reply(_("\002%s\002 not found on the %s list."), mask.c_str(), this->name.c_str()); - return; - } - - FOREACH_MOD(I_OnDelXLine, OnDelXLine(u, x, this->xlm())); - - SXLineDelCallback::DoDel(this->xlm(), source, x); - source.Reply(_("\002%s\002 deleted from the %s list."), mask.c_str(), this->name.c_str()); - } - - if (readonly) - source.Reply(READ_ONLY_MODE); - - return; - } - - void OnList(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!this->xlm() || this->xlm()->GetList().empty()) - { - source.Reply(_("%s list is empty."), this->name.c_str()); - return; - } - - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - SXLineListCallback list(this->xlm(), this, source, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = this->xlm()->GetCount(); i < end; ++i) - { - XLine *x = this->xlm()->GetEntry(i); - - if (mask.empty() || mask.equals_ci(x->Mask) || Anope::Match(x->Mask, mask)) - { - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current %s list:\n Num Mask Reason"), this->name.c_str()); - } - - SXLineListCallback::DoList(source, x, i); - } - } - - if (!SentHeader) - source.Reply(_("No matching entries on the %s list."), this->name.c_str()); - else - source.Reply(END_OF_ANY_LIST, this->name.c_str()); - } - - return; - } - - void OnView(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!this->xlm () || this->xlm()->GetList().empty()) - { - source.Reply(_("%s list is empty."), this->name.c_str()); - return; - } - - const Anope::string &mask = params.size() > 1 ? params[1] : ""; - - if (!mask.empty() && isdigit(mask[0]) && mask.find_first_not_of("1234567890,-") == Anope::string::npos) - { - SXLineViewCallback list(this->xlm(), this, source, mask); - list.Process(); - } - else - { - bool SentHeader = false; - - for (unsigned i = 0, end = this->xlm()->GetCount(); i < end; ++i) - { - XLine *x = this->xlm()->GetEntry(i); - - if (mask.empty() || mask.equals_ci(x->Mask) || Anope::Match(x->Mask, mask)) - { - if (!SentHeader) - { - SentHeader = true; - source.Reply(_("Current %s list:"), this->name.c_str()); - } - - SXLineViewCallback::DoList(source, x, i); - } - } - - if (!SentHeader) - source.Reply(_("No matching entries on the %s list."), this->name.c_str()); - } - - return; - } - - void OnClear(CommandSource &source) - { - User *u = source.u; - FOREACH_MOD(I_OnDelXLine, OnDelXLine(u, NULL, this->xlm())); - this->xlm()->Clear(); - source.Reply(_("The %s list has been cleared."), this->name.c_str()); - - return; - } - public: - CommandOSSXLineBase(Module *creator, const Anope::string &cmd) : Command(creator, cmd, 1, 3) - { - this->SetDesc(Anope::printf(_("Manipulate the %s list"), cmd.c_str())); - this->SetSyntax(_("ADD [+\037expiry\037] \037mask\037:\037reason\037")); - this->SetSyntax(_("DEL {\037mask\037 | \037entry-num\037 | \037list\037}")); - this->SetSyntax(_("LIST [\037mask\037 | \037list\037]")); - this->SetSyntax(_("VIEW [\037mask\037 | \037list\037]")); - this->SetSyntax(_("CLEAR")); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - const Anope::string &cmd = params[0]; - - if (cmd.equals_ci("ADD")) - return this->OnAdd(source, params); - else if (cmd.equals_ci("DEL")) - return this->OnDel(source, params); - else if (cmd.equals_ci("LIST")) - return this->OnList(source, params); - else if (cmd.equals_ci("VIEW")) - return this->OnView(source, params); - else if (cmd.equals_ci("CLEAR")) - return this->OnClear(source); - else - this->OnSyntaxError(source, ""); - - return; - } - - virtual bool OnHelp(CommandSource &source, const Anope::string &subcommand) = 0; -}; - -class CommandOSSNLine : public CommandOSSXLineBase -{ - XLineManager *xlm() - { - return this->snlines; - } - - void OnAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!this->xlm()) - return; - - User *u = source.u; - unsigned last_param = 2; - Anope::string param, expiry; - time_t expires; - - param = params.size() > 1 ? params[1] : ""; - if (!param.empty() && param[0] == '+') - { - expiry = param; - param = params.size() > 2 ? params[2] : ""; - last_param = 3; - } - - expires = !expiry.empty() ? dotime(expiry) : Config->SNLineExpiry; - /* If the expiry given does not contain a final letter, it's in days, - * said the doc. Ah well. - */ - if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) - expires *= 86400; - /* Do not allow less than a minute expiry time */ - if (expires && expires < 60) - { - source.Reply(BAD_EXPIRY_TIME); - return; - } - else if (expires > 0) - expires += Anope::CurTime; - - if (param.empty()) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - Anope::string rest = param; - if (params.size() > last_param) - rest += " " + params[last_param]; - - if (rest.find(':') == Anope::string::npos) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - sepstream sep(rest, ':'); - Anope::string mask; - sep.GetToken(mask); - Anope::string reason = sep.GetRemaining(); - - if (!mask.empty() && !reason.empty()) - { - std::pair<int, XLine *> canAdd = this->xlm()->CanAdd(mask, expires); - if (mask.find_first_not_of("*?") == Anope::string::npos) - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - else if (canAdd.first == 1) - source.Reply(_("\002%s\002 already exists on the %s list."), canAdd.second->Mask.c_str(), this->name.c_str()); - else if (canAdd.first == 2) - source.Reply(_("Expiry time of \002%s\002 changed."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 3) - source.Reply(_("\002%s\002 is already covered by %s."), mask.c_str(), canAdd.second->Mask.c_str()); - else - { - /* Clean up the last character of the mask if it is a space - * See bug #761 - */ - unsigned masklen = mask.length(); - if (mask[masklen - 1] == ' ') - mask.erase(masklen - 1); - unsigned int affected = 0; - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) - if (Anope::Match(it->second->realname, mask)) - ++affected; - float percent = static_cast<float>(affected) / static_cast<float>(UserListByNick.size()) * 100.0; - - if (percent > 95) - { - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - Log(LOG_ADMIN, u, this) << "tried to " << this->name << " " << percent << "% of the network (" << affected << " users)"; - return; - } - - XLine *x = this->xlm()->Add(mask, u->nick, expires, reason); - - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnAddXLine, OnAddXLine(u, x, this->xlm())); - if (MOD_RESULT == EVENT_STOP) - { - delete x; - return; - } - - source.Reply(_("\002%s\002 added to the %s list."), mask.c_str(), this->name.c_str()); - Log(LOG_ADMIN, u, this) << "on " << mask << " (" << reason << ") expires in " << (expires ? duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; - - if (readonly) - source.Reply(READ_ONLY_MODE); - } - - } - else - this->OnSyntaxError(source, "ADD"); - - return; - } - - service_reference<XLineManager> snlines; - public: - CommandOSSNLine(Module *creator) : CommandOSSXLineBase(creator, "operserv/snline"), snlines("xlinemanager/snline") - { - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services operators to manipulate the SNLINE list. If\n" - "a user with a realname matching an SNLINE mask attempts to \n" - "connect, Services will not allow it to pursue his IRC\n" - "session.\n")); - source.Reply(_(" \n" - "\002SNLINE ADD\002 adds the given realname mask to the SNLINE\n" - "list for the given reason (which \002must\002 be given).\n" - "\037expiry\037 is specified as an integer followed by one of \037d\037 \n" - "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as \n" - "\0371h30m\037) are not permitted. If a unit specifier is not \n" - "included, the default is days (so \037+30\037 by itself means 30 \n" - "days). To add an SNLINE which does not expire, use \037+0\037. If the\n" - "realname mask to be added starts with a \037+\037, an expiry time must\n" - "be given, even if it is the same as the default. The\n" - "current SNLINE default expiry time can be found with the\n" - "\002STATS AKILL\002 command.\n" - "Note: because the realname mask may contain spaces, the\n" - "separator between it and the reason is a colon.\n")); - source.Reply(_(" \n" - "The \002SNLINE DEL\002 command removes the given mask from the\n" - "SNLINE list if it is present. If a list of entry numbers is \n" - "given, those entries are deleted. (See the example for LIST \n" - "below.)\n" - " \n" - "The \002SNLINE LIST\002 command displays the SNLINE list. \n" - "If a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002SNLINE LIST 2-5,7-9\002\n" - " Lists SNLINE entries numbered 2 through 5 and 7 \n" - " through 9.\n" - " \n" - "\002SNLINE VIEW\002 is a more verbose version of \002SNLINE LIST\002, and \n" - "will show who added an SNLINE, the date it was added, and when \n" - "it expires, as well as the realname mask and reason.\n" - " \n" - "\002SNLINE CLEAR\002 clears all entries of the SNLINE list.")); - return true; - } -}; - -class CommandOSSQLine : public CommandOSSXLineBase -{ - XLineManager *xlm() - { - return this->sqlines; - } - - void OnAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!this->xlm()) - return; - - User *u = source.u; - unsigned last_param = 2; - Anope::string expiry, mask; - time_t expires; - - mask = params.size() > 1 ? params[1] : ""; - if (!mask.empty() && mask[0] == '+') - { - expiry = mask; - mask = params.size() > 2 ? params[2] : ""; - last_param = 3; - } - - expires = !expiry.empty() ? dotime(expiry) : Config->SQLineExpiry; - /* If the expiry given does not contain a final letter, it's in days, - * said the doc. Ah well. - */ - if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) - expires *= 86400; - /* Do not allow less than a minute expiry time */ - if (expires && expires < 60) - { - source.Reply(BAD_EXPIRY_TIME); - return; - } - else if (expires > 0) - expires += Anope::CurTime; - - if (params.size() <= last_param) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - Anope::string reason = params[last_param]; - if (last_param == 2 && params.size() > 3) - reason += " " + params[3]; - if (!mask.empty() && !reason.empty()) - { - std::pair<int, XLine *> canAdd = this->sqlines->CanAdd(mask, expires); - if (mask.find_first_not_of("*") == Anope::string::npos) - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - else if (canAdd.first == 1) - source.Reply(_("\002%s\002 already exists on the SQLINE list."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 2) - source.Reply(_("Expiry time of \002%s\002 changed."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 3) - source.Reply(_("\002%s\002 is already covered by %s."), mask.c_str(), canAdd.second->Mask.c_str()); - else - { - unsigned int affected = 0; - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) - if (Anope::Match(it->second->nick, mask)) - ++affected; - float percent = static_cast<float>(affected) / static_cast<float>(UserListByNick.size()) * 100.0; - - if (percent > 95) - { - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - Log(LOG_ADMIN, u, this) << "tried to SQLine " << percent << "% of the network (" << affected << " users)"; - return; - } - - XLine *x = this->sqlines->Add(mask, u->nick, expires, reason); - - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnAddXLine, OnAddXLine(u, x, this->xlm())); - if (MOD_RESULT == EVENT_STOP) - { - delete x; - return; - } - - source.Reply(_("\002%s\002 added to the SQLINE list."), mask.c_str()); - Log(LOG_ADMIN, u, this) << "on " << mask << " (" << reason << ") expires in " << (expires ? duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; - - if (readonly) - source.Reply(READ_ONLY_MODE); - } - - } - else - this->OnSyntaxError(source, "ADD"); - - return; - } - - service_reference<XLineManager> sqlines; - public: - CommandOSSQLine(Module *creator) : CommandOSSXLineBase(creator, "operserv/sqline"), sqlines("xlinemanager/sqline") - { - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services operators to manipulate the SQLINE list. If\n" - "a user with a nick matching an SQLINE mask attempts to \n" - "connect, Services will not allow it to pursue his IRC\n" - "session.\n" - "If the first character of the mask is #, services will \n" - "prevent the use of matching channels (on IRCds that \n" - "support it).\n")); - source.Reply(_(" \n" - "\002SQLINE ADD\002 adds the given (nick's) mask to the SQLINE\n" - "list for the given reason (which \002must\002 be given).\n" - "\037expiry\037 is specified as an integer followed by one of \037d\037 \n" - "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as \n" - "\0371h30m\037) are not permitted. If a unit specifier is not \n" - "included, the default is days (so \037+30\037 by itself means 30 \n" - "days). To add an SQLINE which does not expire, use \037+0\037. \n" - "If the mask to be added starts with a \037+\037, an expiry time \n" - "must be given, even if it is the same as the default. The\n" - "current SQLINE default expiry time can be found with the\n" - "\002STATS AKILL\002 command.\n")); - source.Reply(_(" \n" - "The \002SQLINE DEL\002 command removes the given mask from the\n" - "SQLINE list if it is present. If a list of entry numbers is \n" - "given, those entries are deleted. (See the example for LIST \n" - "below.)\n" - " \n" - "The \002SQLINE LIST\002 command displays the SQLINE list. \n" - "If a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002SQLINE LIST 2-5,7-9\002\n" - " Lists SQLINE entries numbered 2 through 5 and 7 \n" - " through 9.\n" - " \n" - "\002SQLINE VIEW\002 is a more verbose version of \002SQLINE LIST\002, and \n" - "will show who added an SQLINE, the date it was added, and when \n" - "it expires, as well as the mask and reason.\n" - " \n" - "\002SQLINE CLEAR\002 clears all entries of the SQLINE list.")); - return true; - } -}; - -class CommandOSSZLine : public CommandOSSXLineBase -{ - XLineManager *xlm() - { - return this->szlines; - } - - void OnAdd(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - if (!this->xlm()) - return; - - User *u = source.u; - unsigned last_param = 2; - Anope::string expiry, mask; - time_t expires; - - mask = params.size() > 1 ? params[1] : ""; - if (!mask.empty() && mask[0] == '+') - { - expiry = mask; - mask = params.size() > 2 ? params[2] : ""; - last_param = 3; - } - - expires = !expiry.empty() ? dotime(expiry) : Config->SZLineExpiry; - /* If the expiry given does not contain a final letter, it's in days, - * said the doc. Ah well. - */ - if (!expiry.empty() && isdigit(expiry[expiry.length() - 1])) - expires *= 86400; - /* Do not allow less than a minute expiry time */ - if (expires && expires < 60) - { - source.Reply(BAD_EXPIRY_TIME); - return; - } - else if (expires > 0) - expires += Anope::CurTime; - - if (params.size() <= last_param) - { - this->OnSyntaxError(source, "ADD"); - return; - } - - Anope::string reason = params[last_param]; - if (last_param == 2 && params.size() > 3) - reason += " " + params[3]; - if (!mask.empty() && !reason.empty()) - { - std::pair<int, XLine *> canAdd = this->szlines->CanAdd(mask, expires); - if (mask.find('!') != Anope::string::npos || mask.find('@') != Anope::string::npos) - source.Reply(_("You can only add IP masks to the SZLINE list.")); - else if (mask.find_first_not_of("*?") == Anope::string::npos) - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - else if (canAdd.first == 1) - source.Reply(_("\002%s\002 already exists on the SZLINE list."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 2) - source.Reply(_("Expiry time of \002%s\002 changed."), canAdd.second->Mask.c_str()); - else if (canAdd.first == 3) - source.Reply(_("\002%s\002 is already covered by %s."), mask.c_str(), canAdd.second->Mask.c_str()); - else - { - User *user = finduser(mask); - if (user && user->ip()) - mask = user->ip.addr(); - unsigned int affected = 0; - for (Anope::insensitive_map<User *>::iterator it = UserListByNick.begin(); it != UserListByNick.end(); ++it) - if (it->second->ip() && Anope::Match(it->second->ip.addr(), mask)) - ++affected; - float percent = static_cast<float>(affected) / static_cast<float>(UserListByNick.size()) * 100.0; - - if (percent > 95) - { - source.Reply(USERHOST_MASK_TOO_WIDE, mask.c_str()); - Log(LOG_ADMIN, u, this) << "tried to SZLine " << percent << "% of the network (" << affected << " users)"; - return; - } - - XLine *x = this->szlines->Add(mask, u->nick, expires, reason); - - EventReturn MOD_RESULT; - FOREACH_RESULT(I_OnAddXLine, OnAddXLine(u, x, this->xlm())); - if (MOD_RESULT == EVENT_STOP) - { - delete x; - return; - } - - source.Reply(_("\002%s\002 added to the SZLINE list."), mask.c_str()); - Log(LOG_ADMIN, u, this) << "on " << mask << " (" << reason << ") expires in " << (expires ? duration(expires - Anope::CurTime) : "never") << " [affects " << affected << " user(s) (" << percent << "%)]"; - - if (readonly) - source.Reply(READ_ONLY_MODE); - } - - } - else - this->OnSyntaxError(source, "ADD"); - - return; - } - - service_reference<XLineManager> szlines; - public: - CommandOSSZLine(Module *creator) : CommandOSSXLineBase(creator, "operserv/szline"), szlines("xlinemanager/szline") - { - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Allows Services operators to manipulate the SZLINE list. If\n" - "a user with an IP matching an SZLINE mask attempts to \n" - "connect, Services will not allow it to pursue his IRC\n" - "session (and this, whether the IP has a PTR RR or not).\n" - " \n")); - source.Reply(_("\002SZLINE ADD\002 adds the given (nick's) IP mask to the SZLINE\n" - "list for the given reason (which \002must\002 be given).\n" - "\037expiry\037 is specified as an integer followed by one of \037d\037 \n" - "(days), \037h\037 (hours), or \037m\037 (minutes). Combinations (such as \n" - "\0371h30m\037) are not permitted. If a unit specifier is not \n" - "included, the default is days (so \037+30\037 by itself means 30 \n" - "days). To add an SZLINE which does not expire, use \037+0\037. If the\n" - "realname mask to be added starts with a \037+\037, an expiry time must\n" - "be given, even if it is the same as the default. The\n" - "current SZLINE default expiry time can be found with the\n" - "\002STATS AKILL\002 command.\n")); - source.Reply(_(" \n" - "The \002SZLINE DEL\002 command removes the given mask from the\n" - "SZLINE list if it is present. If a list of entry numbers is \n" - "given, those entries are deleted. (See the example for LIST \n" - "below.)\n" - " \n" - "The \002SZLINE LIST\002 command displays the SZLINE list.\n" - "If a wildcard mask is given, only those entries matching the\n" - "mask are displayed. If a list of entry numbers is given,\n" - "only those entries are shown; for example:\n" - " \002SZLINE LIST 2-5,7-9\002\n" - " Lists SZLINE entries numbered 2 through 5 and 7 \n" - " through 9.\n" - " \n" - "\002SZLINE VIEW\002 is a more verbose version of \002SZLINE LIST\002, and \n" - "will show who added an SZLINE, the date it was added, and when\n" - "it expires, as well as the IP mask and reason.\n" - " \n" - "\002SZLINE CLEAR\002 clears all entries of the SZLINE list.")); - return true; - } -}; - -class OSSXLine : public Module -{ - CommandOSSNLine commandossnline; - CommandOSSQLine commandossqline; - CommandOSSZLine commandosszline; - - public: - OSSXLine(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandossnline(this), commandossqline(this), commandosszline(this) - { - this->SetAuthor("Anope"); - - if (ircd && ircd->snline) - ModuleManager::RegisterService(&commandossnline); - if (ircd && ircd->sqline) - ModuleManager::RegisterService(&commandossqline); - if (ircd && ircd->szline) - ModuleManager::RegisterService(&commandosszline); - } -}; - -MODULE_INIT(OSSXLine) diff --git a/modules/core/os_update.cpp b/modules/core/os_update.cpp deleted file mode 100644 index 776835cf7..000000000 --- a/modules/core/os_update.cpp +++ /dev/null @@ -1,56 +0,0 @@ -/* OperServ core functions - * - * (C) 2003-2011 Anope Team - * Contact us at team@anope.org - * - * Please read COPYING and README for further details. - * - * Based on the original code of Epona by Lara. - * Based on the original code of Services by Andy Church. - */ - -/*************************************************************************/ - -#include "module.h" - -class CommandOSUpdate : public Command -{ - public: - CommandOSUpdate(Module *creator) : Command(creator, "operserv/update", 0, 0) - { - this->SetDesc(_("Force the Services databases to be updated immediately")); - this->SetSyntax(""); - } - - void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) - { - source.Reply(_("Updating databases.")); - save_databases(); - return; - } - - bool OnHelp(CommandSource &source, const Anope::string &subcommand) - { - this->SendSyntax(source); - source.Reply(" "); - source.Reply(_("Causes Services to update all database files as soon as you\n" - "send the command.")); - return true; - } -}; - -class OSUpdate : public Module -{ - CommandOSUpdate commandosupdate; - - public: - OSUpdate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, CORE), - commandosupdate(this) - { - this->SetAuthor("Anope"); - - ModuleManager::RegisterService(&commandosupdate); - } -}; - -MODULE_INIT(OSUpdate) |
