Version: 2.0.10

home

Bencoding is a common representation in bittorrent used for dictionary, list, int and string hierarchies. It's used to encode .torrent files and some messages in the network protocol. libtorrent also uses it to store settings, resume data and other session state.

Strings in bencoded structures do not necessarily represent text. Strings are raw byte buffers of a certain length. If a string is meant to be interpreted as text, it is required to be UTF-8 encoded. See BEP 3.

The function for decoding bencoded data bdecode(), returning a bdecode_node. This function builds a tree that points back into the original buffer. The returned bdecode_node will not be valid once the buffer it was parsed out of is discarded.

It's possible to construct an entry from a bdecode_node, if a structure needs to be altered and re-encoded.

[report issue]

entry

Declared in "libtorrent/entry.hpp"

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 or a string.

class entry
{
   data_type type () const;
   entry (list_type);
   entry (integer_type);
   entry (span<char const>);
   entry (dictionary_type);
   entry (preformatted_type);
   entry (U v);
   entry (data_type t);
   entry (bdecode_node const& n);
   entry& operator= (span<char const>) &;
   entry& operator= (integer_type) &;
   entry& operator= (preformatted_type) &;
   entry& operator= (dictionary_type) &;
   entry& operator= (list_type) &;
   entry& operator= (entry&&) & noexcept;
   entry& operator= (bdecode_node const&) &;
   entry& operator= (entry const&) &;
   entry& operator= (U v) &;
   string_type& string ();
   list_type& list ();
   dictionary_type const& dict () const;
   dictionary_type& dict ();
   list_type const& list () const;
   preformatted_type const& preformatted () const;
   integer_type const& integer () const;
   string_type const& string () const;
   preformatted_type& preformatted ();
   integer_type& integer ();
   void swap (entry& e);
   entry& operator[] (string_view key);
   entry const& operator[] (string_view key) const;
   entry* find_key (string_view key);
   entry const* find_key (string_view key) const;
   std::string to_string (bool single_line = false) const;

   enum data_type
   {
      int_t,
      string_t,
      list_t,
      dictionary_t,
      undefined_t,
      preformatted_t,
   };
};
[report issue]

type()

data_type type () const;

returns the concrete type of the entry

[report issue]

entry()

entry (list_type);
entry (integer_type);
entry (span<char const>);
entry (dictionary_type);
entry (preformatted_type);

constructors directly from a specific type. The content of the argument is copied into the newly constructed entry

[report issue]

entry()

entry (data_type t);

construct an empty entry of the specified type. see data_type enum.

[report issue]

entry()

entry (bdecode_node const& n);

construct from bdecode_node parsed form (see bdecode())

[report issue]

operator=()

entry& operator= (span<char const>) &;
entry& operator= (integer_type) &;
entry& operator= (preformatted_type) &;
entry& operator= (dictionary_type) &;
entry& operator= (list_type) &;
entry& operator= (entry&&) & noexcept;
entry& operator= (bdecode_node const&) &;
entry& operator= (entry const&) &;

copies the structure of the right hand side into this entry.

[report issue]

preformatted() string() list() integer() dict()

string_type& string ();
list_type& list ();
dictionary_type const& dict () const;
dictionary_type& dict ();
list_type const& list () const;
preformatted_type const& preformatted () const;
integer_type const& integer () const;
string_type const& string () const;
preformatted_type& preformatted ();
integer_type& integer ();

The integer(), string(), list() and dict() functions are accessors that return the respective type. If the entry object isn't of the type you request, the accessor will throw system_error. You can ask an entry for its type through the type() function.

If you want to create an entry you give it the type you want it to have in its constructor, and then use one of the non-const accessors to get a reference which you then can assign the value you want it to have.

The typical code to get info from a torrent file will then look like this:

entry torrent_file;
// ...

// throws if this is not a dictionary
entry::dictionary_type const& dict = torrent_file.dict();
entry::dictionary_type::const_iterator i;
i = dict.find("announce");
if (i != dict.end())
{
        std::string tracker_url = i->second.string();
        std::cout << tracker_url << "\n";
}

The following code is equivalent, but a little bit shorter:

entry torrent_file;
// ...

// throws if this is not a dictionary
if (entry* i = torrent_file.find_key("announce"))
{
        std::string tracker_url = i->string();
        std::cout << tracker_url << "\n";
}

To make it easier to extract information from a torrent file, the class torrent_info exists.

[report issue]

swap()

void swap (entry& e);

swaps the content of this with e.

[report issue]

operator[]()

entry& operator[] (string_view key);
entry const& operator[] (string_view key) const;

All of these functions requires the entry to be a dictionary, if it isn't they will throw system_error.

The non-const versions of the operator[] will return a reference to either the existing element at the given key or, if there is no element with the given key, a reference to a newly inserted element at that key.

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 throw system_error.

[report issue]

find_key()

entry* find_key (string_view key);
entry const* find_key (string_view key) const;

These functions requires the entry to be a dictionary, if it isn't they will throw system_error.

They will look for an element at the given key in the dictionary, if the element cannot be found, they will return nullptr. If an element with the given key is found, the return a pointer to it.

[report issue]

to_string()

std::string to_string (bool single_line = false) const;

returns a pretty-printed string representation of the bencoded structure, with JSON-style syntax

[report issue]

enum data_type

Declared in "libtorrent/entry.hpp"

name value description
int_t 0  
string_t 1  
list_t 2  
dictionary_t 3  
undefined_t 4  
preformatted_t 5  
[report issue]

operator<<()

Declared in "libtorrent/entry.hpp"

inline std::ostream& operator<< (std::ostream& os, const entry& e);

prints the bencoded structure to the ostream as a JSON-style structure.

[report issue]

bencode()

Declared in "libtorrent/bencode.hpp"

template<class OutIt> int bencode (OutIt out, const entry& e);

This function will encode data to bencoded form.

The entry class is the internal representation of the bencoded data and it can be used to retrieve information, an entry can also be build by the program and given to bencode() to encode it into the OutIt iterator.

OutIt is an OutputIterator. It's a template and usually instantiated as ostream_iterator or back_insert_iterator. This function assumes the value_type of the iterator is a char. In order to encode entry e into a buffer, do:

std::vector<char> buf;
bencode(std::back_inserter(buf), e);