mirror of
https://github.com/inspircd/inspircd.git
synced 2025-03-10 02:59:01 -04:00
Add support for multiple hostmasks in <cgiirc:mask>.
This commit is contained in:
parent
79cc3caeb8
commit
744efed4e2
@ -375,14 +375,14 @@
|
||||
# message to the server on connection. For more details please read the
|
||||
# IRCv3 WebIRC specification at: https://ircv3.net/specs/extensions/webirc.html
|
||||
#
|
||||
# When using this method you must specify a wildcard mask or CIDR range
|
||||
# to allow gateway connections from and at least one of either a TLS (SSL)
|
||||
# client certificate fingerprint for the gateway or a password to be
|
||||
# sent in the WEBIRC command.
|
||||
# When using this method you must specify one or more wildcard masks
|
||||
# or CIDR ranges to allow gateway connections from and at least one of
|
||||
# either a TLS (SSL) client certificate fingerprint for the gateway or
|
||||
# a password to be sent in the WEBIRC command.
|
||||
#
|
||||
# <cgihost type="webirc"
|
||||
# fingerprint="bd90547b59c1942b85f382bc059318f4c6ca54c5"
|
||||
# mask="192.0.2.0/24">
|
||||
# mask="192.0.2.0/24 198.51.100.*">
|
||||
# <cgihost type="webirc"
|
||||
# password="$2a$10$WEUpX9GweJiEF1WxBDSkeODBstIBMlVPweQTG9cKM8/Vd58BeM5cW"
|
||||
# hash="bcrypt"
|
||||
@ -393,13 +393,14 @@
|
||||
# address in the ident sent by the user. This is not recommended as it
|
||||
# only works with IPv4 connections.
|
||||
#
|
||||
# When using this method you must specify a wildcard mask or CIDR range to allow
|
||||
# gateway connections from. You can also optionally configure the static value
|
||||
# that replaces the IP in the ident to avoid leaking the real IP address of
|
||||
# gateway clients (defaults to "gateway" if not set).
|
||||
# When using this method you must specify one or more wildcard masks
|
||||
# or CIDR ranges to allow gateway connections from. You can also
|
||||
# optionally configure the static value that replaces the IP in the
|
||||
# ident to avoid leaking the real IP address of gateway clients
|
||||
# (defaults to "gateway" if not set).
|
||||
#
|
||||
# <cgihost type="ident"
|
||||
# mask="198.51.100.0/24"
|
||||
# mask="198.51.100.0/24 203.0.113.*"
|
||||
# newident="wibble">
|
||||
# <cgihost type="ident"
|
||||
# mask="*.ident.gateway.example.com"
|
||||
|
@ -39,16 +39,19 @@ enum
|
||||
RPL_WHOISGATEWAY = 350
|
||||
};
|
||||
|
||||
// One or more hostmask globs or CIDR ranges.
|
||||
typedef std::vector<std::string> MaskList;
|
||||
|
||||
// Encapsulates information about an ident host.
|
||||
class IdentHost
|
||||
{
|
||||
private:
|
||||
std::string hostmask;
|
||||
MaskList hostmasks;
|
||||
std::string newident;
|
||||
|
||||
public:
|
||||
IdentHost(const std::string& mask, const std::string& ident)
|
||||
: hostmask(mask)
|
||||
IdentHost(const MaskList& masks, const std::string& ident)
|
||||
: hostmasks(masks)
|
||||
, newident(ident)
|
||||
{
|
||||
}
|
||||
@ -60,10 +63,19 @@ class IdentHost
|
||||
|
||||
bool Matches(LocalUser* user) const
|
||||
{
|
||||
if (!InspIRCd::Match(user->GetRealHost(), hostmask, ascii_case_insensitive_map))
|
||||
return false;
|
||||
for (MaskList::const_iterator iter = hostmasks.begin(); iter != hostmasks.end(); ++iter)
|
||||
{
|
||||
// Does the user's hostname match this hostmask?
|
||||
if (InspIRCd::Match(user->GetRealHost(), *iter, ascii_case_insensitive_map))
|
||||
return true;
|
||||
|
||||
return InspIRCd::MatchCIDR(user->GetIPString(), hostmask, ascii_case_insensitive_map);
|
||||
// Does the user's IP address match this hostmask?
|
||||
if (InspIRCd::MatchCIDR(user->GetIPString(), *iter, ascii_case_insensitive_map))
|
||||
return true;
|
||||
}
|
||||
|
||||
// The user didn't match any hostmasks.
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
@ -71,14 +83,14 @@ class IdentHost
|
||||
class WebIRCHost
|
||||
{
|
||||
private:
|
||||
std::string hostmask;
|
||||
MaskList hostmasks;
|
||||
std::string fingerprint;
|
||||
std::string password;
|
||||
std::string passhash;
|
||||
|
||||
public:
|
||||
WebIRCHost(const std::string& mask, const std::string& fp, const std::string& pass, const std::string& hash)
|
||||
: hostmask(mask)
|
||||
WebIRCHost(const MaskList& masks, const std::string& fp, const std::string& pass, const std::string& hash)
|
||||
: hostmasks(masks)
|
||||
, fingerprint(fp)
|
||||
, password(pass)
|
||||
, passhash(hash)
|
||||
@ -96,26 +108,22 @@ class WebIRCHost
|
||||
if (!fingerprint.empty() && !InspIRCd::TimingSafeCompare(fp, fingerprint))
|
||||
return false;
|
||||
|
||||
// Does the user's hostname match our hostmask?
|
||||
if (InspIRCd::Match(user->GetRealHost(), hostmask, ascii_case_insensitive_map))
|
||||
return true;
|
||||
for (MaskList::const_iterator iter = hostmasks.begin(); iter != hostmasks.end(); ++iter)
|
||||
{
|
||||
// Does the user's hostname match this hostmask?
|
||||
if (InspIRCd::Match(user->GetRealHost(), *iter, ascii_case_insensitive_map))
|
||||
return true;
|
||||
|
||||
// Does the user's IP address match our hostmask?
|
||||
return InspIRCd::MatchCIDR(user->GetIPString(), hostmask, ascii_case_insensitive_map);
|
||||
// Does the user's IP address match this hostmask?
|
||||
if (InspIRCd::MatchCIDR(user->GetIPString(), *iter, ascii_case_insensitive_map))
|
||||
return true;
|
||||
}
|
||||
|
||||
// The user didn't match any hostmasks.
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
/*
|
||||
* WEBIRC
|
||||
* This is used for the webirc method of CGIIRC auth, and is (really) the best way to do these things.
|
||||
* Syntax: WEBIRC password gateway hostname ip
|
||||
* Where password is a shared key, gateway is the name of the WebIRC gateway and version (e.g. cgiirc), hostname
|
||||
* is the resolved host of the client issuing the command and IP is the real IP of the client.
|
||||
*
|
||||
* How it works:
|
||||
* To tie in with the rest of cgiirc module, and to avoid race conditions, /webirc is only processed locally
|
||||
* and simply sets metadata on the user, which is later decoded on full connect to give something meaningful.
|
||||
*/
|
||||
class CommandWebIRC : public SplitCommand
|
||||
{
|
||||
public:
|
||||
@ -289,9 +297,13 @@ class ModuleCgiIRC
|
||||
{
|
||||
ConfigTag* tag = i->second;
|
||||
|
||||
MaskList masks;
|
||||
irc::spacesepstream maskstream(tag->getString("mask"));
|
||||
for (std::string mask; maskstream.GetToken(mask); )
|
||||
masks.push_back(mask);
|
||||
|
||||
// Ensure that we have the <cgihost:mask> parameter.
|
||||
const std::string mask = tag->getString("mask");
|
||||
if (mask.empty())
|
||||
if (masks.empty())
|
||||
throw ModuleException("<cgihost:mask> is a mandatory field, at " + tag->getTagLocation());
|
||||
|
||||
// Determine what lookup type this host uses.
|
||||
@ -300,7 +312,7 @@ class ModuleCgiIRC
|
||||
{
|
||||
// The IP address should be looked up from the hex IP address.
|
||||
const std::string newident = tag->getString("newident", "gateway", ServerInstance->IsIdent);
|
||||
identhosts.push_back(IdentHost(mask, newident));
|
||||
identhosts.push_back(IdentHost(masks, newident));
|
||||
}
|
||||
else if (stdalgo::string::equalsci(type, "webirc"))
|
||||
{
|
||||
@ -319,7 +331,7 @@ class ModuleCgiIRC
|
||||
tag->getTagLocation().c_str());
|
||||
}
|
||||
|
||||
webirchosts.push_back(WebIRCHost(mask, fingerprint, password, passwordhash));
|
||||
webirchosts.push_back(WebIRCHost(masks, fingerprint, password, passwordhash));
|
||||
}
|
||||
else
|
||||
{
|
||||
|
Loading…
x
Reference in New Issue
Block a user