From 091eda40c984d5a3c34f00b8aa4513b6ef6105af Mon Sep 17 00:00:00 2001 From: Kittywhiskers Van Gogh <63189531+kittywhiskers@users.noreply.github.com> Date: Wed, 1 Aug 2018 13:38:45 -0400 Subject: [PATCH] merge bitcoin#17905: Avoid redundant tx status updates --- src/qt/bitcoin.cpp | 2 +- src/qt/clientmodel.cpp | 10 ++++++++++ src/qt/clientmodel.h | 4 +++- src/qt/test/addressbooktests.cpp | 4 +++- src/qt/test/wallettests.cpp | 2 +- src/qt/transactiontablemodel.cpp | 14 +++++++------- src/qt/walletcontroller.cpp | 10 ++++++---- src/qt/walletcontroller.h | 4 +++- src/qt/walletmodel.cpp | 10 ++++++++-- src/qt/walletmodel.h | 5 ++++- 10 files changed, 46 insertions(+), 19 deletions(-) diff --git a/src/qt/bitcoin.cpp b/src/qt/bitcoin.cpp index fc3c246c29..915863e84d 100644 --- a/src/qt/bitcoin.cpp +++ b/src/qt/bitcoin.cpp @@ -346,7 +346,7 @@ void BitcoinApplication::initializeResult(bool success, interfaces::BlockAndHead window->setClientModel(clientModel, &tip_info); #ifdef ENABLE_WALLET if (WalletModel::isWalletEnabled()) { - m_wallet_controller = new WalletController(m_node, optionsModel, this); + m_wallet_controller = new WalletController(*clientModel, this); window->setWalletController(m_wallet_controller); if (paymentServer) { paymentServer->setOptionsModel(optionsModel); diff --git a/src/qt/clientmodel.cpp b/src/qt/clientmodel.cpp index 2eac328c1e..bbe20f0615 100644 --- a/src/qt/clientmodel.cpp +++ b/src/qt/clientmodel.cpp @@ -137,6 +137,14 @@ void ClientModel::getAllGovernanceObjects(std::vector &obj) m_node.gov().getAllNewerThan(obj, 0); } +int ClientModel::getNumBlocks() const +{ + if (m_cached_num_blocks == -1) { + m_cached_num_blocks = m_node.getNumBlocks(); + } + return m_cached_num_blocks; +} + void ClientModel::updateNumConnections(int numConnections) { Q_EMIT numConnectionsChanged(numConnections); @@ -273,6 +281,8 @@ static void BlockTipChanged(ClientModel *clientmodel, bool initialSync, int heig // cache best headers time and height to reduce future cs_main locks clientmodel->cachedBestHeaderHeight = height; clientmodel->cachedBestHeaderTime = blockTime; + } else { + clientmodel->m_cached_num_blocks = height; } // During initial sync, block notifications, and header notifications from reindexing are both throttled. diff --git a/src/qt/clientmodel.h b/src/qt/clientmodel.h index 330ad8d51f..ef9ec7bc66 100644 --- a/src/qt/clientmodel.h +++ b/src/qt/clientmodel.h @@ -61,6 +61,7 @@ public: //! Return number of connections, default is in- and outbound (total) int getNumConnections(unsigned int flags = CONNECTIONS_ALL) const; + int getNumBlocks() const; int getHeaderTipHeight() const; int64_t getHeaderTipTime() const; @@ -84,9 +85,10 @@ public: bool getProxyInfo(std::string& ip_port) const; - // caches for the best header + // caches for the best header, number of blocks mutable std::atomic cachedBestHeaderHeight; mutable std::atomic cachedBestHeaderTime; + mutable std::atomic m_cached_num_blocks{-1}; private: interfaces::Node& m_node; diff --git a/src/qt/test/addressbooktests.cpp b/src/qt/test/addressbooktests.cpp index ba4b566577..3a7a93c4ac 100644 --- a/src/qt/test/addressbooktests.cpp +++ b/src/qt/test/addressbooktests.cpp @@ -8,6 +8,7 @@ #include #include +#include #include #include #include @@ -105,8 +106,9 @@ void TestAddAddressesToSendBook(interfaces::Node& node) // Initialize relevant QT models. OptionsModel optionsModel(node); + ClientModel clientModel(node, &optionsModel); AddWallet(wallet); - WalletModel walletModel(interfaces::MakeWallet(wallet), node, &optionsModel); + WalletModel walletModel(interfaces::MakeWallet(wallet), clientModel); RemoveWallet(wallet, std::nullopt); EditAddressDialog editAddressDialog(EditAddressDialog::NewSendingAddress); editAddressDialog.setModel(walletModel.getAddressTableModel()); diff --git a/src/qt/test/wallettests.cpp b/src/qt/test/wallettests.cpp index f944c2c366..75df8da71d 100644 --- a/src/qt/test/wallettests.cpp +++ b/src/qt/test/wallettests.cpp @@ -135,7 +135,7 @@ void TestGUI(interfaces::Node& node) TransactionView transactionView; OptionsModel optionsModel(node); ClientModel clientModel(node, &optionsModel); - WalletModel walletModel(interfaces::MakeWallet(wallet), node, &optionsModel);; + WalletModel walletModel(interfaces::MakeWallet(wallet), clientModel);; sendCoinsDialog.setModel(&walletModel); transactionView.setModel(&walletModel); diff --git a/src/qt/transactiontablemodel.cpp b/src/qt/transactiontablemodel.cpp index 31cdd450a3..7c3bc28fcd 100644 --- a/src/qt/transactiontablemodel.cpp +++ b/src/qt/transactiontablemodel.cpp @@ -4,6 +4,7 @@ #include +#include #include #include #include @@ -187,7 +188,7 @@ public: return cachedWallet.size(); } - TransactionRecord *index(interfaces::Wallet& wallet, int numBlocks, int idx) + TransactionRecord *index(interfaces::Wallet& wallet, const int cur_num_blocks, const int idx) { if (idx >= 0 && idx < cachedWallet.size()) { TransactionRecord *rec = &cachedWallet[idx]; @@ -197,8 +198,8 @@ public: // Otherwise, simply re-use the cached status. interfaces::WalletTxStatus wtx; int64_t block_time; - if (rec->statusUpdateNeeded(numBlocks, parent->getChainLockHeight()) && wallet.tryGetTxStatus(rec->hash, wtx, block_time)) { - rec->updateStatus(wtx, numBlocks, parent->getChainLockHeight(), block_time); + if (rec->statusUpdateNeeded(cur_num_blocks, parent->getChainLockHeight()) && wallet.tryGetTxStatus(rec->hash, wtx, block_time)) { + rec->updateStatus(wtx, cur_num_blocks, parent->getChainLockHeight(), block_time); } return rec; } @@ -725,10 +726,9 @@ QVariant TransactionTableModel::headerData(int section, Qt::Orientation orientat QModelIndex TransactionTableModel::index(int row, int column, const QModelIndex &parent) const { Q_UNUSED(parent); - TransactionRecord *data = priv->index(walletModel->wallet(), walletModel->getNumBlocks(), row); - if(data) - { - return createIndex(row, column, priv->index(walletModel->wallet(), walletModel->getNumBlocks(), row)); + TransactionRecord *data = priv->index(walletModel->wallet(), walletModel->clientModel().getNumBlocks(), row); + if (data) { + return createIndex(row, column, data); } return QModelIndex(); } diff --git a/src/qt/walletcontroller.cpp b/src/qt/walletcontroller.cpp index 71194264a7..4782bd47de 100644 --- a/src/qt/walletcontroller.cpp +++ b/src/qt/walletcontroller.cpp @@ -3,6 +3,7 @@ // file COPYING or http://www.opensource.org/licenses/mit-license.php. #include +#include #include #include #include @@ -24,12 +25,13 @@ #include #include -WalletController::WalletController(interfaces::Node& node, OptionsModel* options_model, QObject* parent) +WalletController::WalletController(ClientModel& client_model, QObject* parent) : QObject(parent) , m_activity_thread(new QThread(this)) , m_activity_worker(new QObject) - , m_node(node) - , m_options_model(options_model) + , m_client_model(client_model) + , m_node(client_model.node()) + , m_options_model(client_model.getOptionsModel()) { m_handler_load_wallet = m_node.walletClient().handleLoadWallet([this](std::unique_ptr wallet) { getOrCreateWallet(std::move(wallet)); @@ -103,7 +105,7 @@ WalletModel* WalletController::getOrCreateWallet(std::unique_ptrmoveToThread(thread()); wallet_model->setParent(this); diff --git a/src/qt/walletcontroller.h b/src/qt/walletcontroller.h index e90cca4f46..66fc2a83c4 100644 --- a/src/qt/walletcontroller.h +++ b/src/qt/walletcontroller.h @@ -22,6 +22,7 @@ #include #include +class ClientModel; class OptionsModel; class PlatformStyle; @@ -46,7 +47,7 @@ class WalletController : public QObject void removeAndDeleteWallet(WalletModel* wallet_model); public: - WalletController(interfaces::Node& node, OptionsModel* options_model, QObject* parent); + WalletController(ClientModel& client_model, QObject* parent); ~WalletController(); //! Returns wallet models currently open. @@ -69,6 +70,7 @@ Q_SIGNALS: private: QThread* const m_activity_thread; QObject* const m_activity_worker; + ClientModel& m_client_model; interfaces::Node& m_node; OptionsModel* const m_options_model; mutable QMutex m_mutex; diff --git a/src/qt/walletmodel.cpp b/src/qt/walletmodel.cpp index a497fae136..9b76d7e276 100644 --- a/src/qt/walletmodel.cpp +++ b/src/qt/walletmodel.cpp @@ -10,6 +10,7 @@ #include #include +#include #include #include #include @@ -35,8 +36,13 @@ #include -WalletModel::WalletModel(std::unique_ptr wallet, interfaces::Node& node, OptionsModel *_optionsModel, QObject *parent) : - QObject(parent), m_wallet(std::move(wallet)), m_node(node), optionsModel(_optionsModel), addressTableModel(nullptr), +WalletModel::WalletModel(std::unique_ptr wallet, ClientModel& client_model, QObject *parent) : + QObject(parent), + m_wallet(std::move(wallet)), + m_client_model(client_model), + m_node(client_model.node()), + optionsModel(client_model.getOptionsModel()), + addressTableModel(nullptr), transactionTableModel(nullptr), recentRequestsTableModel(nullptr), cachedEncryptionStatus(Unencrypted), diff --git a/src/qt/walletmodel.h b/src/qt/walletmodel.h index 071afdac0e..801e3b8656 100644 --- a/src/qt/walletmodel.h +++ b/src/qt/walletmodel.h @@ -24,6 +24,7 @@ #include class AddressTableModel; +class ClientModel; class OptionsModel; class RecentRequestsTableModel; class TransactionTableModel; @@ -95,7 +96,7 @@ class WalletModel : public QObject Q_OBJECT public: - explicit WalletModel(std::unique_ptr wallet, interfaces::Node& node, OptionsModel *optionsModel, QObject *parent = nullptr); + explicit WalletModel(std::unique_ptr wallet, ClientModel& client_model, QObject *parent = nullptr); ~WalletModel(); enum StatusCode // Returned by sendCoins @@ -198,6 +199,7 @@ public: interfaces::Node& node() const { return m_node; } interfaces::Wallet& wallet() const { return *m_wallet; } + ClientModel& clientModel() const { return m_client_model; } interfaces::CoinJoin::Client& coinJoin() const { return m_wallet->coinJoin(); } QString getWalletName() const; @@ -217,6 +219,7 @@ private: std::unique_ptr m_handler_show_progress; std::unique_ptr m_handler_watch_only_changed; std::unique_ptr m_handler_can_get_addrs_changed; + ClientModel& m_client_model; interfaces::Node& m_node; bool fHaveWatchOnly;