Bitcoin Core  29.1.0
P2P Digital Currency
validation.h
Go to the documentation of this file.
1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2022 The Bitcoin Core developers
3 // Distributed under the MIT software license, see the accompanying
4 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 
6 #ifndef BITCOIN_CONSENSUS_VALIDATION_H
7 #define BITCOIN_CONSENSUS_VALIDATION_H
8 
9 #include <string>
10 #include <consensus/consensus.h>
11 #include <primitives/transaction.h>
12 #include <primitives/block.h>
13 
15 static constexpr int NO_WITNESS_COMMITMENT{-1};
16 
18 static constexpr size_t MINIMUM_WITNESS_COMMITMENT{38};
19 
23 enum class TxValidationResult {
24  TX_RESULT_UNSET = 0,
25  TX_CONSENSUS,
30 
49  TX_UNKNOWN,
50 };
51 
58  BLOCK_RESULT_UNSET = 0,
68 };
69 
70 
71 
75 template <typename Result>
77 {
78 private:
79  enum class ModeState {
80  M_VALID,
81  M_INVALID,
82  M_ERROR,
83  } m_mode{ModeState::M_VALID};
85  std::string m_reject_reason;
86  std::string m_debug_message;
87 
88 public:
90  const std::string& reject_reason = "",
91  const std::string& debug_message = "")
92  {
93  m_result = result;
94  m_reject_reason = reject_reason;
95  m_debug_message = debug_message;
96  if (m_mode != ModeState::M_ERROR) m_mode = ModeState::M_INVALID;
97  return false;
98  }
99  bool Error(const std::string& reject_reason)
100  {
101  if (m_mode == ModeState::M_VALID)
102  m_reject_reason = reject_reason;
103  m_mode = ModeState::M_ERROR;
104  return false;
105  }
106  bool IsValid() const { return m_mode == ModeState::M_VALID; }
107  bool IsInvalid() const { return m_mode == ModeState::M_INVALID; }
108  bool IsError() const { return m_mode == ModeState::M_ERROR; }
109  Result GetResult() const { return m_result; }
110  std::string GetRejectReason() const { return m_reject_reason; }
111  std::string GetDebugMessage() const { return m_debug_message; }
112  std::string ToString() const
113  {
114  if (IsValid()) {
115  return "Valid";
116  }
117 
118  if (!m_debug_message.empty()) {
119  return m_reject_reason + ", " + m_debug_message;
120  }
121 
122  return m_reject_reason;
123  }
124 };
125 
126 class TxValidationState : public ValidationState<TxValidationResult> {};
127 class BlockValidationState : public ValidationState<BlockValidationResult> {};
128 
129 // These implement the weight = (stripped_size * 4) + witness_size formula,
130 // using only serialization with and without witness data. As witness_size
131 // is equal to total_size - stripped_size, this formula is identical to:
132 // weight = (stripped_size * 3) + total_size.
133 static inline int32_t GetTransactionWeight(const CTransaction& tx)
134 {
136 }
137 static inline int64_t GetBlockWeight(const CBlock& block)
138 {
140 }
141 static inline int64_t GetTransactionInputWeight(const CTxIn& txin)
142 {
143  // scriptWitness size is added here because witnesses and txins are split up in segwit serialization.
145 }
146 
148 inline int GetWitnessCommitmentIndex(const CBlock& block)
149 {
150  int commitpos = NO_WITNESS_COMMITMENT;
151  if (!block.vtx.empty()) {
152  for (size_t o = 0; o < block.vtx[0]->vout.size(); o++) {
153  const CTxOut& vout = block.vtx[0]->vout[o];
155  vout.scriptPubKey[0] == OP_RETURN &&
156  vout.scriptPubKey[1] == 0x24 &&
157  vout.scriptPubKey[2] == 0xaa &&
158  vout.scriptPubKey[3] == 0x21 &&
159  vout.scriptPubKey[4] == 0xa9 &&
160  vout.scriptPubKey[5] == 0xed) {
161  commitpos = o;
162  }
163  }
164  }
165  return commitpos;
166 }
167 
168 #endif // BITCOIN_CONSENSUS_VALIDATION_H
invalid by consensus rules
bool Error(const std::string &reject_reason)
Definition: validation.h:99
static const int WITNESS_SCALE_FACTOR
Definition: consensus.h:21
std::string GetDebugMessage() const
Definition: validation.h:111
CScript scriptPubKey
Definition: transaction.h:153
Template for capturing information about block/transaction validation.
Definition: validation.h:76
Definition: block.h:68
We don&#39;t have the previous block the checked one is built on.
transaction was not validated because package failed
invalid proof of work or time too old
CScriptWitness scriptWitness
Only serialized through CTransaction.
Definition: transaction.h:72
network rule violation (DoS value may be set)
size_t GetSerializeSize(const T &t)
Definition: serialize.h:1103
BlockValidationResult
A "reason" why a block was invalid, suitable for determining whether the provider of the block should...
Definition: validation.h:57
transaction was missing some of its inputs
static constexpr size_t MINIMUM_WITNESS_COMMITMENT
Minimum size of a witness commitment structure.
Definition: validation.h:18
std::vector< std::vector< unsigned char > > stack
Definition: script.h:588
Result m_result
Definition: validation.h:84
violated mempool&#39;s fee/size/descendant/RBF/etc limits
the block header may be on a too-little-work chain
inputs (covered by txid) failed policy rules
transaction spends a coinbase too early, or violates locktime/sequence locks
static constexpr int NO_WITNESS_COMMITMENT
Index marker for when no witness commitment is present in a coinbase transaction. ...
Definition: validation.h:15
static int32_t GetTransactionWeight(const CTransaction &tx)
Definition: validation.h:133
initial value. Tx has not yet been rejected
bool IsValid() const
Definition: validation.h:106
initial value. Block has not yet been rejected
bool Invalid(Result result, const std::string &reject_reason="", const std::string &debug_message="")
Definition: validation.h:89
Transaction might have a witness prior to SegWit activation, or witness may have been malleated (whic...
this block was cached as being invalid and we didn&#39;t store the reason why
An input of a transaction.
Definition: transaction.h:66
static int64_t GetTransactionInputWeight(const CTxIn &txin)
Definition: validation.h:141
std::string ToString() const
Definition: validation.h:112
the block failed to meet one of our checkpoints
Result GetResult() const
Definition: validation.h:109
An output of a transaction.
Definition: transaction.h:149
fails some policy, but might be acceptable if submitted in a (different) package
std::string m_debug_message
Definition: validation.h:86
Transaction is missing a witness.
invalid by consensus rules (excluding any below reasons)
std::vector< CTransactionRef > vtx
Definition: block.h:72
the block&#39;s data didn&#39;t match the data committed to by the PoW
auto result
Definition: common-types.h:74
A block this one builds on is invalid.
bool IsInvalid() const
Definition: validation.h:107
this node does not have a mempool so can&#39;t validate the transaction
size_type size() const
Definition: prevector.h:294
block timestamp was > 2 hours in the future (or our clock is bad)
std::string m_reject_reason
Definition: validation.h:85
The basic transaction that is broadcasted on the network and contained in blocks. ...
Definition: transaction.h:295
std::string GetRejectReason() const
Definition: validation.h:110
int GetWitnessCommitmentIndex(const CBlock &block)
Compute at which vout of the block&#39;s coinbase transaction the witness commitment occurs, or -1 if not found.
Definition: validation.h:148
static int64_t GetBlockWeight(const CBlock &block)
Definition: validation.h:137
Tx already in mempool or conflicts with a tx in the chain (if it conflicts with another tx in mempool...
otherwise didn&#39;t meet our local policy rules
bool IsError() const
Definition: validation.h:108
static constexpr TransactionSerParams TX_WITH_WITNESS
Definition: transaction.h:195
static constexpr TransactionSerParams TX_NO_WITNESS
Definition: transaction.h:196
TxValidationResult
A "reason" why a transaction was invalid, suitable for determining whether the provider of the transa...
Definition: validation.h:23