Skip to content

Commit

Permalink
WIP on parallel download.
Browse files Browse the repository at this point in the history
  • Loading branch information
evoskuil committed Feb 25, 2024
1 parent 1cebb6d commit 523f928
Show file tree
Hide file tree
Showing 20 changed files with 192 additions and 67 deletions.
17 changes: 9 additions & 8 deletions include/bitcoin/node/chasers/chaser_check.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,6 @@
#define LIBBITCOIN_NODE_CHASERS_CHASER_CHECK_HPP

#include <functional>
#include <memory>
#include <unordered_map>
#include <bitcoin/network.hpp>
#include <bitcoin/node/define.hpp>
#include <bitcoin/node/chasers/chaser.hpp>
Expand All @@ -36,10 +34,9 @@ class BCN_API chaser_check
: public chaser
{
public:
typedef std::unordered_map<system::hash_digest,
system::chain::context> hashmap;
typedef std::shared_ptr<hashmap> hashmap_ptr;
typedef std::function<void(const code&, const hashmap_ptr&)> handler;
// context_map casts header_fk into context.minimum_block_version.
using map = database::context_map;
typedef std::function<void(const code&, const map&)> handler;

DELETE_COPY_MOVE(chaser_check);

Expand All @@ -49,18 +46,22 @@ class BCN_API chaser_check
virtual code start() NOEXCEPT;

virtual void get_hashes(handler&& handler) NOEXCEPT;
virtual void put_hashes(handler&& handler) NOEXCEPT;
virtual void put_hashes(const map& map,
network::result_handler&& handler) NOEXCEPT;

protected:
virtual void handle_header(height_t branch_point) NOEXCEPT;
virtual void handle_event(const code& ec, chase event_,
link value) NOEXCEPT;

virtual void do_get_hashes(const handler& handler) NOEXCEPT;
virtual void do_put_hashes(const handler& handler) NOEXCEPT;
virtual void do_put_hashes(const map& map,
const network::result_handler& handler) NOEXCEPT;

private:
void do_handle_event(const code& ec, chase event_, link value) NOEXCEPT;

map map_{};
};

} // namespace node
Expand Down
5 changes: 5 additions & 0 deletions include/bitcoin/node/full_node.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,11 @@ class BCN_API full_node
virtual void organize(const system::chain::block::cptr& block,
network::result_handler&& handler) NOEXCEPT;

/// Manage download queue.
virtual void get_hashes(chaser_check::handler&& handler) NOEXCEPT;
virtual void put_hashes(const chaser_check::map& map,
network::result_handler&& handler) NOEXCEPT;

/// Properties.
/// -----------------------------------------------------------------------

Expand Down
6 changes: 6 additions & 0 deletions include/bitcoin/node/protocols/protocol.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
#define LIBBITCOIN_NODE_PROTOCOLS_PROTOCOL_HPP

#include <bitcoin/network.hpp>
#include <bitcoin/node/chasers/chasers.hpp>
#include <bitcoin/node/configuration.hpp>
#include <bitcoin/node/define.hpp>
#include <bitcoin/node/full_node.hpp>
Expand Down Expand Up @@ -61,6 +62,11 @@ class BCN_API protocol
virtual void organize(const system::chain::block::cptr& block,
network::result_handler&& handler) NOEXCEPT;

/// Manage download queue.
virtual void get_hashes(chaser_check::handler&& handler) NOEXCEPT;
virtual void put_hashes(const chaser_check::map& map,
network::result_handler&& handler) NOEXCEPT;

/// Configuration settings for all libraries.
const configuration& config() const NOEXCEPT;

Expand Down
14 changes: 6 additions & 8 deletions include/bitcoin/node/protocols/protocol_block_in_31800.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -58,12 +58,7 @@ class BCN_API protocol_block_in_31800
void start() NOEXCEPT override;
void stopping(const code& ec) NOEXCEPT override;

/// Manage download queue.
virtual void get_hashes(chaser_check::handler&& handler) NOEXCEPT;
virtual void put_hashes(chaser_check::handler&& handler) NOEXCEPT;

protected:

/// Recieved incoming block message.
virtual bool handle_receive_block(const code& ec,
const network::messages::block::cptr& message) NOEXCEPT;
Expand All @@ -77,20 +72,23 @@ class BCN_API protocol_block_in_31800
/// Manage download queue.
virtual void handle_put_hashes(const code& ec) NOEXCEPT;
virtual void handle_get_hashes(const code& ec,
const chaser_check::hashmap_ptr& hashes) NOEXCEPT;
const chaser_check::map& map) NOEXCEPT;

private:
network::messages::get_data create_get_data() const NOEXCEPT;
network::messages::get_data create_get_data(
const chaser_check::map& map) const NOEXCEPT;

void do_handle_performance(const code& ec) NOEXCEPT;
void do_handle_get_hashes(const code& ec,
const chaser_check::map& map) NOEXCEPT;

// These are thread safe.
const bool report_performance_;
const network::messages::inventory::type_id block_type_;

// These are protected by strand.
uint64_t bytes_{ zero };
chaser_check::hashmap_ptr hashes_{};
chaser_check::map map_{};
network::steady_clock::time_point start_{};
network::deadline::ptr performance_timer_;
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@ class BCN_API protocol_header_in_31800
const system::chain::header::cptr& header_ptr) NOEXCEPT;

private:
network::messages::get_headers create_get_headers() NOEXCEPT;
network::messages::get_headers create_get_headers() const NOEXCEPT;
network::messages::get_headers create_get_headers(
const system::hash_digest& last) const NOEXCEPT;
network::messages::get_headers create_get_headers(
Expand Down
6 changes: 6 additions & 0 deletions include/bitcoin/node/sessions/session.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
#define LIBBITCOIN_NODE_SESSIONS_SESSION_HPP

#include <bitcoin/network.hpp>
#include <bitcoin/node/chasers/chasers.hpp>
#include <bitcoin/node/define.hpp>
#include <bitcoin/node/full_node.hpp>

Expand All @@ -44,6 +45,11 @@ class BCN_API session
virtual void organize(const system::chain::block::cptr& block,
network::result_handler&& handler) NOEXCEPT;

/// Manage download queue.
virtual void get_hashes(chaser_check::handler&& handler) NOEXCEPT;
virtual void put_hashes(const chaser_check::map& map,
network::result_handler&& handler) NOEXCEPT;

/// Configuration settings for all libraries.
const configuration& config() const NOEXCEPT;

Expand Down
5 changes: 3 additions & 2 deletions src/chasers/chaser_block.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -54,8 +54,9 @@ code chaser_block::start() NOEXCEPT
state_ = archive().get_candidate_chain_state(config().bitcoin);
BC_ASSERT_MSG(state_, "Store not initialized.");

return subscribe(std::bind(&chaser_block::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_block::handle_event,
this, _1, _2, _3));
}

// protected
Expand Down
5 changes: 3 additions & 2 deletions src/chasers/chaser_candidate.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,9 @@ chaser_candidate::~chaser_candidate() NOEXCEPT
code chaser_candidate::start() NOEXCEPT
{
BC_ASSERT_MSG(node_stranded(), "chaser_check");
return subscribe(std::bind(&chaser_candidate::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_candidate::handle_event,
this, _1, _2, _3));
}

void chaser_candidate::handle_event(const code& ec, chase event_,
Expand Down
30 changes: 20 additions & 10 deletions src/chasers/chaser_check.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -55,11 +55,12 @@ code chaser_check::start() NOEXCEPT
{
BC_ASSERT_MSG(node_stranded(), "chaser_check");

// TODO: get_all_unassociated_above(0)
BC_ASSERT_MSG(true, "Store not initialized.");
// Initialize from genesis block.
handle_header(zero);

return subscribe(std::bind(&chaser_check::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_check::handle_event,
this, _1, _2, _3));
}

// protected
Expand Down Expand Up @@ -91,11 +92,12 @@ void chaser_check::get_hashes(handler&& handler) NOEXCEPT
this, std::move(handler)));
}

void chaser_check::put_hashes(handler&& handler) NOEXCEPT
void chaser_check::put_hashes(const chaser_check::map& map,
network::result_handler&& handler) NOEXCEPT
{
boost::asio::post(strand(),
std::bind(&chaser_check::do_put_hashes,
this, std::move(handler)));
this, map, std::move(handler)));
}

// protected
Expand All @@ -106,17 +108,25 @@ void chaser_check::do_get_hashes(const handler&) NOEXCEPT
BC_ASSERT_MSG(stranded(), "chaser_check");
}

void chaser_check::do_put_hashes(const handler&) NOEXCEPT
void chaser_check::do_put_hashes(const chaser_check::map&,
const network::result_handler&) NOEXCEPT
{
BC_ASSERT_MSG(stranded(), "chaser_check");
}

// New branch organized, queue up candidate downloads from branch point.
void chaser_check::handle_header(height_t) NOEXCEPT
void chaser_check::handle_header(height_t branch_point) NOEXCEPT
{
BC_ASSERT_MSG(stranded(), "chaser_check");

// TODO: get_all_unassociated_above(branch_point)
// Map and peer maps may have newly stale blocks.
// All stale branches can just be allowed to complete.
// The connect chaser will verify proper advancement.

// get_all_unassociated_above(branch_point) and add to map.
const auto& query = archive();
const auto top = query.get_top_candidate();
const auto last = query.get_last_associated_from(branch_point);
map_.merge(query.get_all_unassociated_above(last));
}

BC_POP_WARNING()
Expand Down
5 changes: 3 additions & 2 deletions src/chasers/chaser_confirm.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,8 +45,9 @@ chaser_confirm::~chaser_confirm() NOEXCEPT
code chaser_confirm::start() NOEXCEPT
{
BC_ASSERT_MSG(node_stranded(), "chaser_confirm");
return subscribe(std::bind(&chaser_confirm::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_confirm::handle_event,
this, _1, _2, _3));
}

void chaser_confirm::handle_event(const code& ec, chase event_,
Expand Down
5 changes: 3 additions & 2 deletions src/chasers/chaser_connect.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,8 +45,9 @@ chaser_connect::~chaser_connect() NOEXCEPT
code chaser_connect::start() NOEXCEPT
{
BC_ASSERT_MSG(node_stranded(), "chaser_connect");
return subscribe(std::bind(&chaser_connect::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_connect::handle_event,
this, _1, _2, _3));
}

void chaser_connect::handle_event(const code& ec, chase event_,
Expand Down
5 changes: 3 additions & 2 deletions src/chasers/chaser_header.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -69,8 +69,9 @@ code chaser_header::start() NOEXCEPT
state_ = archive().get_candidate_chain_state(config().bitcoin);
BC_ASSERT_MSG(state_, "Store not initialized.");

return subscribe(std::bind(&chaser_header::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_header::handle_event,
this, _1, _2, _3));
}

// protected
Expand Down
5 changes: 3 additions & 2 deletions src/chasers/chaser_transaction.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -46,8 +46,9 @@ chaser_transaction::~chaser_transaction() NOEXCEPT
code chaser_transaction::start() NOEXCEPT
{
BC_ASSERT_MSG(node_stranded(), "chaser_transaction");
return subscribe(std::bind(&chaser_transaction::handle_event,
this, _1, _2, _3));
return subscribe(
std::bind(&chaser_transaction::handle_event,
this, _1, _2, _3));
}

void chaser_transaction::handle_event(const code& ec, chase event_,
Expand Down
11 changes: 11 additions & 0 deletions src/full_node.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -143,6 +143,17 @@ void full_node::organize(const system::chain::block::cptr& block,
chaser_block_.organize(block, std::move(handler));
}

void full_node::get_hashes(chaser_check::handler&& handler) NOEXCEPT
{
chaser_check_.get_hashes(std::move(handler));
}

void full_node::put_hashes(const chaser_check::map& map,
network::result_handler&& handler) NOEXCEPT
{
chaser_check_.put_hashes(map, std::move(handler));
}

// Properties.
// ----------------------------------------------------------------------------

Expand Down
12 changes: 12 additions & 0 deletions src/protocols/protocol.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
#include <utility>
#include <bitcoin/network.hpp>
#include <bitcoin/node/configuration.hpp>
#include <bitcoin/node/chasers/chasers.hpp>
#include <bitcoin/node/define.hpp>
#include <bitcoin/node/full_node.hpp>
#include <bitcoin/node/sessions/sessions.hpp>
Expand Down Expand Up @@ -52,6 +53,17 @@ void protocol::organize(const system::chain::block::cptr& block,
session_.organize(block, std::move(handler));
}

void protocol::get_hashes(chaser_check::handler&& handler) NOEXCEPT
{
session_.get_hashes(std::move(handler));
}

void protocol::put_hashes(const chaser_check::map& map,
network::result_handler&& handler) NOEXCEPT
{
session_.put_hashes(map, std::move(handler));
}

const configuration& protocol::config() const NOEXCEPT
{
return session_.config();
Expand Down
8 changes: 6 additions & 2 deletions src/protocols/protocol_block_in.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ bool protocol_block_in::handle_receive_inventory(const code& ec,
if (getter.items.empty())
{
// If the original request was maximal, we assume there are more.
// The inv response to get_blocks is limited to max_get_blocks.
if (message->items.size() == max_get_blocks)
{
LOGP("Get inventory [" << authority() << "] (empty maximal).");
Expand Down Expand Up @@ -189,6 +190,8 @@ bool protocol_block_in::handle_receive_block(const code& ec,
// The distinction is ultimately arbitrary, but this signals initial currency.
void protocol_block_in::complete() NOEXCEPT
{
BC_ASSERT_MSG(stranded(), "protocol_block_in");

LOGN("Blocks from [" << authority() << "] complete at ("
<< top_.height() << ").");
}
Expand Down Expand Up @@ -224,8 +227,9 @@ get_blocks protocol_block_in::create_get_inventory() const NOEXCEPT
// All strong block branches are archived, so this will reflect latest.
// This will bypass all blocks with candidate headers, resulting in block
// orphans if headers-first is run followed by a restart and blocks-first.
return create_get_inventory(archive().get_candidate_hashes(
get_blocks::heights(archive().get_top_candidate())));
const auto& query = archive();
return create_get_inventory(query.get_candidate_hashes(get_blocks::heights(
query.get_top_candidate())));
}

get_blocks protocol_block_in::create_get_inventory(
Expand Down
Loading

0 comments on commit 523f928

Please sign in to comment.