[Libtorrent-devel] relay mode again
Howard Chu
hyc at highlandsun.com
Mon Jun 29 22:38:17 UTC 2009
I'm still trying to get my master/slave patches working against .4. I've
gotten quite lost in the new choke manager, and have no idea how the objects
are connected back to either the choke_manager_node or the peerInfo. Can you
give me some tips on how to proceed?
As a refresher: configuring a slave opens a connection to the specified
address:port, regardless of any other tracker information.
configuring a master is supposed to give high priority to any connection from
that address - no bandwidth limits, and never choked. I have the bandwidth
limit removed, but still haven't figured out the new choke manager.
"blessing" a connection was my second attempt at figuring out the choke
manager; that attempt has also been rather useless. Any help here would be
much appreciated.
--
-- Howard Chu
CTO, Symas Corp. http://www.symas.com
Director, Highland Sun http://highlandsun.com/hyc/
Chief Architect, OpenLDAP http://www.openldap.org/project/
-------------- next part --------------
diff -wur libtorrent-0.12.4/src/download/choke_manager.cc ../libtorrent-0.12.4/src/download/choke_manager.cc
--- libtorrent-0.12.4/src/download/choke_manager.cc 2008-05-07 05:19:13.000000000 -0700
+++ ../libtorrent-0.12.4/src/download/choke_manager.cc 2009-06-16 22:00:51.000000000 -0700
@@ -145,8 +145,8 @@
if (base->snubbed())
return;
- if ((m_flags & flag_unchoke_all_new || (!is_full() && m_slotCanUnchoke())) &&
- base->time_last_choke() + rak::timer::from_seconds(10) < cachedTime) {
+ if (base->blessed() || ((m_flags & flag_unchoke_all_new || (!is_full() && m_slotCanUnchoke())) &&
+ base->time_last_choke() + rak::timer::from_seconds(10) < cachedTime)) {
m_unchoked.push_back(value_type(pc, 0));
m_slotConnection(pc, false);
@@ -221,6 +221,24 @@
}
}
+void
+ChokeManager::set_blessed(PeerConnectionBase* pc, ChokeManagerNode* base, bool v) {
+ if (base->blessed() == v)
+ return;
+
+ base->set_blessed(v);
+
+ if (base->choked()) {
+ m_unchoked.push_back(value_type(pc, 0));
+ m_slotConnection(pc, false);
+
+ m_slotUnchoke(1);
+
+ } else if (base->queued()) {
+ m_queued.push_back(value_type(pc, 0));
+ }
+}
+
// We are no longer in m_connectionList.
void
ChokeManager::disconnected(PeerConnectionBase* pc, ChokeManagerNode* base) {
diff -wur libtorrent-0.12.4/src/download/choke_manager.h ../libtorrent-0.12.4/src/download/choke_manager.h
--- libtorrent-0.12.4/src/download/choke_manager.h 2008-05-07 05:19:13.000000000 -0700
+++ ../libtorrent-0.12.4/src/download/choke_manager.h 2009-06-16 21:22:50.000000000 -0700
@@ -103,6 +103,8 @@
void set_snubbed(PeerConnectionBase* pc, ChokeManagerNode* base);
void set_not_snubbed(PeerConnectionBase* pc, ChokeManagerNode* base);
+ void set_blessed(PeerConnectionBase* pc, ChokeManagerNode* base, bool v);
+
void disconnected(PeerConnectionBase* pc, ChokeManagerNode* base);
uint32_t* choke_weight() { return m_chokeWeight; }
diff -wur libtorrent-0.12.4/src/download/choke_manager_node.h ../libtorrent-0.12.4/src/download/choke_manager_node.h
--- libtorrent-0.12.4/src/download/choke_manager_node.h 2008-05-07 05:19:13.000000000 -0700
+++ ../libtorrent-0.12.4/src/download/choke_manager_node.h 2009-06-16 21:25:04.000000000 -0700
@@ -46,7 +46,8 @@
ChokeManagerNode() :
m_queued(false),
m_unchoked(false),
- m_snubbed(false) {}
+ m_snubbed(false),
+ m_blessed(false) {}
bool queued() const { return m_queued; }
void set_queued(bool s) { m_queued = s; }
@@ -58,6 +59,9 @@
bool snubbed() const { return m_snubbed; }
void set_snubbed(bool s) { m_snubbed = s; }
+ bool blessed() const { return m_blessed; }
+ void set_blessed(bool s) { m_blessed = s; }
+
rak::timer time_last_choke() const { return m_timeLastChoke; }
void set_time_last_choke(rak::timer t) { m_timeLastChoke = t; }
@@ -65,6 +69,7 @@
bool m_queued;
bool m_unchoked;
bool m_snubbed;
+ bool m_blessed;
rak::timer m_timeLastChoke;
};
diff -wur libtorrent-0.12.4/src/download/download_main.cc ../libtorrent-0.12.4/src/download/download_main.cc
--- libtorrent-0.12.4/src/download/download_main.cc 2008-10-22 06:03:59.000000000 -0700
+++ ../libtorrent-0.12.4/src/download/download_main.cc 2009-04-26 16:02:46.000000000 -0700
@@ -184,6 +184,12 @@
m_delegator.set_aggressive(false);
update_endgame();
+ {
+ const rak::socket_address rsa = *rak::socket_address::cast_from(manager->connection_manager()->slave_address());
+ if (!rsa.is_address_any())
+ add_peer(rsa);
+ }
+
receive_connect_peers();
}
diff -wur libtorrent-0.12.4/src/protocol/handshake.cc ../libtorrent-0.12.4/src/protocol/handshake.cc
--- libtorrent-0.12.4/src/protocol/handshake.cc 2008-11-10 18:39:23.000000000 -0800
+++ ../libtorrent-0.12.4/src/protocol/handshake.cc 2009-04-26 16:33:59.000000000 -0700
@@ -1022,6 +1022,14 @@
m_peerInfo->set_flags(PeerInfo::flag_handshake);
}
+ {
+ const rak::socket_address* msa = rak::socket_address::cast_from(manager->connection_manager()->master_address());
+ rak::socket_address sa = m_address;
+ sa.set_port(0);
+ if (sa == *msa)
+ m_peerInfo->set_flags(PeerInfo::flag_master);
+ }
+
std::memcpy(m_peerInfo->set_options(), m_options, 8);
m_peerInfo->mutable_id().assign((const char*)m_readBuffer.position());
m_readBuffer.consume(20);
diff -wur libtorrent-0.12.4/src/protocol/peer_connection_base.cc ../libtorrent-0.12.4/src/protocol/peer_connection_base.cc
--- libtorrent-0.12.4/src/protocol/peer_connection_base.cc 2008-08-26 13:15:15.000000000 -0700
+++ ../libtorrent-0.12.4/src/protocol/peer_connection_base.cc 2009-06-16 22:11:21.000000000 -0700
@@ -196,6 +196,11 @@
m_download->upload_choke_manager()->set_not_snubbed(this, &m_upChoke);
}
+void
+PeerConnectionBase::set_upload_blessed(bool v) {
+ m_download->upload_choke_manager()->set_blessed(this, &m_upChoke, v);
+}
+
bool
PeerConnectionBase::receive_upload_choke(bool choke) {
if (choke == m_upChoke.choked())
@@ -621,6 +626,9 @@
uint32_t quota = m_download->upload_throttle()->node_quota(m_peerChunks.upload_throttle());
+ if (m_peerInfo->is_master())
+ quota = std::numeric_limits<uint32_t>::max();
+
if (quota == 0) {
manager->poll()->remove_write(this);
m_download->upload_throttle()->node_deactivate(m_peerChunks.upload_throttle());
diff -wur libtorrent-0.12.4/src/protocol/peer_connection_base.h ../libtorrent-0.12.4/src/protocol/peer_connection_base.h
--- libtorrent-0.12.4/src/protocol/peer_connection_base.h 2008-05-07 05:19:12.000000000 -0700
+++ ../libtorrent-0.12.4/src/protocol/peer_connection_base.h 2009-06-16 21:20:53.000000000 -0700
@@ -93,6 +93,7 @@
bool is_up_choked() const { return m_upChoke.choked(); }
bool is_up_interested() const { return m_upChoke.queued(); }
bool is_up_snubbed() const { return m_upChoke.snubbed(); }
+ bool is_up_blessed() const { return m_upChoke.blessed(); }
bool is_down_queued() const { return m_downChoke.queued(); }
bool is_down_local_unchoked() const { return m_downChoke.unchoked(); }
@@ -100,9 +101,11 @@
bool is_down_interested() const { return m_downInterested; }
void set_upload_snubbed(bool v);
+ void set_upload_blessed(bool v);
bool is_seeder() const { return m_peerChunks.is_seeder(); }
bool is_not_seeder() const { return !m_peerChunks.is_seeder(); }
+ bool is_master() const { return m_peerInfo->is_master(); }
bool is_encrypted() const { return m_encryption.is_encrypted(); }
bool is_obfuscated() const { return m_encryption.is_obfuscated(); }
diff -wur libtorrent-0.12.4/src/torrent/connection_manager.cc ../libtorrent-0.12.4/src/torrent/connection_manager.cc
--- libtorrent-0.12.4/src/torrent/connection_manager.cc 2008-11-16 06:51:48.000000000 -0800
+++ ../libtorrent-0.12.4/src/torrent/connection_manager.cc 2009-04-26 15:57:37.000000000 -0700
@@ -83,6 +83,12 @@
m_localAddress = (new rak::socket_address())->c_sockaddr();
rak::socket_address::cast_from(m_localAddress)->sa_inet()->clear();
+ m_masterAddress = (new rak::socket_address())->c_sockaddr();
+ rak::socket_address::cast_from(m_masterAddress)->sa_inet()->clear();
+
+ m_slaveAddress = (new rak::socket_address())->c_sockaddr();
+ rak::socket_address::cast_from(m_slaveAddress)->sa_inet()->clear();
+
m_proxyAddress = (new rak::socket_address())->c_sockaddr();
rak::socket_address::cast_from(m_proxyAddress)->sa_inet()->clear();
}
@@ -92,6 +98,8 @@
delete m_bindAddress;
delete m_localAddress;
+ delete m_masterAddress;
+ delete m_slaveAddress;
delete m_proxyAddress;
}
@@ -140,6 +148,26 @@
}
void
+ConnectionManager::set_master_address(const sockaddr* sa) {
+ const rak::socket_address* rsa = rak::socket_address::cast_from(sa);
+
+ if (rsa->family() != rak::socket_address::af_inet)
+ throw input_error("Tried to set a master address that is not an af_inet address.");
+
+ rak::socket_address::cast_from(m_masterAddress)->copy(*rsa, rsa->length());
+}
+
+void
+ConnectionManager::set_slave_address(const sockaddr* sa) {
+ const rak::socket_address* rsa = rak::socket_address::cast_from(sa);
+
+ if (rsa->family() != rak::socket_address::af_inet)
+ throw input_error("Tried to set a slave address that is not an af_inet address.");
+
+ rak::socket_address::cast_from(m_slaveAddress)->copy(*rsa, rsa->length());
+}
+
+void
ConnectionManager::set_proxy_address(const sockaddr* sa) {
const rak::socket_address* rsa = rak::socket_address::cast_from(sa);
diff -wur libtorrent-0.12.4/src/torrent/connection_manager.h ../libtorrent-0.12.4/src/torrent/connection_manager.h
--- libtorrent-0.12.4/src/torrent/connection_manager.h 2008-05-07 05:19:13.000000000 -0700
+++ ../libtorrent-0.12.4/src/torrent/connection_manager.h 2009-04-26 15:34:04.000000000 -0700
@@ -145,6 +145,12 @@
const sockaddr* local_address() const { return m_localAddress; }
void set_local_address(const sockaddr* sa);
+ const sockaddr* master_address() const { return m_masterAddress; }
+ void set_master_address(const sockaddr* sa);
+
+ const sockaddr* slave_address() const { return m_slaveAddress; }
+ void set_slave_address(const sockaddr* sa);
+
const sockaddr* proxy_address() const { return m_proxyAddress; }
void set_proxy_address(const sockaddr* sa);
@@ -193,6 +199,8 @@
sockaddr* m_bindAddress;
sockaddr* m_localAddress;
+ sockaddr* m_masterAddress;
+ sockaddr* m_slaveAddress;
sockaddr* m_proxyAddress;
Listen* m_listen;
diff -wur libtorrent-0.12.4/src/torrent/peer/peer.cc ../libtorrent-0.12.4/src/torrent/peer/peer.cc
--- libtorrent-0.12.4/src/torrent/peer/peer.cc 2008-10-22 06:10:28.000000000 -0700
+++ ../libtorrent-0.12.4/src/torrent/peer/peer.cc 2009-06-16 21:20:15.000000000 -0700
@@ -65,6 +65,9 @@
void Peer::set_snubbed(bool v) { m_ptr()->set_upload_snubbed(v); }
void Peer::set_banned() { m_peerInfo->set_failed_counter(64); }
+bool Peer::is_blessed() const { return c_ptr()->is_up_blessed(); }
+void Peer::set_blessed(bool v) { m_ptr()->set_upload_blessed(v); }
+
const Rate* Peer::down_rate() const { return c_ptr()->c_peer_chunks()->download_throttle()->rate(); }
const Rate* Peer::up_rate() const { return c_ptr()->c_peer_chunks()->upload_throttle()->rate(); }
const Rate* Peer::peer_rate() const { return c_ptr()->c_peer_chunks()->peer_rate(); }
diff -wur libtorrent-0.12.4/src/torrent/peer/peer.h ../libtorrent-0.12.4/src/torrent/peer/peer.h
--- libtorrent-0.12.4/src/torrent/peer/peer.h 2008-10-22 06:07:23.000000000 -0700
+++ ../libtorrent-0.12.4/src/torrent/peer/peer.h 2009-06-16 21:18:01.000000000 -0700
@@ -71,6 +71,9 @@
void set_snubbed(bool v);
void set_banned();
+ bool is_blessed() const;
+ void set_blessed(bool v);
+
const HashString& id() const { return peer_info()->id(); }
const char* options() const { return peer_info()->options(); }
const sockaddr* address() const { return peer_info()->socket_address(); }
diff -wur libtorrent-0.12.4/src/torrent/peer/peer_info.h ../libtorrent-0.12.4/src/torrent/peer/peer_info.h
--- libtorrent-0.12.4/src/torrent/peer/peer_info.h 2008-05-07 05:19:13.000000000 -0700
+++ ../libtorrent-0.12.4/src/torrent/peer/peer_info.h 2009-04-26 16:34:40.000000000 -0700
@@ -56,6 +56,7 @@
static const int flag_handshake = (1 << 2);
static const int flag_blocked = (1 << 3); // For initial seeding.
static const int flag_restart = (1 << 4);
+ static const int flag_master = (1 << 5);
PeerInfo(const sockaddr* address);
~PeerInfo();
@@ -65,6 +66,7 @@
bool is_handshake() const { return m_flags & flag_handshake; }
bool is_blocked() const { return m_flags & flag_blocked; }
bool is_restart() const { return m_flags & flag_restart; }
+ bool is_master() const { return m_flags & flag_master; }
int flags() const { return m_flags; }
-------------- next part --------------
diff -wur rtorrent-0.8.4/src/command_network.cc ../rtorrent-0.8.4/src/command_network.cc
--- rtorrent-0.8.4/src/command_network.cc 2008-08-27 01:25:01.000000000 -0700
+++ ../rtorrent-0.8.4/src/command_network.cc 2009-04-26 15:25:40.000000000 -0700
@@ -334,6 +334,8 @@
ADD_COMMAND_STRING_TRI("bind", rak::make_mem_fun(control->core(), &core::Manager::set_bind_address), rak::make_mem_fun(control->core(), &core::Manager::bind_address));
ADD_COMMAND_STRING_TRI("ip", rak::make_mem_fun(control->core(), &core::Manager::set_local_address), rak::make_mem_fun(control->core(), &core::Manager::local_address));
+ ADD_COMMAND_STRING_TRI("master", rak::make_mem_fun(control->core(), &core::Manager::set_master_address), rak::make_mem_fun(control->core(), &core::Manager::master_address));
+ ADD_COMMAND_STRING_TRI("slave", rak::make_mem_fun(control->core(), &core::Manager::set_slave_address), rak::make_mem_fun(control->core(), &core::Manager::slave_address));
ADD_COMMAND_STRING_TRI("proxy_address", rak::make_mem_fun(control->core(), &core::Manager::set_proxy_address), rak::make_mem_fun(control->core(), &core::Manager::proxy_address));
ADD_COMMAND_STRING_TRI("http_proxy", rak::make_mem_fun(httpStack, &core::CurlStack::set_http_proxy), rak::make_mem_fun(httpStack, &core::CurlStack::http_proxy));
ADD_COMMAND_STRING_TRI("http_capath", rak::make_mem_fun(httpStack, &core::CurlStack::set_http_capath), rak::make_mem_fun(httpStack, &core::CurlStack::http_capath));
diff -wur rtorrent-0.8.4/src/command_peer.cc ../rtorrent-0.8.4/src/command_peer.cc
--- rtorrent-0.8.4/src/command_peer.cc 2008-05-07 05:19:11.000000000 -0700
+++ ../rtorrent-0.8.4/src/command_peer.cc 2009-06-16 22:02:59.000000000 -0700
@@ -133,6 +133,7 @@
ADD_CP_VALUE("is_incoming", std::mem_fun(&torrent::Peer::is_incoming));
ADD_CP_VALUE("is_obfuscated", std::mem_fun(&torrent::Peer::is_obfuscated));
ADD_CP_VALUE("is_snubbed", std::mem_fun(&torrent::Peer::is_snubbed));
+ ADD_CP_VALUE("is_blessed", std::mem_fun(&torrent::Peer::is_blessed));
ADD_CP_STRING_UNI("address", std::ptr_fun(&retrieve_p_address));
ADD_CP_VALUE_UNI("port", std::ptr_fun(&retrieve_p_port));
diff -wur rtorrent-0.8.4/src/core/manager.cc ../rtorrent-0.8.4/src/core/manager.cc
--- rtorrent-0.8.4/src/core/manager.cc 2008-11-18 07:06:32.000000000 -0800
+++ ../rtorrent-0.8.4/src/core/manager.cc 2009-04-26 15:30:34.000000000 -0700
@@ -337,6 +337,66 @@
}
std::string
+Manager::master_address() const {
+ return rak::socket_address::cast_from(torrent::connection_manager()->master_address())->address_str();
+}
+
+void
+Manager::set_master_address(const std::string& addr) {
+ int err;
+ rak::address_info* ai;
+
+ if ((err = rak::address_info::get_address_info(addr.c_str(), PF_INET, SOCK_STREAM, &ai)) != 0)
+ throw torrent::input_error("Could not set master address: " + std::string(rak::address_info::strerror(err)) + ".");
+
+ try {
+
+ torrent::connection_manager()->set_master_address(ai->address()->c_sockaddr());
+ rak::address_info::free_address_info(ai);
+
+ } catch (torrent::input_error& e) {
+ rak::address_info::free_address_info(ai);
+ throw e;
+ }
+}
+
+std::string
+Manager::slave_address() const {
+ return rak::socket_address::cast_from(torrent::connection_manager()->slave_address())->address_str();
+}
+
+void
+Manager::set_slave_address(const std::string& addr) {
+ int port;
+ rak::address_info* ai;
+
+ char buf[addr.length() + 1];
+
+ int err = std::sscanf(addr.c_str(), "%[^:]:%i", buf, &port);
+
+ if (err <= 0)
+ throw torrent::input_error("Could not parse slave address.");
+
+ if (err == 1)
+ port = 80;
+
+ if ((err = rak::address_info::get_address_info(buf, PF_INET, SOCK_STREAM, &ai)) != 0)
+ throw torrent::input_error("Could not set slave address: " + std::string(rak::address_info::strerror(err)) + ".");
+
+ try {
+
+ ai->address()->set_port(port);
+ torrent::connection_manager()->set_slave_address(ai->address()->c_sockaddr());
+
+ rak::address_info::free_address_info(ai);
+
+ } catch (torrent::input_error& e) {
+ rak::address_info::free_address_info(ai);
+ throw e;
+ }
+}
+
+std::string
Manager::proxy_address() const {
return rak::socket_address::cast_from(torrent::connection_manager()->proxy_address())->address_str();
}
diff -wur rtorrent-0.8.4/src/core/manager.h ../rtorrent-0.8.4/src/core/manager.h
--- rtorrent-0.8.4/src/core/manager.h 2008-08-27 01:25:01.000000000 -0700
+++ ../rtorrent-0.8.4/src/core/manager.h 2009-04-26 15:26:30.000000000 -0700
@@ -97,6 +97,12 @@
std::string local_address() const;
void set_local_address(const std::string& addr);
+ std::string master_address() const;
+ void set_master_address(const std::string& addr);
+
+ std::string slave_address() const;
+ void set_slave_address(const std::string& addr);
+
std::string proxy_address() const;
void set_proxy_address(const std::string& addr);
diff -wur rtorrent-0.8.4/src/display/window_peer_list.cc ../rtorrent-0.8.4/src/display/window_peer_list.cc
--- rtorrent-0.8.4/src/display/window_peer_list.cc 2008-05-07 05:19:11.000000000 -0700
+++ ../rtorrent-0.8.4/src/display/window_peer_list.cc 2009-06-16 22:04:21.000000000 -0700
@@ -142,6 +142,9 @@
if (p->is_snubbed())
m_canvas->print(x, y, "*");
+ if (p->is_blessed())
+ m_canvas->print(x+1, y, "+");
+
x += 6;
if (p->failed_counter() != 0)
diff -wur rtorrent-0.8.4/src/ui/element_peer_list.cc ../rtorrent-0.8.4/src/ui/element_peer_list.cc
--- rtorrent-0.8.4/src/ui/element_peer_list.cc 2008-10-22 06:17:34.000000000 -0700
+++ ../rtorrent-0.8.4/src/ui/element_peer_list.cc 2009-06-16 22:06:38.000000000 -0700
@@ -75,6 +75,7 @@
m_bindings['k'] = sigc::mem_fun(this, &ElementPeerList::receive_disconnect_peer);
m_bindings['*'] = sigc::mem_fun(this, &ElementPeerList::receive_snub_peer);
+ m_bindings['+'] = sigc::mem_fun(this, &ElementPeerList::receive_bless_peer);
m_bindings['B'] = sigc::mem_fun(this, &ElementPeerList::receive_ban_peer);
m_bindings[KEY_LEFT] = m_bindings['B' - '@'] = sigc::mem_fun(&m_slotExit, &slot_type::operator());
m_bindings[KEY_RIGHT] = m_bindings['F' - '@'] = sigc::bind(sigc::mem_fun(this, &ElementPeerList::activate_display), DISPLAY_INFO);
@@ -246,6 +247,16 @@
}
void
+ElementPeerList::receive_bless_peer() {
+ if (m_listItr == m_list.end())
+ return;
+
+ (*m_listItr)->set_blessed(!(*m_listItr)->is_blessed());
+
+ update_itr();
+}
+
+void
ElementPeerList::receive_ban_peer() {
if (m_listItr == m_list.end())
return;
diff -wur rtorrent-0.8.4/src/ui/element_peer_list.h ../rtorrent-0.8.4/src/ui/element_peer_list.h
--- rtorrent-0.8.4/src/ui/element_peer_list.h 2008-10-22 06:04:56.000000000 -0700
+++ ../rtorrent-0.8.4/src/ui/element_peer_list.h 2009-06-16 22:07:34.000000000 -0700
@@ -75,6 +75,7 @@
void receive_peer_disconnected(torrent::Peer* p);
void receive_snub_peer();
+ void receive_bless_peer();
void receive_ban_peer();
void update_itr();
More information about the Libtorrent-devel
mailing list