aboutsummaryrefslogtreecommitdiff
path: root/src/net_processing.cpp
diff options
context:
space:
mode:
authorJohn Newbery <john@johnnewbery.com>2020-07-30 10:30:24 +0100
committerJon Atack <jon@atack.com>2020-08-26 11:57:03 +0200
commit42ca5618cae0fd9ef97d2006b17d896bc58cc17c (patch)
tree5fff6027ccdd33dfb4bec9aefcd3141f40b3686e /src/net_processing.cpp
parent39f1dc944554218911b0945fff7e6d06f3dab284 (diff)
downloadbitcoin-42ca5618cae0fd9ef97d2006b17d896bc58cc17c.tar.xz
[net processing] Split AlreadyHave() into separate block and tx functions
Diffstat (limited to 'src/net_processing.cpp')
-rw-r--r--src/net_processing.cpp78
1 files changed, 36 insertions, 42 deletions
diff --git a/src/net_processing.cpp b/src/net_processing.cpp
index a01514185d..3a0613deeb 100644
--- a/src/net_processing.cpp
+++ b/src/net_processing.cpp
@@ -1422,47 +1422,38 @@ void PeerLogicValidation::BlockChecked(const CBlock& block, const BlockValidatio
//
-bool static AlreadyHave(const CInv& inv, const CTxMemPool& mempool) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
+bool static AlreadyHaveTx(const CInv& inv, const CTxMemPool& mempool) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
{
- switch (inv.type)
+ assert(recentRejects);
+ if (::ChainActive().Tip()->GetBlockHash() != hashRecentRejectsChainTip) {
+ // If the chain tip has changed previously rejected transactions
+ // might be now valid, e.g. due to a nLockTime'd tx becoming valid,
+ // or a double-spend. Reset the rejects filter and give those
+ // txs a second chance.
+ hashRecentRejectsChainTip = ::ChainActive().Tip()->GetBlockHash();
+ recentRejects->reset();
+ }
+
{
- case MSG_TX:
- case MSG_WITNESS_TX:
- case MSG_WTX:
- {
- assert(recentRejects);
- if (::ChainActive().Tip()->GetBlockHash() != hashRecentRejectsChainTip)
- {
- // If the chain tip has changed previously rejected transactions
- // might be now valid, e.g. due to a nLockTime'd tx becoming valid,
- // or a double-spend. Reset the rejects filter and give those
- // txs a second chance.
- hashRecentRejectsChainTip = ::ChainActive().Tip()->GetBlockHash();
- recentRejects->reset();
- }
+ LOCK(g_cs_orphans);
+ if (!inv.IsMsgWtx() && mapOrphanTransactions.count(inv.hash)) {
+ return true;
+ } else if (inv.IsMsgWtx() && g_orphans_by_wtxid.count(inv.hash)) {
+ return true;
+ }
+ }
- {
- LOCK(g_cs_orphans);
- if (!inv.IsMsgWtx() && mapOrphanTransactions.count(inv.hash)) {
- return true;
- } else if (inv.IsMsgWtx() && g_orphans_by_wtxid.count(inv.hash)) {
- return true;
- }
- }
+ {
+ LOCK(g_cs_recent_confirmed_transactions);
+ if (g_recent_confirmed_transactions->contains(inv.hash)) return true;
+ }
- {
- LOCK(g_cs_recent_confirmed_transactions);
- if (g_recent_confirmed_transactions->contains(inv.hash)) return true;
- }
+ return recentRejects->contains(inv.hash) || mempool.exists(ToGenTxid(inv));
+}
- return recentRejects->contains(inv.hash) || mempool.exists(ToGenTxid(inv));
- }
- case MSG_BLOCK:
- case MSG_WITNESS_BLOCK:
- return LookupBlockIndex(inv.hash) != nullptr;
- }
- // Don't know what it is, just say we already got one
- return true;
+bool static AlreadyHaveBlock(const CInv& inv, const CTxMemPool& mempool) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
+{
+ return LookupBlockIndex(inv.hash) != nullptr;
}
void RelayTransaction(const uint256& txid, const uint256& wtxid, const CConnman& connman)
@@ -2670,10 +2661,10 @@ void PeerLogicValidation::ProcessMessage(CNode& pfrom, const std::string& msg_ty
if (inv.IsMsgWtx()) continue;
}
- bool fAlreadyHave = AlreadyHave(inv, m_mempool);
- LogPrint(BCLog::NET, "got inv: %s %s peer=%d\n", inv.ToString(), fAlreadyHave ? "have" : "new", pfrom.GetId());
-
if (inv.type == MSG_BLOCK) {
+ bool fAlreadyHave = AlreadyHaveBlock(inv, m_mempool);
+ LogPrint(BCLog::NET, "got inv: %s %s peer=%d\n", inv.ToString(), fAlreadyHave ? "have" : "new", pfrom.GetId());
+
UpdateBlockAvailability(pfrom.GetId(), inv.hash);
if (!fAlreadyHave && !fImporting && !fReindex && !mapBlocksInFlight.count(inv.hash)) {
// Headers-first is the primary method of announcement on
@@ -2684,6 +2675,9 @@ void PeerLogicValidation::ProcessMessage(CNode& pfrom, const std::string& msg_ty
best_block = &inv.hash;
}
} else {
+ bool fAlreadyHave = AlreadyHaveTx(inv, mempool);
+ LogPrint(BCLog::NET, "got inv: %s %s peer=%d\n", inv.ToString(), fAlreadyHave ? "have" : "new", pfrom.GetId());
+
pfrom.AddKnownTx(inv.hash);
if (fBlocksOnly) {
LogPrint(BCLog::NET, "transaction (%s) inv sent in violation of protocol, disconnecting peer=%d\n", inv.hash.ToString(), pfrom.GetId());
@@ -2963,7 +2957,7 @@ void PeerLogicValidation::ProcessMessage(CNode& pfrom, const std::string& msg_ty
// already; and an adversary can already relay us old transactions
// (older than our recency filter) if trying to DoS us, without any need
// for witness malleation.
- if (!AlreadyHave(CInv(MSG_WTX, wtxid), m_mempool) &&
+ if (!AlreadyHaveTx(CInv(MSG_WTX, wtxid), m_mempool) &&
AcceptToMemoryPool(m_mempool, state, ptx, &lRemovedTxn, false /* bypass_limits */, 0 /* nAbsurdFee */)) {
m_mempool.check(&::ChainstateActive().CoinsTip());
RelayTransaction(tx.GetHash(), tx.GetWitnessHash(), m_connman);
@@ -3017,7 +3011,7 @@ void PeerLogicValidation::ProcessMessage(CNode& pfrom, const std::string& msg_ty
// protocol for getting all unconfirmed parents.
CInv _inv(MSG_TX, parent_txid);
pfrom.AddKnownTx(parent_txid);
- if (!AlreadyHave(_inv, m_mempool)) RequestTx(State(pfrom.GetId()), ToGenTxid(_inv), current_time);
+ if (!AlreadyHaveTx(_inv, m_mempool)) RequestTx(State(pfrom.GetId()), ToGenTxid(_inv), current_time);
}
AddOrphanTx(ptx, pfrom.GetId());
@@ -4568,7 +4562,7 @@ bool PeerLogicValidation::SendMessages(CNode* pto)
// processing at a later time, see below)
tx_process_time.erase(tx_process_time.begin());
CInv inv(gtxid.IsWtxid() ? MSG_WTX : (MSG_TX | GetFetchFlags(*pto)), gtxid.GetHash());
- if (!AlreadyHave(inv, m_mempool)) {
+ if (!AlreadyHaveTx(inv, m_mempool)) {
// If this transaction was last requested more than 1 minute ago,
// then request.
const auto last_request_time = GetTxRequestTime(gtxid);