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

Replace active_finalizer_policy_digest with last_pending_finalizer_policy_digest #132

Merged
merged 6 commits into from
May 14, 2024
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
34 changes: 29 additions & 5 deletions libraries/chain/block_header_state.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -43,13 +43,11 @@ digest_type block_header_state::compute_base_digest() const {
}

digest_type block_header_state::compute_finality_digest() const {
assert(active_finalizer_policy);
auto active_finalizer_policy_digest = fc::sha256::hash(*active_finalizer_policy);
auto base_digest = compute_base_digest();

std::pair<const digest_type&, const digest_type&> active_and_base{ active_finalizer_policy_digest, base_digest };
std::pair<const digest_type&, const digest_type&> active_and_base{ last_pending_finalizer_policy_digest, base_digest };
auto afp_base_digest = fc::sha256::hash(active_and_base);

assert(active_finalizer_policy);
finality_digest_data_v1 finality_digest_data {
.active_finalizer_policy_generation = active_finalizer_policy->generation,
.finality_tree_digest = finality_mroot(),
Expand All @@ -67,7 +65,7 @@ const vector<digest_type>& block_header_state::get_new_protocol_feature_activati
return detail::get_new_protocol_feature_activations(header_exts);
}

// The last proposed finalizer policy if none proposed or pending is the active finalizer policy
// The last proposed finalizer policy if none proposed or pending then the active finalizer policy
const finalizer_policy& block_header_state::get_last_proposed_finalizer_policy() const {
if (!finalizer_policies.empty()) {
for (auto ritr = finalizer_policies.rbegin(); ritr != finalizer_policies.rend(); ++ritr) {
Expand All @@ -79,6 +77,30 @@ const finalizer_policy& block_header_state::get_last_proposed_finalizer_policy()
return *active_finalizer_policy;
}

// The last pending finalizer policy if none pending then the active finalizer policy
// Used to populate last_pending_finalizer_policy_digest which is expected to be the highest generation pending
const finalizer_policy& block_header_state::get_last_pending_finalizer_policy() const {
if (!finalizer_policies.empty()) {
[[maybe_unused]] auto highest_pending_generation = [this]() {
linh2931 marked this conversation as resolved.
Show resolved Hide resolved
finalizer_policy_ptr highest;
for (auto ritr = finalizer_policies.rbegin(); ritr != finalizer_policies.rend(); ++ritr) {
if (ritr->second.state == finalizer_policy_tracker::state_t::pending) {
if (!highest || highest->generation < ritr->second.policy->generation)
highest = ritr->second.policy;
}
}
return highest;
};
for (auto ritr = finalizer_policies.rbegin(); ritr != finalizer_policies.rend(); ++ritr) {
if (ritr->second.state == finalizer_policy_tracker::state_t::pending) {
assert(highest_pending_generation() == ritr->second.policy);
return *ritr->second.policy;
}
}
}
return *active_finalizer_policy;
}

// The last proposed proposer policy, if none proposed then the active proposer policy
const proposer_policy& block_header_state::get_last_proposed_proposer_policy() const {
if (proposer_policies.empty()) {
Expand Down Expand Up @@ -183,6 +205,8 @@ void finish_next(const block_header_state& prev,
}
}

next_header_state.last_pending_finalizer_policy_digest = fc::sha256::hash(next_header_state.get_last_pending_finalizer_policy());

if (if_ext.new_finalizer_policy_diff) {
finalizer_policy new_finalizer_policy = prev.get_last_proposed_finalizer_policy().apply_diff(*if_ext.new_finalizer_policy_diff);

Expand Down
1 change: 1 addition & 0 deletions libraries/chain/block_state.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ block_state_ptr block_state::create_if_genesis_block(const block_state_legacy& b
instant_finality_extension if_ext = bsp.block->extract_header_extension<instant_finality_extension>();
assert(if_ext.new_finalizer_policy_diff); // required by transition mechanism
result.active_finalizer_policy = std::make_shared<finalizer_policy>(finalizer_policy{}.apply_diff(std::move(*if_ext.new_finalizer_policy_diff)));
result.last_pending_finalizer_policy_digest = fc::sha256::hash(*result.active_finalizer_policy);
result.active_proposer_policy = std::make_shared<proposer_policy>();
result.active_proposer_policy->active_time = bsp.timestamp();
result.active_proposer_policy->proposer_schedule = bsp.active_schedule;
Expand Down
7 changes: 6 additions & 1 deletion libraries/chain/include/eosio/chain/block_header_state.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,10 @@ struct block_header_state {
// It matches the finalizer policy generation most recently included in this block's `if_extension` or its ancestors
uint32_t finalizer_policy_generation{1};

// digest of the finalizer policy (which includes the generation number in it) with the greatest generation number
// in the history of the blockchain so far that is not in proposed state (so either pending or active state)
digest_type last_pending_finalizer_policy_digest;

// ------ data members caching information available elsewhere ----------------------
header_extension_multimap header_exts; // redundant with the data stored in header

Expand Down Expand Up @@ -131,6 +135,7 @@ struct block_header_state {
const producer_authority& get_scheduled_producer(block_timestamp_type t) const;

const finalizer_policy& get_last_proposed_finalizer_policy() const;
const finalizer_policy& get_last_pending_finalizer_policy() const;
const proposer_policy& get_last_proposed_proposer_policy() const;
};

Expand All @@ -145,6 +150,6 @@ FC_REFLECT( eosio::chain::finalizer_policy_tracker, (state)(policy))
FC_REFLECT( eosio::chain::block_header_state, (block_id)(header)
(activated_protocol_features)(core)(active_finalizer_policy)
(active_proposer_policy)(proposer_policies)(finalizer_policies)
(finalizer_policy_generation)(header_exts))
(finalizer_policy_generation)(last_pending_finalizer_policy_digest)(header_exts))

FC_REFLECT( eosio::chain::finality_digest_data_v1, (major_version)(minor_version)(active_finalizer_policy_generation)(finality_tree_digest)(active_finalizer_policy_and_base_digest) )
12 changes: 6 additions & 6 deletions unittests/svnn_ibc_tests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -108,8 +108,8 @@ BOOST_AUTO_TEST_SUITE(svnn_ibc)

BOOST_CHECK_EQUAL(active_finalizer_policy.generation, 1u);

// compute the digest of the finalizer policy
auto active_finalizer_policy_digest = fc::sha256::hash(active_finalizer_policy);
// compute the digest of the last_pending_finalizer_policy_digest which is active at this point
auto last_pending_finalizer_policy_digest = fc::sha256::hash(active_finalizer_policy);

auto genesis_block_fd = cluster.node0.control->head_finality_data();

Expand All @@ -118,7 +118,7 @@ BOOST_AUTO_TEST_SUITE(svnn_ibc)

// compute IF finality leaf
auto genesis_base_digest = genesis_block_fd.value().base_digest;
auto genesis_afp_base_digest = hash_pair(active_finalizer_policy_digest, genesis_base_digest);
auto genesis_afp_base_digest = hash_pair(last_pending_finalizer_policy_digest, genesis_base_digest);

auto genesis_block_finality_digest = fc::sha256::hash(eosio::chain::finality_digest_data_v1{
.active_finalizer_policy_generation = active_finalizer_policy.generation,
Expand Down Expand Up @@ -171,7 +171,7 @@ BOOST_AUTO_TEST_SUITE(svnn_ibc)
auto block_2_action_mroot = block_2_fd.value().action_mroot;
auto block_2_base_digest = block_2_fd.value().base_digest;
auto block_2_finality_digest = cluster.node0.control->get_strong_digest_by_id(block_2->calculate_id());
auto block_2_afp_base_digest = hash_pair(active_finalizer_policy_digest, block_2_base_digest);
auto block_2_afp_base_digest = hash_pair(last_pending_finalizer_policy_digest, block_2_base_digest);
auto block_2_leaf = fc::sha256::hash(valid_t::finality_leaf_node_t{
.block_num = block_2->block_num(),
.finality_digest = block_2_finality_digest,
Expand All @@ -196,7 +196,7 @@ BOOST_AUTO_TEST_SUITE(svnn_ibc)
cluster.process_votes(1, cluster.num_needed_for_quorum);
auto block_4_fd = cluster.node0.control->head_finality_data();
auto block_4_base_digest = block_4_fd.value().base_digest;
auto block_4_afp_base_digest = hash_pair(active_finalizer_policy_digest, block_4_base_digest);
auto block_4_afp_base_digest = hash_pair(last_pending_finalizer_policy_digest, block_4_base_digest);

auto block_4_finality_root = block_4->action_mroot;
qc_data_t qc_b_4 = extract_qc_data(block_4);
Expand All @@ -209,7 +209,7 @@ BOOST_AUTO_TEST_SUITE(svnn_ibc)
cluster.process_votes(1, cluster.num_needed_for_quorum);
auto block_5_fd = cluster.node0.control->head_finality_data();
auto block_5_base_digest = block_5_fd.value().base_digest;
auto block_5_afp_base_digest = hash_pair(active_finalizer_policy_digest, block_5_base_digest);
auto block_5_afp_base_digest = hash_pair(last_pending_finalizer_policy_digest, block_5_base_digest);
auto block_5_finality_root = block_5->action_mroot;

// retrieve the QC over block_4 that is contained in block_5
Expand Down
Loading