String view entry (#1147)
make entry support string_view in its interface, and make it efficient when in in C++14
This commit is contained in:
parent
b1b74657f6
commit
48a647a169
|
@ -1,3 +1,4 @@
|
||||||
|
* use string_view in entry interface
|
||||||
* deprecate "send_stats" property on trackers (since lt_tracker extension has
|
* deprecate "send_stats" property on trackers (since lt_tracker extension has
|
||||||
been removed)
|
been removed)
|
||||||
* remove deprecate session_settings API (use settings_pack instead)
|
* remove deprecate session_settings API (use settings_pack instead)
|
||||||
|
|
|
@ -47,7 +47,7 @@ namespace libtorrent
|
||||||
struct TORRENT_EXPORT announce_entry
|
struct TORRENT_EXPORT announce_entry
|
||||||
{
|
{
|
||||||
// constructs a tracker announce entry with ``u`` as the URL.
|
// constructs a tracker announce entry with ``u`` as the URL.
|
||||||
announce_entry(std::string const& u);
|
announce_entry(std::string u);
|
||||||
announce_entry();
|
announce_entry();
|
||||||
~announce_entry();
|
~announce_entry();
|
||||||
announce_entry(announce_entry const&) = default;
|
announce_entry(announce_entry const&) = default;
|
||||||
|
|
|
@ -240,7 +240,7 @@ namespace libtorrent
|
||||||
// tracker less torrent. It can be used by clients to bootstrap their DHT node from.
|
// tracker less torrent. It can be used by clients to bootstrap their DHT node from.
|
||||||
// The node is a hostname and a port number where there is a DHT node running.
|
// The node is a hostname and a port number where there is a DHT node running.
|
||||||
// You can have any number of DHT nodes in a torrent.
|
// You can have any number of DHT nodes in a torrent.
|
||||||
void add_node(std::pair<std::string, int> const& node);
|
void add_node(std::pair<std::string, int> node);
|
||||||
|
|
||||||
// Adds a tracker to the torrent. This is not strictly required, but most torrents
|
// Adds a tracker to the torrent. This is not strictly required, but most torrents
|
||||||
// use a tracker as their main source of peers. The url should be an http:// or udp://
|
// use a tracker as their main source of peers. The url should be an http:// or udp://
|
||||||
|
|
|
@ -72,6 +72,7 @@ POSSIBILITY OF SUCH DAMAGE.
|
||||||
#include "libtorrent/assert.hpp"
|
#include "libtorrent/assert.hpp"
|
||||||
#include "libtorrent/error_code.hpp"
|
#include "libtorrent/error_code.hpp"
|
||||||
#include "libtorrent/span.hpp"
|
#include "libtorrent/span.hpp"
|
||||||
|
#include "libtorrent/string_view.hpp"
|
||||||
|
|
||||||
namespace libtorrent
|
namespace libtorrent
|
||||||
{
|
{
|
||||||
|
@ -82,6 +83,21 @@ namespace libtorrent
|
||||||
#endif
|
#endif
|
||||||
struct bdecode_node;
|
struct bdecode_node;
|
||||||
|
|
||||||
|
#if __cplusplus > 201103
|
||||||
|
namespace aux
|
||||||
|
{
|
||||||
|
// this enables us to compare a string_view against the std::string that's
|
||||||
|
// held by the std::map
|
||||||
|
struct strview_less
|
||||||
|
{
|
||||||
|
using is_transparent = std::true_type;
|
||||||
|
template <typename T1, typename T2>
|
||||||
|
bool operator()(T1 const& rhs, T2 const& lhs) const
|
||||||
|
{ return rhs < lhs; }
|
||||||
|
};
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
// The ``entry`` class represents one node in a bencoded hierarchy. It works as a
|
// The ``entry`` class represents one node in a bencoded hierarchy. It works as a
|
||||||
// variant type, it can be either a list, a dictionary (``std::map``), an integer
|
// variant type, it can be either a list, a dictionary (``std::map``), an integer
|
||||||
// or a string.
|
// or a string.
|
||||||
|
@ -92,7 +108,11 @@ namespace libtorrent
|
||||||
// the key is always a string. If a generic entry would be allowed
|
// the key is always a string. If a generic entry would be allowed
|
||||||
// as a key, sorting would become a problem (e.g. to compare a string
|
// as a key, sorting would become a problem (e.g. to compare a string
|
||||||
// to a list). The definition doesn't mention such a limit though.
|
// to a list). The definition doesn't mention such a limit though.
|
||||||
|
#if __cplusplus <= 201103
|
||||||
typedef std::map<std::string, entry> dictionary_type;
|
typedef std::map<std::string, entry> dictionary_type;
|
||||||
|
#else
|
||||||
|
typedef std::map<std::string, entry, aux::strview_less> dictionary_type;
|
||||||
|
#endif
|
||||||
typedef std::string string_type;
|
typedef std::string string_type;
|
||||||
typedef std::vector<entry> list_type;
|
typedef std::vector<entry> list_type;
|
||||||
typedef std::int64_t integer_type;
|
typedef std::int64_t integer_type;
|
||||||
|
@ -119,6 +139,7 @@ namespace libtorrent
|
||||||
entry(span<char const>);
|
entry(span<char const>);
|
||||||
template <typename U, typename Cond = typename std::enable_if<
|
template <typename U, typename Cond = typename std::enable_if<
|
||||||
std::is_same<U, entry::string_type>::value
|
std::is_same<U, entry::string_type>::value
|
||||||
|
|| std::is_same<U, string_view>::value
|
||||||
|| std::is_same<U, char const*>::value>::type>
|
|| std::is_same<U, char const*>::value>::type>
|
||||||
entry(U v)
|
entry(U v)
|
||||||
: m_type(undefined_t)
|
: m_type(undefined_t)
|
||||||
|
@ -250,21 +271,17 @@ namespace libtorrent
|
||||||
// The const version of ``operator[]`` will only return a reference to an
|
// The const version of ``operator[]`` will only return a reference to an
|
||||||
// existing element at the given key. If the key is not found, it will
|
// existing element at the given key. If the key is not found, it will
|
||||||
// throw ``system_error``.
|
// throw ``system_error``.
|
||||||
entry& operator[](char const* key);
|
entry& operator[](string_view key);
|
||||||
entry& operator[](std::string const& key);
|
const entry& operator[](string_view key) const;
|
||||||
const entry& operator[](char const* key) const;
|
|
||||||
const entry& operator[](std::string const& key) const;
|
|
||||||
|
|
||||||
// These functions requires the entry to be a dictionary, if it isn't
|
// These functions requires the entry to be a dictionary, if it isn't
|
||||||
// they will throw ``system_error``.
|
// they will throw ``system_error``.
|
||||||
//
|
//
|
||||||
// They will look for an element at the given key in the dictionary, if
|
// They will look for an element at the given key in the dictionary, if
|
||||||
// the element cannot be found, they will return 0. If an element with
|
// the element cannot be found, they will return nullptr. If an element
|
||||||
// the given key is found, the return a pointer to it.
|
// with the given key is found, the return a pointer to it.
|
||||||
entry* find_key(char const* key);
|
entry* find_key(string_view key);
|
||||||
entry const* find_key(char const* key) const;
|
entry const* find_key(string_view key) const;
|
||||||
entry* find_key(std::string const& key);
|
|
||||||
entry const* find_key(std::string const& key) const;
|
|
||||||
|
|
||||||
// returns a pretty-printed string representation
|
// returns a pretty-printed string representation
|
||||||
// of the bencoded structure, with JSON-style syntax
|
// of the bencoded structure, with JSON-style syntax
|
||||||
|
|
|
@ -65,7 +65,7 @@ protected:
|
||||||
|
|
||||||
put_callback m_put_callback;
|
put_callback m_put_callback;
|
||||||
item m_data;
|
item m_data;
|
||||||
bool m_done;
|
bool m_done = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct put_data_observer : traversal_observer
|
struct put_data_observer : traversal_observer
|
||||||
|
|
|
@ -47,8 +47,8 @@ namespace libtorrent
|
||||||
tracker_retry_delay_max = 60 * 60
|
tracker_retry_delay_max = 60 * 60
|
||||||
};
|
};
|
||||||
|
|
||||||
announce_entry::announce_entry(std::string const& u)
|
announce_entry::announce_entry(std::string u)
|
||||||
: url(u)
|
: url(std::move(u))
|
||||||
, fails(0)
|
, fails(0)
|
||||||
, updating(false)
|
, updating(false)
|
||||||
, source(0)
|
, source(0)
|
||||||
|
|
|
@ -705,9 +705,9 @@ namespace libtorrent
|
||||||
m_filehashes[index] = h;
|
m_filehashes[index] = h;
|
||||||
}
|
}
|
||||||
|
|
||||||
void create_torrent::add_node(std::pair<std::string, int> const& node)
|
void create_torrent::add_node(std::pair<std::string, int> node)
|
||||||
{
|
{
|
||||||
m_nodes.push_back(node);
|
m_nodes.emplace_back(std::move(node));
|
||||||
}
|
}
|
||||||
|
|
||||||
void create_torrent::add_url_seed(string_view url)
|
void create_torrent::add_url_seed(string_view url)
|
||||||
|
|
|
@ -89,64 +89,52 @@ namespace libtorrent
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
entry& entry::operator[](char const* key)
|
entry& entry::operator[](string_view key)
|
||||||
{
|
{
|
||||||
|
#if __cplusplus <= 201103
|
||||||
|
dictionary_type::iterator i = dict().find(key.to_string());
|
||||||
|
#else
|
||||||
dictionary_type::iterator i = dict().find(key);
|
dictionary_type::iterator i = dict().find(key);
|
||||||
|
#endif
|
||||||
if (i != dict().end()) return i->second;
|
if (i != dict().end()) return i->second;
|
||||||
dictionary_type::iterator ret = dict().insert(
|
dictionary_type::iterator ret = dict().insert(
|
||||||
std::pair<const std::string, entry>(key, entry())).first;
|
std::make_pair(key.to_string(), entry())).first;
|
||||||
return ret->second;
|
return ret->second;
|
||||||
}
|
}
|
||||||
|
|
||||||
entry& entry::operator[](std::string const& key)
|
const entry& entry::operator[](string_view key) const
|
||||||
{
|
|
||||||
dictionary_type::iterator i = dict().find(key);
|
|
||||||
if (i != dict().end()) return i->second;
|
|
||||||
dictionary_type::iterator ret = dict().insert(
|
|
||||||
std::make_pair(key, entry())).first;
|
|
||||||
return ret->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
entry* entry::find_key(char const* key)
|
|
||||||
{
|
|
||||||
dictionary_type::iterator i = dict().find(key);
|
|
||||||
if (i == dict().end()) return nullptr;
|
|
||||||
return &i->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
entry const* entry::find_key(char const* key) const
|
|
||||||
{
|
|
||||||
dictionary_type::const_iterator i = dict().find(key);
|
|
||||||
if (i == dict().end()) return nullptr;
|
|
||||||
return &i->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
entry* entry::find_key(std::string const& key)
|
|
||||||
{
|
|
||||||
dictionary_type::iterator i = dict().find(key);
|
|
||||||
if (i == dict().end()) return nullptr;
|
|
||||||
return &i->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
entry const* entry::find_key(std::string const& key) const
|
|
||||||
{
|
|
||||||
dictionary_type::const_iterator i = dict().find(key);
|
|
||||||
if (i == dict().end()) return nullptr;
|
|
||||||
return &i->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
const entry& entry::operator[](char const* key) const
|
|
||||||
{
|
|
||||||
return (*this)[std::string(key)];
|
|
||||||
}
|
|
||||||
|
|
||||||
const entry& entry::operator[](std::string const& key) const
|
|
||||||
{
|
{
|
||||||
|
#if __cplusplus <= 201103
|
||||||
|
dictionary_type::const_iterator i = dict().find(key.to_string());
|
||||||
|
#else
|
||||||
dictionary_type::const_iterator i = dict().find(key);
|
dictionary_type::const_iterator i = dict().find(key);
|
||||||
|
#endif
|
||||||
if (i == dict().end()) throw_error();
|
if (i == dict().end()) throw_error();
|
||||||
return i->second;
|
return i->second;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
entry* entry::find_key(string_view key)
|
||||||
|
{
|
||||||
|
#if __cplusplus <= 201103
|
||||||
|
dictionary_type::iterator i = dict().find(key.to_string());
|
||||||
|
#else
|
||||||
|
dictionary_type::iterator i = dict().find(key);
|
||||||
|
#endif
|
||||||
|
if (i == dict().end()) return nullptr;
|
||||||
|
return &i->second;
|
||||||
|
}
|
||||||
|
|
||||||
|
entry const* entry::find_key(string_view key) const
|
||||||
|
{
|
||||||
|
#if __cplusplus <= 201103
|
||||||
|
dictionary_type::const_iterator i = dict().find(key.to_string());
|
||||||
|
#else
|
||||||
|
dictionary_type::const_iterator i = dict().find(key);
|
||||||
|
#endif
|
||||||
|
if (i == dict().end()) return nullptr;
|
||||||
|
return &i->second;
|
||||||
|
}
|
||||||
|
|
||||||
entry::data_type entry::type() const
|
entry::data_type entry::type() const
|
||||||
{
|
{
|
||||||
#if TORRENT_USE_ASSERTS
|
#if TORRENT_USE_ASSERTS
|
||||||
|
|
|
@ -41,9 +41,7 @@ namespace libtorrent { namespace dht
|
||||||
put_data::put_data(node& dht_node, put_callback const& callback)
|
put_data::put_data(node& dht_node, put_callback const& callback)
|
||||||
: traversal_algorithm(dht_node, (node_id::min)())
|
: traversal_algorithm(dht_node, (node_id::min)())
|
||||||
, m_put_callback(callback)
|
, m_put_callback(callback)
|
||||||
, m_done(false)
|
{}
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
char const* put_data::name() const { return "put_data"; }
|
char const* put_data::name() const { return "put_data"; }
|
||||||
|
|
||||||
|
@ -51,7 +49,7 @@ void put_data::start()
|
||||||
{
|
{
|
||||||
// router nodes must not be added to puts
|
// router nodes must not be added to puts
|
||||||
init();
|
init();
|
||||||
bool is_done = add_requests();
|
bool const is_done = add_requests();
|
||||||
if (is_done) done();
|
if (is_done) done();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -66,7 +64,7 @@ void put_data::set_targets(std::vector<std::pair<node_entry, std::string>> const
|
||||||
#if TORRENT_USE_ASSERTS
|
#if TORRENT_USE_ASSERTS
|
||||||
o->m_in_constructor = false;
|
o->m_in_constructor = false;
|
||||||
#endif
|
#endif
|
||||||
m_results.push_back(o);
|
m_results.push_back(std::move(o));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -32,6 +32,7 @@ POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
#include "test.hpp"
|
#include "test.hpp"
|
||||||
#include "libtorrent/bdecode.hpp"
|
#include "libtorrent/bdecode.hpp"
|
||||||
|
#include "libtorrent/entry.hpp"
|
||||||
|
|
||||||
using namespace libtorrent;
|
using namespace libtorrent;
|
||||||
|
|
||||||
|
@ -51,6 +52,31 @@ TORRENT_TEST(integer)
|
||||||
TEST_EQUAL(e.int_value(), 12453);
|
TEST_EQUAL(e.int_value(), 12453);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TORRENT_TEST(construct_string)
|
||||||
|
{
|
||||||
|
entry e(std::string("abc123"));
|
||||||
|
TEST_EQUAL(e.string(), "abc123");
|
||||||
|
}
|
||||||
|
|
||||||
|
TORRENT_TEST(construct_string_literal)
|
||||||
|
{
|
||||||
|
entry e("abc123");
|
||||||
|
TEST_EQUAL(e.string(), "abc123");
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
TORRENT_TEST(construct_string_view)
|
||||||
|
{
|
||||||
|
entry e(string_view("abc123"));
|
||||||
|
TEST_EQUAL(e.string(), "abc123");
|
||||||
|
}
|
||||||
|
|
||||||
|
TORRENT_TEST(construct_integer)
|
||||||
|
{
|
||||||
|
entry e(4);
|
||||||
|
TEST_EQUAL(e.integer(), 4);
|
||||||
|
}
|
||||||
|
|
||||||
// test string
|
// test string
|
||||||
TORRENT_TEST(string)
|
TORRENT_TEST(string)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in New Issue