From cbd1c26a1168d8f0d03dc1a864f8384f63049039 Mon Sep 17 00:00:00 2001 From: arvidn Date: Sun, 12 Feb 2017 17:55:34 -0500 Subject: [PATCH] fix ABI compatibility issue introduced with preformatted entry type --- ChangeLog | 1 + bindings/python/src/create_torrent.cpp | 2 +- include/libtorrent/create_torrent.hpp | 6 ++++++ src/create_torrent.cpp | 30 +++++++++++++++++++++++--- src/torrent.cpp | 11 +++++++--- test/test_create_torrent.cpp | 2 +- 6 files changed, 44 insertions(+), 8 deletions(-) diff --git a/ChangeLog b/ChangeLog index 8d2857cf8..cab4c9d27 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,4 @@ + * fix ABI compatibility issue introduced with preformatted entry type * add web_seed_name_lookup_retry to session_settings * slightly improve proxy settings backwards compatibility * add function to get default settings diff --git a/bindings/python/src/create_torrent.cpp b/bindings/python/src/create_torrent.cpp index b42272116..cc4b711d8 100644 --- a/bindings/python/src/create_torrent.cpp +++ b/bindings/python/src/create_torrent.cpp @@ -196,7 +196,7 @@ void bind_create_torrent() class_("create_torrent", no_init) .def(init()) - .def(init(arg("ti"))) + .def(init((arg("ti"), arg("version") = LIBTORRENT_VERSION_NUM))) .def(init((arg("storage"), arg("piece_size") = 0 , arg("pad_file_limit") = -1, arg("flags") = int(libtorrent::create_torrent::optimize_alignment)))) diff --git a/include/libtorrent/create_torrent.hpp b/include/libtorrent/create_torrent.hpp index fa111500c..37cea88d7 100644 --- a/include/libtorrent/create_torrent.hpp +++ b/include/libtorrent/create_torrent.hpp @@ -39,6 +39,7 @@ POSSIBILITY OF SUCH DAMAGE. #include "libtorrent/storage.hpp" #include "libtorrent/hasher.hpp" #include "libtorrent/file.hpp" // for combine_path etc. +#include "libtorrent/version.hpp" #include "libtorrent/aux_/disable_warnings_push.hpp" @@ -170,10 +171,13 @@ namespace libtorrent // ``alignment`` is used when pad files are enabled. This is the size // eligible files are aligned to. The default is -1, which means the // piece size of the torrent. + // The ``use_preformatted`` parameter can be set to true to preserve + // invalid encoding of the .torrent file. create_torrent(file_storage& fs, int piece_size = 0 , int pad_file_limit = -1, int flags = optimize_alignment , int alignment = -1); create_torrent(torrent_info const& ti); + create_torrent(torrent_info const& ti, bool use_preformatted); // internal ~create_torrent(); @@ -298,6 +302,8 @@ namespace libtorrent private: + void load_from_torrent_info(torrent_info const& ti, bool const use_preformatted); + file_storage& m_files; // if m_info_dict is initialized, it is // used instead of m_files to generate diff --git a/src/create_torrent.cpp b/src/create_torrent.cpp index 5f2e66a56..ea9e40195 100644 --- a/src/create_torrent.cpp +++ b/src/create_torrent.cpp @@ -382,6 +382,23 @@ namespace libtorrent , m_merkle_torrent(ti.is_merkle_torrent()) , m_include_mtime(false) , m_include_symlinks(false) + { + load_from_torrent_info(ti, false); + } + + create_torrent::create_torrent(torrent_info const& ti, bool const use_preformatted) + : m_files(const_cast(ti.files())) + , m_creation_date(time(0)) + , m_multifile(ti.num_files() > 1) + , m_private(ti.priv()) + , m_merkle_torrent(ti.is_merkle_torrent()) + , m_include_mtime(false) + , m_include_symlinks(false) + { + load_from_torrent_info(ti, use_preformatted); + } + + void create_torrent::load_from_torrent_info(torrent_info const& ti, bool const use_preformatted) { TORRENT_ASSERT(ti.is_valid()); TORRENT_ASSERT(ti.num_pieces() > 0); @@ -418,9 +435,16 @@ namespace libtorrent m_piece_hash.resize(m_files.num_pieces()); for (int i = 0; i < num_pieces(); ++i) set_hash(i, ti.hash_for_piece(i)); - boost::shared_array const info = ti.metadata(); - int const size = ti.metadata_size(); - m_info_dict.preformatted().assign(&info[0], &info[0] + size); + if (use_preformatted) + { + boost::shared_array const info = ti.metadata(); + int const size = ti.metadata_size(); + m_info_dict.preformatted().assign(&info[0], &info[0] + size); + } + else + { + m_info_dict = bdecode(&ti.metadata()[0], &ti.metadata()[0] + ti.metadata_size()); + } m_info_hash = ti.info_hash(); } diff --git a/src/torrent.cpp b/src/torrent.cpp index 521644b4c..83f338473 100644 --- a/src/torrent.cpp +++ b/src/torrent.cpp @@ -7215,9 +7215,14 @@ namespace libtorrent { if (m_magnet_link || (m_save_resume_flags & torrent_handle::save_info_dict)) { - boost::shared_array const info = torrent_file().metadata(); - int const size = torrent_file().metadata_size(); - ret["info"].preformatted().assign(&info[0], &info[0] + size); + ret["info"] = bdecode(&torrent_file().metadata()[0] + , &torrent_file().metadata()[0] + torrent_file().metadata_size()); +// TODO: re-enable this code once there's a non-inlined encoder function. Or +// perhaps this should not be used until saving resume_data via +// add_torrent_params and a free function, similar to read_resume_data +// boost::shared_array const info = torrent_file().metadata(); +// int const size = torrent_file().metadata_size(); +// ret["info"].preformatted().assign(&info[0], &info[0] + size); } } diff --git a/test/test_create_torrent.cpp b/test/test_create_torrent.cpp index 3fb106279..5f1e38d29 100644 --- a/test/test_create_torrent.cpp +++ b/test/test_create_torrent.cpp @@ -49,7 +49,7 @@ TORRENT_TEST(create_verbatim_torrent) lt::torrent_info info(test_torrent, sizeof(test_torrent) - 1); - lt::create_torrent t(info); + lt::create_torrent t(info, true); std::vector buffer; lt::bencode(std::back_inserter(buffer), t.generate());