optimized torrent_handle to use a weak_ptr directly to the torrent object

This commit is contained in:
Arvid Norberg 2008-04-09 20:09:36 +00:00
parent e4483e64e4
commit 291ef2a2c9
5 changed files with 65 additions and 89 deletions

View File

@ -513,7 +513,7 @@ namespace libtorrent
void replace_trackers(std::vector<announce_entry> const& urls); void replace_trackers(std::vector<announce_entry> const& urls);
torrent_handle get_handle() const; torrent_handle get_handle();
// LOGGING // LOGGING
#if defined TORRENT_VERBOSE_LOGGING || defined TORRENT_LOGGING || defined TORRENT_ERROR_LOGGING #if defined TORRENT_VERBOSE_LOGGING || defined TORRENT_LOGGING || defined TORRENT_ERROR_LOGGING

View File

@ -282,7 +282,7 @@ namespace libtorrent
friend struct aux::session_impl; friend struct aux::session_impl;
friend class torrent; friend class torrent;
torrent_handle(): m_ses(0), m_info_hash(0) {} torrent_handle() {}
void get_peer_info(std::vector<peer_info>& v) const; void get_peer_info(std::vector<peer_info>& v) const;
torrent_status status() const; torrent_status status() const;
@ -407,34 +407,28 @@ namespace libtorrent
// post condition: save_path() == save_path if true is returned // post condition: save_path() == save_path if true is returned
void move_storage(fs::path const& save_path) const; void move_storage(fs::path const& save_path) const;
const sha1_hash& info_hash() const sha1_hash info_hash() const;
{ return m_info_hash; }
bool operator==(const torrent_handle& h) const bool operator==(const torrent_handle& h) const
{ return m_info_hash == h.m_info_hash; } { return m_torrent.lock() == h.m_torrent.lock(); }
bool operator!=(const torrent_handle& h) const bool operator!=(const torrent_handle& h) const
{ return m_info_hash != h.m_info_hash; } { return m_torrent.lock() != h.m_torrent.lock(); }
bool operator<(const torrent_handle& h) const bool operator<(const torrent_handle& h) const
{ return m_info_hash < h.m_info_hash; } { return m_torrent.lock() < h.m_torrent.lock(); }
private: private:
torrent_handle(aux::session_impl* s torrent_handle(boost::weak_ptr<torrent> const& t)
, const sha1_hash& h) : m_torrent(t)
: m_ses(s) {}
, m_info_hash(h)
{
TORRENT_ASSERT(m_ses != 0);
}
#ifndef NDEBUG #ifndef NDEBUG
void check_invariant() const; void check_invariant() const;
#endif #endif
aux::session_impl* m_ses; boost::weak_ptr<torrent> m_torrent;
sha1_hash m_info_hash;
}; };

View File

@ -1450,14 +1450,14 @@ namespace aux {
i != end; ++i) i != end; ++i)
{ {
if (i->second->is_aborted()) continue; if (i->second->is_aborted()) continue;
ret.push_back(torrent_handle(this, i->first)); ret.push_back(torrent_handle(i->second));
} }
return ret; return ret;
} }
torrent_handle session_impl::find_torrent_handle(sha1_hash const& info_hash) torrent_handle session_impl::find_torrent_handle(sha1_hash const& info_hash)
{ {
return torrent_handle(this, info_hash); return torrent_handle(find_torrent(info_hash));
} }
torrent_handle session_impl::add_torrent( torrent_handle session_impl::add_torrent(
@ -1535,7 +1535,7 @@ namespace aux {
m_torrents.insert(std::make_pair(ti->info_hash(), torrent_ptr)); m_torrents.insert(std::make_pair(ti->info_hash(), torrent_ptr));
return torrent_handle(this, ti->info_hash()); return torrent_handle(torrent_ptr);
} }
void session_impl::check_torrent(boost::shared_ptr<torrent> const& t) void session_impl::check_torrent(boost::shared_ptr<torrent> const& t)
@ -1605,20 +1605,26 @@ namespace aux {
m_torrents.insert(std::make_pair(info_hash, torrent_ptr)); m_torrents.insert(std::make_pair(info_hash, torrent_ptr));
return torrent_handle(this, info_hash); return torrent_handle(torrent_ptr);
} }
void session_impl::remove_torrent(const torrent_handle& h, int options) void session_impl::remove_torrent(const torrent_handle& h, int options)
{ {
if (h.m_ses != this) return; boost::shared_ptr<torrent> tptr = h.m_torrent.lock();
TORRENT_ASSERT(h.m_ses != 0); if (!tptr)
#ifdef BOOST_NO_EXCEPTIONS
return;
#else
throw invalid_handle();
#endif
mutex_t::scoped_lock l(m_mutex); mutex_t::scoped_lock l(m_mutex);
INVARIANT_CHECK; INVARIANT_CHECK;
session_impl::torrent_map::iterator i = session_impl::torrent_map::iterator i =
m_torrents.find(h.m_info_hash); m_torrents.find(tptr->torrent_file().info_hash());
if (i != m_torrents.end()) if (i != m_torrents.end())
{ {
torrent& t = *i->second; torrent& t = *i->second;

View File

@ -2844,9 +2844,9 @@ namespace libtorrent
} }
torrent_handle torrent::get_handle() const torrent_handle torrent::get_handle()
{ {
return torrent_handle(&m_ses, m_torrent_file->info_hash()); return torrent_handle(shared_from_this());
} }
session_settings const& torrent::settings() const session_settings const& torrent::settings() const

View File

@ -81,47 +81,41 @@ using libtorrent::aux::session_impl;
#ifdef BOOST_NO_EXCEPTIONS #ifdef BOOST_NO_EXCEPTIONS
#define TORRENT_FORWARD(call) \ #define TORRENT_FORWARD(call) \
if (m_ses == 0) return; \ boost::shared_ptr<torrent> t = m_torrent.lock(); \
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); \
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); \
if (!t) return; \ if (!t) return; \
session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
t->call t->call
#define TORRENT_FORWARD_RETURN(call, def) \ #define TORRENT_FORWARD_RETURN(call, def) \
if (m_ses == 0) return def; \ boost::shared_ptr<torrent> t = m_torrent.lock(); \
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); \
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); \
if (!t) return def; \ if (!t) return def; \
session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
return t->call return t->call
#define TORRENT_FORWARD_RETURN2(call, def) \ #define TORRENT_FORWARD_RETURN2(call, def) \
if (m_ses == 0) return def; \ boost::shared_ptr<torrent> t = m_torrent.lock(); \
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); \
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); \
if (!t) return def; \ if (!t) return def; \
session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
t->call t->call
#else #else
#define TORRENT_FORWARD(call) \ #define TORRENT_FORWARD(call) \
if (m_ses == 0) throw_invalid_handle(); \ boost::shared_ptr<torrent> t = m_torrent.lock(); \
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); \
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); \
if (!t) throw_invalid_handle(); \ if (!t) throw_invalid_handle(); \
session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
t->call t->call
#define TORRENT_FORWARD_RETURN(call, def) \ #define TORRENT_FORWARD_RETURN(call, def) \
if (m_ses == 0) throw_invalid_handle(); \ boost::shared_ptr<torrent> t = m_torrent.lock(); \
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); \ if (!t) throw_invalid_handle(); \
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); \ session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
if (!t) return def; \
return t->call return t->call
#define TORRENT_FORWARD_RETURN2(call, def) \ #define TORRENT_FORWARD_RETURN2(call, def) \
if (m_ses == 0) throw_invalid_handle(); \ boost::shared_ptr<torrent> t = m_torrent.lock(); \
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); \ if (!t) throw_invalid_handle(); \
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); \ session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
if (!t) return def; \
t->call t->call
#endif #endif
@ -143,11 +137,17 @@ namespace libtorrent
#ifndef NDEBUG #ifndef NDEBUG
void torrent_handle::check_invariant() const void torrent_handle::check_invariant() const
{ {}
}
#endif #endif
sha1_hash torrent_handle::info_hash() const
{
INVARIANT_CHECK;
const static sha1_hash empty;
TORRENT_FORWARD_RETURN(torrent_file().info_hash(), empty);
}
void torrent_handle::set_max_uploads(int max_uploads) const void torrent_handle::set_max_uploads(int max_uploads) const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
@ -269,22 +269,7 @@ namespace libtorrent
torrent_status torrent_handle::status() const torrent_status torrent_handle::status() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
TORRENT_FORWARD_RETURN(status(), torrent_status());
if (m_ses == 0)
#ifdef BOOST_NO_EXCEPTIONS
return torrent_status();
#else
throw_invalid_handle();
#endif
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
if (t) return t->status();
#ifndef BOOST_NO_EXCEPTIONS
throw_invalid_handle();
#endif
return torrent_status();
} }
void torrent_handle::set_sequential_download(bool sd) const void torrent_handle::set_sequential_download(bool sd) const
@ -412,13 +397,16 @@ namespace libtorrent
INVARIANT_CHECK; INVARIANT_CHECK;
#ifdef BOOST_NO_EXCEPTIONS #ifdef BOOST_NO_EXCEPTIONS
const static torrent_info empty; const static torrent_info empty;
if (m_ses == 0) return empty;
#else
if (m_ses == 0) throw_invalid_handle();
#endif #endif
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex); boost::shared_ptr<torrent> t = m_torrent.lock();
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); if (!t)
if (!t || !t->valid_metadata()) #ifdef BOOST_NO_EXCEPTIONS
return empty;
#else
throw_invalid_handle();
#endif
session_impl::mutex_t::scoped_lock l(t->session().m_mutex);
if (!t->valid_metadata())
#ifdef BOOST_NO_EXCEPTIONS #ifdef BOOST_NO_EXCEPTIONS
return empty; return empty;
#else #else
@ -430,25 +418,22 @@ namespace libtorrent
bool torrent_handle::is_valid() const bool torrent_handle::is_valid() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) return false; return !m_torrent.expired();
session_impl::mutex_t::scoped_lock l1(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
return t != 0;
} }
entry torrent_handle::write_resume_data() const entry torrent_handle::write_resume_data() const
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) boost::shared_ptr<torrent> t = m_torrent.lock();
if (!t)
#ifdef BOOST_NO_EXCEPTIONS #ifdef BOOST_NO_EXCEPTIONS
return entry(); return entry();
#else #else
throw_invalid_handle(); throw_invalid_handle();
#endif #endif
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex); session_impl::mutex_t::scoped_lock l(t->session().m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock(); if (!t->valid_metadata())
if (!t || !t->valid_metadata())
#ifdef BOOST_NO_EXCEPTIONS #ifdef BOOST_NO_EXCEPTIONS
return entry(); return entry();
#else #else
@ -580,24 +565,15 @@ namespace libtorrent
{ {
INVARIANT_CHECK; INVARIANT_CHECK;
if (m_ses == 0) boost::shared_ptr<torrent> t = m_torrent.lock();
#ifdef BOOST_NO_EXCEPTIONS
return;
#else
throw_invalid_handle();
#endif
session_impl::mutex_t::scoped_lock l(m_ses->m_mutex);
boost::shared_ptr<torrent> t = m_ses->find_torrent(m_info_hash).lock();
if (!t) if (!t)
{
#ifdef BOOST_NO_EXCEPTIONS #ifdef BOOST_NO_EXCEPTIONS
return; return;
#else #else
throw_invalid_handle(); throw_invalid_handle();
#endif #endif
} session_impl::mutex_t::scoped_lock l(t->session().m_mutex);
peer_id id; peer_id id;
std::fill(id.begin(), id.end(), 0); std::fill(id.begin(), id.end(), 0);
t->get_policy().peer_from_tracker(adr, id, source, 0); t->get_policy().peer_from_tracker(adr, id, source, 0);