big announce / getPeers change

1) getPeers is obsolete, peers are obtained from getData with r="tracker", t="m"
2) announce api of node.cpp is used to update our own memory table (of the tracker)
3) announce api of node.cpp only do getDate/announce to the network if peer is the local one
4) announcement rpc (to the network) might be removed in future (not sure)
This commit is contained in:
Miguel Freitas 2013-08-09 21:34:00 -03:00
parent 6af8185112
commit 662c5fa833
8 changed files with 82 additions and 49 deletions

View File

@ -90,7 +90,8 @@ namespace libtorrent { namespace dht
entry state() const; entry state() const;
void announce(sha1_hash const& ih, int listen_port, bool seed void announce(std::string const& trackerName, sha1_hash const& ih
, address addr, int listen_port, bool seed, bool myself
, boost::function<void(std::vector<tcp::endpoint> const&)> f); , boost::function<void(std::vector<tcp::endpoint> const&)> f);
void putData(std::string const &username, std::string const &resource, bool multi, void putData(std::string const &username, std::string const &resource, bool multi,

View File

@ -69,7 +69,7 @@ public:
void got_write_token(node_id const& n, std::string const& write_token) void got_write_token(node_id const& n, std::string const& write_token)
{ m_write_tokens[n] = write_token; } { m_write_tokens[n] = write_token; }
find_data(node_impl& node, node_id target find_data(node_impl& node, const std::string &trackerName, node_id target
, data_callback const& dcallback , data_callback const& dcallback
, nodes_callback const& ncallback , nodes_callback const& ncallback
, bool noseeds); , bool noseeds);
@ -89,6 +89,7 @@ private:
data_callback m_data_callback; data_callback m_data_callback;
nodes_callback m_nodes_callback; nodes_callback m_nodes_callback;
std::map<node_id, std::string> m_write_tokens; std::map<node_id, std::string> m_write_tokens;
std::string m_trackerName;
node_id const m_target; node_id const m_target;
bool m_done:1; bool m_done:1;
bool m_got_peers:1; bool m_got_peers:1;

View File

@ -210,7 +210,8 @@ public:
{ m_table.print_state(os); } { m_table.print_state(os); }
#endif #endif
void announce(sha1_hash const& info_hash, int listen_port, bool seed void announce(std::string const& trackerName, sha1_hash const& info_hash
, address addr, int listen_port, bool seed, bool myself
, boost::function<void(std::vector<tcp::endpoint> const&)> f); , boost::function<void(std::vector<tcp::endpoint> const&)> f);
void putData(std::string const &username, std::string const &resource, bool multi, void putData(std::string const &username, std::string const &resource, bool multi,
@ -263,8 +264,7 @@ protected:
void lookup_peers(sha1_hash const& info_hash, int prefix, entry& reply void lookup_peers(sha1_hash const& info_hash, int prefix, entry& reply
, bool noseed, bool scrape) const; , bool noseed, bool scrape) const;
bool lookup_torrents(sha1_hash const& target, entry& reply void add_peer(std::string const& name, sha1_hash const& info_hash, address addr, int port, bool seed);
, char* tags) const;
dht_settings const& m_settings; dht_settings const& m_settings;

View File

@ -416,10 +416,11 @@ namespace libtorrent { namespace dht
#endif #endif
} }
void dht_tracker::announce(sha1_hash const& ih, int listen_port, bool seed void dht_tracker::announce(std::string const& trackerName, sha1_hash const& ih
, address addr, int listen_port, bool seed, bool myself
, boost::function<void(std::vector<tcp::endpoint> const&)> f) , boost::function<void(std::vector<tcp::endpoint> const&)> f)
{ {
m_dht.announce(ih, listen_port, seed, f); m_dht.announce(trackerName, ih, addr, listen_port, seed, myself, f);
} }
void dht_tracker::putData(std::string const &username, std::string const &resource, bool multi, void dht_tracker::putData(std::string const &username, std::string const &resource, bool multi,

View File

@ -171,6 +171,7 @@ static void add_entry_fun(void* userdata, node_entry const& e)
find_data::find_data( find_data::find_data(
node_impl& node node_impl& node
, std::string const& trackerName
, node_id target , node_id target
, data_callback const& dcallback , data_callback const& dcallback
, nodes_callback const& ncallback , nodes_callback const& ncallback
@ -178,6 +179,7 @@ find_data::find_data(
: traversal_algorithm(node, target) : traversal_algorithm(node, target)
, m_data_callback(dcallback) , m_data_callback(dcallback)
, m_nodes_callback(ncallback) , m_nodes_callback(ncallback)
, m_trackerName(trackerName)
, m_target(target) , m_target(target)
, m_done(false) , m_done(false)
, m_got_peers(false) , m_got_peers(false)
@ -206,8 +208,12 @@ bool find_data::invoke(observer_ptr o)
entry e; entry e;
e["z"] = "q"; e["z"] = "q";
e["q"] = "getPeers"; e["q"] = "getData"; // "getPeers"
entry& a = e["x"]; entry& a = e["x"];
entry& target = a["target"];
target["n"] = m_trackerName;
target["r"] = "tracker";
target["t"] = "m";
a["infoHash"] = m_target.to_string(); a["infoHash"] = m_target.to_string();
if (m_noseeds) a["noseed"] = 1; if (m_noseeds) a["noseed"] = 1;
return m_node.m_rpc.invoke(e, o->target_ep(), o); return m_node.m_rpc.invoke(e, o->target_ep(), o);

View File

@ -417,18 +417,23 @@ void node_impl::add_node(udp::endpoint node)
m_rpc.invoke(e, node, o); m_rpc.invoke(e, node, o);
} }
void node_impl::announce(sha1_hash const& info_hash, int listen_port, bool seed void node_impl::announce(std::string const& trackerName, sha1_hash const& info_hash, address addr, int listen_port, bool seed, bool myself
, boost::function<void(std::vector<tcp::endpoint> const&)> f) , boost::function<void(std::vector<tcp::endpoint> const&)> f)
{ {
#ifdef TORRENT_DHT_VERBOSE_LOGGING #ifdef TORRENT_DHT_VERBOSE_LOGGING
TORRENT_LOG(node) << "announcing [ ih: " << info_hash << " p: " << listen_port << " ]" ; TORRENT_LOG(node) << "announcing [ ih: " << info_hash << " p: " << listen_port << " ]" ;
#endif #endif
// search for nodes with ids close to id or with peers add_peer( trackerName, info_hash, addr, listen_port, seed );
// for info-hash id. then send announce_peer to them.
boost::intrusive_ptr<find_data> ta(new find_data(*this, info_hash, f // do not announce other peers, just add them to our local m_map.
, boost::bind(&announce_fun, _1, boost::ref(*this) if( myself ) {
, listen_port, info_hash, seed), seed)); // search for nodes with ids close to id or with peers
ta->start(); // for info-hash id. then send announce_peer to them.
boost::intrusive_ptr<find_data> ta(new find_data(*this, trackerName, info_hash, f
, boost::bind(&announce_fun, _1, boost::ref(*this)
, listen_port, info_hash, seed), seed));
ta->start();
}
} }
void node_impl::putData(std::string const &username, std::string const &resource, bool multi, void node_impl::putData(std::string const &username, std::string const &resource, bool multi,
@ -592,6 +597,27 @@ void node_impl::lookup_peers(sha1_hash const& info_hash, int prefix, entry& repl
return; return;
} }
void node_impl::add_peer(std::string const &name, sha1_hash const& info_hash, address addr, int port, bool seed)
{
torrent_entry& v = m_map[info_hash];
// the peer announces a torrent name, and we don't have a name
// for this torrent. Store it.
if (name.size() && v.name.empty())
{
v.name = name;
if (v.name.size() > 50) v.name.resize(50);
}
peer_entry peer;
peer.addr = tcp::endpoint(addr, port);
peer.added = time_now();
peer.seed = seed;
std::set<peer_entry>::iterator i = v.peers.find(peer);
if (i != v.peers.end()) v.peers.erase(i++);
v.peers.insert(i, peer);
}
namespace namespace
{ {
void write_nodes_entry(entry& r, nodes_t const& nodes) void write_nodes_entry(entry& r, nodes_t const& nodes)
@ -774,6 +800,7 @@ void node_impl::incoming_request(msg const& m, entry& e)
// we already have 't' and 'id' in the response // we already have 't' and 'id' in the response
// no more left to add // no more left to add
} }
/*
else if (strcmp(query, "getPeers") == 0) else if (strcmp(query, "getPeers") == 0)
{ {
key_desc_t msg_desc[] = { key_desc_t msg_desc[] = {
@ -813,7 +840,7 @@ void node_impl::incoming_request(msg const& m, entry& e)
TORRENT_LOG(node) << " values: " << reply["values"].list().size(); TORRENT_LOG(node) << " values: " << reply["values"].list().size();
} }
#endif #endif
} }*/
else if (strcmp(query, "findNode") == 0) else if (strcmp(query, "findNode") == 0)
{ {
key_desc_t msg_desc[] = { key_desc_t msg_desc[] = {
@ -909,24 +936,10 @@ void node_impl::incoming_request(msg const& m, entry& e)
} }
m_map.erase(candidate); m_map.erase(candidate);
} }
torrent_entry& v = m_map[info_hash];
// the peer announces a torrent name, and we don't have a name add_peer( msg_keys[3] ? msg_keys[3]->string_value() : std::string(), info_hash,
// for this torrent. Store it. m.addr.address(), port, msg_keys[4] && msg_keys[4]->int_value());
if (msg_keys[3] && v.name.empty())
{
std::string name = msg_keys[3]->string_value();
if (name.size() > 50) name.resize(50);
v.name = name;
}
peer_entry peer;
peer.addr = tcp::endpoint(m.addr.address(), port);
peer.added = time_now();
peer.seed = msg_keys[4] && msg_keys[4]->int_value();
std::set<peer_entry>::iterator i = v.peers.find(peer);
if (i != v.peers.end()) v.peers.erase(i++);
v.peers.insert(i, peer);
#ifdef TORRENT_DHT_VERBOSE_LOGGING #ifdef TORRENT_DHT_VERBOSE_LOGGING
++g_announces; ++g_announces;
#endif #endif
@ -1135,6 +1148,12 @@ void node_impl::incoming_request(msg const& m, entry& e)
return; return;
} }
if (msg_keys[mk_t]->string_value() != "s" &&
msg_keys[mk_t]->string_value() != "m") {
incoming_error(e, "invalid target.t value");
return;
}
// target id is hash of bencoded dict "target" // target id is hash of bencoded dict "target"
std::pair<char const*, int> targetbuf = msg_keys[mk_target]->data_section(); std::pair<char const*, int> targetbuf = msg_keys[mk_target]->data_section();
sha1_hash target = hasher(targetbuf.first,targetbuf.second).final(); sha1_hash target = hasher(targetbuf.first,targetbuf.second).final();
@ -1159,22 +1178,27 @@ void node_impl::incoming_request(msg const& m, entry& e)
write_nodes_entry(reply, n); write_nodes_entry(reply, n);
bool hasData = false; bool hasData = false;
dht_storage_table_t::iterator i = m_storage_table.find(target);
if (i != m_storage_table.end())
{
hasData = true;
reply["values"] = entry::list_type();
entry::list_type &values = reply["values"].list();
dht_storage_list_t const& lsto = i->second; if( msg_keys[mk_r]->string_value() == "tracker" ) {
for (dht_storage_list_t::const_iterator j = lsto.begin() lookup_peers(target, 20, reply, false, false);
, end(lsto.end()); j != end && !justtoken; ++j) } else {
dht_storage_table_t::iterator i = m_storage_table.find(target);
if (i != m_storage_table.end())
{ {
entry::dictionary_type v; hasData = true;
v["p"] = bdecode(j->p.begin(), j->p.end()); reply["values"] = entry::list_type();
v["sig_p"] = j->sig_p; entry::list_type &values = reply["values"].list();
v["sig_user"] = j->sig_user;
values.push_back(v); dht_storage_list_t const& lsto = i->second;
for (dht_storage_list_t::const_iterator j = lsto.begin()
, end(lsto.end()); j != end && !justtoken; ++j)
{
entry::dictionary_type v;
v["p"] = bdecode(j->p.begin(), j->p.end());
v["sig_p"] = j->sig_p;
v["sig_user"] = j->sig_user;
values.push_back(v);
}
} }
} }

View File

@ -49,7 +49,7 @@ refresh::refresh(
node_impl& node node_impl& node
, node_id target , node_id target
, done_callback const& callback) , done_callback const& callback)
: find_data(node, target, find_data::data_callback(), callback, false) : find_data(node, std::string(), target, find_data::data_callback(), callback, false)
{ {
} }

View File

@ -2245,8 +2245,8 @@ namespace libtorrent
#endif #endif
boost::weak_ptr<torrent> self(shared_from_this()); boost::weak_ptr<torrent> self(shared_from_this());
m_ses.m_dht->announce(m_torrent_file->info_hash() m_ses.m_dht->announce(m_torrent_file->name(), m_torrent_file->info_hash()
, port, is_seed() , m_ses.external_address().external_address(address_v4()), port, is_seed(), true
, boost::bind(&torrent::on_dht_announce_response_disp, self, _1)); , boost::bind(&torrent::on_dht_announce_response_disp, self, _1));
} }