File resolver.cpp¶
File List > modules > net > resolver.cpp
Go to the documentation of this file.
#include <coroutine/net.h>
#include <coroutine/yield.hpp>
using namespace std;
namespace coro {
GSL_SUPPRESS(type .1)
uint32_t get_name(const sockaddr_in& addr, //
gsl::zstring<NI_MAXHOST> name, gsl::zstring<NI_MAXSERV> serv,
int32_t flags) noexcept {
const auto* ptr = reinterpret_cast<const sockaddr*>(addressof(addr));
return ::getnameinfo(ptr, sizeof(sockaddr_in), //
name, NI_MAXHOST, //
serv, (serv == nullptr) ? 0 : NI_MAXSERV, //
flags);
}
GSL_SUPPRESS(type .1)
uint32_t get_name(const sockaddr_in6& addr, //
gsl::zstring<NI_MAXHOST> name, gsl::zstring<NI_MAXSERV> serv,
int32_t flags) noexcept {
const auto* ptr = reinterpret_cast<const sockaddr*>(addressof(addr));
return ::getnameinfo(ptr, sizeof(sockaddr_in6), //
name, NI_MAXHOST, //
serv, (serv == nullptr) ? 0 : NI_MAXSERV, //
flags);
}
auto get_address(addrinfo* list) noexcept -> enumerable<sockaddr*> {
auto on_return = gsl::finally([list]() noexcept {
// RAII clean up for the assigned addrinfo
::freeaddrinfo(list);
});
for (addrinfo* it = list; it != nullptr; it = it->ai_next) {
co_yield it->ai_addr;
}
}
auto get_address(addrinfo* list, sockaddr_in addr) noexcept
-> enumerable<sockaddr_in> {
for (sockaddr* item : get_address(list)) {
const auto* ptr = reinterpret_cast<sockaddr_in*>(item);
addr = *ptr;
co_yield addr;
}
}
auto get_address(addrinfo* list, sockaddr_in6 addr) noexcept
-> enumerable<sockaddr_in6> {
for (sockaddr* item : get_address(list)) {
const auto* ptr = reinterpret_cast<sockaddr_in6*>(item);
addr = *ptr;
co_yield addr;
}
}
uint32_t get_address(const addrinfo& hint, //
gsl::czstring<> host, gsl::czstring<> serv,
gsl::span<sockaddr_in> output) noexcept {
addrinfo* list = nullptr;
if (const auto ec = ::getaddrinfo(host, serv, //
&hint, &list))
return ec; // std::system_error{ec, system_category(), ::gai_strerror(ec)};
auto i = 0u;
for (auto addr : get_address(list, sockaddr_in{})) {
output[i++] = addr;
if (i == output.size())
break;
}
return 0;
}
uint32_t get_address(const addrinfo& hint, //
gsl::czstring<> host, gsl::czstring<> serv,
gsl::span<sockaddr_in6> output) noexcept {
addrinfo* list = nullptr;
if (const auto ec = ::getaddrinfo(host, serv, //
&hint, &list))
return ec;
auto i = 0u;
for (auto addr : get_address(list, sockaddr_in6{})) {
output[i++] = addr;
if (i == output.size())
break;
}
return 0;
}
} // namespace coro