From 4b9d09e95d36fcc4d1aa272c1fb4ea823b58d197 Mon Sep 17 00:00:00 2001 From: wfurt Date: Wed, 12 Jun 2024 15:24:47 -0700 Subject: [PATCH 1/2] match IPv4MappedToIPv6 address in IPv4 networks --- .../System.Net.Primitives/src/System/Net/IPAddress.cs | 9 +++++++-- .../System.Net.Primitives/src/System/Net/IPNetwork.cs | 4 ++-- .../tests/FunctionalTests/IPNetworkTest.cs | 2 ++ 3 files changed, 11 insertions(+), 4 deletions(-) diff --git a/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs b/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs index 48f424407b400c..718602b94bc5d9 100644 --- a/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs +++ b/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs @@ -74,8 +74,13 @@ internal uint PrivateAddress { get { - Debug.Assert(IsIPv4); - return _addressOrScopeId; + Debug.Assert(IsIPv4 || IsIPv4MappedToIPv6); + if (IsIPv4) + { + return _addressOrScopeId; + } + uint address = (uint)_numbers[6] << 16 | (uint)_numbers[7]; + return (uint)HostToNetworkOrder(unchecked((int)address)); } private set { diff --git a/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs b/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs index 1c3a3acd42932e..f7c572a399e809 100644 --- a/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs +++ b/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs @@ -84,7 +84,7 @@ public bool Contains(IPAddress address) { ArgumentNullException.ThrowIfNull(address); - if (address.AddressFamily != BaseAddress.AddressFamily) + if (address.AddressFamily != BaseAddress.AddressFamily && (BaseAddress.AddressFamily != AddressFamily.InterNetwork || !address.IsIPv4MappedToIPv6)) { return false; } @@ -95,7 +95,7 @@ public bool Contains(IPAddress address) return true; } - if (address.AddressFamily == AddressFamily.InterNetwork) + if (address.AddressFamily == AddressFamily.InterNetwork || address.IsIPv4MappedToIPv6) { uint mask = uint.MaxValue << (32 - PrefixLength); if (BitConverter.IsLittleEndian) diff --git a/src/libraries/System.Net.Primitives/tests/FunctionalTests/IPNetworkTest.cs b/src/libraries/System.Net.Primitives/tests/FunctionalTests/IPNetworkTest.cs index 6688b7a7864343..4c56e2d709e346 100644 --- a/src/libraries/System.Net.Primitives/tests/FunctionalTests/IPNetworkTest.cs +++ b/src/libraries/System.Net.Primitives/tests/FunctionalTests/IPNetworkTest.cs @@ -151,10 +151,12 @@ public void Contains_DifferentAddressFamily_ReturnsFalse() [Theory] [InlineData("0.0.0.0/0", "0.0.0.0", "127.127.127.127", "255.255.255.255")] // the whole IPv4 space + [InlineData("0.0.0.0/0", "0.0.0.0", "::ffff:127.127.127.127", "::ffff:255.255.255.255")] // the whole IPv4 space [InlineData("::/0", "::", "ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff")] // the whole IPv6 space [InlineData("255.255.255.255/32", "255.255.255.255")] // single IPv4 address [InlineData("ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff/128", "ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff")] // single IPv6 address [InlineData("255.255.255.0/24", "255.255.255.0", "255.255.255.255")] + [InlineData("255.255.255.0/24", "::ffff:255.255.255.0", "::ffff:255.255.255.255")] [InlineData("198.51.248.0/22", "198.51.248.0", "198.51.250.42", "198.51.251.255")] [InlineData("255.255.255.128/25", "255.255.255.128", "255.255.255.129", "255.255.255.255")] [InlineData("2a00::/13", "2a00::", "2a00::1", "2a01::", "2a07::", "2a07:ffff:ffff:ffff:ffff:ffff:ffff:ffff")] From 206bee022cbdfbbcefe89a2f2d6c360950dcdf14 Mon Sep 17 00:00:00 2001 From: wfurt Date: Fri, 14 Jun 2024 19:40:32 +0000 Subject: [PATCH 2/2] feedback --- .../src/System/Net/IPAddress.cs | 23 +++++++++++++------ .../src/System/Net/IPNetwork.cs | 2 +- 2 files changed, 17 insertions(+), 8 deletions(-) diff --git a/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs b/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs index 718602b94bc5d9..cf45264cf0d30d 100644 --- a/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs +++ b/src/libraries/System.Net.Primitives/src/System/Net/IPAddress.cs @@ -74,13 +74,8 @@ internal uint PrivateAddress { get { - Debug.Assert(IsIPv4 || IsIPv4MappedToIPv6); - if (IsIPv4) - { - return _addressOrScopeId; - } - uint address = (uint)_numbers[6] << 16 | (uint)_numbers[7]; - return (uint)HostToNetworkOrder(unchecked((int)address)); + Debug.Assert(IsIPv4); + return _addressOrScopeId; } private set { @@ -91,6 +86,20 @@ private set } } + internal uint PrivateIPv4Address + { + get + { + Debug.Assert(IsIPv4 || IsIPv4MappedToIPv6); + if (IsIPv4) + { + return _addressOrScopeId; + } + uint address = (uint)_numbers[6] << 16 | (uint)_numbers[7]; + return (uint)HostToNetworkOrder(unchecked((int)address)); + } + } + private uint PrivateScopeId { get diff --git a/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs b/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs index f7c572a399e809..b57cc93126aa1e 100644 --- a/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs +++ b/src/libraries/System.Net.Primitives/src/System/Net/IPNetwork.cs @@ -103,7 +103,7 @@ public bool Contains(IPAddress address) mask = BinaryPrimitives.ReverseEndianness(mask); } - return BaseAddress.PrivateAddress == (address.PrivateAddress & mask); + return BaseAddress.PrivateIPv4Address == (address.PrivateIPv4Address & mask); } else {