aboutsummaryrefslogtreecommitdiff
path: root/src/p2p/net_node.inl
diff options
context:
space:
mode:
authormydesktop <dev.mc2@gmail.com>2014-05-25 13:06:40 -0400
committermydesktop <dev.mc2@gmail.com>2014-05-25 13:06:40 -0400
commit3a3a8176782a4fa75b0607fba0393c9d4a1746be (patch)
treee8e38bdeaf0e9ea8ba773bb27e1de4b288b8150d /src/p2p/net_node.inl
parentMerge pull request #12 from quazarcoin/MRO_master (diff)
downloadmonero-3a3a8176782a4fa75b0607fba0393c9d4a1746be.tar.xz
0.8.8update
Diffstat (limited to 'src/p2p/net_node.inl')
-rw-r--r--src/p2p/net_node.inl194
1 files changed, 126 insertions, 68 deletions
diff --git a/src/p2p/net_node.inl b/src/p2p/net_node.inl
index 31d3e6597..e45e51b77 100644
--- a/src/p2p/net_node.inl
+++ b/src/p2p/net_node.inl
@@ -4,9 +4,10 @@
#pragma once
+#include <algorithm>
+
#include "version.h"
#include "string_tools.h"
-#include "common/command_line.h"
#include "common/util.h"
#include "net/net_helper.h"
#include "math_helper.h"
@@ -31,8 +32,11 @@ namespace nodetool
const command_line::arg_descriptor<bool> arg_p2p_allow_local_ip = {"allow-local-ip", "Allow local ip add to peer list, mostly in debug purposes"};
const command_line::arg_descriptor<std::vector<std::string> > arg_p2p_add_peer = {"add-peer", "Manually add peer to local peerlist"};
const command_line::arg_descriptor<std::vector<std::string> > arg_p2p_add_priority_node = {"add-priority-node", "Specify list of peers to connect to and attempt to keep the connection open"};
+ const command_line::arg_descriptor<std::vector<std::string> > arg_p2p_add_exclusive_node = {"add-exclusive-node", "Specify list of peers to connect to only."
+ " If this option is given the options add-priority-node and seed-node are ignored"};
const command_line::arg_descriptor<std::vector<std::string> > arg_p2p_seed_node = {"seed-node", "Connect to a node to retrieve peer addresses, and disconnect"};
- const command_line::arg_descriptor<bool> arg_p2p_hide_my_port = {"hide-my-port", "Do not announce yourself as peerlist candidate", false, true}; }
+ const command_line::arg_descriptor<bool> arg_p2p_hide_my_port = {"hide-my-port", "Do not announce yourself as peerlist candidate", false, true};
+ }
//-----------------------------------------------------------------------------------
template<class t_payload_net_handler>
@@ -44,6 +48,7 @@ namespace nodetool
command_line::add_arg(desc, arg_p2p_allow_local_ip);
command_line::add_arg(desc, arg_p2p_add_peer);
command_line::add_arg(desc, arg_p2p_add_priority_node);
+ command_line::add_arg(desc, arg_p2p_add_exclusive_node);
command_line::add_arg(desc, arg_p2p_seed_node);
command_line::add_arg(desc, arg_p2p_hide_my_port); }
//-----------------------------------------------------------------------------------
@@ -96,7 +101,7 @@ namespace nodetool
template<class t_payload_net_handler>
bool node_server<t_payload_net_handler>::parse_peer_from_string(nodetool::net_address& pe, const std::string& node_addr)
{
- return string_tools::parse_peer_from_string(pe.ip, pe.port, node_addr);
+ return epee::string_tools::parse_peer_from_string(pe.ip, pe.port, node_addr);
}
//-----------------------------------------------------------------------------------
template<class t_payload_net_handler>
@@ -120,30 +125,26 @@ namespace nodetool
}
}
- if (command_line::has_arg(vm, arg_p2p_add_priority_node))
- {
- std::vector<std::string> perrs = command_line::get_arg(vm, arg_p2p_add_priority_node);
- for(const std::string& pr_str: perrs)
- {
- nodetool::net_address na = AUTO_VAL_INIT(na);
- bool r = parse_peer_from_string(na, pr_str);
- CHECK_AND_ASSERT_MES(r, false, "Failed to parse address from string: " << pr_str);
- m_priority_peers.push_back(na);
- }
+ if (command_line::has_arg(vm,arg_p2p_add_exclusive_node))
+ {
+ if (!parse_peers_and_add_to_container(vm, arg_p2p_add_exclusive_node, m_exclusive_peers))
+ return false;
+ }
+ else if (command_line::has_arg(vm, arg_p2p_add_priority_node))
+ {
+ if (!parse_peers_and_add_to_container(vm, arg_p2p_add_priority_node, m_priority_peers))
+ return false;
}
if (command_line::has_arg(vm, arg_p2p_seed_node))
{
- std::vector<std::string> seed_perrs = command_line::get_arg(vm, arg_p2p_seed_node);
- for(const std::string& pr_str: seed_perrs)
- {
- nodetool::net_address na = AUTO_VAL_INIT(na);
- bool r = parse_peer_from_string(na, pr_str);
- CHECK_AND_ASSERT_MES(r, false, "Failed to parse seed address from string: " << pr_str);
- m_seed_nodes.push_back(na);
- }
+ if (!parse_peers_and_add_to_container(vm, arg_p2p_seed_node, m_seed_nodes))
+ return false;
}
+
if(command_line::has_arg(vm, arg_p2p_hide_my_port))
- m_hide_my_port = true; return true;
+ m_hide_my_port = true;
+
+ return true;
}
//-----------------------------------------------------------------------------------
namespace
@@ -353,23 +354,23 @@ namespace nodetool
get_local_node_data(arg.node_data);
m_payload_handler.get_payload_sync_data(arg.payload_data);
- simple_event ev;
+ epee::simple_event ev;
std::atomic<bool> hsh_result(false);
- bool r = net_utils::async_invoke_remote_command2<typename COMMAND_HANDSHAKE::response>(context_.m_connection_id, COMMAND_HANDSHAKE::ID, arg, m_net_server.get_config_object(),
+ bool r = epee::net_utils::async_invoke_remote_command2<typename COMMAND_HANDSHAKE::response>(context_.m_connection_id, COMMAND_HANDSHAKE::ID, arg, m_net_server.get_config_object(),
[this, &pi, &ev, &hsh_result, &just_take_peerlist](int code, const typename COMMAND_HANDSHAKE::response& rsp, p2p_connection_context& context)
{
- misc_utils::auto_scope_leave_caller scope_exit_handler = misc_utils::create_scope_leave_handler([&](){ev.raise();});
+ epee::misc_utils::auto_scope_leave_caller scope_exit_handler = epee::misc_utils::create_scope_leave_handler([&](){ev.raise();});
if(code < 0)
{
- LOG_PRINT_CC_RED(context, "COMMAND_HANDSHAKE invoke failed. (" << code << ", " << levin::get_err_descr(code) << ")", LOG_LEVEL_1);
+ LOG_PRINT_CC_RED(context, "COMMAND_HANDSHAKE invoke failed. (" << code << ", " << epee::levin::get_err_descr(code) << ")", LOG_LEVEL_1);
return;
}
if(rsp.node_data.network_id != BYTECOIN_NETWORK)
{
- LOG_ERROR_CCONTEXT("COMMAND_HANDSHAKE Failed, wrong network! (" << string_tools::get_str_from_guid_a(rsp.node_data.network_id) << "), closing connection.");
+ LOG_ERROR_CCONTEXT("COMMAND_HANDSHAKE Failed, wrong network! (" << epee::string_tools::get_str_from_guid_a(rsp.node_data.network_id) << "), closing connection.");
return;
}
@@ -397,10 +398,10 @@ namespace nodetool
hsh_result = false;
return;
}
- LOG_PRINT_CCONTEXT_L0(" COMMAND_HANDSHAKE INVOKED OK");
+ LOG_PRINT_CCONTEXT_L1(" COMMAND_HANDSHAKE INVOKED OK");
}else
{
- LOG_PRINT_CCONTEXT_L0(" COMMAND_HANDSHAKE(AND CLOSE) INVOKED OK");
+ LOG_PRINT_CCONTEXT_L1(" COMMAND_HANDSHAKE(AND CLOSE) INVOKED OK");
}
}, P2P_DEFAULT_HANDSHAKE_INVOKE_TIMEOUT);
@@ -411,7 +412,7 @@ namespace nodetool
if(!hsh_result)
{
- LOG_PRINT_CC_L0(context_, "COMMAND_HANDSHAKE Failed");
+ LOG_PRINT_CC_L1(context_, "COMMAND_HANDSHAKE Failed");
m_net_server.get_config_object().close(context_.m_connection_id);
}
@@ -419,17 +420,17 @@ namespace nodetool
}
//-----------------------------------------------------------------------------------
template<class t_payload_net_handler>
- bool node_server<t_payload_net_handler>::do_peer_timed_sync(const net_utils::connection_context_base& context_, peerid_type peer_id)
+ bool node_server<t_payload_net_handler>::do_peer_timed_sync(const epee::net_utils::connection_context_base& context_, peerid_type peer_id)
{
typename COMMAND_TIMED_SYNC::request arg = AUTO_VAL_INIT(arg);
m_payload_handler.get_payload_sync_data(arg.payload_data);
- bool r = net_utils::async_invoke_remote_command2<typename COMMAND_TIMED_SYNC::response>(context_.m_connection_id, COMMAND_TIMED_SYNC::ID, arg, m_net_server.get_config_object(),
+ bool r = epee::net_utils::async_invoke_remote_command2<typename COMMAND_TIMED_SYNC::response>(context_.m_connection_id, COMMAND_TIMED_SYNC::ID, arg, m_net_server.get_config_object(),
[this](int code, const typename COMMAND_TIMED_SYNC::response& rsp, p2p_connection_context& context)
{
if(code < 0)
{
- LOG_PRINT_CC_RED(context, "COMMAND_TIMED_SYNC invoke failed. (" << code << ", " << levin::get_err_descr(code) << ")", LOG_LEVEL_1);
+ LOG_PRINT_CC_RED(context, "COMMAND_TIMED_SYNC invoke failed. (" << code << ", " << epee::levin::get_err_descr(code) << ")", LOG_LEVEL_1);
return;
}
@@ -502,36 +503,53 @@ namespace nodetool
return connected;
}
- //-----------------------------------------------------------------------------------
+#define LOG_PRINT_CC_PRIORITY_NODE(priority, con, msg) \
+ do { \
+ if (priority) {\
+ LOG_PRINT_CC_L0(con, msg); \
+ } else {\
+ LOG_PRINT_CC_L1(con, msg); \
+ } \
+ } while(0)
+
template<class t_payload_net_handler>
bool node_server<t_payload_net_handler>::try_to_connect_and_handshake_with_new_peer(const net_address& na, bool just_take_peerlist, uint64_t last_seen_stamp, bool white)
{
- LOG_PRINT_L0("Connecting to " << string_tools::get_ip_string_from_int32(na.ip) << ":" << string_tools::num_to_string_fast(na.port) << "(white=" << white << ", last_seen: " << (last_seen_stamp?misc_utils::get_time_interval_string(time(NULL) - last_seen_stamp):"never" ) << ")...");
+ LOG_PRINT_L1("Connecting to " << epee::string_tools::get_ip_string_from_int32(na.ip) << ":"
+ << epee::string_tools::num_to_string_fast(na.port) << "(white=" << white << ", last_seen: "
+ << (last_seen_stamp ? epee::misc_utils::get_time_interval_string(time(NULL) - last_seen_stamp):"never")
+ << ")...");
typename net_server::t_connection_context con = AUTO_VAL_INIT(con);
- bool res = m_net_server.connect(string_tools::get_ip_string_from_int32(na.ip),
- string_tools::num_to_string_fast(na.port),
+ bool res = m_net_server.connect(epee::string_tools::get_ip_string_from_int32(na.ip),
+ epee::string_tools::num_to_string_fast(na.port),
m_config.m_net_config.connection_timeout,
con);
+
if(!res)
{
- LOG_PRINT_L0("Connect failed to "
- << string_tools::get_ip_string_from_int32(na.ip)
- << ":" << string_tools::num_to_string_fast(na.port)
+ bool is_priority = is_priority_node(na);
+ LOG_PRINT_CC_PRIORITY_NODE(is_priority, con, "Connect failed to "
+ << epee::string_tools::get_ip_string_from_int32(na.ip)
+ << ":" << epee::string_tools::num_to_string_fast(na.port)
/*<< ", try " << try_count*/);
//m_peerlist.set_peer_unreachable(pe);
return false;
}
+
peerid_type pi = AUTO_VAL_INIT(pi);
res = do_handshake_with_peer(pi, con, just_take_peerlist);
+
if(!res)
{
- LOG_PRINT_CC_L0(con, "Failed to HANDSHAKE with peer "
- << string_tools::get_ip_string_from_int32(na.ip)
- << ":" << string_tools::num_to_string_fast(na.port)
+ bool is_priority = is_priority_node(na);
+ LOG_PRINT_CC_PRIORITY_NODE(is_priority, con, "Failed to HANDSHAKE with peer "
+ << epee::string_tools::get_ip_string_from_int32(na.ip)
+ << ":" << epee::string_tools::num_to_string_fast(na.port)
/*<< ", try " << try_count*/);
return false;
}
+
if(just_take_peerlist)
{
m_net_server.get_config_object().close(con.m_connection_id);
@@ -549,6 +567,9 @@ namespace nodetool
LOG_PRINT_CC_GREEN(con, "CONNECTION HANDSHAKED OK.", LOG_LEVEL_2);
return true;
}
+
+#undef LOG_PRINT_CC_PRIORITY_NODE
+
//-----------------------------------------------------------------------------------
template<class t_payload_net_handler>
bool node_server<t_payload_net_handler>::make_new_connection_from_peerlist(bool use_white_list)
@@ -582,7 +603,10 @@ namespace nodetool
if(is_peer_used(pe))
continue;
- LOG_PRINT_L1("Selected peer: " << pe.id << " " << string_tools::get_ip_string_from_int32(pe.adr.ip) << ":" << boost::lexical_cast<std::string>(pe.adr.port) << "[white=" << use_white_list << "] last_seen: " << (pe.last_seen ? misc_utils::get_time_interval_string(time(NULL) - pe.last_seen) : "never"));
+ LOG_PRINT_L1("Selected peer: " << pe.id << " " << epee::string_tools::get_ip_string_from_int32(pe.adr.ip)
+ << ":" << boost::lexical_cast<std::string>(pe.adr.port)
+ << "[white=" << use_white_list
+ << "] last_seen: " << (pe.last_seen ? epee::misc_utils::get_time_interval_string(time(NULL) - pe.last_seen) : "never"));
if(!try_to_connect_and_handshake_with_new_peer(pe.adr, false, pe.last_seen, use_white_list))
continue;
@@ -595,6 +619,10 @@ namespace nodetool
template<class t_payload_net_handler>
bool node_server<t_payload_net_handler>::connections_maker()
{
+ if (!connect_to_peerlist(m_exclusive_peers)) return false;
+
+ if (!m_exclusive_peers.empty()) return true;
+
if(!m_peerlist.get_white_peers_count() && m_seed_nodes.size())
{
size_t try_count = 0;
@@ -616,15 +644,7 @@ namespace nodetool
}
}
- for(const net_address& na: m_priority_peers)
- {
- if(m_net_server.is_stop_signal_sent())
- return false;
-
- if(is_addr_connected(na))
- continue;
- try_to_connect_and_handshake_with_new_peer(na);
- }
+ if (!connect_to_peerlist(m_priority_peers)) return false;
size_t expected_white_connections = (m_config.m_net_config.connections_count*P2P_DEFAULT_WHITELIST_CONNECTIONS_PERCENT)/100;
@@ -698,7 +718,7 @@ namespace nodetool
bool node_server<t_payload_net_handler>::peer_sync_idle_maker()
{
LOG_PRINT_L2("STARTED PEERLIST IDLE HANDSHAKE");
- typedef std::list<std::pair<net_utils::connection_context_base, peerid_type> > local_connects_type;
+ typedef std::list<std::pair<epee::net_utils::connection_context_base, peerid_type> > local_connects_type;
local_connects_type cncts;
m_net_server.get_config_object().foreach_connection([&](const p2p_connection_context& cntxt)
{
@@ -725,7 +745,7 @@ namespace nodetool
{
if(be.last_seen > local_time)
{
- LOG_PRINT_RED_L0("FOUND FUTURE peerlist for entry " << string_tools::get_ip_string_from_int32(be.adr.ip) << ":" << be.adr.port << " last_seen: " << be.last_seen << ", local_time(on remote node):" << local_time);
+ LOG_PRINT_RED_L0("FOUND FUTURE peerlist for entry " << epee::string_tools::get_ip_string_from_int32(be.adr.ip) << ":" << be.adr.port << " last_seen: " << be.last_seen << ", local_time(on remote node):" << local_time);
return false;
}
be.last_seen += delta;
@@ -734,7 +754,7 @@ namespace nodetool
}
//-----------------------------------------------------------------------------------
template<class t_payload_net_handler>
- bool node_server<t_payload_net_handler>::handle_remote_peerlist(const std::list<peerlist_entry>& peerlist, time_t local_time, const net_utils::connection_context_base& context)
+ bool node_server<t_payload_net_handler>::handle_remote_peerlist(const std::list<peerlist_entry>& peerlist, time_t local_time, const epee::net_utils::connection_context_base& context)
{
int64_t delta = 0;
std::list<peerlist_entry> peerlist_ = peerlist;
@@ -782,7 +802,7 @@ namespace nodetool
return false;
}
crypto::public_key pk = AUTO_VAL_INIT(pk);
- string_tools::hex_to_pod(P2P_STAT_TRUSTED_PUB_KEY, pk);
+ epee::string_tools::hex_to_pod(P2P_STAT_TRUSTED_PUB_KEY, pk);
crypto::hash h = tools::get_proof_of_trust_hash(tr);
if(!crypto::check_signature(h, pk, tr.sign))
{
@@ -903,8 +923,8 @@ namespace nodetool
uint32_t actual_ip = context.m_remote_ip;
if(!m_peerlist.is_ip_allowed(actual_ip))
return false;
- std::string ip = string_tools::get_ip_string_from_int32(actual_ip);
- std::string port = string_tools::num_to_string_fast(node_data.my_port);
+ std::string ip = epee::string_tools::get_ip_string_from_int32(actual_ip);
+ std::string port = epee::string_tools::num_to_string_fast(node_data.my_port);
peerid_type pr = node_data.peer_id;
bool r = m_net_server.connect_async(ip, port, m_config.m_net_config.ping_connection_timeout, [cb, /*context,*/ ip, port, pr, this](
const typename net_server::t_connection_context& ping_context,
@@ -922,12 +942,12 @@ namespace nodetool
std::string port_=port;
peerid_type pr_ = pr;
auto cb_ = cb;*/
- bool inv_call_res = net_utils::async_invoke_remote_command2<COMMAND_PING::response>(ping_context.m_connection_id, COMMAND_PING::ID, req, m_net_server.get_config_object(),
+ bool inv_call_res = epee::net_utils::async_invoke_remote_command2<COMMAND_PING::response>(ping_context.m_connection_id, COMMAND_PING::ID, req, m_net_server.get_config_object(),
[=](int code, const COMMAND_PING::response& rsp, p2p_connection_context& context)
{
if(code <= 0)
{
- LOG_PRINT_CC_L2(ping_context, "Failed to invoke COMMAND_PING to " << ip << ":" << port << "(" << code << ", " << levin::get_err_descr(code) << ")");
+ LOG_PRINT_CC_L2(ping_context, "Failed to invoke COMMAND_PING to " << ip << ":" << port << "(" << code << ", " << epee::levin::get_err_descr(code) << ")");
return;
}
@@ -979,7 +999,7 @@ namespace nodetool
if(arg.node_data.network_id != BYTECOIN_NETWORK)
{
- LOG_PRINT_CCONTEXT_L0("WRONG NETWORK AGENT CONNECTED! id=" << string_tools::get_str_from_guid_a(arg.node_data.network_id));
+ LOG_PRINT_CCONTEXT_L0("WRONG NETWORK AGENT CONNECTED! id=" << epee::string_tools::get_str_from_guid_a(arg.node_data.network_id));
drop_connection(context);
return 1;
}
@@ -1021,7 +1041,7 @@ namespace nodetool
time(&pe.last_seen);
pe.id = peer_id_l;
this->m_peerlist.append_with_peer_white(pe);
- LOG_PRINT_CCONTEXT_L2("PING SUCCESS " << string_tools::get_ip_string_from_int32(context.m_remote_ip) << ":" << port_l);
+ LOG_PRINT_CCONTEXT_L2("PING SUCCESS " << epee::string_tools::get_ip_string_from_int32(context.m_remote_ip) << ":" << port_l);
});
}
@@ -1066,9 +1086,9 @@ namespace nodetool
std::stringstream ss;
m_net_server.get_config_object().foreach_connection([&](const p2p_connection_context& cntxt)
{
- ss << string_tools::get_ip_string_from_int32(cntxt.m_remote_ip) << ":" << cntxt.m_remote_port
+ ss << epee::string_tools::get_ip_string_from_int32(cntxt.m_remote_ip) << ":" << cntxt.m_remote_port
<< " \t\tpeer_id " << cntxt.peer_id
- << " \t\tconn_id " << string_tools::get_str_from_guid_a(cntxt.m_connection_id) << (cntxt.m_is_income ? " INC":" OUT")
+ << " \t\tconn_id " << epee::string_tools::get_str_from_guid_a(cntxt.m_connection_id) << (cntxt.m_is_income ? " INC":" OUT")
<< std::endl;
return true;
});
@@ -1079,13 +1099,51 @@ namespace nodetool
template<class t_payload_net_handler>
void node_server<t_payload_net_handler>::on_connection_new(p2p_connection_context& context)
{
- LOG_PRINT_L2("["<< net_utils::print_connection_context(context) << "] NEW CONNECTION");
+ LOG_PRINT_L2("["<< epee::net_utils::print_connection_context(context) << "] NEW CONNECTION");
}
//-----------------------------------------------------------------------------------
template<class t_payload_net_handler>
void node_server<t_payload_net_handler>::on_connection_close(p2p_connection_context& context)
{
- LOG_PRINT_L2("["<< net_utils::print_connection_context(context) << "] CLOSE CONNECTION");
+ LOG_PRINT_L2("["<< epee::net_utils::print_connection_context(context) << "] CLOSE CONNECTION");
+ }
+
+ template<class t_payload_net_handler>
+ bool node_server<t_payload_net_handler>::is_priority_node(const net_address& na)
+ {
+ return (std::find(m_priority_peers.begin(), m_priority_peers.end(), na) != m_priority_peers.end()) || (std::find(m_exclusive_peers.begin(), m_exclusive_peers.end(), na) != m_exclusive_peers.end());
+ }
+
+ template<class t_payload_net_handler> template <class Container>
+ bool node_server<t_payload_net_handler>::connect_to_peerlist(const Container& peers)
+ {
+ for(const net_address& na: peers)
+ {
+ if(m_net_server.is_stop_signal_sent())
+ return false;
+
+ if(is_addr_connected(na))
+ continue;
+
+ try_to_connect_and_handshake_with_new_peer(na);
+ }
+
+ return true;
+ }
+
+ template<class t_payload_net_handler> template <class Container>
+ bool node_server<t_payload_net_handler>::parse_peers_and_add_to_container(const boost::program_options::variables_map& vm, const command_line::arg_descriptor<std::vector<std::string> > & arg, Container& container)
+ {
+ std::vector<std::string> perrs = command_line::get_arg(vm, arg);
+
+ for(const std::string& pr_str: perrs)
+ {
+ nodetool::net_address na = AUTO_VAL_INIT(na);
+ bool r = parse_peer_from_string(na, pr_str);
+ CHECK_AND_ASSERT_MES(r, false, "Failed to parse address from string: " << pr_str);
+ container.push_back(na);
+ }
+
+ return true;
}
- //-----------------------------------------------------------------------------------
}