changed the definition of file_progress and deprecated the old function. Python bindi...
[libtorrent.git] / src / torrent_handle.cpp
blob8e8542c77137c24573abcc2120c8fad2916022e0
1 /*
3 Copyright (c) 2003, Arvid Norberg
4 All rights reserved.
6 Redistribution and use in source and binary forms, with or without
7 modification, are permitted provided that the following conditions
8 are met:
10 * Redistributions of source code must retain the above copyright
11 notice, this list of conditions and the following disclaimer.
12 * Redistributions in binary form must reproduce the above copyright
13 notice, this list of conditions and the following disclaimer in
14 the documentation and/or other materials provided with the distribution.
15 * Neither the name of the author nor the names of its
16 contributors may be used to endorse or promote products derived
17 from this software without specific prior written permission.
19 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
20 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
21 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
22 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
23 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 POSSIBILITY OF SUCH DAMAGE.
33 #include "libtorrent/pch.hpp"
35 #include <ctime>
36 #include <iostream>
37 #include <fstream>
38 #include <iomanip>
39 #include <iterator>
40 #include <algorithm>
41 #include <set>
42 #include <cctype>
43 #include <algorithm>
45 #ifdef _MSC_VER
46 #pragma warning(push, 1)
47 #endif
49 #include <boost/lexical_cast.hpp>
50 #include <boost/filesystem/convenience.hpp>
51 #include <boost/optional.hpp>
52 #include <boost/bind.hpp>
54 #ifdef _MSC_VER
55 #pragma warning(pop)
56 #endif
58 #include "libtorrent/peer_id.hpp"
59 #include "libtorrent/bt_peer_connection.hpp"
60 #include "libtorrent/torrent_info.hpp"
61 #include "libtorrent/tracker_manager.hpp"
62 #include "libtorrent/bencode.hpp"
63 #include "libtorrent/hasher.hpp"
64 #include "libtorrent/entry.hpp"
65 #include "libtorrent/session.hpp"
66 #include "libtorrent/aux_/session_impl.hpp"
67 #include "libtorrent/invariant_check.hpp"
69 #if defined(_MSC_VER) && _MSC_VER < 1300
70 namespace std
72 using ::srand;
73 using ::isalnum;
75 #endif
77 using boost::bind;
78 using boost::mutex;
79 using libtorrent::aux::session_impl;
81 #ifdef BOOST_NO_EXCEPTIONS
83 #define TORRENT_FORWARD(call) \
84 boost::shared_ptr<torrent> t = m_torrent.lock(); \
85 if (!t) return; \
86 session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
87 t->call
89 #define TORRENT_FORWARD_RETURN(call, def) \
90 boost::shared_ptr<torrent> t = m_torrent.lock(); \
91 if (!t) return def; \
92 session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
93 return t->call
95 #define TORRENT_FORWARD_RETURN2(call, def) \
96 boost::shared_ptr<torrent> t = m_torrent.lock(); \
97 if (!t) return def; \
98 session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
99 t->call
101 #else
103 #define TORRENT_FORWARD(call) \
104 boost::shared_ptr<torrent> t = m_torrent.lock(); \
105 if (!t) throw_invalid_handle(); \
106 session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
107 t->call
109 #define TORRENT_FORWARD_RETURN(call, def) \
110 boost::shared_ptr<torrent> t = m_torrent.lock(); \
111 if (!t) throw_invalid_handle(); \
112 session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
113 return t->call
115 #define TORRENT_FORWARD_RETURN2(call, def) \
116 boost::shared_ptr<torrent> t = m_torrent.lock(); \
117 if (!t) throw_invalid_handle(); \
118 session_impl::mutex_t::scoped_lock l(t->session().m_mutex); \
119 t->call
121 #endif
123 namespace libtorrent
125 namespace fs = boost::filesystem;
127 namespace
129 #ifndef BOOST_NO_EXCEPTIONS
130 void throw_invalid_handle()
132 throw invalid_handle();
134 #endif
137 #ifndef NDEBUG
139 void torrent_handle::check_invariant() const
142 #endif
144 sha1_hash torrent_handle::info_hash() const
146 INVARIANT_CHECK;
147 const static sha1_hash empty;
148 TORRENT_FORWARD_RETURN(torrent_file().info_hash(), empty);
151 void torrent_handle::set_max_uploads(int max_uploads) const
153 INVARIANT_CHECK;
154 TORRENT_ASSERT(max_uploads >= 2 || max_uploads == -1);
155 TORRENT_FORWARD(set_max_uploads(max_uploads));
158 void torrent_handle::use_interface(const char* net_interface) const
160 INVARIANT_CHECK;
161 TORRENT_FORWARD(use_interface(net_interface));
164 void torrent_handle::set_max_connections(int max_connections) const
166 INVARIANT_CHECK;
167 TORRENT_ASSERT(max_connections >= 2 || max_connections == -1);
168 TORRENT_FORWARD(set_max_connections(max_connections));
171 void torrent_handle::set_peer_upload_limit(tcp::endpoint ip, int limit) const
173 INVARIANT_CHECK;
174 TORRENT_ASSERT(limit >= -1);
175 TORRENT_FORWARD(set_peer_upload_limit(ip, limit));
178 void torrent_handle::set_peer_download_limit(tcp::endpoint ip, int limit) const
180 INVARIANT_CHECK;
181 TORRENT_ASSERT(limit >= -1);
182 TORRENT_FORWARD(set_peer_download_limit(ip, limit));
185 void torrent_handle::set_upload_limit(int limit) const
187 INVARIANT_CHECK;
188 TORRENT_ASSERT(limit >= -1);
189 TORRENT_FORWARD(set_upload_limit(limit));
192 int torrent_handle::upload_limit() const
194 INVARIANT_CHECK;
195 TORRENT_FORWARD_RETURN(upload_limit(), 0);
198 void torrent_handle::set_download_limit(int limit) const
200 INVARIANT_CHECK;
201 TORRENT_ASSERT(limit >= -1);
202 TORRENT_FORWARD(set_download_limit(limit));
205 int torrent_handle::download_limit() const
207 INVARIANT_CHECK;
208 TORRENT_FORWARD_RETURN(download_limit(), 0);
211 void torrent_handle::move_storage(
212 fs::path const& save_path) const
214 INVARIANT_CHECK;
215 TORRENT_FORWARD(move_storage(save_path));
218 void torrent_handle::rename_file(int index, fs::path const& new_name) const
220 INVARIANT_CHECK;
221 TORRENT_FORWARD(rename_file(index, new_name.string()));
224 void torrent_handle::add_extension(
225 boost::function<boost::shared_ptr<torrent_plugin>(torrent*, void*)> const& ext
226 , void* userdata)
228 INVARIANT_CHECK;
229 TORRENT_FORWARD(add_extension(ext, userdata));
232 bool torrent_handle::has_metadata() const
234 INVARIANT_CHECK;
235 TORRENT_FORWARD_RETURN(valid_metadata(), false);
238 bool torrent_handle::is_seed() const
240 INVARIANT_CHECK;
241 TORRENT_FORWARD_RETURN(is_seed(), false);
244 bool torrent_handle::is_finished() const
246 INVARIANT_CHECK;
247 TORRENT_FORWARD_RETURN(is_finished(), false);
250 bool torrent_handle::is_paused() const
252 INVARIANT_CHECK;
253 TORRENT_FORWARD_RETURN(is_paused(), false);
256 void torrent_handle::pause() const
258 INVARIANT_CHECK;
259 TORRENT_FORWARD(pause());
262 void torrent_handle::save_resume_data() const
264 INVARIANT_CHECK;
265 TORRENT_FORWARD(save_resume_data());
268 void torrent_handle::force_recheck() const
270 INVARIANT_CHECK;
271 TORRENT_FORWARD(force_recheck());
274 void torrent_handle::resume() const
276 INVARIANT_CHECK;
277 TORRENT_FORWARD(resume());
280 bool torrent_handle::is_auto_managed() const
282 INVARIANT_CHECK;
283 TORRENT_FORWARD_RETURN(is_auto_managed(), true);
286 void torrent_handle::auto_managed(bool m) const
288 INVARIANT_CHECK;
289 TORRENT_FORWARD(auto_managed(m));
292 int torrent_handle::queue_position() const
294 INVARIANT_CHECK;
295 TORRENT_FORWARD_RETURN(queue_position(), -1);
298 void torrent_handle::queue_position_up() const
300 INVARIANT_CHECK;
301 TORRENT_FORWARD(set_queue_position(t->queue_position() - 1));
304 void torrent_handle::queue_position_down() const
306 INVARIANT_CHECK;
307 TORRENT_FORWARD(set_queue_position(t->queue_position() + 1));
310 void torrent_handle::queue_position_top() const
312 INVARIANT_CHECK;
313 TORRENT_FORWARD(set_queue_position(0));
316 void torrent_handle::queue_position_bottom() const
318 INVARIANT_CHECK;
319 TORRENT_FORWARD(set_queue_position((std::numeric_limits<int>::max)()));
322 void torrent_handle::set_tracker_login(std::string const& name
323 , std::string const& password) const
325 INVARIANT_CHECK;
326 TORRENT_FORWARD(set_tracker_login(name, password));
329 void torrent_handle::file_progress(std::vector<float>& progress) const
331 INVARIANT_CHECK;
332 TORRENT_FORWARD(file_progress(progress));
335 void torrent_handle::file_progress(std::vector<size_type>& progress) const
337 INVARIANT_CHECK;
338 TORRENT_FORWARD(file_progress(progress));
341 torrent_status torrent_handle::status() const
343 INVARIANT_CHECK;
344 TORRENT_FORWARD_RETURN(status(), torrent_status());
347 void torrent_handle::set_sequential_download(bool sd) const
349 INVARIANT_CHECK;
350 TORRENT_FORWARD(set_sequential_download(sd));
353 bool torrent_handle::is_sequential_download() const
355 INVARIANT_CHECK;
356 TORRENT_FORWARD_RETURN(is_sequential_download(), false);
359 std::string torrent_handle::name() const
361 INVARIANT_CHECK;
362 TORRENT_FORWARD_RETURN(name(), "");
365 void torrent_handle::piece_availability(std::vector<int>& avail) const
367 INVARIANT_CHECK;
368 TORRENT_FORWARD(piece_availability(avail));
371 void torrent_handle::piece_priority(int index, int priority) const
373 INVARIANT_CHECK;
374 TORRENT_FORWARD(set_piece_priority(index, priority));
377 int torrent_handle::piece_priority(int index) const
379 INVARIANT_CHECK;
380 TORRENT_FORWARD_RETURN(piece_priority(index), 0);
383 void torrent_handle::prioritize_pieces(std::vector<int> const& pieces) const
385 INVARIANT_CHECK;
386 TORRENT_FORWARD(prioritize_pieces(pieces));
389 std::vector<int> torrent_handle::piece_priorities() const
391 INVARIANT_CHECK;
392 std::vector<int> ret;
393 TORRENT_FORWARD_RETURN2(piece_priorities(ret), ret);
394 return ret;
397 void torrent_handle::prioritize_files(std::vector<int> const& files) const
399 INVARIANT_CHECK;
400 TORRENT_FORWARD(prioritize_files(files));
403 // ============ start deprecation ===============
405 void torrent_handle::filter_piece(int index, bool filter) const
407 INVARIANT_CHECK;
408 TORRENT_FORWARD(filter_piece(index, filter));
411 void torrent_handle::filter_pieces(std::vector<bool> const& pieces) const
413 INVARIANT_CHECK;
414 TORRENT_FORWARD(filter_pieces(pieces));
417 bool torrent_handle::is_piece_filtered(int index) const
419 INVARIANT_CHECK;
420 TORRENT_FORWARD_RETURN(is_piece_filtered(index), false);
423 std::vector<bool> torrent_handle::filtered_pieces() const
425 INVARIANT_CHECK;
426 std::vector<bool> ret;
427 TORRENT_FORWARD_RETURN2(filtered_pieces(ret), ret);
428 return ret;
431 void torrent_handle::filter_files(std::vector<bool> const& files) const
433 INVARIANT_CHECK;
434 TORRENT_FORWARD(filter_files(files));
437 // ============ end deprecation ===============
440 std::vector<announce_entry> const& torrent_handle::trackers() const
442 INVARIANT_CHECK;
443 const static std::vector<announce_entry> empty;
444 TORRENT_FORWARD_RETURN(trackers(), empty);
447 void torrent_handle::add_url_seed(std::string const& url) const
449 INVARIANT_CHECK;
450 TORRENT_FORWARD(add_url_seed(url));
453 void torrent_handle::remove_url_seed(std::string const& url) const
455 INVARIANT_CHECK;
456 TORRENT_FORWARD(remove_url_seed(url));
459 std::set<std::string> torrent_handle::url_seeds() const
461 INVARIANT_CHECK;
462 const static std::set<std::string> empty;
463 TORRENT_FORWARD_RETURN(url_seeds(), empty);
466 void torrent_handle::replace_trackers(
467 std::vector<announce_entry> const& urls) const
469 INVARIANT_CHECK;
470 TORRENT_FORWARD(replace_trackers(urls));
473 torrent_info const& torrent_handle::get_torrent_info() const
475 INVARIANT_CHECK;
476 #ifdef BOOST_NO_EXCEPTIONS
477 const static torrent_info empty;
478 #endif
479 boost::shared_ptr<torrent> t = m_torrent.lock();
480 if (!t)
481 #ifdef BOOST_NO_EXCEPTIONS
482 return empty;
483 #else
484 throw_invalid_handle();
485 #endif
486 session_impl::mutex_t::scoped_lock l(t->session().m_mutex);
487 if (!t->valid_metadata())
488 #ifdef BOOST_NO_EXCEPTIONS
489 return empty;
490 #else
491 throw_invalid_handle();
492 #endif
493 return t->torrent_file();
496 bool torrent_handle::is_valid() const
498 INVARIANT_CHECK;
499 return !m_torrent.expired();
502 entry torrent_handle::write_resume_data() const
504 INVARIANT_CHECK;
506 entry ret(entry::dictionary_t);
507 TORRENT_FORWARD(write_resume_data(ret));
508 t->filesystem().write_resume_data(ret);
510 return ret;
514 fs::path torrent_handle::save_path() const
516 INVARIANT_CHECK;
517 TORRENT_FORWARD_RETURN(save_path(), fs::path());
520 void torrent_handle::connect_peer(tcp::endpoint const& adr, int source) const
522 INVARIANT_CHECK;
524 boost::shared_ptr<torrent> t = m_torrent.lock();
525 if (!t)
526 #ifdef BOOST_NO_EXCEPTIONS
527 return;
528 #else
529 throw_invalid_handle();
530 #endif
531 session_impl::mutex_t::scoped_lock l(t->session().m_mutex);
533 peer_id id;
534 std::fill(id.begin(), id.end(), 0);
535 t->get_policy().peer_from_tracker(adr, id, source, 0);
538 void torrent_handle::force_reannounce(
539 boost::posix_time::time_duration duration) const
541 INVARIANT_CHECK;
542 TORRENT_FORWARD(force_tracker_request(time_now() + seconds(duration.total_seconds())));
545 void torrent_handle::force_reannounce() const
547 INVARIANT_CHECK;
548 TORRENT_FORWARD(force_tracker_request());
551 void torrent_handle::scrape_tracker() const
553 INVARIANT_CHECK;
554 TORRENT_FORWARD(scrape_tracker());
557 void torrent_handle::set_ratio(float ratio) const
559 INVARIANT_CHECK;
561 TORRENT_ASSERT(ratio >= 0.f);
562 if (ratio < 1.f && ratio > 0.f)
563 ratio = 1.f;
564 TORRENT_FORWARD(set_ratio(ratio));
567 #ifndef TORRENT_DISABLE_RESOLVE_COUNTRIES
568 void torrent_handle::resolve_countries(bool r)
570 INVARIANT_CHECK;
571 TORRENT_FORWARD(resolve_countries(r));
574 bool torrent_handle::resolve_countries() const
576 INVARIANT_CHECK;
577 TORRENT_FORWARD_RETURN(resolving_countries(), false);
579 #endif
581 void torrent_handle::get_full_peer_list(std::vector<peer_list_entry>& v) const
583 INVARIANT_CHECK;
584 TORRENT_FORWARD(get_full_peer_list(v));
587 void torrent_handle::get_peer_info(std::vector<peer_info>& v) const
589 INVARIANT_CHECK;
590 TORRENT_FORWARD(get_peer_info(v));
593 void torrent_handle::get_download_queue(std::vector<partial_piece_info>& queue) const
595 INVARIANT_CHECK;
596 TORRENT_FORWARD(get_download_queue(queue));