Bitcoin ABC  0.26.3
P2P Digital Currency
processor.h
Go to the documentation of this file.
1 // Copyright (c) 2018-2019 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_PROCESSOR_H
6 #define BITCOIN_AVALANCHE_PROCESSOR_H
7 
8 #include <avalanche/config.h>
9 #include <avalanche/node.h>
11 #include <avalanche/protocol.h>
13 #include <eventloop.h>
14 #include <interfaces/chain.h>
15 #include <interfaces/handler.h>
16 #include <key.h>
17 #include <net.h>
18 #include <rwcollection.h>
19 
20 #include <boost/multi_index/composite_key.hpp>
21 #include <boost/multi_index/hashed_index.hpp>
22 #include <boost/multi_index/member.hpp>
23 #include <boost/multi_index/ordered_index.hpp>
24 #include <boost/multi_index_container.hpp>
25 
26 #include <atomic>
27 #include <chrono>
28 #include <cstdint>
29 #include <memory>
30 #include <vector>
31 
32 class ArgsManager;
33 class CBlockIndex;
34 class CConnman;
35 class CNode;
36 class CScheduler;
37 class Config;
38 class PeerManager;
39 struct bilingual_str;
40 
44 static constexpr size_t AVALANCHE_MAX_ELEMENT_POLL = 16;
45 
49 static constexpr std::chrono::milliseconds AVALANCHE_DEFAULT_QUERY_TIMEOUT{
50  10000};
51 
52 namespace avalanche {
53 
54 class Delegation;
55 class PeerManager;
56 class Proof;
57 struct VoteRecord;
58 
59 enum struct VoteStatus : uint8_t {
60  Invalid,
61  Rejected,
62  Accepted,
63  Finalized,
64  Stale,
65 };
66 
67 template <typename VoteItem> class VoteItemUpdate {
68  VoteItem item;
70 
71 public:
72  VoteItemUpdate(const VoteItem itemIn, VoteStatus statusIn)
73  : item(std::move(itemIn)), status(statusIn) {}
74 
75  const VoteStatus &getStatus() const { return status; }
76 
77  VoteItem getVoteItem() { return item; }
78  const VoteItem getVoteItem() const { return item; }
79 };
80 
83 
84 using BlockVoteMap =
85  std::map<const CBlockIndex *, VoteRecord, CBlockIndexWorkComparator>;
86 using ProofVoteMap =
87  std::map<const ProofRef, VoteRecord, ProofComparatorByScore>;
88 
89 struct query_timeout {};
90 
91 namespace {
92  struct AvalancheTest;
93 }
94 
95 // FIXME Implement a proper notification handler for node disconnection instead
96 // of implementing the whole NetEventsInterface for a single interesting event.
97 class Processor final : public NetEventsInterface {
101 
106 
111 
115  std::atomic<uint64_t> round;
116 
121  std::unique_ptr<PeerManager> peerManager GUARDED_BY(cs_peerManager);
122 
123  struct Query {
125  uint64_t round;
127 
134  mutable std::vector<CInv> invs;
135  };
136 
137  using QuerySet = boost::multi_index_container<
138  Query,
139  boost::multi_index::indexed_by<
140  // index by nodeid/round
141  boost::multi_index::hashed_unique<boost::multi_index::composite_key<
142  Query,
143  boost::multi_index::member<Query, NodeId, &Query::nodeid>,
144  boost::multi_index::member<Query, uint64_t, &Query::round>>>,
145  // sorted by timeout
146  boost::multi_index::ordered_non_unique<
147  boost::multi_index::tag<query_timeout>,
148  boost::multi_index::member<Query, TimePoint,
149  &Query::timeout>>>>;
150 
152 
154  struct PeerData;
155  std::unique_ptr<PeerData> peerData;
157 
160 
164  uint32_t minQuorumScore;
166  std::atomic<bool> quorumIsEstablished{false};
168  std::atomic<int64_t> avaproofsNodeCounter{0};
169 
171  const uint32_t staleVoteThreshold;
172  const uint32_t staleVoteFactor;
173 
175  class NotificationsHandler;
176  std::unique_ptr<interfaces::Handler> chainNotificationsHandler;
177 
179  CBlockIndex *finalizationTip GUARDED_BY(cs_finalizationTip){nullptr};
180 
183  std::unique_ptr<PeerData> peerDataIn, CKey sessionKeyIn,
184  uint32_t minQuorumTotalScoreIn,
185  double minQuorumConnectedScoreRatioIn,
186  int64_t minAvaproofsNodeCountIn, uint32_t staleVoteThresholdIn,
187  uint32_t staleVoteFactorIn, Amount stakeUtxoDustThresholdIn);
188 
189 public:
190  ~Processor();
191 
192  static std::unique_ptr<Processor>
193  MakeProcessor(const ArgsManager &argsman, interfaces::Chain &chain,
195  CScheduler &scheduler, bilingual_str &error);
196 
197  bool addBlockToReconcile(const CBlockIndex *pindex);
198  bool addProofToReconcile(const ProofRef &proof);
199  bool isAccepted(const CBlockIndex *pindex) const;
200  bool isAccepted(const ProofRef &proof) const;
201  int getConfidence(const CBlockIndex *pindex) const;
202  int getConfidence(const ProofRef &proof) const;
203 
204  // TODO: Refactor the API to remove the dependency on avalanche/protocol.h
205  void sendResponse(CNode *pfrom, Response response) const;
206  bool registerVotes(NodeId nodeid, const Response &response,
207  std::vector<BlockUpdate> &blockUpdates,
208  std::vector<ProofUpdate> &proofUpdates, int &banscore,
209  std::string &error);
210 
211  template <typename Callable> auto withPeerManager(Callable &&func) const {
213  return func(*peerManager);
214  }
215 
216  CPubKey getSessionPubKey() const;
217  bool sendHello(CNode *pfrom) const;
218 
219  ProofRef getLocalProof() const;
220 
221  /*
222  * Return whether the avalanche service flag should be set.
223  */
225 
226  bool startEventLoop(CScheduler &scheduler);
227  bool stopEventLoop();
228 
230  int64_t getAvaproofsNodeCounter() const {
231  return avaproofsNodeCounter.load();
232  }
234 
235  // Implement NetEventInterface. Only FinalizeNode is of interest.
236  void InitializeNode(const ::Config &config, CNode *pnode) override {}
237  bool ProcessMessages(const ::Config &config, CNode *pnode,
238  std::atomic<bool> &interrupt) override {
239  return false;
240  }
241  bool SendMessages(const ::Config &config, CNode *pnode) override {
242  return false;
243  }
244 
246  void FinalizeNode(const ::Config &config, const CNode &node) override
248 
249 private:
250  void runEventLoop();
251  void clearTimedoutRequests();
252  std::vector<CInv> getInvsForNextPoll(bool forPoll = true);
253 
254  bool isWorthPolling(const CBlockIndex *pindex)
256  bool isWorthPolling(const ProofRef &proof) const
258 
259  friend struct ::avalanche::AvalancheTest;
260 };
261 
262 } // namespace avalanche
263 
264 #endif // BITCOIN_AVALANCHE_PROCESSOR_H
std::chrono::time_point< std::chrono::steady_clock > TimePoint
Definition: node.h:17
RecursiveMutex cs_main
Global state.
Definition: validation.cpp:112
The block chain is a tree shaped structure starting with the genesis block at the root,...
Definition: blockindex.h:23
Definition: net.h:923
An encapsulated secp256k1 private key.
Definition: key.h:28
Information about a peer.
Definition: net.h:455
An encapsulated public key.
Definition: pubkey.h:31
Simple class for background tasks that should be run periodically or once "after a while".
Definition: scheduler.h:36
Provides an interface for creating and interacting with one or two chainstates: an IBD chainstate gen...
Definition: validation.h:1077
Definition: config.h:17
Interface for message handling.
Definition: net.h:879
void avaproofsSent(NodeId nodeid) LOCKS_EXCLUDED(cs_main)
Definition: processor.cpp:689
void sendResponse(CNode *pfrom, Response response) const
Definition: processor.cpp:475
const uint32_t staleVoteThreshold
Voting parameters.
Definition: processor.h:171
std::atomic< bool > quorumIsEstablished
Definition: processor.h:166
std::unique_ptr< PeerManager > peerManager GUARDED_BY(cs_peerManager)
auto withPeerManager(Callable &&func) const
Definition: processor.h:211
bool addProofToReconcile(const ProofRef &proof)
Definition: processor.cpp:375
boost::multi_index_container< Query, boost::multi_index::indexed_by< boost::multi_index::hashed_unique< boost::multi_index::composite_key< Query, boost::multi_index::member< Query, NodeId, &Query::nodeid >, boost::multi_index::member< Query, uint64_t, &Query::round > >>, boost::multi_index::ordered_non_unique< boost::multi_index::tag< query_timeout >, boost::multi_index::member< Query, TimePoint, &Query::timeout > >> > QuerySet
Definition: processor.h:149
int64_t getAvaproofsNodeCounter() const
Definition: processor.h:230
RWCollection< QuerySet > queries
Definition: processor.h:151
bool ProcessMessages(const ::Config &config, CNode *pnode, std::atomic< bool > &interrupt) override
Definition: processor.h:237
static std::unique_ptr< Processor > MakeProcessor(const ArgsManager &argsman, interfaces::Chain &chain, CConnman *connman, ChainstateManager &chainman, CScheduler &scheduler, bilingual_str &error)
Definition: processor.cpp:171
bool sendHello(CNode *pfrom) const
Definition: processor.cpp:649
bool isWorthPolling(const CBlockIndex *pindex) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
Definition: processor.cpp:979
bool isAccepted(const CBlockIndex *pindex) const
Definition: processor.cpp:396
void clearTimedoutRequests()
Definition: processor.cpp:855
bool startEventLoop(CScheduler &scheduler)
Definition: processor.cpp:680
int getConfidence(const CBlockIndex *pindex) const
Definition: processor.cpp:421
std::atomic< uint64_t > round
Keep track of peers and queries sent.
Definition: processor.h:115
EventLoop eventLoop
Event loop machinery.
Definition: processor.h:159
int64_t minAvaproofsNodeCount
Definition: processor.h:167
bool isAvalancheServiceAvailable()
Definition: processor.h:224
RWCollection< ProofVoteMap > proofVoteRecords
Proofs to run avalanche on.
Definition: processor.h:110
bool registerVotes(NodeId nodeid, const Response &response, std::vector< BlockUpdate > &blockUpdates, std::vector< ProofUpdate > &proofUpdates, int &banscore, std::string &error)
Definition: processor.cpp:482
std::unique_ptr< interfaces::Handler > chainNotificationsHandler
Definition: processor.h:175
uint32_t minQuorumScore
Quorum management.
Definition: processor.h:164
ProofRef getLocalProof() const
Definition: processor.cpp:676
void InitializeNode(const ::Config &config, CNode *pnode) override
Definition: processor.h:236
const uint32_t staleVoteFactor
Definition: processor.h:172
std::unique_ptr< PeerData > peerData
Definition: processor.h:154
Processor(Config avaconfig, interfaces::Chain &chain, CConnman *connmanIn, ChainstateManager &chainman, CScheduler &scheduler, std::unique_ptr< PeerData > peerDataIn, CKey sessionKeyIn, uint32_t minQuorumTotalScoreIn, double minQuorumConnectedScoreRatioIn, int64_t minAvaproofsNodeCountIn, uint32_t staleVoteThresholdIn, uint32_t staleVoteFactorIn, Amount stakeUtxoDustThresholdIn)
Definition: processor.cpp:134
CConnman * connman
Definition: processor.h:99
CPubKey getSessionPubKey() const
Definition: processor.cpp:645
ChainstateManager & chainman
Definition: processor.h:100
std::atomic< int64_t > avaproofsNodeCounter
Definition: processor.h:168
bool SendMessages(const ::Config &config, CNode *pnode) override
Definition: processor.h:241
bool isQuorumEstablished() LOCKS_EXCLUDED(cs_main)
Definition: processor.cpp:710
void FinalizeNode(const ::Config &config, const CNode &node) override LOCKS_EXCLUDED(cs_main)
Handle removal of a node.
Definition: processor.cpp:781
std::vector< CInv > getInvsForNextPoll(bool forPoll=true)
Definition: processor.cpp:918
RWCollection< BlockVoteMap > blockVoteRecords
Blocks to run avalanche on.
Definition: processor.h:105
bool addBlockToReconcile(const CBlockIndex *pindex)
Definition: processor.cpp:353
Mutex cs_peerManager
Keep track of the peers and associated infos.
Definition: processor.h:120
CBlockIndex *finalizationTip GUARDED_BY(cs_finalizationTip)
Definition: processor.h:179
double minQuorumConnectedScoreRatio
Definition: processor.h:165
const VoteItem getVoteItem() const
Definition: processor.h:78
const VoteStatus & getStatus() const
Definition: processor.h:75
VoteItemUpdate(const VoteItem itemIn, VoteStatus statusIn)
Definition: processor.h:72
Interface giving clients (wallet processes, maybe other analysis tools in the future) ability to acce...
Definition: chain.h:123
std::map< const ProofRef, VoteRecord, ProofComparatorByScore > ProofVoteMap
Definition: processor.h:87
std::map< const CBlockIndex *, VoteRecord, CBlockIndexWorkComparator > BlockVoteMap
Definition: processor.h:85
Definition: init.h:28
int64_t NodeId
Definition: nodeid.h:10
Response response
Definition: processor.cpp:452
static constexpr std::chrono::milliseconds AVALANCHE_DEFAULT_QUERY_TIMEOUT
How long before we consider that a query timed out.
Definition: processor.h:49
static constexpr size_t AVALANCHE_MAX_ELEMENT_POLL
Maximum item that can be polled at once.
Definition: processor.h:44
Definition: amount.h:19
std::vector< CInv > invs
We declare this as mutable so it can be modified in the multi_index.
Definition: processor.h:134
Bilingual messages:
Definition: translation.h:17
#define LOCK(cs)
Definition: sync.h:243
bool error(const char *fmt, const Args &...args)
Definition: system.h:46
#define EXCLUSIVE_LOCKS_REQUIRED(...)
Definition: threadsafety.h:56
#define LOCKS_EXCLUDED(...)
Definition: threadsafety.h:55