mirror of
https://github.com/anope/anope.git
synced 2026-07-05 04:53:12 +02:00
Added cs_mode, rewrote the old list mode code, and added CIDR support
This commit is contained in:
+2
-1
@@ -639,6 +639,7 @@ log
|
||||
*
|
||||
* chanserv/access/list chanserv/drop chanserv/forbid chanserv/getkey
|
||||
* chanserv/list chanserv/suspend chanserv/topic chanserv/status
|
||||
* chanserv/mode
|
||||
*
|
||||
* chanserv/saset/bantype chanserv/saset/description chanserv/saset/email chanserv/saset/entrymsg
|
||||
* chanserv/saset/founder chanserv/saset/keeptopic chanserv/saset/opnotice
|
||||
@@ -1044,7 +1045,7 @@ chanserv
|
||||
* The core modules to load for ChanServ. This is a space separated list that corresponds
|
||||
* to the base names of the modules for ChanServ. This directive is optional, but highly recommended.
|
||||
*/
|
||||
modules = "cs_help cs_register cs_set cs_saset cs_saset_noexpire cs_set_bantype cs_set_description cs_set_entrymsg cs_set_founder cs_set_keeptopic cs_set_opnotice cs_set_peace cs_set_persist cs_set_private cs_set_restricted cs_set_secure cs_set_securefounder cs_set_secureops cs_set_signkick cs_set_successor cs_set_topiclock cs_set_xop cs_xop cs_access cs_akick cs_drop cs_ban cs_clearusers cs_modes cs_getkey cs_invite cs_kick cs_list cs_topic cs_info cs_forbid cs_suspend cs_status cs_unban cs_clone"
|
||||
modules = "cs_help cs_register cs_set cs_saset cs_saset_noexpire cs_set_bantype cs_set_description cs_set_entrymsg cs_set_founder cs_set_keeptopic cs_set_opnotice cs_set_peace cs_set_persist cs_set_private cs_set_restricted cs_set_secure cs_set_securefounder cs_set_secureops cs_set_signkick cs_set_successor cs_set_topiclock cs_set_xop cs_xop cs_access cs_akick cs_drop cs_ban cs_clearusers cs_modes cs_getkey cs_invite cs_kick cs_list cs_topic cs_info cs_forbid cs_suspend cs_status cs_unban cs_clone cs_mode"
|
||||
|
||||
/*
|
||||
* The default options for newly registered channels. Note that changing these options
|
||||
|
||||
@@ -111,6 +111,7 @@ CREATE TABLE IF NOT EXISTS `anope_cs_info` (
|
||||
`mlock_on` text NOT NULL,
|
||||
`mlock_off` text NOT NULL,
|
||||
`mlock_params` text NOT NULL,
|
||||
`mlock_params_off` text NOT NULL,
|
||||
`entry_message` text NOT NULL,
|
||||
`memomax` smallint(5) unsigned NOT NULL DEFAULT '0',
|
||||
`botnick` varchar(255) NOT NULL DEFAULT '',
|
||||
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
Anope Version 1.9.4
|
||||
-------------------
|
||||
memoserv:modules added ms_ignore
|
||||
chanserv:modules added cs_clone
|
||||
chanserv:modules added cs_clone and cs_mode
|
||||
|
||||
Anope Version 1.9.3
|
||||
------------------
|
||||
|
||||
@@ -106,18 +106,10 @@ How To Add IRCd Support
|
||||
|
||||
23) TS6: Does the IRCd support TS6? Use 1 for yes, 0 for no.
|
||||
|
||||
24) Channel CIDR: Set to 1 if channel bans, excepts and invites
|
||||
support CIDR masks. Expected syntax: *!*@ip/mask.
|
||||
When set to 1, anope will only parse strict CIDR masks.
|
||||
IRCd's that try to correct invalid CIDR's (like nefarious)
|
||||
will need a custom implementation in the core.
|
||||
Contact the anope Dev Team if this is the case.
|
||||
Set to 0 if CIDR's are not supported by your IRCd.
|
||||
|
||||
25) Global TLD Prefix: Prefix used to send global messages, should probably
|
||||
24) Global TLD Prefix: Prefix used to send global messages, should probably
|
||||
be "$"
|
||||
|
||||
26) Max Modes: The max number of mode changes we can send in one line
|
||||
25) Max Modes: The max number of mode changes we can send in one line
|
||||
|
||||
3) Modes
|
||||
|
||||
|
||||
+12
-44
@@ -64,13 +64,12 @@ enum ChannelFlags
|
||||
|
||||
class CoreExport Channel : public Extensible, public Flags<ChannelFlags>
|
||||
{
|
||||
public:
|
||||
typedef std::multimap<ChannelModeName, Anope::string> ModeList;
|
||||
private:
|
||||
/** A map of channel modes with their parameters set on this channel
|
||||
*/
|
||||
std::map<ChannelModeName, Anope::string> Params;
|
||||
|
||||
/* Modes set on the channel */
|
||||
Flags<ChannelModeName, CMODE_END * 2> modes;
|
||||
ModeList modes;
|
||||
|
||||
public:
|
||||
/** Default constructor
|
||||
@@ -87,10 +86,6 @@ class CoreExport Channel : public Extensible, public Flags<ChannelFlags>
|
||||
ChannelInfo *ci; /* Corresponding ChannelInfo */
|
||||
time_t creation_time; /* When channel was created */
|
||||
|
||||
EList *bans;
|
||||
EList *excepts;
|
||||
EList *invites;
|
||||
|
||||
/* List of users in the channel */
|
||||
CUserList users;
|
||||
|
||||
@@ -146,16 +141,18 @@ class CoreExport Channel : public Extensible, public Flags<ChannelFlags>
|
||||
*/
|
||||
bool HasUserStatus(User *u, ChannelModeName Name) const;
|
||||
|
||||
/** See if the channel has any modes at all
|
||||
* @return true or false
|
||||
*/
|
||||
inline bool HasModes() const { return modes.FlagCount(); }
|
||||
|
||||
/** See if a channel has a mode
|
||||
* @param Name The mode name
|
||||
* @return true or false
|
||||
* @return The number of modes set
|
||||
* @param param The optional mode param
|
||||
*/
|
||||
bool HasMode(ChannelModeName Name) const;
|
||||
size_t HasMode(ChannelModeName Name, const Anope::string ¶m = "");
|
||||
|
||||
/** Get a list of modes on a channel
|
||||
* @param Name A mode name to get the list of
|
||||
* @return a pair of iterators for the beginning and end of the list
|
||||
*/
|
||||
std::pair<ModeList::iterator, ModeList::iterator> GetModeList(ChannelModeName Name);
|
||||
|
||||
/** Set a mode internally on a channel, this is not sent out to the IRCd
|
||||
* @param cm The mode
|
||||
@@ -205,30 +202,6 @@ class CoreExport Channel : public Extensible, public Flags<ChannelFlags>
|
||||
*/
|
||||
void RemoveMode(BotInfo *bi, ChannelModeName Name, const Anope::string ¶m = "", bool EnforceMLock = true);
|
||||
|
||||
/** Clear all the modes from the channel
|
||||
* @param bi The client unsetting the modes
|
||||
* @param internal Only remove the modes internally
|
||||
*/
|
||||
void ClearModes(BotInfo *bi = NULL, bool internal = false);
|
||||
|
||||
/** Clear all the bans from the channel
|
||||
* @param bi The client unsetting the modes
|
||||
* @param internal Only remove the modes internally
|
||||
*/
|
||||
void ClearBans(BotInfo *bi = NULL, bool internal = false);
|
||||
|
||||
/** Clear all the excepts from the channel
|
||||
* @param bi The client unsetting the modes
|
||||
* @param internal Only remove the modes internally
|
||||
*/
|
||||
void ClearExcepts(BotInfo *bi = NULL, bool internal = false);
|
||||
|
||||
/** Clear all the invites from the channel
|
||||
* @param bi The client unsetting the modes
|
||||
* @param internal Only remove the modes internally
|
||||
*/
|
||||
void ClearInvites(BotInfo *bi = NULL, bool internal = false);
|
||||
|
||||
/** Get a param from the channel
|
||||
* @param Name The mode
|
||||
* @param Target a string to put the param into
|
||||
@@ -236,11 +209,6 @@ class CoreExport Channel : public Extensible, public Flags<ChannelFlags>
|
||||
*/
|
||||
bool GetParam(ChannelModeName Name, Anope::string &Target) const;
|
||||
|
||||
/** Check if a mode is set and has a param
|
||||
* @param Name The mode
|
||||
*/
|
||||
bool HasParam(ChannelModeName Name) const;
|
||||
|
||||
/** Set a string of modes on the channel
|
||||
* @param bi The client setting the modes
|
||||
* @param EnforceMLock Should mlock be enforced on this mode change
|
||||
|
||||
+1
-15
@@ -75,18 +75,6 @@ E void MassChannelModes(BotInfo *bi, const Anope::string &modes);
|
||||
|
||||
E void chan_set_correct_modes(User *user, Channel *c, int give_modes);
|
||||
|
||||
E Entry *entry_create(const Anope::string &mask);
|
||||
E Entry *entry_add(EList *list, const Anope::string &mask);
|
||||
E void entry_delete(EList *list, Entry *e);
|
||||
E EList *list_create();
|
||||
E int entry_match(Entry *e, const Anope::string &nick, const Anope::string &user, const Anope::string &host, uint32 ip);
|
||||
E int entry_match_mask(Entry *e, const Anope::string &mask, uint32 ip);
|
||||
E Entry *elist_match(EList *list, const Anope::string &nick, const Anope::string &user, const Anope::string &host, uint32 ip);
|
||||
E Entry *elist_match_mask(EList *list, const Anope::string &mask, uint32 ip);
|
||||
E Entry *elist_match_user(EList *list, User *u);
|
||||
E Entry *elist_find_mask(EList *list, const Anope::string &mask);
|
||||
E long get_memuse(EList *list);
|
||||
|
||||
inline BotInfo *whosends(ChannelInfo *ci)
|
||||
{
|
||||
if (!ci || !ci->bi || !ci->c || !ci->botflags.HasFlag(BS_SYMBIOSIS) || !ci->c->FindUser(ci->bi))
|
||||
@@ -272,9 +260,7 @@ E bool str_is_cidr(const Anope::string &str, uint32 &ip, uint32 &mask, Anope::st
|
||||
/**** modes.cpp ****/
|
||||
/* Number of generic modes we support */
|
||||
E unsigned GenericChannelModes, GenericUserModes;
|
||||
E Flags<ChannelModeName, CMODE_END * 2> DefMLockOn;
|
||||
E Flags<ChannelModeName, CMODE_END * 2> DefMLockOff;
|
||||
E std::map<ChannelModeName, Anope::string> DefMLockParams;
|
||||
E std::multimap<ChannelModeName, ModeLock> def_mode_locks;
|
||||
E void SetDefaultMLock(ServerConfig *config);
|
||||
|
||||
/**** nickserv.c ****/
|
||||
|
||||
+15
-14
@@ -274,7 +274,6 @@ enum LanguageString
|
||||
CHAN_LEVEL_INVITE,
|
||||
CHAN_LEVEL_AKICK,
|
||||
CHAN_LEVEL_SET,
|
||||
CHAN_LEVEL_CLEAR,
|
||||
CHAN_LEVEL_UNBAN,
|
||||
CHAN_LEVEL_OPDEOP,
|
||||
CHAN_LEVEL_ACCESS_LIST,
|
||||
@@ -300,6 +299,7 @@ enum LanguageString
|
||||
CHAN_LEVEL_BANME,
|
||||
CHAN_LEVEL_BAN,
|
||||
CHAN_LEVEL_TOPIC,
|
||||
CHAN_LEVEL_MODE,
|
||||
CHAN_LEVEL_INFO,
|
||||
CHAN_LEVEL_AUTOOWNER,
|
||||
CHAN_LEVEL_OWNER,
|
||||
@@ -555,13 +555,8 @@ enum LanguageString
|
||||
CHAN_UNBANNED,
|
||||
CHAN_UNBANNED_OTHER,
|
||||
CHAN_TOPIC_SYNTAX,
|
||||
CHAN_CLEAR_SYNTAX,
|
||||
CHAN_CLEARED_BANS,
|
||||
CHAN_CLEARED_EXCEPTS,
|
||||
CHAN_CLEARED_MODES,
|
||||
CHAN_CLEARED_OPS,
|
||||
CHAN_CLEARUSERS_SYNTAX,
|
||||
CHAN_CLEARED_USERS,
|
||||
CHAN_CLEARED_INVITES,
|
||||
CHAN_CLONED,
|
||||
CHAN_CLONED_ACCESS,
|
||||
CHAN_CLONED_AKICK,
|
||||
@@ -597,6 +592,15 @@ enum LanguageString
|
||||
CHAN_DEOWNER_SYNTAX,
|
||||
CHAN_KICK_SYNTAX,
|
||||
CHAN_BAN_SYNTAX,
|
||||
CHAN_MODE_SYNTAX,
|
||||
CHAN_MODE_LOCK_UNKNOWN,
|
||||
CHAN_MODE_LOCK_MISSING_PARAM,
|
||||
CHAN_MODE_LOCK_NONE,
|
||||
CHAN_MODE_LOCK_HEADER,
|
||||
CHAN_MODE_LOCKED,
|
||||
CHAN_MODE_NOT_LOCKED,
|
||||
CHAN_MODE_UNLOCKED,
|
||||
CHAN_MODE_LIST_FMT,
|
||||
MEMO_HAVE_NEW_MEMO,
|
||||
MEMO_HAVE_NEW_MEMOS,
|
||||
MEMO_TYPE_READ_LAST,
|
||||
@@ -931,9 +935,6 @@ enum LanguageString
|
||||
OPER_OLINE_SYNTAX,
|
||||
OPER_OLINE_SUCCESS,
|
||||
OPER_OLINE_IRCOP,
|
||||
OPER_CLEARMODES_SYNTAX,
|
||||
OPER_CLEARMODES_DONE,
|
||||
OPER_CLEARMODES_ALL_DONE,
|
||||
OPER_KICK_SYNTAX,
|
||||
OPER_SVSNICK_SYNTAX,
|
||||
OPER_SVSNICK_NEWNICK,
|
||||
@@ -1266,7 +1267,7 @@ enum LanguageString
|
||||
CHAN_HELP_CMD_AKICK,
|
||||
CHAN_HELP_CMD_DROP,
|
||||
CHAN_HELP_CMD_BAN,
|
||||
CHAN_HELP_CMD_CLEAR,
|
||||
CHAN_HELP_CMD_CLEARUSERS,
|
||||
CHAN_HELP_CMD_DEVOICE,
|
||||
CHAN_HELP_CMD_GETKEY,
|
||||
CHAN_HELP_CMD_INFO,
|
||||
@@ -1287,6 +1288,7 @@ enum LanguageString
|
||||
CHAN_HELP_CMD_PROTECT,
|
||||
CHAN_HELP_CMD_DEOP,
|
||||
CHAN_HELP_CMD_CLONE,
|
||||
CHAN_HELP_CMD_MODE,
|
||||
CHAN_HELP,
|
||||
CHAN_HELP_EXPIRES,
|
||||
CHAN_HELP_REGISTER,
|
||||
@@ -1358,9 +1360,10 @@ enum LanguageString
|
||||
CHAN_HELP_KICK,
|
||||
CHAN_HELP_BAN,
|
||||
CHAN_HELP_TOPIC,
|
||||
CHAN_HELP_CLEAR,
|
||||
CHAN_HELP_CLEARUSERS,
|
||||
CHAN_HELP_GETKEY,
|
||||
CHAN_HELP_CLONE,
|
||||
CHAN_HELP_MODE,
|
||||
CHAN_SERVADMIN_HELP,
|
||||
CHAN_SERVADMIN_HELP_DROP,
|
||||
CHAN_SERVADMIN_HELP_SET_NOEXPIRE,
|
||||
@@ -1403,7 +1406,6 @@ enum LanguageString
|
||||
OPER_HELP_CMD_STAFF,
|
||||
OPER_HELP_CMD_MODE,
|
||||
OPER_HELP_CMD_KICK,
|
||||
OPER_HELP_CMD_CLEARMODES,
|
||||
OPER_HELP_CMD_AKILL,
|
||||
OPER_HELP_CMD_SNLINE,
|
||||
OPER_HELP_CMD_SQLINE,
|
||||
@@ -1442,7 +1444,6 @@ enum LanguageString
|
||||
OPER_HELP_MODE,
|
||||
OPER_HELP_UMODE,
|
||||
OPER_HELP_OLINE,
|
||||
OPER_HELP_CLEARMODES,
|
||||
OPER_HELP_KICK,
|
||||
OPER_HELP_SVSNICK,
|
||||
OPER_HELP_AKILL,
|
||||
|
||||
+10
-10
@@ -185,17 +185,17 @@ class CoreExport ChannelModeList : public ChannelMode
|
||||
*/
|
||||
virtual bool IsValid(const Anope::string &mask) const { return true; }
|
||||
|
||||
/** Add the mask to the channel, this should be overridden
|
||||
/** Called when a mask is added to a channel
|
||||
* @param chan The channel
|
||||
* @param mask The mask
|
||||
*/
|
||||
virtual void AddMask(Channel *chan, const Anope::string &mask) { }
|
||||
virtual void OnAdd(Channel *chan, const Anope::string &mask) { }
|
||||
|
||||
/** Delete the mask from the channel, this should be overridden
|
||||
/** Called when a mask is removed from a channel
|
||||
* @param chan The channel
|
||||
* @param mask The mask
|
||||
*/
|
||||
virtual void DelMask(Channel *chan, const Anope::string &mask) { }
|
||||
virtual void OnDel(Channel *chan, const Anope::string &mask) { }
|
||||
|
||||
};
|
||||
|
||||
@@ -254,9 +254,9 @@ class CoreExport ChannelModeBan : public ChannelModeList
|
||||
public:
|
||||
ChannelModeBan(char modeChar) : ChannelModeList(CMODE_BAN, "CMODE_BAN", modeChar) { }
|
||||
|
||||
void AddMask(Channel *chan, const Anope::string &mask);
|
||||
void OnAdd(Channel *chan, const Anope::string &mask);
|
||||
|
||||
void DelMask(Channel *chan, const Anope::string &mask);
|
||||
void OnDel(Channel *chan, const Anope::string &mask);
|
||||
};
|
||||
|
||||
/** Channel mode +e
|
||||
@@ -266,9 +266,9 @@ class CoreExport ChannelModeExcept : public ChannelModeList
|
||||
public:
|
||||
ChannelModeExcept(char modeChar) : ChannelModeList(CMODE_EXCEPT, "CMODE_EXCEPT", modeChar) { }
|
||||
|
||||
void AddMask(Channel *chan, const Anope::string &mask);
|
||||
void OnAdd(Channel *chan, const Anope::string &mask);
|
||||
|
||||
void DelMask(Channel *chan, const Anope::string &mask);
|
||||
void OnDel(Channel *chan, const Anope::string &mask);
|
||||
};
|
||||
|
||||
/** Channel mode +I
|
||||
@@ -278,9 +278,9 @@ class CoreExport ChannelModeInvex : public ChannelModeList
|
||||
public:
|
||||
ChannelModeInvex(char modeChar) : ChannelModeList(CMODE_INVITEOVERRIDE, "CMODE_INVITEOVERRIDE", modeChar) { }
|
||||
|
||||
void AddMask(Channel *chan, const Anope::string &mask);
|
||||
void OnAdd(Channel *chan, const Anope::string &mask);
|
||||
|
||||
void DelMask(Channel *chan, const Anope::string &mask);
|
||||
void OnDel(Channel *chan, const Anope::string &mask);
|
||||
};
|
||||
|
||||
|
||||
|
||||
+6
-8
@@ -991,20 +991,18 @@ class CoreExport Module : public Extensible
|
||||
virtual void OnUserModeAdd(UserMode *um) { }
|
||||
|
||||
/** Called when a mode is about to be mlocked
|
||||
* @param ci The channel
|
||||
* @param Name The mode being mlocked
|
||||
* @param status true if its being mlocked +, false for -
|
||||
* @param param The param, if there is one and if status is true
|
||||
* @param ci The channel the mode is being locked on
|
||||
* @param lock The mode lock
|
||||
* @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to deny the mlock.
|
||||
*/
|
||||
virtual EventReturn OnMLock(ChannelInfo *ci, ChannelModeName Name, bool status, const Anope::string ¶m) { return EVENT_CONTINUE; }
|
||||
virtual EventReturn OnMLock(ChannelInfo *ci, ModeLock *lock) { return EVENT_CONTINUE; }
|
||||
|
||||
/** Called when a mode is about to be unlocked
|
||||
* @param ci The channel
|
||||
* @param Name The mode being mlocked
|
||||
* @param ci The channel the mode is being unlocked from
|
||||
* @param mode The mode being unlocked
|
||||
* @return EVENT_CONTINUE to let other modules decide, EVENT_STOP to deny the mlock.
|
||||
*/
|
||||
virtual EventReturn OnUnMLock(ChannelInfo *ci, ChannelModeName Name) { return EVENT_CONTINUE; }
|
||||
virtual EventReturn OnUnMLock(ChannelInfo *ci, ChannelMode *mode, const Anope::string ¶m) { return EVENT_CONTINUE; }
|
||||
|
||||
/** Called after a module is loaded
|
||||
* @param u The user loading the module, can be NULL
|
||||
|
||||
+37
-26
@@ -62,15 +62,26 @@ enum ChannelInfoFlag
|
||||
CI_END
|
||||
};
|
||||
|
||||
struct ModeLock
|
||||
{
|
||||
bool set;
|
||||
ChannelModeName name;
|
||||
Anope::string param;
|
||||
Anope::string setter;
|
||||
time_t created;
|
||||
|
||||
ModeLock(bool s, ChannelModeName n, const Anope::string &p, const Anope::string &se = "", time_t c = Anope::CurTime) : set(s), name(n), param(p), setter(se), created(c) { }
|
||||
};
|
||||
|
||||
class CoreExport ChannelInfo : public Extensible, public Flags<ChannelInfoFlag, CI_END>
|
||||
{
|
||||
private:
|
||||
std::map<ChannelModeName, Anope::string> Params; /* Map of parameters by mode name for mlock */
|
||||
typedef std::multimap<ChannelModeName, ModeLock> ModeList;
|
||||
private:
|
||||
std::vector<ChanAccess *> access; /* List of authorized users */
|
||||
std::vector<AutoKick *> akick; /* List of users to kickban */
|
||||
std::vector<BadWord *> badwords; /* List of badwords */
|
||||
Flags<ChannelModeName, CMODE_END * 2> mlock_on; /* Modes mlocked on */
|
||||
Flags<ChannelModeName, CMODE_END * 2> mlock_off; /* Modes mlocked off */
|
||||
ModeList mode_locks;
|
||||
|
||||
public:
|
||||
/** Default constructor
|
||||
@@ -241,51 +252,51 @@ class CoreExport ChannelInfo : public Extensible, public Flags<ChannelInfoFlag,
|
||||
void LoadMLock();
|
||||
|
||||
/** Check if a mode is mlocked
|
||||
* @param Name The mode
|
||||
* @param mode The mode
|
||||
* @param An optional param
|
||||
* @param status True to check mlock on, false for mlock off
|
||||
* @return true on success, false on fail
|
||||
*/
|
||||
bool HasMLock(ChannelModeName Name, bool status) const;
|
||||
bool HasMLock(ChannelMode *mode, const Anope::string ¶m, bool status) const;
|
||||
|
||||
/** Set a mlock
|
||||
* @param Name The mode
|
||||
* @param mode The mode
|
||||
* @param status True for mlock on, false for mlock off
|
||||
* @param param An optional param arg for + mlocked modes
|
||||
* @param setter Who is setting the mlock
|
||||
* @param created When the mlock was created
|
||||
* @return true on success, false on failure (module blocking)
|
||||
*/
|
||||
bool SetMLock(ChannelModeName Name, bool status, const Anope::string ¶m = "");
|
||||
bool SetMLock(ChannelMode *mode, bool status, const Anope::string ¶m = "", const Anope::string &setter = "", time_t created = Anope::CurTime);
|
||||
|
||||
/** Remove a mlock
|
||||
* @param Name The mode
|
||||
* @return true on success, false on failure (module blcoking)
|
||||
* @param mode The mode
|
||||
* @param param The param of the mode, required if it is a list or status mode
|
||||
* @return true on success, false on failure
|
||||
*/
|
||||
bool RemoveMLock(ChannelModeName Name);
|
||||
bool RemoveMLock(ChannelMode *mode, const Anope::string ¶m = "");
|
||||
|
||||
/** Clear all mlocks on the channel
|
||||
*/
|
||||
void ClearMLock();
|
||||
|
||||
/** Get the number of mlocked modes for this channel
|
||||
* @param status true for mlock on, false for mlock off
|
||||
* @return The number of mlocked modes
|
||||
/** Get all of the mlocks for this channel
|
||||
* @return The mlocks
|
||||
*/
|
||||
size_t GetMLockCount(bool status) const;
|
||||
const std::multimap<ChannelModeName, ModeLock> &GetMLock() const;
|
||||
|
||||
/** Get a param from the channel
|
||||
* @param Name The mode
|
||||
* @param Target a string to put the param into
|
||||
* @return true on success
|
||||
/** Get a list of modes on a channel
|
||||
* @param Name The mode name to get a list of
|
||||
* @return a pair of iterators for the beginning and end of the list
|
||||
*/
|
||||
bool GetParam(ChannelModeName Name, Anope::string &Target) const;
|
||||
std::pair<ModeList::iterator, ModeList::iterator> GetModeList(ChannelModeName Name);
|
||||
|
||||
/** Check if a mode is set and has a param
|
||||
* @param Name The mode
|
||||
/** Get details for a specific mlock
|
||||
* @param name The mode name
|
||||
* @param An optional param to match with
|
||||
* @return The MLock, if any
|
||||
*/
|
||||
bool HasParam(ChannelModeName Name) const;
|
||||
|
||||
/** Clear all the params from the channel
|
||||
*/
|
||||
void ClearParams();
|
||||
ModeLock *GetMLock(ChannelModeName name, const Anope::string ¶m = "");
|
||||
|
||||
/** Check whether a user is permitted to be on this channel
|
||||
* @param u The user
|
||||
|
||||
+22
-15
@@ -453,9 +453,6 @@ struct IRCDVar
|
||||
int svsmode_ucmode; /* Can remove User Channel Modes with SVSMODE */
|
||||
int sglineenforce;
|
||||
int ts6; /* ircd is TS6 */
|
||||
int cidrchanbei; /* channel bans/excepts/invites support CIDR (syntax: +b *!*@192.168.0.0/15)
|
||||
* 0 for no support, 1 for strict cidr support, anything else
|
||||
* for ircd specific support (nefarious only cares about first /mask) */
|
||||
const char *globaltldprefix; /* TLD prefix used for Global */
|
||||
unsigned maxmodes; /* Max modes to send per line */
|
||||
};
|
||||
@@ -636,7 +633,6 @@ enum ChannelAccess
|
||||
CA_AUTOVOICE,
|
||||
CA_OPDEOP, /* ChanServ commands OP and DEOP */
|
||||
CA_ACCESS_LIST,
|
||||
CA_CLEAR,
|
||||
CA_NOJOIN, /* Maximum */
|
||||
CA_ACCESS_CHANGE,
|
||||
CA_MEMO,
|
||||
@@ -662,6 +658,7 @@ enum ChannelAccess
|
||||
CA_BANME,
|
||||
CA_BAN,
|
||||
CA_TOPIC,
|
||||
CA_MODE,
|
||||
CA_INFO,
|
||||
CA_AUTOOWNER,
|
||||
CA_OWNER,
|
||||
@@ -756,7 +753,7 @@ struct LevelInfo
|
||||
enum EntryType
|
||||
{
|
||||
ENTRYTYPE_NONE,
|
||||
ENTRYTYPE_CIDR4,
|
||||
ENTRYTYPE_CIDR,
|
||||
ENTRYTYPE_NICK_WILD,
|
||||
ENTRYTYPE_NICK,
|
||||
ENTRYTYPE_USER_WILD,
|
||||
@@ -767,17 +764,27 @@ enum EntryType
|
||||
|
||||
class Entry : public Flags<EntryType>
|
||||
{
|
||||
public:
|
||||
Entry *next, *prev;
|
||||
uint32 cidr_ip; /* IP mask for CIDR matching */
|
||||
uint32 cidr_mask; /* Netmask for CIDR matching */
|
||||
Anope::string nick, user, host, mask;
|
||||
};
|
||||
Anope::string mask;
|
||||
|
||||
struct EList
|
||||
{
|
||||
Entry *entries;
|
||||
int32 count;
|
||||
public:
|
||||
unsigned char cidr_len;
|
||||
Anope::string nick, user, host;
|
||||
|
||||
/** Constructor
|
||||
* @param _host A full nick!ident@host/cidr mask
|
||||
*/
|
||||
Entry(const Anope::string &_host);
|
||||
|
||||
/** Get the banned mask for this entry
|
||||
* @return The mask
|
||||
*/
|
||||
const Anope::string GetMask();
|
||||
|
||||
/** Check if this entry matches a user
|
||||
* @param u The user
|
||||
* @return true on match
|
||||
*/
|
||||
bool Matches(User *u) const;
|
||||
};
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
@@ -80,6 +80,18 @@ union CoreExport sockaddrs
|
||||
void ntop(int type, const void *src);
|
||||
};
|
||||
|
||||
class CoreExport cidr
|
||||
{
|
||||
sockaddrs addr;
|
||||
Anope::string cidr_ip;
|
||||
unsigned char cidr_len;
|
||||
public:
|
||||
cidr(const Anope::string &ip);
|
||||
cidr(const Anope::string &ip, unsigned char len);
|
||||
Anope::string mask() const;
|
||||
bool match(sockaddrs &other);
|
||||
};
|
||||
|
||||
class SocketException : public CoreException
|
||||
{
|
||||
public:
|
||||
|
||||
@@ -139,6 +139,10 @@ class CoreExport User : public Extensible
|
||||
*/
|
||||
Anope::string GetMask() const;
|
||||
|
||||
/** Get the full display mask (nick!vident@vhost/chost)
|
||||
*/
|
||||
Anope::string GetDisplayedMask() const;
|
||||
|
||||
/** Updates the realname of the user record.
|
||||
*/
|
||||
void SetRealname(const Anope::string &realname);
|
||||
|
||||
@@ -28,15 +28,9 @@ class CommandCSClearUsers : public Command
|
||||
ChannelInfo *ci = c ? c->ci : NULL;
|
||||
Anope::string modebuf;
|
||||
|
||||
ChannelMode *owner = ModeManager::FindChannelModeByName(CMODE_OWNER);
|
||||
ChannelMode *admin = ModeManager::FindChannelModeByName(CMODE_PROTECT);
|
||||
ChannelMode *op = ModeManager::FindChannelModeByName(CMODE_OP);
|
||||
ChannelMode *halfop = ModeManager::FindChannelModeByName(CMODE_HALFOP);
|
||||
ChannelMode *voice = ModeManager::FindChannelModeByName(CMODE_VOICE);
|
||||
|
||||
if (!c)
|
||||
u->SendMessage(ChanServ, CHAN_X_NOT_IN_USE, chan.c_str());
|
||||
else if (!check_access(u, ci, CA_CLEAR))
|
||||
else if (!check_access(u, ci, CA_FOUNDER))
|
||||
u->SendMessage(ChanServ, ACCESS_DENIED);
|
||||
|
||||
Anope::string buf = "CLEAR USERS command from " + u->nick + " (" + u->Account()->display + ")";
|
||||
@@ -55,18 +49,18 @@ class CommandCSClearUsers : public Command
|
||||
|
||||
bool OnHelp(User *u, const Anope::string &subcommand)
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_HELP_CLEAR);
|
||||
u->SendMessage(ChanServ, CHAN_HELP_CLEARUSERS);
|
||||
return true;
|
||||
}
|
||||
|
||||
void OnSyntaxError(User *u, const Anope::string &subcommand)
|
||||
{
|
||||
SyntaxError(ChanServ, u, "CLEAR", CHAN_CLEAR_SYNTAX);
|
||||
SyntaxError(ChanServ, u, "CLEAR", CHAN_CLEARUSERS_SYNTAX);
|
||||
}
|
||||
|
||||
void OnServHelp(User *u)
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_HELP_CMD_CLEAR);
|
||||
u->SendMessage(ChanServ, CHAN_HELP_CMD_CLEARUSERS);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -63,12 +63,16 @@ class CommandCSForbid : public Command
|
||||
ci->forbidby = u->nick;
|
||||
ci->forbidreason = reason;
|
||||
|
||||
if ((c = findchan(ci->name)))
|
||||
if ((c = ci->c))
|
||||
{
|
||||
/* Before banning everyone, it might be prudent to clear +e and +I lists..
|
||||
* to prevent ppl from rejoining.. ~ Viper */
|
||||
c->ClearExcepts();
|
||||
c->ClearInvites();
|
||||
std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> modes = c->GetModeList(CMODE_EXCEPT);
|
||||
for (; modes.first != modes.second; ++modes.first)
|
||||
c->RemoveMode(NULL, CMODE_EXCEPT, modes.first->second);
|
||||
modes = c->GetModeList(CMODE_INVITEOVERRIDE);
|
||||
for (; modes.first != modes.second; ++modes.first)
|
||||
c->RemoveMode(NULL, CMODE_INVITEOVERRIDE, modes.first->second);
|
||||
|
||||
for (CUserList::iterator it = c->users.begin(), it_end = c->users.end(); it != it_end; )
|
||||
{
|
||||
|
||||
@@ -66,7 +66,8 @@ class CommandCSInfo : public Command
|
||||
u->SendMessage(ChanServ, CHAN_INFO_TIME_REGGED, do_strftime(ci->time_registered).c_str());
|
||||
u->SendMessage(ChanServ, CHAN_INFO_LAST_USED, do_strftime(ci->last_used).c_str());
|
||||
|
||||
if (!ci->last_topic.empty() && (show_all || (!ci->HasMLock(CMODE_SECRET, true) && (!ci->c || !ci->c->HasMode(CMODE_SECRET)))))
|
||||
ModeLock *secret = ci->GetMLock(CMODE_SECRET);
|
||||
if (!ci->last_topic.empty() && (show_all || ((!secret || secret->set == false) && (!ci->c || !ci->c->HasMode(CMODE_SECRET)))))
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_INFO_LAST_TOPIC, ci->last_topic.c_str());
|
||||
u->SendMessage(ChanServ, CHAN_INFO_TOPIC_SET_BY, ci->last_topic_setter.c_str());
|
||||
|
||||
@@ -0,0 +1,306 @@
|
||||
/* ChanServ core functions
|
||||
*
|
||||
* (C) 2003-2010 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
|
||||
{
|
||||
void DoLock(User *u, ChannelInfo *ci, const std::vector<Anope::string> ¶ms)
|
||||
{
|
||||
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))
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCK_UNKNOWN, 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)))
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCK_MISSING_PARAM, cm->ModeChar);
|
||||
else
|
||||
{
|
||||
ci->SetMLock(cm, adding, mode_param, u->nick);
|
||||
if (!mode_param.empty())
|
||||
mode_param = " " + mode_param;
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCKED, 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))
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCK_UNKNOWN, modes[i]);
|
||||
break;
|
||||
}
|
||||
Anope::string mode_param;
|
||||
if (!cm->Type == MODE_REGULAR && !sep.GetToken(mode_param))
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCK_MISSING_PARAM, cm->ModeChar);
|
||||
else
|
||||
{
|
||||
if (ci->RemoveMLock(cm, mode_param))
|
||||
{
|
||||
if (!mode_param.empty())
|
||||
mode_param = " " + mode_param;
|
||||
u->SendMessage(ChanServ, CHAN_MODE_UNLOCKED, adding == 1 ? '+' : '-', cm->ModeChar, mode_param.c_str(), ci->name.c_str());
|
||||
}
|
||||
else
|
||||
u->SendMessage(ChanServ, CHAN_MODE_NOT_LOCKED, cm->ModeChar, ci->name.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (subcommand.equals_ci("LIST"))
|
||||
{
|
||||
const std::multimap<ChannelModeName, ModeLock> &mlocks = ci->GetMLock();
|
||||
if (mlocks.empty())
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCK_NONE, ci->name.c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LOCK_HEADER, 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;
|
||||
Anope::string setter = ml.setter;
|
||||
if (setter.empty())
|
||||
setter = ci->founder ? ci->founder->display : "Unknown";
|
||||
u->SendMessage(ChanServ, CHAN_MODE_LIST_FMT, ml.set ? '+' : '-', cm->ModeChar, modeparam.c_str(), setter.c_str(), do_strftime(ml.created).c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
this->OnSyntaxError(u, subcommand);
|
||||
}
|
||||
|
||||
void DoSet(User *u, ChannelInfo *ci, const std::vector<Anope::string> ¶ms)
|
||||
{
|
||||
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 (std::map<Anope::string, Mode *>::const_iterator it = ModeManager::Modes.begin(), it_end = ModeManager::Modes.end(); it != it_end; ++it)
|
||||
{
|
||||
Mode *m = it->second;
|
||||
if (m->Class == MC_CHANNEL)
|
||||
{
|
||||
ChannelMode *cm = debug_cast<ChannelMode *>(m);
|
||||
if (cm->Type == MODE_REGULAR || (!adding && cm->Type == MODE_PARAM))
|
||||
{
|
||||
if (!cm->CanSet(u))
|
||||
continue;
|
||||
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 (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;
|
||||
|
||||
if (Anope::Match(u->GetMask(), param))
|
||||
{
|
||||
if (adding)
|
||||
ci->c->SetMode(NULL, cm, uc->user->nick);
|
||||
else
|
||||
ci->c->RemoveMode(NULL, cm, uc->user->nick);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
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() : Command("MODE", 3, 4)
|
||||
{
|
||||
}
|
||||
|
||||
CommandReturn Execute(User *u, const std::vector<Anope::string> ¶ms)
|
||||
{
|
||||
const Anope::string &subcommand = params[1];
|
||||
|
||||
ChannelInfo *ci = cs_findchan(params[0]);
|
||||
|
||||
if (!ci || !ci->c)
|
||||
u->SendMessage(ChanServ, CHAN_X_NOT_IN_USE, ci->name.c_str());
|
||||
else if (!check_access(u, ci, CA_MODE) && !u->Account()->HasCommand("chanserv/mode"))
|
||||
u->SendMessage(ChanServ, ACCESS_DENIED);
|
||||
else if (subcommand.equals_ci("LOCK"))
|
||||
this->DoLock(u, ci, params);
|
||||
else if (subcommand.equals_ci("SET"))
|
||||
this->DoSet(u, ci, params);
|
||||
else
|
||||
this->OnSyntaxError(u, "");
|
||||
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
bool OnHelp(User *u, const Anope::string &subcommand)
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_HELP_MODE);
|
||||
return true;
|
||||
}
|
||||
|
||||
void OnSyntaxError(User *u, const Anope::string &subcommand)
|
||||
{
|
||||
SyntaxError(ChanServ, u, "MODE", CHAN_MODE_SYNTAX);
|
||||
}
|
||||
|
||||
void OnServHelp(User *u)
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_HELP_CMD_MODE);
|
||||
}
|
||||
};
|
||||
|
||||
class CSMode : public Module
|
||||
{
|
||||
CommandCSMode commandcsmode;
|
||||
|
||||
public:
|
||||
CSMode(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator)
|
||||
{
|
||||
this->SetAuthor("Anope");
|
||||
this->SetType(CORE);
|
||||
|
||||
this->AddCommand(ChanServ, &commandcsmode);
|
||||
}
|
||||
};
|
||||
|
||||
MODULE_INIT(CSMode)
|
||||
@@ -44,7 +44,7 @@ class CommandCSSet : public Command
|
||||
// XXX Remove after 1.9.4 release
|
||||
if (params[1].equals_ci("MLOCK"))
|
||||
{
|
||||
u->SendMessage(ChanServ, CHAN_SET_MLOCK_DEPRECATED);
|
||||
u->SendMessage(ChanServ, CHAN_SET_MLOCK_DEPRECATED, Config->s_ChanServ.c_str());
|
||||
return MOD_CONT;
|
||||
}
|
||||
|
||||
|
||||
@@ -61,7 +61,7 @@ class CommandCSSetPersist : public Command
|
||||
if (ci->c && !ci->c->HasMode(CMODE_PERM))
|
||||
ci->c->SetMode(NULL, cm);
|
||||
/* Add it to the channels mlock */
|
||||
ci->SetMLock(CMODE_PERM, true);
|
||||
ci->SetMLock(cm, true);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -81,7 +81,7 @@ class CommandCSSetPersist : public Command
|
||||
if (ci->c && ci->c->HasMode(CMODE_PERM))
|
||||
ci->c->RemoveMode(NULL, cm);
|
||||
/* Remove from mlock */
|
||||
ci->RemoveMLock(CMODE_PERM);
|
||||
ci->RemoveMLock(cm);
|
||||
}
|
||||
|
||||
/* No channel mode, no BotServ, but using ChanServ as the botserv bot
|
||||
|
||||
+46
-29
@@ -258,7 +258,6 @@ ChannelLevel ChannelLevels[] = {
|
||||
{"AUTOVOICE", CA_AUTOVOICE},
|
||||
{"OPDEOP", CA_OPDEOP},
|
||||
{"ACCESS_LIST", CA_ACCESS_LIST},
|
||||
{"CLEAR", CA_CLEAR},
|
||||
{"NOJOIN", CA_NOJOIN},
|
||||
{"ACCESS_CHANGE", CA_ACCESS_CHANGE},
|
||||
{"MEMO", CA_MEMO},
|
||||
@@ -749,6 +748,16 @@ class DBPlain : public Module
|
||||
/* For now store mlocked modes in extensible, Anope hasn't yet connected to the IRCd and doesn't know what modes exist */
|
||||
ci->Extend("db_mlp", new ExtensibleItemRegular<std::vector<std::pair<Anope::string, Anope::string> > >(mlp));
|
||||
}
|
||||
else if (key.equals_ci("MLP_OFF"))
|
||||
{
|
||||
std::vector<std::pair<Anope::string, Anope::string> > mlp;
|
||||
ci->GetExtRegular("db_mlp_off", mlp);
|
||||
|
||||
mlp.push_back(std::make_pair(params[0], params[1]));
|
||||
|
||||
/* For now store mlocked modes in extensible, Anope hasn't yet connected to the IRCd and doesn't know what modes exist */
|
||||
ci->Extend("db_mlp_off", new ExtensibleItemRegular<std::vector<std::pair<Anope::string, Anope::string> > >(mlp));
|
||||
}
|
||||
else if (key.equals_ci("MI"))
|
||||
{
|
||||
Memo *m = new Memo;
|
||||
@@ -972,30 +981,29 @@ class DBPlain : public Module
|
||||
db << ci->GetAkick(k)->reason;
|
||||
db << endl;
|
||||
}
|
||||
if (ci->GetMLockCount(true))
|
||||
db << "MD MLOCK_ON";
|
||||
{
|
||||
db << "MD MLOCK_ON";
|
||||
|
||||
Anope::string oldmodes;
|
||||
if ((!Me || !Me->IsSynced()) && ci->GetExtRegular("db_mlock_modes_on", oldmodes))
|
||||
{
|
||||
db << " " << oldmodes;
|
||||
}
|
||||
else
|
||||
{
|
||||
for (std::map<char, ChannelMode *>::iterator it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
for (std::map<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it)
|
||||
{
|
||||
ChannelMode *cm = it->second;
|
||||
if (ci->HasMLock(cm->Name, true))
|
||||
const ModeLock &ml = it->second;
|
||||
if (ml.set)
|
||||
{
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name);
|
||||
if (!cm || cm->Type != MODE_REGULAR)
|
||||
continue;
|
||||
db << " " << cm->NameAsString;
|
||||
}
|
||||
}
|
||||
}
|
||||
db << endl;
|
||||
}
|
||||
if (ci->GetMLockCount(false))
|
||||
db << endl;
|
||||
db << "MD MLOCK_OFF";
|
||||
{
|
||||
db << "MD MLOCK_OFF";
|
||||
|
||||
Anope::string oldmodes;
|
||||
if ((!Me || !Me->IsSynced()) && ci->GetExtRegular("db_mlock_modes_off", oldmodes))
|
||||
{
|
||||
@@ -1003,32 +1011,41 @@ class DBPlain : public Module
|
||||
}
|
||||
else
|
||||
{
|
||||
for (std::map<char, ChannelMode *>::iterator it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
for (std::map<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it)
|
||||
{
|
||||
ChannelMode *cm = it->second;
|
||||
if (ci->HasMLock(cm->Name, false))
|
||||
const ModeLock &ml = it->second;
|
||||
if (!ml.set)
|
||||
{
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name);
|
||||
if (!cm || cm->Type != MODE_REGULAR)
|
||||
continue;
|
||||
db << " " << cm->NameAsString;
|
||||
}
|
||||
}
|
||||
}
|
||||
db << endl;
|
||||
}
|
||||
std::vector<std::pair<Anope::string, Anope::string> > oldparams;;
|
||||
if ((!Me || !Me->IsSynced()) && ci->GetExtRegular("db_mlp", oldparams))
|
||||
db << endl;
|
||||
{
|
||||
for (std::vector<std::pair<Anope::string, Anope::string> >::iterator it = oldparams.begin(), it_end = oldparams.end(); it != it_end; ++it)
|
||||
std::vector<std::pair<Anope::string, Anope::string> > oldparams;;
|
||||
if ((!Me || !Me->IsSynced()) && ci->GetExtRegular("db_mlp", oldparams))
|
||||
{
|
||||
db << "MD MLP " << it->first << " " << it->second << endl;
|
||||
for (std::vector<std::pair<Anope::string, Anope::string> >::iterator it = oldparams.begin(), it_end = oldparams.end(); it != it_end; ++it)
|
||||
{
|
||||
db << "MD MLP " << it->first << " " << it->second << endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for (std::map<char, ChannelMode *>::iterator it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
else
|
||||
{
|
||||
ChannelMode *cm = it->second;
|
||||
Anope::string Param;
|
||||
for (std::map<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)
|
||||
continue;
|
||||
|
||||
if (ci->GetParam(cm->Name, Param))
|
||||
db << "MD MLP " << cm->NameAsString << " " << Param << endl;
|
||||
if (!ml.param.empty())
|
||||
db << "MD MLP" << (ml.set ? " " : "_OFF ") << cm->NameAsString << " " << ml.param << endl;
|
||||
}
|
||||
}
|
||||
}
|
||||
MemoInfo *memos = &ci->memos;
|
||||
|
||||
@@ -207,7 +207,7 @@ class OSDefcon : public Module
|
||||
|
||||
EventReturn OnPreCommandRun(User *u, BotInfo *bi, Anope::string &command, Anope::string &message, bool fantasy)
|
||||
{
|
||||
if (!is_oper(u) && CheckDefCon(DEFCON_OPER_ONLY) || CheckDefCon(DEFCON_SILENT_OPER_ONLY))
|
||||
if (!is_oper(u) && (CheckDefCon(DEFCON_OPER_ONLY) || CheckDefCon(DEFCON_SILENT_OPER_ONLY)))
|
||||
{
|
||||
if (!CheckDefCon(DEFCON_SILENT_OPER_ONLY))
|
||||
u->SendMessage(bi, OPER_DEFCON_DENIED);
|
||||
|
||||
+35
-15
@@ -203,11 +203,16 @@ static Anope::string MakeMLock(ChannelInfo *ci, bool status)
|
||||
;
|
||||
else
|
||||
{
|
||||
for (std::map<char, ChannelMode *>::iterator it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
for (std::map<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it)
|
||||
{
|
||||
ChannelMode *cm = it->second;
|
||||
if (ci->HasMLock(cm->Name, status))
|
||||
const ModeLock &ml = it->second;
|
||||
if (ml.set == status)
|
||||
{
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name);
|
||||
if (!cm || cm->Type != MODE_REGULAR)
|
||||
continue;
|
||||
ret += " " + cm->NameAsString;
|
||||
}
|
||||
}
|
||||
|
||||
if (!ret.empty())
|
||||
@@ -227,12 +232,12 @@ static inline Anope::string GetMLockOff(ChannelInfo *ci)
|
||||
return MakeMLock(ci, false);
|
||||
}
|
||||
|
||||
static Anope::string GetMLockParams(ChannelInfo *ci)
|
||||
static Anope::string GetMLockParams(ChannelInfo *ci, bool onoff)
|
||||
{
|
||||
Anope::string ret;
|
||||
|
||||
std::vector<std::pair<Anope::string, Anope::string> > oldparams;;
|
||||
if ((!Me || !Me->IsSynced()) && ci->GetExtRegular("db_mlp", oldparams))
|
||||
if ((!Me || !Me->IsSynced()) && ci->GetExtRegular(onoff ? "db_mlp" : "db_mlp_off", oldparams))
|
||||
{
|
||||
for (std::vector<std::pair<Anope::string, Anope::string> >::iterator it = oldparams.begin(), it_end = oldparams.end(); it != it_end; ++it)
|
||||
{
|
||||
@@ -241,13 +246,16 @@ static Anope::string GetMLockParams(ChannelInfo *ci)
|
||||
}
|
||||
else
|
||||
{
|
||||
for (std::map<char, ChannelMode *>::iterator it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
for (std::map<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it)
|
||||
{
|
||||
ChannelMode *cm = it->second;
|
||||
const ModeLock &ml = it->second;
|
||||
|
||||
Anope::string param;
|
||||
if (ci->GetParam(cm->Name, param))
|
||||
ret += " " + cm->NameAsString + " " + param;
|
||||
if (!ml.param.empty() && ml.set == onoff)
|
||||
{
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name);
|
||||
if (cm)
|
||||
ret += " " + cm->NameAsString + " " + ml.param;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -661,10 +669,21 @@ class DBMySQL : public Module
|
||||
spacesepstream sep(r.Get(i, "mlock_params"));
|
||||
Anope::string buf, buf2;
|
||||
while (sep.GetToken(buf) && sep.GetToken(buf2))
|
||||
mlp.push_back(std::make_pair(Anope::string(buf), Anope::string(buf2)));
|
||||
mlp.push_back(std::make_pair(buf, buf2));
|
||||
|
||||
ci->Extend("db_mlp", new ExtensibleItemRegular<std::vector<std::pair<Anope::string, Anope::string> > >(mlp));
|
||||
}
|
||||
if (!r.Get(i, "mlock_params_off").empty())
|
||||
{
|
||||
std::vector<std::pair<Anope::string, Anope::string> > mlp;
|
||||
|
||||
spacesepstream sep(r.Get(i, "mlock_params_off"));
|
||||
Anope::string buf, buf2;
|
||||
while (sep.GetToken(buf) && sep.GetToken(buf2))
|
||||
mlp.push_back(std::make_pair(buf, buf2));
|
||||
|
||||
ci->Extend("db_mlp_off", new ExtensibleItemRegular<std::vector<std::pair<Anope::string, Anope::string> > >(mlp));
|
||||
}
|
||||
|
||||
if (!r.Get(i, "flags").empty())
|
||||
{
|
||||
@@ -1022,7 +1041,8 @@ class DBMySQL : public Module
|
||||
{
|
||||
this->RunQuery("UPDATE `anope_cs_info` SET `mlock_on` = '" + GetMLockOn(ci) + "' WHERE `name` = '" + this->Escape(ci->name) + "'");
|
||||
this->RunQuery("UPDATE `anope_cs_info` SET `mlock_off` = '" + GetMLockOff(ci) + "' WHERE `name` = '" + this->Escape(ci->name) + "'");
|
||||
this->RunQuery("UPDATE `anope_cs_info` SET `mlock_params` = '" + GetMLockParams(ci) + "' WHERE `name` = '" + this->Escape(ci->name) + "'");
|
||||
this->RunQuery("UPDATE `anope_cs_info` SET `mlock_params` = '" + GetMLockParams(ci, true) + "' WHERE `name` = '" + this->Escape(ci->name) + "'");
|
||||
this->RunQuery("UPDATE `anope_cs_info` SET `mlock_params_off` = '" + GetMLockParams(ci, false) + "' WHERE `name` = '" + this->Escape(ci->name) + "'");
|
||||
}
|
||||
else if (params[1].equals_ci("BANTYPE"))
|
||||
{
|
||||
@@ -1240,14 +1260,14 @@ class DBMySQL : public Module
|
||||
|
||||
void OnChanRegistered(ChannelInfo *ci)
|
||||
{
|
||||
Anope::string flags = BuildFlagsList(ci), mlockon = GetMLockOn(ci), mlockoff = GetMLockOff(ci), mlockparams = GetMLockParams(ci);
|
||||
this->RunQuery("INSERT INTO `anope_cs_info` (name, founder, successor, descr, time_registered, last_used, last_topic, last_topic_setter, last_topic_time, flags, forbidby, forbidreason, bantype, mlock_on, mlock_off, mlock_params, entry_message, memomax, botnick, botflags, capsmin, capspercent, floodlines, floodsecs, repeattimes) VALUES('" +
|
||||
Anope::string flags = BuildFlagsList(ci), mlockon = GetMLockOn(ci), mlockoff = GetMLockOff(ci), mlockparams = GetMLockParams(ci, true), mlockparams_off = GetMLockParams(ci, false);
|
||||
this->RunQuery("INSERT INTO `anope_cs_info` (name, founder, successor, descr, time_registered, last_used, last_topic, last_topic_setter, last_topic_time, flags, forbidby, forbidreason, bantype, mlock_on, mlock_off, mlock_params, mlock_params_off, entry_message, memomax, botnick, botflags, capsmin, capspercent, floodlines, floodsecs, repeattimes) VALUES('" +
|
||||
this->Escape(ci->name) + "', '" + this->Escape(ci->founder ? ci->founder->display : "") + "', '" +
|
||||
this->Escape(ci->successor ? ci->successor->display : "") + "', '" + this->Escape(ci->desc) + "', " +
|
||||
stringify(ci->time_registered) + ", " + stringify(ci->last_used) + ", '" + this->Escape(ci->last_topic) + "', '" +
|
||||
this->Escape(ci->last_topic_setter) + "', " + stringify(ci->last_topic_time) + ", '" + flags + "', '" +
|
||||
this->Escape(ci->forbidby) + "', '" + this->Escape(ci->forbidreason) + "', " + stringify(ci->bantype) + ", '" +
|
||||
mlockon + "', '" + mlockoff + "', '" + mlockparams + "', '" + this->Escape(ci->entry_message) + "', " +
|
||||
mlockon + "', '" + mlockoff + "', '" + mlockparams + "', '" + mlockparams_off + "', '" + this->Escape(ci->entry_message) + "', " +
|
||||
stringify(ci->memos.memomax) + ", '" + this->Escape(ci->bi ? ci->bi->nick : "") + "', '" + GetBotFlags(ci->botflags) +
|
||||
"', " + stringify(ci->capsmin) + ", " + stringify(ci->capspercent) + ", " + stringify(ci->floodlines) + ", " + stringify(ci->floodsecs) + ", " + stringify(ci->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), forbidby=VALUES(forbidby), forbidreason=VALUES(forbidreason), bantype=VALUES(bantype), mlock_on=VALUES(mlock_on), mlock_off=VALUES(mlock_off), mlock_params=VALUES(mlock_params), entry_message=VALUES(entry_message), memomax=VALUES(memomax), botnick=VALUES(botnick), botflags=VALUES(botflags), capsmin=VALUES(capsmin), capspercent=VALUES(capspercent), floodlines=VALUES(floodlines), floodsecs=VALUES(floodsecs), repeattimes=VALUES(repeattimes)");
|
||||
|
||||
@@ -174,27 +174,23 @@ class MyXMLRPCEvent : public XMLRPCEvent
|
||||
|
||||
if (c)
|
||||
{
|
||||
request->reply("bancount", stringify((c && c->bans ? c->bans->count : 0)));
|
||||
if (c->bans && c->bans->count)
|
||||
{
|
||||
int i = 0;
|
||||
for (Entry *entry = c->bans->entries; entry; entry = entry->next, ++i)
|
||||
request->reply("ban" + stringify(i), iface->Sanitize(entry->mask));
|
||||
}
|
||||
request->reply("exceptcount", stringify((c && c->excepts ? c->excepts->count : 0)));
|
||||
if (c->excepts && c->excepts->count)
|
||||
{
|
||||
int i = 0;
|
||||
for (Entry *entry = c->excepts->entries; entry; entry = entry->next, ++i)
|
||||
request->reply("except" + stringify(i), iface->Sanitize(entry->mask));
|
||||
}
|
||||
request->reply("invitecount", stringify((c && c->invites ? c->invites->count : 0)));
|
||||
if (c->invites && c->invites->count)
|
||||
{
|
||||
int i = 0;
|
||||
for (Entry *entry = c->invites->entries; entry; entry = entry->next, ++i)
|
||||
request->reply("invite" + stringify(i), iface->Sanitize(entry->mask));
|
||||
}
|
||||
request->reply("bancount", stringify(c->HasMode(CMODE_BAN)));
|
||||
int count = 0;
|
||||
std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> its = c->GetModeList(CMODE_BAN);
|
||||
for (; its.first != its.second; ++its.first)
|
||||
request->reply("ban" + stringify(++count), iface->Sanitize(its.first->second));
|
||||
|
||||
request->reply("exceptcount", stringify(c->HasMode(CMODE_EXCEPT)));
|
||||
count = 0;
|
||||
its = c->GetModeList(CMODE_EXCEPT);
|
||||
for (; its.first != its.second; ++its.first)
|
||||
request->reply("except" + stringify(++count), iface->Sanitize(its.first->second));
|
||||
|
||||
request->reply("invitecount", stringify(c->HasMode(CMODE_INVITEOVERRIDE)));
|
||||
count = 0;
|
||||
its = c->GetModeList(CMODE_INVITEOVERRIDE);
|
||||
for (; its.first != its.second; ++its.first)
|
||||
request->reply("invite" + stringify(++count), iface->Sanitize(its.first->second));
|
||||
|
||||
Anope::string users;
|
||||
for (CUserList::const_iterator it = c->users.begin(); it != c->users.end(); ++it)
|
||||
|
||||
@@ -37,7 +37,6 @@ IRCDVar myIrcd[] = {
|
||||
0, /* Can remove User Channel Modes with SVSMODE */
|
||||
0, /* Sglines are not enforced until user reconnects */
|
||||
0, /* ts6 */
|
||||
0, /* CIDR channelbans */
|
||||
"$", /* TLD Prefix for Global */
|
||||
6, /* Max number of modes we can send per line */
|
||||
}
|
||||
|
||||
@@ -38,7 +38,6 @@ IRCDVar myIrcd[] = {
|
||||
0, /* Can remove User Channel Modes with SVSMODE */
|
||||
0, /* Sglines are not enforced until user reconnects */
|
||||
0, /* ts6 */
|
||||
1, /* CIDR channelbans */
|
||||
"$", /* TLD Prefix for Global */
|
||||
20, /* Max number of modes we can send per line */
|
||||
}
|
||||
|
||||
@@ -38,7 +38,6 @@ IRCDVar myIrcd[] = {
|
||||
0, /* Can remove User Channel Modes with SVSMODE */
|
||||
0, /* Sglines are not enforced until user reconnects */
|
||||
1, /* ts6 */
|
||||
1, /* CIDR channelbans */
|
||||
"$", /* TLD Prefix for Global */
|
||||
20, /* Max number of modes we can send per line */
|
||||
}
|
||||
|
||||
@@ -38,7 +38,6 @@ IRCDVar myIrcd[] = {
|
||||
0, /* Can remove User Channel Modes with SVSMODE */
|
||||
0, /* Sglines are not enforced until user reconnects */
|
||||
1, /* ts6 */
|
||||
1, /* CIDR channelbans */
|
||||
"$", /* TLD Prefix for Global */
|
||||
20, /* Max number of modes we can send per line */
|
||||
}
|
||||
|
||||
@@ -37,7 +37,6 @@ IRCDVar myIrcd[] = {
|
||||
0, /* Can remove User Channel Modes with SVSMODE */
|
||||
0, /* Sglines are not enforced until user reconnects */
|
||||
1, /* ts6 */
|
||||
0, /* CIDR channelbans */
|
||||
"$$", /* TLD Prefix for Global */
|
||||
4, /* Max number of modes we can send per line */
|
||||
}
|
||||
@@ -626,26 +625,20 @@ bool event_bmask(const Anope::string &source, const std::vector<Anope::string> &
|
||||
|
||||
if (c)
|
||||
{
|
||||
ChannelMode *ban = ModeManager::FindChannelModeByName(CMODE_BAN),
|
||||
*except = ModeManager::FindChannelModeByName(CMODE_EXCEPT),
|
||||
*invex = ModeManager::FindChannelModeByName(CMODE_INVITEOVERRIDE);
|
||||
Anope::string bans = params[3];
|
||||
int count = myNumToken(bans, ' '), i;
|
||||
for (i = 0; i <= count - 1; ++i)
|
||||
{
|
||||
Anope::string b = myStrGetToken(bans, ' ', i);
|
||||
if (params[2].equals_cs("b"))
|
||||
{
|
||||
ChannelModeList *cml = debug_cast<ChannelModeList *>(ModeManager::FindChannelModeByChar('b'));
|
||||
cml->AddMask(c, b);
|
||||
}
|
||||
else if (params[2].equals_cs("e"))
|
||||
{
|
||||
ChannelModeList *cml = debug_cast<ChannelModeList *>(ModeManager::FindChannelModeByChar('e'));
|
||||
cml->AddMask(c, b);
|
||||
}
|
||||
if (params[2].equals_cs("I"))
|
||||
{
|
||||
ChannelModeList *cml = debug_cast<ChannelModeList *>(ModeManager::FindChannelModeByChar('I'));
|
||||
cml->AddMask(c, b);
|
||||
}
|
||||
if (ban && params[2].equals_cs("b"))
|
||||
c->SetModeInternal(ban, b);
|
||||
else if (except && params[2].equals_cs("e"))
|
||||
c->SetModeInternal(except, b);
|
||||
if (invex && params[2].equals_cs("I"))
|
||||
c->SetModeInternal(invex, b);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
|
||||
@@ -37,7 +37,6 @@ IRCDVar myIrcd[] = {
|
||||
1, /* Can remove User Channel Modes with SVSMODE */
|
||||
0, /* Sglines are not enforced until user reconnects */
|
||||
0, /* ts6 */
|
||||
0, /* CIDR channelbans */
|
||||
"$", /* TLD Prefix for Global */
|
||||
12, /* Max number of modes we can send per line */
|
||||
}
|
||||
@@ -986,36 +985,30 @@ bool event_sjoin(const Anope::string &source, const std::vector<Anope::string> &
|
||||
c->SetModesInternal(NULL, modes);
|
||||
}
|
||||
|
||||
ChannelMode *ban = ModeManager::FindChannelModeByName(CMODE_BAN),
|
||||
*except = ModeManager::FindChannelModeByName(CMODE_EXCEPT),
|
||||
*invex = ModeManager::FindChannelModeByName(CMODE_INVITEOVERRIDE);
|
||||
spacesepstream sep(params[params.size() - 1]);
|
||||
Anope::string buf;
|
||||
while (sep.GetToken(buf))
|
||||
{
|
||||
/* Ban */
|
||||
if (keep_their_modes && buf[0] == '&')
|
||||
if (keep_their_modes && ban && buf[0] == '&')
|
||||
{
|
||||
buf.erase(buf.begin());
|
||||
ChannelModeList *cml = debug_cast<ChannelModeList *>(ModeManager::FindChannelModeByName(CMODE_BAN));
|
||||
|
||||
if (cml->IsValid(buf))
|
||||
cml->AddMask(c, buf);
|
||||
c->SetModeInternal(ban, buf);
|
||||
}
|
||||
/* Except */
|
||||
else if (keep_their_modes && buf[0] == '"')
|
||||
else if (keep_their_modes && except && buf[0] == '"')
|
||||
{
|
||||
buf.erase(buf.begin());
|
||||
ChannelModeList *cml = debug_cast<ChannelModeList *>(ModeManager::FindChannelModeByName(CMODE_EXCEPT));
|
||||
|
||||
if (cml->IsValid(buf))
|
||||
cml->AddMask(c, buf);
|
||||
c->SetModeInternal(except, buf);
|
||||
}
|
||||
/* Invex */
|
||||
else if (keep_their_modes && buf[0] == '\'')
|
||||
else if (keep_their_modes && invex && buf[0] == '\'')
|
||||
{
|
||||
buf.erase(buf.begin());
|
||||
ChannelModeList *cml = debug_cast<ChannelModeList *>(ModeManager::FindChannelModeByName(CMODE_INVITEOVERRIDE));
|
||||
|
||||
if (cml->IsValid(buf))
|
||||
cml->AddMask(c, buf);
|
||||
c->SetModeInternal(invex, buf);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
+11
-10
@@ -71,28 +71,29 @@ void kill_user(const Anope::string &source, const Anope::string &user, const Ano
|
||||
*/
|
||||
void common_unban(ChannelInfo *ci, const Anope::string &nick)
|
||||
{
|
||||
//uint32 ip = 0;
|
||||
User *u;
|
||||
Entry *ban, *next;
|
||||
|
||||
if (!ci || !ci->c || nick.empty())
|
||||
return;
|
||||
|
||||
if (!(u = finduser(nick)))
|
||||
User *u = finduser(nick);
|
||||
if (!u)
|
||||
return;
|
||||
|
||||
if (!ci->c->bans || !ci->c->bans->count)
|
||||
if (!ci->c->HasMode(CMODE_BAN))
|
||||
return;
|
||||
|
||||
if (ircd->svsmode_unban)
|
||||
ircdproto->SendBanDel(ci->c, nick);
|
||||
else
|
||||
for (ban = ci->c->bans->entries; ban; ban = next)
|
||||
{
|
||||
std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> bans = ci->c->GetModeList(CMODE_BAN);
|
||||
for (; bans.first != bans.second;)
|
||||
{
|
||||
next = ban->next;
|
||||
if (entry_match(ban, u->nick, u->GetIdent(), u->host, /*ip XXX */ 0) || entry_match(ban, u->nick, u->GetIdent(), u->GetDisplayedHost(), /*ip XXX */0))
|
||||
ci->c->RemoveMode(NULL, CMODE_BAN, ban->mask);
|
||||
Entry ban(bans.first->second);
|
||||
++bans.first;
|
||||
if (ban.Matches(u))
|
||||
ci->c->RemoveMode(NULL, CMODE_BAN, ban.GetMask());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
+15
-19
@@ -141,29 +141,25 @@ void BotInfo::Join(Channel *c, bool update_ts)
|
||||
{
|
||||
if (Config->BSSmartJoin)
|
||||
{
|
||||
std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> bans = c->GetModeList(CMODE_BAN);
|
||||
|
||||
/* We check for bans */
|
||||
if (c->bans && c->bans->count)
|
||||
for (; bans.first != bans.second; ++bans.first)
|
||||
{
|
||||
Entry *ban, *next;
|
||||
|
||||
for (ban = c->bans->entries; ban; ban = next)
|
||||
{
|
||||
next = ban->next;
|
||||
|
||||
if (entry_match(ban, this->nick, this->GetIdent(), this->host, 0))
|
||||
c->RemoveMode(NULL, CMODE_BAN, ban->mask);
|
||||
}
|
||||
|
||||
Anope::string Limit;
|
||||
unsigned limit = 0;
|
||||
if (c->GetParam(CMODE_LIMIT, Limit) && Limit.is_pos_number_only())
|
||||
limit = convertTo<unsigned>(Limit);
|
||||
|
||||
/* Should we be invited? */
|
||||
if (c->HasMode(CMODE_INVITE) || (limit && c->users.size() >= limit))
|
||||
ircdproto->SendNoticeChanops(this, c, "%s invited %s into the channel.", this->nick.c_str(), this->nick.c_str());
|
||||
Entry ban(bans.first->second);
|
||||
if (ban.Matches(this))
|
||||
c->RemoveMode(NULL, CMODE_BAN, ban.GetMask());
|
||||
}
|
||||
|
||||
Anope::string Limit;
|
||||
unsigned limit = 0;
|
||||
if (c->GetParam(CMODE_LIMIT, Limit) && Limit.is_pos_number_only())
|
||||
limit = convertTo<unsigned>(Limit);
|
||||
|
||||
/* Should we be invited? */
|
||||
if (c->HasMode(CMODE_INVITE) || (limit && c->users.size() >= limit))
|
||||
ircdproto->SendNoticeChanops(this, c, "%s invited %s into the channel.", this->nick.c_str(), this->nick.c_str());
|
||||
|
||||
ModeManager::ProcessModes();
|
||||
}
|
||||
|
||||
|
||||
+243
-625
File diff suppressed because it is too large
Load Diff
+58
-98
@@ -24,7 +24,6 @@ static int def_levels[][2] = {
|
||||
{ CA_INVITE, 5 },
|
||||
{ CA_AKICK, 10 },
|
||||
{ CA_SET, ACCESS_QOP },
|
||||
{ CA_CLEAR, ACCESS_FOUNDER },
|
||||
{ CA_UNBAN, 5 },
|
||||
{ CA_OPDEOP, 5 },
|
||||
{ CA_ACCESS_LIST, 1 },
|
||||
@@ -52,6 +51,7 @@ static int def_levels[][2] = {
|
||||
{ CA_BANME, 5 },
|
||||
{ CA_BAN, 5 },
|
||||
{ CA_TOPIC, ACCESS_FOUNDER },
|
||||
{ CA_MODE, ACCESS_FOUNDER },
|
||||
{ CA_INFO, ACCESS_QOP },
|
||||
{ CA_AUTOOWNER, ACCESS_QOP },
|
||||
{ CA_OWNER, ACCESS_FOUNDER },
|
||||
@@ -74,7 +74,6 @@ LevelInfo levelinfo[] = {
|
||||
{ CA_SET, "SET", CHAN_LEVEL_SET },
|
||||
{ CA_BAN, "BAN", CHAN_LEVEL_BAN },
|
||||
{ CA_BANME, "BANME", CHAN_LEVEL_BANME },
|
||||
{ CA_CLEAR, "CLEAR", CHAN_LEVEL_CLEAR },
|
||||
{ CA_GETKEY, "GETKEY", CHAN_LEVEL_GETKEY },
|
||||
{ CA_HALFOP, "HALFOP", CHAN_LEVEL_HALFOP },
|
||||
{ CA_HALFOPME, "HALFOPME", CHAN_LEVEL_HALFOPME },
|
||||
@@ -87,6 +86,7 @@ LevelInfo levelinfo[] = {
|
||||
{ CA_PROTECT, "PROTECT", CHAN_LEVEL_PROTECT },
|
||||
{ CA_PROTECTME, "PROTECTME", CHAN_LEVEL_PROTECTME },
|
||||
{ CA_TOPIC, "TOPIC", CHAN_LEVEL_TOPIC },
|
||||
{ CA_MODE, "MODE", CHAN_LEVEL_MODE },
|
||||
{ CA_UNBAN, "UNBAN", CHAN_LEVEL_UNBAN },
|
||||
{ CA_VOICE, "VOICE", CHAN_LEVEL_VOICE },
|
||||
{ CA_VOICEME, "VOICEME", CHAN_LEVEL_VOICEME },
|
||||
@@ -111,59 +111,30 @@ int levelinfo_maxwidth = 0;
|
||||
|
||||
Anope::string get_mlock_modes(ChannelInfo *ci, int complete)
|
||||
{
|
||||
ChannelMode *cm;
|
||||
ChannelModeParam *cmp;
|
||||
std::map<char, ChannelMode *>::iterator it, it_end;
|
||||
Anope::string res, param;
|
||||
Anope::string pos = "+", neg = "-", params;
|
||||
|
||||
if (ci->GetMLockCount(true) || ci->GetMLockCount(false))
|
||||
for (std::map<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it)
|
||||
{
|
||||
if (ci->GetMLockCount(true))
|
||||
{
|
||||
res += '+';
|
||||
const ModeLock &ml = it->second;
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name);
|
||||
if (!cm)
|
||||
continue;
|
||||
|
||||
for (it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
{
|
||||
cm = it->second;
|
||||
if (ml.set)
|
||||
pos += cm->ModeChar;
|
||||
else
|
||||
neg += cm->ModeChar;
|
||||
|
||||
if (ci->HasMLock(cm->Name, true))
|
||||
res += it->first;
|
||||
}
|
||||
}
|
||||
|
||||
if (ci->GetMLockCount(false))
|
||||
{
|
||||
res += '-';
|
||||
|
||||
for (it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
{
|
||||
cm = it->second;
|
||||
|
||||
if (ci->HasMLock(cm->Name, false))
|
||||
res += it->first;
|
||||
}
|
||||
}
|
||||
|
||||
if (ci->GetMLockCount(true) && complete)
|
||||
{
|
||||
for (it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
{
|
||||
cm = it->second;
|
||||
|
||||
if (cm->Type == MODE_PARAM)
|
||||
{
|
||||
cmp = debug_cast<ChannelModeParam *>(cm);
|
||||
|
||||
ci->GetParam(cmp->Name, param);
|
||||
|
||||
if (!param.empty())
|
||||
res += " " + param;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (complete && !ml.param.empty() && (cm->Type == MODE_PARAM || cm->Type == MODE_LIST))
|
||||
params += " " + ml.param;
|
||||
}
|
||||
|
||||
return res;
|
||||
if (pos.length() == 1)
|
||||
pos.clear();
|
||||
if (neg.length() == 1)
|
||||
neg.clear();
|
||||
|
||||
return pos + neg + params;
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
@@ -173,7 +144,7 @@ Anope::string get_mlock_modes(ChannelInfo *ci, int complete)
|
||||
void get_chanserv_stats(long *nrec, long *memuse)
|
||||
{
|
||||
long count = 0, mem = 0;
|
||||
Anope::string param;
|
||||
ModeLock *ml;
|
||||
|
||||
for (registered_channel_map::const_iterator it = RegisteredChannelList.begin(), it_end = RegisteredChannelList.end(); it != it_end; ++it)
|
||||
{
|
||||
@@ -186,14 +157,17 @@ void get_chanserv_stats(long *nrec, long *memuse)
|
||||
mem += ci->GetAccessCount() * sizeof(ChanAccess);
|
||||
mem += ci->GetAkickCount() * sizeof(AutoKick);
|
||||
|
||||
if (ci->GetParam(CMODE_KEY, param))
|
||||
mem += param.length() + 1;
|
||||
ml = ci->GetMLock(CMODE_KEY);
|
||||
if (ml && !ml->param.empty())
|
||||
mem += ml->param.length() + 1;
|
||||
|
||||
if (ci->GetParam(CMODE_FLOOD, param))
|
||||
mem += param.length() + 1;
|
||||
ml = ci->GetMLock(CMODE_FLOOD);
|
||||
if (ml && !ml->param.empty())
|
||||
mem += ml->param.length() + 1;
|
||||
|
||||
if (ci->GetParam(CMODE_REDIRECT, param))
|
||||
mem += param.length() + 1;
|
||||
ml = ci->GetMLock(CMODE_REDIRECT);
|
||||
if (ml && !ml->param.empty())
|
||||
mem += ml->param.length() + 1;
|
||||
|
||||
if (!ci->last_topic.empty())
|
||||
mem += ci->last_topic.length() + 1;
|
||||
@@ -237,11 +211,6 @@ void cs_init()
|
||||
|
||||
void check_modes(Channel *c)
|
||||
{
|
||||
ChannelInfo *ci;
|
||||
ChannelMode *cm;
|
||||
std::map<char, ChannelMode *>::iterator it, it_end;
|
||||
Anope::string param, ciparam;
|
||||
|
||||
if (!c)
|
||||
{
|
||||
Log() << "check_modes called with NULL values";
|
||||
@@ -268,61 +237,52 @@ void check_modes(Channel *c)
|
||||
c->chanserv_modecount++;
|
||||
|
||||
/* Check if the channel is registered; if not remove mode -r */
|
||||
if (!(ci = c->ci))
|
||||
ChannelInfo *ci = c->ci;
|
||||
if (!ci)
|
||||
{
|
||||
if (c->HasMode(CMODE_REGISTERED))
|
||||
c->RemoveMode(NULL, CMODE_REGISTERED);
|
||||
return;
|
||||
}
|
||||
|
||||
for (it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
for (std::map<ChannelModeName, ModeLock>::const_iterator it = ci->GetMLock().begin(), it_end = ci->GetMLock().end(); it != it_end; ++it)
|
||||
{
|
||||
cm = it->second;
|
||||
const ModeLock &ml = it->second;
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByName(ml.name);
|
||||
if (!cm)
|
||||
continue;
|
||||
|
||||
/* If this channel does not have the mode and the mode is mlocked */
|
||||
if (cm->Type == MODE_REGULAR && !c->HasMode(cm->Name) && ci->HasMLock(cm->Name, true))
|
||||
if (cm->Type == MODE_REGULAR)
|
||||
{
|
||||
/* Add the eventual parameter and modify the Channel structure */
|
||||
if (cm->Type == MODE_PARAM)
|
||||
{
|
||||
if (ci->GetParam(cm->Name, ciparam))
|
||||
c->SetMode(NULL, cm, ciparam);
|
||||
}
|
||||
else
|
||||
if (!c->HasMode(cm->Name) && ml.set)
|
||||
c->SetMode(NULL, cm);
|
||||
else if (c->HasMode(cm->Name) && !ml.set)
|
||||
c->RemoveMode(NULL, cm);
|
||||
}
|
||||
/* If this is a param mode and its mlocked, check to ensure it is set and set to the correct value */
|
||||
else if (cm->Type == MODE_PARAM && ci->HasMLock(cm->Name, true))
|
||||
else if (cm->Type == MODE_PARAM)
|
||||
{
|
||||
Anope::string param;
|
||||
c->GetParam(cm->Name, param);
|
||||
ci->GetParam(cm->Name, ciparam);
|
||||
|
||||
/* If the channel doesnt have the mode, or it does and it isn't set correctly */
|
||||
if (!c->HasMode(cm->Name) || (!param.empty() && !ciparam.empty() && !param.equals_cs(ciparam)))
|
||||
c->SetMode(NULL, cm, ciparam);
|
||||
}
|
||||
}
|
||||
|
||||
for (it = ModeManager::ChannelModesByChar.begin(), it_end = ModeManager::ChannelModesByChar.end(); it != it_end; ++it)
|
||||
{
|
||||
cm = it->second;
|
||||
|
||||
/* If the channel has the mode */
|
||||
if (c->HasMode(cm->Name) && ci->HasMLock(cm->Name, false))
|
||||
{
|
||||
/* Add the eventual parameter */
|
||||
if (cm->Type == MODE_PARAM)
|
||||
if (ml.set)
|
||||
{
|
||||
ChannelModeParam *cmp = debug_cast<ChannelModeParam *>(cm);
|
||||
|
||||
if (!cmp->MinusNoArg)
|
||||
{
|
||||
if (c->GetParam(cmp->Name, param))
|
||||
c->RemoveMode(NULL, cm, param);
|
||||
}
|
||||
if (!c->HasMode(cm->Name) || (!param.empty() && !ml.param.empty() && !param.equals_cs(ml.param)))
|
||||
c->SetMode(NULL, cm, ml.param);
|
||||
}
|
||||
else
|
||||
c->RemoveMode(NULL, cm);
|
||||
{
|
||||
if (c->HasMode(cm->Name))
|
||||
c->RemoveMode(NULL, cm);
|
||||
}
|
||||
|
||||
}
|
||||
else if (cm->Type == MODE_LIST) // XXX we still need better list code...
|
||||
{
|
||||
if (ml.set)
|
||||
c->SetMode(NULL, cm, ml.param);
|
||||
else
|
||||
c->RemoveMode(NULL, cm, ml.param);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -167,7 +167,7 @@ ServerConfig::ServerConfig() : errstr(""), config_data()
|
||||
}
|
||||
}
|
||||
|
||||
this->WallOper = this->WallBadOS = this->WallOSGlobal = this->WallOSMode = this->WallOSClearmodes = this->WallOSKick = this->WallOSAkill = this->WallOSSNLine = this->WallOSSQLine =
|
||||
this->WallOper = this->WallBadOS = this->WallOSGlobal = this->WallOSMode = this->WallOSKick = this->WallOSAkill = this->WallOSSNLine = this->WallOSSQLine =
|
||||
this->WallOSSZLine = this->WallOSNoOp = this->WallOSJupe = this->WallAkillExpire = this->WallSNLineExpire = this->WallSQLineExpire = this->WallSZLineExpire = this->WallExceptionExpire =
|
||||
this->WallGetpass = this->WallSetpass = this->WallForbid = this->WallDrop = false;
|
||||
if (!OSNotifications.empty())
|
||||
|
||||
+45
-1
@@ -769,6 +769,8 @@ const char *const language_strings[LANG_STRING_COUNT] = {
|
||||
_("Allowed to use BAN command"),
|
||||
/* CHAN_LEVEL_TOPIC */
|
||||
_("Allowed to use TOPIC command"),
|
||||
/* CHAN_LEVEL_MODE */
|
||||
_("Allowed to use MODE command"),
|
||||
/* CHAN_LEVEL_INFO */
|
||||
_("Allowed to use INFO command with ALL option"),
|
||||
/* CHAN_LEVEL_AUTOOWNER */
|
||||
@@ -1294,8 +1296,10 @@ const char *const language_strings[LANG_STRING_COUNT] = {
|
||||
_("%s has been unbanned from %s."),
|
||||
/* CHAN_TOPIC_SYNTAX */
|
||||
_("TOPIC channel [topic]"),
|
||||
/* CHAN_CLEARUSERS */
|
||||
/* CHAN_CLEARUSERS_SYNTAX */
|
||||
_("CLEARUSERS \037channel\037"),
|
||||
/* CHAN_CLEARED_USERS */
|
||||
_("All users have been kicked from \2%s\2."),
|
||||
/* CHAN_CLONED */
|
||||
_("All settings from \002%s\002 have been transferred to \002%s\002"),
|
||||
/* CHAN_CLONED_ACCESS */
|
||||
@@ -1366,6 +1370,24 @@ const char *const language_strings[LANG_STRING_COUNT] = {
|
||||
_("KICK #channel nick [reason]"),
|
||||
/* CHAN_BAN_SYNTAX */
|
||||
_("BAN #channel nick [reason]"),
|
||||
/* CHAN_MODE_SYNTAX */
|
||||
_("MODE \037channel\037 {LOCK|SET} [\037modes\037 | {ADD|DEL|LIST} [\037what\037]]"),
|
||||
/* CHAN_MODE_LOCK_UNKNOWN */
|
||||
_("Unknown mode character %c ignored."),
|
||||
/* CHAN_MODE_LOCK_MISSING_PARAM */
|
||||
_("Missing parameter for mode %c."),
|
||||
/* CHAN_MODE_LOCK_NONE */
|
||||
_("Channel %s has no mode locks."),
|
||||
/* CHAN_MODE_LOCK_HEADER */
|
||||
_("Mode locks for %s:"),
|
||||
/* CHAN_MODE_LOCKED */
|
||||
_("%c%c%s locked on %s"),
|
||||
/* CHAN_MODE_NOT_LOCKED */
|
||||
_("%c is not locked on %s."),
|
||||
/* CHAN_MODE_UNLOCKED */
|
||||
_("%c%c%s has been unlocked from %s."),
|
||||
/* CHAN_MODE_LIST_FMT */
|
||||
_("%c%c%s, by %s on %s"),
|
||||
/* MEMO_HAVE_NEW_MEMO */
|
||||
_("You have 1 new memo."),
|
||||
/* MEMO_HAVE_NEW_MEMOS */
|
||||
@@ -3338,6 +3360,8 @@ const char *const language_strings[LANG_STRING_COUNT] = {
|
||||
_(" DEOP Deops a selected nick on a channel"),
|
||||
/* CHAN_HELP_CMD_CLONE */
|
||||
_(" CLONE Copy all settings from one channel to another"),
|
||||
/* CHAN_HELP_CMD_MODE */
|
||||
_(" MODE Control modes and mode locks on a channel"),
|
||||
/* CHAN_HELP */
|
||||
_("%S allows you to register and control various\n"
|
||||
"aspects of channels. %S can often prevent\n"
|
||||
@@ -4062,6 +4086,26 @@ const char *const language_strings[LANG_STRING_COUNT] = {
|
||||
"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."),
|
||||
/* CHAN_HELP_MODE */
|
||||
_("Syntax: \002MODE \037channel\037 LOCK {ADD|DEL|LIST} [\037what\037]\002\n"
|
||||
" \002MODE \037channel\037 SET \037modes\037\002\n"
|
||||
" \n"
|
||||
"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:"),
|
||||
/* CHAN_SERVADMIN_HELP */
|
||||
_(" \n"
|
||||
"Services Operators can also drop any channel without needing\n"
|
||||
|
||||
+70
-10
@@ -831,6 +831,74 @@ char *str_signed(unsigned char *str)
|
||||
return nstr;
|
||||
}
|
||||
|
||||
bool Anope::Match(const Anope::string &str, const Anope::string &mask, bool case_sensitive)
|
||||
{
|
||||
size_t s = 0, m = 0, str_len = str.length(), mask_len = mask.length();
|
||||
|
||||
while (s < str_len && m < mask_len && mask[m] != '*')
|
||||
{
|
||||
char string = str[s], wild = mask[m];
|
||||
if (case_sensitive)
|
||||
{
|
||||
if (wild != string && wild != '?')
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (tolower(wild) != tolower(string) && wild != '?')
|
||||
return false;
|
||||
}
|
||||
|
||||
++m;
|
||||
++s;
|
||||
}
|
||||
|
||||
size_t sp = Anope::string::npos, mp = Anope::string::npos;
|
||||
while (s < str_len)
|
||||
{
|
||||
char string = str[s], wild = mask[m];
|
||||
if (wild == '*')
|
||||
{
|
||||
if (++m == mask_len)
|
||||
return 1;
|
||||
|
||||
mp = m;
|
||||
sp = s + 1;
|
||||
}
|
||||
else if (case_sensitive)
|
||||
{
|
||||
if (wild == string || wild == '?')
|
||||
{
|
||||
++m;
|
||||
++s;
|
||||
}
|
||||
else
|
||||
{
|
||||
m = mp;
|
||||
s = sp++;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (tolower(wild) == tolower(string) || wild == '?')
|
||||
{
|
||||
++m;
|
||||
++s;
|
||||
}
|
||||
else
|
||||
{
|
||||
m = mp;
|
||||
s = sp++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (mask[m] == '*')
|
||||
++m;
|
||||
|
||||
return m == mask_len;
|
||||
}
|
||||
|
||||
/*
|
||||
* strlcat and strlcpy were ripped from openssh 2.5.1p2
|
||||
* They had the following Copyright info:
|
||||
@@ -1107,11 +1175,7 @@ uint16 netmask_to_cidr(uint32 mask)
|
||||
*/
|
||||
bool str_is_wildcard(const Anope::string &str)
|
||||
{
|
||||
for (Anope::string::const_iterator c = str.begin(), c_end = str.end(); c != c_end; ++c)
|
||||
if (*c == '*' || *c == '?')
|
||||
return true;
|
||||
|
||||
return false;
|
||||
return str.find_first_of("*?") != Anope::string::npos;
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -1121,11 +1185,7 @@ bool str_is_wildcard(const Anope::string &str)
|
||||
*/
|
||||
bool str_is_pure_wildcard(const Anope::string &str)
|
||||
{
|
||||
for (Anope::string::const_iterator c = str.begin(), c_end = str.end(); c != c_end; ++c)
|
||||
if (*c != '*')
|
||||
return false;
|
||||
|
||||
return true;
|
||||
return str.find_first_not_of('*') == Anope::string::npos;
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
+33
-103
@@ -27,53 +27,42 @@ std::map<ChannelModeName, ChannelMode *> ModeManager::ChannelModesByName;
|
||||
|
||||
/* Number of generic modes we support */
|
||||
unsigned GenericChannelModes = 0, GenericUserModes = 0;
|
||||
/* Default mlocked modes on */
|
||||
Flags<ChannelModeName, CMODE_END * 2> DefMLockOn;
|
||||
/* Default mlocked modes off */
|
||||
Flags<ChannelModeName, CMODE_END * 2> DefMLockOff;
|
||||
/* Map for default mlocked mode parameters */
|
||||
std::map<ChannelModeName, Anope::string> DefMLockParams;
|
||||
/* Default mlocked modes */
|
||||
std::multimap<ChannelModeName, ModeLock> def_mode_locks;
|
||||
|
||||
/** Parse the mode string from the config file and set the default mlocked modes
|
||||
*/
|
||||
void SetDefaultMLock(ServerConfig *config)
|
||||
{
|
||||
DefMLockOn.ClearFlags();
|
||||
DefMLockOff.ClearFlags();
|
||||
DefMLockParams.clear();
|
||||
Flags<ChannelModeName, CMODE_END * 2> *ptr = NULL;
|
||||
def_mode_locks.clear();
|
||||
|
||||
Anope::string modes, param;
|
||||
Anope::string modes;
|
||||
spacesepstream sep(config->MLock);
|
||||
sep.GetToken(modes);
|
||||
|
||||
int adding = -1;
|
||||
for (unsigned i = 0, end_mode = modes.length(); i < end_mode; ++i)
|
||||
{
|
||||
if (modes[i] == '+')
|
||||
ptr = &DefMLockOn;
|
||||
adding = 1;
|
||||
else if (modes[i] == '-')
|
||||
ptr = &DefMLockOff;
|
||||
else
|
||||
adding = 0;
|
||||
else if (adding != -1)
|
||||
{
|
||||
if (!ptr)
|
||||
continue;
|
||||
|
||||
ChannelMode *cm = ModeManager::FindChannelModeByChar(modes[i]);
|
||||
|
||||
if (cm && (cm->Type == MODE_REGULAR || cm->Type == MODE_PARAM))
|
||||
if (cm && cm->Type != MODE_STATUS)
|
||||
{
|
||||
ptr->SetFlag(cm->Name);
|
||||
|
||||
if (ptr == &DefMLockOn && cm->Type == MODE_PARAM)
|
||||
Anope::string param;
|
||||
if (adding == 1 && cm->Type != MODE_REGULAR && !sep.GetToken(param)) // MODE_LIST OR MODE_PARAM
|
||||
{
|
||||
if (sep.GetToken(param))
|
||||
DefMLockParams.insert(std::make_pair(cm->Name, param));
|
||||
else
|
||||
{
|
||||
Log() << "Warning: Got default mlock mode " << cm->ModeChar << " with no param?";
|
||||
ptr->UnsetFlag(cm->Name);
|
||||
}
|
||||
Log() << "Warning: Got default mlock mode " << cm->ModeChar << " with no param?";
|
||||
continue;
|
||||
}
|
||||
|
||||
if (cm->Type != MODE_LIST) // Only MODE_LIST can have duplicates
|
||||
def_mode_locks.erase(cm->Name);
|
||||
def_mode_locks.insert(std::make_pair(cm->Name, ModeLock(adding == 1, cm->Name, param)));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -298,36 +287,20 @@ bool ChannelModeRegistered::CanSet(User *u) const
|
||||
* @param chan The channel
|
||||
* @param mask The ban
|
||||
*/
|
||||
void ChannelModeBan::AddMask(Channel *chan, const Anope::string &mask)
|
||||
void ChannelModeBan::OnAdd(Channel *chan, const Anope::string &mask)
|
||||
{
|
||||
/* check for NULL values otherwise we will segfault */
|
||||
if (!chan || mask.empty())
|
||||
{
|
||||
Log() << "add_ban called with NULL values";
|
||||
return;
|
||||
}
|
||||
|
||||
/* Check if the list already exists, if not create it.
|
||||
* Create a new ban and add it to the list.. ~ Viper */
|
||||
if (!chan->bans)
|
||||
chan->bans = list_create();
|
||||
|
||||
Entry *ban = entry_add(chan->bans, mask);
|
||||
if (!ban)
|
||||
throw CoreException("Creating new ban entry failed");
|
||||
|
||||
/* Check whether it matches a botserv bot after adding internally
|
||||
* and parsing it through cidr support. ~ Viper */
|
||||
/* Check whether it matches a botserv bot */
|
||||
if (!Config->s_BotServ.empty() && Config->BSSmartJoin && chan->ci && chan->ci->bi && chan->FindUser(chan->ci->bi))
|
||||
{
|
||||
BotInfo *bi = chan->ci->bi;
|
||||
|
||||
if (entry_match(ban, bi->nick, bi->GetIdent(), bi->host, 0))
|
||||
{
|
||||
ircdproto->SendMode(bi, chan, "-b %s", mask.c_str());
|
||||
entry_delete(chan->bans, ban);
|
||||
return;
|
||||
}
|
||||
Entry ban(mask);
|
||||
if (ban.Matches(bi))
|
||||
chan->RemoveMode(NULL, CMODE_BAN, mask);
|
||||
}
|
||||
|
||||
Log(LOG_DEBUG) << "Added ban " << mask << " to channel " << chan->name;
|
||||
@@ -337,41 +310,22 @@ void ChannelModeBan::AddMask(Channel *chan, const Anope::string &mask)
|
||||
* @param chan The channel
|
||||
* @param mask The ban
|
||||
*/
|
||||
void ChannelModeBan::DelMask(Channel *chan, const Anope::string &mask)
|
||||
void ChannelModeBan::OnDel(Channel *chan, const Anope::string &mask)
|
||||
{
|
||||
/* Sanity check as it seems some IRCD will just send -b without a mask */
|
||||
if (mask.empty() || !chan->bans || !chan->bans->count)
|
||||
if (!chan || mask.empty())
|
||||
return;
|
||||
|
||||
Entry *ban = elist_find_mask(chan->bans, mask);
|
||||
if (ban)
|
||||
{
|
||||
entry_delete(chan->bans, ban);
|
||||
|
||||
Log(LOG_DEBUG) << "Deleted ban " << mask << " from channel " << chan->name;
|
||||
}
|
||||
Log(LOG_DEBUG) << "Deleted ban " << mask << " from channel " << chan->name;
|
||||
}
|
||||
|
||||
/** Add an except to the channel
|
||||
* @param chan The channel
|
||||
* @param mask The except
|
||||
*/
|
||||
void ChannelModeExcept::AddMask(Channel *chan, const Anope::string &mask)
|
||||
void ChannelModeExcept::OnAdd(Channel *chan, const Anope::string &mask)
|
||||
{
|
||||
if (!chan || mask.empty())
|
||||
{
|
||||
Log() << "add_exception called with NULL values";
|
||||
return;
|
||||
}
|
||||
|
||||
/* Check if the list already exists, if not create it.
|
||||
* Create a new exception and add it to the list.. ~ Viper */
|
||||
if (!chan->excepts)
|
||||
chan->excepts = list_create();
|
||||
|
||||
Entry *exception = entry_add(chan->excepts, mask);
|
||||
if (!exception)
|
||||
throw CoreException("Creating new exception entry failed");
|
||||
|
||||
Log(LOG_DEBUG) << "Added except " << mask << " to channel " << chan->name;
|
||||
}
|
||||
@@ -380,40 +334,22 @@ void ChannelModeExcept::AddMask(Channel *chan, const Anope::string &mask)
|
||||
* @param chan The channel
|
||||
* @param mask The except
|
||||
*/
|
||||
void ChannelModeExcept::DelMask(Channel *chan, const Anope::string &mask)
|
||||
void ChannelModeExcept::OnDel(Channel *chan, const Anope::string &mask)
|
||||
{
|
||||
/* Sanity check as it seems some IRCD will just send -e without a mask */
|
||||
if (mask.empty() || !chan->excepts || !chan->excepts->count)
|
||||
if (!chan || mask.empty())
|
||||
return;
|
||||
|
||||
Entry *exception = elist_find_mask(chan->excepts, mask);
|
||||
if (exception)
|
||||
{
|
||||
entry_delete(chan->excepts, exception);
|
||||
Log(LOG_DEBUG) << "Deleted except " << mask << " to channel " << chan->name;
|
||||
}
|
||||
Log(LOG_DEBUG) << "Deleted except " << mask << " to channel " << chan->name;
|
||||
}
|
||||
|
||||
/** Add an invex to the channel
|
||||
* @param chan The channel
|
||||
* @param mask The invex
|
||||
*/
|
||||
void ChannelModeInvex::AddMask(Channel *chan, const Anope::string &mask)
|
||||
void ChannelModeInvex::OnAdd(Channel *chan, const Anope::string &mask)
|
||||
{
|
||||
if (!chan || mask.empty())
|
||||
{
|
||||
Log() << "add_invite called with NULL values";
|
||||
return;
|
||||
}
|
||||
|
||||
/* Check if the list already exists, if not create it.
|
||||
* Create a new invite and add it to the list.. ~ Viper */
|
||||
if (!chan->invites)
|
||||
chan->invites = list_create();
|
||||
|
||||
Entry *invite = entry_add(chan->invites, mask);
|
||||
if (!invite)
|
||||
throw CoreException("Creating new invex entry failed");
|
||||
|
||||
Log(LOG_DEBUG) << "Added invite " << mask << " to channel " << chan->name;
|
||||
|
||||
@@ -423,18 +359,12 @@ void ChannelModeInvex::AddMask(Channel *chan, const Anope::string &mask)
|
||||
* @param chan The channel
|
||||
* @param mask The index
|
||||
*/
|
||||
void ChannelModeInvex::DelMask(Channel *chan, const Anope::string &mask)
|
||||
void ChannelModeInvex::OnDel(Channel *chan, const Anope::string &mask)
|
||||
{
|
||||
/* Sanity check as it seems some IRCD will just send -I without a mask */
|
||||
if (mask.empty() || !chan->invites || !chan->invites->count)
|
||||
if (!chan || mask.empty())
|
||||
return;
|
||||
|
||||
Entry *invite = elist_find_mask(chan->invites, mask);
|
||||
if (invite)
|
||||
{
|
||||
entry_delete(chan->invites, invite);
|
||||
Log(LOG_DEBUG) << "Deleted invite " << mask << " to channel " << chan->name;
|
||||
}
|
||||
Log(LOG_DEBUG) << "Deleted invite " << mask << " to channel " << chan->name;
|
||||
}
|
||||
|
||||
void StackerInfo::AddMode(Mode *mode, bool Set, const Anope::string &Param)
|
||||
|
||||
+12
-1
@@ -428,7 +428,18 @@ XLine *XLineManager::Check(User *u)
|
||||
if (!x->GetUser().empty() && !Anope::Match(u->GetIdent(), x->GetUser()))
|
||||
continue;
|
||||
|
||||
if (x->GetHost().empty() || (u->ip() && Anope::Match(u->ip.addr(), x->GetHost())) || Anope::Match(u->host, x->GetHost()) || (!u->chost.empty() && Anope::Match(u->chost, x->GetHost())) || (!u->vhost.empty() && Anope::Match(u->vhost, x->GetHost())))
|
||||
if (u->ip() && !x->GetHost().empty())
|
||||
{
|
||||
try
|
||||
{
|
||||
cidr cidr_ip(x->GetHost());
|
||||
if (cidr_ip.match(u->ip))
|
||||
return x;
|
||||
}
|
||||
catch (const SocketException &) { }
|
||||
}
|
||||
|
||||
if (x->GetHost().empty() || (Anope::Match(u->host, x->GetHost()) || (!u->chost.empty() && Anope::Match(u->chost, x->GetHost())) || (!u->vhost.empty() && Anope::Match(u->vhost, x->GetHost()))))
|
||||
{
|
||||
OnMatch(u, x);
|
||||
return x;
|
||||
|
||||
+102
-86
@@ -33,9 +33,7 @@ ChannelInfo::ChannelInfo(const Anope::string &chname)
|
||||
|
||||
this->name = chname;
|
||||
|
||||
this->mlock_on = DefMLockOn;
|
||||
this->mlock_off = DefMLockOff;
|
||||
this->Params = DefMLockParams;
|
||||
this->mode_locks = def_mode_locks;
|
||||
|
||||
size_t t;
|
||||
/* Set default channel flags */
|
||||
@@ -392,7 +390,9 @@ void ChannelInfo::LoadMLock()
|
||||
std::vector<Anope::string> modenames_on, modenames_off;
|
||||
|
||||
// Force +r
|
||||
this->SetMLock(CMODE_REGISTERED, true);
|
||||
ChannelMode *chm = ModeManager::FindChannelModeByName(CMODE_REGISTERED);
|
||||
if (chm)
|
||||
this->SetMLock(chm, true);
|
||||
this->GetExtRegular("db_mlock_modes_on", modenames_on);
|
||||
this->GetExtRegular("db_mlock_modes_off", modenames_off);
|
||||
|
||||
@@ -405,7 +405,7 @@ void ChannelInfo::LoadMLock()
|
||||
if (m && m->NameAsString.equals_cs(*it))
|
||||
{
|
||||
ChannelMode *cm = debug_cast<ChannelMode *>(m);
|
||||
this->SetMLock(cm->Name, true);
|
||||
this->SetMLock(cm, true);
|
||||
}
|
||||
}
|
||||
for (std::vector<Anope::string>::iterator it = modenames_off.begin(), it_end = modenames_off.end(); it != it_end; ++it)
|
||||
@@ -415,7 +415,7 @@ void ChannelInfo::LoadMLock()
|
||||
if (m && m->NameAsString.equals_cs(*it))
|
||||
{
|
||||
ChannelMode *cm = debug_cast<ChannelMode *>(m);
|
||||
this->SetMLock(cm->Name, false);
|
||||
this->SetMLock(cm, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -429,15 +429,28 @@ void ChannelInfo::LoadMLock()
|
||||
if (m && m->Class == MC_CHANNEL)
|
||||
{
|
||||
ChannelMode *cm = debug_cast<ChannelMode *>(m);
|
||||
this->SetMLock(cm->Name, true, it->second);
|
||||
this->SetMLock(cm, true, it->second);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
if (this->GetExtRegular("db_mlp_off", params))
|
||||
{
|
||||
for (std::vector<std::pair<Anope::string, Anope::string> >::iterator it = params.begin(), it_end = params.end(); it != it_end; ++it)
|
||||
{
|
||||
Mode *m = ModeManager::FindModeByName(it->first);
|
||||
if (m && m->Class == MC_CHANNEL)
|
||||
{
|
||||
ChannelMode *cm = debug_cast<ChannelMode *>(m);
|
||||
this->SetMLock(cm, false, it->second);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
this->Shrink("db_mlock_modes_on");
|
||||
this->Shrink("db_mlock_modes_off");
|
||||
this->Shrink("db_mlp");
|
||||
this->Shrink("db_mlp_off");
|
||||
|
||||
/* Create perm channel */
|
||||
if (this->HasFlag(CI_PERSIST) && !this->c)
|
||||
@@ -453,132 +466,135 @@ void ChannelInfo::LoadMLock()
|
||||
}
|
||||
|
||||
/** Check if a mode is mlocked
|
||||
* @param Name The mode
|
||||
* @param mode The mode
|
||||
* @param status True to check mlock on, false for mlock off
|
||||
* @return true on success, false on fail
|
||||
*/
|
||||
bool ChannelInfo::HasMLock(ChannelModeName Name, bool status) const
|
||||
bool ChannelInfo::HasMLock(ChannelMode *mode, const Anope::string ¶m, bool status) const
|
||||
{
|
||||
if (status)
|
||||
return this->mlock_on.HasFlag(Name);
|
||||
else
|
||||
return this->mlock_off.HasFlag(Name);
|
||||
std::map<ChannelModeName, ModeLock>::const_iterator it = this->mode_locks.find(mode->Name);
|
||||
|
||||
if (it != this->mode_locks.end())
|
||||
{
|
||||
if (mode->Type != MODE_REGULAR)
|
||||
{
|
||||
std::map<ChannelModeName, ModeLock>::const_iterator it_end = this->mode_locks.upper_bound(mode->Name);
|
||||
for (; it != it_end; ++it)
|
||||
{
|
||||
const ModeLock &ml = it->second;
|
||||
if (ml.param == param)
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
return it->second.set == status;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/** Set a mlock
|
||||
* @param Name The mode
|
||||
* @param mode The mode
|
||||
* @param status True for mlock on, false for mlock off
|
||||
* @param param The param to use for this mode, if required
|
||||
* @return true on success, false on failure (module blocking)
|
||||
*/
|
||||
bool ChannelInfo::SetMLock(ChannelModeName Name, bool status, const Anope::string ¶m)
|
||||
bool ChannelInfo::SetMLock(ChannelMode *mode, bool status, const Anope::string ¶m, const Anope::string &setter, time_t created)
|
||||
{
|
||||
if (!status && !param.empty())
|
||||
throw CoreException("Was told to mlock a mode negatively with a param?");
|
||||
std::pair<ChannelModeName, ModeLock> ml = std::make_pair(mode->Name, ModeLock(status, mode->Name, param, setter, created));
|
||||
|
||||
EventReturn MOD_RESULT;
|
||||
FOREACH_RESULT(I_OnMLock, OnMLock(this, Name, status, param));
|
||||
FOREACH_RESULT(I_OnMLock, OnMLock(this, &ml.second));
|
||||
if (MOD_RESULT == EVENT_STOP)
|
||||
return false;
|
||||
|
||||
/* First, remove this everywhere */
|
||||
this->mlock_on.UnsetFlag(Name);
|
||||
this->mlock_off.UnsetFlag(Name);
|
||||
|
||||
std::map<ChannelModeName, Anope::string>::iterator it = Params.find(Name);
|
||||
if (it != Params.end())
|
||||
Params.erase(it);
|
||||
|
||||
if (status)
|
||||
this->mlock_on.SetFlag(Name);
|
||||
else
|
||||
this->mlock_off.SetFlag(Name);
|
||||
|
||||
if (status && !param.empty())
|
||||
this->Params.insert(std::make_pair(Name, param));
|
||||
/* First, remove this */
|
||||
this->RemoveMLock(mode, param);
|
||||
|
||||
this->mode_locks.insert(ml);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/** Remove a mlock
|
||||
* @param Name The mode
|
||||
* @return true on success, false on failure (module blocking)
|
||||
* @param mode The mode
|
||||
* @param param The param of the mode, required if it is a list or status mode
|
||||
* @return true on success, false on failure
|
||||
*/
|
||||
bool ChannelInfo::RemoveMLock(ChannelModeName Name)
|
||||
bool ChannelInfo::RemoveMLock(ChannelMode *mode, const Anope::string ¶m)
|
||||
{
|
||||
EventReturn MOD_RESULT;
|
||||
FOREACH_RESULT(I_OnUnMLock, OnUnMLock(this, Name));
|
||||
FOREACH_RESULT(I_OnUnMLock, OnUnMLock(this, mode, param));
|
||||
if (MOD_RESULT == EVENT_STOP)
|
||||
return false;
|
||||
|
||||
this->mlock_on.UnsetFlag(Name);
|
||||
this->mlock_off.UnsetFlag(Name);
|
||||
if (mode->Type == MODE_REGULAR || mode->Type == MODE_PARAM)
|
||||
return this->mode_locks.erase(mode->Name) > 0;
|
||||
else
|
||||
{
|
||||
// For list or status modes, we must check the parameter
|
||||
std::multimap<ChannelModeName, ModeLock>::iterator it = this->mode_locks.find(mode->Name), it_end = this->mode_locks.upper_bound(mode->Name);
|
||||
for (; it != it_end; ++it)
|
||||
{
|
||||
const ModeLock &ml = it->second;
|
||||
if (ml.param == param)
|
||||
{
|
||||
this->mode_locks.erase(it);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
std::map<ChannelModeName, Anope::string>::iterator it = Params.find(Name);
|
||||
if (it != Params.end())
|
||||
this->Params.erase(it);
|
||||
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/** Clear all mlocks on the channel
|
||||
*/
|
||||
void ChannelInfo::ClearMLock()
|
||||
{
|
||||
this->mlock_on.ClearFlags();
|
||||
this->mlock_off.ClearFlags();
|
||||
this->mode_locks.clear();
|
||||
}
|
||||
|
||||
/** Get the number of mlocked modes for this channel
|
||||
* @param status true for mlock on, false for mlock off
|
||||
* @return The number of mlocked modes
|
||||
/** Get all of the mlocks for this channel
|
||||
* @return The mlocks
|
||||
*/
|
||||
size_t ChannelInfo::GetMLockCount(bool status) const
|
||||
const std::multimap<ChannelModeName, ModeLock> &ChannelInfo::GetMLock() const
|
||||
{
|
||||
if (status)
|
||||
return this->mlock_on.FlagCount();
|
||||
else
|
||||
return this->mlock_off.FlagCount();
|
||||
return this->mode_locks;
|
||||
}
|
||||
|
||||
/** Get a param from the channel
|
||||
* @param Name The mode
|
||||
* @param Target a string to put the param into
|
||||
* @return true on success
|
||||
/** Get a list of modes on a channel
|
||||
* @param Name The mode name to get a list of
|
||||
* @return a pair of iterators for the beginning and end of the list
|
||||
*/
|
||||
bool ChannelInfo::GetParam(ChannelModeName Name, Anope::string &Target) const
|
||||
std::pair<ChannelInfo::ModeList::iterator, ChannelInfo::ModeList::iterator> ChannelInfo::GetModeList(ChannelModeName Name)
|
||||
{
|
||||
std::map<ChannelModeName, Anope::string>::const_iterator it = this->Params.find(Name);
|
||||
return std::make_pair(this->mode_locks.find(Name), this->mode_locks.upper_bound(Name));
|
||||
}
|
||||
|
||||
Target.clear();
|
||||
|
||||
if (it != this->Params.end())
|
||||
/** Get details for a specific mlock
|
||||
* @param name The mode name
|
||||
* @param param An optional param to match with
|
||||
* @return The MLock, if any
|
||||
*/
|
||||
ModeLock *ChannelInfo::GetMLock(ChannelModeName name, const Anope::string ¶m)
|
||||
{
|
||||
std::multimap<ChannelModeName, ModeLock>::iterator it = this->mode_locks.find(name);
|
||||
if (it != this->mode_locks.end())
|
||||
{
|
||||
Target = it->second;
|
||||
return true;
|
||||
if (param.empty())
|
||||
return &it->second;
|
||||
else
|
||||
{
|
||||
std::multimap<ChannelModeName, ModeLock>::iterator it_end = this->mode_locks.upper_bound(name);
|
||||
for (; it != it_end; ++it)
|
||||
{
|
||||
if (Anope::Match(param, it->second.param))
|
||||
return &it->second;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/** Check if a mode is set and has a param
|
||||
* @param Name The mode
|
||||
*/
|
||||
bool ChannelInfo::HasParam(ChannelModeName Name) const
|
||||
{
|
||||
std::map<ChannelModeName, Anope::string>::const_iterator it = this->Params.find(Name);
|
||||
|
||||
if (it != this->Params.end())
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/** Clear all the params from the channel
|
||||
*/
|
||||
void ChannelInfo::ClearParams()
|
||||
{
|
||||
Params.clear();
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/** Check whether a user is permitted to be on this channel
|
||||
|
||||
@@ -171,6 +171,80 @@ void sockaddrs::ntop(int type, const void *src)
|
||||
throw CoreException("Invalid socket type");
|
||||
}
|
||||
|
||||
cidr::cidr(const Anope::string &ip)
|
||||
{
|
||||
if (ip.find_first_not_of("01234567890:./") != Anope::string::npos)
|
||||
throw SocketException("Invalid IP");
|
||||
|
||||
bool ipv6 = ip.find(':') != Anope::string::npos;
|
||||
size_t sl = ip.find_last_of('/');
|
||||
if (sl == Anope::string::npos)
|
||||
{
|
||||
this->cidr_ip = ip;
|
||||
this->cidr_len = ipv6 ? 128 : 32;
|
||||
this->addr.pton(ipv6 ? AF_INET6 : AF_INET, ip);
|
||||
}
|
||||
else
|
||||
{
|
||||
Anope::string real_ip = ip.substr(0, sl);
|
||||
Anope::string cidr_range = ip.substr(sl + 1);
|
||||
if (!cidr_range.is_pos_number_only())
|
||||
throw SocketException("Invalid CIDR range");
|
||||
|
||||
this->cidr_ip = real_ip;
|
||||
this->cidr_len = convertTo<unsigned int>(cidr_range);
|
||||
this->addr.pton(ipv6 ? AF_INET6 : AF_INET, real_ip);
|
||||
}
|
||||
}
|
||||
|
||||
cidr::cidr(const Anope::string &ip, unsigned char len)
|
||||
{
|
||||
bool ipv6 = ip.find(':') != Anope::string::npos;
|
||||
this->addr.pton(ipv6 ? AF_INET6 : AF_INET, ip);
|
||||
this->cidr_ip = ip;
|
||||
this->cidr_len = len;
|
||||
}
|
||||
|
||||
Anope::string cidr::mask() const
|
||||
{
|
||||
return this->cidr_ip + "/" + this->cidr_len;
|
||||
}
|
||||
|
||||
bool cidr::match(sockaddrs &other)
|
||||
{
|
||||
if (this->addr.sa.sa_family != other.sa.sa_family)
|
||||
return false;
|
||||
|
||||
unsigned char *ip, *their_ip, byte;
|
||||
|
||||
switch (this->addr.sa.sa_family)
|
||||
{
|
||||
case AF_INET:
|
||||
ip = reinterpret_cast<unsigned char *>(&this->addr.sa4.sin_addr);
|
||||
byte = this->cidr_len / 8;
|
||||
their_ip = reinterpret_cast<unsigned char *>(&other.sa4.sin_addr);
|
||||
break;
|
||||
case AF_INET6:
|
||||
ip = reinterpret_cast<unsigned char *>(&this->addr.sa6.sin6_addr);
|
||||
byte = this->cidr_len / 8;
|
||||
their_ip = reinterpret_cast<unsigned char *>(&other.sa6.sin6_addr);
|
||||
break;
|
||||
default:
|
||||
throw SocketException("Invalid address type");
|
||||
}
|
||||
|
||||
if (memcmp(ip, their_ip, byte))
|
||||
return false;
|
||||
|
||||
ip += byte;
|
||||
their_ip += byte;
|
||||
byte = this->cidr_len % 8;
|
||||
if ((*ip & byte) != (*their_ip & byte))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/** Default constructor
|
||||
*/
|
||||
SocketEngineBase::SocketEngineBase()
|
||||
|
||||
+23
-2
@@ -165,6 +165,11 @@ Anope::string User::GetMask() const
|
||||
return this->nick + "!" + this->ident + "@" + this->host;
|
||||
}
|
||||
|
||||
Anope::string User::GetDisplayedMask() const
|
||||
{
|
||||
return this->nick + "!" + this->GetVIdent() + "@" + this->GetDisplayedHost();
|
||||
}
|
||||
|
||||
void User::SetRealname(const Anope::string &srealname)
|
||||
{
|
||||
if (srealname.empty())
|
||||
@@ -921,7 +926,16 @@ bool is_excepted(ChannelInfo *ci, User *user)
|
||||
if (!ci->c || !ModeManager::FindChannelModeByName(CMODE_EXCEPT))
|
||||
return false;
|
||||
|
||||
return elist_match_user(ci->c->excepts, user);
|
||||
|
||||
std::pair<Channel::ModeList::iterator, Channel::ModeList::iterator> modes = ci->c->GetModeList(CMODE_EXCEPT);
|
||||
for (; modes.first != modes.second; ++modes.first)
|
||||
{
|
||||
Entry e(modes.first->second);
|
||||
if (e.Matches(user))
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
@@ -932,7 +946,14 @@ bool is_excepted_mask(ChannelInfo *ci, const Anope::string &mask)
|
||||
if (!ci->c || !ModeManager::FindChannelModeByName(CMODE_EXCEPT))
|
||||
return false;
|
||||
|
||||
return elist_match_mask(ci->c->excepts, mask, 0);
|
||||
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))
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
|
||||
@@ -1,72 +0,0 @@
|
||||
#include "services.h"
|
||||
|
||||
bool Anope::Match(const Anope::string &str, const Anope::string &mask, bool case_sensitive)
|
||||
{
|
||||
size_t s = 0, m = 0, str_len = str.length(), mask_len = mask.length();
|
||||
|
||||
while (s < str_len && m < mask_len && mask[m] != '*')
|
||||
{
|
||||
char string = str[s], wild = mask[m];
|
||||
if (case_sensitive)
|
||||
{
|
||||
if (wild != string && wild != '?')
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (tolower(wild) != tolower(string) && wild != '?')
|
||||
return false;
|
||||
}
|
||||
|
||||
++m;
|
||||
++s;
|
||||
}
|
||||
|
||||
size_t sp = 0, mp = 0;
|
||||
while (s < str_len)
|
||||
{
|
||||
char string = str[s], wild = mask[m];
|
||||
if (wild == '*')
|
||||
{
|
||||
if (++m == mask_len)
|
||||
return 1;
|
||||
|
||||
mp = m;
|
||||
sp = s + 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (case_sensitive)
|
||||
{
|
||||
if (wild == string || wild == '?')
|
||||
{
|
||||
++m;
|
||||
++s;
|
||||
}
|
||||
else
|
||||
{
|
||||
m = mp;
|
||||
s = sp++;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (tolower(wild) == tolower(string) || wild == '?')
|
||||
{
|
||||
++m;
|
||||
++s;
|
||||
}
|
||||
else
|
||||
{
|
||||
m = mp;
|
||||
s = sp++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (mask[m] == '*')
|
||||
++m;
|
||||
|
||||
return m == mask_len;
|
||||
}
|
||||
Reference in New Issue
Block a user