diff --git a/libraries/chain/db_maint.cpp b/libraries/chain/db_maint.cpp index c7c978c4..c6af081d 100644 --- a/libraries/chain/db_maint.cpp +++ b/libraries/chain/db_maint.cpp @@ -178,36 +178,49 @@ void database::update_worker_votes() void database::pay_sons() { - auto get_weight = []( uint64_t total_votes ) { - int8_t bits_to_drop = std::max(int(boost::multiprecision::detail::find_msb(total_votes)) - 15, 0); - uint16_t weight = std::max((total_votes >> bits_to_drop), uint64_t(1) ); - return weight; - }; time_point_sec now = head_block_time(); const dynamic_global_property_object& dpo = get_dynamic_global_properties(); // Current requirement is that we have to pay every 24 hours, so the following check if( dpo.son_budget.value > 0 && ((now - dpo.last_son_payout_time) >= fc::seconds(get_global_properties().parameters.son_pay_time()))) { + auto sons = sort_votable_objects(get_global_properties().parameters.maximum_son_count()); + // After NEXT HF + uint64_t total_votes = 0; + for( const son_object& son : sons ) + { + total_votes += _vote_tally_buffer[son.vote_id]; + } + int8_t bits_to_drop = std::max(int(boost::multiprecision::detail::find_msb(total_votes)) - 15, 0); + auto get_weight = [&bits_to_drop]( uint64_t son_votes ) { + uint16_t weight = std::max((son_votes >> bits_to_drop), uint64_t(1) ); + return weight; + }; + // Before NEXT HF + auto get_weight_next_hf = []( uint64_t son_votes ) { + int8_t bits_to_drop = std::max(int(boost::multiprecision::detail::find_msb(son_votes)) - 15, 0); + uint16_t weight = std::max((son_votes >> bits_to_drop), uint64_t(1) ); + return weight; + }; uint64_t weighted_total_txs_signed = 0; share_type son_budget = dpo.son_budget; - get_index_type().inspect_all_objects([this, &weighted_total_txs_signed, &get_weight](const object& o) { + get_index_type().inspect_all_objects([this, &weighted_total_txs_signed, &get_weight, &now, &get_weight_next_hf](const object& o) { const son_statistics_object& s = static_cast(o); const auto& idx = get_index_type().indices().get(); auto son_obj = idx.find( s.owner ); auto son_weight = get_weight(_vote_tally_buffer[son_obj->vote_id]); + if( now < HARDFORK_NEXT_TIME ) { + son_weight = get_weight_next_hf(_vote_tally_buffer[son_obj->vote_id]); + } weighted_total_txs_signed += (s.txs_signed * son_weight); }); - // Now pay off each SON proportional to the number of transactions signed. get_index_type().inspect_all_objects([this, &weighted_total_txs_signed, &dpo, &son_budget, &get_weight](const object& o) { const son_statistics_object& s = static_cast(o); if(s.txs_signed > 0){ - auto son_params = get_global_properties().parameters; const auto& idx = get_index_type().indices().get(); auto son_obj = idx.find( s.owner ); auto son_weight = get_weight(_vote_tally_buffer[son_obj->vote_id]); share_type pay = (s.txs_signed * son_weight * son_budget.value)/weighted_total_txs_signed; - modify( *son_obj, [&]( son_object& _son_obj) { _son_obj.pay_son_fee(pay, *this);