Commit d23a59db authored by Dominik Charousset's avatar Dominik Charousset

Replace mask/masked with network_address

The mutating `mask` essentially computed the network address. Giving
this operation a proper name makes code much more readable.
parent 45cdea3d
......@@ -52,23 +52,22 @@ public:
return memcmp(buf.data(), other.bytes().data(), Derived::num_bytes);
}
// -- mutators ---------------------------------------------------------------
/// Masks out lower bytes of the address. For example, calling `mask(1)` on
/// the IPv4 address `192.168.1.1` would produce `192.0.0.0`.
/// @pre `bytes_to_keep < num_bytes`
void mask(int bytes_to_keep) noexcept {
auto& buf = dref().bytes();
memset(buf.data() + bytes_to_keep, 0, Derived::num_bytes - bytes_to_keep);
}
/// Returns a copy of this address with that masks out lower bytes. For
/// example, calling `masked(1)` on the IPv4 address `192.168.1.1` would
/// return `192.0.0.0`.
/// @pre `bytes_to_keep < num_bytes`
Derived masked(int bytes_to_keep) const noexcept {
// -- transformations --------------------------------------------------------
Derived network_address(size_t prefix_length) const noexcept {
static constexpr uint8_t netmask_tbl[] = {0x00, 0x80, 0xC0, 0xE0,
0xF0, 0xF8, 0xFC, 0xFE};
prefix_length = std::min(prefix_length, Derived::num_bytes * 8);
Derived netmask;
auto bytes_to_keep = prefix_length / 8;
auto remainder = prefix_length % 8;
size_t i = 0;
for (; i < bytes_to_keep; ++i)
netmask[i] = 0xFF;
if (remainder != 0)
netmask[i] = netmask_tbl[remainder];
Derived result{dref()};
result.mask(bytes_to_keep);
result &= netmask;
return result;
}
......
......@@ -92,6 +92,13 @@ public:
return bytes_.size();
}
// -- inspection -------------------------------------------------------------
template <class Inspector>
friend typename Inspector::result_type inspect(Inspector& f, ipv4_address& x) {
return f(x.bits_);
}
private:
// -- member variables -------------------------------------------------------
......
......@@ -64,11 +64,17 @@ CAF_TEST(properties) {
CAF_CHECK_EQUAL(addr(224, 0, 0, 254).is_multicast(), true);
CAF_CHECK_EQUAL(addr(224, 0, 1, 1).is_multicast(), true);
CAF_CHECK_EQUAL(addr(225, 0, 0, 1).is_multicast(), false);
CAF_CHECK_EQUAL(addr(1, 2, 3, 4).masked(0), addr(0, 0, 0, 0));
CAF_CHECK_EQUAL(addr(1, 2, 3, 4).masked(1), addr(1, 0, 0, 0));
CAF_CHECK_EQUAL(addr(1, 2, 3, 4).masked(2), addr(1, 2, 0, 0));
CAF_CHECK_EQUAL(addr(1, 2, 3, 4).masked(3), addr(1, 2, 3, 0));
CAF_CHECK_EQUAL(addr(1, 2, 3, 4).masked(4), addr(1, 2, 3, 4));
}
CAF_TEST(network addresses) {
auto all1 = addr(255, 255, 255, 255);
CAF_CHECK_EQUAL(all1.network_address(0), addr(0x00, 0x00, 0x00, 0x00));
CAF_CHECK_EQUAL(all1.network_address(7), addr(0xFE, 0x00, 0x00, 0x00));
CAF_CHECK_EQUAL(all1.network_address(8), addr(0xFF, 0x00, 0x00, 0x00));
CAF_CHECK_EQUAL(all1.network_address(9), addr(0xFF, 0x80, 0x00, 0x00));
CAF_CHECK_EQUAL(all1.network_address(31), addr(0xFF, 0xFF, 0xFF, 0xFE));
CAF_CHECK_EQUAL(all1.network_address(32), addr(0xFF, 0xFF, 0xFF, 0xFF));
CAF_CHECK_EQUAL(all1.network_address(33), addr(0xFF, 0xFF, 0xFF, 0xFF));
}
CAF_TEST(operators) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment