Skip to content

Commit

Permalink
Use attempts list for TCP channels
Browse files Browse the repository at this point in the history
* Use attempts list for TCP channels to prevent multiple concurrent connections start to same peer
* Erase from attempts list after connection failure (udp fallback function) or success (insert function)
* Close sockets after connection failure
* Use tags for TCP & UDP attempts lists
  • Loading branch information
SergiySW committed Feb 21, 2020
1 parent 9d9d377 commit 5a50926
Show file tree
Hide file tree
Showing 4 changed files with 31 additions and 9 deletions.
15 changes: 13 additions & 2 deletions nano/node/transport/tcp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,7 @@ bool nano::transport::tcp_channels::insert (std::shared_ptr<nano::transport::cha
channels.get<node_id_tag> ().erase (node_id);
}
channels.get<endpoint_tag> ().emplace (channel_a, socket_a, bootstrap_server_a);
attempts.get<endpoint_tag> ().erase (endpoint);
error = false;
lock.unlock ();
node.network.channel_observer (channel_a);
Expand Down Expand Up @@ -351,6 +352,10 @@ bool nano::transport::tcp_channels::max_ip_connections (nano::tcp_endpoint const
{
nano::unique_lock<std::mutex> lock (mutex);
bool result (channels.get<ip_address_tag> ().count (endpoint_a.address ()) >= nano::transport::max_peers_per_ip);
if (!result)
{
result = attempts.get<ip_address_tag> ().count (endpoint_a.address ()) >= nano::transport::max_peers_per_ip;
}
return result;
}

Expand Down Expand Up @@ -396,8 +401,8 @@ void nano::transport::tcp_channels::purge (std::chrono::steady_clock::time_point
auto disconnect_cutoff (channels.get<last_packet_sent_tag> ().lower_bound (cutoff_a));
channels.get<last_packet_sent_tag> ().erase (channels.get<last_packet_sent_tag> ().begin (), disconnect_cutoff);
// Remove keepalive attempt tracking for attempts older than cutoff
auto attempts_cutoff (attempts.get<1> ().lower_bound (cutoff_a));
attempts.get<1> ().erase (attempts.get<1> ().begin (), attempts_cutoff);
auto attempts_cutoff (attempts.get<last_attempt_tag> ().lower_bound (cutoff_a));
attempts.get<last_attempt_tag> ().erase (attempts.get<last_attempt_tag> ().begin (), attempts_cutoff);

// Cleanup any sockets which may still be existing from failed node id handshakes
node_id_handshake_sockets.erase (std::remove_if (node_id_handshake_sockets.begin (), node_id_handshake_sockets.end (), [this](auto socket) {
Expand Down Expand Up @@ -545,6 +550,7 @@ void nano::transport::tcp_channels::start_tcp (nano::endpoint const & endpoint_a
if (auto socket_l = channel->socket.lock ())
{
node_l->network.tcp_channels.remove_node_id_handshake_socket (socket_l);
socket_l->close ();
}
if (node_l->config.logging.network_node_id_handshake_logging ())
{
Expand Down Expand Up @@ -576,6 +582,7 @@ void nano::transport::tcp_channels::start_tcp_receive_node_id (std::shared_ptr<n
if (auto socket_l = socket_w.lock ())
{
node_l->network.tcp_channels.remove_node_id_handshake_socket (socket_l);
socket_l->close ();
}
}
};
Expand Down Expand Up @@ -677,6 +684,10 @@ void nano::transport::tcp_channels::start_tcp_receive_node_id (std::shared_ptr<n

void nano::transport::tcp_channels::udp_fallback (nano::endpoint const & endpoint_a, std::function<void(std::shared_ptr<nano::transport::channel>)> const & callback_a)
{
{
nano::lock_guard<std::mutex> lock (mutex);
attempts.get<endpoint_tag> ().erase (nano::transport::map_endpoint_to_tcp (endpoint_a));
}
if (callback_a && !node.flags.disable_udp)
{
auto channel_udp (node.network.udp_channels.create (endpoint_a));
Expand Down
13 changes: 10 additions & 3 deletions nano/node/transport/tcp.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,9 @@ namespace transport
class last_bootstrap_attempt_tag
{
};
class last_attempt_tag
{
};
class node_id_tag
{
};
Expand Down Expand Up @@ -171,10 +174,12 @@ namespace transport
{
public:
nano::tcp_endpoint endpoint;
boost::asio::ip::address address;
std::chrono::steady_clock::time_point last_attempt{ std::chrono::steady_clock::now () };

explicit tcp_endpoint_attempt (nano::tcp_endpoint const & endpoint_a) :
endpoint (endpoint_a)
endpoint (endpoint_a),
address (endpoint_a.address ())
{
}
};
Expand All @@ -196,9 +201,11 @@ namespace transport
channels;
boost::multi_index_container<tcp_endpoint_attempt,
mi::indexed_by<
mi::hashed_unique<
mi::hashed_unique<mi::tag<endpoint_tag>,
mi::member<tcp_endpoint_attempt, nano::tcp_endpoint, &tcp_endpoint_attempt::endpoint>>,
mi::ordered_non_unique<
mi::hashed_non_unique<mi::tag<ip_address_tag>,
mi::member<tcp_endpoint_attempt, boost::asio::ip::address, &tcp_endpoint_attempt::address>>,
mi::ordered_non_unique<mi::tag<last_attempt_tag>,
mi::member<tcp_endpoint_attempt, std::chrono::steady_clock::time_point, &tcp_endpoint_attempt::last_attempt>>>>
attempts;
// clang-format on
Expand Down
5 changes: 3 additions & 2 deletions nano/node/transport/udp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -116,6 +116,7 @@ std::shared_ptr<nano::transport::channel_udp> nano::transport::udp_channels::ins
{
result = std::make_shared<nano::transport::channel_udp> (*this, endpoint_a, network_version_a);
channels.get<endpoint_tag> ().insert (result);
attempts.get<endpoint_tag> ().erase (endpoint_a);
lock.unlock ();
node.network.channel_observer (result);
}
Expand Down Expand Up @@ -677,8 +678,8 @@ void nano::transport::udp_channels::purge (std::chrono::steady_clock::time_point
auto disconnect_cutoff (channels.get<last_packet_received_tag> ().lower_bound (cutoff_a));
channels.get<last_packet_received_tag> ().erase (channels.get<last_packet_received_tag> ().begin (), disconnect_cutoff);
// Remove keepalive attempt tracking for attempts older than cutoff
auto attempts_cutoff (attempts.get<1> ().lower_bound (cutoff_a));
attempts.get<1> ().erase (attempts.get<1> ().begin (), attempts_cutoff);
auto attempts_cutoff (attempts.get<last_attempt_tag> ().lower_bound (cutoff_a));
attempts.get<last_attempt_tag> ().erase (attempts.get<last_attempt_tag> ().begin (), attempts_cutoff);
}

void nano::transport::udp_channels::ongoing_keepalive ()
Expand Down
7 changes: 5 additions & 2 deletions nano/node/transport/udp.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,9 @@ namespace transport
class last_bootstrap_attempt_tag
{
};
class last_attempt_tag
{
};
class node_id_tag
{
};
Expand Down Expand Up @@ -191,9 +194,9 @@ namespace transport
boost::multi_index_container<
endpoint_attempt,
mi::indexed_by<
mi::hashed_unique<
mi::hashed_unique<mi::tag<endpoint_tag>,
mi::member<endpoint_attempt, nano::endpoint, &endpoint_attempt::endpoint>>,
mi::ordered_non_unique<
mi::ordered_non_unique<mi::tag<last_attempt_tag>,
mi::member<endpoint_attempt, std::chrono::steady_clock::time_point, &endpoint_attempt::last_attempt>>>>
attempts;
// clang-format on
Expand Down

0 comments on commit 5a50926

Please sign in to comment.