* +------------------------------------+
*
* InspIRCd: (C) 2002-2009 InspIRCd Development Team
- * See: http://www.inspircd.org/wiki/index.php/Credits
+ * See: http://wiki.inspircd.org/Credits
*
* This program is free but copyrighted software; see
* the file COPYING for details.
char ModeHandler::GetNeededPrefix()
{
+ if (prefixneeded == '%' && !ServerInstance->Config->AllowHalfop)
+ return '@';
return prefixneeded;
}
User* targetuser = ServerInstance->FindNick(parameters[0]);
LastParse.clear();
+ LastParseParams.clear();
+ LastParseTranslate.clear();
/* Special case for displaying the list for listmodes,
* e.g. MODE #chan b, or MODE #chan +b without a parameter
if ((IS_LOCAL(user)) && (!ServerInstance->ULine(user->server)) && (!servermode))
{
+ /* Make modes that are being changed visible to OnAccessCheck */
+ LastParse = parameters[1];
/* We don't have halfop */
int MOD_RESULT = 0;
FOREACH_RESULT(I_OnAccessCheck,OnAccessCheck(user, NULL, targetchannel, AC_GENERAL_MODE));
+ LastParse.clear();
if (MOD_RESULT == ACR_DENY)
return;
SkipAccessChecks = (MOD_RESULT == ACR_ALLOW);
std::string mode_sequence = parameters[1];
std::string parameter;
std::ostringstream parameter_list;
- std::vector<TranslateType> parameter_xlate;
- parameter_xlate.push_back(TR_TEXT);
std::string output_sequence;
bool adding = true, state_change = false;
unsigned char handler_id = 0;
unsigned int parameter_counter = 2; /* Index of first parameter */
unsigned int parameter_count = 0;
bool last_successful_state_change = false;
+ LastParseTranslate.push_back(TR_TEXT);
/* A mode sequence that doesnt start with + or -. Assume +. - Thanks for the suggestion spike (bug#132) */
if ((*mode_sequence.begin() != '+') && (*mode_sequence.begin() != '-'))
/* If the mode defined by the handler is not '\0', but the handler for it
* cannot be found, they probably dont have the right module loaded to implement
* the prefix they want to compare the mode against, e.g. '&' for m_chanprotect.
- * Revert to checking against the minimum core prefix, '%'.
+ * Revert to checking against the minimum core prefix, '%' or '@'.
*/
if (needed && !prefixmode)
- prefixmode = FindPrefix('%');
+ prefixmode = ServerInstance->Config->AllowHalfop ? FindPrefix('%') : FindPrefix('@');
unsigned int neededrank = prefixmode->GetPrefixRank();
/* Compare our rank on the channel against the rank of the required prefix,
if ((modehandlers[handler_id]->GetNumParams(adding)) && (!parameter.empty()))
{
parameter_list << " " << parameter;
- parameter_xlate.push_back(modehandlers[handler_id]->GetTranslateType());
+ LastParseParams.push_back(parameter);
+ LastParseTranslate.push_back(modehandlers[handler_id]->GetTranslateType());
parameter_count++;
/* Does this mode have a prefix? */
if (modehandlers[handler_id]->GetPrefix() && targetchannel)
/* Was there at least one valid mode in the sequence? */
if (!output_sequence.empty())
{
+ LastParseParams.push_front(output_sequence);
if (servermode)
{
if (type == MODETYPE_CHANNEL)
if (type == MODETYPE_CHANNEL)
{
targetchannel->WriteChannel(user, "MODE %s %s%s", targetchannel->name.c_str(), output_sequence.c_str(), parameter_list.str().c_str());
- FOREACH_MOD(I_OnMode,OnMode(user, targetchannel, TYPE_CHANNEL, output_sequence + parameter_list.str(), parameter_xlate));
+ FOREACH_MOD(I_OnMode,OnMode(user, targetchannel, TYPE_CHANNEL, LastParseParams, LastParseTranslate));
this->LastParse = targetchannel->name;
}
else
{
user->WriteTo(targetuser, "MODE %s %s%s", targetuser->nick.c_str(), output_sequence.c_str(), parameter_list.str().c_str());
- FOREACH_MOD(I_OnMode,OnMode(user, targetuser, TYPE_USER, output_sequence + parameter_list.str(), parameter_xlate));
+ FOREACH_MOD(I_OnMode,OnMode(user, targetuser, TYPE_USER, LastParseParams, LastParseTranslate));
this->LastParse = targetuser->nick;
}
}