Raven Core  3.0.0
P2P Digital Currency
chain.h
Go to the documentation of this file.
1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2016 The Bitcoin Core developers
3 // Copyright (c) 2017-2019 The Raven Core developers
4 // Distributed under the MIT software license, see the accompanying
5 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
6 
7 #ifndef RAVEN_CHAIN_H
8 #define RAVEN_CHAIN_H
9 
10 #include "arith_uint256.h"
11 #include "primitives/block.h"
12 #include "pow.h"
13 #include "tinyformat.h"
14 #include "uint256.h"
15 
16 #include <vector>
17 
22 static const int64_t MAX_FUTURE_BLOCK_TIME = 2 * 60 * 60;
23 static const int64_t MAX_FUTURE_BLOCK_TIME_DGW = MAX_FUTURE_BLOCK_TIME / 10;
24 
31 static const int64_t TIMESTAMP_WINDOW = MAX_FUTURE_BLOCK_TIME;
32 
34 {
35 public:
36  unsigned int nBlocks;
37  unsigned int nSize;
38  unsigned int nUndoSize;
39  unsigned int nHeightFirst;
40  unsigned int nHeightLast;
41  uint64_t nTimeFirst;
42  uint64_t nTimeLast;
43 
45 
46  template <typename Stream, typename Operation>
47  inline void SerializationOp(Stream& s, Operation ser_action) {
48  READWRITE(VARINT(nBlocks));
49  READWRITE(VARINT(nSize));
50  READWRITE(VARINT(nUndoSize));
51  READWRITE(VARINT(nHeightFirst));
52  READWRITE(VARINT(nHeightLast));
53  READWRITE(VARINT(nTimeFirst));
54  READWRITE(VARINT(nTimeLast));
55  }
56 
57  void SetNull() {
58  nBlocks = 0;
59  nSize = 0;
60  nUndoSize = 0;
61  nHeightFirst = 0;
62  nHeightLast = 0;
63  nTimeFirst = 0;
64  nTimeLast = 0;
65  }
66 
68  SetNull();
69  }
70 
71  std::string ToString() const;
72 
74  void AddBlock(unsigned int nHeightIn, uint64_t nTimeIn) {
75  if (nBlocks==0 || nHeightFirst > nHeightIn)
76  nHeightFirst = nHeightIn;
77  if (nBlocks==0 || nTimeFirst > nTimeIn)
78  nTimeFirst = nTimeIn;
79  nBlocks++;
80  if (nHeightIn > nHeightLast)
81  nHeightLast = nHeightIn;
82  if (nTimeIn > nTimeLast)
83  nTimeLast = nTimeIn;
84  }
85 };
86 
88 {
89  int nFile;
90  unsigned int nPos;
91 
93 
94  template <typename Stream, typename Operation>
95  inline void SerializationOp(Stream& s, Operation ser_action) {
96  READWRITE(VARINT(nFile));
97  READWRITE(VARINT(nPos));
98  }
99 
101  SetNull();
102  }
103 
104  CDiskBlockPos(int nFileIn, unsigned int nPosIn) {
105  nFile = nFileIn;
106  nPos = nPosIn;
107  }
108 
109  friend bool operator==(const CDiskBlockPos &a, const CDiskBlockPos &b) {
110  return (a.nFile == b.nFile && a.nPos == b.nPos);
111  }
112 
113  friend bool operator!=(const CDiskBlockPos &a, const CDiskBlockPos &b) {
114  return !(a == b);
115  }
116 
117  void SetNull() { nFile = -1; nPos = 0; }
118  bool IsNull() const { return (nFile == -1); }
119 
120  std::string ToString() const
121  {
122  return strprintf("CBlockDiskPos(nFile=%i, nPos=%i)", nFile, nPos);
123  }
124 
125 };
126 
127 enum BlockStatus: uint32_t {
130 
133 
137 
144 
148 
151 
155 
159 
163 
165 };
166 
173 {
174 public:
177 
180 
183 
185  int nHeight;
186 
188  int nFile;
189 
191  unsigned int nDataPos;
192 
194  unsigned int nUndoPos;
195 
198 
201  unsigned int nTx;
202 
206  unsigned int nChainTx;
207 
209  uint32_t nStatus;
210 
212  int32_t nVersion;
214  uint32_t nTime;
215  uint32_t nBits;
216  uint32_t nNonce;
217 
219  int32_t nSequenceId;
220 
222  unsigned int nTimeMax;
223 
224  void SetNull()
225  {
226  phashBlock = nullptr;
227  pprev = nullptr;
228  pskip = nullptr;
229  nHeight = 0;
230  nFile = 0;
231  nDataPos = 0;
232  nUndoPos = 0;
233  nChainWork = arith_uint256();
234  nTx = 0;
235  nChainTx = 0;
236  nStatus = 0;
237  nSequenceId = 0;
238  nTimeMax = 0;
239 
240  nVersion = 0;
241  hashMerkleRoot = uint256();
242  nTime = 0;
243  nBits = 0;
244  nNonce = 0;
245  }
246 
248  {
249  SetNull();
250  }
251 
252  explicit CBlockIndex(const CBlockHeader& block)
253  {
254  SetNull();
255 
256  nVersion = block.nVersion;
257  hashMerkleRoot = block.hashMerkleRoot;
258  nTime = block.nTime;
259  nBits = block.nBits;
260  nNonce = block.nNonce;
261  }
262 
264  CDiskBlockPos ret;
265  if (nStatus & BLOCK_HAVE_DATA) {
266  ret.nFile = nFile;
267  ret.nPos = nDataPos;
268  }
269  return ret;
270  }
271 
273  CDiskBlockPos ret;
274  if (nStatus & BLOCK_HAVE_UNDO) {
275  ret.nFile = nFile;
276  ret.nPos = nUndoPos;
277  }
278  return ret;
279  }
280 
282  {
283  CBlockHeader block;
284  block.nVersion = nVersion;
285  if (pprev)
286  block.hashPrevBlock = pprev->GetBlockHash();
287  block.hashMerkleRoot = hashMerkleRoot;
288  block.nTime = nTime;
289  block.nBits = nBits;
290  block.nNonce = nNonce;
291  return block;
292  }
293 
295  {
296  return *phashBlock;
297  }
298 
299  int64_t GetBlockTime() const
300  {
301  return (int64_t)nTime;
302  }
303 
304  int64_t GetBlockTimeMax() const
305  {
306  return (int64_t)nTimeMax;
307  }
308 
309  enum { nMedianTimeSpan=11 };
310 
311  int64_t GetMedianTimePast() const
312  {
313  int64_t pmedian[nMedianTimeSpan];
314  int64_t* pbegin = &pmedian[nMedianTimeSpan];
315  int64_t* pend = &pmedian[nMedianTimeSpan];
316 
317  const CBlockIndex* pindex = this;
318  for (int i = 0; i < nMedianTimeSpan && pindex; i++, pindex = pindex->pprev)
319  *(--pbegin) = pindex->GetBlockTime();
320 
321  std::sort(pbegin, pend);
322  return pbegin[(pend - pbegin)/2];
323  }
324 
325  std::string ToString() const
326  {
327  return strprintf("CBlockIndex(pprev=%p, nHeight=%d, merkle=%s, hashBlock=%s)",
328  pprev, nHeight,
329  hashMerkleRoot.ToString(),
330  GetBlockHash().ToString());
331  }
332 
335  {
336  assert(!(nUpTo & ~BLOCK_VALID_MASK)); // Only validity flags allowed.
337  if (nStatus & BLOCK_FAILED_MASK)
338  return false;
339  return ((nStatus & BLOCK_VALID_MASK) >= nUpTo);
340  }
341 
344  bool RaiseValidity(enum BlockStatus nUpTo)
345  {
346  assert(!(nUpTo & ~BLOCK_VALID_MASK)); // Only validity flags allowed.
347  if (nStatus & BLOCK_FAILED_MASK)
348  return false;
349  if ((nStatus & BLOCK_VALID_MASK) < nUpTo) {
350  nStatus = (nStatus & ~BLOCK_VALID_MASK) | nUpTo;
351  return true;
352  }
353  return false;
354  }
355 
357  void BuildSkip();
358 
360  CBlockIndex* GetAncestor(int height);
361  const CBlockIndex* GetAncestor(int height) const;
362 };
363 
366 int64_t GetBlockProofEquivalentTime(const CBlockIndex& to, const CBlockIndex& from, const CBlockIndex& tip, const Consensus::Params&);
368 const CBlockIndex* LastCommonAncestor(const CBlockIndex* pa, const CBlockIndex* pb);
369 
370 
373 {
374 public:
376 
378  hashPrev = uint256();
379  }
380 
381  explicit CDiskBlockIndex(const CBlockIndex* pindex) : CBlockIndex(*pindex) {
382  hashPrev = (pprev ? pprev->GetBlockHash() : uint256());
383  }
384 
386 
387  template <typename Stream, typename Operation>
388  inline void SerializationOp(Stream& s, Operation ser_action) {
389  int _nVersion = s.GetVersion();
390  if (!(s.GetType() & SER_GETHASH))
391  READWRITE(VARINT(_nVersion));
392 
393  READWRITE(VARINT(nHeight));
394  READWRITE(VARINT(nStatus));
395  READWRITE(VARINT(nTx));
396  if (nStatus & (BLOCK_HAVE_DATA | BLOCK_HAVE_UNDO))
397  READWRITE(VARINT(nFile));
398  if (nStatus & BLOCK_HAVE_DATA)
399  READWRITE(VARINT(nDataPos));
400  if (nStatus & BLOCK_HAVE_UNDO)
401  READWRITE(VARINT(nUndoPos));
402 
403  // block header
404  READWRITE(this->nVersion);
405  READWRITE(hashPrev);
406  READWRITE(hashMerkleRoot);
407  READWRITE(nTime);
408  READWRITE(nBits);
409  READWRITE(nNonce);
410  }
411 
413  {
414  CBlockHeader block;
415  block.nVersion = nVersion;
416  block.hashPrevBlock = hashPrev;
417  block.hashMerkleRoot = hashMerkleRoot;
418  block.nTime = nTime;
419  block.nBits = nBits;
420  block.nNonce = nNonce;
421  return block.GetHash();
422  }
423 
424 
425  std::string ToString() const
426  {
427  std::string str = "CDiskBlockIndex(";
428  str += CBlockIndex::ToString();
429  str += strprintf("\n hashBlock=%s, hashPrev=%s)",
430  GetBlockHash().ToString(),
431  hashPrev.ToString());
432  return str;
433  }
434 };
435 
437 class CChain {
438 private:
439  std::vector<CBlockIndex*> vChain;
440 
441 public:
443  CBlockIndex *Genesis() const {
444  return vChain.size() > 0 ? vChain[0] : nullptr;
445  }
446 
448  CBlockIndex *Tip() const {
449  return vChain.size() > 0 ? vChain[vChain.size() - 1] : nullptr;
450  }
451 
453  CBlockIndex *operator[](int nHeight) const {
454  if (nHeight < 0 || nHeight >= (int)vChain.size())
455  return nullptr;
456  return vChain[nHeight];
457  }
458 
460  friend bool operator==(const CChain &a, const CChain &b) {
461  return a.vChain.size() == b.vChain.size() &&
462  a.vChain[a.vChain.size() - 1] == b.vChain[b.vChain.size() - 1];
463  }
464 
466  bool Contains(const CBlockIndex *pindex) const {
467  return (*this)[pindex->nHeight] == pindex;
468  }
469 
471  CBlockIndex *Next(const CBlockIndex *pindex) const {
472  if (Contains(pindex))
473  return (*this)[pindex->nHeight + 1];
474  else
475  return nullptr;
476  }
477 
479  int Height() const {
480  return vChain.size() - 1;
481  }
482 
484  void SetTip(CBlockIndex *pindex);
485 
487  CBlockLocator GetLocator(const CBlockIndex *pindex = nullptr) const;
488 
490  const CBlockIndex *FindFork(const CBlockIndex *pindex) const;
491 
493  CBlockIndex* FindEarliestAtLeast(int64_t nTime) const;
494 };
495 
496 #endif // RAVEN_CHAIN_H
uint32_t nNonce
Definition: block.h:30
arith_uint256 nChainWork
(memory only) Total amount of work (expected number of hashes) in the chain up to and including this ...
Definition: chain.h:197
#define VARINT(obj)
Definition: serialize.h:367
ADD_SERIALIZE_METHODS
Definition: chain.h:385
CDiskBlockPos GetBlockPos() const
Definition: chain.h:263
std::string ToString() const
Definition: chain.h:325
int32_t nSequenceId
(memory only) Sequential id assigned to distinguish order in which blocks are received.
Definition: chain.h:219
ADD_SERIALIZE_METHODS
Definition: chain.h:44
CBlockIndex * pskip
pointer to the index of some further predecessor of this block
Definition: chain.h:182
std::vector< CBlockIndex * > vChain
Definition: chain.h:439
CDiskBlockPos(int nFileIn, unsigned int nPosIn)
Definition: chain.h:104
int64_t GetBlockTime() const
Definition: chain.h:299
Describes a place in the block chain to another node such that if the other node doesn&#39;t have the sam...
Definition: block.h:132
descends from failed block
Definition: chain.h:161
CBlockIndex * pprev
pointer to the index of the predecessor of this block
Definition: chain.h:179
#define READWRITE(obj)
Definition: serialize.h:163
uint32_t nStatus
Verification status of this block. See enum BlockStatus.
Definition: chain.h:209
void AddBlock(unsigned int nHeightIn, uint64_t nTimeIn)
update statistics (does not update nSize)
Definition: chain.h:74
const CBlockIndex * LastCommonAncestor(const CBlockIndex *pa, const CBlockIndex *pb)
Find the forking point between two chain tips.
Definition: chain.cpp:155
#define strprintf
Definition: tinyformat.h:1054
An in-memory indexed chain of blocks.
Definition: chain.h:437
CBlockIndex()
Definition: chain.h:247
All parent headers found, difficulty matches, timestamp >= median previous, checkpoint.
Definition: chain.h:136
CBlockHeader GetBlockHeader() const
Definition: chain.h:281
int Height() const
Return the maximal height in the chain.
Definition: chain.h:479
stage after last reached validness failed
Definition: chain.h:160
Only first tx is coinbase, 2 <= coinbase input script length <= 100, transactions valid...
Definition: chain.h:143
unsigned int nSize
number of used bytes of block file
Definition: chain.h:37
friend bool operator==(const CDiskBlockPos &a, const CDiskBlockPos &b)
Definition: chain.h:109
CBlockIndex * Genesis() const
Returns the index entry for the genesis block of this chain, or nullptr if none.
Definition: chain.h:443
uint32_t nTime
Definition: chain.h:214
undo data available in rev*.dat
Definition: chain.h:157
int nFile
Which # file this block is stored in (blk?????.dat)
Definition: chain.h:188
Unused.
Definition: chain.h:129
unsigned int nHeightLast
highest height of block in file
Definition: chain.h:40
uint32_t nTime
Definition: block.h:28
unsigned int nChainTx
(memory only) Number of transactions in the chain up to and including this block. ...
Definition: chain.h:206
unsigned int nUndoSize
number of used bytes in the undo file
Definition: chain.h:38
friend bool operator!=(const CDiskBlockPos &a, const CDiskBlockPos &b)
Definition: chain.h:113
uint256 GetBlockHash() const
Definition: chain.h:294
void SetNull()
Definition: chain.h:57
bool IsValid(enum BlockStatus nUpTo=BLOCK_VALID_TRANSACTIONS) const
Check whether this block index entry is valid up to the passed validity level.
Definition: chain.h:334
arith_uint256 GetBlockProof(const CBlockIndex &block)
Definition: chain.cpp:121
Outputs do not overspend inputs, no double spends, coinbase output ok, no immature coinbase spends...
Definition: chain.h:147
unsigned int nTimeMax
(memory only) Maximum nTime in the chain up to and including this block.
Definition: chain.h:222
uint64_t nTimeFirst
earliest time of block in file
Definition: chain.h:41
ADD_SERIALIZE_METHODS
Definition: chain.h:92
CBlockIndex * operator[](int nHeight) const
Returns the index entry at a particular height in this chain, or nullptr if no such height exists...
Definition: chain.h:453
Scripts & signatures ok. Implies all parents are also at least SCRIPTS.
Definition: chain.h:150
uint256 hashMerkleRoot
Definition: block.h:27
void SerializationOp(Stream &s, Operation ser_action)
Definition: chain.h:95
uint32_t nNonce
Definition: chain.h:216
unsigned int nDataPos
Byte offset within blk?????.dat where this block&#39;s data is stored.
Definition: chain.h:191
CBlockFileInfo()
Definition: chain.h:67
Parsed, version ok, hash satisfies claimed PoW, 1 <= vtx count <= max, timestamp not in future...
Definition: chain.h:132
bool Contains(const CBlockIndex *pindex) const
Efficiently check whether a block is present in this chain.
Definition: chain.h:466
CBlockIndex(const CBlockHeader &block)
Definition: chain.h:252
CBlockIndex * Next(const CBlockIndex *pindex) const
Find the successor of a block in this chain, or nullptr if the given index is not found or is the tip...
Definition: chain.h:471
uint256 hashPrevBlock
Definition: block.h:26
int64_t GetBlockTimeMax() const
Definition: chain.h:304
CDiskBlockIndex()
Definition: chain.h:377
CDiskBlockPos()
Definition: chain.h:100
uint256 hashMerkleRoot
Definition: chain.h:213
friend bool operator==(const CChain &a, const CChain &b)
Compare two chains efficiently.
Definition: chain.h:460
unsigned int nHeightFirst
lowest height of block in file
Definition: chain.h:39
std::string ToString() const
Definition: chain.h:120
Used to marshal pointers into hashes for db storage.
Definition: chain.h:372
std::string ToString() const
Definition: uint256.cpp:63
Parameters that influence chain consensus.
Definition: params.h:47
bool IsNull() const
Definition: chain.h:118
256-bit unsigned big integer.
int64_t GetMedianTimePast() const
Definition: chain.h:311
block data in blk*.data was received with a witness-enforcing client
Definition: chain.h:164
unsigned int nPos
Definition: chain.h:90
void SerializationOp(Stream &s, Operation ser_action)
Definition: chain.h:47
int64_t GetBlockProofEquivalentTime(const CBlockIndex &to, const CBlockIndex &from, const CBlockIndex &tip, const Consensus::Params &)
Return the time it would take to redo the work difference between from and to, assuming the current h...
Definition: chain.cpp:136
unsigned int nUndoPos
Byte offset within rev?????.dat where this block&#39;s undo data is stored.
Definition: chain.h:194
uint256 GetHash() const
Definition: block.cpp:14
int32_t nVersion
block header
Definition: chain.h:212
256-bit opaque blob.
Definition: uint256.h:123
uint256 hashPrev
Definition: chain.h:375
void SerializationOp(Stream &s, Operation ser_action)
Definition: chain.h:388
CDiskBlockIndex(const CBlockIndex *pindex)
Definition: chain.h:381
The block chain is a tree shaped structure starting with the genesis block at the root...
Definition: chain.h:172
CDiskBlockPos GetUndoPos() const
Definition: chain.h:272
void SetNull()
Definition: chain.h:117
CBlockIndex * Tip() const
Returns the index entry for the tip of this chain, or nullptr if none.
Definition: chain.h:448
unsigned int nBlocks
number of blocks stored in file
Definition: chain.h:36
std::string ToString() const
Definition: chain.h:425
bool RaiseValidity(enum BlockStatus nUpTo)
Raise the validity level of this block index entry.
Definition: chain.h:344
BlockStatus
Definition: chain.h:127
All validity bits.
Definition: chain.h:153
uint64_t nTimeLast
latest time of block in file
Definition: chain.h:42
int nHeight
height of the entry in the chain. The genesis block has height 0
Definition: chain.h:185
full block available in blk*.dat
Definition: chain.h:156
uint256 GetBlockHash() const
Definition: chain.h:412
int nFile
Definition: chain.h:89
std::string ToString() const
int32_t nVersion
Definition: block.h:25
uint32_t nBits
Definition: chain.h:215
unsigned int nTx
Number of transactions in this block.
Definition: chain.h:201
Nodes collect new transactions into a block, hash them into a hash tree, and scan through nonce value...
Definition: block.h:21
uint32_t nBits
Definition: block.h:29
void SetNull()
Definition: chain.h:224
const uint256 * phashBlock
pointer to the hash of the block, if any. Memory is owned by this CBlockIndex
Definition: chain.h:176