Skip to content

Commit

Permalink
[3.7] bpo-41004: Resolve hash collisions for IPv4Interface and IPv6In…
Browse files Browse the repository at this point in the history
…terface (GH-21033) (GH-21231)

CVE-2020-14422
The __hash__() methods of classes IPv4Interface and IPv6Interface had issue
of generating constant hash values of 32 and 128 respectively causing hash collisions.
The fix uses the hash() function to generate hash values for the objects
instead of XOR operation
(cherry picked from commit b30ee26)

Co-authored-by: Ravi Teja P <rvteja92@gmail.com>

Signed-off-by: Tapas Kundu <tkundu@vmware.com>
  • Loading branch information
tapakund committed Jun 30, 2020
1 parent 4fdc175 commit b98e779
Show file tree
Hide file tree
Showing 3 changed files with 14 additions and 2 deletions.
4 changes: 2 additions & 2 deletions Lib/ipaddress.py
Expand Up @@ -1442,7 +1442,7 @@ def __lt__(self, other):
return False

def __hash__(self):
return self._ip ^ self._prefixlen ^ int(self.network.network_address)
return hash((self._ip, self._prefixlen, int(self.network.network_address)))

__reduce__ = _IPAddressBase.__reduce__

Expand Down Expand Up @@ -2088,7 +2088,7 @@ def __lt__(self, other):
return False

def __hash__(self):
return self._ip ^ self._prefixlen ^ int(self.network.network_address)
return hash((self._ip, self._prefixlen, int(self.network.network_address)))

__reduce__ = _IPAddressBase.__reduce__

Expand Down
11 changes: 11 additions & 0 deletions Lib/test/test_ipaddress.py
Expand Up @@ -2091,6 +2091,17 @@ def testsixtofour(self):
sixtofouraddr.sixtofour)
self.assertFalse(bad_addr.sixtofour)

# issue41004 Hash collisions in IPv4Interface and IPv6Interface
def testV4HashIsNotConstant(self):
ipv4_address1 = ipaddress.IPv4Interface("1.2.3.4")
ipv4_address2 = ipaddress.IPv4Interface("2.3.4.5")
self.assertNotEqual(ipv4_address1.__hash__(), ipv4_address2.__hash__())

# issue41004 Hash collisions in IPv4Interface and IPv6Interface
def testV6HashIsNotConstant(self):
ipv6_address1 = ipaddress.IPv6Interface("2001:658:22a:cafe:200:0:0:1")
ipv6_address2 = ipaddress.IPv6Interface("2001:658:22a:cafe:200:0:0:2")
self.assertNotEqual(ipv6_address1.__hash__(), ipv6_address2.__hash__())

if __name__ == '__main__':
unittest.main()
@@ -0,0 +1 @@
CVE-2020-14422: The __hash__() methods of ipaddress.IPv4Interface and ipaddress.IPv6Interface incorrectly generated constant hash values of 32 and 128 respectively. This resulted in always causing hash collisions. The fix uses hash() to generate hash values for the tuple of (address, mask length, network address).

0 comments on commit b98e779

Please sign in to comment.