Browse Source

Add proper dns-resolving (#73)

* Add proper dns-resolving

Signed-off-by: kamilsa <kamilsa16@gmail.com>
pull/74/head v0.0.1-p0
kamilsa 5 years ago
committed by GitHub
parent
commit
1c5764c7b9
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
  1. 17
      include/libp2p/transport/tcp/tcp_connection.hpp
  2. 27
      include/libp2p/transport/tcp/tcp_util.hpp
  3. 23
      src/transport/tcp/tcp_connection.cpp
  4. 57
      src/transport/tcp/tcp_transport.cpp

17
include/libp2p/transport/tcp/tcp_connection.hpp

@ -44,6 +44,23 @@ namespace libp2p::transport {
*/
void resolve(const Tcp::endpoint &endpoint, ResolveCallbackFunc cb);
/**
* @brief Resolve service name (DNS).
* @param host_name host name to resolve
* @param cb callback executed on operation completion.
*/
void resolve(const std::string &host_name, const std::string &port,
ResolveCallbackFunc cb);
/**
* @brief Resolve service name (DNS).
* @param protocol is either Tcp::ip4 or Tcp::ip6 protocol
* @param host_name host name to resolve
* @param cb callback executed on operation completion.
*/
void resolve(const Tcp &protocol, const std::string &host_name,
const std::string &port, ResolveCallbackFunc cb);
/**
* @brief Connect to a remote service.
* @param iterator list of resolved IP addresses of remote service.

27
include/libp2p/transport/tcp/tcp_util.hpp

@ -12,8 +12,8 @@
#include <boost/asio.hpp>
#include <boost/lexical_cast.hpp>
#include <gsl/span>
#include <libp2p/outcome/outcome.hpp>
#include <libp2p/multi/multiaddress.hpp>
#include <libp2p/outcome/outcome.hpp>
namespace libp2p::transport::detail {
template <typename T>
@ -56,10 +56,33 @@ namespace libp2p::transport::detail {
inline bool supportsIpTcp(const multi::Multiaddress &ma) {
using P = multi::Protocol::Code;
return (ma.hasProtocol(P::IP4) || ma.hasProtocol(P::IP6))
return (ma.hasProtocol(P::IP4) || ma.hasProtocol(P::IP6)
|| ma.hasProtocol(P::DNS4) || ma.hasProtocol(P::DNS6)
|| ma.hasProtocol(P::DNS))
&& ma.hasProtocol(P::TCP);
}
inline auto getFirstProtocol(const multi::Multiaddress &ma) {
return ma.getProtocolsWithValues().front().first.code;
}
// Obtain host and port strings from provided address
inline std::pair<std::string, std::string> getHostAndTcpPort(
const multi::Multiaddress &address) {
auto v = address.getProtocolsWithValues();
// get host
auto it = v.begin();
auto host = it->second;
// get port
it++;
BOOST_ASSERT(it->first.code == multi::Protocol::Code::TCP);
auto port = it->second;
return {host, port};
}
inline outcome::result<boost::asio::ip::tcp::endpoint> makeEndpoint(
const multi::Multiaddress &ma) {
using P = multi::Protocol::Code;

23
src/transport/tcp/tcp_connection.cpp

@ -64,6 +64,29 @@ namespace libp2p::transport {
});
}
void TcpConnection::resolve(const std::string &host_name,
const std::string &port,
TcpConnection::ResolveCallbackFunc cb) {
auto resolver = std::make_shared<Tcp::resolver>(context_);
resolver->async_resolve(
host_name, port,
[resolver, cb{std::move(cb)}](const ErrorCode &ec, auto &&iterator) {
cb(ec, std::forward<decltype(iterator)>(iterator));
});
}
void TcpConnection::resolve(const TcpConnection::Tcp &protocol,
const std::string &host_name,
const std::string &port,
TcpConnection::ResolveCallbackFunc cb) {
auto resolver = std::make_shared<Tcp::resolver>(context_);
resolver->async_resolve(
protocol, host_name, port,
[resolver, cb{std::move(cb)}](const ErrorCode &ec, auto &&iterator) {
cb(ec, std::forward<decltype(iterator)>(iterator));
});
}
void TcpConnection::connect(
const TcpConnection::ResolverResultsType &iterator,
TcpConnection::ConnectCallbackFunc cb) {

57
src/transport/tcp/tcp_transport.cpp

@ -17,32 +17,39 @@ namespace libp2p::transport {
}
auto conn = std::make_shared<TcpConnection>(*context_);
auto rendpoint = detail::makeEndpoint(address);
if (!rendpoint) {
return handler(rendpoint.error());
}
conn->resolve(rendpoint.value(),
[self{shared_from_this()}, conn, handler{std::move(handler)},
remoteId](auto ec, auto r) mutable {
if (ec) {
return handler(ec);
}
conn->connect(
r,
[self, conn, handler{std::move(handler)}, remoteId](
auto ec, auto &e) mutable {
if (ec) {
return handler(ec);
}
auto session = std::make_shared<UpgraderSession>(
self->upgrader_, std::move(conn), handler);
session->secureOutbound(remoteId);
});
});
auto [host, port] = detail::getHostAndTcpPort(address);
auto connect = [self{shared_from_this()}, conn, handler{std::move(handler)},
remoteId](auto ec, auto r) mutable {
if (ec) {
return handler(ec);
}
conn->connect(r,
[self, conn, handler{std::move(handler)}, remoteId](
auto ec, auto &e) mutable {
if (ec) {
return handler(ec);
}
auto session = std::make_shared<UpgraderSession>(
self->upgrader_, std::move(conn), handler);
session->secureOutbound(remoteId);
});
};
using P = multi::Protocol::Code;
switch (detail::getFirstProtocol(address)) {
case P::DNS4:
return conn->resolve(boost::asio::ip::tcp::v4(), host, port, connect);
case P::DNS6:
return conn->resolve(boost::asio::ip::tcp::v6(), host, port, connect);
default: // Could be only DNS, IP6 or IP4 as canDial already checked for
// that in the beginning of the method
return conn->resolve(host, port, connect);
}
}
std::shared_ptr<TransportListener> TcpTransport::createListener(

Loading…
Cancel
Save