diff --git a/include/bitcoin/node/protocols/protocol_observer.hpp b/include/bitcoin/node/protocols/protocol_observer.hpp index c1e145c8..fd414b19 100644 --- a/include/bitcoin/node/protocols/protocol_observer.hpp +++ b/include/bitcoin/node/protocols/protocol_observer.hpp @@ -44,6 +44,7 @@ class BCN_API protocol_observer is_negotiated(network::messages::peer::level::bip37) && !session->network_settings().enable_relay ), + group_(to_group>()), network::tracker(session->log) { } @@ -63,9 +64,33 @@ class BCN_API protocol_observer virtual bool handle_receive_inventory(const code& ec, const network::messages::peer::inventory::cptr& message) NOEXCEPT; + /// Add the channel row to a capture of which it is a member. + virtual bool handle_broadcast_diagnostics(const code& ec, + const network::diagnostics::cptr& message, uint64_t sender) NOEXCEPT; + + /// The capture group of the channel (the session determines the group). + virtual network::diagnostics::target group() const NOEXCEPT; + private: + // The session configuration type identifies its capture group. + template + static constexpr network::diagnostics::target to_group() NOEXCEPT + { + using options = typename Session::options_t; + using inbound = network::settings::peer_inbound; + using manual = network::settings::peer_manual; + + if constexpr (is_same_type) + return network::diagnostics::target::inbound; + else if constexpr (is_same_type) + return network::diagnostics::target::manual; + else + return network::diagnostics::target::outbound; + } + // These are thread safe. const bool relay_disallowed_; + const network::diagnostics::target group_; }; } // namespace node diff --git a/src/protocols/protocol_observer.cpp b/src/protocols/protocol_observer.cpp index 85cc95a3..ac36bccf 100644 --- a/src/protocols/protocol_observer.cpp +++ b/src/protocols/protocol_observer.cpp @@ -50,6 +50,9 @@ void protocol_observer::start() NOEXCEPT SUBSCRIBE_CHANNEL(inventory, handle_receive_inventory, _1, _2); } + SUBSCRIBE_BROADCAST(network::diagnostics, handle_broadcast_diagnostics, + _1, _2, _3); + ////SUBSCRIBE_CHANNEL(get_data, handle_receive_get_data, _1, _2); protocol_peer::start(); } @@ -117,6 +120,43 @@ bool protocol_observer::handle_receive_inventory(const code& ec, return true; } +// Diagnostics (capture). +// ---------------------------------------------------------------------------- + +network::diagnostics::target protocol_observer::group() const NOEXCEPT +{ + return group_; +} + +bool protocol_observer::handle_broadcast_diagnostics(const code& ec, + const network::diagnostics::cptr& message, uint64_t) NOEXCEPT +{ + BC_ASSERT(stranded()); + + if (stopped(ec)) + return false; + + if (!message->member(identifier()) && !message->member(group())) + return true; + + const auto peer = peer_version(); + + message->add( + { + identifier(), + outbound(), + group(), + negotiated_version(), + peer ? peer->services : service::node_none, + sent(), + start_height(), + encrypted(), + peer ? peer->user_agent : std::string{} + }); + + return true; +} + BC_POP_WARNING() BC_POP_WARNING()