Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix partially done downloads and choke groups #575

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
49 changes: 9 additions & 40 deletions src/command_download.cc
Original file line number Diff line number Diff line change
Expand Up @@ -196,19 +196,6 @@ apply_d_connection_type(core::Download* download, const std::string& name) {
return torrent::Object();
}

torrent::Object
apply_d_choke_heuristics(core::Download* download, const std::string& name, bool is_down) {
torrent::Download::HeuristicType t =
(torrent::Download::HeuristicType)torrent::option_find_string(torrent::OPTION_CHOKE_HEURISTICS, name.c_str());

if (is_down)
download->download()->set_download_choke_heuristic(t);
else
download->download()->set_upload_choke_heuristic(t);

return torrent::Object();
}

const char*
retrieve_d_priority_str(core::Download* download) {
switch (download->priority()) {
Expand Down Expand Up @@ -687,6 +674,7 @@ initialize_command_download() {
CMD2_DL ("d.is_partially_done", CMD2_ON_DATA(is_partially_done));
CMD2_DL ("d.is_not_partially_done", CMD2_ON_DATA(is_not_partially_done));
CMD2_DL ("d.is_meta", CMD2_ON_INFO(is_meta_download));
CMD2_DL ("d.is_done", CMD2_ON_FL(is_done));

CMD2_DL_V ("d.resume", std::bind(&core::DownloadList::resume_default, control->core()->download_list(), std::placeholders::_1));
CMD2_DL_V ("d.pause", std::bind(&core::DownloadList::pause_default, control->core()->download_list(), std::placeholders::_1));
Expand Down Expand Up @@ -760,16 +748,6 @@ initialize_command_download() {
CMD2_DL_VAR_STRING("d.connection_leech", "rtorrent", "connection_leech");
CMD2_DL_VAR_STRING("d.connection_seed", "rtorrent", "connection_seed");

CMD2_DL ("d.up.choke_heuristics", std::bind(&torrent::option_as_string, torrent::OPTION_CHOKE_HEURISTICS, CMD2_ON_DL(upload_choke_heuristic)));
CMD2_DL_STRING("d.up.choke_heuristics.set", std::bind(&apply_d_choke_heuristics, std::placeholders::_1, std::placeholders::_2, false));
CMD2_DL ("d.down.choke_heuristics", std::bind(&torrent::option_as_string, torrent::OPTION_CHOKE_HEURISTICS, CMD2_ON_DL(download_choke_heuristic)));
CMD2_DL_STRING("d.down.choke_heuristics.set", std::bind(&apply_d_choke_heuristics, std::placeholders::_1, std::placeholders::_2, true));

CMD2_DL_VAR_STRING("d.up.choke_heuristics.leech", "rtorrent", "choke_heuristics.up.leech");
CMD2_DL_VAR_STRING("d.up.choke_heuristics.seed", "rtorrent", "choke_heuristics.up.seed");
CMD2_DL_VAR_STRING("d.down.choke_heuristics.leech", "rtorrent", "choke_heuristics.down.leech");
CMD2_DL_VAR_STRING("d.down.choke_heuristics.seed", "rtorrent", "choke_heuristics.down.seed");

CMD2_DL ("d.hashing_failed", std::bind(&core::Download::is_hash_failed, std::placeholders::_1));
CMD2_DL_VALUE_V ("d.hashing_failed.set", std::bind(&core::Download::set_hash_failed, std::placeholders::_1, std::placeholders::_2));

Expand Down Expand Up @@ -819,12 +797,13 @@ initialize_command_download() {
CMD2_DL ("d.chunks_hashed", CMD2_ON_DL(chunks_hashed));
CMD2_DL ("d.free_diskspace", CMD2_ON_FL(free_diskspace));

CMD2_DL ("d.size_files", CMD2_ON_FL(size_files));
CMD2_DL ("d.size_bytes", CMD2_ON_FL(size_bytes));
CMD2_DL ("d.size_chunks", CMD2_ON_FL(size_chunks));
CMD2_DL ("d.chunk_size", CMD2_ON_FL(chunk_size));
CMD2_DL ("d.size_pex", CMD2_ON_DL(size_pex));
CMD2_DL ("d.max_size_pex", CMD2_ON_DL(max_size_pex));
CMD2_DL ("d.size_files", CMD2_ON_FL(size_files));
CMD2_DL ("d.selected_size_bytes", CMD2_ON_FL(selected_size_bytes));
CMD2_DL ("d.size_bytes", CMD2_ON_FL(size_bytes));
CMD2_DL ("d.size_chunks", CMD2_ON_FL(size_chunks));
CMD2_DL ("d.chunk_size", CMD2_ON_FL(chunk_size));
CMD2_DL ("d.size_pex", CMD2_ON_DL(size_pex));
CMD2_DL ("d.max_size_pex", CMD2_ON_DL(max_size_pex));

CMD2_DL ("d.chunks_seen", std::bind(&d_chunks_seen, std::placeholders::_1));

Expand Down Expand Up @@ -853,18 +832,8 @@ initialize_command_download() {
CMD2_DL ("d.priority_str", std::bind(&retrieve_d_priority_str, std::placeholders::_1));
CMD2_DL_VALUE_V ("d.priority.set", std::bind(&core::Download::set_priority, std::placeholders::_1, std::placeholders::_2));

// CMD2_DL ("d.group", std::bind(&torrent::resource_manager_entry::group,
// std::bind(&torrent::ResourceManager::entry_at, torrent::resource_manager(),
// std::bind(&core::Download::main, std::placeholders::_1))));

// CMD2_DL_V ("d.group.set", std::bind(&torrent::ResourceManager::set_group,
// torrent::resource_manager(),
// std::bind(&torrent::ResourceManager::find_throw, torrent::resource_manager(),
// std::bind(&core::Download::main, std::placeholders::_1)),
// CG_GROUP_INDEX()));

CMD2_DL ("d.group", std::bind(&cg_d_group, std::placeholders::_1));
CMD2_DL ("d.group.name", std::bind(&cg_d_group, std::placeholders::_1));
CMD2_DL ("d.group.name", std::bind(&cg_d_group_name, std::placeholders::_1));
CMD2_DL_V ("d.group.set", std::bind(&cg_d_group_set, std::placeholders::_1, std::placeholders::_2));

CMD2_DL_LIST ("f.multicall", std::bind(&f_multicall, std::placeholders::_1, std::placeholders::_2));
Expand Down
111 changes: 0 additions & 111 deletions src/command_groups.cc
Original file line number Diff line number Diff line change
Expand Up @@ -52,12 +52,6 @@
// For cg_d_group.
#include "core/download.h"

// A hack to allow testing of the new choke_group API without the
// working parts present.
#define USE_CHOKE_GROUP 0

#if USE_CHOKE_GROUP

int64_t
cg_get_index(const torrent::Object& raw_args) {
const torrent::Object& arg = (raw_args.is_list() && !raw_args.as_list().empty()) ? raw_args.as_list().front() : raw_args;
Expand Down Expand Up @@ -122,104 +116,6 @@ apply_cg_insert(const std::string& arg) {
return torrent::Object();
}

//
// The hacked version:
//
#else

std::vector<torrent::choke_group*> cg_list_hack;

int64_t
cg_get_index(const torrent::Object& raw_args) {
const torrent::Object& arg = (raw_args.is_list() && !raw_args.as_list().empty()) ? raw_args.as_list().front() : raw_args;

int64_t index = 0;

if (arg.is_string()) {
if (!rpc::parse_whole_value_nothrow(arg.as_string().c_str(), &index)) {
std::vector<torrent::choke_group*>::iterator itr = std::find_if(cg_list_hack.begin(), cg_list_hack.end(),
rak::equal(arg.as_string(), std::mem_fun(&torrent::choke_group::name)));

if (itr == cg_list_hack.end())
throw torrent::input_error("Choke group not found.");

return std::distance(cg_list_hack.begin(), itr);
}

} else {
index = arg.as_value();
}

if (index < 0)
index = (int64_t)cg_list_hack.size() + index;

if ((size_t)index >= cg_list_hack.size())
throw torrent::input_error("Choke group not found.");

return index;
}

torrent::choke_group*
cg_get_group(const torrent::Object& raw_args) {
int64_t index = cg_get_index(raw_args);

if ((size_t)index >= cg_list_hack.size())
throw torrent::input_error("Choke group not found.");

return cg_list_hack.at(index);
}

int64_t cg_d_group(core::Download* download) { return download->group(); }
void cg_d_group_set(core::Download* download, const torrent::Object& arg) { download->set_group(cg_get_index(arg)); }

torrent::Object
apply_cg_list() {
torrent::Object::list_type result;

for (std::vector<torrent::choke_group*>::iterator itr = cg_list_hack.begin(), last = cg_list_hack.end(); itr != last; itr++)
result.push_back((*itr)->name());

return torrent::Object::from_list(result);
}

torrent::Object
apply_cg_insert(const std::string& arg) {
int64_t dummy;

if (rpc::parse_whole_value_nothrow(arg.c_str(), &dummy))
throw torrent::input_error("Cannot use a value string as choke group name.");

if (arg.empty() ||
std::find_if(cg_list_hack.begin(), cg_list_hack.end(),
rak::equal(arg, std::mem_fun(&torrent::choke_group::name))) != cg_list_hack.end())
throw torrent::input_error("Duplicate name for choke group.");

cg_list_hack.push_back(new torrent::choke_group());
cg_list_hack.back()->set_name(arg);

cg_list_hack.back()->up_queue()->set_heuristics(torrent::choke_queue::HEURISTICS_UPLOAD_LEECH);
cg_list_hack.back()->down_queue()->set_heuristics(torrent::choke_queue::HEURISTICS_DOWNLOAD_LEECH);

return torrent::Object();
}

torrent::Object
apply_cg_index_of(const std::string& arg) {
std::vector<torrent::choke_group*>::iterator itr =
std::find_if(cg_list_hack.begin(), cg_list_hack.end(), rak::equal(arg, std::mem_fun(&torrent::choke_group::name)));

if (itr == cg_list_hack.end())
throw torrent::input_error("Choke group not found.");

return std::distance(cg_list_hack.begin(), itr);
}

//
// End of choke group hack.
//
#endif


torrent::Object
apply_cg_max_set(const torrent::Object::list_type& args, bool is_up) {
if (args.size() != 2)
Expand Down Expand Up @@ -338,15 +234,8 @@ initialize_command_groups() {
CMD2_ANY ("choke_group.list", std::bind(&apply_cg_list));
CMD2_ANY_STRING ("choke_group.insert", std::bind(&apply_cg_insert, std::placeholders::_2));

#if USE_CHOKE_GROUP
CMD2_ANY ("choke_group.size", std::bind(&torrent::ResourceManager::group_size, torrent::resource_manager()));
CMD2_ANY_STRING ("choke_group.index_of", std::bind(&torrent::ResourceManager::group_index_of, torrent::resource_manager(), std::placeholders::_2));
#else
apply_cg_insert("default");

CMD2_ANY ("choke_group.size", std::bind(&std::vector<torrent::choke_group*>::size, cg_list_hack));
CMD2_ANY_STRING ("choke_group.index_of", std::bind(&apply_cg_index_of, std::placeholders::_2));
#endif

// Commands specific for a group. Supports as the first argument the
// name, the index or a negative index.
Expand Down
2 changes: 1 addition & 1 deletion src/command_local.cc
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ apply_pieces_stats_total_size() {

for (core::DownloadList::iterator itr = d_list->begin(), last = d_list->end(); itr != last; itr++)
if ((*itr)->is_active())
size += (*itr)->file_list()->size_bytes();
size += (*itr)->file_list()->selected_size_bytes();

return size;
}
Expand Down
5 changes: 0 additions & 5 deletions src/command_network.cc
Original file line number Diff line number Diff line change
Expand Up @@ -254,11 +254,6 @@ initialize_command_network() {
CMD2_VAR_STRING ("protocol.connection.leech", "leech");
CMD2_VAR_STRING ("protocol.connection.seed", "seed");

CMD2_VAR_STRING ("protocol.choke_heuristics.up.leech", "upload_leech");
CMD2_VAR_STRING ("protocol.choke_heuristics.up.seed", "upload_leech");
CMD2_VAR_STRING ("protocol.choke_heuristics.down.leech", "download_leech");
CMD2_VAR_STRING ("protocol.choke_heuristics.down.seed", "download_leech");

CMD2_ANY ("network.http.cacert", std::bind(&core::CurlStack::http_cacert, httpStack));
CMD2_ANY_STRING_V("network.http.cacert.set", std::bind(&core::CurlStack::set_http_cacert, httpStack, std::placeholders::_2));
CMD2_ANY ("network.http.capath", std::bind(&core::CurlStack::http_capath, httpStack));
Expand Down
12 changes: 12 additions & 0 deletions src/command_ui.cc
Original file line number Diff line number Diff line change
Expand Up @@ -361,6 +361,17 @@ apply_to_throttle(const torrent::Object& rawArgs) {
return std::string(buffer);
}

torrent::Object
apply_to_group(const torrent::Object& rawArgs) {
int64_t arg = rawArgs.as_value();
if (arg < 0)
return "--";

char buffer[16];
snprintf(buffer, 16, "%2d", (int)(arg));
return std::string(buffer);
}

// A series of if/else statements. Every even arguments are
// conditionals and odd arguments are branches to be executed, except
// the last one which is always a branch.
Expand Down Expand Up @@ -584,6 +595,7 @@ initialize_command_ui() {
CMD2_ANY_VALUE("convert.mb", std::bind(&apply_to_mb, std::placeholders::_2));
CMD2_ANY_VALUE("convert.xb", std::bind(&apply_to_xb, std::placeholders::_2));
CMD2_ANY_VALUE("convert.throttle", std::bind(&apply_to_throttle, std::placeholders::_2));
CMD2_ANY_VALUE("convert.group", std::bind(&apply_to_group, std::placeholders::_2));

CMD2_ANY_LIST ("elapsed.less", std::bind(&apply_elapsed_less, std::placeholders::_2));
CMD2_ANY_LIST ("elapsed.greater", std::bind(&apply_elapsed_greater, std::placeholders::_2));
Expand Down
2 changes: 1 addition & 1 deletion src/core/download.cc
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ Download::set_priority(uint32_t p) {
p %= 4;

// Seeding torrents get half the priority of unfinished torrents.
if (!is_done())
if (!is_partially_done())
torrent::download_set_priority(m_download, p * p * 2);
else
torrent::download_set_priority(m_download, p * p);
Expand Down
6 changes: 3 additions & 3 deletions src/core/download.h
Original file line number Diff line number Diff line change
Expand Up @@ -79,8 +79,9 @@ class Download {
bool is_open() const { return m_download.info()->is_open(); }
bool is_active() const { return m_download.info()->is_active(); }
bool is_done() const { return m_download.file_list()->is_done(); }
bool is_downloading() const { return is_active() && !is_done(); }
bool is_seeding() const { return is_active() && is_done(); }
bool is_partially_done() const { return m_download.data()->is_partially_done(); }
bool is_downloading() const { return is_active() && !is_partially_done(); }
bool is_seeding() const { return is_active() && is_partially_done(); }

// FIXME: Fixed a bug in libtorrent that caused is_hash_checked to
// return true when the torrent is closed. Remove this redundant
Expand Down Expand Up @@ -129,7 +130,6 @@ class Download {

float distributed_copies() const;

// HACK: Choke group setting.
unsigned int group() const { return m_group; }
void set_group(unsigned int g) { m_group = g; }

Expand Down
11 changes: 6 additions & 5 deletions src/core/download_factory.cc
Original file line number Diff line number Diff line change
Expand Up @@ -421,6 +421,12 @@ DownloadFactory::initialize_rtorrent(Download* download, torrent::Object* rtorre
if (rtorrent->has_key_value("total_downloaded"))
download->info()->mutable_down_rate()->set_total(rtorrent->get_key_value("total_downloaded"));

if (rtorrent->has_key_value("total_skipped"))
download->info()->mutable_skip_rate()->set_total(rtorrent->get_key_value("total_skipped"));

if (rtorrent->has_key_value("size_selected"))
download->file_list()->set_selected_size_bytes(rtorrent->get_key_value("size_selected"));

if (rtorrent->has_key_value("chunks_done") && rtorrent->has_key_value("chunks_wanted"))
download->download()->set_chunks_done(rtorrent->get_key_value("chunks_done"), rtorrent->get_key_value("chunks_wanted"));

Expand All @@ -433,11 +439,6 @@ DownloadFactory::initialize_rtorrent(Download* download, torrent::Object* rtorre

rtorrent->insert_preserve_type("connection_leech", m_variables["connection_leech"]);
rtorrent->insert_preserve_type("connection_seed", m_variables["connection_seed"]);

rtorrent->insert_preserve_copy("choke_heuristics.up.leech", std::string());
rtorrent->insert_preserve_copy("choke_heuristics.up.seed", std::string());
rtorrent->insert_preserve_copy("choke_heuristics.down.leech", std::string());
rtorrent->insert_preserve_copy("choke_heuristics.down.seed", std::string());
}

}
Loading