aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorJesse Cohen <jc@jc.lol>2018-04-15 11:22:28 -0400
committerfanquake <fanquake@gmail.com>2018-05-18 14:10:39 +0800
commitacdf4338221e35d5ec7b299bb18ccd953e28c985 (patch)
treee873d3583a965dd667ca49a553e5ad61d996c5a7 /src
parent5ff571e90c9fa71e189863e9cb21d15d5991f7da (diff)
downloadbitcoin-acdf4338221e35d5ec7b299bb18ccd953e28c985.tar.xz
Hold cs_main while calling UpdatedBlockTip() and ui.NotifyBlockTip
Ensures that callbacks are invoked in the order in which the chain is updated Resolves #12978 GitHub-Pull: #12988 Rebased-From: d86edd3
Diffstat (limited to 'src')
-rw-r--r--src/validation.cpp19
-rw-r--r--src/validationinterface.cpp4
2 files changed, 13 insertions, 10 deletions
diff --git a/src/validation.cpp b/src/validation.cpp
index 1f0ceba70c..f981d2659a 100644
--- a/src/validation.cpp
+++ b/src/validation.cpp
@@ -351,7 +351,7 @@ bool CheckSequenceLocks(const CTransaction &tx, int flags, LockPoints* lp, bool
CBlockIndex* tip = chainActive.Tip();
assert(tip != nullptr);
-
+
CBlockIndex index;
index.pprev = tip;
// CheckSequenceLocks() uses chainActive.Height()+1 to evaluate
@@ -2607,18 +2607,17 @@ bool CChainState::ActivateBestChain(CValidationState &state, const CChainParams&
assert(trace.pblock && trace.pindex);
GetMainSignals().BlockConnected(trace.pblock, trace.pindex, trace.conflictedTxs);
}
- }
- // When we reach this point, we switched to a new tip (stored in pindexNewTip).
- // Notifications/callbacks that can run without cs_main
+ // Notify external listeners about the new tip.
+ // Enqueue while holding cs_main to ensure that UpdatedBlockTip is called in the order in which blocks are connected
+ GetMainSignals().UpdatedBlockTip(pindexNewTip, pindexFork, fInitialDownload);
- // Notify external listeners about the new tip.
- GetMainSignals().UpdatedBlockTip(pindexNewTip, pindexFork, fInitialDownload);
-
- // Always notify the UI if a new block tip was connected
- if (pindexFork != pindexNewTip) {
- uiInterface.NotifyBlockTip(fInitialDownload, pindexNewTip);
+ // Always notify the UI if a new block tip was connected
+ if (pindexFork != pindexNewTip) {
+ uiInterface.NotifyBlockTip(fInitialDownload, pindexNewTip);
+ }
}
+ // When we reach this point, we switched to a new tip (stored in pindexNewTip).
if (nStopAtHeight && pindexNewTip && pindexNewTip->nHeight >= nStopAtHeight) StartShutdown();
diff --git a/src/validationinterface.cpp b/src/validationinterface.cpp
index 928df4fa65..746263f113 100644
--- a/src/validationinterface.cpp
+++ b/src/validationinterface.cpp
@@ -139,6 +139,10 @@ void CMainSignals::MempoolEntryRemoved(CTransactionRef ptx, MemPoolRemovalReason
}
void CMainSignals::UpdatedBlockTip(const CBlockIndex *pindexNew, const CBlockIndex *pindexFork, bool fInitialDownload) {
+ // Dependencies exist that require UpdatedBlockTip events to be delivered in the order in which
+ // the chain actually updates. One way to ensure this is for the caller to invoke this signal
+ // in the same critical section where the chain is updated
+
m_internals->m_schedulerClient.AddToProcessQueue([pindexNew, pindexFork, fInitialDownload, this] {
m_internals->UpdatedBlockTip(pindexNew, pindexFork, fInitialDownload);
});