merged RC_1_1 into master

This commit is contained in:
arvidn 2017-03-30 18:07:24 -04:00
commit 0b6fe4d0bd
17 changed files with 119 additions and 456 deletions

View File

@ -63,6 +63,8 @@
* resume data no longer has timestamps of files
* require C++11 to build libtorrent
* removed (broken) support for incoming connections over socks5
* restore announce_entry's timestamp fields to posix time in python binding
* deprecate torrent_added_alert (in favor of add_torrent_alert)
* fix python binding for parse_magnet_uri
* fix minor robustness issue in DHT bootstrap logic

View File

@ -8,6 +8,7 @@
#include <libtorrent/torrent.hpp>
#include <libtorrent/magnet_uri.hpp>
#include "gil.hpp"
#include "bytes.hpp"
using namespace boost::python;
using namespace libtorrent;

View File

@ -237,6 +237,21 @@ void add_tracker(torrent_handle& h, dict d)
h.add_tracker(ae);
}
namespace
{
#if defined BOOST_ASIO_HAS_STD_CHRONO
using std::chrono::system_clock;
#else
using boost::chrono::system_clock;
#endif
time_t to_ptime(time_point tpt)
{
return system_clock::to_time_t(system_clock::now()
+ duration_cast<system_clock::duration>(tpt - clock_type::now()));
}
}
list trackers(torrent_handle& h)
{
list ret;
@ -251,8 +266,18 @@ list trackers(torrent_handle& h)
last_error["value"] = i->last_error.value();
last_error["category"] = i->last_error.category().name();
d["last_error"] = last_error;
d["next_announce"] = i->next_announce;
d["min_announce"] = i->min_announce;
if (i->next_announce > min_time()) {
d["next_announce"] = to_ptime(i->next_announce);
}
else {
d["next_announce"] = object();
}
if (i->min_announce > min_time()) {
d["min_announce"] = to_ptime(i->min_announce);
}
else {
d["min_announce"] = object();
}
d["scrape_incomplete"] = i->scrape_incomplete;
d["scrape_complete"] = i->scrape_complete;
d["scrape_downloaded"] = i->scrape_downloaded;

View File

@ -128,6 +128,11 @@ class test_torrent_handle(unittest.TestCase):
"""Test to ensure the dict contains only python built-in types"""
self.setup()
self.h.add_tracker({'url':'udp://tracker1.com'})
tr = self.h.trackers()[0]
# wait a bit until a valid timestamp appears
while tr['next_announce'] == None:
time.sleep(0.1)
tr = self.h.trackers()[0]
import json
print(json.dumps(self.h.trackers()[0]))

View File

@ -745,6 +745,64 @@ Custom peer classes can be assigned to torrents, with the ??? call, in which
case all its peers will belong to the class. They can also be assigned based on
the peer's IP address. See set_peer_class_filter() for more information.
peer class examples
-------------------
Here are a few examples of common peer class operations.
To make the global rate limit apply to local peers as well, update the IP-filter
based peer class assignment:
.. code:: c++
std::uint32_t const mask = 1 << lt::session::global_peer_class_id;
ip_filter f;
// for every IPv4 address, assign the global peer class
f.add_rule(address_v4::from_string("0.0.0.0")
, address_v4::from_string("255.255.255.255")
, mask);
// for every IPv6 address, assign the global peer class
f.add_rule(address_v6::from_string("::")
, address_v6::from_string("ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff")
, mask);
ses.set_peer_class_filter(f);
To make uTP sockets exempt from rate limiting:
.. code:: c++
peer_class_type_filter flt;
// filter out the global and local peer class for uTP sockets, if these
// classes are set by the IP filter
flt.disallow(peer_class_type_filter::utp_socket, session::global_peer_class_id);
flt.disallow(peer_class_type_filter::utp_socket, session::local_peer_class_id);
// this filter should not add the global or local peer class to utp sockets
flt.remove(peer_class_type_filter::utp_socket, session::global_peer_class_id);
flt.remove(peer_class_type_filter::utp_socket, session::local_peer_class_id);
ses.set_peer_class_type_filter(flt);
To make all peers on the internal network unthrottled:
.. code:: c++
std::uint32_t const mask = 1 << lt::session::global_peer_class_id;
ip_filter f;
// for every IPv4 address, assign the global peer class
f.add_rule(address_v4::from_string("0.0.0.0")
, address_v4::from_string("255.255.255.255")
, mask);
// for every address on the local metwork, set the mastk to 0
f.add_rule(address_v4::from_string("10.0.0.0")
, address_v4::from_string("10.255.255.255")
, 0);
ses.set_peer_class_filter(f);
SSL torrents
============

View File

@ -29,6 +29,7 @@ For example:
#include <libtorrent/session.hpp>
#include <libtorrent/add_torrent_params.hpp>
#include <libtorrent/torrent_handle.hpp>
#include <libtorrent/magnet_uri.hpp>
namespace lt = libtorrent;
int main(int argc, char const* argv[])
@ -40,7 +41,8 @@ For example:
lt::session ses;
lt::add_torrent_params atp;
atp.url = argv[1];
lt::error_code ec;
lt::parse_magnet_uri(argv[1], atp, ec);
atp.save_path = "."; // save in current dir
lt::torrent_handle h = ses.add_torrent(atp);

View File

@ -1228,9 +1228,8 @@ MAGNETURL is a magnet link
if (rate_limit_locals)
{
ip_filter pcf;
// 1 is the global peer class. This should be done properly in the future
pcf.add_rule(address_v4::from_string("0.0.0.0")
, address_v4::from_string("255.255.255.255"), 1);
, address_v4::from_string("255.255.255.255"), 1 << lt::session::global_peer_class_id);
#if TORRENT_USE_IPV6
pcf.add_rule(address_v6::from_string("::")
, address_v6::from_string("ffff:ffff:ffff:ffff:ffff:ffff:ffff:ffff"), 1);

View File

@ -374,6 +374,9 @@ namespace libtorrent
//
// -1 means unlimited on these settings just like their counterpart
// functions on torrent_handle
//
// For fine grained control over rate limits, including making them apply
// to local peers, see peer-classes_.
int max_uploads = -1;
int max_connections = -1;

View File

@ -309,10 +309,6 @@ namespace libtorrent
void async_accept(std::shared_ptr<tcp::acceptor> const& listener, bool ssl);
void on_accept_connection(std::shared_ptr<socket_type> const& s
, std::weak_ptr<tcp::acceptor> listener, error_code const& e, bool ssl);
void on_socks_listen(std::shared_ptr<socket_type> const& s
, error_code const& e);
void on_socks_accept(std::shared_ptr<socket_type> const& s
, error_code const& e);
void incoming_connection(std::shared_ptr<socket_type> const& s);
@ -918,16 +914,9 @@ namespace libtorrent
void ssl_handshake(error_code const& ec, std::shared_ptr<socket_type> s);
#endif
// when as a socks proxy is used for peers, also
// listen for incoming connections on a socks connection
std::shared_ptr<socket_type> m_socks_listen_socket;
std::uint16_t m_socks_listen_port = 0;
// round-robin index into m_outgoing_interfaces
mutable std::uint8_t m_interface_index = 0;
void open_new_incoming_socks_connection();
enum listen_on_flags_t
{
open_ssl_socket = 0x10

View File

@ -1290,6 +1290,9 @@ namespace libtorrent
// limited.
//
// A value of 0 means unlimited.
//
// For fine grained control over rate limits, including making them apply
// to local peers, see peer-classes_.
upload_rate_limit,
download_rate_limit,
#ifndef TORRENT_NO_DEPRECATE

View File

@ -84,7 +84,6 @@ public:
// commands
enum {
socks5_connect = 1,
socks5_bind = 2,
socks5_udp_associate = 3
};
@ -92,14 +91,13 @@ public:
: proxy_base(io_service)
, m_version(5)
, m_command(socks5_connect)
, m_listen(0)
{}
void set_version(int v) { m_version = v; }
void set_command(int c)
{
TORRENT_ASSERT(c >= socks5_connect && c <= socks5_udp_associate);
TORRENT_ASSERT(c == socks5_connect || c == socks5_udp_associate);
m_command = c;
}
@ -110,39 +108,6 @@ public:
m_password = password;
}
template <typename Handler>
void async_accept(Handler const& handler)
{
TORRENT_ASSERT(m_listen == 1);
TORRENT_ASSERT(m_command == socks5_bind);
// to avoid unnecessary copying of the handler,
// store it in a shared_ptr
error_code e;
#if defined TORRENT_ASIO_DEBUGGING
add_outstanding_async("socks5_stream::connect1");
#endif
handler_type h(std::move(handler));
connect1(e, h);
}
template <typename Handler>
void async_listen(tcp::endpoint const& ep, Handler handler)
{
m_command = socks5_bind;
m_remote_endpoint = ep;
#if defined TORRENT_ASIO_DEBUGGING
add_outstanding_async("socks5_stream::name_lookup");
#endif
using std::placeholders::_1;
using std::placeholders::_2;
tcp::resolver::query q(m_hostname, to_string(m_port).data());
m_resolver.async_resolve(q, std::bind(
&socks5_stream::name_lookup, this, _1, _2, handler_type(std::move(handler))));
}
void set_dst_name(std::string const& host)
{
// if this assert trips, set_dst_name() is called wth an IP address rather
@ -168,26 +133,12 @@ public:
}
#endif
#ifndef BOOST_NO_EXCEPTIONS
endpoint_type local_endpoint() const
{
return m_local_endpoint;
}
#endif
endpoint_type local_endpoint(error_code&) const
{
return m_local_endpoint;
}
// TODO: 2 add async_connect() that takes a hostname and port as well
template <class Handler>
void async_connect(endpoint_type const& endpoint, Handler const& handler)
{
// make sure we don't try to connect to INADDR_ANY. binding is fine,
// and using a hostname is fine on SOCKS version 5.
TORRENT_ASSERT(m_command != socks5_bind);
TORRENT_ASSERT(endpoint.address() != address()
|| (!m_dst_name.empty() && m_version == 5));
@ -231,19 +182,10 @@ private:
std::string m_password;
std::string m_dst_name;
// when listening via a socks proxy, this is the IP and port our listen
// socket bound to
endpoint_type m_local_endpoint;
int m_version;
// the socks command to send for this connection (connect, bind,
// udp associate)
// the socks command to send for this connection (connect or udp associate)
int m_command;
// set to one when we're waiting for the
// second message to accept an incoming connection
int m_listen;
};
}

View File

@ -1088,6 +1088,8 @@ namespace libtorrent
//
// ``upload_limit`` and ``download_limit`` will return the current limit
// setting, for upload and download, respectively.
//
// Local peers are not rate limited by default. see peer-classes_.
void set_upload_limit(int limit) const;
int upload_limit() const;
void set_download_limit(int limit) const;

View File

@ -101,143 +101,6 @@ void run_test(Setup const& setup
test(sim, *ses, params.ti);
}
TORRENT_TEST(socks5_tcp_accept)
{
using namespace libtorrent;
bool incoming_connection = false;
run_test(
[](lt::session& ses)
{
set_proxy(ses, settings_pack::socks5);
},
[&](lt::session&, lt::alert const* alert) {
if (auto* a = lt::alert_cast<lt::incoming_connection_alert>(alert))
{
TEST_EQUAL(a->socket_type, 2);
incoming_connection = true;
}
},
[](sim::simulation& sim, lt::session&
, std::shared_ptr<lt::torrent_info> ti)
{
// test connecting to the client via its socks5 listen port
// TODO: maybe we could use peer_conn here instead
fake_peer peer1(sim, "60.0.0.0");
fake_peer peer2(sim, "60.0.0.1");
sim::timer t1(sim, lt::seconds(2), [&](boost::system::error_code const&)
{
peer1.connect_to(tcp::endpoint(addr("50.50.50.50"), 6881), ti->info_hash());
});
sim::timer t2(sim, lt::seconds(3), [&](boost::system::error_code const&)
{
peer2.connect_to(tcp::endpoint(addr("50.50.50.50"), 6881), ti->info_hash());
});
sim.run();
}
);
TEST_EQUAL(incoming_connection, true);
}
TORRENT_TEST(socks4_tcp_accept)
{
using namespace libtorrent;
bool incoming_connection = false;
run_test(
[](lt::session& ses)
{
set_proxy(ses, settings_pack::socks4);
},
[&](lt::session&, lt::alert const* alert) {
if (auto* a = lt::alert_cast<lt::incoming_connection_alert>(alert))
{
TEST_EQUAL(a->socket_type, 2);
TEST_EQUAL(a->endpoint.address(), addr("60.0.0.0"))
incoming_connection = true;
}
},
[](sim::simulation& sim, lt::session&
, std::shared_ptr<lt::torrent_info> ti)
{
fake_peer peer1(sim, "60.0.0.0");
sim::timer t1(sim, lt::seconds(2), [&](boost::system::error_code const&)
{
peer1.connect_to(tcp::endpoint(addr("50.50.50.50"), 6881), ti->info_hash());
});
sim.run();
}
);
TEST_EQUAL(incoming_connection, true);
}
// make sure a listen_succeeded_alert is issued when successfully listening on
// incoming connections via a socks5 proxy
TORRENT_TEST(socks4_tcp_listen_alert)
{
using namespace libtorrent;
bool listen_alert = false;
run_test(
[](lt::session& ses)
{
set_proxy(ses, settings_pack::socks4);
},
[&](lt::session&, lt::alert const* alert) {
if (auto* a = lt::alert_cast<lt::listen_succeeded_alert>(alert))
{
if (a->socket_type == socket_type_t::socks5)
{
TEST_EQUAL(a->address, addr("50.50.50.50"));
TEST_EQUAL(a->port, 6881);
listen_alert = true;
}
}
},
[](sim::simulation& sim, lt::session&
, std::shared_ptr<lt::torrent_info> ti)
{
sim.run();
}
);
TEST_EQUAL(listen_alert, true);
}
TORRENT_TEST(socks5_tcp_listen_alert)
{
using namespace libtorrent;
bool listen_alert = false;
run_test(
[](lt::session& ses)
{
set_proxy(ses, settings_pack::socks5);
},
[&](lt::session&, lt::alert const* alert) {
if (auto* a = lt::alert_cast<lt::listen_succeeded_alert>(alert))
{
if (a->socket_type == socket_type_t::socks5)
{
TEST_EQUAL(a->address, addr("50.50.50.50"));
TEST_EQUAL(a->port, 6881);
listen_alert = true;
}
}
},
[](sim::simulation& sim, lt::session&
, std::shared_ptr<lt::torrent_info> ti)
{
sim.run();
}
);
TEST_EQUAL(listen_alert, true);
}
TORRENT_TEST(socks5_tcp_announce)
{
using namespace libtorrent;
@ -257,7 +120,7 @@ TORRENT_TEST(socks5_tcp_announce)
[&alert_port](lt::session&, lt::alert const* alert) {
if (auto* a = lt::alert_cast<lt::listen_succeeded_alert>(alert))
{
if (a->socket_type == socket_type_t::socks5)
if (a->socket_type == socket_type_t::udp)
{
alert_port = a->port;
}
@ -291,7 +154,8 @@ TORRENT_TEST(socks5_tcp_announce)
}
);
TEST_EQUAL(alert_port, tracker_port);
// since force_proxy is enabled, don't send the port
TEST_EQUAL(tracker_port, 0);
TEST_CHECK(alert_port != -1);
TEST_CHECK(tracker_port != -1);
}

View File

@ -756,7 +756,7 @@ TORRENT_TEST(tracker_ipv6_argument)
TEST_CHECK(pos != std::string::npos || stop_event);
got_ipv6 |= pos != std::string::npos;
// make sure the IPv6 argument is url encoded
TEST_CHECK(req.substr(pos + 6, req.find_first_of('&', pos + 6))
TEST_CHECK(req.substr(pos + 6, req.substr(pos + 6).find_first_of('&'))
== "ffff%3a%3a1337");
return sim::send_response(200, "OK", 11) + "d5:peers0:e";
}

View File

@ -52,8 +52,6 @@ using namespace sim;
namespace lt = libtorrent;
const int connect_socks = 2;
std::string make_ep_string(char const* address, bool const is_v6
, char const* port)
{
@ -125,8 +123,7 @@ void run_test(
print_alerts(*ses[0], [=](lt::session& ses, lt::alert const* a) {
if (auto ta = alert_cast<lt::add_torrent_alert>(a))
{
ta->handle.connect_peer(lt::tcp::endpoint(
(flags & connect_socks) ? proxy : peer1, 6881));
ta->handle.connect_peer(lt::tcp::endpoint(peer1, 6881));
}
on_alert(ses, a);
});
@ -192,26 +189,6 @@ TORRENT_TEST(socks5_tcp_connect)
);
}
TORRENT_TEST(socks5_tcp_accept)
{
using namespace libtorrent;
run_test(
[](lt::session& ses0, lt::session& ses1)
{
// this time, the session accepting the connection is listening on a
// socks5 BIND session
set_proxy(ses1, settings_pack::socks5);
filter_ips(ses0);
},
[](lt::session&, lt::alert const*) {},
[](std::shared_ptr<lt::session> ses[2]) {
TEST_EQUAL(is_seed(*ses[0]), true);
},
connect_socks
);
}
TORRENT_TEST(encryption_tcp)
{
using namespace libtorrent;

View File

@ -949,12 +949,6 @@ namespace aux {
l.udp_sock->close();
}
}
if (m_socks_listen_socket && m_socks_listen_socket->is_open())
{
m_socks_listen_socket->close(ec);
TORRENT_ASSERT(!ec);
}
m_socks_listen_socket.reset();
#if TORRENT_USE_I2P
if (m_i2p_listen_socket && m_i2p_listen_socket->is_open())
@ -1965,7 +1959,6 @@ namespace aux {
remap_ports(remap_natpmp_and_upnp, s);
}
open_new_incoming_socks_connection();
#if TORRENT_USE_I2P
open_new_incoming_i2p_connection();
#endif
@ -2003,96 +1996,6 @@ namespace aux {
}
}
void session_impl::open_new_incoming_socks_connection()
{
int const proxy_type = m_settings.get_int(settings_pack::proxy_type);
if (proxy_type != settings_pack::socks5
&& proxy_type != settings_pack::socks5_pw
&& proxy_type != settings_pack::socks4)
return;
if (m_socks_listen_socket) return;
m_socks_listen_socket = std::make_shared<socket_type>(m_io_service);
bool const ret = instantiate_connection(m_io_service, proxy()
, *m_socks_listen_socket, nullptr, nullptr, false, false);
TORRENT_ASSERT_VAL(ret, ret);
TORRENT_UNUSED(ret);
ADD_OUTSTANDING_ASYNC("session_impl::on_socks_listen");
socks5_stream& s = *m_socks_listen_socket->get<socks5_stream>();
// figure out which port to ask the socks5 proxy to open or us.
m_socks_listen_port = (m_listen_sockets.empty()
|| m_settings.get_bool(settings_pack::anonymous_mode))
? std::uint16_t(2000 + random(60000))
: std::uint16_t(m_listen_sockets.front().tcp_external_port);
s.async_listen(tcp::endpoint(address_v4::any(), m_socks_listen_port)
, std::bind(&session_impl::on_socks_listen, this
, m_socks_listen_socket, _1));
}
void session_impl::on_socks_listen(std::shared_ptr<socket_type> const& sock
, error_code const& e)
{
#if defined TORRENT_ASIO_DEBUGGING
complete_async("session_impl::on_socks_listen");
#endif
TORRENT_ASSERT(sock == m_socks_listen_socket || !m_socks_listen_socket);
if (e)
{
m_socks_listen_socket.reset();
if (e == boost::asio::error::operation_aborted) return;
if (m_alerts.should_post<listen_failed_alert>())
m_alerts.emplace_alert<listen_failed_alert>("socks5"
, listen_failed_alert::accept, e
, socket_type_t::socks5);
return;
}
if (m_abort) return;
error_code ec;
tcp::endpoint ep = sock->local_endpoint(ec);
TORRENT_ASSERT(!ec);
TORRENT_UNUSED(ec);
if (m_alerts.should_post<listen_succeeded_alert>())
m_alerts.emplace_alert<listen_succeeded_alert>(
ep, socket_type_t::socks5);
#if defined TORRENT_ASIO_DEBUGGING
add_outstanding_async("session_impl::on_socks_accept");
#endif
socks5_stream& s = *m_socks_listen_socket->get<socks5_stream>();
s.async_accept(std::bind(&session_impl::on_socks_accept, this
, m_socks_listen_socket, _1));
}
void session_impl::on_socks_accept(std::shared_ptr<socket_type> const& s
, error_code const& e)
{
COMPLETE_ASYNC("session_impl::on_socks_accept");
TORRENT_ASSERT(s == m_socks_listen_socket || !m_socks_listen_socket);
m_socks_listen_socket.reset();
if (e == boost::asio::error::operation_aborted) return;
if (e)
{
if (m_alerts.should_post<listen_failed_alert>())
m_alerts.emplace_alert<listen_failed_alert>("socks5"
, listen_failed_alert::accept, e
, socket_type_t::socks5);
return;
}
if (m_abort) return;
open_new_incoming_socks_connection();
incoming_connection(s);
}
void session_impl::update_i2p_bridge()
{
// we need this socket to be open before we
@ -5194,9 +5097,6 @@ namespace aux {
void session_impl::update_proxy()
{
// in case we just set a socks proxy, we might have to
// open the socks incoming connection
if (!m_socks_listen_socket) open_new_incoming_socks_connection();
for (auto& i : m_listen_sockets)
{
i.udp_sock->set_proxy_settings(proxy());
@ -5274,12 +5174,6 @@ namespace aux {
std::uint16_t session_impl::listen_port() const
{
// if peer connections are set up to be received over a socks
// proxy, and it's the same one as we're using for the tracker
// just tell the tracker the socks5 port we're listening on
if (m_socks_listen_socket && m_socks_listen_socket->is_open())
return m_socks_listen_socket->local_endpoint().port();
// if not, don't tell the tracker anything if we're in force_proxy
// mode. We don't want to leak our listen port since it can
// potentially identify us if it is leaked elsewhere
@ -5293,12 +5187,6 @@ namespace aux {
std::uint16_t session_impl::ssl_listen_port() const
{
#ifdef TORRENT_USE_OPENSSL
// if peer connections are set up to be received over a socks
// proxy, and it's the same one as we're using for the tracker
// just tell the tracker the socks5 port we're listening on
if (m_socks_listen_socket && m_socks_listen_socket->is_open())
return m_socks_listen_port;
// if not, don't tell the tracker anything if we're in force_proxy
// mode. We don't want to leak our listen port since it can
// potentially identify us if it is leaked elsewhere

View File

@ -80,56 +80,6 @@ namespace libtorrent
return cat;
}
namespace
{
// parse out the endpoint from a SOCKS response
tcp::endpoint parse_endpoint(std::vector<char> const& buffer
, int const version)
{
using namespace libtorrent::detail;
char const* p = &buffer[0];
p += 2; // version & response code
if (version == 5)
{
++p; // reserved byte
int const atyp = read_uint8(p);
if (atyp == 1)
{
tcp::endpoint ret;
ret.address(read_v4_address(p));
ret.port(read_uint16(p));
return ret;
}
else if (atyp == 3)
{
// we don't support resolving the endpoint address
// if we receive a domain name, just set the remote
// endpoint to INADDR_ANY
return tcp::endpoint();
}
else if (atyp == 4)
{
tcp::endpoint ret;
#if TORRENT_USE_IPV6
ret.address(read_v6_address(p));
ret.port(read_uint16(p));
#endif
return ret;
}
}
else if (version == 4)
{
tcp::endpoint ret;
ret.port(read_uint16(p));
ret.address(read_v4_address(p));
return ret;
}
TORRENT_ASSERT_FAIL();
return tcp::endpoint();
}
}
void socks5_stream::name_lookup(error_code const& e, tcp::resolver::iterator i
, handler_type& h)
{
@ -301,7 +251,7 @@ namespace libtorrent
:(m_remote_endpoint.address().is_v4()?4:16)));
char* p = &m_buffer[0];
write_uint8(5, p); // SOCKS VERSION 5
write_uint8(std::uint8_t(m_command), p); // CONNECT/BIND command
write_uint8(std::uint8_t(m_command), p); // CONNECT command
write_uint8(0, p); // reserved
if (!m_dst_name.empty())
{
@ -314,8 +264,7 @@ namespace libtorrent
else
{
// we either need a hostname or a valid endpoint
TORRENT_ASSERT(m_command == socks5_bind
|| m_remote_endpoint.address() != address());
TORRENT_ASSERT(m_remote_endpoint.address() != address());
write_uint8(m_remote_endpoint.address().is_v4()?1:4, p); // address type
write_address(m_remote_endpoint.address(), p);
@ -333,7 +282,7 @@ namespace libtorrent
m_buffer.resize(m_user.size() + 9);
char* p = &m_buffer[0];
write_uint8(4, p); // SOCKS VERSION 4
write_uint8(std::uint8_t(m_command), p); // CONNECT/BIND command
write_uint8(std::uint8_t(m_command), p); // CONNECT command
write_uint16(m_remote_endpoint.port(), p);
write_uint32(m_remote_endpoint.address().to_v4().to_ulong(), p);
std::copy(m_user.begin(), m_user.end(), p);
@ -406,25 +355,8 @@ namespace libtorrent
// on address type)
if (atyp == 1)
{
if (m_command == socks5_bind)
{
if (m_listen == 0)
{
m_local_endpoint = parse_endpoint(m_buffer, m_version);
m_listen = 1;
}
else
{
m_remote_endpoint = parse_endpoint(m_buffer, m_version);
}
std::vector<char>().swap(m_buffer);
h(e);
}
else
{
std::vector<char>().swap(m_buffer);
h(e);
}
std::vector<char>().swap(m_buffer);
h(e);
return;
}
std::size_t extra_bytes = 0;
@ -461,25 +393,8 @@ namespace libtorrent
// access granted
if (response == 90)
{
if (m_command == socks5_bind)
{
if (m_listen == 0)
{
m_local_endpoint = parse_endpoint(m_buffer, m_version);
m_listen = 1;
}
else
{
m_remote_endpoint = parse_endpoint(m_buffer, m_version);
}
std::vector<char>().swap(m_buffer);
h(e);
}
else
{
std::vector<char>().swap(m_buffer);
h(e);
}
std::vector<char>().swap(m_buffer);
h(e);
return;
}
@ -501,18 +416,6 @@ namespace libtorrent
if (handle_error(e, h)) return;
if (m_command == socks5_bind)
{
if (m_listen == 0)
{
m_local_endpoint = parse_endpoint(m_buffer, m_version);
m_listen = 1;
}
else
{
m_remote_endpoint = parse_endpoint(m_buffer, m_version);
}
}
std::vector<char>().swap(m_buffer);
h(e);
}