mirror of
https://github.com/anope/anope.git
synced 2026-06-15 12:14:45 +02:00
Compare commits
38 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| f3c94e5d23 | |||
| f2ab092742 | |||
| 7d5ca5c90b | |||
| 8ee85efd70 | |||
| 0cab675825 | |||
| f1751dcb21 | |||
| 8b02613549 | |||
| c9625ccf3f | |||
| 435ce51196 | |||
| 57ac7cb4db | |||
| 8cb2b801e9 | |||
| 66b45534a8 | |||
| 499077826c | |||
| bc4d34ebd8 | |||
| f40719787f | |||
| 934a13c21f | |||
| e5602f956d | |||
| de11a19e03 | |||
| b437468b84 | |||
| 0a99571c0f | |||
| e704fa6266 | |||
| f908514095 | |||
| bafcba023c | |||
| 9a44b74186 | |||
| 883935c3e0 | |||
| 6d34054b78 | |||
| 3da9b6df0d | |||
| 0ab0e4737c | |||
| cdf356ed33 | |||
| 7d268bb4ca | |||
| 184350ff4a | |||
| 4cdbf560e1 | |||
| cbccc79d37 | |||
| 9b188a6c04 | |||
| 2f74513246 | |||
| 94dbb19593 | |||
| 8232759a92 | |||
| b006966d25 |
+1
-1
@@ -14,6 +14,6 @@ Version | Supported
|
||||
|
||||
## Reporting a Vulnerability
|
||||
|
||||
Please do not report security vulnerabilities on GitHub. Instead, email the details to team@anope.org or get the attention of a developer in our development IRC channel at irc.anope.org #anope-devel and PM them the details.
|
||||
Please do not report security vulnerabilities on GitHub. Instead, email the details to team@anope.org or get the attention of a developer in our development IRC channel at irc.teranova.net #anope-devel and PM them the details.
|
||||
|
||||
We will triage your issue as soon as possible and try to release a fixed version within a week of receiving your report.
|
||||
|
||||
@@ -4,7 +4,7 @@ Anope is an open source set of IRC services. It is highly modular, with a vast n
|
||||
|
||||
* [Website](https://anope.org)
|
||||
* [GitHub](https://github.com/anope)
|
||||
* IRC \#anope on irc.anope.org
|
||||
* IRC \#anope on irc.teranova.net
|
||||
|
||||
## Installation
|
||||
|
||||
@@ -33,7 +33,7 @@ Copy conf/anope.example.conf to conf/anope.conf
|
||||
$ cp conf/anope.example.conf conf/anope.conf
|
||||
```
|
||||
|
||||
Edit anope.conf, configuring the uplink, serverinfo, and protocol module configurations. Example link blocks for popular IRCds are included in the anope.example.conf documentation. The [Anope wiki](https://wiki.anope.org) is also a good source of information. Our support channel is located at #anope on [irc.anope.org](irc://irc.anope.org/#anope).
|
||||
Edit anope.conf, configuring the uplink, serverinfo, and protocol module configurations. Example link blocks for popular IRCds are included in the the example.conf documentation. The [Anope wiki](https://wiki.anope.org) is also a good source of information. Our support channel is located at #anope on [irc.teranova.net](ircs://irc.teranova.net/anope).
|
||||
|
||||
Note that the example configuration file includes other example configuration files. If you want to modify the other example configuration files, copy them (e.g. `modules.example.conf` to `modules.conf`) and modify the `include` directive in `anope.conf` to include the new file.
|
||||
|
||||
|
||||
+1
-1
@@ -1,4 +1,4 @@
|
||||
# Only install example.chk and anope.example.conf from this directory
|
||||
# Only install cron.example.sh and anope.example.conf from this directory
|
||||
# NOTE: I would've had this just find all files in the directory, but that would include files not needed (like this file)
|
||||
set(DATA cron.example.sh anope.example.conf botserv.example.conf hostserv.example.conf modules.example.conf operserv.example.conf chanserv.example.conf global.example.conf memoserv.example.conf nickserv.example.conf chanstats.example.conf irc2sql.example.conf stats.standalone.example.conf)
|
||||
install(FILES ${DATA}
|
||||
|
||||
+4
-19
@@ -430,26 +430,11 @@ options
|
||||
timeoutcheck = 3s
|
||||
|
||||
/*
|
||||
* If set, this will allow users to let services send PRIVMSGs to them
|
||||
* instead of NOTICEs. Also see the "msg" option of nickserv:defaults,
|
||||
* which also toggles the default communication (PRIVMSG or NOTICE) to
|
||||
* use for unregistered users.
|
||||
*
|
||||
* This is a feature that is against the IRC RFC and should be used ONLY
|
||||
* if absolutely necessary.
|
||||
*
|
||||
* This directive is optional, and not recommended.
|
||||
* If set Anope will tell users to use a server-side alias for messaging
|
||||
* services instead of /msg. The alias for each service defaults to the
|
||||
* bot name but can be configured in the service block.
|
||||
*/
|
||||
#useprivmsg = yes
|
||||
|
||||
/*
|
||||
* If set, will force services to only respond to PRIVMSGs addresses to
|
||||
* Nick@ServerName - e.g. NickServ@example.com. This should be used in
|
||||
* conjunction with IRCd aliases. This directive is optional.
|
||||
*
|
||||
* This option will have no effect on some IRCds, such as TS6 IRCds.
|
||||
*/
|
||||
#usestrictprivmsg = yes
|
||||
#servicealias = yes
|
||||
|
||||
/*
|
||||
* If set, Anope will only show /stats o to IRC Operators. This directive
|
||||
|
||||
@@ -59,6 +59,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "BS"
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -334,10 +345,10 @@ privilege
|
||||
/*
|
||||
* fantasy
|
||||
*
|
||||
* Allows 'fantasist' commands to be used in channels.
|
||||
* Allows fantasy commands (e.g. !kick) to be used in channels.
|
||||
*
|
||||
* Provides the commands:
|
||||
* botserv/set/fantasy - Used for enabling or disabling BotServ's fantasist commands.
|
||||
* botserv/set/fantasy - Used for enabling or disabling BotServ's fantasy commands.
|
||||
*/
|
||||
module
|
||||
{
|
||||
|
||||
@@ -49,6 +49,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "CS"
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -49,6 +49,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "GL"
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -49,6 +49,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "HS"
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -49,6 +49,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "MS"
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -49,6 +49,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "NS"
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -106,8 +117,7 @@ module
|
||||
* - memo_mail: Notify user if they have a new memo by mail
|
||||
* - autoop: User will be automatically opped in channels they enter and have access to
|
||||
* - neverop: User can not be added to access lists
|
||||
* - msg: Messages will be sent as PRIVMSGs instead of NOTICEs, requires options:useprivmsg
|
||||
* to be enabled as well
|
||||
* - msg: Messages will be sent as PRIVMSGs instead of NOTICEs
|
||||
* - ns_keep_modes: Enables keepmodes, which retains user modes across sessions
|
||||
*
|
||||
* This directive is optional, if left blank, the options will default to memo_signon, and
|
||||
@@ -512,7 +522,6 @@ command { service = "NickServ"; name = "RESETPASS"; command = "nickserv/resetpas
|
||||
* nickserv/set/email, nickserv/saset/email - Used for setting a users email address.
|
||||
* nickserv/set/keepmodes, nickserv/saset/keepmodes - Configure whether or not services should retain a user's modes across sessions.
|
||||
* nickserv/set/kill, nickserv/saset/kill - Used for configuring nickname protection.
|
||||
* nickserv/set/message, nickserv/saset/message - Used to configure how services send messages to you.
|
||||
* nickserv/set/neverop, nickserv/saset/neverop - Used to configure whether a user can be added to access lists
|
||||
* nickserv/saset/noexpire - Used for configuring noexpire, which prevents nicks from expiring.
|
||||
* nickserv/set/password, nickserv/saset/password - Used for changing a users password.
|
||||
@@ -547,9 +556,6 @@ command { service = "NickServ"; name = "SASET KEEPMODES"; command = "nickserv/sa
|
||||
command { service = "NickServ"; name = "SET KILL"; command = "nickserv/set/kill"; }
|
||||
command { service = "NickServ"; name = "SASET KILL"; command = "nickserv/saset/kill"; permission = "nickserv/saset/kill"; }
|
||||
|
||||
command { service = "NickServ"; name = "SET MESSAGE"; command = "nickserv/set/message"; }
|
||||
command { service = "NickServ"; name = "SASET MESSAGE"; command = "nickserv/saset/message"; permission = "nickserv/saset/message"; }
|
||||
|
||||
command { service = "NickServ"; name = "SET PASSWORD"; command = "nickserv/set/password"; }
|
||||
command { service = "NickServ"; name = "SASET PASSWORD"; command = "nickserv/saset/password"; permission = "nickserv/saset/password"; }
|
||||
|
||||
@@ -569,6 +575,21 @@ module { name = "ns_set_language" }
|
||||
command { service = "NickServ"; name = "SET LANGUAGE"; command = "nickserv/set/language"; }
|
||||
command { service = "NickServ"; name = "SASET LANGUAGE"; command = "nickserv/saset/language"; permission = "nickserv/saset/language"; }
|
||||
|
||||
/*
|
||||
* ns_set_message
|
||||
*
|
||||
* Provides the command nickserv/set/message and nickserv/saset/message.
|
||||
*
|
||||
* Allows users to let services send them PRIVMSGs instead of NOTICEs.
|
||||
*
|
||||
* This might cause problems with badly written clients as the IRC RFC
|
||||
* requires that automatic responses to a PRIVMSG use a NOTICE to avoid
|
||||
* message loops. Only enable this if you are sure this can not happen.
|
||||
*/
|
||||
#module { name = "ns_set_message" }
|
||||
#command { service = "NickServ"; name = "SET MESSAGE"; command = "nickserv/set/message"; }
|
||||
#command { service = "NickServ"; name = "SASET MESSAGE"; command = "nickserv/saset/message"; permission = "nickserv/saset/message"; }
|
||||
|
||||
/*
|
||||
* ns_set_misc
|
||||
*
|
||||
@@ -582,10 +603,10 @@ command { service = "NickServ"; name = "SET URL"; command = "nickserv/set/misc";
|
||||
command { service = "NickServ"; name = "SASET URL"; command = "nickserv/saset/misc"; misc_description = _("Associate a URL with this account"); permission = "nickserv/saset/url"; group = "nickserv/admin"; }
|
||||
#command { service = "NickServ"; name = "SET DISCORD"; command = "nickserv/set/misc"; misc_description = _("Associate a Discord account with your account"); }
|
||||
#command { service = "NickServ"; name = "SASET DISCORD"; command = "nickserv/saset/misc"; misc_description = _("Associate a Discord account with this account"); permission = "nickserv/saset/discord"; group = "nickserv/admin"; }
|
||||
#command { service = "NickServ"; name = "SET FACEBOOK"; command = "nickserv/set/misc"; misc_description = _("Associate a Facebook URL with your account"); }
|
||||
#command { service = "NickServ"; name = "SASET FACEBOOK"; command = "nickserv/saset/misc"; misc_description = _("Associate a Facebook URL with this account"); permission = "nickserv/saset/facebook"; group = "nickserv/admin"; }
|
||||
#command { service = "NickServ"; name = "SET MASTODON"; command = "nickserv/set/misc"; misc_description = _("Associate a Mastodon account with your account"); }
|
||||
#command { service = "NickServ"; name = "SASET MASTODON"; command = "nickserv/saset/misc"; misc_description = _("Associate a Mastodon account with this account"); permission = "nickserv/saset/mastodon"; group = "nickserv/admin"; }
|
||||
#command { service = "NickServ"; name = "SET TIMEZONE"; command = "nickserv/set/misc"; misc_description = _("Associate a time zone with your account"); }
|
||||
#command { service = "NickServ"; name = "SASET TIMEZONE"; command = "nickserv/saset/misc"; misc_description = _("Associate a time zone with this account"); permission = "nickserv/saset/timezone"; group = "nickserv/admin"; }
|
||||
|
||||
/*
|
||||
* ns_suspend
|
||||
|
||||
@@ -49,6 +49,17 @@ service
|
||||
* Prefixes may be given to the channels in the form of mode characters or prefix symbols.
|
||||
*/
|
||||
#channels = "@#services,#mychan"
|
||||
|
||||
/*
|
||||
* The server alias that can be used to securely message this service. If
|
||||
* your IRC server does not have an alias for this service you can set this
|
||||
* to an empty string to tell users to use /msg instead.
|
||||
*
|
||||
* This setting is ignored when options:servicealias is disabled.
|
||||
*
|
||||
* Defaults to the nick of the service if not set.
|
||||
*/
|
||||
#alias = "OS"
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -1,3 +1,16 @@
|
||||
Anope Version 2.1.10
|
||||
--------------------
|
||||
Added support for NEXTBANS on UnrealIRCd.
|
||||
Changed hostmask access entries added by nick to use that nick as the default description.
|
||||
Changed modes to be handled internally in their split form.
|
||||
Changed ns_cert to notify a user that their certificate is being automatically added to their account.
|
||||
Fixed matching users against extended bans.
|
||||
Fixed parsing name-only extended bans on InspIRCd.
|
||||
Fixed respecting the preferred extended ban format on InspIRCd.
|
||||
Fixed the name of the cron script in the docs.
|
||||
Updated the list of supported IRCds.
|
||||
Updated the location of the Anope IRC channels
|
||||
|
||||
Anope Version 2.1.9
|
||||
-------------------
|
||||
Bumped the minimum supported version of UnrealIRCd to 6.
|
||||
|
||||
@@ -1,3 +1,10 @@
|
||||
Anope Version 2.1.10
|
||||
--------------------
|
||||
Added options:servicealias.
|
||||
Moved nickserv/set/message and nickserv/saset/message to the ns_set_message module.
|
||||
Removed options:useprivmsg.
|
||||
Removed options:usestrictprivmsg
|
||||
|
||||
Anope Version 2.1.9
|
||||
-------------------
|
||||
No significant changes.
|
||||
|
||||
+1
-1
@@ -90,4 +90,4 @@ Anope DefCon
|
||||
6) Support
|
||||
|
||||
You might get DefCon support by posting on our online forum, or maybe on
|
||||
our #anope channel at /server irc.anope.org.
|
||||
our #anope channel at /server irc.teranova.net.
|
||||
|
||||
+5
-5
@@ -60,7 +60,7 @@ Note: You should also read the README and FAQ files!
|
||||
most likely not work!
|
||||
|
||||
If you need help, you should visit https://forum.anope.org/ or #anope on
|
||||
irc.anope.org. Provide *complete* error output, along with other relevant
|
||||
irc.teranova.net. Provide *complete* error output, along with other relevant
|
||||
information eg. OS, compiler and C++ library versions.
|
||||
See the README file for more information.
|
||||
|
||||
@@ -111,17 +111,17 @@ Note: You should also read the README and FAQ files!
|
||||
A crontab entry will allow you to check periodically whether Anope is
|
||||
still running, and restart it if not.
|
||||
|
||||
First rename the example.chk script that is in Anope path (by default,
|
||||
this is ~/anope/conf) to anope.chk and edit it. You'll need to
|
||||
First rename the cron.example.sh script that is in Anope path (by default,
|
||||
this is ~/anope/conf) to cron.sh and edit it. You'll need to
|
||||
modify the CONFIGURATION part of the file. Then ensure that the file is
|
||||
marked as executable by typing chmod +x anope.chk, and try to launch the
|
||||
marked as executable by typing chmod +x cron.sh, and try to launch the
|
||||
script to see if it works (Anope must not be running when you do this ;))
|
||||
|
||||
When this is done, you'll have to add the crontab entry. Type crontab -e.
|
||||
This will open the default text editor with the crontab file. Enter the
|
||||
following (with correct path):
|
||||
|
||||
*/5 * * * * /home/ircd/anope/conf/anope.chk >/dev/null 2>&1
|
||||
*/5 * * * * /home/ircd/anope/conf/cron.sh >/dev/null 2>&1
|
||||
|
||||
The */5 at the beginning means "check every 5 minutes". You may replace
|
||||
the 5 with other another number if you want (but less than 60). Consult
|
||||
|
||||
+5
-5
@@ -64,7 +64,7 @@ Note : Vous devrez également lire les fichiers README et FAQ !
|
||||
recommandée, et Anope ne fonctionnera probablement pas !
|
||||
|
||||
Si vous avez besoin d'aide, vous pouvez aller sur le site
|
||||
https://forum.anope.org/ ou le canal #anope sur irc.anope.org.
|
||||
https://forum.anope.org/ ou le canal #anope sur irc.teranova.net.
|
||||
Fournissez *l'essemble* des erreurs qui apparaîssent, en plus de
|
||||
toutes informations utiles, comme les versions de votre OS, du
|
||||
compilateur utilisé et de la librairie C++. Lisez le fichier README
|
||||
@@ -121,11 +121,11 @@ Note : Vous devrez également lire les fichiers README et FAQ !
|
||||
Une entrée crontab vous permettra de vérifier périodiquement si Anope
|
||||
est toujours en cours d'exécution et de le redémarrer s'il n'est pas.
|
||||
|
||||
D'abord renommez le script example.chk qui est dans les dossiers
|
||||
d'Anope (par défaut, ~/anope/conf) en anope.chk et modifiez-le.
|
||||
D'abord renommez le script cron.example.sh qui est dans les dossiers
|
||||
d'Anope (par défaut, ~/anope/conf) en cron.sh et modifiez-le.
|
||||
Vous aurez besoin de modifier la partie CONFIGURATION du fichier.
|
||||
Assurez-vous ensuite que le fichier est marqué comme exécutable en
|
||||
tapant chmod +x anope.chk et essayez de lancer le script pour voir
|
||||
tapant chmod +x cron.sh et essayez de lancer le script pour voir
|
||||
si cela fonctionne (Anope ne doit pas être en marche lorsque vous
|
||||
testez cela ;))
|
||||
|
||||
@@ -133,7 +133,7 @@ Note : Vous devrez également lire les fichiers README et FAQ !
|
||||
crontab -e. Cela va ouvrir l'éditeur de texte par défaut avec le
|
||||
fichier crontab. Entrez la ligne suivante (avec le chemin correct) :
|
||||
|
||||
*/5 * * * * /home/ircd/anope/conf/anope.chk > /dev/null 2>&1
|
||||
*/5 * * * * /home/ircd/anope/conf/cron.sh > /dev/null 2>&1
|
||||
|
||||
Le */5 au début signifie "vérifier toutes les 5 minutes". Vous pouvez
|
||||
remplacer le 5 par un autre numéro si vous voulez (mais moins de 60).
|
||||
|
||||
+1
-1
@@ -111,7 +111,7 @@ Anope Modules
|
||||
Use modules at your own risk, and make sure you get them from a
|
||||
reputable source. You might get module support by contacting the module
|
||||
author, posting on our online forum, or maybe on our #anope channel
|
||||
at /server irc.anope.org.
|
||||
at /server irc.teranova.net.
|
||||
|
||||
7) Information for Developers
|
||||
|
||||
|
||||
+3
-3
@@ -167,11 +167,11 @@ Table of Contents
|
||||
Anope currently works with:
|
||||
|
||||
* Bahamut 2.0 or later
|
||||
* ircd-hybrid 8.2.23 or later
|
||||
* InspIRCd 3 or later
|
||||
* ircd-hybrid 8.2.23 or later
|
||||
* ircd-ratbox 3 or later
|
||||
* ngIRCd 19.2 or later
|
||||
* Plexus 3 or later
|
||||
* Ratbox 2.0.6 or later
|
||||
* Solanum (all versions)
|
||||
* UnrealIRCd 6 or later
|
||||
|
||||
@@ -245,7 +245,7 @@ Table of Contents
|
||||
|
||||
If you read the documentation carefully, and didn't find the answer to
|
||||
your question, feel free to post on the website forums or join our irc
|
||||
channel (irc.anope.org #anope). Once you join our Support channel be as
|
||||
channel (irc.teranova.net #anope). Once you join our Support channel be as
|
||||
precise as possible when asking a question, because we have no extraordinary
|
||||
powers and can't guess things if they aren't provided.
|
||||
|
||||
|
||||
@@ -31,6 +31,8 @@ public:
|
||||
time_t lastmsg;
|
||||
/* Map of actual command names -> service name/permission required */
|
||||
CommandInfo::map commands;
|
||||
/* The server-side alias used to message this bot. */
|
||||
Anope::string alias;
|
||||
/* Modes the bot should have as configured in service:modes */
|
||||
Anope::string botmodes;
|
||||
/* Channels the bot should be in as configured in service:channels */
|
||||
@@ -126,6 +128,9 @@ public:
|
||||
*/
|
||||
CommandInfo *GetCommand(const Anope::string &cname);
|
||||
|
||||
/** Get the command that users can use to send a message to this bot. */
|
||||
Anope::string GetQueryCommand() const;
|
||||
|
||||
/** Find a bot by nick
|
||||
* @param nick The nick
|
||||
* @param nick_only True to only look by nick, and not by UID
|
||||
|
||||
+1
-1
@@ -215,7 +215,7 @@ public:
|
||||
* @param mode the modes
|
||||
* @param enforce_mlock true to enforce mlock
|
||||
*/
|
||||
void SetModesInternal(MessageSource &source, const Anope::string &mode, time_t ts = 0, bool enforce_mlock = true);
|
||||
void SetModesInternal(MessageSource &source, const Anope::string &modes, const std::vector<Anope::string> ¶ms, time_t ts = 0, bool enforce_mlock = true);
|
||||
|
||||
/** Does the given user match the given list? (CMODE_BAN, CMODE_EXCEPT, etc, a list mode)
|
||||
* @param u The user
|
||||
|
||||
+2
-6
@@ -88,21 +88,17 @@ namespace Configuration
|
||||
{
|
||||
/* options:readtimeout */
|
||||
time_t ReadTimeout;
|
||||
/* options:useprivmsg */
|
||||
bool UsePrivmsg;
|
||||
/* If we should default to privmsging clients */
|
||||
bool DefPrivmsg;
|
||||
/* Default language */
|
||||
Anope::string DefLanguage;
|
||||
/* options:timeoutcheck */
|
||||
time_t TimeoutCheck;
|
||||
/* options:usestrictprivmsg */
|
||||
bool UseStrictPrivmsg;
|
||||
/* options:servicealias */
|
||||
bool ServiceAlias;
|
||||
/* networkinfo:nickchars */
|
||||
Anope::string NickChars;
|
||||
|
||||
/* either "/msg " or "/" */
|
||||
Anope::string StrictPrivmsg;
|
||||
/* List of uplink servers to try and connect to */
|
||||
std::vector<Uplink> Uplinks;
|
||||
/* A vector of our logfile options */
|
||||
|
||||
+5
-5
@@ -65,9 +65,9 @@ namespace Language
|
||||
} // namespace Language
|
||||
|
||||
/* Commonly used language strings */
|
||||
#define CONFIRM_DROP _("Please confirm that you want to drop \002%s\002 with \002%s%s DROP %s %s\002")
|
||||
#define CONFIRM_DROP _("Please confirm that you want to drop \002%s\002 with \002%s DROP %s %s\002")
|
||||
#define SERVICE_UNAVAILABLE _("Sorry, %s is temporarily unavailable.")
|
||||
#define MORE_INFO _("\002%s%s HELP %s\002 for more information.")
|
||||
#define MORE_INFO _("\002%s HELP %s\002 for more information.")
|
||||
#define BAD_USERHOST_MASK _("Mask must be in the form \037user\037@\037host\037.")
|
||||
#define BAD_EXPIRY_TIME _("Invalid expiry time.")
|
||||
#define USERHOST_MASK_TOO_WIDE _("%s coverage is too wide; Please use a more specific mask.")
|
||||
@@ -93,7 +93,7 @@ namespace Language
|
||||
#define NO_EXPIRE _("does not expire")
|
||||
#define LIST_INCORRECT_RANGE _("Incorrect range specified. The correct syntax is \002#\037from\037-\037to\037\002.")
|
||||
#define NICK_IS_SECURE _("This nickname is registered and protected. If it is your\n" \
|
||||
"nick, type \002%s%s IDENTIFY \037password\037\002. Otherwise,\n" \
|
||||
"nick, type \002%s IDENTIFY \037password\037\002. Otherwise,\n" \
|
||||
"please choose a different nick.")
|
||||
#define FORCENICKCHANGE_NOW _("This nickname has been registered; you may not use it.")
|
||||
#define NICK_CANNOT_BE_REGISTERED _("Nickname \002%s\002 may not be registered.")
|
||||
@@ -111,9 +111,9 @@ namespace Language
|
||||
#define CHAN_INFO_HEADER _("Information about channel \002%s\002:")
|
||||
#define CHAN_EXCEPTED _("\002%s\002 matches an except on %s and cannot be banned until the except has been removed.")
|
||||
#define MEMO_NEW_X_MEMO_ARRIVED _("There is a new memo on channel %s.\n" \
|
||||
"Type \002%s%s READ %s %zu\002 to read it.")
|
||||
"Type \002%s READ %s %zu\002 to read it.")
|
||||
#define MEMO_NEW_MEMO_ARRIVED _("You have a new memo from %s.\n" \
|
||||
"Type \002%s%s READ %zu\002 to read it.")
|
||||
"Type \002%s READ %zu\002 to read it.")
|
||||
#define MEMO_HAVE_NO_MEMOS _("You have no memos.")
|
||||
#define MEMO_X_HAS_NO_MEMOS _("%s has no memos.")
|
||||
#define MEMO_HAVE_NO_NEW_MEMOS _("You have no new memos.")
|
||||
|
||||
+3
-2
@@ -66,10 +66,11 @@ namespace Message
|
||||
* @param source The source of the SJOIN
|
||||
* @param chan The channel the users are joining to
|
||||
* @param ts The TS for the channel
|
||||
* @param modes The modes sent with the SJOIN, if any
|
||||
* @param modes The mode letters sent with the SJOIN, if any
|
||||
* @param modeparams The mode parameters sent with the SJOIN, if any
|
||||
* @param users The users and their status, if any
|
||||
*/
|
||||
static void SJoin(MessageSource &source, const Anope::string &chan, time_t ts, const Anope::string &modes, const std::list<SJoinUser> &users);
|
||||
static void SJoin(MessageSource &source, const Anope::string &chan, time_t ts, const Anope::string &modes, const std::vector<Anope::string> &modeparams, const std::list<SJoinUser> &users);
|
||||
};
|
||||
|
||||
struct CoreExport Kick
|
||||
|
||||
+4
-1
@@ -216,9 +216,12 @@ template<typename T>
|
||||
class CoreExport ChannelModeVirtual
|
||||
: public T
|
||||
{
|
||||
Anope::string base;
|
||||
private:
|
||||
ChannelMode *basech;
|
||||
|
||||
protected:
|
||||
Anope::string base;
|
||||
|
||||
public:
|
||||
ChannelModeVirtual(const Anope::string &mname, const Anope::string &basename);
|
||||
|
||||
|
||||
+5
-5
@@ -107,14 +107,14 @@ protected:
|
||||
* @param suid The unique identifier of the user.
|
||||
* @param nc The account the user is identified as, if any
|
||||
*/
|
||||
User(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc);
|
||||
User(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const std::vector<Anope::string> &smodeparams, const Anope::string &suid, NickCore *nc);
|
||||
|
||||
/** Destroy a user.
|
||||
*/
|
||||
virtual ~User();
|
||||
|
||||
public:
|
||||
static User *OnIntroduce(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc);
|
||||
static User *OnIntroduce(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc, const std::vector<Anope::string> &smodeparams = {});
|
||||
|
||||
/** Update the nickname of a user record accordingly, should be
|
||||
* called from ircd protocol.
|
||||
@@ -307,10 +307,10 @@ public:
|
||||
|
||||
/** Set a string of modes on a user internally
|
||||
* @param setter who/what is setting the mode
|
||||
* @param umodes The modes
|
||||
* @param umodes The mode letters
|
||||
* @param umodeparams The mode values
|
||||
*/
|
||||
void SetModesInternal(const MessageSource &source, const char *umodes, ...) ATTR_FORMAT(3, 4);
|
||||
void SetModesInternal(const MessageSource &source, const Anope::string &umodes);
|
||||
void SetModesInternal(const MessageSource &source, const Anope::string &umodes, const std::vector<Anope::string> &umodeparams = {});
|
||||
|
||||
/** Get modes set for this user.
|
||||
* @return A string of modes set on the user
|
||||
|
||||
+80
-72
@@ -7,8 +7,8 @@ msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: Anope\n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2024-09-26 13:24+0100\n"
|
||||
"PO-Revision-Date: 2024-09-26 13:25+0100\n"
|
||||
"POT-Creation-Date: 2024-10-22 16:28+0100\n"
|
||||
"PO-Revision-Date: 2024-10-22 16:29+0100\n"
|
||||
"Last-Translator: Sadie Powell <sadie@witchery.services>\n"
|
||||
"Language-Team: English\n"
|
||||
"Language: en_US\n"
|
||||
@@ -82,47 +82,47 @@ msgid ""
|
||||
"It has been created for users that can't host or\n"
|
||||
"configure a bot, or for use on networks that don't\n"
|
||||
"allow user bots. Available commands are listed\n"
|
||||
"below; to use them, type %s%s command. For\n"
|
||||
"below; to use them, type %s command. For\n"
|
||||
"more information on a specific command, type\n"
|
||||
"%s%s %s command.\n"
|
||||
"%s %s command.\n"
|
||||
msgstr ""
|
||||
"%s allows you to have a bot on your own channel.\n"
|
||||
"It has been created for users that can't host or\n"
|
||||
"configure a bot, or for use on networks that don't\n"
|
||||
"allow user bots. Available commands are listed\n"
|
||||
"below; to use them, type %s%s command. For\n"
|
||||
"below; to use them, type %s command. For\n"
|
||||
"more information on a specific command, type\n"
|
||||
"%s%s %s command.\n"
|
||||
"%s %s command.\n"
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"%s allows you to register a nickname and\n"
|
||||
"prevent others from using it. The following\n"
|
||||
"commands allow for registration and maintenance of\n"
|
||||
"nicknames; to use them, type %s%s command.\n"
|
||||
"nicknames; to use them, type %s command.\n"
|
||||
"For more information on a specific command, type\n"
|
||||
"%s%s %s command.\n"
|
||||
"%s %s command.\n"
|
||||
msgstr ""
|
||||
"%s allows you to register a nickname and\n"
|
||||
"prevent others from using it. The following\n"
|
||||
"commands allow for registration and maintenance of\n"
|
||||
"nicknames; to use them, type %s%s command.\n"
|
||||
"nicknames; to use them, type %s command.\n"
|
||||
"For more information on a specific command, type\n"
|
||||
"%s%s %s command.\n"
|
||||
"%s %s command.\n"
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"%s allows you to register an account.\n"
|
||||
"The following commands allow for registration and maintenance of\n"
|
||||
"accounts; to use them, type %s%s command.\n"
|
||||
"accounts; to use them, type %s command.\n"
|
||||
"For more information on a specific command, type\n"
|
||||
"%s%s %s command.\n"
|
||||
"%s %s command.\n"
|
||||
msgstr ""
|
||||
"%s allows you to register an account.\n"
|
||||
"The following commands allow for registration and maintenance of\n"
|
||||
"accounts; to use them, type %s%s command.\n"
|
||||
"accounts; to use them, type %s command.\n"
|
||||
"For more information on a specific command, type\n"
|
||||
"%s%s %s command.\n"
|
||||
"%s %s command.\n"
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
@@ -131,16 +131,16 @@ msgid ""
|
||||
"malicious users from \"taking over\" channels by limiting\n"
|
||||
"who is allowed channel operator privileges. Available\n"
|
||||
"commands are listed below; to use them, type\n"
|
||||
"%s%s command. For more information on a\n"
|
||||
"specific command, type %s%s HELP command.\n"
|
||||
"%s command. For more information on a\n"
|
||||
"specific command, type %s HELP command.\n"
|
||||
msgstr ""
|
||||
"%s allows you to register and control various\n"
|
||||
"aspects of channels. %s can often prevent\n"
|
||||
"malicious users from \"taking over\" channels by limiting\n"
|
||||
"who is allowed channel operator privileges. Available\n"
|
||||
"commands are listed below; to use them, type\n"
|
||||
"%s%s command. For more information on a\n"
|
||||
"specific command, type %s%s HELP command.\n"
|
||||
"%s command. For more information on a\n"
|
||||
"specific command, type %s HELP command.\n"
|
||||
|
||||
#, c-format
|
||||
msgid "%s already exists in %s bad words list."
|
||||
@@ -387,8 +387,8 @@ msgid "%s will now permanently be ignored."
|
||||
msgstr "%s will now permanently be ignored."
|
||||
|
||||
#, c-format
|
||||
msgid "%s%s HELP %s for more information."
|
||||
msgstr "%s%s HELP %s for more information."
|
||||
msgid "%s HELP %s for more information."
|
||||
msgstr "%s HELP %s for more information."
|
||||
|
||||
msgid "ADD nick user host real"
|
||||
msgstr "ADD nick user host real"
|
||||
@@ -458,11 +458,11 @@ msgstr ""
|
||||
#, c-format
|
||||
msgid ""
|
||||
"User access levels can be seen by using the\n"
|
||||
"%s command; type %s%s HELP LEVELS for\n"
|
||||
"%s command; type %s HELP LEVELS for\n"
|
||||
"information."
|
||||
msgstr ""
|
||||
"User access levels can be seen by using the\n"
|
||||
"%s command; type %s%s HELP LEVELS for\n"
|
||||
"%s command; type %s HELP LEVELS for\n"
|
||||
"information."
|
||||
|
||||
#, c-format
|
||||
@@ -947,12 +947,12 @@ msgstr ""
|
||||
#, c-format
|
||||
msgid ""
|
||||
" \n"
|
||||
"See the %s command (%s%s HELP ACCESS) for\n"
|
||||
"See the %s command (%s HELP ACCESS) for\n"
|
||||
"information on giving a subset of these privileges to\n"
|
||||
"other channel users.\n"
|
||||
msgstr ""
|
||||
" \n"
|
||||
"See the %s command (%s%s HELP ACCESS) for\n"
|
||||
"See the %s command (%s HELP ACCESS) for\n"
|
||||
"information on giving a subset of these privileges to\n"
|
||||
"other channel users.\n"
|
||||
|
||||
@@ -1219,11 +1219,11 @@ msgstr ""
|
||||
#, c-format
|
||||
msgid ""
|
||||
" \n"
|
||||
"Type %s%s HELP command for help on any of the\n"
|
||||
"Type %s HELP command for help on any of the\n"
|
||||
"above commands."
|
||||
msgstr ""
|
||||
" \n"
|
||||
"Type %s%s HELP command for help on any of the\n"
|
||||
"Type %s HELP command for help on any of the\n"
|
||||
"above commands."
|
||||
|
||||
#, c-format
|
||||
@@ -1249,10 +1249,6 @@ msgstr " Loaded at: %p"
|
||||
msgid " but %s mysteriously dematerialized."
|
||||
msgstr " but %s mysteriously dematerialized."
|
||||
|
||||
#, c-format
|
||||
msgid "\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead."
|
||||
msgstr "\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead."
|
||||
|
||||
msgid "\"Jupiter\" a server"
|
||||
msgstr "\"Jupiter\" a server"
|
||||
|
||||
@@ -4790,7 +4786,7 @@ msgid ""
|
||||
"Maintains the bad words list for a channel. The bad\n"
|
||||
"words list determines which words are to be kicked\n"
|
||||
"when the bad words kicker is enabled. For more information,\n"
|
||||
"type %s%s HELP KICK %s.\n"
|
||||
"type %s HELP KICK %s.\n"
|
||||
" \n"
|
||||
"The ADD command adds the given word to the\n"
|
||||
"bad words list. If SINGLE is specified, a kick will be\n"
|
||||
@@ -4805,7 +4801,7 @@ msgstr ""
|
||||
"Maintains the bad words list for a channel. The bad\n"
|
||||
"words list determines which words are to be kicked\n"
|
||||
"when the bad words kicker is enabled. For more information,\n"
|
||||
"type %s%s HELP KICK %s.\n"
|
||||
"type %s HELP KICK %s.\n"
|
||||
" \n"
|
||||
"The ADD command adds the given word to the\n"
|
||||
"bad words list. If SINGLE is specified, a kick will be\n"
|
||||
@@ -5414,8 +5410,8 @@ msgid "Persistent"
|
||||
msgstr "Persistent"
|
||||
|
||||
#, c-format
|
||||
msgid "Please confirm that you want to drop %s with %s%s DROP %s %s"
|
||||
msgstr "Please confirm that you want to drop %s with %s%s DROP %s %s"
|
||||
msgid "Please confirm that you want to drop %s with %s DROP %s %s"
|
||||
msgstr "Please confirm that you want to drop %s with %s DROP %s %s"
|
||||
|
||||
msgid "Please contact an Operator to get a vhost assigned to this nick."
|
||||
msgstr "Please contact an Operator to get a vhost assigned to this nick."
|
||||
@@ -5911,18 +5907,18 @@ msgstr "Secureops enforced on %s."
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"See %s%s HELP %s for more information\n"
|
||||
"See %s HELP %s for more information\n"
|
||||
"about the access list."
|
||||
msgstr ""
|
||||
"See %s%s HELP %s for more information\n"
|
||||
"See %s HELP %s for more information\n"
|
||||
"about the access list."
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"See %s%s HELP %s for more information\n"
|
||||
"See %s HELP %s for more information\n"
|
||||
"about the flags system."
|
||||
msgstr ""
|
||||
"See %s%s HELP %s for more information\n"
|
||||
"See %s HELP %s for more information\n"
|
||||
"about the flags system."
|
||||
|
||||
msgid "Send a memo to a nick or channel"
|
||||
@@ -6236,7 +6232,7 @@ msgid ""
|
||||
"option tells the bot to kick users who say certain words\n"
|
||||
"on the channels.\n"
|
||||
"You can define bad words for your channel using the\n"
|
||||
"BADWORDS command. Type %s%s HELP BADWORDS for\n"
|
||||
"BADWORDS command. Type %s HELP BADWORDS for\n"
|
||||
"more information.\n"
|
||||
" \n"
|
||||
"ttb is the number of times a user can be kicked\n"
|
||||
@@ -6247,7 +6243,7 @@ msgstr ""
|
||||
"option tells the bot to kick users who say certain words\n"
|
||||
"on the channels.\n"
|
||||
"You can define bad words for your channel using the\n"
|
||||
"BADWORDS command. Type %s%s HELP BADWORDS for\n"
|
||||
"BADWORDS command. Type %s HELP BADWORDS for\n"
|
||||
"more information.\n"
|
||||
" \n"
|
||||
"ttb is the number of times a user can be kicked\n"
|
||||
@@ -6473,7 +6469,7 @@ msgid ""
|
||||
" LIMIT Sets the maximum number of memos you can\n"
|
||||
" receive\n"
|
||||
" \n"
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option."
|
||||
msgstr ""
|
||||
"Sets various memo options. option can be one of:\n"
|
||||
@@ -6483,7 +6479,7 @@ msgstr ""
|
||||
" LIMIT Sets the maximum number of memos you can\n"
|
||||
" receive\n"
|
||||
" \n"
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option."
|
||||
|
||||
msgid "Sets various nickname options. option can be one of:"
|
||||
@@ -6539,8 +6535,8 @@ msgstr ""
|
||||
"may not get set automatically."
|
||||
|
||||
#, c-format
|
||||
msgid "Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings."
|
||||
msgstr "Setting %s not known. Type %s%s HELP LEVELS for a list of valid settings."
|
||||
msgid "Setting %s not known. Type %s HELP LEVELS for a list of valid settings."
|
||||
msgstr "Setting %s not known. Type %s HELP LEVELS for a list of valid settings."
|
||||
|
||||
msgid "Setting for DEBUG must be ON, OFF, or a positive number."
|
||||
msgstr "Setting for DEBUG must be ON, OFF, or a positive number."
|
||||
@@ -7450,10 +7446,10 @@ msgstr "There is %zu memo on channel %s."
|
||||
#, c-format
|
||||
msgid ""
|
||||
"There is a new memo on channel %s.\n"
|
||||
"Type %s%s READ %s %zu to read it."
|
||||
"Type %s READ %s %zu to read it."
|
||||
msgstr ""
|
||||
"There is a new memo on channel %s.\n"
|
||||
"Type %s%s READ %s %zu to read it."
|
||||
"Type %s READ %s %zu to read it."
|
||||
|
||||
#, c-format
|
||||
msgid "There is no bot assigned to %s anymore."
|
||||
@@ -7750,20 +7746,20 @@ msgstr "This nickname is suspended."
|
||||
#, c-format
|
||||
msgid ""
|
||||
"This nickname is registered and protected. If it is your\n"
|
||||
"nick, type %s%s IDENTIFY password. Otherwise,\n"
|
||||
"nick, type %s IDENTIFY password. Otherwise,\n"
|
||||
"please choose a different nick."
|
||||
msgstr ""
|
||||
"This nickname is registered and protected. If it is your\n"
|
||||
"nick, type %s%s IDENTIFY password. Otherwise,\n"
|
||||
"nick, type %s IDENTIFY password. Otherwise,\n"
|
||||
"please choose a different nick."
|
||||
|
||||
#, c-format
|
||||
msgid "To delete, type: %s%s %s %d"
|
||||
msgstr "To delete, type: %s%s %s %d"
|
||||
msgid "To delete, type: %s %s %d"
|
||||
msgstr "To delete, type: %s %s %d"
|
||||
|
||||
#, c-format
|
||||
msgid "To delete, type: %s%s %s %s %d"
|
||||
msgstr "To delete, type: %s%s %s %s %d"
|
||||
msgid "To delete, type: %s %s %s %d"
|
||||
msgstr "To delete, type: %s %s %s %d"
|
||||
|
||||
msgid "To protect ops against bot kicks"
|
||||
msgstr "To protect ops against bot kicks"
|
||||
@@ -7918,21 +7914,21 @@ msgstr "Type"
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option."
|
||||
msgstr ""
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option."
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option.\n"
|
||||
" \n"
|
||||
"Note: access to this command is controlled by the\n"
|
||||
"level SET."
|
||||
msgstr ""
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option.\n"
|
||||
" \n"
|
||||
"Note: access to this command is controlled by the\n"
|
||||
@@ -7940,25 +7936,25 @@ msgstr ""
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option. The options will be set on the given\n"
|
||||
"nickname."
|
||||
msgstr ""
|
||||
"Type %s%s HELP %s option for more information\n"
|
||||
"Type %s HELP %s option for more information\n"
|
||||
"on a specific option. The options will be set on the given\n"
|
||||
"nickname."
|
||||
|
||||
#, c-format
|
||||
msgid ""
|
||||
"Type %s%s HELP %s option for more information on a\n"
|
||||
"Type %s HELP %s option for more information on a\n"
|
||||
"particular option."
|
||||
msgstr ""
|
||||
"Type %s%s HELP %s option for more information on a\n"
|
||||
"Type %s HELP %s option for more information on a\n"
|
||||
"particular option."
|
||||
|
||||
#, c-format
|
||||
msgid "Type %s%s SET EMAIL email in order to set your email."
|
||||
msgstr "Type %s%s SET EMAIL email in order to set your email."
|
||||
msgid "Type %s SET EMAIL email in order to set your email."
|
||||
msgstr "Type %s SET EMAIL email in order to set your email."
|
||||
|
||||
msgid "Un-Load a module"
|
||||
msgstr "Un-Load a module"
|
||||
@@ -8006,16 +8002,16 @@ msgid "Unknown command %s."
|
||||
msgstr "Unknown command %s."
|
||||
|
||||
#, c-format
|
||||
msgid "Unknown command %s. \"%s%s HELP\" for help."
|
||||
msgstr "Unknown command %s. \"%s%s HELP\" for help."
|
||||
msgid "Unknown command %s. \"%s HELP\" for help."
|
||||
msgstr "Unknown command %s. \"%s HELP\" for help."
|
||||
|
||||
#, c-format
|
||||
msgid "Unknown command %s. Did you mean %s?"
|
||||
msgstr "Unknown command %s. Did you mean %s?"
|
||||
|
||||
#, c-format
|
||||
msgid "Unknown command %s. Did you mean %s? \"%s%s HELP\" for help."
|
||||
msgstr "Unknown command %s. Did you mean %s? \"%s%s HELP\" for help."
|
||||
msgid "Unknown command %s. Did you mean %s? \"%s HELP\" for help."
|
||||
msgstr "Unknown command %s. Did you mean %s? \"%s HELP\" for help."
|
||||
|
||||
#, c-format
|
||||
msgid "Unknown mode character %c ignored."
|
||||
@@ -8360,10 +8356,6 @@ msgstr "You can't add a channel to its own access list."
|
||||
msgid "You can't logout %s, they are a Services Operator."
|
||||
msgstr "You can't logout %s, they are a Services Operator."
|
||||
|
||||
#, c-format
|
||||
msgid "You cannot %s on this network."
|
||||
msgstr "You cannot %s on this network."
|
||||
|
||||
#, c-format
|
||||
msgid "You cannot set the %c flag."
|
||||
msgstr "You cannot set the %c flag."
|
||||
@@ -8438,10 +8430,10 @@ msgstr "You have 1 new memo."
|
||||
#, c-format
|
||||
msgid ""
|
||||
"You have a new memo from %s.\n"
|
||||
"Type %s%s READ %zu to read it."
|
||||
"Type %s READ %zu to read it."
|
||||
msgstr ""
|
||||
"You have a new memo from %s.\n"
|
||||
"Type %s%s READ %zu to read it."
|
||||
"Type %s READ %zu to read it."
|
||||
|
||||
#, c-format
|
||||
msgid "You have been invited to %s by %s."
|
||||
@@ -8603,6 +8595,10 @@ msgstr "Your IRCd does not support SVSPART."
|
||||
msgid "Your IRCd does not support vidents. If this is incorrect please report this as a possible bug."
|
||||
msgstr "Your IRCd does not support vidents. If this is incorrect please report this as a possible bug."
|
||||
|
||||
#, c-format
|
||||
msgid "Your SSL certificate fingerprint %s has been automatically added to your certificate list."
|
||||
msgstr "Your SSL certificate fingerprint %s has been automatically added to your certificate list."
|
||||
|
||||
#, c-format
|
||||
msgid "Your account %s has been successfully created."
|
||||
msgstr "Your account %s has been successfully created."
|
||||
@@ -8909,3 +8905,15 @@ msgstr "{nick | channel}"
|
||||
|
||||
msgid "{nick | channel} memo-text"
|
||||
msgstr "{nick | channel} memo-text"
|
||||
|
||||
#, c-format
|
||||
#~ msgid "\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead."
|
||||
#~ msgstr "\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead."
|
||||
|
||||
#, c-format
|
||||
#~ msgid "To delete, type: %s%s %s %s %d"
|
||||
#~ msgstr "To delete, type: %s%s %s %s %d"
|
||||
|
||||
#, c-format
|
||||
#~ msgid "You cannot %s on this network."
|
||||
#~ msgstr "You cannot %s on this network."
|
||||
|
||||
@@ -153,11 +153,11 @@ public:
|
||||
"It has been created for users that can't host or\n"
|
||||
"configure a bot, or for use on networks that don't\n"
|
||||
"allow user bots. Available commands are listed\n"
|
||||
"below; to use them, type \002%s%s \037command\037\002. For\n"
|
||||
"below; to use them, type \002%s \037command\037\002. For\n"
|
||||
"more information on a specific command, type\n"
|
||||
"\002%s%s %s \037command\037\002.\n"),
|
||||
BotServ->nick.c_str(), Config->StrictPrivmsg.c_str(), BotServ->nick.c_str(),
|
||||
Config->StrictPrivmsg.c_str(), BotServ->nick.c_str(), source.command.c_str());
|
||||
"\002%s %s \037command\037\002.\n"),
|
||||
BotServ->nick.c_str(), BotServ->GetQueryCommand().c_str(),
|
||||
BotServ->GetQueryCommand().c_str(), source.command.c_str());
|
||||
}
|
||||
|
||||
return EVENT_CONTINUE;
|
||||
|
||||
@@ -430,7 +430,7 @@ public:
|
||||
source.Reply(_("Maintains the \002bad words list\002 for a channel. The bad\n"
|
||||
"words list determines which words are to be kicked\n"
|
||||
"when the bad words kicker is enabled. For more information,\n"
|
||||
"type \002%s%s HELP KICK %s\002.\n"
|
||||
"type \002%s HELP KICK %s\002.\n"
|
||||
" \n"
|
||||
"The \002ADD\002 command adds the given word to the\n"
|
||||
"bad words list. If SINGLE is specified, a kick will be\n"
|
||||
@@ -440,7 +440,7 @@ public:
|
||||
"will be done if a user says a word that ends with\n"
|
||||
"\037word\037. If you don't specify anything, a kick will\n"
|
||||
"be issued every time \037word\037 is said by a user.\n"
|
||||
" \n"), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str());
|
||||
" \n"), source.service->GetQueryCommand().c_str(), source.command.c_str());
|
||||
source.Reply(_("The \002DEL\002 command removes the given word from the\n"
|
||||
"bad words list. If a list of entry numbers is given, those\n"
|
||||
"entries are deleted. (See the example for LIST below.)\n"
|
||||
|
||||
@@ -153,11 +153,11 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n"
|
||||
source.Reply(_("Type \002%s HELP %s \037option\037\002 for more information\n"
|
||||
"on a specific option.\n"
|
||||
" \n"
|
||||
"Note: access to this command is controlled by the\n"
|
||||
"level SET."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str());
|
||||
"level SET."), source.service->GetQueryCommand().c_str(), this_name.c_str());
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -308,12 +308,12 @@ public:
|
||||
"option tells the bot to kick users who say certain words\n"
|
||||
"on the channels.\n"
|
||||
"You can define bad words for your channel using the\n"
|
||||
"\002BADWORDS\002 command. Type \002%s%s HELP BADWORDS\002 for\n"
|
||||
"\002BADWORDS\002 command. Type \002%s HELP BADWORDS\002 for\n"
|
||||
"more information.\n"
|
||||
" \n"
|
||||
"\037ttb\037 is the number of times a user can be kicked\n"
|
||||
"before it gets banned. Don't give ttb to disable\n"
|
||||
"the ban system once activated."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str());
|
||||
"the ban system once activated."), source.service->GetQueryCommand().c_str());
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
@@ -58,8 +58,8 @@ public:
|
||||
}
|
||||
}
|
||||
}
|
||||
source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information on a\n"
|
||||
"particular option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str());
|
||||
source.Reply(_("Type \002%s HELP %s \037option\037\002 for more information on a\n"
|
||||
"particular option."), source.service->GetQueryCommand().c_str(), this_name.c_str());
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -262,9 +262,9 @@ public:
|
||||
"malicious users from \"taking over\" channels by limiting\n"
|
||||
"who is allowed channel operator privileges. Available\n"
|
||||
"commands are listed below; to use them, type\n"
|
||||
"\002%s%s \037command\037\002. For more information on a\n"
|
||||
"specific command, type \002%s%s HELP \037command\037\002.\n"),
|
||||
ChanServ->nick.c_str(), ChanServ->nick.c_str(), Config->StrictPrivmsg.c_str(), ChanServ->nick.c_str(), Config->StrictPrivmsg.c_str(), ChanServ->nick.c_str());
|
||||
"\002%s \037command\037\002. For more information on a\n"
|
||||
"specific command, type \002%s HELP \037command\037\002.\n"),
|
||||
ChanServ->nick.c_str(), ChanServ->nick.c_str(), ChanServ->GetQueryCommand().c_str(), ChanServ->GetQueryCommand().c_str());
|
||||
return EVENT_CONTINUE;
|
||||
}
|
||||
|
||||
@@ -382,8 +382,11 @@ public:
|
||||
return EVENT_CONTINUE;
|
||||
}
|
||||
|
||||
void OnPostInit() override
|
||||
void OnUplinkSync(Server* s) override
|
||||
{
|
||||
// We need to do this when the uplink is synced as we may not know if
|
||||
// the mode exists before then on some IRCds (e.g. InspIRCd).
|
||||
|
||||
if (!persist)
|
||||
return;
|
||||
|
||||
|
||||
@@ -87,6 +87,7 @@ class CommandCSAccess final
|
||||
void DoAdd(CommandSource &source, ChannelInfo *ci, const std::vector<Anope::string> ¶ms)
|
||||
{
|
||||
Anope::string mask = params[2];
|
||||
Anope::string description = params.size() > 4 ? params[4] : "";
|
||||
Privilege *p = NULL;
|
||||
int level = ACCESS_INVALID;
|
||||
|
||||
@@ -172,7 +173,11 @@ class CommandCSAccess final
|
||||
{
|
||||
User *targ = User::Find(mask, true);
|
||||
if (targ != NULL)
|
||||
{
|
||||
mask = "*!*@" + targ->GetDisplayedHost();
|
||||
if (description.empty())
|
||||
description = targ->nick;
|
||||
}
|
||||
else
|
||||
{
|
||||
source.Reply(NICK_X_NOT_REGISTERED, mask.c_str());
|
||||
@@ -216,7 +221,7 @@ class CommandCSAccess final
|
||||
access->level = level;
|
||||
access->last_seen = 0;
|
||||
access->created = Anope::CurTime;
|
||||
access->description = params.size() > 4 ? params[4] : "";
|
||||
access->description = description;
|
||||
ci->AddAccess(access);
|
||||
|
||||
FOREACH_MOD(OnAccessAdd, (ci, source, access));
|
||||
@@ -625,8 +630,8 @@ public:
|
||||
Anope::string cmd;
|
||||
if (Command::FindCommandFromService("chanserv/levels", bi, cmd))
|
||||
source.Reply(_("\002User access levels\002 can be seen by using the\n"
|
||||
"\002%s\002 command; type \002%s%s HELP LEVELS\002 for\n"
|
||||
"information."), cmd.c_str(), Config->StrictPrivmsg.c_str(), bi->nick.c_str());
|
||||
"\002%s\002 command; type \002%s HELP LEVELS\002 for\n"
|
||||
"information."), cmd.c_str(), bi->GetQueryCommand().c_str());
|
||||
return true;
|
||||
}
|
||||
};
|
||||
@@ -660,7 +665,10 @@ class CommandCSLevels final
|
||||
{
|
||||
Privilege *p = PrivilegeManager::FindPrivilege(what);
|
||||
if (p == NULL)
|
||||
source.Reply(_("Setting \002%s\002 not known. Type \002%s%s HELP LEVELS\002 for a list of valid settings."), what.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str());
|
||||
{
|
||||
source.Reply(_("Setting \002%s\002 not known. Type \002%s HELP LEVELS\002 for a list of valid settings."),
|
||||
what.c_str(), source.service->GetQueryCommand().c_str());
|
||||
}
|
||||
else
|
||||
{
|
||||
bool override = !source.AccessFor(ci).HasPriv("FOUNDER");
|
||||
@@ -701,7 +709,8 @@ class CommandCSLevels final
|
||||
return;
|
||||
}
|
||||
|
||||
source.Reply(_("Setting \002%s\002 not known. Type \002%s%s HELP LEVELS\002 for a list of valid settings."), what.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str());
|
||||
source.Reply(_("Setting \002%s\002 not known. Type \002%s HELP LEVELS\002 for a list of valid settings."),
|
||||
what.c_str(), source.service->GetQueryCommand().c_str());
|
||||
}
|
||||
|
||||
static void DoList(CommandSource &source, ChannelInfo *ci)
|
||||
|
||||
@@ -58,8 +58,8 @@ public:
|
||||
*code = Anope::Random(15);
|
||||
}
|
||||
|
||||
source.Reply(CONFIRM_DROP, ci->name.c_str(), Config->StrictPrivmsg.c_str(),
|
||||
source.service->nick.c_str(), ci->name.c_str(), code->c_str());
|
||||
source.Reply(CONFIRM_DROP, ci->name.c_str(), source.service->GetQueryCommand().c_str(),
|
||||
ci->name.c_str(), code->c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
@@ -79,7 +79,7 @@ FlagsAccessProvider *FlagsAccessProvider::ap;
|
||||
class CommandCSFlags final
|
||||
: public Command
|
||||
{
|
||||
void DoModify(CommandSource &source, ChannelInfo *ci, Anope::string mask, const Anope::string &flags, const Anope::string &description)
|
||||
void DoModify(CommandSource &source, ChannelInfo *ci, Anope::string mask, const Anope::string &flags, Anope::string description)
|
||||
{
|
||||
if (flags.empty())
|
||||
{
|
||||
@@ -131,7 +131,11 @@ class CommandCSFlags final
|
||||
{
|
||||
User *targ = User::Find(mask, true);
|
||||
if (targ != NULL)
|
||||
{
|
||||
mask = "*!*@" + targ->GetDisplayedHost();
|
||||
if (description.empty())
|
||||
description = targ->nick;
|
||||
}
|
||||
else
|
||||
{
|
||||
source.Reply(NICK_X_NOT_REGISTERED, mask.c_str());
|
||||
|
||||
@@ -100,9 +100,9 @@ public:
|
||||
Anope::string cmd;
|
||||
if (Command::FindCommandFromService("chanserv/access", bi, cmd))
|
||||
source.Reply(_(" \n"
|
||||
"See the \002%s\002 command (\002%s%s HELP ACCESS\002) for\n"
|
||||
"See the \002%s\002 command (\002%s HELP ACCESS\002) for\n"
|
||||
"information on giving a subset of these privileges to\n"
|
||||
"other channel users.\n"), cmd.c_str(), Config->StrictPrivmsg.c_str(), bi->nick.c_str());
|
||||
"other channel users.\n"), cmd.c_str(), bi->GetQueryCommand().c_str());
|
||||
source.Reply(_(" \n"
|
||||
"NOTICE: In order to register a channel, you must have\n"
|
||||
"first registered your nickname."));
|
||||
|
||||
@@ -59,8 +59,8 @@ public:
|
||||
c->OnServHelp(source);
|
||||
}
|
||||
}
|
||||
source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information on a\n"
|
||||
"particular option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str());
|
||||
source.Reply(_("Type \002%s HELP %s \037option\037\002 for more information on a\n"
|
||||
"particular option."), source.service->GetQueryCommand().c_str(), this_name.c_str());
|
||||
return true;
|
||||
}
|
||||
};
|
||||
@@ -513,12 +513,13 @@ public:
|
||||
/* Set the perm mode */
|
||||
if (cm)
|
||||
{
|
||||
if (ci->c && !ci->c->HasMode("PERM"))
|
||||
ci->c->SetMode(NULL, cm);
|
||||
/* Add it to the channels mlock */
|
||||
ModeLocks *ml = ci->Require<ModeLocks>("modelocks");
|
||||
if (ml)
|
||||
ml->SetMLock(cm, true, "", source.GetNick());
|
||||
|
||||
if (ci->c && !ci->c->HasMode("PERM"))
|
||||
ci->c->SetMode(NULL, cm);
|
||||
}
|
||||
/* No botserv bot, no channel mode, give them ChanServ.
|
||||
* Yes, this works fine with no BotServ.
|
||||
@@ -556,12 +557,13 @@ public:
|
||||
/* Unset perm mode */
|
||||
if (cm)
|
||||
{
|
||||
if (ci->c && ci->c->HasMode("PERM"))
|
||||
ci->c->RemoveMode(NULL, cm);
|
||||
/* Remove from mlock */
|
||||
ModeLocks *ml = ci->GetExt<ModeLocks>("modelocks");
|
||||
if (ml)
|
||||
ml->RemoveMLock(cm, true);
|
||||
|
||||
if (ci->c && ci->c->HasMode("PERM"))
|
||||
ci->c->RemoveMode(NULL, cm);
|
||||
}
|
||||
/* No channel mode, no BotServ, but using ChanServ as the botserv bot
|
||||
* which was assigned when persist was set on
|
||||
|
||||
@@ -11,57 +11,47 @@
|
||||
class StatusUpdate final
|
||||
: public Module
|
||||
{
|
||||
public:
|
||||
StatusUpdate(const Anope::string &modname, const Anope::string &creator) : Module(modname, creator, VENDOR)
|
||||
private:
|
||||
void OnAccessChange(ChannelInfo *ci, ChanAccess *access, bool adding)
|
||||
{
|
||||
if (!ci->c)
|
||||
return;
|
||||
|
||||
for (const auto &[_, uc] : ci->c->users)
|
||||
{
|
||||
auto *user = uc->user;
|
||||
|
||||
ChannelInfo *next;
|
||||
if (user->server != Me && access->Matches(user, user->Account(), next))
|
||||
{
|
||||
auto ag = ci->AccessFor(user);
|
||||
|
||||
for (auto *cms : ModeManager::GetStatusChannelModesByRank())
|
||||
{
|
||||
if (!ag.HasPriv("AUTO" + cms->name))
|
||||
ci->c->RemoveMode(NULL, cms, user->GetUID());
|
||||
}
|
||||
|
||||
if (adding)
|
||||
ci->c->SetCorrectModes(user, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public:
|
||||
StatusUpdate(const Anope::string &modname, const Anope::string &creator)
|
||||
: Module(modname, creator, VENDOR)
|
||||
{
|
||||
}
|
||||
|
||||
void OnAccessAdd(ChannelInfo *ci, CommandSource &, ChanAccess *access) override
|
||||
{
|
||||
if (ci->c)
|
||||
{
|
||||
for (const auto &[_, uc] : ci->c->users)
|
||||
{
|
||||
User *user = uc->user;
|
||||
|
||||
ChannelInfo *next;
|
||||
if (user->server != Me && access->Matches(user, user->Account(), next))
|
||||
{
|
||||
AccessGroup ag = ci->AccessFor(user);
|
||||
|
||||
for (auto *cms : ModeManager::GetStatusChannelModesByRank())
|
||||
{
|
||||
if (!ag.HasPriv("AUTO" + cms->name))
|
||||
ci->c->RemoveMode(NULL, cms, user->GetUID());
|
||||
}
|
||||
ci->c->SetCorrectModes(user, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
OnAccessChange(ci, access, true);
|
||||
}
|
||||
|
||||
void OnAccessDel(ChannelInfo *ci, CommandSource &, ChanAccess *access) override
|
||||
{
|
||||
if (ci->c)
|
||||
{
|
||||
for (const auto &[_, uc] : ci->c->users)
|
||||
{
|
||||
User *user = uc->user;
|
||||
|
||||
ChannelInfo *next;
|
||||
if (user->server != Me && access->Matches(user, user->Account(), next))
|
||||
{
|
||||
AccessGroup ag = ci->AccessFor(user);
|
||||
|
||||
for (auto *cms : ModeManager::GetStatusChannelModesByRank())
|
||||
{
|
||||
if (!ag.HasPriv("AUTO" + cms->name))
|
||||
ci->c->RemoveMode(NULL, cms, user->GetUID());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
OnAccessChange(ci, access, false);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -179,7 +179,11 @@ private:
|
||||
{
|
||||
User *targ = User::Find(mask, true);
|
||||
if (targ != NULL)
|
||||
{
|
||||
mask = "*!*@" + targ->GetDisplayedHost();
|
||||
if (description.empty())
|
||||
description = targ->nick;
|
||||
}
|
||||
else
|
||||
{
|
||||
source.Reply(NICK_X_NOT_REGISTERED, mask.c_str());
|
||||
@@ -590,11 +594,11 @@ public:
|
||||
source.Reply(_("Alternative methods of modifying channel access lists are\n"
|
||||
"available."));
|
||||
if (!access_cmd.empty())
|
||||
source.Reply(_("See \002%s%s HELP %s\002 for more information\n"
|
||||
"about the access list."), Config->StrictPrivmsg.c_str(), access_bi->nick.c_str(), access_cmd.c_str());
|
||||
source.Reply(_("See \002%s HELP %s\002 for more information\n"
|
||||
"about the access list."), access_bi->GetQueryCommand().c_str(), access_cmd.c_str());
|
||||
if (!flags_cmd.empty())
|
||||
source.Reply(_("See \002%s%s HELP %s\002 for more information\n"
|
||||
"about the flags system."), Config->StrictPrivmsg.c_str(), flags_bi->nick.c_str(), flags_cmd.c_str());
|
||||
source.Reply(_("See \002%s HELP %s\002 for more information\n"
|
||||
"about the flags system."), flags_bi->GetQueryCommand().c_str(), flags_cmd.c_str());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -101,7 +101,7 @@ public:
|
||||
if (ci->AccessFor(cu->user).HasPriv("MEMO"))
|
||||
{
|
||||
if (cu->user->Account() && cu->user->Account()->HasExt("MEMO_RECEIVE"))
|
||||
cu->user->SendMessage(MemoServ, MEMO_NEW_X_MEMO_ARRIVED, ci->name.c_str(), Config->StrictPrivmsg.c_str(), MemoServ->nick.c_str(), ci->name.c_str(), mi->memos->size());
|
||||
cu->user->SendMessage(MemoServ, MEMO_NEW_X_MEMO_ARRIVED, ci->name.c_str(), MemoServ->GetQueryCommand().c_str(), ci->name.c_str(), mi->memos->size());
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -116,7 +116,7 @@ public:
|
||||
{
|
||||
User *user = User::Find(na->nick, true);
|
||||
if (user && user->IsIdentified())
|
||||
user->SendMessage(MemoServ, MEMO_NEW_MEMO_ARRIVED, source.c_str(), Config->StrictPrivmsg.c_str(), MemoServ->nick.c_str(), mi->memos->size());
|
||||
user->SendMessage(MemoServ, MEMO_NEW_MEMO_ARRIVED, source.c_str(), MemoServ->GetQueryCommand().c_str(), mi->memos->size());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -229,8 +229,8 @@ public:
|
||||
if (!params.empty() || source.c || source.service != *MemoServ)
|
||||
return;
|
||||
source.Reply(_(" \n"
|
||||
"Type \002%s%s HELP \037command\037\002 for help on any of the\n"
|
||||
"above commands."), Config->StrictPrivmsg.c_str(), MemoServ->nick.c_str());
|
||||
"Type \002%s HELP \037command\037\002 for help on any of the\n"
|
||||
"above commands."), MemoServ->GetQueryCommand().c_str());
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -91,9 +91,9 @@ public:
|
||||
if (Command::FindCommandFromService("memoserv/del", bi, cmd))
|
||||
{
|
||||
if (ci)
|
||||
source.Reply(_("To delete, type: \002%s%s %s %s %d\002"), Config->StrictPrivmsg.c_str(), bi->nick.c_str(), cmd.c_str(), ci->name.c_str(), index + 1);
|
||||
source.Reply(_("To delete, type: \002%s %s %s %d\002"), bi->GetQueryCommand().c_str(), cmd.c_str(), ci->name.c_str(), index + 1);
|
||||
else
|
||||
source.Reply(_("To delete, type: \002%s%s %s %d\002"), Config->StrictPrivmsg.c_str(), bi->nick.c_str(), cmd.c_str(), index + 1);
|
||||
source.Reply(_("To delete, type: \002%s %s %d\002"), bi->GetQueryCommand().c_str(), cmd.c_str(), index + 1);
|
||||
}
|
||||
|
||||
source.Reply("%s", m->text.c_str());
|
||||
|
||||
@@ -232,8 +232,8 @@ public:
|
||||
" LIMIT Sets the maximum number of memos you can\n"
|
||||
" receive\n"
|
||||
" \n"
|
||||
"Type \002%s%s HELP %s \037option\037\002 for more information\n"
|
||||
"on a specific option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str());
|
||||
"Type \002%s HELP %s \037option\037\002 for more information\n"
|
||||
"on a specific option."), source.service->GetQueryCommand().c_str(), source.command.c_str());
|
||||
}
|
||||
else if (subcommand.equals_ci("NOTIFY"))
|
||||
source.Reply(_("Syntax: \002NOTIFY {ON | LOGON | NEW | MAIL | NOMAIL | OFF}\002\n"
|
||||
|
||||
@@ -98,7 +98,7 @@ class NickServRelease final
|
||||
|
||||
public:
|
||||
NickServRelease(Module *me, NickAlias *na, time_t delay)
|
||||
: User(na->nick, Config->GetModule("nickserv")->Get<const Anope::string>("enforceruser", "user"), Config->GetModule("nickserv")->Get<const Anope::string>("enforcerhost", Me->GetName()), "", "", Me, "Services Enforcer", Anope::CurTime, "", IRCD->UID_Retrieve(), NULL)
|
||||
: User(na->nick, Config->GetModule("nickserv")->Get<const Anope::string>("enforceruser", "user"), Config->GetModule("nickserv")->Get<const Anope::string>("enforcerhost", Me->GetName()), "", "", Me, "Services Enforcer", Anope::CurTime, "", {}, IRCD->UID_Retrieve(), NULL)
|
||||
, Timer(me, delay)
|
||||
, nick(na->nick)
|
||||
{
|
||||
@@ -195,7 +195,7 @@ public:
|
||||
|
||||
if (!na->nc->HasExt("KILL_IMMED"))
|
||||
{
|
||||
u->SendMessage(NickServ, NICK_IS_SECURE, Config->StrictPrivmsg.c_str(), NickServ->nick.c_str());
|
||||
u->SendMessage(NickServ, NICK_IS_SECURE, NickServ->GetQueryCommand().c_str());
|
||||
}
|
||||
if (na->nc->HasExt("KILLPROTECT"))
|
||||
{
|
||||
@@ -362,8 +362,8 @@ public:
|
||||
u->SendMessage(NickServ, _("You must now supply an email for your nick.\n"
|
||||
"This email will allow you to retrieve your password in\n"
|
||||
"case you forget it."));
|
||||
u->SendMessage(NickServ, _("Type \002%s%s SET EMAIL \037email\037\002 in order to set your email."),
|
||||
Config->StrictPrivmsg.c_str(), NickServ->nick.c_str());
|
||||
u->SendMessage(NickServ, _("Type \002%s SET EMAIL \037email\037\002 in order to set your email."),
|
||||
NickServ->GetQueryCommand().c_str());
|
||||
}
|
||||
|
||||
for (auto *c : collides)
|
||||
@@ -465,15 +465,15 @@ public:
|
||||
source.Reply(_("\002%s\002 allows you to register a nickname and\n"
|
||||
"prevent others from using it. The following\n"
|
||||
"commands allow for registration and maintenance of\n"
|
||||
"nicknames; to use them, type \002%s%s \037command\037\002.\n"
|
||||
"nicknames; to use them, type \002%s \037command\037\002.\n"
|
||||
"For more information on a specific command, type\n"
|
||||
"\002%s%s %s \037command\037\002.\n"), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), source.command.c_str());
|
||||
"\002%s %s \037command\037\002.\n"), NickServ->nick.c_str(), NickServ->GetQueryCommand().c_str(), NickServ->GetQueryCommand().c_str(), source.command.c_str());
|
||||
else
|
||||
source.Reply(_("\002%s\002 allows you to register an account.\n"
|
||||
"The following commands allow for registration and maintenance of\n"
|
||||
"accounts; to use them, type \002%s%s \037command\037\002.\n"
|
||||
"accounts; to use them, type \002%s \037command\037\002.\n"
|
||||
"For more information on a specific command, type\n"
|
||||
"\002%s%s %s \037command\037\002.\n"), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), Config->StrictPrivmsg.c_str(), NickServ->nick.c_str(), source.command.c_str());
|
||||
"\002%s %s \037command\037\002.\n"), NickServ->nick.c_str(), NickServ->GetQueryCommand().c_str(), NickServ->GetQueryCommand().c_str(), source.command.c_str());
|
||||
return EVENT_CONTINUE;
|
||||
}
|
||||
|
||||
|
||||
@@ -425,6 +425,9 @@ public:
|
||||
|
||||
auto *cl = certs.Require(na->nc);
|
||||
cl->AddCert(u->fingerprint);
|
||||
|
||||
auto *NickServ = Config->GetClient("NickServ");
|
||||
u->SendMessage(NickServ, _("Your SSL certificate fingerprint \002%s\002 has been automatically added to your certificate list."), u->fingerprint.c_str());
|
||||
}
|
||||
|
||||
EventReturn OnNickValidate(User *u, NickAlias *na) override
|
||||
|
||||
@@ -72,8 +72,8 @@ public:
|
||||
*code = Anope::Random(15);
|
||||
}
|
||||
|
||||
source.Reply(CONFIRM_DROP, na->nick.c_str(), Config->StrictPrivmsg.c_str(),
|
||||
source.service->nick.c_str(), na->nick.c_str(), code->c_str());
|
||||
source.Reply(CONFIRM_DROP, na->nick.c_str(), source.service->GetQueryCommand().c_str(),
|
||||
na->nick.c_str(), code->c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
+6
-118
@@ -57,8 +57,8 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n"
|
||||
"on a specific option."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str());
|
||||
source.Reply(_("Type \002%s HELP %s \037option\037\002 for more information\n"
|
||||
"on a specific option."), source.service->GetQueryCommand().c_str(), this_name.c_str());
|
||||
|
||||
return true;
|
||||
}
|
||||
@@ -100,9 +100,9 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
source.Reply(_("Type \002%s%s HELP %s \037option\037\002 for more information\n"
|
||||
source.Reply(_("Type \002%s HELP %s \037option\037\002 for more information\n"
|
||||
"on a specific option. The options will be set on the given\n"
|
||||
"\037nickname\037."), Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), this_name.c_str());
|
||||
"\037nickname\037."), source.service->GetQueryCommand().c_str(), this_name.c_str());
|
||||
return true;
|
||||
}
|
||||
};
|
||||
@@ -892,112 +892,6 @@ public:
|
||||
}
|
||||
};
|
||||
|
||||
class CommandNSSetMessage
|
||||
: public Command
|
||||
{
|
||||
public:
|
||||
CommandNSSetMessage(Module *creator, const Anope::string &sname = "nickserv/set/message", size_t min = 1) : Command(creator, sname, min, min + 1)
|
||||
{
|
||||
this->SetDesc(_("Change the communication method of services"));
|
||||
this->SetSyntax("{ON | OFF}");
|
||||
}
|
||||
|
||||
void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m)
|
||||
{
|
||||
if (Anope::ReadOnly)
|
||||
{
|
||||
source.Reply(READ_ONLY_MODE);
|
||||
return;
|
||||
}
|
||||
|
||||
const NickAlias *na = NickAlias::Find(user);
|
||||
if (!na)
|
||||
{
|
||||
source.Reply(NICK_X_NOT_REGISTERED, user.c_str());
|
||||
return;
|
||||
}
|
||||
NickCore *nc = na->nc;
|
||||
|
||||
if (!Config->GetBlock("options")->Get<bool>("useprivmsg"))
|
||||
{
|
||||
source.Reply(_("You cannot %s on this network."), source.command.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
EventReturn MOD_RESULT;
|
||||
FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param));
|
||||
if (MOD_RESULT == EVENT_STOP)
|
||||
return;
|
||||
|
||||
if (param.equals_ci("ON"))
|
||||
{
|
||||
Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable " << source.command << " for " << nc->display;
|
||||
nc->Extend<bool>("MSG");
|
||||
source.Reply(_("Services will now reply to \002%s\002 with \002messages\002."), nc->display.c_str());
|
||||
}
|
||||
else if (param.equals_ci("OFF"))
|
||||
{
|
||||
Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable " << source.command << " for " << nc->display;
|
||||
nc->Shrink<bool>("MSG");
|
||||
source.Reply(_("Services will now reply to \002%s\002 with \002notices\002."), nc->display.c_str());
|
||||
}
|
||||
else
|
||||
this->OnSyntaxError(source, "MSG");
|
||||
}
|
||||
|
||||
void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) override
|
||||
{
|
||||
this->Run(source, source.nc->display, params[0]);
|
||||
}
|
||||
|
||||
bool OnHelp(CommandSource &source, const Anope::string &) override
|
||||
{
|
||||
Anope::string cmd = source.command;
|
||||
size_t i = cmd.find_last_of(' ');
|
||||
if (i != Anope::string::npos)
|
||||
cmd = cmd.substr(i + 1);
|
||||
|
||||
this->SendSyntax(source);
|
||||
source.Reply(" ");
|
||||
source.Reply(_("Allows you to choose the way services are communicating with\n"
|
||||
"you. With \002%s\002 set, services will use messages, else they'll\n"
|
||||
"use notices."), cmd.upper().c_str());
|
||||
return true;
|
||||
}
|
||||
|
||||
void OnServHelp(CommandSource &source) override
|
||||
{
|
||||
if (Config->GetBlock("options")->Get<bool>("useprivmsg"))
|
||||
Command::OnServHelp(source);
|
||||
}
|
||||
};
|
||||
|
||||
class CommandNSSASetMessage final
|
||||
: public CommandNSSetMessage
|
||||
{
|
||||
public:
|
||||
CommandNSSASetMessage(Module *creator) : CommandNSSetMessage(creator, "nickserv/saset/message", 2)
|
||||
{
|
||||
this->ClearSyntax();
|
||||
this->SetSyntax(_("\037nickname\037 {ON | OFF}"));
|
||||
}
|
||||
|
||||
bool OnHelp(CommandSource &source, const Anope::string &) override
|
||||
{
|
||||
this->SendSyntax(source);
|
||||
source.Reply(" ");
|
||||
source.Reply(_("Allows you to choose the way services are communicating with\n"
|
||||
"the given user. With \002MSG\002 set, services will use messages,\n"
|
||||
"else they'll use notices."));
|
||||
return true;
|
||||
}
|
||||
|
||||
void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) override
|
||||
{
|
||||
this->Run(source, params[0], params[1]);
|
||||
}
|
||||
};
|
||||
|
||||
class CommandNSSASetNoexpire final
|
||||
: public Command
|
||||
{
|
||||
@@ -1075,16 +969,13 @@ class NSSet final
|
||||
CommandNSSetKill commandnssetkill;
|
||||
CommandNSSASetKill commandnssasetkill;
|
||||
|
||||
CommandNSSetMessage commandnssetmessage;
|
||||
CommandNSSASetMessage commandnssasetmessage;
|
||||
|
||||
CommandNSSetPassword commandnssetpassword;
|
||||
CommandNSSASetPassword commandnssasetpassword;
|
||||
|
||||
CommandNSSASetNoexpire commandnssasetnoexpire;
|
||||
|
||||
SerializableExtensibleItem<bool> autoop, neverop, killprotect, kill_quick, kill_immed,
|
||||
message, noexpire;
|
||||
noexpire;
|
||||
|
||||
struct KeepModes final
|
||||
: SerializableExtensibleItem<bool>
|
||||
@@ -1145,13 +1036,12 @@ public:
|
||||
commandnssetemail(this), commandnssasetemail(this),
|
||||
commandnssetkeepmodes(this), commandnssasetkeepmodes(this),
|
||||
commandnssetkill(this), commandnssasetkill(this),
|
||||
commandnssetmessage(this), commandnssasetmessage(this),
|
||||
commandnssetpassword(this), commandnssasetpassword(this),
|
||||
commandnssasetnoexpire(this),
|
||||
|
||||
autoop(this, "AUTOOP"), neverop(this, "NEVEROP"),
|
||||
killprotect(this, "KILLPROTECT"), kill_quick(this, "KILL_QUICK"),
|
||||
kill_immed(this, "KILL_IMMED"), message(this, "MSG"),
|
||||
kill_immed(this, "KILL_IMMED"),
|
||||
noexpire(this, "NS_NO_EXPIRE"),
|
||||
|
||||
keep_modes(this, "NS_KEEP_MODES"), ns_set_email(this, "ns_set_email")
|
||||
@@ -1208,8 +1098,6 @@ public:
|
||||
info.AddOption(_("Quick protection"));
|
||||
else if (killprotect.HasExt(na->nc))
|
||||
info.AddOption(_("Protection"));
|
||||
if (message.HasExt(na->nc))
|
||||
info.AddOption(_("Message mode"));
|
||||
if (autoop.HasExt(na->nc))
|
||||
info.AddOption(_("Auto-op"));
|
||||
if (neverop.HasExt(na->nc))
|
||||
|
||||
@@ -0,0 +1,137 @@
|
||||
/* NickServ core functions
|
||||
*
|
||||
* (C) 2003-2024 Anope Team
|
||||
* Contact us at team@anope.org
|
||||
*
|
||||
* Please read COPYING and README for further details.
|
||||
*
|
||||
* Based on the original code of Epona by Lara.
|
||||
* Based on the original code of Services by Andy Church.
|
||||
*/
|
||||
|
||||
#include "module.h"
|
||||
|
||||
class CommandNSSetMessage
|
||||
: public Command
|
||||
{
|
||||
public:
|
||||
CommandNSSetMessage(Module *creator, const Anope::string &sname = "nickserv/set/message", size_t min = 1)
|
||||
: Command(creator, sname, min, min + 1)
|
||||
{
|
||||
this->SetDesc(_("Change the communication method of services"));
|
||||
this->SetSyntax("{ON | OFF}");
|
||||
}
|
||||
|
||||
void Run(CommandSource &source, const Anope::string &user, const Anope::string ¶m)
|
||||
{
|
||||
if (Anope::ReadOnly)
|
||||
{
|
||||
source.Reply(READ_ONLY_MODE);
|
||||
return;
|
||||
}
|
||||
|
||||
const NickAlias *na = NickAlias::Find(user);
|
||||
if (!na)
|
||||
{
|
||||
source.Reply(NICK_X_NOT_REGISTERED, user.c_str());
|
||||
return;
|
||||
}
|
||||
NickCore *nc = na->nc;
|
||||
|
||||
|
||||
EventReturn MOD_RESULT;
|
||||
FOREACH_RESULT(OnSetNickOption, MOD_RESULT, (source, this, nc, param));
|
||||
if (MOD_RESULT == EVENT_STOP)
|
||||
return;
|
||||
|
||||
if (param.equals_ci("ON"))
|
||||
{
|
||||
Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to enable " << source.command << " for " << nc->display;
|
||||
nc->Extend<bool>("MSG");
|
||||
source.Reply(_("Services will now reply to \002%s\002 with \002messages\002."), nc->display.c_str());
|
||||
}
|
||||
else if (param.equals_ci("OFF"))
|
||||
{
|
||||
Log(nc == source.GetAccount() ? LOG_COMMAND : LOG_ADMIN, source, this) << "to disable " << source.command << " for " << nc->display;
|
||||
nc->Shrink<bool>("MSG");
|
||||
source.Reply(_("Services will now reply to \002%s\002 with \002notices\002."), nc->display.c_str());
|
||||
}
|
||||
else
|
||||
this->OnSyntaxError(source, "MSG");
|
||||
}
|
||||
|
||||
void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) override
|
||||
{
|
||||
this->Run(source, source.nc->display, params[0]);
|
||||
}
|
||||
|
||||
bool OnHelp(CommandSource &source, const Anope::string &) override
|
||||
{
|
||||
Anope::string cmd = source.command;
|
||||
size_t i = cmd.find_last_of(' ');
|
||||
if (i != Anope::string::npos)
|
||||
cmd = cmd.substr(i + 1);
|
||||
|
||||
this->SendSyntax(source);
|
||||
source.Reply(" ");
|
||||
source.Reply(_("Allows you to choose the way services are communicating with\n"
|
||||
"you. With \002%s\002 set, services will use messages, else they'll\n"
|
||||
"use notices."), cmd.upper().c_str());
|
||||
return true;
|
||||
}
|
||||
};
|
||||
|
||||
class CommandNSSASetMessage final
|
||||
: public CommandNSSetMessage
|
||||
{
|
||||
public:
|
||||
CommandNSSASetMessage(Module *creator) : CommandNSSetMessage(creator, "nickserv/saset/message", 2)
|
||||
{
|
||||
this->ClearSyntax();
|
||||
this->SetSyntax(_("\037nickname\037 {ON | OFF}"));
|
||||
}
|
||||
|
||||
bool OnHelp(CommandSource &source, const Anope::string &) override
|
||||
{
|
||||
this->SendSyntax(source);
|
||||
source.Reply(" ");
|
||||
source.Reply(_("Allows you to choose the way services are communicating with\n"
|
||||
"the given user. With \002MSG\002 set, services will use messages,\n"
|
||||
"else they'll use notices."));
|
||||
return true;
|
||||
}
|
||||
|
||||
void Execute(CommandSource &source, const std::vector<Anope::string> ¶ms) override
|
||||
{
|
||||
this->Run(source, params[0], params[1]);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
class NSSetMessage final
|
||||
: public Module
|
||||
{
|
||||
private:
|
||||
CommandNSSetMessage commandnssetmessage;
|
||||
CommandNSSASetMessage commandnssasetmessage;
|
||||
SerializableExtensibleItem<bool> message;
|
||||
|
||||
public:
|
||||
NSSetMessage(const Anope::string &modname, const Anope::string &creator)
|
||||
: Module(modname, creator, VENDOR)
|
||||
, commandnssetmessage(this)
|
||||
, commandnssasetmessage(this)
|
||||
, message(this, "MSG")
|
||||
{
|
||||
}
|
||||
|
||||
void OnNickInfo(CommandSource &source, NickAlias *na, InfoFormatter &info, bool show_hidden) override
|
||||
{
|
||||
if (!show_hidden)
|
||||
return;
|
||||
if (message.HasExt(na->nc))
|
||||
info.AddOption(_("Message mode"));
|
||||
}
|
||||
};
|
||||
|
||||
MODULE_INIT(NSSetMessage)
|
||||
@@ -312,12 +312,8 @@ struct IRCDMessageMode final
|
||||
Channel *c = Channel::Find(params[0]);
|
||||
auto ts = IRCD->ExtractTimestamp(params[1]);
|
||||
|
||||
Anope::string modes = params[2];
|
||||
for (unsigned int i = 3; i < params.size(); ++i)
|
||||
modes += " " + params[i];
|
||||
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes, ts);
|
||||
c->SetModesInternal(source, params[2], { params.begin() + 3, params.end() }, ts);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -400,11 +396,12 @@ struct IRCDMessageSJoin final
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
Anope::string modes;
|
||||
std::vector<Anope::string> modeparams;
|
||||
if (params.size() >= 4)
|
||||
for (unsigned i = 2; i < params.size(); ++i)
|
||||
modes += " " + params[i];
|
||||
if (!modes.empty())
|
||||
modes.erase(modes.begin());
|
||||
{
|
||||
modes = params[2];
|
||||
modeparams = { params.begin() + 3, params.end() };
|
||||
}
|
||||
|
||||
std::list<Message::Join::SJoinUser> users;
|
||||
|
||||
@@ -445,7 +442,7 @@ struct IRCDMessageSJoin final
|
||||
}
|
||||
|
||||
auto ts = IRCD->ExtractTimestamp(params[0]);
|
||||
Message::Join::SJoin(source, params[1], ts, modes, users);
|
||||
Message::Join::SJoin(source, params[1], ts, modes, modeparams, users);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -547,14 +547,6 @@ struct IRCDMessageSJoin final
|
||||
/* :0MC SJOIN 1654877335 #nether +nt :@0MCAAAAAB +0MCAAAAAC */
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
Anope::string modes;
|
||||
|
||||
for (unsigned i = 2; i < params.size() - 1; ++i)
|
||||
modes += " " + params[i];
|
||||
|
||||
if (!modes.empty())
|
||||
modes.erase(modes.begin());
|
||||
|
||||
std::list<Message::Join::SJoinUser> users;
|
||||
|
||||
spacesepstream sep(params[params.size() - 1]);
|
||||
@@ -582,7 +574,7 @@ struct IRCDMessageSJoin final
|
||||
}
|
||||
|
||||
auto ts = IRCD->ExtractTimestamp(params[0]);
|
||||
Message::Join::SJoin(source, params[1], ts, modes, users);
|
||||
Message::Join::SJoin(source, params[1], ts, params[2], { params.begin() + 3, params.end() - 1 }, users);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -637,13 +629,9 @@ struct IRCDMessageTMode final
|
||||
{
|
||||
auto ts = IRCD->ExtractTimestamp(params[0]);
|
||||
Channel *c = Channel::Find(params[1]);
|
||||
Anope::string modes = params[2];
|
||||
|
||||
for (unsigned i = 3; i < params.size(); ++i)
|
||||
modes += " " + params[i];
|
||||
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes, ts);
|
||||
c->SetModesInternal(source, params[2], { params.begin() + 3, params.end() }, ts);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -27,6 +27,9 @@ struct SASLUser final
|
||||
|
||||
namespace
|
||||
{
|
||||
/** Whether we should send extbans using their named form. */
|
||||
bool named_extbans = false;
|
||||
|
||||
// The SID of a server we are waiting to squit.
|
||||
Anope::string rsquit_id;
|
||||
|
||||
@@ -723,7 +726,8 @@ namespace InspIRCdExtBan
|
||||
|
||||
ChannelMode *Wrap(Anope::string ¶m) override
|
||||
{
|
||||
param = Anope::string(xbchar) + ":" + param;
|
||||
auto xbprefix = named_extbans || !xbchar ? xbname : Anope::string(xbchar);
|
||||
param = xbprefix + ":" + param;
|
||||
return ChannelModeVirtual<ChannelModeList>::Wrap(param);
|
||||
}
|
||||
|
||||
@@ -757,10 +761,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
|
||||
return Entry(this->name, real_mask).Matches(u);
|
||||
return Entry(this->name, e->GetMask()).Matches(u);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -775,10 +776,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
|
||||
Anope::string channel = mask.substr(2);
|
||||
|
||||
auto channel = e->GetMask();
|
||||
ChannelMode *cm = NULL;
|
||||
if (channel[0] != '#')
|
||||
{
|
||||
@@ -813,10 +811,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
|
||||
return u->IsIdentified() && real_mask.equals_ci(u->Account()->display);
|
||||
return u->IsIdentified() && e->GetMask().equals_ci(u->Account()->display);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -831,9 +826,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
return Anope::Match(u->realname, real_mask);
|
||||
return Anope::Match(u->realname, e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
@@ -848,9 +841,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
return Anope::Match(u->server->GetName(), real_mask);
|
||||
return Anope::Match(u->server->GetName(), e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
@@ -865,9 +856,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
return !u->fingerprint.empty() && Anope::Match(u->fingerprint, real_mask);
|
||||
return !u->fingerprint.empty() && Anope::Match(u->fingerprint, e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
@@ -882,9 +871,7 @@ namespace InspIRCdExtBan
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
return !u->Account() && Entry("BAN", real_mask).Matches(u);
|
||||
return !u->Account() && Entry(this->base, e->GetMask()).Matches(u);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -903,9 +890,7 @@ namespace InspIRCdExtBan
|
||||
if (!opertype)
|
||||
return false; // Not an operator.
|
||||
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(2);
|
||||
return Anope::Match(opertype->replace_all_cs(' ', '_'), real_mask);
|
||||
return Anope::Match(opertype->replace_all_cs(' ', '_'), e->GetMask());
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -1091,19 +1076,25 @@ struct IRCDMessageCapab final
|
||||
|
||||
static bool ParseExtBan(const Anope::string &token, ExtBanInfo &extban)
|
||||
{
|
||||
// acting:foo=f matching:foo=f
|
||||
// A B A B
|
||||
// acting:foo=f matching:bar=b matching:baz
|
||||
// A B A B A
|
||||
auto a = token.find(':');
|
||||
if (a == Anope::string::npos)
|
||||
return false;
|
||||
|
||||
auto b = token.find(':', a + 1);
|
||||
auto b = token.find('=', a + 1);
|
||||
if (b == Anope::string::npos)
|
||||
return false;
|
||||
|
||||
{
|
||||
// ExtBan only has a name.
|
||||
extban.name = token.substr(a + 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
// ExtBan has a name and letter.
|
||||
extban.name = token.substr(a + 1, b - a - 1);
|
||||
extban.letter = token[b + 1];
|
||||
}
|
||||
extban.type = token.substr(0, a);
|
||||
extban.name = token.substr(a + 1, b - a - 1);
|
||||
extban.letter = token[b + 1];
|
||||
|
||||
if (Anope::ProtocolDebug)
|
||||
Log(LOG_DEBUG) << "Parsed extban: type=" << extban.type << " name=" << extban.name << " letter=" << extban.letter;
|
||||
@@ -1573,6 +1564,8 @@ struct IRCDMessageCapab final
|
||||
auto [tokname, tokvalue] = ParseCapability(capab);
|
||||
if (tokname == "CHALLENGE")
|
||||
challenge = tokvalue;
|
||||
if (tokname == "EXTBANFORMAT")
|
||||
named_extbans = tokvalue.equals_ci("any") || tokvalue.equals_ci("name");
|
||||
else if (tokname == "MAXCHANNEL")
|
||||
IRCD->MaxChannel = Anope::Convert<size_t>(tokvalue, IRCD->MaxChannel);
|
||||
else if (tokname == "MAXHOST")
|
||||
@@ -2056,15 +2049,6 @@ struct IRCDMessageFJoin final
|
||||
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
Anope::string modes;
|
||||
if (params.size() >= 3)
|
||||
{
|
||||
for (unsigned i = 2; i < params.size() - 1; ++i)
|
||||
modes += " " + params[i];
|
||||
if (!modes.empty())
|
||||
modes.erase(modes.begin());
|
||||
}
|
||||
|
||||
std::list<Message::Join::SJoinUser> users;
|
||||
|
||||
spacesepstream sep(params[params.size() - 1]);
|
||||
@@ -2102,7 +2086,7 @@ struct IRCDMessageFJoin final
|
||||
}
|
||||
|
||||
auto ts = IRCD->ExtractTimestamp(params[1]);
|
||||
Message::Join::SJoin(source, params[0], ts, modes, users);
|
||||
Message::Join::SJoin(source, params[0], ts, params[2], { params.begin() + 3, params.end() - 1 }, users);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -2114,15 +2098,10 @@ struct IRCDMessageFMode final
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
/* :source FMODE #test 12345678 +nto foo */
|
||||
|
||||
Anope::string modes = params[2];
|
||||
for (unsigned n = 3; n < params.size(); ++n)
|
||||
modes += " " + params[n];
|
||||
|
||||
Channel *c = Channel::Find(params[0]);
|
||||
auto ts = IRCD->ExtractTimestamp(params[1]);
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes, ts);
|
||||
c->SetModesInternal(source, params[2], { params.begin() + 3, params.end() }, ts);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -2198,7 +2177,7 @@ struct IRCDMessageIJoin final
|
||||
|
||||
std::list<Message::Join::SJoinUser> users;
|
||||
users.push_back(user);
|
||||
Message::Join::SJoin(source, params[0], chants, "", users);
|
||||
Message::Join::SJoin(source, params[0], chants, "", {}, users);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -2250,12 +2229,8 @@ struct IRCDMessageMode final
|
||||
{
|
||||
Channel *c = Channel::Find(params[0]);
|
||||
|
||||
Anope::string modes = params[1];
|
||||
for (unsigned n = 2; n < params.size(); ++n)
|
||||
modes += " " + params[n];
|
||||
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes);
|
||||
c->SetModesInternal(source, params[2], { params.begin() + 3, params.end() });
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -2415,10 +2390,6 @@ struct IRCDMessageUID final
|
||||
size_t offset = params[8][0] == '+' ? 0 : 1;
|
||||
auto ts = IRCD->ExtractTimestamp(params[1]);
|
||||
|
||||
Anope::string modes = params[8+offset];
|
||||
for (unsigned i = 9+offset; i < params.size() - 1; ++i)
|
||||
modes += " " + params[i];
|
||||
|
||||
NickAlias *na = NULL;
|
||||
if (SASL::sasl)
|
||||
for (std::list<SASLUser>::iterator it = saslusers.begin(); it != saslusers.end();)
|
||||
@@ -2436,7 +2407,7 @@ struct IRCDMessageUID final
|
||||
++it;
|
||||
}
|
||||
|
||||
User *u = User::OnIntroduce(params[2], params[5+offset], params[3], params[4], params[6+offset], source.GetServer(), params[params.size() - 1], ts, modes, params[0], na ? *na->nc : NULL);
|
||||
auto *u = User::OnIntroduce(params[2], params[5+offset], params[3], params[4], params[6+offset], source.GetServer(), params[params.size() - 1], ts, params[8 + offset], params[0], na ? *na->nc : NULL, { params.begin() + 9 + offset, params.end() - 1 });
|
||||
if (u)
|
||||
u->signon = IRCD->ExtractTimestamp(params[7+offset]);
|
||||
}
|
||||
|
||||
+10
-13
@@ -224,7 +224,7 @@ struct IRCDMessageChaninfo final
|
||||
bool created;
|
||||
Channel *c = Channel::FindOrCreate(params[0], created);
|
||||
|
||||
Anope::string modes = params[1];
|
||||
std::vector<Anope::string> modeparams;
|
||||
|
||||
if (params.size() == 3)
|
||||
{
|
||||
@@ -237,17 +237,17 @@ struct IRCDMessageChaninfo final
|
||||
switch(params[1][i])
|
||||
{
|
||||
case 'k':
|
||||
modes += " " + params[2];
|
||||
modeparams.push_back(params[2]);
|
||||
continue;
|
||||
case 'l':
|
||||
modes += " " + params[3];
|
||||
modeparams.push_back(params[3]);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
c->ChangeTopicInternal(NULL, source.GetName(), params[4], Anope::CurTime);
|
||||
}
|
||||
|
||||
c->SetModesInternal(source, modes);
|
||||
c->SetModesInternal(source, params[1], modeparams);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -267,11 +267,13 @@ struct IRCDMessageJoin final
|
||||
User *user = source.GetUser();
|
||||
size_t pos = params[0].find('\7');
|
||||
Anope::string channel, modes;
|
||||
std::vector<Anope::string> modeparams;
|
||||
|
||||
if (pos != Anope::string::npos)
|
||||
{
|
||||
channel = params[0].substr(0, pos);
|
||||
modes = '+' + params[0].substr(pos+1, params[0].length()) + " " + user->nick;
|
||||
modes = '+' + params[0].substr(pos+1, params[0].length());
|
||||
modeparams.push_back(user->nick);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -287,7 +289,7 @@ struct IRCDMessageJoin final
|
||||
{
|
||||
Channel *c = Channel::Find(channel);
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes);
|
||||
c->SetModesInternal(source, modes, modeparams);
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -367,17 +369,12 @@ struct IRCDMessageMode final
|
||||
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
Anope::string modes = params[1];
|
||||
|
||||
for (size_t i = 2; i < params.size(); ++i)
|
||||
modes += " " + params[i];
|
||||
|
||||
if (IRCD->IsChannelValid(params[0]))
|
||||
{
|
||||
Channel *c = Channel::Find(params[0]);
|
||||
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes);
|
||||
c->SetModesInternal(source, params[1], { params.begin() + 2, params.end() });
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -485,7 +482,7 @@ struct IRCDMessageNJoin final
|
||||
users.push_back(sju);
|
||||
}
|
||||
|
||||
Message::Join::SJoin(source, params[0], 0, "", users);
|
||||
Message::Join::SJoin(source, params[0], 0, "", {}, users);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@@ -33,7 +33,7 @@ class RatboxProto final
|
||||
}
|
||||
|
||||
public:
|
||||
RatboxProto(Module *creator) : IRCDProto(creator, "Ratbox 3.0+")
|
||||
RatboxProto(Module *creator) : IRCDProto(creator, "ircd-ratbox 3+")
|
||||
{
|
||||
DefaultPseudoclientModes = "+oiS";
|
||||
CanSNLine = true;
|
||||
|
||||
+111
-105
@@ -14,7 +14,25 @@
|
||||
#include "modules/sasl.h"
|
||||
|
||||
typedef Anope::map<Anope::string> ModData;
|
||||
static Anope::string UplinkSID;
|
||||
|
||||
namespace
|
||||
{
|
||||
Anope::string UplinkSID;
|
||||
|
||||
bool IsExtBan(const Anope::string &str, Anope::string &name, Anope::string &value)
|
||||
{
|
||||
if (str[0] != '~')
|
||||
return false;
|
||||
|
||||
auto endpos = str.find_first_not_of("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789", 1);
|
||||
if (endpos == Anope::string::npos || str[endpos] != ':' || endpos+1 == str.length())
|
||||
return false;
|
||||
|
||||
name = str.substr(1, endpos - 1);
|
||||
value = str.substr(endpos + 1);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
class UnrealIRCdProto final
|
||||
: public IRCDProto
|
||||
@@ -225,9 +243,10 @@ private:
|
||||
// EAUTH: communicates information about the local server.
|
||||
// MLOCK: enable receiving the MLOCK message when a mode lock changes.
|
||||
// MTAGS: enable receiving IRCv3 message tags.
|
||||
// NEXTBANS: enables receiving named extended bans.
|
||||
// SID: communicates the unique identifier of the local server.
|
||||
// VHP: enable receiving the vhost in UID.
|
||||
Uplink::Send("PROTOCTL", "BIGLINES", "MLOCK", "MTAGS", "VHP");
|
||||
Uplink::Send("PROTOCTL", "BIGLINES", "MLOCK", "MTAGS", "NEXTBANS", "VHP");
|
||||
Uplink::Send("PROTOCTL", "EAUTH=" + Me->GetName() + ",,,Anope-" + Anope::VersionShort());
|
||||
Uplink::Send("PROTOCTL", "SID=" + Me->GetSID());
|
||||
|
||||
@@ -345,7 +364,8 @@ private:
|
||||
|
||||
bool IsExtbanValid(const Anope::string &mask) override
|
||||
{
|
||||
return mask.length() >= 4 && mask[0] == '~' && mask[2] == ':';
|
||||
Anope::string name, value;
|
||||
return IsExtBan(mask, name, value);
|
||||
}
|
||||
|
||||
void SendLogin(User *u, NickAlias *na) override
|
||||
@@ -446,48 +466,61 @@ private:
|
||||
}
|
||||
};
|
||||
|
||||
class UnrealExtBan
|
||||
: public ChannelModeVirtual<ChannelModeList>
|
||||
namespace UnrealExtBan
|
||||
{
|
||||
char ext;
|
||||
|
||||
public:
|
||||
UnrealExtBan(const Anope::string &mname, const Anope::string &basename, char extban) : ChannelModeVirtual<ChannelModeList>(mname, basename)
|
||||
, ext(extban)
|
||||
class Base
|
||||
: public ChannelModeVirtual<ChannelModeList>
|
||||
{
|
||||
}
|
||||
private:
|
||||
char xbchar;
|
||||
Anope::string xbname;
|
||||
|
||||
ChannelMode *Wrap(Anope::string ¶m) override
|
||||
{
|
||||
param = "~" + Anope::string(ext) + ":" + param;
|
||||
return ChannelModeVirtual<ChannelModeList>::Wrap(param);
|
||||
}
|
||||
public:
|
||||
Base(const Anope::string &mname, const Anope::string& uname, char uchar)
|
||||
: ChannelModeVirtual<ChannelModeList>(mname, "BAN")
|
||||
, xbchar(uchar)
|
||||
, xbname(uname)
|
||||
{
|
||||
}
|
||||
|
||||
ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) override
|
||||
{
|
||||
if (cm->type != MODE_LIST || param.length() < 4 || param[0] != '~' || param[1] != ext || param[2] != ':')
|
||||
return cm;
|
||||
ChannelMode *Wrap(Anope::string ¶m) override
|
||||
{
|
||||
auto prefix = Servers::Capab.count("NEXTBANS") ? xbname : Anope::string(xbchar);
|
||||
param = Anope::printf("~%s:%s", prefix.c_str(), param.c_str());
|
||||
return ChannelModeVirtual<ChannelModeList>::Wrap(param);
|
||||
}
|
||||
|
||||
param = param.substr(3);
|
||||
return this;
|
||||
}
|
||||
};
|
||||
ChannelMode *Unwrap(ChannelMode *cm, Anope::string ¶m) override
|
||||
{
|
||||
// The mask must be in the format ~<letter>:<value> or ~<name>:<value>.
|
||||
if (cm->type != MODE_LIST)
|
||||
return cm;
|
||||
|
||||
Anope::string name, value;
|
||||
if (!IsExtBan(param, name, value))
|
||||
return cm;
|
||||
|
||||
if (name.length() == 1 ? name[0] != xbchar : name != xbname)
|
||||
return cm;
|
||||
|
||||
param = value;
|
||||
return this;
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
namespace UnrealExtban
|
||||
{
|
||||
class ChannelMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
ChannelMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
ChannelMatcher()
|
||||
: Base("CHANNELBAN", "channel", 'c')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string channel = mask.substr(3);
|
||||
|
||||
auto channel = e->GetMask();
|
||||
ChannelMode *cm = NULL;
|
||||
if (channel[0] != '#')
|
||||
{
|
||||
@@ -512,137 +545,113 @@ namespace UnrealExtban
|
||||
};
|
||||
|
||||
class EntryMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
EntryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
EntryMatcher(const Anope::string &mname, const Anope::string &uname, char uchar)
|
||||
: Base(mname, uname, uchar)
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
|
||||
return Entry(this->name, real_mask).Matches(u);
|
||||
return Entry(this->base, e->GetMask()).Matches(u);
|
||||
}
|
||||
};
|
||||
|
||||
class RealnameMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
RealnameMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
RealnameMatcher()
|
||||
: Base("REALNAMEBAN", "realname", 'r')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
|
||||
return Anope::Match(u->realname, real_mask);
|
||||
}
|
||||
};
|
||||
|
||||
class RegisteredMatcher final
|
||||
: public UnrealExtBan
|
||||
{
|
||||
public:
|
||||
RegisteredMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
return u->HasMode("REGISTERED") && mask.equals_ci(u->nick);
|
||||
return Anope::Match(u->realname, e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
class AccountMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
AccountMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
AccountMatcher()
|
||||
: Base("ACCOUNTBAN", "account", 'a')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
|
||||
if (real_mask == "0" && !u->Account()) /* ~a:0 is special and matches all unauthenticated users */
|
||||
if (e->GetMask() == "0" && !u->Account()) /* ~a:0 is special and matches all unauthenticated users */
|
||||
return true;
|
||||
|
||||
return u->Account() && Anope::Match(u->Account()->display, real_mask);
|
||||
return u->Account() && Anope::Match(u->Account()->display, e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
class FingerprintMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
FingerprintMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
FingerprintMatcher()
|
||||
: Base("SSLBAN", "certfp", 'S')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
return !u->fingerprint.empty() && Anope::Match(u->fingerprint, real_mask);
|
||||
return !u->fingerprint.empty() && Anope::Match(u->fingerprint, e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
class OperclassMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
OperclassMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
OperclassMatcher()
|
||||
: Base("OPERCLASSBAN", "operclass", 'O')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
ModData *moddata = u->GetExt<ModData>("ClientModData");
|
||||
return moddata != NULL && moddata->find("operclass") != moddata->end() && Anope::Match((*moddata)["operclass"], real_mask);
|
||||
return moddata != NULL && moddata->find("operclass") != moddata->end() && Anope::Match((*moddata)["operclass"], e->GetMask());
|
||||
}
|
||||
};
|
||||
|
||||
class TimedBanMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
TimedBanMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
TimedBanMatcher()
|
||||
: Base("TIMEDBAN", "time", 't')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
/* strip down the time (~t:1234:) and call other matchers */
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
auto real_mask = e->GetMask();
|
||||
real_mask = real_mask.substr(real_mask.find(":") + 1);
|
||||
return Entry("BAN", real_mask).Matches(u);
|
||||
}
|
||||
};
|
||||
|
||||
class CountryMatcher final
|
||||
: public UnrealExtBan
|
||||
: public Base
|
||||
{
|
||||
public:
|
||||
CountryMatcher(const Anope::string &mname, const Anope::string &mbase, char c) : UnrealExtBan(mname, mbase, c)
|
||||
CountryMatcher()
|
||||
: Base("COUNTRYBAN", "country", 'C')
|
||||
{
|
||||
}
|
||||
|
||||
bool Matches(User *u, const Entry *e) override
|
||||
{
|
||||
const Anope::string &mask = e->GetMask();
|
||||
Anope::string real_mask = mask.substr(3);
|
||||
ModData *moddata = u->GetExt<ModData>("ClientModData");
|
||||
if (moddata == NULL || moddata->find("geoip") == moddata->end())
|
||||
return false;
|
||||
@@ -652,7 +661,7 @@ namespace UnrealExtban
|
||||
while (sep.GetToken(tokenbuf))
|
||||
{
|
||||
if (tokenbuf.rfind("cc=", 0) == 0)
|
||||
return (tokenbuf.substr(3, 2) == real_mask);
|
||||
return (tokenbuf.substr(3, 2) == e->GetMask());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
@@ -838,17 +847,16 @@ struct IRCDMessageCapab final
|
||||
case 'b':
|
||||
ModeManager::AddChannelMode(new ChannelModeList("BAN", 'b'));
|
||||
|
||||
ModeManager::AddChannelMode(new UnrealExtban::ChannelMatcher("CHANNELBAN", "BAN", 'c'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("JOINBAN", "BAN", 'j'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("NONICKBAN", "BAN", 'n'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::EntryMatcher("QUIET", "BAN", 'q'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::RealnameMatcher("REALNAMEBAN", "BAN", 'r'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::RegisteredMatcher("REGISTEREDBAN", "BAN", 'R'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::AccountMatcher("ACCOUNTBAN", "BAN", 'a'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::FingerprintMatcher("SSLBAN", "BAN", 'S'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::TimedBanMatcher("TIMEDBAN", "BAN", 't'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::OperclassMatcher("OPERCLASSBAN", "BAN", 'O'));
|
||||
ModeManager::AddChannelMode(new UnrealExtban::CountryMatcher("COUNTRYBAN", "BAN", 'C'));
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::ChannelMatcher());
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::EntryMatcher("JOINBAN", "join", 'j'));
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::EntryMatcher("NONICKBAN", "nickchange", 'n'));
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::EntryMatcher("QUIET", "quiet", 'q'));
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::RealnameMatcher());
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::AccountMatcher());
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::FingerprintMatcher());
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::TimedBanMatcher());
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::OperclassMatcher());
|
||||
ModeManager::AddChannelMode(new UnrealExtBan::CountryMatcher());
|
||||
continue;
|
||||
case 'e':
|
||||
ModeManager::AddChannelMode(new ChannelModeList("EXCEPT", 'e'));
|
||||
@@ -1147,10 +1155,7 @@ struct IRCDMessageMode final
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
auto final_is_ts = server_ts && source.GetServer() != NULL;
|
||||
|
||||
Anope::string modes = params[1];
|
||||
for (unsigned i = 2; i < params.size() - (final_is_ts ? 1 : 0); ++i)
|
||||
modes += " " + params[i];
|
||||
auto last_param = params.end() - (params.size() > 3 && final_is_ts ? 1 : 0);
|
||||
|
||||
if (IRCD->IsChannelValid(params[0]))
|
||||
{
|
||||
@@ -1158,7 +1163,7 @@ struct IRCDMessageMode final
|
||||
auto ts = final_is_ts ? IRCD->ExtractTimestamp(params.back()) : 0;
|
||||
|
||||
if (c)
|
||||
c->SetModesInternal(source, modes, ts);
|
||||
c->SetModesInternal(source, params[1], { params.begin() + 2, last_param }, ts);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -1420,11 +1425,12 @@ struct IRCDMessageSJoin final
|
||||
void Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags) override
|
||||
{
|
||||
Anope::string modes;
|
||||
std::vector<Anope::string> modeparams;
|
||||
if (params.size() >= 4)
|
||||
for (unsigned i = 2; i < params.size() - 1; ++i)
|
||||
modes += " " + params[i];
|
||||
if (!modes.empty())
|
||||
modes.erase(modes.begin());
|
||||
{
|
||||
modes = params[2];
|
||||
modeparams = { params.begin() + 3, params.end() };
|
||||
}
|
||||
|
||||
std::list<Anope::string> bans, excepts, invites;
|
||||
std::list<Message::Join::SJoinUser> users;
|
||||
@@ -1474,7 +1480,7 @@ struct IRCDMessageSJoin final
|
||||
}
|
||||
|
||||
auto ts = IRCD->ExtractTimestamp(params[0]);
|
||||
Message::Join::SJoin(source, params[1], ts, modes, users);
|
||||
Message::Join::SJoin(source, params[1], ts, modes, modeparams, users);
|
||||
|
||||
if (!bans.empty() || !excepts.empty() || !invites.empty())
|
||||
{
|
||||
|
||||
+22
-4
@@ -20,7 +20,11 @@
|
||||
|
||||
Serialize::Checker<botinfo_map> BotListByNick("BotInfo"), BotListByUID("BotInfo");
|
||||
|
||||
BotInfo::BotInfo(const Anope::string &nnick, const Anope::string &nuser, const Anope::string &nhost, const Anope::string &nreal, const Anope::string &bmodes) : User(nnick, nuser, nhost, "", "", Me, nreal, Anope::CurTime, "", IRCD ? IRCD->UID_Retrieve() : "", NULL), Serializable("BotInfo"), channels("ChannelInfo"), botmodes(bmodes)
|
||||
BotInfo::BotInfo(const Anope::string &nnick, const Anope::string &nuser, const Anope::string &nhost, const Anope::string &nreal, const Anope::string &bmodes)
|
||||
: User(nnick, nuser, nhost, "", "", Me, nreal, Anope::CurTime, "", {}, IRCD ? IRCD->UID_Retrieve() : "", NULL)
|
||||
, Serializable("BotInfo")
|
||||
, channels("ChannelInfo")
|
||||
, botmodes(bmodes)
|
||||
{
|
||||
this->lastmsg = this->created = Anope::CurTime;
|
||||
this->introduced = false;
|
||||
@@ -35,9 +39,16 @@ BotInfo::BotInfo(const Anope::string &nnick, const Anope::string &nuser, const A
|
||||
// If we're synchronised with the uplink already, send the bot.
|
||||
if (Me && Me->IsSynced())
|
||||
{
|
||||
Anope::string tmodes = !this->botmodes.empty() ? ("+" + this->botmodes) : IRCD->DefaultPseudoclientModes;
|
||||
if (!tmodes.empty())
|
||||
this->SetModesInternal(this, tmodes);
|
||||
spacesepstream modesep(this->botmodes.empty() ? IRCD->DefaultPseudoclientModes : "+" + this->botmodes);
|
||||
|
||||
Anope::string modechars;
|
||||
modesep.GetToken(modechars);
|
||||
|
||||
std::vector<Anope::string> modeparams;
|
||||
modesep.GetTokens(modeparams);
|
||||
|
||||
if (!modechars.empty())
|
||||
this->SetModesInternal(this, modechars, modeparams);
|
||||
|
||||
XLine x(this->nick, "Reserved for services");
|
||||
IRCD->SendSQLine(NULL, &x);
|
||||
@@ -254,6 +265,13 @@ CommandInfo *BotInfo::GetCommand(const Anope::string &cname)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
Anope::string BotInfo::GetQueryCommand() const
|
||||
{
|
||||
if (Config->ServiceAlias && !this->alias.empty())
|
||||
return Anope::printf("/%s", this->alias.c_str());
|
||||
return Anope::printf("/msg %s", this->nick.c_str());
|
||||
}
|
||||
|
||||
BotInfo *BotInfo::Find(const Anope::string &nick, bool nick_only)
|
||||
{
|
||||
if (!nick_only && IRCD != NULL && IRCD->RequiresID)
|
||||
|
||||
+13
-15
@@ -611,13 +611,13 @@ void Channel::SetModes(BotInfo *bi, bool enforce_mlock, const Anope::string &cmo
|
||||
}
|
||||
}
|
||||
|
||||
void Channel::SetModesInternal(MessageSource &source, const Anope::string &mode, time_t ts, bool enforce_mlock)
|
||||
void Channel::SetModesInternal(MessageSource &source, const Anope::string &modes, const std::vector<Anope::string> ¶ms, time_t ts, bool enforce_mlock)
|
||||
{
|
||||
if (!ts)
|
||||
;
|
||||
else if (ts > this->creation_time)
|
||||
{
|
||||
Log(LOG_DEBUG) << "Dropping mode " << mode << " on " << this->name << ", " << ts << " > " << this->creation_time;
|
||||
Log(LOG_DEBUG) << "Dropping mode " << modes << " on " << this->name << ", " << ts << " > " << this->creation_time;
|
||||
return;
|
||||
}
|
||||
else if (ts < this->creation_time)
|
||||
@@ -631,20 +631,18 @@ void Channel::SetModesInternal(MessageSource &source, const Anope::string &mode,
|
||||
/* Removing channel modes *may* delete this channel */
|
||||
Reference<Channel> this_reference(this);
|
||||
|
||||
spacesepstream sep_modes(mode);
|
||||
Anope::string m;
|
||||
|
||||
sep_modes.GetToken(m);
|
||||
|
||||
Anope::string modestring;
|
||||
Anope::string paramstring;
|
||||
int add = -1;
|
||||
bool changed = false;
|
||||
for (unsigned int i = 0, end = m.length(); i < end && this_reference; ++i)
|
||||
auto paramit = params.begin();
|
||||
for (const auto mchar : modes)
|
||||
{
|
||||
ChannelMode *cm;
|
||||
if (!this_reference)
|
||||
break;
|
||||
|
||||
switch (m[i])
|
||||
ChannelMode *cm;
|
||||
switch (mchar)
|
||||
{
|
||||
case '+':
|
||||
modestring += '+';
|
||||
@@ -657,10 +655,10 @@ void Channel::SetModesInternal(MessageSource &source, const Anope::string &mode,
|
||||
default:
|
||||
if (add == -1)
|
||||
continue;
|
||||
cm = ModeManager::FindChannelModeByChar(m[i]);
|
||||
cm = ModeManager::FindChannelModeByChar(mchar);
|
||||
if (!cm)
|
||||
{
|
||||
Log(LOG_DEBUG) << "Channel::SetModeInternal: Unknown mode char " << m[i];
|
||||
Log(LOG_DEBUG) << "Channel::SetModeInternal: Unknown mode char " << mchar;
|
||||
continue;
|
||||
}
|
||||
modestring += cm->mchar;
|
||||
@@ -686,9 +684,9 @@ void Channel::SetModesInternal(MessageSource &source, const Anope::string &mode,
|
||||
continue;
|
||||
}
|
||||
}
|
||||
Anope::string token;
|
||||
if (sep_modes.GetToken(token))
|
||||
if (paramit != params.end())
|
||||
{
|
||||
auto token = *paramit++;
|
||||
User *u = NULL;
|
||||
if (cm->type == MODE_STATUS && (u = User::Find(token)))
|
||||
paramstring += " " + u->nick;
|
||||
@@ -703,7 +701,7 @@ void Channel::SetModesInternal(MessageSource &source, const Anope::string &mode,
|
||||
this->RemoveModeInternal(source, cm, token, enforce_mlock);
|
||||
}
|
||||
else
|
||||
Log() << "warning: Channel::SetModesInternal() received more modes requiring params than params, modes: " << mode;
|
||||
Log() << "warning: Channel::SetModesInternal() received more modes requiring params than params, modes: " << modes;
|
||||
}
|
||||
|
||||
if (!this_reference)
|
||||
|
||||
+5
-5
@@ -199,7 +199,7 @@ void Command::OnSyntaxError(CommandSource &source, const Anope::string &subcomma
|
||||
this->SendSyntax(source);
|
||||
bool has_help = source.service->commands.find("HELP") != source.service->commands.end();
|
||||
if (has_help)
|
||||
source.Reply(MORE_INFO, Config->StrictPrivmsg.c_str(), source.service->nick.c_str(), source.command.c_str());
|
||||
source.Reply(MORE_INFO, source.service->GetQueryCommand().c_str(), source.command.c_str());
|
||||
}
|
||||
|
||||
namespace
|
||||
@@ -226,13 +226,13 @@ namespace
|
||||
bool has_help = source.service->commands.find("HELP") != source.service->commands.end();
|
||||
if (has_help && similar.empty())
|
||||
{
|
||||
source.Reply(_("Unknown command \002%s\002. \"%s%s HELP\" for help."), message.c_str(),
|
||||
Config->StrictPrivmsg.c_str(), source.service->nick.c_str());
|
||||
source.Reply(_("Unknown command \002%s\002. \"%s HELP\" for help."), message.c_str(),
|
||||
source.service->GetQueryCommand().c_str());
|
||||
}
|
||||
else if (has_help)
|
||||
{
|
||||
source.Reply(_("Unknown command \002%s\002. Did you mean \002%s\002? \"%s%s HELP\" for help."),
|
||||
message.c_str(), similar.c_str(), Config->StrictPrivmsg.c_str(), source.service->nick.c_str());
|
||||
source.Reply(_("Unknown command \002%s\002. Did you mean \002%s\002? \"%s HELP\" for help."),
|
||||
message.c_str(), similar.c_str(), source.service->GetQueryCommand().c_str());
|
||||
}
|
||||
else if (similar.empty())
|
||||
{
|
||||
|
||||
+6
-5
@@ -121,7 +121,7 @@ template<typename T> static void ValidateNotZero(const Anope::string &block, con
|
||||
Conf::Conf() : Block("")
|
||||
{
|
||||
ReadTimeout = 0;
|
||||
UsePrivmsg = DefPrivmsg = false;
|
||||
DefPrivmsg = false;
|
||||
|
||||
this->LoadConf(ServicesConf);
|
||||
|
||||
@@ -195,9 +195,7 @@ Conf::Conf() : Block("")
|
||||
}
|
||||
|
||||
this->ReadTimeout = options->Get<time_t>("readtimeout");
|
||||
this->UsePrivmsg = options->Get<bool>("useprivmsg");
|
||||
this->UseStrictPrivmsg = options->Get<bool>("usestrictprivmsg");
|
||||
this->StrictPrivmsg = !UseStrictPrivmsg ? "/msg " : "/";
|
||||
this->ServiceAlias = options->Get<bool>("servicealias");
|
||||
{
|
||||
std::vector<Anope::string> defaults;
|
||||
spacesepstream(this->GetModule("nickserv")->Get<const Anope::string>("defaults")).GetTokens(defaults);
|
||||
@@ -339,7 +337,8 @@ Conf::Conf() : Block("")
|
||||
&host = service->Get<const Anope::string>("host"),
|
||||
&gecos = service->Get<const Anope::string>("gecos"),
|
||||
&modes = service->Get<const Anope::string>("modes"),
|
||||
&channels = service->Get<const Anope::string>("channels");
|
||||
&channels = service->Get<const Anope::string>("channels"),
|
||||
&alias = service->Get<const Anope::string>("alias", nick.upper());
|
||||
|
||||
ValidateNotEmptyOrSpaces("service", "nick", nick);
|
||||
ValidateNotEmptyOrSpaces("service", "user", user);
|
||||
@@ -350,6 +349,8 @@ Conf::Conf() : Block("")
|
||||
BotInfo *bi = BotInfo::Find(nick, true);
|
||||
if (!bi)
|
||||
bi = new BotInfo(nick, user, host, gecos, modes);
|
||||
|
||||
bi->alias = alias;
|
||||
bi->conf = true;
|
||||
|
||||
std::vector<Anope::string> oldchannels = bi->botchannels;
|
||||
|
||||
+2
-2
@@ -337,7 +337,7 @@ bool Anope::Init(int ac, char **av)
|
||||
Log(LOG_TERMINAL) << "-v, --version";
|
||||
Log(LOG_TERMINAL) << "";
|
||||
Log(LOG_TERMINAL) << "Further support is available from https://www.anope.org/";
|
||||
Log(LOG_TERMINAL) << "Or visit us on IRC at irc.anope.org #anope";
|
||||
Log(LOG_TERMINAL) << "Or visit us on IRC at irc.teranova.net #anope";
|
||||
Anope::ReturnValue = EXIT_SUCCESS;
|
||||
return false;
|
||||
}
|
||||
@@ -488,7 +488,7 @@ bool Anope::Init(int ac, char **av)
|
||||
Log(LOG_TERMINAL) << "*** Support resources: Read through the anope.conf self-contained";
|
||||
Log(LOG_TERMINAL) << "*** documentation. Read the documentation files found in the 'docs'";
|
||||
Log(LOG_TERMINAL) << "*** folder. Visit our portal located at https://www.anope.org/. Join";
|
||||
Log(LOG_TERMINAL) << "*** our support channel on /server irc.anope.org channel #anope.";
|
||||
Log(LOG_TERMINAL) << "*** our support channel on /server irc.teranova.net channel #anope.";
|
||||
throw CoreException("Configuration file failed to validate");
|
||||
}
|
||||
|
||||
|
||||
@@ -36,6 +36,7 @@ Mail::Message::~Message()
|
||||
|
||||
void Mail::Message::Run()
|
||||
{
|
||||
errno = 0;
|
||||
auto *pipe = popen(sendmail_path.c_str(), "w");
|
||||
if (!pipe)
|
||||
{
|
||||
|
||||
+5
-19
@@ -98,11 +98,11 @@ void Join::Run(MessageSource &source, const std::vector<Anope::string> ¶ms,
|
||||
users.emplace_back(ChannelStatus(), user);
|
||||
|
||||
Channel *chan = Channel::Find(channel);
|
||||
SJoin(source, channel, chan ? chan->creation_time : Anope::CurTime, "", users);
|
||||
SJoin(source, channel, chan ? chan->creation_time : Anope::CurTime, "", {}, users);
|
||||
}
|
||||
}
|
||||
|
||||
void Join::SJoin(MessageSource &source, const Anope::string &chan, time_t ts, const Anope::string &modes, const std::list<SJoinUser> &users)
|
||||
void Join::SJoin(MessageSource &source, const Anope::string &chan, time_t ts, const Anope::string &modes, const std::vector<Anope::string> &modeparams, const std::list<SJoinUser> &users)
|
||||
{
|
||||
bool created;
|
||||
Channel *c = Channel::FindOrCreate(chan, created, ts ? ts : Anope::CurTime);
|
||||
@@ -128,7 +128,7 @@ void Join::SJoin(MessageSource &source, const Anope::string &chan, time_t ts, co
|
||||
/* If we are syncing, mlock is checked later in Channel::Sync. It is important to not check it here
|
||||
* so that Channel::SetCorrectModes can correctly detect the presence of channel mode +r.
|
||||
*/
|
||||
c->SetModesInternal(source, modes, ts, !c->syncing);
|
||||
c->SetModesInternal(source, modes, modeparams, ts, !c->syncing);
|
||||
|
||||
for (const auto &[status, u] : users)
|
||||
{
|
||||
@@ -214,23 +214,19 @@ void Kill::Run(MessageSource &source, const std::vector<Anope::string> ¶ms,
|
||||
|
||||
void Message::Mode::Run(MessageSource &source, const std::vector<Anope::string> ¶ms, const Anope::map<Anope::string> &tags)
|
||||
{
|
||||
Anope::string buf;
|
||||
for (unsigned i = 1; i < params.size(); ++i)
|
||||
buf += " " + params[i];
|
||||
|
||||
if (IRCD->IsChannelValid(params[0]))
|
||||
{
|
||||
Channel *c = Channel::Find(params[0]);
|
||||
|
||||
if (c)
|
||||
c->SetModesInternal(source, buf.substr(1), 0);
|
||||
c->SetModesInternal(source, params[1], { params.begin() + 2, params.end() });
|
||||
}
|
||||
else
|
||||
{
|
||||
User *u = User::Find(params[0]);
|
||||
|
||||
if (u)
|
||||
u->SetModesInternal(source, buf.substr(1));
|
||||
u->SetModesInternal(source, params[1], { params.begin() + 2, params.end() });
|
||||
}
|
||||
}
|
||||
|
||||
@@ -328,18 +324,8 @@ void Privmsg::Run(MessageSource &source, const std::vector<Anope::string> ¶m
|
||||
if (!servername.equals_ci(Me->GetName()))
|
||||
return;
|
||||
}
|
||||
else if (!IRCD->RequiresID && Config->UseStrictPrivmsg)
|
||||
{
|
||||
BotInfo *bi = BotInfo::Find(receiver);
|
||||
if (!bi)
|
||||
return;
|
||||
Log(LOG_DEBUG) << "Ignored PRIVMSG without @ from " << u->nick;
|
||||
u->SendMessage(bi, _("\"/msg %s\" is no longer supported. Use \"/msg %s@%s\" or \"/%s\" instead."), bi->nick.c_str(), bi->nick.c_str(), Me->GetName().c_str(), bi->nick.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
BotInfo *bi = BotInfo::Find(botname, nick_only);
|
||||
|
||||
if (bi)
|
||||
{
|
||||
Anope::string ctcpname, ctcpbody;
|
||||
|
||||
+1
-2
@@ -835,8 +835,7 @@ bool Entry::Matches(User *u, bool full) const
|
||||
if (cm != NULL && cm->type == MODE_LIST)
|
||||
{
|
||||
ChannelModeList *cml = anope_dynamic_static_cast<ChannelModeList *>(cm);
|
||||
if (cml->Matches(u, this))
|
||||
return true;
|
||||
return cml->Matches(u, this);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+9
-3
@@ -50,9 +50,15 @@ Server::Server(Server *up, const Anope::string &sname, unsigned shops, const Ano
|
||||
/* Now do mode related stuff as we know what modes exist .. */
|
||||
for (auto &[_, bi] : *BotListByNick)
|
||||
{
|
||||
Anope::string modes = !bi->botmodes.empty() ? ("+" + bi->botmodes) : IRCD->DefaultPseudoclientModes;
|
||||
spacesepstream modesep(bi->botmodes.empty() ? IRCD->DefaultPseudoclientModes : "+" + bi->botmodes);
|
||||
|
||||
bi->SetModesInternal(bi, modes);
|
||||
Anope::string modechars;
|
||||
modesep.GetToken(modechars);
|
||||
|
||||
std::vector<Anope::string> modeparams;
|
||||
modesep.GetTokens(modeparams);
|
||||
|
||||
bi->SetModesInternal(bi, modechars, modeparams);
|
||||
for (const auto &botchannel : bi->botchannels)
|
||||
{
|
||||
size_t h = botchannel.find('#');
|
||||
@@ -322,7 +328,7 @@ bool Server::IsQuitting() const
|
||||
|
||||
void Server::Notice(BotInfo *source, const Anope::string &message)
|
||||
{
|
||||
if (Config->UsePrivmsg && Config->DefPrivmsg)
|
||||
if (Config->DefPrivmsg)
|
||||
IRCD->SendGlobalPrivmsg(source, this, message);
|
||||
else
|
||||
IRCD->SendGlobalNotice(source, this, message);
|
||||
|
||||
@@ -24,8 +24,8 @@ die="yes"
|
||||
###########################
|
||||
|
||||
# The GeoIP data is created by MaxMind, available from www.maxmind.com.
|
||||
geoip_country_source="https://geolite.maxmind.com/download/geoip/database/GeoIPCountryCSV.zip"
|
||||
geoip_city_source="https://geolite.maxmind.com/download/geoip/database/GeoLiteCity_CSV/GeoLiteCity-latest.zip"
|
||||
geoip_country_source="https://mirrors-cdn.liferay.com/geolite.maxmind.com/download/geoip/database/GeoIPCountryCSV.zip"
|
||||
geoip_city_source="https://mirrors-cdn.liferay.com/geolite.maxmind.com/download/geoip/database/GeoLiteCity-latest.tar.xz"
|
||||
geoip_region_source="https://www.maxmind.com/download/geoip/misc/region_codes.csv"
|
||||
|
||||
###########################
|
||||
@@ -65,17 +65,17 @@ elif test $geoip_database = "city"; then
|
||||
download "$geoip_city_source" "City Database:"
|
||||
download "$geoip_region_source" "Region Database:"
|
||||
echo "Unpacking..."
|
||||
unzip -jo GeoLiteCity-latest.zip
|
||||
rm GeoLiteCity-latest.zip
|
||||
tar -xf GeoLiteCity-latest.tar.xz --strip-components 1
|
||||
rm GeoLiteCity-latest.tar.xz
|
||||
echo "Converting to utf-8..."
|
||||
iconv -f ISO-8859-1 -t UTF-8 GeoLiteCity-Blocks.csv -o $prefix"geoip_city_blocks.csv"
|
||||
iconv -f ISO-8859-1 -t UTF-8 GeoLiteCity-Location.csv -o $prefix"geoip_city_location.csv"
|
||||
iconv -f ISO-8859-1 -t UTF-8 region.csv -o $prefix"geoip_city_region.csv"
|
||||
rm GeoLiteCity-Blocks.csv GeoLiteCity-Location.csv region.csv
|
||||
iconv -f ISO-8859-1 -t UTF-8 region_codes.csv -o $prefix"geoip_city_region.csv"
|
||||
rm GeoLiteCity-Blocks.csv GeoLiteCity-Location.csv region_codes.csv
|
||||
echo "Importing..."
|
||||
mysqlimport --columns=start,end,locID --ignore-lines=2 $PARAMS $prefix"geoip_city_blocks.csv"
|
||||
mysqlimport --columns=locID,country,region,city,@x,latitude,longitude,@x,areaCode --ignore-lines=2 $PARAMS $prefix"geoip_city_location.csv"
|
||||
mysqlimport --columns=country,region,regionname $PARAMS $prefix"geoip_city_region.csv"
|
||||
rm $prefix"geoip_city_blocks.csv" $prefix"geoip_city_location.csv" $prefix"geoip_city_region.csv" $prefix"geoip_country6.csv"
|
||||
rm $prefix"geoip_city_blocks.csv" $prefix"geoip_city_location.csv" $prefix"geoip_city_region.csv"
|
||||
echo "Done..."
|
||||
fi
|
||||
|
||||
+14
-26
@@ -31,7 +31,8 @@ time_t MaxUserTime = 0;
|
||||
|
||||
std::list<User *> User::quitting_users;
|
||||
|
||||
User::User(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &uip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *account) : ip(uip)
|
||||
User::User(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &uip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const std::vector<Anope::string> &smodeparams, const Anope::string &suid, NickCore *account)
|
||||
: ip(uip)
|
||||
{
|
||||
if (snick.empty() || sident.empty() || shost.empty())
|
||||
throw CoreException("Bad args passed to User::User");
|
||||
@@ -49,7 +50,7 @@ User::User(const Anope::string &snick, const Anope::string &sident, const Anope:
|
||||
this->server = sserver;
|
||||
this->realname = srealname;
|
||||
this->timestamp = this->signon = ts;
|
||||
this->SetModesInternal(sserver, smodes);
|
||||
this->SetModesInternal(sserver, smodes, smodeparams);
|
||||
this->uid = suid;
|
||||
this->super_admin = false;
|
||||
this->nc = NULL;
|
||||
@@ -110,7 +111,7 @@ static void Collide(User *u, const Anope::string &id, const Anope::string &type)
|
||||
CollideKill(u, type);
|
||||
}
|
||||
|
||||
User *User::OnIntroduce(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc)
|
||||
User *User::OnIntroduce(const Anope::string &snick, const Anope::string &sident, const Anope::string &shost, const Anope::string &svhost, const Anope::string &sip, Server *sserver, const Anope::string &srealname, time_t ts, const Anope::string &smodes, const Anope::string &suid, NickCore *nc, const std::vector<Anope::string> &smodeparams)
|
||||
{
|
||||
// How IRCds handle collisions varies a lot, for safety well just always kill both sides
|
||||
// With properly set qlines, this can almost never happen anyway
|
||||
@@ -132,7 +133,7 @@ User *User::OnIntroduce(const Anope::string &snick, const Anope::string &sident,
|
||||
}
|
||||
}
|
||||
|
||||
return new User(snick, sident, shost, svhost, sip, sserver, srealname, ts, smodes, suid, nc);
|
||||
return new User(snick, sident, shost, svhost, sip, sserver, srealname, ts, smodes, smodeparams, suid, nc);
|
||||
}
|
||||
|
||||
void User::ChangeNick(const Anope::string &newnick, time_t ts)
|
||||
@@ -672,27 +673,14 @@ void User::SetModes(BotInfo *bi, const Anope::string &umodes)
|
||||
}
|
||||
}
|
||||
|
||||
void User::SetModesInternal(const MessageSource &source, const char *umodes, ...)
|
||||
{
|
||||
char buf[BUFSIZE] = "";
|
||||
va_list args;
|
||||
va_start(args, umodes);
|
||||
vsnprintf(buf, BUFSIZE - 1, umodes, args);
|
||||
va_end(args);
|
||||
|
||||
SetModesInternal(source, Anope::string(buf));
|
||||
}
|
||||
|
||||
void User::SetModesInternal(const MessageSource &source, const Anope::string &umodes)
|
||||
void User::SetModesInternal(const MessageSource &source, const Anope::string &umodes, const std::vector<Anope::string> &umodeparams)
|
||||
{
|
||||
if (this->server && this->server->IsSynced() && Anope::string(umodes) != "+")
|
||||
Log(this, "mode") << "changes modes to " << umodes;
|
||||
|
||||
int add = -1;
|
||||
Anope::string modebuf;
|
||||
spacesepstream sep(umodes);
|
||||
sep.GetToken(modebuf);
|
||||
for (auto mode : modebuf)
|
||||
auto paramit = umodeparams.begin();
|
||||
for (const auto mode : umodes)
|
||||
{
|
||||
UserMode *um;
|
||||
|
||||
@@ -715,8 +703,8 @@ void User::SetModesInternal(const MessageSource &source, const Anope::string &um
|
||||
if (add)
|
||||
{
|
||||
Anope::string sbuf;
|
||||
if (um->type == MODE_PARAM && sep.GetToken(sbuf))
|
||||
this->SetModeInternal(source, um, sbuf);
|
||||
if (um->type == MODE_PARAM && paramit != umodeparams.end())
|
||||
this->SetModeInternal(source, um, *paramit++);
|
||||
else
|
||||
this->SetModeInternal(source, um);
|
||||
}
|
||||
@@ -851,10 +839,10 @@ bool User::BadPassword()
|
||||
bool User::ShouldPrivmsg() const
|
||||
{
|
||||
// Send a PRIVMSG instead of a NOTICE if:
|
||||
// 1. options:useprivmsg is enabled.
|
||||
// 2. The user is not registered and msg is in nickserv:defaults.
|
||||
// 3. The user is registered and has set /ns set message on.
|
||||
return Config->UsePrivmsg && ((!nc && Config->DefPrivmsg) || (nc && nc->HasExt("MSG")));
|
||||
// 1. The user is not registered and msg is in nickserv:defaults.
|
||||
// 2. The user is registered and has set /ns set message on.
|
||||
static ExtensibleRef<bool> msg("MSG");
|
||||
return (!nc && Config->DefPrivmsg) || (nc && msg && msg->HasExt(nc));
|
||||
}
|
||||
|
||||
User *User::Find(const Anope::string &name, bool nick_only)
|
||||
|
||||
+1
-1
@@ -2,5 +2,5 @@
|
||||
|
||||
VERSION_MAJOR=2
|
||||
VERSION_MINOR=1
|
||||
VERSION_PATCH=9
|
||||
VERSION_PATCH=10
|
||||
VERSION_EXTRA=""
|
||||
|
||||
Reference in New Issue
Block a user