From 3c665065f132fd80ea3b1733785b98e45c8b371e Mon Sep 17 00:00:00 2001 From: TheCharlatan Date: Thu, 22 Aug 2024 22:22:01 +0200 Subject: [PATCH] node: Track last block that received a blockTip notification --- src/node/interfaces.cpp | 10 ++++++---- src/node/kernel_notifications.cpp | 6 ++++++ src/node/kernel_notifications.h | 12 +++++++++++- 3 files changed, 23 insertions(+), 5 deletions(-) diff --git a/src/node/interfaces.cpp b/src/node/interfaces.cpp index 5087c300ed992..1a0d1fdde435e 100644 --- a/src/node/interfaces.cpp +++ b/src/node/interfaces.cpp @@ -34,6 +34,7 @@ #include #include #include +#include #include #include #include @@ -879,14 +880,14 @@ class MinerImpl : public Mining // std::chrono does not check against overflow if (deadline < now) deadline = std::chrono::steady_clock::time_point::max(); { - WAIT_LOCK(g_best_block_mutex, lock); - while ((g_best_block == uint256() || g_best_block == current_tip) && !chainman().m_interrupt) { + WAIT_LOCK(notifications().m_tip_block_mutex, lock); + while ((notifications().m_tip_block == uint256() || notifications().m_tip_block == current_tip) && !chainman().m_interrupt) { now = std::chrono::steady_clock::now(); if (now >= deadline) break; - g_best_block_cv.wait_until(lock, std::min(deadline, now + tick)); + notifications().m_tip_block_cv.wait_until(lock, std::min(deadline, now + tick)); } } - // Must release g_best_block_mutex before locking cs_main, to avoid deadlocks. + // Must release m_tip_block_mutex before locking cs_main, to avoid deadlocks. LOCK(::cs_main); return BlockRef{chainman().ActiveChain().Tip()->GetBlockHash(), chainman().ActiveChain().Tip()->nHeight}; } @@ -923,6 +924,7 @@ class MinerImpl : public Mining NodeContext* context() override { return &m_node; } ChainstateManager& chainman() { return *Assert(m_node.chainman); } + KernelNotifications& notifications() { return *Assert(m_node.notifications); } NodeContext& m_node; }; } // namespace diff --git a/src/node/kernel_notifications.cpp b/src/node/kernel_notifications.cpp index 9894052a3a0ef..9b41c00404c10 100644 --- a/src/node/kernel_notifications.cpp +++ b/src/node/kernel_notifications.cpp @@ -50,6 +50,12 @@ namespace node { kernel::InterruptResult KernelNotifications::blockTip(SynchronizationState state, CBlockIndex& index) { + { + LOCK(m_tip_block_mutex); + m_tip_block= index.GetBlockHash(); + m_tip_block_cv.notify_all(); + } + uiInterface.NotifyBlockTip(state, &index); if (m_stop_at_height && index.nHeight >= m_stop_at_height) { if (!m_shutdown()) { diff --git a/src/node/kernel_notifications.h b/src/node/kernel_notifications.h index e37f4d4e1e4bc..9ff980ea56dfd 100644 --- a/src/node/kernel_notifications.h +++ b/src/node/kernel_notifications.h @@ -7,6 +7,10 @@ #include +#include +#include +#include + #include #include @@ -34,7 +38,7 @@ class KernelNotifications : public kernel::Notifications KernelNotifications(util::SignalInterrupt& shutdown, std::atomic& exit_status, node::Warnings& warnings) : m_shutdown(shutdown), m_exit_status{exit_status}, m_warnings{warnings} {} - [[nodiscard]] kernel::InterruptResult blockTip(SynchronizationState state, CBlockIndex& index) override; + [[nodiscard]] kernel::InterruptResult blockTip(SynchronizationState state, CBlockIndex& index) override EXCLUSIVE_LOCKS_REQUIRED(!m_tip_block_mutex); void headerTip(SynchronizationState state, int64_t height, int64_t timestamp, bool presync) override; @@ -52,6 +56,12 @@ class KernelNotifications : public kernel::Notifications int m_stop_at_height{DEFAULT_STOPATHEIGHT}; //! Useful for tests, can be set to false to avoid shutdown on fatal error. bool m_shutdown_on_fatal_error{true}; + + Mutex m_tip_block_mutex; + std::condition_variable m_tip_block_cv; + //! The block for which the last blockTip notification was received for. + uint256 m_tip_block; + private: util::SignalInterrupt& m_shutdown; std::atomic& m_exit_status;