Skip to content

Commit 818075a

Browse files
committed
Create new mutex for orphans, no cs_main in PLV::BlockConnected
This should (marginally) speed up validationinterface queue draining by avoiding a cs_main lock in one client.
1 parent df71819 commit 818075a

File tree

1 file changed

+22
-14
lines changed

1 file changed

+22
-14
lines changed

src/net_processing.cpp

Lines changed: 22 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -51,12 +51,13 @@ struct COrphanTx {
5151
NodeId fromPeer;
5252
int64_t nTimeExpire;
5353
};
54-
std::map<uint256, COrphanTx> mapOrphanTransactions GUARDED_BY(cs_main);
55-
std::map<COutPoint, std::set<std::map<uint256, COrphanTx>::iterator, IteratorComparator>> mapOrphanTransactionsByPrev GUARDED_BY(cs_main);
56-
void EraseOrphansFor(NodeId peer) EXCLUSIVE_LOCKS_REQUIRED(cs_main);
54+
static CCriticalSection g_cs_orphans;
55+
std::map<uint256, COrphanTx> mapOrphanTransactions GUARDED_BY(g_cs_orphans);
56+
std::map<COutPoint, std::set<std::map<uint256, COrphanTx>::iterator, IteratorComparator>> mapOrphanTransactionsByPrev GUARDED_BY(g_cs_orphans);
57+
void EraseOrphansFor(NodeId peer);
5758

58-
static size_t vExtraTxnForCompactIt = 0;
59-
static std::vector<std::pair<uint256, CTransactionRef>> vExtraTxnForCompact GUARDED_BY(cs_main);
59+
static size_t vExtraTxnForCompactIt GUARDED_BY(g_cs_orphans) = 0;
60+
static std::vector<std::pair<uint256, CTransactionRef>> vExtraTxnForCompact GUARDED_BY(g_cs_orphans);
6061

6162
static const uint64_t RANDOMIZER_ID_ADDRESS_RELAY = 0x3cac0035b5866b90ULL; // SHA256("main address relay")[0:8]
6263

@@ -127,7 +128,7 @@ namespace {
127128
int g_outbound_peers_with_protect_from_disconnect = 0;
128129

129130
/** When our tip was last updated. */
130-
int64_t g_last_tip_update = 0;
131+
std::atomic<int64_t> g_last_tip_update(0);
131132

132133
/** Relay map, protected by cs_main. */
133134
typedef std::map<uint256, CTransactionRef> MapRelay;
@@ -631,7 +632,7 @@ bool GetNodeStateStats(NodeId nodeid, CNodeStateStats &stats) {
631632
// mapOrphanTransactions
632633
//
633634

634-
void AddToCompactExtraTransactions(const CTransactionRef& tx) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
635+
void AddToCompactExtraTransactions(const CTransactionRef& tx) EXCLUSIVE_LOCKS_REQUIRED(g_cs_orphans)
635636
{
636637
size_t max_extra_txn = gArgs.GetArg("-blockreconstructionextratxn", DEFAULT_BLOCK_RECONSTRUCTION_EXTRA_TXN);
637638
if (max_extra_txn <= 0)
@@ -642,7 +643,7 @@ void AddToCompactExtraTransactions(const CTransactionRef& tx) EXCLUSIVE_LOCKS_RE
642643
vExtraTxnForCompactIt = (vExtraTxnForCompactIt + 1) % max_extra_txn;
643644
}
644645

645-
bool AddOrphanTx(const CTransactionRef& tx, NodeId peer) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
646+
bool AddOrphanTx(const CTransactionRef& tx, NodeId peer) EXCLUSIVE_LOCKS_REQUIRED(g_cs_orphans)
646647
{
647648
const uint256& hash = tx->GetHash();
648649
if (mapOrphanTransactions.count(hash))
@@ -675,7 +676,7 @@ bool AddOrphanTx(const CTransactionRef& tx, NodeId peer) EXCLUSIVE_LOCKS_REQUIRE
675676
return true;
676677
}
677678

678-
int static EraseOrphanTx(uint256 hash) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
679+
int static EraseOrphanTx(uint256 hash) EXCLUSIVE_LOCKS_REQUIRED(g_cs_orphans)
679680
{
680681
std::map<uint256, COrphanTx>::iterator it = mapOrphanTransactions.find(hash);
681682
if (it == mapOrphanTransactions.end())
@@ -695,6 +696,7 @@ int static EraseOrphanTx(uint256 hash) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
695696

696697
void EraseOrphansFor(NodeId peer)
697698
{
699+
LOCK(g_cs_orphans);
698700
int nErased = 0;
699701
std::map<uint256, COrphanTx>::iterator iter = mapOrphanTransactions.begin();
700702
while (iter != mapOrphanTransactions.end())
@@ -709,8 +711,10 @@ void EraseOrphansFor(NodeId peer)
709711
}
710712

711713

712-
unsigned int LimitOrphanTxSize(unsigned int nMaxOrphans) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
714+
unsigned int LimitOrphanTxSize(unsigned int nMaxOrphans)
713715
{
716+
LOCK(g_cs_orphans);
717+
714718
unsigned int nEvicted = 0;
715719
static int64_t nNextSweep;
716720
int64_t nNow = GetTime();
@@ -804,7 +808,7 @@ PeerLogicValidation::PeerLogicValidation(CConnman* connmanIn, CScheduler &schedu
804808
}
805809

806810
void PeerLogicValidation::BlockConnected(const std::shared_ptr<const CBlock>& pblock, const CBlockIndex* pindex, const std::vector<CTransactionRef>& vtxConflicted) {
807-
LOCK(cs_main);
811+
LOCK(g_cs_orphans);
808812

809813
std::vector<uint256> vOrphanErase;
810814

@@ -971,9 +975,13 @@ bool static AlreadyHave(const CInv& inv) EXCLUSIVE_LOCKS_REQUIRED(cs_main)
971975
recentRejects->reset();
972976
}
973977

978+
{
979+
LOCK(g_cs_orphans);
980+
if (mapOrphanTransactions.count(inv.hash)) return true;
981+
}
982+
974983
return recentRejects->contains(inv.hash) ||
975984
mempool.exists(inv.hash) ||
976-
mapOrphanTransactions.count(inv.hash) ||
977985
pcoinsTip->HaveCoinInCache(COutPoint(inv.hash, 0)) || // Best effort: only try output 0 and 1
978986
pcoinsTip->HaveCoinInCache(COutPoint(inv.hash, 1));
979987
}
@@ -2101,7 +2109,7 @@ bool static ProcessMessage(CNode* pfrom, const std::string& strCommand, CDataStr
21012109
CInv inv(MSG_TX, tx.GetHash());
21022110
pfrom->AddInventoryKnown(inv);
21032111

2104-
LOCK(cs_main);
2112+
LOCK2(cs_main, g_cs_orphans);
21052113

21062114
bool fMissingInputs = false;
21072115
CValidationState state;
@@ -2324,7 +2332,7 @@ bool static ProcessMessage(CNode* pfrom, const std::string& strCommand, CDataStr
23242332
bool fBlockReconstructed = false;
23252333

23262334
{
2327-
LOCK(cs_main);
2335+
LOCK2(cs_main, g_cs_orphans);
23282336
// If AcceptBlockHeader returned true, it set pindex
23292337
assert(pindex);
23302338
UpdateBlockAvailability(pfrom->GetId(), pindex->GetBlockHash());

0 commit comments

Comments
 (0)