Bitcoin ABC 0.33.11
P2P Digital Currency
stakecontendercache.h
Go to the documentation of this file.
1// Copyright (c) 2024 The Bitcoin developers
2// Distributed under the MIT software license, see the accompanying
3// file COPYING or http://www.opensource.org/licenses/mit-license.php.
4
5#ifndef BITCOIN_AVALANCHE_STAKECONTENDERCACHE_H
6#define BITCOIN_AVALANCHE_STAKECONTENDERCACHE_H
7
8#include <avalanche/proof.h>
11#include <script/script.h>
12#include <util/hasher.h>
13
14#include <boost/multi_index/hashed_index.hpp>
15#include <boost/multi_index/member.hpp>
16#include <boost/multi_index/ordered_index.hpp>
17#include <boost/multi_index_container.hpp>
18
19#include <cstdint>
20#include <functional>
21#include <optional>
22#include <utility>
23#include <vector>
24
25class CBlockIndex;
26
27namespace avalanche {
28
29enum StakeContenderStatus : uint8_t {
31 // Set according to avalanche acceptance
32 ACCEPTED = (1 << 0),
33 // If set, this contender should be in the stake winner set
34 IN_WINNER_SET = (1 << 1),
35};
36
42 uint8_t status;
43 // Cache payout script and proof score because the peer manager does not
44 // track past-valid proofs.
46 uint32_t score;
47
48 StakeContenderCacheEntry(const BlockHash &_prevblockhash, int _blockheight,
49 int64_t _prevblocktime, const ProofId &_proofid,
50 uint8_t _status,
51 const CScript &_payoutScriptPubkey,
52 uint32_t _score)
53 : prevblockhash(_prevblockhash), blockheight(_blockheight),
54 prevblocktime(_prevblocktime), proofid(_proofid), status(_status),
55 payoutScriptPubkey(_payoutScriptPubkey), score(_score) {}
56
57 double computeRewardRank() const {
59 }
62 }
64 bool isInWinnerSet() const {
66 }
67};
68
72 std::vector<CScript> payoutScripts;
73
74 ManualWinners(const BlockHash &_prevblockhash, int _blockheight,
75 const std::vector<CScript> &_payoutScripts)
76 : prevblockhash(_prevblockhash), blockheight(_blockheight),
77 payoutScripts(_payoutScripts) {}
78};
79
83 return entry.getStakeContenderId();
84 }
85};
86
87struct by_stakecontenderid;
88struct by_prevblockhash;
89struct by_blockheight;
90
91namespace bmi = boost::multi_index;
92
101};
102
105
106 using ContenderSet = boost::multi_index_container<
108 bmi::indexed_by<
109 // index by stake contender id
110 bmi::hashed_unique<bmi::tag<by_stakecontenderid>,
112 // index by prevblockhash
113 bmi::hashed_non_unique<
114 bmi::tag<by_prevblockhash>,
118 // index by block height
119 bmi::ordered_non_unique<
120 bmi::tag<by_blockheight>,
121 bmi::member<StakeContenderCacheEntry, int,
123
125
126 using ManualWinnersSet = boost::multi_index_container<
128 bmi::indexed_by<
129 // index by prevblockhash
130 bmi::hashed_unique<bmi::tag<by_prevblockhash>,
131 bmi::member<ManualWinners, BlockHash,
134 // index by block height
135 bmi::ordered_unique<
136 bmi::tag<by_blockheight>,
137 bmi::member<ManualWinners, int, &ManualWinners::blockheight>>>>;
138
140
141public:
143
144 void cleanup(const int requestedMinHeight);
145
149 bool isEmpty() const {
150 return (contenders.size() + manualWinners.size()) == 0;
151 }
152
156 bool add(const CBlockIndex *pindex, const ProofRef &proof,
157 uint8_t status = StakeContenderStatus::UNKNOWN);
158
162 void promoteToBlock(
163 const CBlockIndex *activeTip,
164 std::function<bool(const ProofId &proofid)> const &shouldPromote);
165
170 bool setWinners(const CBlockIndex *pindex,
171 const std::vector<CScript> &payoutScripts);
172
176 bool accept(const StakeContenderId &contenderId);
177 bool finalize(const StakeContenderId &contenderId);
178 bool reject(const StakeContenderId &contenderId);
179
180 std::optional<StakeContenderCacheInfo>
181 getContenderInfo(const StakeContenderId &contenderId) const;
182
188 int getVoteStatus(const StakeContenderId &contenderId,
189 BlockHash &prevblockhashout) const;
190
197 const BlockHash &prevblockhash, size_t maxPollable,
198 std::vector<StakeContenderId> &pollableContenders) const;
199
200 bool getWinners(const BlockHash &prevblockhash,
201 std::vector<std::pair<ProofId, CScript>> &winners) const;
202};
203
204} // namespace avalanche
205
206#endif // BITCOIN_AVALANCHE_STAKECONTENDERCACHE_H
The block chain is a tree shaped structure starting with the genesis block at the root,...
Definition: blockindex.h:25
Serialized script, used inside transaction inputs and outputs.
Definition: script.h:432
bool getWinners(const BlockHash &prevblockhash, std::vector< std::pair< ProofId, CScript > > &winners) const
bool accept(const StakeContenderId &contenderId)
Helpers to set avalanche state of a contender.
void cleanup(const int requestedMinHeight)
size_t getPollableContenders(const BlockHash &prevblockhash, size_t maxPollable, std::vector< StakeContenderId > &pollableContenders) const
Get the best ranking contenders, accepted contenders ranking first.
bool reject(const StakeContenderId &contenderId)
bool setWinners(const CBlockIndex *pindex, const std::vector< CScript > &payoutScripts)
Set proof(s) that should be treated as winners (already finalized).
bool add(const CBlockIndex *pindex, const ProofRef &proof, uint8_t status=StakeContenderStatus::UNKNOWN)
Add a proof to consider in staking rewards pre-consensus.
std::optional< StakeContenderCacheInfo > getContenderInfo(const StakeContenderId &contenderId) const
void promoteToBlock(const CBlockIndex *activeTip, std::function< bool(const ProofId &proofid)> const &shouldPromote)
Promote cache entries to a the active chain tip.
boost::multi_index_container< StakeContenderCacheEntry, bmi::indexed_by< bmi::hashed_unique< bmi::tag< by_stakecontenderid >, stakecontenderid_index, SaltedUint256Hasher >, bmi::hashed_non_unique< bmi::tag< by_prevblockhash >, bmi::member< StakeContenderCacheEntry, BlockHash, &StakeContenderCacheEntry::prevblockhash >, SaltedUint256Hasher >, bmi::ordered_non_unique< bmi::tag< by_blockheight >, bmi::member< StakeContenderCacheEntry, int, &StakeContenderCacheEntry::blockheight > > > > ContenderSet
int getVoteStatus(const StakeContenderId &contenderId, BlockHash &prevblockhashout) const
Get contender acceptance state for avalanche voting.
boost::multi_index_container< ManualWinners, bmi::indexed_by< bmi::hashed_unique< bmi::tag< by_prevblockhash >, bmi::member< ManualWinners, BlockHash, &ManualWinners::prevblockhash >, SaltedUint256Hasher >, bmi::ordered_unique< bmi::tag< by_blockheight >, bmi::member< ManualWinners, int, &ManualWinners::blockheight > > > > ManualWinnersSet
bool finalize(const StakeContenderId &contenderId)
A BlockHash is a unqiue identifier for a block.
Definition: blockhash.h:13
ManualWinners(const BlockHash &_prevblockhash, int _blockheight, const std::vector< CScript > &_payoutScripts)
std::vector< CScript > payoutScripts
bool isAccepted() const
CScript payoutScriptPubkey
BlockHash prevblockhash
bool isInWinnerSet() const
int64_t prevblocktime
uint32_t score
uint8_t status
ProofId proofid
int blockheight
double computeRewardRank() const
StakeContenderCacheEntry(const BlockHash &_prevblockhash, int _blockheight, int64_t _prevblocktime, const ProofId &_proofid, uint8_t _status, const CScript &_payoutScriptPubkey, uint32_t _score)
StakeContenderId getStakeContenderId() const
Cache to track stake contenders for recent blocks.
StakeContenderIds are unique for each block to ensure that the peer polling for their acceptance has ...
double ComputeProofRewardRank(uint32_t proofScore) const
To make sure the selection is properly weighted according to the proof score, we normalize the conten...
result_type operator()(const StakeContenderCacheEntry &entry) const