many fixes in libtorrent sync 1586

This commit is contained in:
Marcos Pinto 2007-09-19 20:39:29 +00:00
parent 760acc8f30
commit cd10e9bbaa
8 changed files with 251 additions and 100 deletions

View File

@ -180,12 +180,8 @@ struct bandwidth_manager
, m_limit(bandwidth_limit::inf) , m_limit(bandwidth_limit::inf)
, m_current_quota(0) , m_current_quota(0)
, m_channel(channel) , m_channel(channel)
{ , m_in_hand_out_bandwidth(false)
{}
#ifndef NDEBUG
m_in_hand_out_bandwidth = false;
#endif
}
void throttle(int limit) throw() void throttle(int limit) throw()
{ {
@ -333,10 +329,11 @@ private:
void hand_out_bandwidth() throw() void hand_out_bandwidth() throw()
{ {
#ifndef NDEBUG // if we're already handing out bandwidth, just return back
assert(m_in_hand_out_bandwidth == false); // to the loop further down on the callstack
if (m_in_hand_out_bandwidth) return;
m_in_hand_out_bandwidth = true; m_in_hand_out_bandwidth = true;
#ifndef NDEBUG
try { try {
#endif #endif
INVARIANT_CHECK; INVARIANT_CHECK;
@ -451,9 +448,8 @@ private:
} }
catch (std::exception& e) catch (std::exception& e)
{ assert(false); }; { assert(false); };
m_in_hand_out_bandwidth = false;
#endif #endif
m_in_hand_out_bandwidth = false;
} }
@ -487,9 +483,9 @@ private:
// that bandwidth is assigned to (upload or download) // that bandwidth is assigned to (upload or download)
int m_channel; int m_channel;
#ifndef NDEBUG // this is true while we're in the hand_out_bandwidth loop
// to prevent recursive invocations to interfere
bool m_in_hand_out_bandwidth; bool m_in_hand_out_bandwidth;
#endif
}; };

View File

@ -344,7 +344,8 @@ namespace libtorrent
std::multimap<sha1_hash, int> m_hash_to_piece; std::multimap<sha1_hash, int> m_hash_to_piece;
// this map contains partial hashes for downloading // this map contains partial hashes for downloading
// pieces. // pieces. This is only accessed from within the
// disk-io thread.
std::map<int, partial_hash> m_piece_hasher; std::map<int, partial_hash> m_piece_hasher;
disk_io_thread& m_io_thread; disk_io_thread& m_io_thread;
@ -362,3 +363,4 @@ namespace libtorrent
#endif // TORRENT_STORAGE_HPP_INCLUDED #endif // TORRENT_STORAGE_HPP_INCLUDED

View File

@ -399,6 +399,7 @@ namespace libtorrent
, m_info_hash(h) , m_info_hash(h)
{ {
assert(m_ses != 0); assert(m_ses != 0);
assert(m_chk != 0);
} }
#ifndef NDEBUG #ifndef NDEBUG
@ -416,3 +417,4 @@ namespace libtorrent
#endif // TORRENT_TORRENT_HANDLE_HPP_INCLUDED #endif // TORRENT_TORRENT_HANDLE_HPP_INCLUDED

View File

@ -1952,7 +1952,6 @@ namespace libtorrent
} }
t->remove_peer(this); t->remove_peer(this);
m_torrent.reset(); m_torrent.reset();
} }
@ -2856,6 +2855,8 @@ namespace libtorrent
return; return;
} }
assert(t->connection_for(remote()) != 0 || m_in_constructor);
if (!m_in_constructor && t->connection_for(remote()) != this if (!m_in_constructor && t->connection_for(remote()) != this
&& !m_ses.settings().allow_multiple_connections_per_ip) && !m_ses.settings().allow_multiple_connections_per_ip)
{ {
@ -3021,3 +3022,4 @@ namespace libtorrent
} }
} }

View File

@ -138,28 +138,28 @@ namespace
return free_upload; return free_upload;
} }
struct match_peer_ip struct match_peer_address
{ {
match_peer_ip(address const& ip) match_peer_address(address const& addr)
: m_ip(ip) : m_addr(addr)
{} {}
bool operator()(policy::peer const& p) const bool operator()(policy::peer const& p) const
{ return p.ip.address() == m_ip; } { return p.ip.address() == m_addr; }
address const& m_ip; address const& m_addr;
}; };
struct match_peer_id struct match_peer_endpoint
{ {
match_peer_id(peer_id const& id_) match_peer_endpoint(tcp::endpoint const& ep)
: m_id(id_) : m_ep(ep)
{} {}
bool operator()(policy::peer const& p) const bool operator()(policy::peer const& p) const
{ return p.connection && p.connection->pid() == m_id; } { return p.ip == m_ep; }
peer_id const& m_id; tcp::endpoint const& m_ep;
}; };
struct match_peer_connection struct match_peer_connection
@ -939,7 +939,7 @@ namespace libtorrent
i = std::find_if( i = std::find_if(
m_peers.begin() m_peers.begin()
, m_peers.end() , m_peers.end()
, match_peer_ip(c.remote().address())); , match_peer_address(c.remote().address()));
} }
if (i != m_peers.end()) if (i != m_peers.end())
@ -1029,14 +1029,14 @@ namespace libtorrent
i = std::find_if( i = std::find_if(
m_peers.begin() m_peers.begin()
, m_peers.end() , m_peers.end()
, match_peer_id(pid)); , match_peer_endpoint(remote));
} }
else else
{ {
i = std::find_if( i = std::find_if(
m_peers.begin() m_peers.begin()
, m_peers.end() , m_peers.end()
, match_peer_ip(remote.address())); , match_peer_address(remote.address()));
} }
if (i == m_peers.end()) if (i == m_peers.end())
@ -1291,9 +1291,15 @@ namespace libtorrent
try try
{ {
INVARIANT_CHECK;
p->connected = time_now(); p->connected = time_now();
p->connection = m_torrent->connect_to_peer(&*p); p->connection = m_torrent->connect_to_peer(&*p);
if (p->connection == 0) return false; assert(p->connection == m_torrent->connection_for(p->ip));
if (p->connection == 0)
{
++p->failcount;
return false;
}
p->connection->add_stat(p->prev_amount_download, p->prev_amount_upload); p->connection->add_stat(p->prev_amount_download, p->prev_amount_upload);
p->prev_amount_download = 0; p->prev_amount_download = 0;
p->prev_amount_upload = 0; p->prev_amount_upload = 0;
@ -1305,6 +1311,7 @@ namespace libtorrent
(*m_torrent->session().m_logger) << "*** CONNECTION FAILED '" (*m_torrent->session().m_logger) << "*** CONNECTION FAILED '"
<< e.what() << "'\n"; << e.what() << "'\n";
#endif #endif
std::cerr << e.what() << std::endl;
++p->failcount; ++p->failcount;
return false; return false;
} }
@ -1402,15 +1409,22 @@ namespace libtorrent
int nonempty_connections = 0; int nonempty_connections = 0;
std::set<address> unique_test; std::set<address> unique_test;
std::set<tcp::endpoint> unique_test2;
for (const_iterator i = m_peers.begin(); for (const_iterator i = m_peers.begin();
i != m_peers.end(); ++i) i != m_peers.end(); ++i)
{ {
peer const& p = *i; peer const& p = *i;
if (!m_torrent->settings().allow_multiple_connections_per_ip) if (!m_torrent->settings().allow_multiple_connections_per_ip)
assert(unique_test.find(p.ip.address()) == unique_test.end()); assert(unique_test.find(p.ip.address()) == unique_test.end());
assert(unique_test2.find(p.ip) == unique_test2.end());
unique_test.insert(p.ip.address()); unique_test.insert(p.ip.address());
unique_test2.insert(p.ip);
++total_connections; ++total_connections;
if (!p.connection) continue; if (!p.connection)
{
// assert(m_torrent->connection_for(p.ip) == 0);
continue;
}
if (!m_torrent->settings().allow_multiple_connections_per_ip) if (!m_torrent->settings().allow_multiple_connections_per_ip)
{ {
std::vector<peer_connection*> conns; std::vector<peer_connection*> conns;
@ -1537,3 +1551,4 @@ namespace libtorrent
} }
} }

View File

@ -400,16 +400,20 @@ namespace libtorrent
partial.update(&m_scratch_buffer[0], ph.offset); partial.update(&m_scratch_buffer[0], ph.offset);
whole.update(&m_scratch_buffer[0], slot_size1); whole.update(&m_scratch_buffer[0], slot_size1);
hasher partial_copy = ph.h; hasher partial_copy = ph.h;
std::cerr << partial_copy.final() << " " << partial.final() << std::endl;
assert(ph.offset == 0 || partial_copy.final() == partial.final()); assert(ph.offset == 0 || partial_copy.final() == partial.final());
#endif #endif
int slot_size = piece_size - ph.offset; int slot_size = piece_size - ph.offset;
if (slot_size == 0) return ph.h.final(); if (slot_size == 0)
{
assert(ph.h.final() == whole.final());
return ph.h.final();
}
m_scratch_buffer.resize(slot_size); m_scratch_buffer.resize(slot_size);
read_impl(&m_scratch_buffer[0], slot, ph.offset, slot_size, true); read_impl(&m_scratch_buffer[0], slot, ph.offset, slot_size, true);
ph.h.update(&m_scratch_buffer[0], slot_size); ph.h.update(&m_scratch_buffer[0], slot_size);
sha1_hash ret = ph.h.final(); assert(whole.final() == ph.h.final());
assert(whole.final() == ret); return ph.h.final();
return ret;
} }
void storage::initialize(bool allocate_files) void storage::initialize(bool allocate_files)
@ -996,9 +1000,6 @@ namespace libtorrent
int err = statfs(query_path.native_directory_string().c_str(), &buf); int err = statfs(query_path.native_directory_string().c_str(), &buf);
if (err == 0) if (err == 0)
{ {
#ifndef NDEBUG
std::cerr << "buf.f_type " << std::hex << buf.f_type << std::endl;
#endif
switch (buf.f_type) switch (buf.f_type)
{ {
case 0x5346544e: // NTFS case 0x5346544e: // NTFS
@ -1297,6 +1298,7 @@ namespace libtorrent
if (i != m_piece_hasher.end()) if (i != m_piece_hasher.end())
{ {
assert(i->second.offset > 0); assert(i->second.offset > 0);
assert(offset >= i->second.offset);
if (offset == i->second.offset) if (offset == i->second.offset)
{ {
i->second.offset += size; i->second.offset += size;
@ -2211,3 +2213,4 @@ namespace libtorrent
#endif #endif
} // namespace libtorrent } // namespace libtorrent

View File

@ -1653,6 +1653,7 @@ namespace libtorrent
assert(m_connections.find(a) == m_connections.end()); assert(m_connections.find(a) == m_connections.end());
// add the newly connected peer to this torrent's peer list // add the newly connected peer to this torrent's peer list
assert(m_connections.find(a) == m_connections.end());
m_connections.insert( m_connections.insert(
std::make_pair(a, boost::get_pointer(c))); std::make_pair(a, boost::get_pointer(c)));
m_ses.m_connections.insert(std::make_pair(s, c)); m_ses.m_connections.insert(std::make_pair(s, c));
@ -1669,8 +1670,8 @@ namespace libtorrent
#endif #endif
// TODO: post an error alert! // TODO: post an error alert!
std::map<tcp::endpoint, peer_connection*>::iterator i = m_connections.find(a); // std::map<tcp::endpoint, peer_connection*>::iterator i = m_connections.find(a);
if (i != m_connections.end()) m_connections.erase(i); // if (i != m_connections.end()) m_connections.erase(i);
m_ses.connection_failed(s, a, e.what()); m_ses.connection_failed(s, a, e.what());
c->disconnect(); c->disconnect();
} }
@ -1857,6 +1858,8 @@ namespace libtorrent
try try
{ {
assert(m_connections.find(a) == m_connections.end());
// add the newly connected peer to this torrent's peer list // add the newly connected peer to this torrent's peer list
m_connections.insert( m_connections.insert(
std::make_pair(a, boost::get_pointer(c))); std::make_pair(a, boost::get_pointer(c)));
@ -1869,6 +1872,7 @@ namespace libtorrent
} }
catch (std::exception& e) catch (std::exception& e)
{ {
assert(false);
// TODO: post an error alert! // TODO: post an error alert!
std::map<tcp::endpoint, peer_connection*>::iterator i = m_connections.find(a); std::map<tcp::endpoint, peer_connection*>::iterator i = m_connections.find(a);
if (i != m_connections.end()) m_connections.erase(i); if (i != m_connections.end()) m_connections.erase(i);
@ -1925,6 +1929,7 @@ namespace libtorrent
= m_connections.find(p->remote()); = m_connections.find(p->remote());
if (c != m_connections.end()) if (c != m_connections.end())
{ {
assert(p != c->second);
// we already have a peer_connection to this ip. // we already have a peer_connection to this ip.
// It may currently be waiting for completing a // It may currently be waiting for completing a
// connection attempt that might fail. So, // connection attempt that might fail. So,
@ -1948,6 +1953,7 @@ namespace libtorrent
throw protocol_error("session is closing"); throw protocol_error("session is closing");
} }
assert(m_connections.find(p->remote()) == m_connections.end());
peer_iterator ci = m_connections.insert( peer_iterator ci = m_connections.insert(
std::make_pair(p->remote(), p)).first; std::make_pair(p->remote(), p)).first;
try try
@ -2408,6 +2414,12 @@ namespace libtorrent
assert(m_abort || m_have_pieces.empty()); assert(m_abort || m_have_pieces.empty());
} }
/* for (policy::const_iterator i = m_policy->begin_peer()
, end(m_policy->end_peer()); i != end; ++i)
{
assert(i->connection == const_cast<torrent*>(this)->connection_for(i->ip));
}
*/
size_type total_done = quantized_bytes_done(); size_type total_done = quantized_bytes_done();
if (m_torrent_file->is_valid()) if (m_torrent_file->is_valid())
{ {
@ -2925,3 +2937,4 @@ namespace libtorrent
} }

View File

@ -94,18 +94,11 @@ namespace libtorrent
, aux::checker_impl* chk , aux::checker_impl* chk
, sha1_hash const& hash) , sha1_hash const& hash)
{ {
if (ses == 0) throw_invalid_handle(); aux::piece_checker_data* d = chk->find_torrent(hash);
if (d != 0) return d->torrent_ptr;
if (chk) boost::shared_ptr<torrent> t = ses->find_torrent(hash).lock();
{ if (t) return t;
aux::piece_checker_data* d = chk->find_torrent(hash);
if (d != 0) return d->torrent_ptr;
}
{
boost::shared_ptr<torrent> t = ses->find_torrent(hash).lock();
if (t) return t;
}
// throwing directly instead of calling // throwing directly instead of calling
// the throw_invalid_handle() function // the throw_invalid_handle() function
@ -118,7 +111,7 @@ namespace libtorrent
void torrent_handle::check_invariant() const void torrent_handle::check_invariant() const
{ {
assert((m_ses == 0 && m_chk == 0) || (m_ses != 0)); assert((m_ses == 0 && m_chk == 0) || (m_ses != 0 && m_chk != 0));
} }
#endif #endif
@ -127,6 +120,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
assert(max_uploads >= 2 || max_uploads == -1); assert(max_uploads >= 2 || max_uploads == -1);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
@ -138,6 +134,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->use_interface(net_interface); find_torrent(m_ses, m_chk, m_info_hash)->use_interface(net_interface);
@ -147,6 +146,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
assert(max_connections >= 2 || max_connections == -1); assert(max_connections >= 2 || max_connections == -1);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
@ -159,6 +161,9 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
assert(limit >= -1); assert(limit >= -1);
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->set_peer_upload_limit(ip, limit); find_torrent(m_ses, m_chk, m_info_hash)->set_peer_upload_limit(ip, limit);
@ -169,6 +174,9 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
assert(limit >= -1); assert(limit >= -1);
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->set_peer_download_limit(ip, limit); find_torrent(m_ses, m_chk, m_info_hash)->set_peer_download_limit(ip, limit);
@ -178,6 +186,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
assert(limit >= -1); assert(limit >= -1);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
@ -188,6 +199,10 @@ namespace libtorrent
int torrent_handle::upload_limit() const int torrent_handle::upload_limit() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->upload_limit(); return find_torrent(m_ses, m_chk, m_info_hash)->upload_limit();
@ -197,6 +212,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
assert(limit >= -1); assert(limit >= -1);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
@ -208,6 +226,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->download_limit(); return find_torrent(m_ses, m_chk, m_info_hash)->download_limit();
@ -218,6 +239,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->move_storage(save_path); find_torrent(m_ses, m_chk, m_info_hash)->move_storage(save_path);
@ -227,6 +251,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->valid_metadata(); return find_torrent(m_ses, m_chk, m_info_hash)->valid_metadata();
@ -236,6 +263,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->is_seed(); return find_torrent(m_ses, m_chk, m_info_hash)->is_seed();
@ -245,6 +275,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->is_paused(); return find_torrent(m_ses, m_chk, m_info_hash)->is_paused();
@ -254,6 +287,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->pause(); find_torrent(m_ses, m_chk, m_info_hash)->pause();
@ -263,6 +299,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->resume(); find_torrent(m_ses, m_chk, m_info_hash)->resume();
@ -273,6 +312,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->set_tracker_login(name, password); find_torrent(m_ses, m_chk, m_info_hash)->set_tracker_login(name, password);
@ -283,31 +325,27 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex);
if (m_chk) aux::piece_checker_data* d = m_chk->find_torrent(m_info_hash);
if (d != 0)
{ {
mutex::scoped_lock l(m_chk->m_mutex); if (!d->processing)
aux::piece_checker_data* d = m_chk->find_torrent(m_info_hash);
if (d != 0)
{ {
if (!d->processing) torrent_info const& info = d->torrent_ptr->torrent_file();
{ progress.clear();
torrent_info const& info = d->torrent_ptr->torrent_file(); progress.resize(info.num_files(), 0.f);
progress.clear();
progress.resize(info.num_files(), 0.f);
return;
}
d->torrent_ptr->file_progress(progress);
return; return;
} }
d->torrent_ptr->file_progress(progress);
return;
} }
{ boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); if (t) return t->file_progress(progress);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
if (t) return t->file_progress(progress);
}
throw_invalid_handle(); throw_invalid_handle();
} }
@ -317,36 +355,32 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex);
if (m_chk) aux::piece_checker_data* d = m_chk->find_torrent(m_info_hash);
if (d != 0)
{ {
mutex::scoped_lock l(m_chk->m_mutex); torrent_status st;
aux::piece_checker_data* d = m_chk->find_torrent(m_info_hash); if (d->processing)
if (d != 0)
{ {
torrent_status st; if (d->torrent_ptr->is_allocating())
st.state = torrent_status::allocating;
if (d->processing)
{
if (d->torrent_ptr->is_allocating())
st.state = torrent_status::allocating;
else
st.state = torrent_status::checking_files;
}
else else
st.state = torrent_status::queued_for_checking; st.state = torrent_status::checking_files;
st.progress = d->progress;
st.paused = d->torrent_ptr->is_paused();
return st;
} }
else
st.state = torrent_status::queued_for_checking;
st.progress = d->progress;
st.paused = d->torrent_ptr->is_paused();
return st;
} }
{ boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); if (t) return t->status();
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
if (t) return t->status();
}
throw_invalid_handle(); throw_invalid_handle();
return torrent_status(); return torrent_status();
@ -355,6 +389,10 @@ namespace libtorrent
void torrent_handle::set_sequenced_download_threshold(int threshold) const void torrent_handle::set_sequenced_download_threshold(int threshold) const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->set_sequenced_download_threshold(threshold); find_torrent(m_ses, m_chk, m_info_hash)->set_sequenced_download_threshold(threshold);
@ -364,6 +402,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->name(); return find_torrent(m_ses, m_chk, m_info_hash)->name();
@ -374,6 +415,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->piece_availability(avail); find_torrent(m_ses, m_chk, m_info_hash)->piece_availability(avail);
@ -383,6 +427,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->set_piece_priority(index, priority); find_torrent(m_ses, m_chk, m_info_hash)->set_piece_priority(index, priority);
@ -392,6 +439,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->piece_priority(index); return find_torrent(m_ses, m_chk, m_info_hash)->piece_priority(index);
@ -401,6 +451,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->prioritize_pieces(pieces); find_torrent(m_ses, m_chk, m_info_hash)->prioritize_pieces(pieces);
@ -409,6 +462,10 @@ namespace libtorrent
std::vector<int> torrent_handle::piece_priorities() const std::vector<int> torrent_handle::piece_priorities() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
std::vector<int> ret; std::vector<int> ret;
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
@ -420,6 +477,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->prioritize_files(files); find_torrent(m_ses, m_chk, m_info_hash)->prioritize_files(files);
@ -430,6 +490,10 @@ namespace libtorrent
void torrent_handle::filter_piece(int index, bool filter) const void torrent_handle::filter_piece(int index, bool filter) const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->filter_piece(index, filter); find_torrent(m_ses, m_chk, m_info_hash)->filter_piece(index, filter);
@ -438,6 +502,10 @@ namespace libtorrent
void torrent_handle::filter_pieces(std::vector<bool> const& pieces) const void torrent_handle::filter_pieces(std::vector<bool> const& pieces) const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->filter_pieces(pieces); find_torrent(m_ses, m_chk, m_info_hash)->filter_pieces(pieces);
@ -446,6 +514,10 @@ namespace libtorrent
bool torrent_handle::is_piece_filtered(int index) const bool torrent_handle::is_piece_filtered(int index) const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->is_piece_filtered(index); return find_torrent(m_ses, m_chk, m_info_hash)->is_piece_filtered(index);
@ -454,6 +526,10 @@ namespace libtorrent
std::vector<bool> torrent_handle::filtered_pieces() const std::vector<bool> torrent_handle::filtered_pieces() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
std::vector<bool> ret; std::vector<bool> ret;
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
@ -464,6 +540,10 @@ namespace libtorrent
void torrent_handle::filter_files(std::vector<bool> const& files) const void torrent_handle::filter_files(std::vector<bool> const& files) const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->filter_files(files); find_torrent(m_ses, m_chk, m_info_hash)->filter_files(files);
@ -476,6 +556,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->trackers(); return find_torrent(m_ses, m_chk, m_info_hash)->trackers();
@ -485,6 +568,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->add_url_seed(url); find_torrent(m_ses, m_chk, m_info_hash)->add_url_seed(url);
@ -494,6 +580,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->remove_url_seed(url); find_torrent(m_ses, m_chk, m_info_hash)->remove_url_seed(url);
@ -503,6 +592,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->url_seeds(); return find_torrent(m_ses, m_chk, m_info_hash)->url_seeds();
@ -513,6 +605,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->replace_trackers(urls); find_torrent(m_ses, m_chk, m_info_hash)->replace_trackers(urls);
@ -521,6 +616,10 @@ namespace libtorrent
torrent_info const& torrent_handle::get_torrent_info() const torrent_info const& torrent_handle::get_torrent_info() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
boost::shared_ptr<torrent> t = find_torrent(m_ses, m_chk, m_info_hash); boost::shared_ptr<torrent> t = find_torrent(m_ses, m_chk, m_info_hash);
@ -533,16 +632,14 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) return false; if (m_ses == 0) return false;
assert(m_chk);
if (m_chk) session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
{ mutex::scoped_lock l2(m_chk->m_mutex);
mutex::scoped_lock l(m_chk->m_mutex); aux::piece_checker_data* d = m_chk->find_torrent(m_info_hash);
aux::piece_checker_data* d = m_chk->find_torrent(m_info_hash); if (d != 0) return true;
if (d != 0) return true;
}
{ {
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::weak_ptr<torrent> t = m_ses->find_torrent(m_info_hash); boost::weak_ptr<torrent> t = m_ses->find_torrent(m_info_hash);
if (!t.expired()) return true; if (!t.expired()) return true;
} }
@ -556,6 +653,7 @@ namespace libtorrent
std::vector<int> piece_index; std::vector<int> piece_index;
if (m_ses == 0) return entry(); if (m_ses == 0) return entry();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
@ -674,6 +772,9 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->save_path(); return find_torrent(m_ses, m_chk, m_info_hash)->save_path();
@ -684,6 +785,7 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
@ -712,6 +814,7 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
@ -726,6 +829,7 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
@ -738,8 +842,10 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
assert(ratio >= 0.f); assert(ratio >= 0.f);
if (ratio < 1.f && ratio > 0.f) if (ratio < 1.f && ratio > 0.f)
ratio = 1.f; ratio = 1.f;
@ -752,6 +858,10 @@ namespace libtorrent
void torrent_handle::resolve_countries(bool r) void torrent_handle::resolve_countries(bool r)
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
find_torrent(m_ses, m_chk, m_info_hash)->resolve_countries(r); find_torrent(m_ses, m_chk, m_info_hash)->resolve_countries(r);
@ -760,6 +870,10 @@ namespace libtorrent
bool torrent_handle::resolve_countries() const bool torrent_handle::resolve_countries() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
mutex::scoped_lock l2(m_chk->m_mutex); mutex::scoped_lock l2(m_chk->m_mutex);
return find_torrent(m_ses, m_chk, m_info_hash)->resolving_countries(); return find_torrent(m_ses, m_chk, m_info_hash)->resolving_countries();
@ -770,8 +884,10 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
v.clear();
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
v.clear();
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
@ -803,6 +919,7 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) throw_invalid_handle(); if (m_ses == 0) throw_invalid_handle();
assert(m_chk);
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
@ -884,3 +1001,4 @@ namespace libtorrent
} }