From cd44caccafefe2fc709e4344ed37124122497634 Mon Sep 17 00:00:00 2001 From: Stephen Shelton Date: Mon, 11 May 2020 09:11:44 -0600 Subject: [PATCH] Attempt to get this SockAddr refactor up and running --- llarp/net/exit_info.cpp | 28 ++++++++++++-------- llarp/net/ip_address.cpp | 55 ++++++++++++++++++++++++++++++---------- llarp/net/ip_address.hpp | 2 +- llarp/net/net.cpp | 19 +++++--------- llarp/net/sock_addr.cpp | 11 +++++++- llarp/net/sock_addr.hpp | 1 + 6 files changed, 78 insertions(+), 38 deletions(-) diff --git a/llarp/net/exit_info.cpp b/llarp/net/exit_info.cpp index a028d8fee..000f5abc2 100644 --- a/llarp/net/exit_info.cpp +++ b/llarp/net/exit_info.cpp @@ -16,16 +16,17 @@ namespace llarp bool ExitInfo::BEncode(llarp_buffer_t* buf) const { - // TODO: derive these from ipAdress - throw std::runtime_error("FIXME: need in6_addr and netmask from IpAddress"); - in6_addr address; + SockAddr addr = ipAddress.createSockAddr(); + const sockaddr_in6* addr6 = addr; + in6_addr netmask; + memset(netmask.s6_addr, 0xff, 16); char tmp[128] = {0}; if (!bencode_start_dict(buf)) return false; - if (!inet_ntop(AF_INET6, address.s6_addr, tmp, sizeof(tmp))) + if (!inet_ntop(AF_INET6, &addr6->sin6_addr, tmp, sizeof(tmp))) return false; if (!BEncodeWriteDictString("a", std::string(tmp), buf)) return false; @@ -63,26 +64,31 @@ namespace llarp bool ExitInfo::DecodeKey(const llarp_buffer_t& k, llarp_buffer_t* buf) { - // TODO: derive these from ipAdress - throw std::runtime_error("FIXME: need in6_addr and netmask from IpAddress"); - in6_addr address; - in6_addr netmask; - bool read = false; if (!BEncodeMaybeReadDictEntry("k", pubkey, read, k, buf)) return false; if (!BEncodeMaybeReadDictInt("v", version, read, k, buf)) return false; if (k == "a") - return bdecode_ip_string(buf, address); + { + // TODO: read into ipAddress + in6_addr tmp; + return bdecode_ip_string(buf, tmp); + } if (k == "b") + { + // TODO: we don't use this currently, but we shoudn't drop it on the floor + // it appears that all clients should be advertising 0xff..ff for netmask + in6_addr netmask; return bdecode_ip_string(buf, netmask); + } return read; } std::ostream& ExitInfo::print(std::ostream& stream, int level, int spaces) const { + /* // TODO: derive these from ipAdress throw std::runtime_error("FIXME: need in6_addr and netmask from IpAddress"); in6_addr address; @@ -105,6 +111,8 @@ namespace llarp ss << std::to_string(llarp::bits::count_array_bits(netmask.s6_addr)); #endif printer.printValue(ss.str()); + */ + stream << ipAddress.toString(); return stream; } diff --git a/llarp/net/ip_address.cpp b/llarp/net/ip_address.cpp index d2e0228bb..334d09002 100644 --- a/llarp/net/ip_address.cpp +++ b/llarp/net/ip_address.cpp @@ -1,50 +1,72 @@ #include +#include + namespace llarp { IpAddress::IpAddress(std::string_view str) { - throw std::runtime_error("FIXME"); + setAddress(str); } IpAddress::IpAddress(std::string_view str, std::optional port) { - throw std::runtime_error("FIXME"); + setAddress(str, port); } IpAddress::IpAddress(const SockAddr& addr) { - throw std::runtime_error("FIXME"); + m_ipAddress = addr.toString(); + uint16_t port = addr.getPort(); + if (port > 0) + m_port = port; } - SockAddr& + IpAddress& IpAddress::operator=(const sockaddr& other) { - throw std::runtime_error("FIXME"); + SockAddr addr(other); + + m_ipAddress = addr.toString(); + uint16_t port = addr.getPort(); + if (port > 0) + m_port = port; + + return *this; } std::optional IpAddress::getPort() const { - throw std::runtime_error("FIXME"); + return m_port; } void IpAddress::setPort(std::optional port) { - throw std::runtime_error("FIXME"); + m_port = port; } void IpAddress::setAddress(std::string_view str) { - throw std::runtime_error("FIXME"); + SockAddr addr; + addr.fromString(str); + + m_ipAddress = std::string(str); + uint16_t port = addr.getPort(); + if (port > 0) + m_port = port; } void IpAddress::setAddress(std::string_view str, std::optional port) { - throw std::runtime_error("FIXME"); + SockAddr addr; + addr.fromString(str); + + m_ipAddress = std::string(str); + m_port = port; } bool @@ -62,19 +84,26 @@ namespace llarp SockAddr IpAddress::createSockAddr() const { - throw std::runtime_error("FIXME"); + SockAddr addr(m_ipAddress); + if (m_port) + addr.setPort(m_port.value()); + + return addr; } bool IpAddress::isBogon() const { - throw std::runtime_error("FIXME"); + SockAddr addr(m_ipAddress); + const sockaddr_in6* addr6 = addr; + uint8_t* raw = addr6->sin6_addr.s6_addr; + return IsIPv4Bogon(ipaddr_ipv4_bits(raw[12], raw[13], raw[14], raw[15])); } std::string IpAddress::toString() const { - throw std::runtime_error("FIXME"); + return m_ipAddress; // TODO: port } bool @@ -92,7 +121,7 @@ namespace llarp std::ostream& operator<<(std::ostream& out, const IpAddress& address) { - throw std::runtime_error("FIXME"); + out << address.toString(); } } // namespace llarp diff --git a/llarp/net/ip_address.hpp b/llarp/net/ip_address.hpp index 8a151c222..ec334c838 100644 --- a/llarp/net/ip_address.hpp +++ b/llarp/net/ip_address.hpp @@ -48,7 +48,7 @@ namespace llarp /// @param addr is an SockAddr to initialize from. IpAddress(const SockAddr& addr); - SockAddr& + IpAddress& operator=(const sockaddr& other); /// Return the port. Returns -1 if no port has been provided. diff --git a/llarp/net/net.cpp b/llarp/net/net.cpp index ac164411a..db58a8465 100644 --- a/llarp/net/net.cpp +++ b/llarp/net/net.cpp @@ -428,17 +428,14 @@ namespace llarp { if (i->ifa_addr->sa_family == af) { - /* TODO: why the fuck does'n this work? - // llarp::SockAddr a(i->ifa_addr); - // llarp::IpAddress ip(a); + llarp::SockAddr a(i->ifa_addr); + llarp::IpAddress ip(a); if (!ip.isBogon()) { ifname = i->ifa_name; found = true; } - */ - throw std::runtime_error("WTF"); } } }); @@ -544,10 +541,8 @@ namespace llarp sockaddr* sptr = (sockaddr*)&s; if (!llarp_getifaddr(ifname.c_str(), af, sptr)) return std::nullopt; - // TODO: why the fuck does this not compile? - // llarp::SockAddr saddr = SockAddr(*sptr); - // return llarp::IpAddress(saddr); - throw std::runtime_error("WTF"); + llarp::SockAddr saddr = SockAddr(*sptr); + return llarp::IpAddress(saddr); } bool @@ -559,10 +554,8 @@ namespace llarp addr.sin_family = AF_INET; addr.sin_addr.s_addr = htonl(INADDR_ANY); addr.sin_port = htons(0); - // TODO: why the fuck doesn't this work? - // SockAddr saddr = SockAddr(addr); - // result = IpAddress(saddr); - throw std::runtime_error("WTF"); + SockAddr saddr = SockAddr(addr); + result = IpAddress(saddr); return true; } if (af == AF_INET6) diff --git a/llarp/net/sock_addr.cpp b/llarp/net/sock_addr.cpp index 1b5497fad..0ad501eb5 100644 --- a/llarp/net/sock_addr.cpp +++ b/llarp/net/sock_addr.cpp @@ -125,11 +125,20 @@ namespace llarp return (sockaddr*)&m_addr; } + SockAddr::operator const sockaddr_in6*() const + { + return &m_addr; + } + void SockAddr::fromString(std::string_view str) { if (str.empty()) - throw std::invalid_argument("cannot construct IPv4 from empty string"); + { + init(); + m_empty = true; + return; + } // NOTE: this potentially involves multiple memory allocations, // reimplement without split() if it is performance bottleneck diff --git a/llarp/net/sock_addr.hpp b/llarp/net/sock_addr.hpp index e7fd798eb..cbcd42d8d 100644 --- a/llarp/net/sock_addr.hpp +++ b/llarp/net/sock_addr.hpp @@ -33,6 +33,7 @@ namespace llarp operator=(const sockaddr_in6& addr); operator const sockaddr*() const; + operator const sockaddr_in6*() const; void fromString(std::string_view str);