Skip to content

Commit

Permalink
Normalize IPv6 used in Endpoint.equivalent C# and C++ (#3428)
Browse files Browse the repository at this point in the history
  • Loading branch information
pepone authored Jan 28, 2025
1 parent e2a8f14 commit 78506e7
Show file tree
Hide file tree
Showing 5 changed files with 58 additions and 3 deletions.
10 changes: 8 additions & 2 deletions cpp/src/Ice/IPEndpointI.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -116,7 +116,8 @@ IceInternal::IPEndpointI::equivalent(const EndpointIPtr& endpoint) const
{
return false;
}
return ipEndpointI->type() == type() && ipEndpointI->_host == _host && ipEndpointI->_port == _port;
return ipEndpointI->type() == type() && ipEndpointI->_normalizedHost == _normalizedHost &&
ipEndpointI->_port == _port;
}

size_t
Expand Down Expand Up @@ -306,12 +307,14 @@ IceInternal::IPEndpointI::initWithOptions(vector<string>& args, bool oaEndpoint)
if (_host.empty())
{
const_cast<string&>(_host) = _instance->defaultHost();
const_cast<string&>(_normalizedHost) = normalizeIPv6Address(_host);
}
else if (_host == "*")
{
if (oaEndpoint)
{
const_cast<string&>(_host) = string();
const_cast<string&>(_host) = string{};
const_cast<string&>(_normalizedHost) = string{};
}
else
{
Expand Down Expand Up @@ -348,6 +351,7 @@ IceInternal::IPEndpointI::checkOption(const string& option, const string& argume
"no argument provided for -h option in endpoint '" + endpoint + "'");
}
const_cast<string&>(_host) = argument;
const_cast<string&>(_normalizedHost) = normalizeIPv6Address(_host);
}
else if (option == "-p")
{
Expand Down Expand Up @@ -407,6 +411,7 @@ IceInternal::IPEndpointI::IPEndpointI(
string connectionId)
: _instance(std::move(instance)),
_host(std::move(host)),
_normalizedHost(normalizeIPv6Address(_host)),
_port(port),
_sourceAddr(sourceAddr),
_connectionId(std::move(connectionId))
Expand All @@ -420,6 +425,7 @@ IceInternal::IPEndpointI::IPEndpointI(ProtocolInstancePtr instance, InputStream*
_port(0)
{
s->read(const_cast<string&>(_host), false);
const_cast<string&>(_normalizedHost) = normalizeIPv6Address(_host);
s->read(const_cast<int32_t&>(_port));
}

Expand Down
1 change: 1 addition & 0 deletions cpp/src/Ice/IPEndpointI.h
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ namespace IceInternal

const ProtocolInstancePtr _instance;
const std::string _host;
const std::string _normalizedHost;
const int _port;
const Address _sourceAddr;
const std::string _connectionId;
Expand Down
21 changes: 21 additions & 0 deletions cpp/src/Ice/Network.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1563,6 +1563,27 @@ IceInternal::getNumericAddress(const std::string& address)
}
}

string
IceInternal::normalizeIPv6Address(const string& host)
{
if (host.find(':') != string::npos)
{
struct in6_addr result;
if (inet_pton(AF_INET6, host.c_str(), &result) == 1)
{
// Normalize the address
char buf[INET6_ADDRSTRLEN];
if (inet_ntop(AF_INET6, &result, buf, sizeof(buf)) != nullptr)
{
return string{buf};
}
// else conversion to string failed, keep host as is
}
// else it's not a valid IPv6 address keep host as is
}
return host;
}

SyscallException::ErrorCode
IceInternal::getSocketErrno()
{
Expand Down
1 change: 1 addition & 0 deletions cpp/src/Ice/Network.h
Original file line number Diff line number Diff line change
Expand Up @@ -249,6 +249,7 @@ namespace IceInternal
ICE_API Ice::SyscallException::ErrorCode getSocketErrno();

ICE_API Address getNumericAddress(const std::string&);
ICE_API std::string normalizeIPv6Address(const std::string&);

#if defined(ICE_USE_IOCP)
ICE_API void doConnectAsync(SOCKET, const Address&, const Address&, AsyncInfo&);
Expand Down
28 changes: 27 additions & 1 deletion csharp/src/Ice/Internal/IPEndpointI.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ protected IPEndpointI(ProtocolInstance instance, string host, int port, EndPoint
{
instance_ = instance;
host_ = host;
_normalizedHost = normalizeHost(host_);
port_ = port;
sourceAddr_ = sourceAddr;
connectionId_ = connectionId;
Expand All @@ -20,6 +21,7 @@ protected IPEndpointI(ProtocolInstance instance)
{
instance_ = instance;
host_ = null;
_normalizedHost = null;
port_ = 0;
sourceAddr_ = null;
connectionId_ = "";
Expand All @@ -29,6 +31,7 @@ protected IPEndpointI(ProtocolInstance instance, Ice.InputStream s)
{
instance_ = instance;
host_ = s.readString();
_normalizedHost = normalizeHost(host_);
port_ = s.readInt();
sourceAddr_ = null;
connectionId_ = "";
Expand Down Expand Up @@ -117,7 +120,7 @@ public override bool equivalent(EndpointI endpoint)
}
IPEndpointI ipEndpointI = (IPEndpointI)endpoint;
return ipEndpointI.type() == type() &&
ipEndpointI.host_.Equals(host_, StringComparison.Ordinal) &&
ipEndpointI._normalizedHost == _normalizedHost &&
ipEndpointI.port_ == port_;
}

Expand Down Expand Up @@ -245,12 +248,14 @@ public virtual void initWithOptions(List<string> args, bool oaEndpoint)
if (host_ == null || host_.Length == 0)
{
host_ = instance_.defaultHost();
_normalizedHost = normalizeHost(host_);
}
else if (host_ == "*")
{
if (oaEndpoint)
{
host_ = "";
_normalizedHost = "";
}
else
{
Expand All @@ -261,6 +266,7 @@ public virtual void initWithOptions(List<string> args, bool oaEndpoint)
if (host_ == null)
{
host_ = "";
_normalizedHost = normalizeHost(host_);
}

if (sourceAddr_ != null)
Expand All @@ -285,6 +291,7 @@ protected override bool checkOption(string option, string argument, string endpo
throw new ParseException($"no argument provided for -h option in endpoint '{endpoint}'");
}
host_ = argument;
_normalizedHost = normalizeHost(host_);
}
else if (option == "-p")
{
Expand Down Expand Up @@ -327,6 +334,23 @@ protected override bool checkOption(string option, string argument, string endpo
return true;
}

private static string normalizeHost(string host)
{
if (host is not null && host.Contains(':', StringComparison.Ordinal))
{
// Could be an IPv6 address that we need to normalize.
try
{
return IPAddress.Parse(host).ToString(); // normalized host
}
catch
{
// Ignore - don't normalize host.
}
}
return host;
}

protected abstract Connector createConnector(EndPoint addr, NetworkProxy proxy);

protected abstract IPEndpointI createEndpoint(string host, int port, string connectionId);
Expand All @@ -336,4 +360,6 @@ protected override bool checkOption(string option, string argument, string endpo
protected int port_;
protected EndPoint sourceAddr_;
protected string connectionId_;
// Set when we set _host; used by the implementation of equivalent.
private string _normalizedHost;
}

0 comments on commit 78506e7

Please sign in to comment.