From 1710a0d091ccfd81f8a9601f471d81542a577559 Mon Sep 17 00:00:00 2001 From: iphydf Date: Tue, 30 Jan 2024 10:31:57 +0000 Subject: [PATCH] refactor: Move pack/unpack `IP_Port` from DHT into network module. It's misplaced in DHT, since the data structures are located in network. --- .../docker/tox-bootstrapd.sha256 | 2 +- toxcore/BUILD.bazel | 1 + toxcore/DHT.c | 139 ------------------ toxcore/DHT.h | 20 --- toxcore/TCP_client.c | 1 - toxcore/TCP_server.c | 1 - toxcore/network.c | 138 +++++++++++++++++ toxcore/network.h | 24 +++ 8 files changed, 164 insertions(+), 162 deletions(-) diff --git a/other/bootstrap_daemon/docker/tox-bootstrapd.sha256 b/other/bootstrap_daemon/docker/tox-bootstrapd.sha256 index 09c28e7a..93e25005 100644 --- a/other/bootstrap_daemon/docker/tox-bootstrapd.sha256 +++ b/other/bootstrap_daemon/docker/tox-bootstrapd.sha256 @@ -1 +1 @@ -af83f07bb96eb17a7ee69f174c9960d23758c9c9314144d73e0f57fdef5d55e4 /usr/local/bin/tox-bootstrapd +e9e6e7baafe3cfe9b212ffb4f1ea8a8b48e2dc1ee4c07c6b1b0b04893b3b6464 /usr/local/bin/tox-bootstrapd diff --git a/toxcore/BUILD.bazel b/toxcore/BUILD.bazel index 7a6e67da..1e9d7e0c 100644 --- a/toxcore/BUILD.bazel +++ b/toxcore/BUILD.bazel @@ -292,6 +292,7 @@ cc_library( "//c-toxcore/toxav:__pkg__", ], deps = [ + ":bin_pack", ":ccompat", ":crypto_core", ":logger", diff --git a/toxcore/DHT.c b/toxcore/DHT.c index 1f8383f0..0073a289 100644 --- a/toxcore/DHT.c +++ b/toxcore/DHT.c @@ -9,7 +9,6 @@ #include "DHT.h" #include -#include #include #include @@ -364,84 +363,6 @@ int packed_node_size(Family ip_family) } -/** @brief Packs an IP structure. - * - * It's the caller's responsibility to make sure `is_ipv4` tells the truth. This - * function is an implementation detail of @ref bin_pack_ip_port. - * - * @param is_ipv4 whether this IP is an IP4 or IP6. - * - * @retval true on success. - */ -non_null() -static bool bin_pack_ip(Bin_Pack *bp, const IP *ip, bool is_ipv4) -{ - if (is_ipv4) { - return bin_pack_bin_b(bp, ip->ip.v4.uint8, SIZE_IP4); - } else { - return bin_pack_bin_b(bp, ip->ip.v6.uint8, SIZE_IP6); - } -} - -/** @brief Packs an IP_Port structure. - * - * @retval true on success. - */ -non_null() -static bool bin_pack_ip_port(Bin_Pack *bp, const Logger *logger, const IP_Port *ip_port) -{ - bool is_ipv4; - uint8_t family; - - if (net_family_is_ipv4(ip_port->ip.family)) { - // TODO(irungentoo): use functions to convert endianness - is_ipv4 = true; - family = TOX_AF_INET; - } else if (net_family_is_tcp_ipv4(ip_port->ip.family)) { - is_ipv4 = true; - family = TOX_TCP_INET; - } else if (net_family_is_ipv6(ip_port->ip.family)) { - is_ipv4 = false; - family = TOX_AF_INET6; - } else if (net_family_is_tcp_ipv6(ip_port->ip.family)) { - is_ipv4 = false; - family = TOX_TCP_INET6; - } else { - Ip_Ntoa ip_str; - // TODO(iphydf): Find out why we're trying to pack invalid IPs, stop - // doing that, and turn this into an error. - LOGGER_TRACE(logger, "cannot pack invalid IP: %s", net_ip_ntoa(&ip_port->ip, &ip_str)); - return false; - } - - return bin_pack_u08_b(bp, family) - && bin_pack_ip(bp, &ip_port->ip, is_ipv4) - && bin_pack_u16_b(bp, net_ntohs(ip_port->port)); -} - -non_null() -static bool bin_pack_ip_port_handler(const void *obj, const Logger *logger, Bin_Pack *bp) -{ - const IP_Port *ip_port = (const IP_Port *)obj; - return bin_pack_ip_port(bp, logger, ip_port); -} - -int pack_ip_port(const Logger *logger, uint8_t *data, uint16_t length, const IP_Port *ip_port) -{ - const uint32_t size = bin_pack_obj_size(bin_pack_ip_port_handler, ip_port, logger); - - if (size > length) { - return -1; - } - - if (!bin_pack_obj(bin_pack_ip_port_handler, ip_port, logger, data, length)) { - return -1; - } - - assert(size < INT_MAX); - return (int)size; -} - int dht_create_packet(const Memory *mem, const Random *rng, const uint8_t public_key[CRYPTO_PUBLIC_KEY_SIZE], const uint8_t *shared_key, const uint8_t type, @@ -478,66 +399,6 @@ int dht_create_packet(const Memory *mem, const Random *rng, return 1 + CRYPTO_PUBLIC_KEY_SIZE + CRYPTO_NONCE_SIZE + encrypted_length; } -int unpack_ip_port(IP_Port *ip_port, const uint8_t *data, uint16_t length, bool tcp_enabled) -{ - if (data == nullptr) { - return -1; - } - - bool is_ipv4; - Family host_family; - - if (data[0] == TOX_AF_INET) { - is_ipv4 = true; - host_family = net_family_ipv4(); - } else if (data[0] == TOX_TCP_INET) { - if (!tcp_enabled) { - return -1; - } - - is_ipv4 = true; - host_family = net_family_tcp_ipv4(); - } else if (data[0] == TOX_AF_INET6) { - is_ipv4 = false; - host_family = net_family_ipv6(); - } else if (data[0] == TOX_TCP_INET6) { - if (!tcp_enabled) { - return -1; - } - - is_ipv4 = false; - host_family = net_family_tcp_ipv6(); - } else { - return -1; - } - - ipport_reset(ip_port); - - if (is_ipv4) { - const uint32_t size = 1 + SIZE_IP4 + sizeof(uint16_t); - - if (size > length) { - return -1; - } - - ip_port->ip.family = host_family; - memcpy(&ip_port->ip.ip.v4, data + 1, SIZE_IP4); - memcpy(&ip_port->port, data + 1 + SIZE_IP4, sizeof(uint16_t)); - return size; - } else { - const uint32_t size = 1 + SIZE_IP6 + sizeof(uint16_t); - - if (size > length) { - return -1; - } - - ip_port->ip.family = host_family; - memcpy(&ip_port->ip.ip.v6, data + 1, SIZE_IP6); - memcpy(&ip_port->port, data + 1 + SIZE_IP6, sizeof(uint16_t)); - return size; - } -} - /** @brief Pack a single node from a node array. * * @retval true on success. diff --git a/toxcore/DHT.h b/toxcore/DHT.h index cb6e5e25..3e40f1ce 100644 --- a/toxcore/DHT.h +++ b/toxcore/DHT.h @@ -204,26 +204,6 @@ non_null() const Client_data *dht_friend_client(const DHT_Friend *dht_friend, si */ int packed_node_size(Family ip_family); -/** @brief Pack an IP_Port structure into data of max size length. - * - * Packed_length is the offset of data currently packed. - * - * @return size of packed IP_Port data on success. - * @retval -1 on failure. - */ -non_null() -int pack_ip_port(const Logger *logger, uint8_t *data, uint16_t length, const IP_Port *ip_port); - -/** @brief Unpack IP_Port structure from data of max size length into ip_port. - * - * len_processed is the offset of data currently unpacked. - * - * @return size of unpacked ip_port on success. - * @retval -1 on failure. - */ -non_null() -int unpack_ip_port(IP_Port *ip_port, const uint8_t *data, uint16_t length, bool tcp_enabled); - /** @brief Encrypt plain and write resulting DHT packet into packet with max size length. * * @return size of packet on success. diff --git a/toxcore/TCP_client.c b/toxcore/TCP_client.c index ddb2e36a..f65d4d60 100644 --- a/toxcore/TCP_client.c +++ b/toxcore/TCP_client.c @@ -12,7 +12,6 @@ #include #include -#include "DHT.h" #include "TCP_common.h" #include "ccompat.h" #include "crypto_core.h" diff --git a/toxcore/TCP_server.c b/toxcore/TCP_server.c index 52c96c35..de31fa1e 100644 --- a/toxcore/TCP_server.c +++ b/toxcore/TCP_server.c @@ -18,7 +18,6 @@ #include #endif /* TCP_SERVER_USE_EPOLL */ -#include "DHT.h" #include "TCP_common.h" #include "ccompat.h" #include "crypto_core.h" diff --git a/toxcore/network.c b/toxcore/network.c index c5fb31d2..1442f1a5 100644 --- a/toxcore/network.c +++ b/toxcore/network.c @@ -81,6 +81,7 @@ #include #include +#include "bin_pack.h" #include "ccompat.h" #include "logger.h" #include "mem.h" @@ -1573,6 +1574,143 @@ void ipport_copy(IP_Port *target, const IP_Port *source) *target = tmp; } +/** @brief Packs an IP structure. + * + * It's the caller's responsibility to make sure `is_ipv4` tells the truth. This + * function is an implementation detail of @ref bin_pack_ip_port. + * + * @param is_ipv4 whether this IP is an IP4 or IP6. + * + * @retval true on success. + */ +non_null() +static bool bin_pack_ip(Bin_Pack *bp, const IP *ip, bool is_ipv4) +{ + if (is_ipv4) { + return bin_pack_bin_b(bp, ip->ip.v4.uint8, SIZE_IP4); + } else { + return bin_pack_bin_b(bp, ip->ip.v6.uint8, SIZE_IP6); + } +} + +/** @brief Packs an IP_Port structure. + * + * @retval true on success. + */ +bool bin_pack_ip_port(Bin_Pack *bp, const Logger *logger, const IP_Port *ip_port) +{ + bool is_ipv4; + uint8_t family; + + if (net_family_is_ipv4(ip_port->ip.family)) { + // TODO(irungentoo): use functions to convert endianness + is_ipv4 = true; + family = TOX_AF_INET; + } else if (net_family_is_tcp_ipv4(ip_port->ip.family)) { + is_ipv4 = true; + family = TOX_TCP_INET; + } else if (net_family_is_ipv6(ip_port->ip.family)) { + is_ipv4 = false; + family = TOX_AF_INET6; + } else if (net_family_is_tcp_ipv6(ip_port->ip.family)) { + is_ipv4 = false; + family = TOX_TCP_INET6; + } else { + Ip_Ntoa ip_str; + // TODO(iphydf): Find out why we're trying to pack invalid IPs, stop + // doing that, and turn this into an error. + LOGGER_TRACE(logger, "cannot pack invalid IP: %s", net_ip_ntoa(&ip_port->ip, &ip_str)); + return false; + } + + return bin_pack_u08_b(bp, family) + && bin_pack_ip(bp, &ip_port->ip, is_ipv4) + && bin_pack_u16_b(bp, net_ntohs(ip_port->port)); +} + +non_null() +static bool bin_pack_ip_port_handler(const void *obj, const Logger *logger, Bin_Pack *bp) +{ + const IP_Port *ip_port = (const IP_Port *)obj; + return bin_pack_ip_port(bp, logger, ip_port); +} + +int pack_ip_port(const Logger *logger, uint8_t *data, uint16_t length, const IP_Port *ip_port) +{ + const uint32_t size = bin_pack_obj_size(bin_pack_ip_port_handler, ip_port, logger); + + if (size > length) { + return -1; + } + + if (!bin_pack_obj(bin_pack_ip_port_handler, ip_port, logger, data, length)) { + return -1; + } + + assert(size < INT_MAX); + return (int)size; +} + +int unpack_ip_port(IP_Port *ip_port, const uint8_t *data, uint16_t length, bool tcp_enabled) +{ + if (data == nullptr) { + return -1; + } + + bool is_ipv4; + Family host_family; + + if (data[0] == TOX_AF_INET) { + is_ipv4 = true; + host_family = net_family_ipv4(); + } else if (data[0] == TOX_TCP_INET) { + if (!tcp_enabled) { + return -1; + } + + is_ipv4 = true; + host_family = net_family_tcp_ipv4(); + } else if (data[0] == TOX_AF_INET6) { + is_ipv4 = false; + host_family = net_family_ipv6(); + } else if (data[0] == TOX_TCP_INET6) { + if (!tcp_enabled) { + return -1; + } + + is_ipv4 = false; + host_family = net_family_tcp_ipv6(); + } else { + return -1; + } + + ipport_reset(ip_port); + + if (is_ipv4) { + const uint32_t size = 1 + SIZE_IP4 + sizeof(uint16_t); + + if (size > length) { + return -1; + } + + ip_port->ip.family = host_family; + memcpy(&ip_port->ip.ip.v4, data + 1, SIZE_IP4); + memcpy(&ip_port->port, data + 1 + SIZE_IP4, sizeof(uint16_t)); + return size; + } else { + const uint32_t size = 1 + SIZE_IP6 + sizeof(uint16_t); + + if (size > length) { + return -1; + } + + ip_port->ip.family = host_family; + memcpy(&ip_port->ip.ip.v6, data + 1, SIZE_IP6); + memcpy(&ip_port->port, data + 1 + SIZE_IP6, sizeof(uint16_t)); + return size; + } +} + const char *net_ip_ntoa(const IP *ip, Ip_Ntoa *ip_str) { assert(ip_str != nullptr); diff --git a/toxcore/network.h b/toxcore/network.h index 4697bffb..6aea1cb3 100644 --- a/toxcore/network.h +++ b/toxcore/network.h @@ -13,6 +13,7 @@ #include // size_t #include // uint*_t +#include "bin_pack.h" #include "logger.h" #include "mem.h" @@ -518,6 +519,29 @@ int32_t net_getipport(const Memory *mem, const char *node, IP_Port **res, int to non_null(1) nullable(2) void net_freeipport(const Memory *mem, IP_Port *ip_ports); +non_null() +bool bin_pack_ip_port(Bin_Pack *bp, const Logger *logger, const IP_Port *ip_port); + +/** @brief Pack an IP_Port structure into data of max size length. + * + * Packed_length is the offset of data currently packed. + * + * @return size of packed IP_Port data on success. + * @retval -1 on failure. + */ +non_null() +int pack_ip_port(const Logger *logger, uint8_t *data, uint16_t length, const IP_Port *ip_port); + +/** @brief Unpack IP_Port structure from data of max size length into ip_port. + * + * len_processed is the offset of data currently unpacked. + * + * @return size of unpacked ip_port on success. + * @retval -1 on failure. + */ +non_null() +int unpack_ip_port(IP_Port *ip_port, const uint8_t *data, uint16_t length, bool tcp_enabled); + /** * @return true on success, false on failure. */