]>
Commit | Line | Data |
---|---|---|
319b1160 | 1 | // Copyright (c) 2009-2010 Satoshi Nakamoto |
f914f1a7 | 2 | // Copyright (c) 2009-2014 The Bitcoin Core developers |
7329fdd1 | 3 | // Distributed under the MIT software license, see the accompanying |
319b1160 | 4 | // file COPYING or http://www.opensource.org/licenses/mit-license.php. |
093303a8 | 5 | |
319b1160 GA |
6 | #ifndef BITCOIN_TXMEMPOOL_H |
7 | #define BITCOIN_TXMEMPOOL_H | |
8 | ||
93a18a36 GA |
9 | #include <list> |
10 | ||
8b78a819 T |
11 | #include "addressindex.h" |
12 | #include "spentindex.h" | |
eda37330 | 13 | #include "amount.h" |
a0fa20a1 | 14 | #include "coins.h" |
d2270111 | 15 | #include "primitives/transaction.h" |
51ed9ec9 | 16 | #include "sync.h" |
319b1160 | 17 | |
e328fa32 AH |
18 | #undef foreach |
19 | #include "boost/multi_index_container.hpp" | |
20 | #include "boost/multi_index/ordered_index.hpp" | |
21 | ||
41f170fd MT |
22 | #include "pbaas/reserves.h" |
23 | ||
fa736190 CF |
24 | class CAutoFile; |
25 | ||
c1c9d5b4 CL |
26 | inline double AllowFreeThreshold() |
27 | { | |
28 | return COIN * 144 / 250; | |
29 | } | |
30 | ||
171ca774 GA |
31 | inline bool AllowFree(double dPriority) |
32 | { | |
33 | // Large (in bytes) low-priority (new, small-coin) transactions | |
34 | // need a fee. | |
c1c9d5b4 | 35 | return dPriority > AllowFreeThreshold(); |
171ca774 GA |
36 | } |
37 | ||
a0fa20a1 PW |
38 | /** Fake height value used in CCoins to signify they are only in the memory pool (since 0.8) */ |
39 | static const unsigned int MEMPOOL_HEIGHT = 0x7FFFFFFF; | |
40 | ||
7329fdd1 | 41 | /** |
4d707d51 GA |
42 | * CTxMemPool stores these: |
43 | */ | |
44 | class CTxMemPoolEntry | |
45 | { | |
46 | private: | |
47 | CTransaction tx; | |
7329fdd1 MF |
48 | CAmount nFee; //! Cached to avoid expensive parent-transaction lookups |
49 | size_t nTxSize; //! ... and avoid recomputing tx size | |
50 | size_t nModSize; //! ... and modified size for priority | |
bde5c8b0 | 51 | size_t nUsageSize; //! ... and total memory usage |
e328fa32 | 52 | CFeeRate feeRate; //! ... and fee per kB |
7329fdd1 MF |
53 | int64_t nTime; //! Local time when entering the mempool |
54 | double dPriority; //! Priority when entering the mempool | |
55 | unsigned int nHeight; //! Chain height when entering the mempool | |
b649e039 | 56 | bool hadNoDependencies; //! Not dependent on any other txs when it entered the mempool |
a4b25180 | 57 | bool spendsCoinbase; //! keep track of transactions that spend a coinbase |
41f170fd | 58 | bool hasReserve; //! keep track of transactions that spend a coinbase |
34a64fe0 | 59 | uint32_t nBranchId; //! Branch ID this transaction is known to commit to, cached for efficiency |
4d707d51 GA |
60 | |
61 | public: | |
a372168e | 62 | CTxMemPoolEntry(const CTransaction& _tx, const CAmount& _nFee, |
a4b25180 | 63 | int64_t _nTime, double _dPriority, unsigned int _nHeight, |
41f170fd | 64 | bool poolHasNoInputsOf, bool spendsCoinbase, uint32_t nBranchId, bool hasreserve=false); |
4d707d51 GA |
65 | CTxMemPoolEntry(); |
66 | CTxMemPoolEntry(const CTxMemPoolEntry& other); | |
67 | ||
68 | const CTransaction& GetTx() const { return this->tx; } | |
69 | double GetPriority(unsigned int currentHeight) const; | |
a372168e | 70 | CAmount GetFee() const { return nFee; } |
e328fa32 | 71 | CFeeRate GetFeeRate() const { return feeRate; } |
4d707d51 GA |
72 | size_t GetTxSize() const { return nTxSize; } |
73 | int64_t GetTime() const { return nTime; } | |
74 | unsigned int GetHeight() const { return nHeight; } | |
b649e039 | 75 | bool WasClearAtEntry() const { return hadNoDependencies; } |
bde5c8b0 | 76 | size_t DynamicMemoryUsage() const { return nUsageSize; } |
a4b25180 SD |
77 | |
78 | bool GetSpendsCoinbase() const { return spendsCoinbase; } | |
34a64fe0 | 79 | uint32_t GetValidatedBranchId() const { return nBranchId; } |
4d707d51 GA |
80 | }; |
81 | ||
e328fa32 AH |
82 | // extracts a TxMemPoolEntry's transaction hash |
83 | struct mempoolentry_txid | |
84 | { | |
85 | typedef uint256 result_type; | |
86 | result_type operator() (const CTxMemPoolEntry &entry) const | |
87 | { | |
88 | return entry.GetTx().GetHash(); | |
89 | } | |
90 | }; | |
91 | ||
92 | class CompareTxMemPoolEntryByFee | |
93 | { | |
94 | public: | |
95 | bool operator()(const CTxMemPoolEntry& a, const CTxMemPoolEntry& b) | |
96 | { | |
97 | if (a.GetFeeRate() == b.GetFeeRate()) | |
98 | return a.GetTime() < b.GetTime(); | |
99 | return a.GetFeeRate() > b.GetFeeRate(); | |
100 | } | |
4d707d51 GA |
101 | }; |
102 | ||
b649e039 | 103 | class CBlockPolicyEstimator; |
171ca774 | 104 | |
e8ea0fd1 | 105 | /** An inpoint - a combination of a transaction and an index n into its vin */ |
106 | class CInPoint | |
107 | { | |
108 | public: | |
109 | const CTransaction* ptx; | |
110 | uint32_t n; | |
111 | ||
112 | CInPoint() { SetNull(); } | |
113 | CInPoint(const CTransaction* ptxIn, uint32_t nIn) { ptx = ptxIn; n = nIn; } | |
114 | void SetNull() { ptx = NULL; n = (uint32_t) -1; } | |
115 | bool IsNull() const { return (ptx == NULL && n == (uint32_t) -1); } | |
bde5c8b0 | 116 | size_t DynamicMemoryUsage() const { return 0; } |
e8ea0fd1 | 117 | }; |
118 | ||
7329fdd1 | 119 | /** |
319b1160 GA |
120 | * CTxMemPool stores valid-according-to-the-current-best-chain |
121 | * transactions that may be included in the next block. | |
122 | * | |
123 | * Transactions are added when they are seen on the network | |
124 | * (or created by the local node), but not all transactions seen | |
125 | * are added to the pool: if a new transaction double-spends | |
126 | * an input of a transaction in the pool, it is dropped, | |
127 | * as are non-standard transactions. | |
128 | */ | |
129 | class CTxMemPool | |
130 | { | |
131 | private: | |
934fd197 | 132 | uint32_t nCheckFrequency; //! Value n means that n times in 2^32 we check. |
319b1160 | 133 | unsigned int nTransactionsUpdated; |
b649e039 | 134 | CBlockPolicyEstimator* minerPolicyEstimator; |
319b1160 | 135 | |
43873535 | 136 | uint64_t totalTxSize = 0; //! sum of all mempool tx' byte sizes |
bde5c8b0 | 137 | uint64_t cachedInnerUsage; //! sum of dynamic memory usage of all the map elements (NOT the maps themselves) |
13fc83c7 | 138 | |
9669920f | 139 | std::map<uint256, const CTransaction*> mapSproutNullifiers; |
685e936c EOW |
140 | std::map<uint256, const CTransaction*> mapSaplingNullifiers; |
141 | ||
41f170fd MT |
142 | std::map<uint256, std::pair<double, CAmount> > mapDeltas; |
143 | std::map<uint256, CReserveTransactionDescriptor> mapReserveTransactions; // all reserve transactions in the mempool go here | |
144 | ||
28d20bdb | 145 | void checkNullifiers(ShieldedType type) const; |
685e936c | 146 | |
319b1160 | 147 | public: |
e328fa32 AH |
148 | typedef boost::multi_index_container< |
149 | CTxMemPoolEntry, | |
150 | boost::multi_index::indexed_by< | |
151 | // sorted by txid | |
152 | boost::multi_index::ordered_unique<mempoolentry_txid>, | |
153 | // sorted by fee rate | |
154 | boost::multi_index::ordered_non_unique< | |
155 | boost::multi_index::identity<CTxMemPoolEntry>, | |
156 | CompareTxMemPoolEntryByFee | |
157 | > | |
158 | > | |
159 | > indexed_transaction_set; | |
160 | ||
319b1160 | 161 | mutable CCriticalSection cs; |
e328fa32 | 162 | indexed_transaction_set mapTx; |
8b78a819 T |
163 | |
164 | private: | |
165 | typedef std::map<CMempoolAddressDeltaKey, CMempoolAddressDelta, CMempoolAddressDeltaKeyCompare> addressDeltaMap; | |
166 | addressDeltaMap mapAddress; | |
167 | ||
168 | typedef std::map<uint256, std::vector<CMempoolAddressDeltaKey> > addressDeltaMapInserted; | |
169 | addressDeltaMapInserted mapAddressInserted; | |
170 | ||
171 | typedef std::map<CSpentIndexKey, CSpentIndexValue, CSpentIndexKeyCompare> mapSpentIndex; | |
172 | mapSpentIndex mapSpent; | |
173 | ||
174 | typedef std::map<uint256, std::vector<CSpentIndexKey> > mapSpentIndexInserted; | |
175 | mapSpentIndexInserted mapSpentInserted; | |
176 | ||
177 | public: | |
319b1160 GA |
178 | std::map<COutPoint, CInPoint> mapNextTx; |
179 | ||
13fc83c7 | 180 | CTxMemPool(const CFeeRate& _minRelayFee); |
171ca774 | 181 | ~CTxMemPool(); |
319b1160 | 182 | |
7329fdd1 | 183 | /** |
319b1160 GA |
184 | * If sanity-checking is turned on, check makes sure the pool is |
185 | * consistent (does not contain two transactions that spend the same inputs, | |
186 | * all inputs are in the mapNextTx array). If sanity-checking is turned off, | |
187 | * check does nothing. | |
188 | */ | |
d0867acb | 189 | void check(const CCoinsViewCache *pcoins) const; |
a0c977ca | 190 | void setSanityCheck(double dFrequency = 1.0) { nCheckFrequency = static_cast<uint32_t>(dFrequency * 4294967295.0); } |
319b1160 | 191 | |
b649e039 | 192 | bool addUnchecked(const uint256& hash, const CTxMemPoolEntry &entry, bool fCurrentEstimate = true); |
8b78a819 T |
193 | void addAddressIndex(const CTxMemPoolEntry &entry, const CCoinsViewCache &view); |
194 | bool getAddressIndex(std::vector<std::pair<uint160, int> > &addresses, | |
195 | std::vector<std::pair<CMempoolAddressDeltaKey, CMempoolAddressDelta> > &results); | |
196 | bool removeAddressIndex(const uint256 txhash); | |
197 | ||
198 | void addSpentIndex(const CTxMemPoolEntry &entry, const CCoinsViewCache &view); | |
199 | bool getSpentIndex(CSpentIndexKey &key, CSpentIndexValue &value); | |
200 | bool removeSpentIndex(const uint256 txhash); | |
93a18a36 | 201 | void remove(const CTransaction &tx, std::list<CTransaction>& removed, bool fRecursive = false); |
98d2f090 | 202 | void removeWithAnchor(const uint256 &invalidRoot, ShieldedType type); |
233c9eb6 | 203 | void removeForReorg(const CCoinsViewCache *pcoins, unsigned int nMemPoolHeight, int flags); |
93a18a36 | 204 | void removeConflicts(const CTransaction &tx, std::list<CTransaction>& removed); |
9bb37bf0 | 205 | void removeExpired(unsigned int nBlockHeight); |
171ca774 | 206 | void removeForBlock(const std::vector<CTransaction>& vtx, unsigned int nBlockHeight, |
b649e039 | 207 | std::list<CTransaction>& conflicts, bool fCurrentEstimate = true); |
34a64fe0 | 208 | void removeWithoutBranchId(uint32_t nMemPoolBranchId); |
319b1160 GA |
209 | void clear(); |
210 | void queryHashes(std::vector<uint256>& vtxid); | |
211 | void pruneSpent(const uint256& hash, CCoins &coins); | |
212 | unsigned int GetTransactionsUpdated() const; | |
213 | void AddTransactionsUpdated(unsigned int n); | |
b649e039 AM |
214 | /** |
215 | * Check that none of this transactions inputs are in the mempool, and thus | |
216 | * the tx is not dependent on other mempool transactions to be included in a block. | |
217 | */ | |
218 | bool HasNoInputsOf(const CTransaction& tx) const; | |
319b1160 | 219 | |
2a72d459 | 220 | /** Affect CreateNewBlock prioritisation of transactions */ |
41f170fd | 221 | void PrioritiseTransaction(const uint256 &hash, const std::string strHash, double dPriorityDelta, const CAmount& nFeeDelta); |
47aecf2f | 222 | bool PrioritiseReserveTransaction(const CReserveTransactionDescriptor &txDesc, const CCurrencyState ¤cyState); |
223 | bool IsKnownReserveTransaction(const uint256 &hash, CReserveTransactionDescriptor &txDesc); // know to be reserve transaction, get descriptor, update mempool | |
a372168e | 224 | void ApplyDeltas(const uint256 hash, double &dPriorityDelta, CAmount &nFeeDelta); |
2a72d459 LD |
225 | void ClearPrioritisation(const uint256 hash); |
226 | ||
28d20bdb | 227 | bool nullifierExists(const uint256& nullifier, ShieldedType type) const; |
685e936c | 228 | |
319b1160 GA |
229 | unsigned long size() |
230 | { | |
231 | LOCK(cs); | |
232 | return mapTx.size(); | |
233 | } | |
bde5c8b0 | 234 | |
6f2c26a4 JG |
235 | uint64_t GetTotalTxSize() |
236 | { | |
237 | LOCK(cs); | |
238 | return totalTxSize; | |
239 | } | |
319b1160 | 240 | |
b649e039 | 241 | bool exists(uint256 hash) const |
319b1160 GA |
242 | { |
243 | LOCK(cs); | |
244 | return (mapTx.count(hash) != 0); | |
245 | } | |
246 | ||
247 | bool lookup(uint256 hash, CTransaction& result) const; | |
171ca774 | 248 | |
7329fdd1 | 249 | /** Estimate fee rate needed to get into the next nBlocks */ |
171ca774 | 250 | CFeeRate estimateFee(int nBlocks) const; |
7329fdd1 MF |
251 | |
252 | /** Estimate priority needed to get into the next nBlocks */ | |
171ca774 | 253 | double estimatePriority(int nBlocks) const; |
7329fdd1 MF |
254 | |
255 | /** Write/Read estimates to disk */ | |
171ca774 GA |
256 | bool WriteFeeEstimates(CAutoFile& fileout) const; |
257 | bool ReadFeeEstimates(CAutoFile& filein); | |
bde5c8b0 PW |
258 | |
259 | size_t DynamicMemoryUsage() const; | |
a0c977ca S |
260 | |
261 | /** Return nCheckFrequency */ | |
262 | uint32_t GetCheckFrequency() const { | |
263 | return nCheckFrequency; | |
264 | } | |
319b1160 GA |
265 | }; |
266 | ||
7329fdd1 MF |
267 | /** |
268 | * CCoinsView that brings transactions from a memorypool into view. | |
269 | * It does not check for spendings by memory pool transactions. | |
270 | */ | |
a0fa20a1 PW |
271 | class CCoinsViewMemPool : public CCoinsViewBacked |
272 | { | |
273 | protected: | |
274 | CTxMemPool &mempool; | |
275 | ||
276 | public: | |
7c70438d | 277 | CCoinsViewMemPool(CCoinsView *baseIn, CTxMemPool &mempoolIn); |
28d20bdb | 278 | bool GetNullifier(const uint256 &txid, ShieldedType type) const; |
a3dc587a DK |
279 | bool GetCoins(const uint256 &txid, CCoins &coins) const; |
280 | bool HaveCoins(const uint256 &txid) const; | |
a0fa20a1 PW |
281 | }; |
282 | ||
093303a8 | 283 | #endif // BITCOIN_TXMEMPOOL_H |