fixed bug in connect candidate counter

This commit is contained in:
Arvid Norberg 2009-06-18 16:16:41 +00:00
parent b8f17f34e3
commit 6b048dc85e
7 changed files with 63 additions and 11 deletions

View File

@ -62,6 +62,7 @@ release 0.14.5
* fixed bug when setting unlimited upload or download rates for torrents
* fix to make torrent_status::list_peers more accurate.
* fixed memory leak in disk io thread when not using the cache
* fixed bug in connect candidate counter
release 0.14.4

View File

@ -88,6 +88,8 @@ namespace libtorrent
// the given connection was just closed
void connection_closed(const peer_connection& c, int session_time);
void ban_peer(policy::peer* p);
// the peer has got at least one interesting piece
void peer_is_interesting(peer_connection& c);

View File

@ -4247,7 +4247,8 @@ namespace libtorrent
{
// if the remote endpoint is the same as the local endpoint, we're connected
// to ourselves
if (m_peer_info) m_peer_info->banned = true;
boost::shared_ptr<torrent> t = m_torrent.lock();
if (m_peer_info && t) t->get_policy().ban_peer(m_peer_info);
disconnect(error_code(errors::self_connection, libtorrent_category), 1);
return;
}

View File

@ -408,7 +408,10 @@ namespace libtorrent
m_torrent->picker().clear_peer(*i);
if ((*i)->seed) --m_num_seeds;
if (is_connect_candidate(**i, m_finished))
{
TORRENT_ASSERT(m_num_connect_candidates > 0);
--m_num_connect_candidates;
}
if (m_round_robin > i - m_peers.begin()) --m_round_robin;
#if TORRENT_USE_IPV6
@ -488,6 +491,16 @@ namespace libtorrent
erase_peer(m_peers.begin() + erase_candidate);
}
void policy::ban_peer(policy::peer* p)
{
INVARIANT_CHECK;
if (is_connect_candidate(*p, m_finished))
--m_num_connect_candidates;
p->banned = true;
}
bool policy::is_connect_candidate(peer const& p, bool finished) const
{
if (p.connection
@ -714,6 +727,8 @@ namespace libtorrent
if (iter != m_peers.end() && (*iter)->address() == c.remote().address()) found = true;
}
bool was_conn_cand = false;
if (found)
{
i = *iter;
@ -724,6 +739,8 @@ namespace libtorrent
return false;
}
was_conn_cand = is_connect_candidate(*i, m_finished);
if (i->connection != 0)
{
boost::shared_ptr<socket_type> other_socket
@ -772,9 +789,6 @@ namespace libtorrent
i->connection->disconnect(error_code(errors::duplicate_peer_id, libtorrent_category));
}
}
if (m_num_connect_candidates > 0)
--m_num_connect_candidates;
}
else
{
@ -836,6 +850,13 @@ namespace libtorrent
TORRENT_ASSERT(i->connection);
if (!c.fast_reconnect())
i->last_connected = session_time;
if (was_conn_cand != is_connect_candidate(*i, m_finished))
{
m_num_connect_candidates += was_conn_cand ? -1 : 1;
TORRENT_ASSERT(m_num_connect_candidates >= 0);
if (m_num_connect_candidates < 0) m_num_connect_candidates = 0;
}
return true;
}
@ -844,6 +865,8 @@ namespace libtorrent
TORRENT_ASSERT(p != 0);
TORRENT_ASSERT(p->connection);
INVARIANT_CHECK;
if (p->port == port) return true;
if (m_torrent->settings().allow_multiple_connections_per_ip)
@ -857,7 +880,15 @@ namespace libtorrent
policy::peer& pp = **i;
if (pp.connection)
{
bool was_conn_cand = is_connect_candidate(pp, m_finished);
// if we already have an entry with this
// new endpoint, disconnect this one
pp.connectable = true;
pp.source |= src;
if (!was_conn_cand && is_connect_candidate(pp, m_finished))
++m_num_connect_candidates;
p->connection->disconnect(error_code(errors::duplicate_peer_id, libtorrent_category));
erase_peer(p);
return false;
}
erase_peer(i);
@ -879,6 +910,7 @@ namespace libtorrent
if (was_conn_cand != is_connect_candidate(*p, m_finished))
{
m_num_connect_candidates += was_conn_cand ? -1 : 1;
TORRENT_ASSERT(m_num_connect_candidates >= 0);
if (m_num_connect_candidates < 0) m_num_connect_candidates = 0;
}
return true;
@ -899,7 +931,14 @@ namespace libtorrent
{
if (p == 0) return;
if (p->seed == s) return;
bool was_conn_cand = is_connect_candidate(*p, m_finished);
p->seed = s;
if (was_conn_cand && !is_connect_candidate(*p, m_finished))
{
--m_num_connect_candidates;
if (m_num_connect_candidates < 0) m_num_connect_candidates = 0;
}
if (s) ++m_num_seeds;
else --m_num_seeds;
}
@ -1220,6 +1259,8 @@ namespace libtorrent
{
// failcount is a 5 bit value
if (p.failcount < 31) ++p.failcount;
if (!is_connect_candidate(p, m_finished))
--m_num_connect_candidates;
return false;
}
TORRENT_ASSERT(p.connection);
@ -1308,10 +1349,12 @@ namespace libtorrent
void policy::recalculate_connect_candidates()
{
m_num_connect_candidates = 0;
INVARIANT_CHECK;
const bool is_finished = m_torrent->is_finished();
if (is_finished == m_finished) return;
m_num_connect_candidates = 0;
m_finished = is_finished;
for (const_iterator i = m_peers.begin();
i != m_peers.end(); ++i)
@ -1346,6 +1389,7 @@ namespace libtorrent
int total_connections = 0;
int nonempty_connections = 0;
int connect_candidates = 0;
std::set<tcp::endpoint> unique_test;
const_iterator prev = m_peers.end();
@ -1362,6 +1406,7 @@ namespace libtorrent
TORRENT_ASSERT((*prev)->address() < (*i)->address());
}
peer const& p = **i;
if (is_connect_candidate(p, m_finished)) ++connect_candidates;
#ifndef TORRENT_DISABLE_GEO_IP
TORRENT_ASSERT(p.inet_as == 0 || p.inet_as->first == p.inet_as_num);
#endif
@ -1395,6 +1440,8 @@ namespace libtorrent
++connected_peers;
}
TORRENT_ASSERT(m_num_connect_candidates == connect_candidates);
int num_torrent_peers = 0;
for (torrent::const_peer_iterator i = m_torrent->begin();
i != m_torrent->end(); ++i)

View File

@ -609,6 +609,7 @@ namespace aux {
void session_impl::set_port_filter(port_filter const& f)
{
m_port_filter = f;
// TODO: recalculate all connect candidates for all torrents
}
void session_impl::set_ip_filter(ip_filter const& f)

View File

@ -213,7 +213,7 @@ namespace libtorrent { namespace
<< " | crc2: " << e.crc
<< " | ip: " << p->ip() << " ]\n";
#endif
p->banned = true;
m_torrent.get_policy().ban_peer(p);
if (p->connection) p->connection->disconnect(
error_code(errors::peer_banned, libtorrent_category));
}
@ -276,7 +276,7 @@ namespace libtorrent { namespace
<< " | bad_crc: " << b.second.crc
<< " | ip: " << p->ip() << " ]\n";
#endif
p->banned = true;
m_torrent.get_policy().ban_peer(p);
if (p->connection) p->connection->disconnect(
error_code(errors::peer_banned, libtorrent_category));
}

View File

@ -718,7 +718,7 @@ namespace libtorrent
{
policy::peer* p = m_policy.add_peer(read_v4_endpoint<tcp::endpoint>(ptr)
, id, peer_info::resume_data, 0);
if (p) p->banned = true;
if (p) m_policy.ban_peer(p);
}
}
@ -742,7 +742,7 @@ namespace libtorrent
{
policy::peer* p = m_policy.add_peer(read_v6_endpoint<tcp::endpoint>(ptr)
, id, peer_info::resume_data, 0);
if (p) p->banned = true;
if (p) m_policy.ban_peer(p);
}
}
#endif
@ -778,7 +778,7 @@ namespace libtorrent
tcp::endpoint a(address::from_string(ip, ec), (unsigned short)port);
if (ec) continue;
policy::peer* p = m_policy.add_peer(a, id, peer_info::resume_data, 0);
if (p) p->banned = true;
if (p) m_policy.ban_peer(p);
}
}
}
@ -1916,7 +1916,7 @@ namespace libtorrent
}
// mark the peer as banned
p->banned = true;
m_policy.ban_peer(p);
if (p->connection)
{