From a811f533018d5069ae8ec4685f951825e5ef94df Mon Sep 17 00:00:00 2001 From: rakshasa Date: Sat, 25 Mar 2006 20:20:52 +0000 Subject: [PATCH] * Applied a patch from josef that cleand up the chunks seen window. * More work on rarity-first chunk selection. git-svn-id: svn://rakshasa.no/libtorrent/trunk/rtorrent@657 e378c898-3ddf-0310-93e7-cc216c733640 --- src/core/download.cc | 22 ++++++++++++++ src/core/download.h | 2 ++ src/display/window_download_chunks_seen.cc | 34 +++++++++++++++++----- 3 files changed, 50 insertions(+), 8 deletions(-) diff --git a/src/core/download.cc b/src/core/download.cc index a12091ca..1d8ee9f5 100644 --- a/src/core/download.cc +++ b/src/core/download.cc @@ -217,6 +217,28 @@ Download::priority_to_string(uint32_t p) { } } +float +Download::distributed_copies() const { + const uint8_t* avail = m_download.chunks_seen(); + const uint8_t* end = avail + m_download.chunks_total(); + + if (avail == NULL) + return 0; + + int minAvail = std::numeric_limits::max(); + int num = 0; + + for (; avail < end; ++avail) + if (*avail == minAvail) { + num++; + } else if (*avail < minAvail) { + minAvail = *avail; + num = 1; + } + + return minAvail + 1 - (float)num / m_download.chunks_total(); +} + void Download::receive_chunk_failed(__UNUSED uint32_t idx) { m_chunksFailed++; diff --git a/src/core/download.h b/src/core/download.h index 76ec7e88..60a83eba 100644 --- a/src/core/download.h +++ b/src/core/download.h @@ -95,6 +95,8 @@ public: static uint32_t string_to_priority(const std::string& name); static const char* priority_to_string(uint32_t p); + float distributed_copies() const; + private: Download(const Download&); void operator () (const Download&); diff --git a/src/display/window_download_chunks_seen.cc b/src/display/window_download_chunks_seen.cc index 84eaf034..a9b20dfc 100644 --- a/src/display/window_download_chunks_seen.cc +++ b/src/display/window_download_chunks_seen.cc @@ -36,6 +36,7 @@ #include "config.h" +#include #include #include @@ -56,28 +57,45 @@ WindowDownloadChunksSeen::redraw() { m_slotSchedule(this, (cachedTime + rak::timer::from_seconds(10)).round_seconds()); m_canvas->erase(); - if (m_canvas->get_height() < 3 || m_canvas->get_width() < 10) + if (m_canvas->get_height() < 3 || m_canvas->get_width() < 18) return; - m_canvas->print(2, 0, "Chunks seen: [C/A %i/%i]", + m_canvas->print(2, 0, "Chunks seen: [C/A/D %i/%i/%.2f]", (int)m_download->get_download().peers_complete(), - (int)m_download->get_download().peers_accounted()); + (int)m_download->get_download().peers_accounted(), + std::floor(m_download->distributed_copies() * 100.0f) / 100.0f); const uint8_t* seen = m_download->get_download().chunks_seen(); - const uint8_t* last = seen + m_download->get_download().chunks_total(); if (seen == NULL) { m_canvas->print(2, 2, "Not available."); return; } - for (int y = 1; y < m_canvas->get_height() && seen != last; ++y) { + char buffer[m_canvas->get_width()]; + char* position; + char* end = buffer + m_canvas->get_width() - 2; - for (int x = 2; x < m_canvas->get_width() && seen != last; ++x) { - m_canvas->print(x, y, "%c", rak::value_to_hexchar<0>(std::min(*seen, 0xF))); + const uint8_t* chunk = seen; + const uint8_t* last = seen + m_download->get_download().chunks_total(); - seen++; + for (int y = 1; y < m_canvas->get_height() && chunk < last; ++y) { + position = buffer + std::max(snprintf(buffer, end - buffer, "%5d", chunk - seen), 0); + + while (chunk < last) { + if ((chunk - seen) % 10 == 0) { + if (end - position < 11) + break; + + *position++ = ' '; + } + + *position++ = rak::value_to_hexchar<0>(std::min(*chunk, 0xF)); + chunk++; } + + *position = 0; + m_canvas->print(0, y, "%s", buffer); } }