Skip to content

Commit

Permalink
Merge pull request #128 from jagerman/fix-addr-less-than
Browse files Browse the repository at this point in the history
Add three-way operator to Address and fix port order
  • Loading branch information
jagerman committed May 10, 2024
2 parents 17d6695 + fa56748 commit f4b75ec
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 33 deletions.
46 changes: 13 additions & 33 deletions include/oxen/quic/address.hpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
#pragma once

#include <oxenc/endian.h>

#include <compare>

#include "formattable.hpp"
#include "ip.hpp"
#include "utils.hpp"
Expand Down Expand Up @@ -232,52 +236,28 @@ namespace oxen::quic
return &_addr;
}

bool operator==(const Address& other) const
auto operator<=>(const Address& other) const
{
if (is_ipv4() && other.is_ipv4())
{
auto& a = in4();
auto& b = other.in4();
return a.sin_port == b.sin_port &&
memcmp(&a.sin_addr.s_addr, &b.sin_addr.s_addr, sizeof(a.sin_addr.s_addr)) == 0;
if (auto r = memcmp(&a.sin_addr.s_addr, &b.sin_addr.s_addr, sizeof(a.sin_addr.s_addr)); r != 0)
return r <=> 0;
return oxenc::big_to_host(a.sin_port) <=> oxenc::big_to_host(b.sin_port);
}
if (is_ipv6() && other.is_ipv6())
{
auto& a = in6();
auto& b = other.in6();
return a.sin6_port == b.sin6_port &&
memcmp(a.sin6_addr.s6_addr, b.sin6_addr.s6_addr, sizeof(a.sin6_addr.s6_addr)) == 0;
}
return false;
}

bool operator<(const Address& other) const
{
if (is_ipv4() && other.is_ipv4())
{
auto& a = in4();
auto& b = other.in4();

if (auto r = memcmp(&a.sin_addr.s_addr, &b.sin_addr.s_addr, sizeof(a.sin_addr.s_addr)); r == 0)
return a.sin_port < b.sin_port;
else
return (r < 0);
}
if (is_ipv6() && other.is_ipv6())
{
auto& a = in6();
auto& b = other.in6();

if (auto r = memcmp(a.sin6_addr.s6_addr, b.sin6_addr.s6_addr, sizeof(a.sin6_addr.s6_addr)); r == 0)
return a.sin6_port < b.sin6_port;
else
return (r < 0);
if (auto r = memcmp(a.sin6_addr.s6_addr, b.sin6_addr.s6_addr, sizeof(a.sin6_addr.s6_addr)); r != 0)
return r <=> 0;
return oxenc::big_to_host(a.sin6_port) <=> oxenc::big_to_host(b.sin6_port);
}
if (is_ipv6() && other.is_ipv4())
return false;
return true;
return is_ipv6() <=> other.is_ipv6();
}

bool operator==(const Address& other) const { return (*this <=> other) == 0; }
bool operator!=(const Address& other) const { return !(*this == other); }

// Returns the size of the sockaddr
Expand Down
8 changes: 8 additions & 0 deletions tests/001-handshake.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,14 @@ namespace oxen::quic::test
CHECK_FALSE(public_ipv6.is_any_port());
CHECK(public_ipv6.is_addressable());
CHECK_FALSE(public_ipv6.is_loopback());

CHECK(Address{"127.0.0.1", 2} < Address{"127.0.0.1", 256});
CHECK(Address{"127.0.0.1", 256} < Address{"127.0.0.2", 2});
CHECK(Address{"127.0.0.1", 256} < public_ipv6);
CHECK(Address{"127.0.0.1", 2} == Address{"127.0.0.1", 2});
CHECK(Address{"127.0.0.1", 256} > Address{"127.0.0.1", 2});
CHECK(Address{"127.0.0.1", 256} <= public_ipv6);
CHECK(public_ipv6 >= Address{"127.0.0.1", 256});
}

SECTION("IP Address Ranges", "[range][operators][ipaddr]")
Expand Down

0 comments on commit f4b75ec

Please sign in to comment.