[3.12] gh-113171: gh-65056: Fix "private" (non-global) IP address ranges (GH-113179) (GH-113186) (GH-118177)

* GH-113171: Fix "private" (non-global) IP address ranges (GH-113179)

The _private_networks variables, used by various is_private
implementations, were missing some ranges and at the same time had
overly strict ranges (where there are more specific ranges considered
globally reachable by the IANA registries).

This patch updates the ranges with what was missing or otherwise
incorrect.

100.64.0.0/10 is left alone, for now, as it's been made special in [1].

The _address_exclude_many() call returns 8 networks for IPv4, 121
networks for IPv6.

[1] https://github.com/python/cpython/issues/61602

* GH-65056: Improve the IP address' is_global/is_private documentation (GH-113186)

It wasn't clear what the semantics of is_global/is_private are and, when
one gets to the bottom of it, it's not quite so simple (hence the
exceptions listed).

(cherry picked from commit 2a4cbf17af)
(cherry picked from commit 40d75c2b7f)

---------

Co-authored-by: Jakub Stasiak <jakub@stasiak.at>
This commit is contained in:
Petr Viktorin 2024-04-24 14:29:30 +02:00 committed by GitHub
parent 2eaf9ba9ce
commit f86b17ac51
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
5 changed files with 157 additions and 24 deletions

View file

@ -2269,6 +2269,10 @@ class IpaddrUnitTest(unittest.TestCase):
self.assertEqual(True, ipaddress.ip_address(
'172.31.255.255').is_private)
self.assertEqual(False, ipaddress.ip_address('172.32.0.0').is_private)
self.assertFalse(ipaddress.ip_address('192.0.0.0').is_global)
self.assertTrue(ipaddress.ip_address('192.0.0.9').is_global)
self.assertTrue(ipaddress.ip_address('192.0.0.10').is_global)
self.assertFalse(ipaddress.ip_address('192.0.0.255').is_global)
self.assertEqual(True,
ipaddress.ip_address('169.254.100.200').is_link_local)
@ -2294,6 +2298,7 @@ class IpaddrUnitTest(unittest.TestCase):
self.assertEqual(True, ipaddress.ip_network("169.254.0.0/16").is_private)
self.assertEqual(True, ipaddress.ip_network("172.16.0.0/12").is_private)
self.assertEqual(True, ipaddress.ip_network("192.0.0.0/29").is_private)
self.assertEqual(False, ipaddress.ip_network("192.0.0.9/32").is_private)
self.assertEqual(True, ipaddress.ip_network("192.0.0.170/31").is_private)
self.assertEqual(True, ipaddress.ip_network("192.0.2.0/24").is_private)
self.assertEqual(True, ipaddress.ip_network("192.168.0.0/16").is_private)
@ -2310,8 +2315,8 @@ class IpaddrUnitTest(unittest.TestCase):
self.assertEqual(True, ipaddress.ip_network("::/128").is_private)
self.assertEqual(True, ipaddress.ip_network("::ffff:0:0/96").is_private)
self.assertEqual(True, ipaddress.ip_network("100::/64").is_private)
self.assertEqual(True, ipaddress.ip_network("2001::/23").is_private)
self.assertEqual(True, ipaddress.ip_network("2001:2::/48").is_private)
self.assertEqual(False, ipaddress.ip_network("2001:3::/48").is_private)
self.assertEqual(True, ipaddress.ip_network("2001:db8::/32").is_private)
self.assertEqual(True, ipaddress.ip_network("2001:10::/28").is_private)
self.assertEqual(True, ipaddress.ip_network("fc00::/7").is_private)
@ -2390,6 +2395,20 @@ class IpaddrUnitTest(unittest.TestCase):
self.assertEqual(True, ipaddress.ip_address('0::0').is_unspecified)
self.assertEqual(False, ipaddress.ip_address('::1').is_unspecified)
self.assertFalse(ipaddress.ip_address('64:ff9b:1::').is_global)
self.assertFalse(ipaddress.ip_address('2001::').is_global)
self.assertTrue(ipaddress.ip_address('2001:1::1').is_global)
self.assertTrue(ipaddress.ip_address('2001:1::2').is_global)
self.assertFalse(ipaddress.ip_address('2001:2::').is_global)
self.assertTrue(ipaddress.ip_address('2001:3::').is_global)
self.assertFalse(ipaddress.ip_address('2001:4::').is_global)
self.assertTrue(ipaddress.ip_address('2001:4:112::').is_global)
self.assertFalse(ipaddress.ip_address('2001:10::').is_global)
self.assertTrue(ipaddress.ip_address('2001:20::').is_global)
self.assertTrue(ipaddress.ip_address('2001:30::').is_global)
self.assertFalse(ipaddress.ip_address('2001:40::').is_global)
self.assertFalse(ipaddress.ip_address('2002::').is_global)
# some generic IETF reserved addresses
self.assertEqual(True, ipaddress.ip_address('100::').is_reserved)
self.assertEqual(True, ipaddress.ip_network('4000::1/128').is_reserved)