Beispiel #1
0
	bool OnHelp(CommandSource &source, const Anope::string &subcommand) override
	{
		if (subcommand.empty())
		{
			source.Reply(_("Sets various global Services options.  Option names 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"))
#warning "?"
			//source.Reply(_("Syntax: \002LIST\002\n"
			//		" \n"
			source.Reply(("Display the various {0} settings."), source.service->nick);
		else if (subcommand.equals_ci("READONLY"))
			//source.Reply(_("Syntax: \002READONLY {ON | OFF}\002\n"
			//		" \n"
			source.Reply(_("Sets read-only mode on or off.  In read-only mode, norma users will not be allowed to modify any Services data, including channel and nickname access lists, etc."
				       "Services Operators will still be able to do most tasks, but should understand any changes they do may not be permanent.\n"
				       "\n"
			               "This option is equivalent to the command-line option \002--readonly\002."));
		else if (subcommand.equals_ci("DEBUG"))
			//source.Reply(_("Syntax: \002DEBUG {ON | OFF}\002\n"
			//		" \n"
			source.Reply(_("Sets debug mode on or off.\n"
			               "\n"
			               "This option is equivalent to the command-line option \002--debug\002."));
		else if (subcommand.equals_ci("NOEXPIRE"))
			//source.Reply(_("Syntax: \002NOEXPIRE {ON | OFF}\002\n"
			//		" \n"
			source.Reply(_("Sets no expire mode on or off. In no expire mode, nicks, channels, akills and exceptions won't expire until the option is unset.\n"
			               "\n"
			               "This option is equivalent to the command-line option \002--noexpire\002."));
		else if (subcommand.equals_ci("SUPERADMIN"))
			//source.Reply(_("Syntax: \002SUPERADMIN {ON | OFF}\002\n"
			//		" \n"
			source.Reply(_("Setting this will grant you extra privileges, such as the ability to be \"founder\" on all channels."
			               "\n"
			               "This option is \002not\002 persistent, and should only be used when needed, and set back to OFF when no longer needed."));
		else
			return false;
		
		return true;
	}
Beispiel #2
0
	void DoAdd(CommandSource &source, ChanServ::Channel *ci, const Anope::string &word)
	{
		size_t pos = word.rfind(' ');
		BadWordType bwtype = 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"))
					bwtype = BW_SINGLE;
				else if (opt.equals_ci("START"))
					bwtype = BW_START;
				else if (opt.equals_ci("END"))
					bwtype = BW_END;
			}
			realword = word.substr(0, pos);
		}

		unsigned badwordsmax = Config->GetModule(this->module)->Get<unsigned>("badwordsmax");
		if (badwords->GetBadWordCount(ci) >= badwordsmax)
		{
			source.Reply(_("Sorry, you can only have \002{0}\002 bad words entries on a channel."), badwordsmax);
			return;
		}

		bool casesensitive = Config->GetModule(this->module)->Get<bool>("casesensitive");

		for (BadWord *bw : badwords->GetBadWords(ci))
			if ((casesensitive && realword.equals_cs(bw->GetWord())) || (!casesensitive && realword.equals_ci(bw->GetWord())))
			{
				source.Reply(_("\002{0}\002 already exists in \002{1}\002 bad words list."), bw->GetWord(), ci->GetName());
				return;
			}

		bool override = !source.AccessFor(ci).HasPriv("BADWORDS");
		Log(override ? LOG_OVERRIDE : LOG_COMMAND, source, this, ci) << "ADD " << realword;
		badwords->AddBadWord(ci, realword, bwtype);

		source.Reply(_("\002{0}\002 added to \002{1}\002 bad words list."), realword, ci->GetName());
	}
Beispiel #3
0
	void Run(CommandSource &source, const Anope::string &user, const Anope::string &param)
	{
		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");
	}
Beispiel #4
0
	int CountEmail(const Anope::string &email, NickServ::Account *unc)
	{
		int count = 0;

		if (email.empty())
			return 0;

		Anope::string cleanemail = clean ? CleanMail(email) : email;

		for (NickServ::Account *nc : NickServ::service->GetAccountList())
		{
			Anope::string cleannc = clean ? CleanMail(nc->GetEmail()) : nc->GetEmail();

			if (unc != nc && cleanemail.equals_ci(cleannc))
				++count;
		}

		return count;
	}
Beispiel #5
0
/**
 * Is the given nick a network service
 * @param nick to check
 * @param int Check if botserv bots
 * @return int
 */
bool nickIsServices(const Anope::string &tempnick, bool bot)
{
	if (tempnick.empty())
		return false;

	Anope::string nick = tempnick;

	size_t at = nick.find('@');
	if (at != Anope::string::npos)
	{
		Anope::string servername = nick.substr(at + 1);
		if (!servername.equals_ci(Config->ServerName))
			return false;
		nick = nick.substr(0, at);
	}

	BotInfo *bi = findbot(nick);
	if (bi)
		return bot ? true : bi->HasFlag(BI_CORE);
	return false;
}
Beispiel #6
0
	bool OnHelp(CommandSource &source, const Anope::string &subcommand) override
	{
		if (subcommand.empty())
		{
			CommandInfo *help = source.service->FindCommand("generic/help");
			if (!help)
				return false;
			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{0}{1} {2} {3} \037option\037\002 for more information on a specific option."),
			               Config->StrictPrivmsg, source.service->nick, help->cname, source.command);
		}
		else if (subcommand.equals_ci("NOTIFY"))
			source.Reply(_("Syntax: \002NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\002\n"
			               "\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"
			               "\n"
			               "    LOGON   You will only be notified of memos when you log\n"
			               "            on or when you unset /AWAY.\n"
			               "\n"
			               "    NEW     You will only be notified of memos when they\n"
			               "            are sent to you.\n"
			               "\n"
			               "    MAIL    You will be notified of memos by email as well as\n"
			               "            any other settings you have.\n"
			               "\n"
			               "    NOMAIL  You will not be notified of memos by email.\n"
			               "\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"))
		{
			int max_memos = Config->GetModule("memoserv")->Get<int>("maxmemos");
			if (source.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 allowed to have."
				               "  Setting the limit to 0 prevents the user from receiving any memos; setting it to \002NONE\002 allows the user to receive and keep as many memos as they want."
				               "  If you do not give a nickname or channel, your own limit is set.\n"
				               "\n"
				               "Adding \002HARD\002 prevents the user from changing the limit."
				               " Not adding \002HARD\002 has the opposite effect, allowing the user to change the limit, even if a previous limit was set.\n"
				               " \n"
				               "This use of the \002{0} LIMIT\002 command is limited to \002Services Operators\002."
				               " Other users may only enter a limit for themselves or a channel on which they have the \002MEMO\002 privilege on, may not remove their limit, may not set a limit above {1}, and may not set a hard limit."),
				               source.command, max_memos);
			else
				source.Reply(_("Syntax: \002LIMIT [\037channel\037] \037limit\037\002\n"
				               "\n"
				              "Sets the maximum number of memos you, or the given channel, are allowed to have."
				              " If you set this to 0, no one will be able to send any memos to you."
				              "However, you cannot set this any higher than {0}."), max_memos);
		}
		else
			return false;

		return true;
	}
Beispiel #7
0
	void Execute(CommandSource &source, const std::vector<Anope::string> &params) override
	{

		MemoServ::MemoInfo *mi;
		ChanServ::Channel *ci = NULL;
		Anope::string numstr = params[0], chan;

		if (!numstr.empty() && numstr[0] == '#')
		{
			chan = numstr;
			numstr = params.size() > 1 ? params[1] : "";

			ci = ChanServ::Find(chan);
			if (!ci)
			{
				source.Reply(_("Channel \002{0}\002 isn't registered."), chan);
				return;
			}

			if (!source.AccessFor(ci).HasPriv("MEMO"))
			{
				source.Reply(_("Access denied. You do not have privilege \002{0}\002 on \002{1}\002."), "MEMO", ci->GetName());
				return;
			}

			mi = ci->GetMemos();
		}
		else
			mi = source.nc->GetMemos();

		if (numstr.empty() || (!numstr.equals_ci("LAST") && !numstr.equals_ci("NEW") && !numstr.is_number_only()))
		{
			this->OnSyntaxError(source, numstr);
			return;
		}

		if (!mi)
			return;

		auto memos = mi->GetMemos();

		if (memos.empty())
		{
			if (!chan.empty())
				source.Reply(_("\002{0}\002 has no memos."), chan);
			else
				source.Reply(_("You have no memos."));
			return;
		}

		int i, end;

		if (numstr.equals_ci("NEW"))
		{
			int readcount = 0;
			for (i = 0, end = memos.size(); i < end; ++i)
				if (mi->GetMemo(i)->GetUnread())
				{
					DoRead(source, mi, ci, i);
					++readcount;
				}
			if (!readcount)
			{
				if (!chan.empty())
					source.Reply(_("\002{0}\002 has no new memos."), chan);
				else
					source.Reply(_("You have no new memos."));
			}
		}
		else if (numstr.equals_ci("LAST"))
		{
			for (i = 0, end = memos.size() - 1; i < end; ++i);
			DoRead(source, mi, ci, i);
		}
		else /* number[s] */
		{
			NumberList(numstr, false,
				[&](unsigned int number)
				{
					if (!number || number > memos.size())
						return;

					DoRead(source, mi, ci, number - 1);
				},
				[]{});
		}
	}
Beispiel #8
0
	void Execute(CommandSource &source, const std::vector<Anope::string> &params) override
	{

		Anope::string param = !params.empty() ? params[0] : "", chan;
		ChanServ::Channel *ci = NULL;
		MemoServ::MemoInfo *mi;

		if (!param.empty() && param[0] == '#')
		{
			chan = param;
			param = params.size() > 1 ? params[1] : "";

			ci = ChanServ::Find(chan);
			if (!ci)
			{
				source.Reply(_("Channel \002{0}\002 isn't registered."), chan);
				return;
			}

			if (!source.AccessFor(ci).HasPriv("MEMO"))
			{
				source.Reply(_("Access denied. You do not have privilege \002{0}\002 on \002{1}\002."), "MEMO", ci->GetName());
				return;
			}

			mi = ci->GetMemos();
		}
		else
		{
			mi = source.nc->GetMemos();
		}

		if (!param.empty() && !isdigit(param[0]) && !param.equals_ci("NEW"))
		{
			this->OnSyntaxError(source);
			return;
		}

		if (!mi)
			return;

		auto memos = mi->GetMemos();

		if (!memos.size())
		{
			if (!chan.empty())
				source.Reply(_("\002{0}\002 has no memos."), chan);
			else
				source.Reply(_("You have no memos."));
			return;
		}

		ListFormatter list(source.GetAccount());

		list.AddColumn(_("Number")).AddColumn(_("Sender")).AddColumn(_("Date/Time"));

		if (!param.empty() && isdigit(param[0]))
		{
			NumberList(param, false,
				[&](unsigned int number)
				{
					if (!number || number > memos.size())
						return;

					MemoServ::Memo *m = mi->GetMemo(number - 1);

					ListFormatter::ListEntry entry;
					entry["Number"] = (m->GetUnread() ? "* " : "  ") + stringify(number);
					entry["Sender"] = m->GetSender();
					entry["Date/Time"] = Anope::strftime(m->GetTime(), source.GetAccount());
					list.AddEntry(entry);
				},
				[]{});
		}
		else
		{
			if (!param.empty())
			{
				unsigned i, end;
				for (i = 0, end = memos.size(); i < end; ++i)
					if (mi->GetMemo(i)->GetUnread())
						break;
				if (i == end)
				{
					if (!chan.empty())
						source.Reply(_("\002{0}\002 has no new memos."), chan);
					else
						source.Reply(_("You have no new memos."));
					return;
				}
			}

			for (unsigned i = 0, end = memos.size(); i < end; ++i)
			{
				if (!param.empty() && !mi->GetMemo(i)->GetUnread())
					continue;

				MemoServ::Memo *m = mi->GetMemo(i);

				ListFormatter::ListEntry entry;
				entry["Number"] = (m->GetUnread() ? "* " : "  ") + stringify(i + 1);
				entry["Sender"] = m->GetSender();
				entry["Date/Time"] = Anope::strftime(m->GetTime(), source.GetAccount());
				list.AddEntry(entry);
			}
		}

		std::vector<Anope::string> replies;
		list.Process(replies);

		source.Reply(_("Memos for \002{0}\002:"), ci ? ci->GetName().c_str() : source.GetNick().c_str());
		for (unsigned i = 0; i < replies.size(); ++i)
			source.Reply(replies[i]);
	}
Beispiel #9
0
	void Execute(CommandSource &source, const std::vector<Anope::string> &params)
	{
		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->AccessFor(u).HasPriv("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 (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 persistent */
				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, &Config->BotModeList);
			}

			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 cloned to \002%s\002"), channel.c_str(), target.c_str());
		}
		else if (what.equals_ci("ACCESS"))
		{
			for (unsigned i = 0; i < ci->GetAccessCount(); ++i)
			{
				ChanAccess *taccess = ci->GetAccess(i);
				AccessProvider *provider = taccess->provider;

				ChanAccess *newaccess = provider->Create();
				newaccess->ci = target_ci;
				newaccess->mask = taccess->mask;
				newaccess->creator = taccess->creator;
				newaccess->last_seen = taccess->last_seen;
				newaccess->created = taccess->created;
				newaccess->Unserialize(taccess->Serialize());

				target_ci->AddAccess(newaccess);
			}

			source.Reply(_("All access entries from \002%s\002 have been cloned to \002%s\002"), channel.c_str(), target.c_str());
		}
		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 cloned 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 cloned to \002%s\002"), channel.c_str(), target.c_str());
		}
		else
		{
			this->OnSyntaxError(source, "");
			return;
		}

		Log(LOG_COMMAND, u, this, ci) << "to clone " << (what.empty() ? "everything from it" : what) << " to " << target_ci->name;

		return;
	}
Beispiel #10
0
	void Execute(CommandSource &source, const std::vector<Anope::string> &params) override
	{
		if (Anope::ReadOnly)
		{
			source.Reply(_("Services are in read-only mode."));
			return;
		}

		MemoServ::MemoInfo *mi;
		ChanServ::Channel *ci = NULL;
		Anope::string numstr = !params.empty() ? params[0] : "", chan;

		if (!numstr.empty() && numstr[0] == '#')
		{
			chan = numstr;
			numstr = params.size() > 1 ? params[1] : "";

			ci = ChanServ::Find(chan);
			if (!ci)
			{
				source.Reply(_("Channel \002{0}\002 isn't registered."), chan);
				return;
			}

			if (!source.AccessFor(ci).HasPriv("MEMO"))
			{
				source.Reply(_("Access denied. You do not have privilege \002{0}\002 on \002{1}\002."), "MEMO", ci->GetName());
				return;
			}

			mi = ci->GetMemos();
		}
		else
		{
			mi = source.nc->GetMemos();
		}

		if (numstr.empty() || (!isdigit(numstr[0]) && !numstr.equals_ci("ALL") && !numstr.equals_ci("LAST")))
		{
			this->OnSyntaxError(source, numstr);
			return;
		}

		if (!mi || mi->GetMemos().empty())
		{
			if (!chan.empty())
				source.Reply(_("\002{0}\002 has no memos."), chan);
			else
				source.Reply(_("You have no memos."));
			return;
		}

		auto memos = mi->GetMemos();

		if (isdigit(numstr[0]))
		{
			NumberList(numstr, true,
				[&](unsigned int number)
				{
					if (!number || number > memos.size())
						return;

					EventManager::Get()->Dispatch(&MemoServ::Event::MemoDel::OnMemoDel, ci ? ci->GetName() : source.nc->GetDisplay(), mi, mi->GetMemo(number - 1));

					mi->Del(number - 1);
					source.Reply(_("Memo \002{0}\002 has been deleted."), number);
				},
				[](){});
		}
		else if (numstr.equals_ci("LAST"))
		{
			/* Delete last memo. */
			EventManager::Get()->Dispatch(&MemoServ::Event::MemoDel::OnMemoDel, ci ? ci->GetName() : source.nc->GetDisplay(), mi, mi->GetMemo(memos.size() - 1));
			mi->Del(memos.size() - 1);
			source.Reply(_("Memo \002{0}\002 has been deleted."), memos.size() + 1);
		}
		else
		{
			/* Delete all memos. */
			std::for_each(memos.begin(), memos.end(),
			[&](MemoServ::Memo *m)
			{
				EventManager::Get()->Dispatch(&MemoServ::Event::MemoDel::OnMemoDel, ci ? ci->GetName() : source.nc->GetDisplay(), mi, m);
				delete m;
			});
			if (!chan.empty())
				source.Reply(_("All memos for channel \002{0}\002 have been deleted."), chan);
			else
				source.Reply(_("All of your memos have been deleted."));
		}
	}
Beispiel #11
0
	void Execute(CommandSource &source, const std::vector<Anope::string> &params) override
	{
		Anope::string extra = !params.empty() ? params[0] : "";

		Log(LOG_ADMIN, source, this) << extra;

		if (extra.equals_ci("RESET"))
			return this->DoStatsReset(source);

		if (extra.equals_ci("ALL") || extra.equals_ci("AKILL"))
			this->DoStatsAkill(source);

		if (extra.equals_ci("ALL") || extra.equals_ci("HASH"))
			this->DoStatsHash(source);

		if (extra.equals_ci("ALL") || extra.equals_ci("UPLINK"))
			this->DoStatsUplink(source);

		if (extra.empty() || extra.equals_ci("ALL") || extra.equals_ci("UPTIME"))
			this->DoStatsUptime(source);

		if (!extra.empty() && !extra.equals_ci("ALL") && !extra.equals_ci("AKILL") && !extra.equals_ci("HASH") && !extra.equals_ci("UPLINK") && !extra.equals_ci("UPTIME"))
			source.Reply(_("Unknown STATS option: \002{0}\002"), extra);
	}