/* BotServ vhost function * * Requires Fantasy setting to be on to work using in channel * command !vhost . * * This sets a TEMPORARY vhost. If the user wants a pernanent * vhost they should use the normal vhost request system in * hostserv. * * * * You need to set * /chanserv levels #channel FANTASIA 0 * to allow anyone in the active channel to issue the command. * * * Configuration: * * Add to your botserv module config: * * vHostChannel = "#help" * vHostRestricted = "space speperated list of prohibited words" * * if vHostRestricted is empty, then only "admin" and "ircop" are protected. * if vHostRestricted begings with "none" then nothing is protested. * * Example: * * vHostRestricted = "admin ircop damn turn jerk sucker"; * * This would prevent any vhost mask that contained admin, ircop, damn, turn, jerk, or sucker. * Examples: * !vhost I.am.an.admin * !vhost Ircops.are.idiots * !vhost damn.the.torpedos * !vhost turn.up.the.volume * !vhost you.are.akk.jerks * !vhost you.are.suckers * * These would be prevented from being used by the config line above. * */ #include "module.h" class CommandBSVhost : public Command { std::vector defaults; int vHostRestrictedNr; private: bool isvalidchar(char c) { if ((c >= 'A' && c <= 'Z') || (c >= 'a' && c <= 'z') || (c >= '0' && c <= '9') || c == '.' || c == '-') return true; return false; } public: CommandBSVhost(Module *creator) : Command(creator, "botserv/vhost", 1, 2) { this->SetDesc(_("Enable a temporary vhost.")); this->SetSyntax(_("\037host name\037")); } void Execute(CommandSource &source, const std::vector ¶ms) anope_override { const Anope::string &vhost = params[0]; const Anope::string &vhost2 = params.size() > 1 ? params[1] : ""; const Anope::string &onlychan = Config->GetModule("botserv")->Get("vHostChannel","#help"); User *u = source.GetUser(); const NickAlias *na = NickAlias::Find(u->nick); const Anope::string &nid = u->GetIdent(); Anope::string target = ""; Anope::string chan = ""; Anope::string host = ""; Anope::string user = ""; spacesepstream(Config->GetModule("botserv")->Get("vHostRestricted","")).GetTokens(defaults); if (defaults.empty()) { defaults.push_back("ircop"); defaults.push_back("admin"); } else if (defaults[0].equals_ci("none")) defaults.clear(); vHostRestrictedNr = defaults.size(); if (vhost[0] == '#') { chan = vhost.c_str(); target = vhost2.c_str(); } else { target = vhost.c_str(); } if (!chan.empty()) { if(chan.equals_ci(onlychan.c_str()) != 1) { source.Reply(_("You can only issue this command in %s"),onlychan.c_str()); return; } } size_t a = target.find('@'); if (a == Anope::string::npos) host = target.c_str(); else { user = target.substr(0, a); host = target.substr(a + 1); } if (host.empty()) { this->OnSyntaxError(source, ""); return; } if (!user.empty()) { if (user.length() > Config->GetBlock("networkinfo")->Get("userlen")) { source.Reply(HOST_SET_IDENTTOOLONG, Config->GetBlock("networkinfo")->Get("userlen")); return; } else if (!IRCD->CanSetVIdent) { 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->GetBlock("networkinfo")->Get("hostlen")) { source.Reply(HOST_SET_TOOLONG, Config->GetBlock("networkinfo")->Get("hostlen")); return; } if (!IRCD->IsHostValid(host)) { source.Reply(HOST_SET_ERROR); return; } int idx; for (idx = 0; idx < vHostRestrictedNr; idx++) { if (target.find_ci(defaults[idx]) != Anope::string::npos) { source.Reply(_("Vhost invalid. Containes prohibited word %s."),defaults[idx].c_str()); return; } } if(na && u->Account() == na->nc && !na->HasVhost() && (u->chost.equals_ci(u->GetDisplayedHost()) || u->host.equals_ci(u->GetDisplayedHost()) ) ) { Log(LOG_COMMAND,source,this) << "to set Vhost to " << target.c_str(); IRCD->SendVhost(u, nid.c_str(), target.c_str()); u->SetDisplayedHost(target.c_str()); // na->SetVhost(nid, target, source.GetNick()); // FOREACH_MOD(OnSetVhost, (na)); source.Reply(_("Vhost %s set."),target.c_str()); } else { source.Reply(_("You already have a vhost. You cannot set a temporary one.")); return; } } bool OnHelp(CommandSource &source, const Anope::string &subcommand) anope_override { this->SendSyntax(source); source.Reply(" "); source.Reply(_("Allows you to set a temproary vhost.")); return true; } }; class BSVhost : public Module { CommandBSVhost commandbsvhost; public: BSVhost(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR), commandbsvhost(this) { if (!IRCD || !IRCD->CanSetVHost) throw ModuleException("Your IRCd does not support vhosts"); if (Anope::VersionMajor() < 2) { throw ModuleException("Requires version 2 of Anope."); } this->SetAuthor("Azander"); this->SetVersion("1.0.1"); } }; MODULE_INIT(BSVhost)