Branch data Line data Source code
1 : : // Copyright (c) 2009-present The Bitcoin Core 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_KERNEL_MEMPOOL_ENTRY_H
6 : : #define BITCOIN_KERNEL_MEMPOOL_ENTRY_H
7 : :
8 : : #include <consensus/amount.h>
9 : : #include <consensus/validation.h>
10 : : #include <core_memusage.h>
11 : : #include <policy/policy.h>
12 : : #include <policy/settings.h>
13 : : #include <primitives/transaction.h>
14 : : #include <txgraph.h>
15 : : #include <util/epochguard.h>
16 : : #include <util/overflow.h>
17 : :
18 : : #include <chrono>
19 : : #include <cstddef>
20 : : #include <cstdint>
21 : : #include <functional>
22 : : #include <memory>
23 : : #include <set>
24 : :
25 : : class CBlockIndex;
26 : :
27 : : struct LockPoints {
28 : : // Will be set to the blockchain height and median time past
29 : : // values that would be necessary to satisfy all relative locktime
30 : : // constraints (BIP68) of this tx given our view of block chain history
31 : : int height{0};
32 : : int64_t time{0};
33 : : // As long as the current chain descends from the highest height block
34 : : // containing one of the inputs used in the calculation, then the cached
35 : : // values are still valid even after a reorg.
36 : : CBlockIndex* maxInputBlock{nullptr};
37 : : };
38 : :
39 : : struct CompareIteratorByHash {
40 : : // SFINAE for T where T is either a pointer type (e.g., a txiter) or a reference_wrapper<T>
41 : : // (e.g. a wrapped CTxMemPoolEntry&)
42 : : template <typename T>
43 : 488096 : bool operator()(const std::reference_wrapper<T>& a, const std::reference_wrapper<T>& b) const
44 : : {
45 : 488096 : return a.get().GetTx().GetHash() < b.get().GetTx().GetHash();
46 : : }
47 : : template <typename T>
48 : 1497813 : bool operator()(const T& a, const T& b) const
49 : : {
50 : 1497813 : return a->GetTx().GetHash() < b->GetTx().GetHash();
51 : : }
52 : : };
53 : :
54 : : /** \class CTxMemPoolEntry
55 : : *
56 : : * CTxMemPoolEntry stores data about the corresponding transaction, as well
57 : : * as data about all in-mempool transactions that depend on the transaction
58 : : * ("descendant" transactions).
59 : : *
60 : : * When a new entry is added to the mempool, we update the descendant state
61 : : * (m_count_with_descendants, nSizeWithDescendants, and nModFeesWithDescendants) for
62 : : * all ancestors of the newly added transaction.
63 : : *
64 : : */
65 : :
66 : : class CTxMemPoolEntry : public TxGraph::Ref
67 : : {
68 : : public:
69 : : typedef std::reference_wrapper<const CTxMemPoolEntry> CTxMemPoolEntryRef;
70 : :
71 : : private:
72 : : CTxMemPoolEntry(const CTxMemPoolEntry&) = delete;
73 : :
74 : : const CTransactionRef tx;
75 : : const CAmount nFee; //!< Cached to avoid expensive parent-transaction lookups
76 : : const int32_t nTxWeight; //!< ... and avoid recomputing tx weight (also used for GetTxSize())
77 : : const size_t nUsageSize; //!< ... and total memory usage
78 : : const int64_t nTime; //!< Local time when entering the mempool
79 : : const uint64_t entry_sequence; //!< Sequence number used to determine whether this transaction is too recent for relay
80 : : const unsigned int entryHeight; //!< Chain height when entering the mempool
81 : : const bool spendsCoinbase; //!< keep track of transactions that spend a coinbase
82 : : const int64_t sigOpCost; //!< Total sigop cost
83 : : CAmount m_modified_fee; //!< Used for determining the priority of the transaction for mining in a block
84 : : mutable LockPoints lockPoints; //!< Track the height and time at which tx was final
85 : :
86 : : public:
87 [ + - ]: 179848 : virtual ~CTxMemPoolEntry() = default;
88 : 89924 : CTxMemPoolEntry(TxGraph::Ref&& ref, const CTransactionRef& tx, CAmount fee,
89 : : int64_t time, unsigned int entry_height, uint64_t entry_sequence,
90 : : bool spends_coinbase,
91 : : int64_t sigops_cost, LockPoints lp)
92 : 89924 : : TxGraph::Ref(std::move(ref)),
93 : 179848 : tx{tx},
94 : 89924 : nFee{fee},
95 : 89924 : nTxWeight{GetTransactionWeight(*tx)},
96 : 89924 : nUsageSize{RecursiveDynamicUsage(tx)},
97 : 89924 : nTime{time},
98 : 89924 : entry_sequence{entry_sequence},
99 : 89924 : entryHeight{entry_height},
100 : 89924 : spendsCoinbase{spends_coinbase},
101 : 89924 : sigOpCost{sigops_cost},
102 : 89924 : m_modified_fee{nFee},
103 [ + - ]: 89924 : lockPoints{lp} {}
104 : :
105 : : CTxMemPoolEntry& operator=(const CTxMemPoolEntry&) = delete;
106 : : CTxMemPoolEntry(CTxMemPoolEntry&&) = default;
107 : : CTxMemPoolEntry& operator=(CTxMemPoolEntry&&) = delete;
108 : :
109 [ + - + - : 148556770 : const CTransaction& GetTx() const { return *this->tx; }
- + + - +
- - + + +
+ + - - +
- + - + +
- + - + +
+ + - +
+ ][ + + +
+ + + ][ +
+ + - #
# ][ + + #
# # # # #
# # ][ - -
- - + - +
- - + # #
# # # # #
# # # # #
# # # # #
# # # # #
# # ][ - -
+ - + - +
- + - + -
+ - + - +
- ]
110 [ + - + - : 712606 : CTransactionRef GetSharedTx() const { return this->tx; }
+ - + - +
- + - - -
- - ][ + -
+ + # # #
# ][ + - +
- + - + -
# # # # #
# # # ][ +
- + - + -
+ - + - +
- + - + -
+ - + - +
- + - + -
+ - + - +
- + - ]
[ + - ][ + -
+ - + - +
- + - + -
+ - ][ + -
+ - - - -
- - - -
- ]
111 [ + - + - : 58173 : const CAmount& GetFee() const { return nFee; }
+ - + - +
- + - + -
+ - ]
112 : 12612197 : int32_t GetTxSize() const
113 : : {
114 : 12612197 : return GetVirtualTransactionSize(nTxWeight, sigOpCost, ::nBytesPerSigOp);
115 : : }
116 : 25876 : int32_t GetAdjustedWeight() const { return GetSigOpsAdjustedWeight(nTxWeight, sigOpCost, ::nBytesPerSigOp); }
117 [ + + ]: 19229 : int32_t GetTxWeight() const { return nTxWeight; }
118 [ + + - - ]: 94866 : std::chrono::seconds GetTime() const { return std::chrono::seconds{nTime}; }
[ + - # # ]
119 [ + - ]: 81466 : unsigned int GetHeight() const { return entryHeight; }
120 [ + + + - ]: 39933 : uint64_t GetSequence() const { return entry_sequence; }
121 [ + + ]: 92274 : int64_t GetSigOpCost() const { return sigOpCost; }
122 [ + - ][ + - : 622400 : CAmount GetModifiedFee() const { return m_modified_fee; }
+ - + - ]
[ + - + - ]
123 [ + + ]: 11942379 : size_t DynamicMemoryUsage() const { return nUsageSize; }
124 [ + - ]: 29340 : const LockPoints& GetLockPoints() const { return lockPoints; }
125 : :
126 : : // Updates the modified fees with descendants/ancestors.
127 : 299 : void UpdateModifiedFee(CAmount fee_diff)
128 : : {
129 : 299 : m_modified_fee = SaturatingAdd(m_modified_fee, fee_diff);
130 : : }
131 : :
132 : : // Update the LockPoints after a reorg
133 : 223 : void UpdateLockPoints(const LockPoints& lp) const
134 : : {
135 : 223 : lockPoints = lp;
136 : : }
137 : :
138 [ + + ]: 27960 : bool GetSpendsCoinbase() const { return spendsCoinbase; }
139 : :
140 : : mutable size_t idx_randomized; //!< Index in mempool's txns_randomized
141 : : mutable Epoch::Marker m_epoch_marker; //!< epoch when last touched, useful for graph algorithms
142 : : };
143 : :
144 : : using CTxMemPoolEntryRef = CTxMemPoolEntry::CTxMemPoolEntryRef;
145 : :
146 : 753028 : struct TransactionInfo {
147 : : const CTransactionRef m_tx;
148 : : /* The fee the transaction paid */
149 : : const CAmount m_fee;
150 : : /**
151 : : * The virtual transaction size.
152 : : *
153 : : * This is a policy field which considers the sigop cost of the
154 : : * transaction as well as its weight, and reinterprets it as bytes.
155 : : *
156 : : * It is the primary metric by which the mining algorithm selects
157 : : * transactions.
158 : : */
159 : : const int64_t m_virtual_transaction_size;
160 : : /* The block height the transaction entered the mempool */
161 : : const unsigned int txHeight;
162 : :
163 : 96069 : TransactionInfo(const CTransactionRef& tx, const CAmount& fee, const int64_t vsize, const unsigned int height)
164 : 192138 : : m_tx{tx},
165 : 96069 : m_fee{fee},
166 : 96069 : m_virtual_transaction_size{vsize},
167 : 96069 : txHeight{height} {}
168 : : };
169 : :
170 [ - - + - ]: 783598 : struct RemovedMempoolTransactionInfo {
[ - - ]
171 : : TransactionInfo info;
172 : 46094 : explicit RemovedMempoolTransactionInfo(const CTxMemPoolEntry& entry)
173 [ + - + - : 184376 : : info{entry.GetSharedTx(), entry.GetFee(), entry.GetTxSize(), entry.GetHeight()} {}
+ - + - ]
174 : : };
175 : :
176 [ + - - - : 199900 : struct NewMempoolTransactionInfo {
+ - - - ]
[ + - - - ]
[ + - + -
+ - + - +
- + - - -
- - - - ]
177 : : TransactionInfo info;
178 : : /*
179 : : * This boolean indicates whether the transaction was added
180 : : * without enforcing mempool fee limits.
181 : : */
182 : : const bool m_mempool_limit_bypassed;
183 : : /* This boolean indicates whether the transaction is part of a package. */
184 : : const bool m_submitted_in_package;
185 : : /*
186 : : * This boolean indicates whether the blockchain is up to date when the
187 : : * transaction is added to the mempool.
188 : : */
189 : : const bool m_chainstate_is_current;
190 : : /* Indicates whether the transaction has unconfirmed parents. */
191 : : const bool m_has_no_mempool_parents;
192 : :
193 : 49975 : explicit NewMempoolTransactionInfo(const CTransactionRef& tx, const CAmount& fee,
194 : : const int64_t vsize, const unsigned int height,
195 : : const bool mempool_limit_bypassed, const bool submitted_in_package,
196 : : const bool chainstate_is_current,
197 : : const bool has_no_mempool_parents)
198 [ + - + - ]: 49975 : : info{tx, fee, vsize, height},
[ + - + -
+ - ]
199 : 49975 : m_mempool_limit_bypassed{mempool_limit_bypassed},
200 : 49975 : m_submitted_in_package{submitted_in_package},
201 : 49975 : m_chainstate_is_current{chainstate_is_current},
202 [ + - + - ]: 49975 : m_has_no_mempool_parents{has_no_mempool_parents} {}
[ + - + -
+ - ]
203 : : };
204 : :
205 : : #endif // BITCOIN_KERNEL_MEMPOOL_ENTRY_H
|