From 4dc668286d8b78a0d2f9d4e66e39bdf1773d4444 Mon Sep 17 00:00:00 2001 From: cryptocode <34946442+cryptocode@users.noreply.github.com> Date: Mon, 7 Jan 2019 23:52:39 +0100 Subject: [PATCH] Lack of contact timestamping drops peers (#1536) * Lack of contact timestamping drops peers * Added test to make sure last_contact is updated --- nano/core_test/network.cpp | 33 +++++++++++++++++++++++++++++++++ nano/node/peers.cpp | 11 +++++++++++ 2 files changed, 44 insertions(+) diff --git a/nano/core_test/network.cpp b/nano/core_test/network.cpp index b6a44572d..0c41cf097 100644 --- a/nano/core_test/network.cpp +++ b/nano/core_test/network.cpp @@ -116,6 +116,39 @@ TEST (network, keepalive_ipv4) node1->stop (); } +TEST (network, last_contacted) +{ + nano::system system (24000, 1); + auto list1 (system.nodes[0]->peers.list ()); + ASSERT_EQ (0, list1.size ()); + nano::node_init init1; + auto node1 (std::make_shared (init1, system.io_ctx, 24001, nano::unique_path (), system.alarm, system.logging, system.work)); + node1->start (); + system.nodes.push_back (node1); + node1->send_keepalive (nano::endpoint (boost::asio::ip::address_v4::loopback (), 24000)); + system.deadline_set (10s); + + // Wait until the handshake is complete + while (system.nodes[0]->peers.size () < 1) + { + ASSERT_NO_ERROR (system.poll ()); + } + ASSERT_EQ (system.nodes[0]->peers.size (), 1); + + // Make sure last_contact gets updated on receiving a non-handshake message + auto timestamp_before_keepalive = system.nodes[0]->peers.list_vector (1).front ().last_contact; + node1->send_keepalive (nano::endpoint (boost::asio::ip::address_v4::loopback (), 24000)); + while (system.nodes[0]->stats.count (nano::stat::type::message, nano::stat::detail::keepalive, nano::stat::dir::in) < 2) + { + ASSERT_NO_ERROR (system.poll ()); + } + ASSERT_EQ (system.nodes[0]->peers.size (), 1); + auto timestamp_after_keepalive = system.nodes[0]->peers.list_vector (1).front ().last_contact; + ASSERT_GT (timestamp_after_keepalive, timestamp_before_keepalive); + + node1->stop (); +} + TEST (network, multi_keepalive) { nano::system system (24000, 1); diff --git a/nano/node/peers.cpp b/nano/node/peers.cpp index 4af128e18..6e70d28bc 100644 --- a/nano/node/peers.cpp +++ b/nano/node/peers.cpp @@ -62,6 +62,17 @@ bool nano::peer_container::contacted (nano::endpoint const & endpoint_a, unsigne should_handshake = true; } } + else + { + std::lock_guard lock (mutex); + auto existing (peers.find (endpoint_a)); + if (existing != peers.end ()) + { + peers.modify (existing, [](nano::peer_information & info) { + info.last_contact = std::chrono::steady_clock::now (); + }); + } + } return should_handshake; }