diff --git a/src/init.cpp b/src/init.cpp index d819b749f8..0c6fd46276 100644 --- a/src/init.cpp +++ b/src/init.cpp @@ -1954,7 +1954,7 @@ bool AppInitMain(const CoreContext& context, NodeContext& node, interfaces::Bloc node.llmq_ctx->Stop(); } node.llmq_ctx.reset(); - node.llmq_ctx.reset(new LLMQContext(chainman.ActiveChainstate(), *node.connman, *node.dmnman, *node.evodb, *node.mnhf_manager, *node.sporkman, *node.mempool, node.peerman, false, fReset || fReindexChainState)); + node.llmq_ctx.reset(new LLMQContext(chainman.ActiveChainstate(), *node.connman, *node.dmnman, *node.evodb, *node.mnhf_manager, *node.sporkman, *node.mempool, node.mn_activeman, node.peerman, false, fReset || fReindexChainState)); // Have to start it early to let VerifyDB check ChainLock signatures in coinbase node.llmq_ctx->Start(); diff --git a/src/llmq/context.cpp b/src/llmq/context.cpp index c37415343b..0b88365d56 100644 --- a/src/llmq/context.cpp +++ b/src/llmq/context.cpp @@ -20,7 +20,7 @@ #include LLMQContext::LLMQContext(CChainState& chainstate, CConnman& connman, CDeterministicMNManager& dmnman, CEvoDB& evo_db, - CMNHFManager& mnhfman, CSporkManager& sporkman, CTxMemPool& mempool, + CMNHFManager& mnhfman, CSporkManager& sporkman, CTxMemPool& mempool, const CActiveMasternodeManager* mn_activeman, const std::unique_ptr& peerman, bool unit_tests, bool wipe) : bls_worker{std::make_shared()}, dkg_debugman{std::make_unique()}, @@ -29,14 +29,14 @@ LLMQContext::LLMQContext(CChainState& chainstate, CConnman& connman, CDeterminis llmq::quorumBlockProcessor = std::make_unique(chainstate, connman, dmnman, evo_db); return llmq::quorumBlockProcessor.get(); }()}, - qdkgsman{std::make_unique(*bls_worker, chainstate, connman, dmnman, *dkg_debugman, *quorum_block_processor, sporkman, unit_tests, wipe)}, + qdkgsman{std::make_unique(*bls_worker, chainstate, connman, dmnman, *dkg_debugman, *quorum_block_processor, mn_activeman, sporkman, unit_tests, wipe)}, qman{[&]() -> llmq::CQuorumManager* const { assert(llmq::quorumManager == nullptr); - llmq::quorumManager = std::make_unique(*bls_worker, chainstate, connman, dmnman, *qdkgsman, evo_db, *quorum_block_processor, sporkman, ::masternodeSync); + llmq::quorumManager = std::make_unique(*bls_worker, chainstate, connman, dmnman, *qdkgsman, evo_db, *quorum_block_processor, mn_activeman, sporkman, ::masternodeSync); return llmq::quorumManager.get(); }()}, - sigman{std::make_unique(connman, *llmq::quorumManager, unit_tests, wipe)}, - shareman{std::make_unique(connman, *sigman, *llmq::quorumManager, sporkman, peerman)}, + sigman{std::make_unique(connman, mn_activeman, *llmq::quorumManager, unit_tests, wipe)}, + shareman{std::make_unique(connman, *sigman, mn_activeman, *llmq::quorumManager, sporkman, peerman)}, clhandler{[&]() -> llmq::CChainLocksHandler* const { assert(llmq::chainLocksHandler == nullptr); llmq::chainLocksHandler = std::make_unique(chainstate, connman, *::masternodeSync, *llmq::quorumManager, *sigman, *shareman, sporkman, mempool); diff --git a/src/llmq/context.h b/src/llmq/context.h index 320ae0b3f5..d338a9e8b9 100644 --- a/src/llmq/context.h +++ b/src/llmq/context.h @@ -7,6 +7,7 @@ #include +class CActiveMasternodeManager; class CBLSWorker; class CChainState; class CConnman; @@ -34,7 +35,7 @@ struct LLMQContext { LLMQContext() = delete; LLMQContext(const LLMQContext&) = delete; LLMQContext(CChainState& chainstate, CConnman& connman, CDeterministicMNManager& dmnman, CEvoDB& evo_db, - CMNHFManager& mnhfman, CSporkManager& sporkman, CTxMemPool& mempool, + CMNHFManager& mnhfman, CSporkManager& sporkman, CTxMemPool& mempool, const CActiveMasternodeManager* mn_activeman, const std::unique_ptr& peerman, bool unit_tests, bool wipe); ~LLMQContext(); diff --git a/src/llmq/dkgsession.cpp b/src/llmq/dkgsession.cpp index 47495ccbd5..b819a59347 100644 --- a/src/llmq/dkgsession.cpp +++ b/src/llmq/dkgsession.cpp @@ -199,7 +199,7 @@ void CDKGSession::SendContributions(CDKGPendingMessages& pendingMessages) logger.Batch("encrypted contributions. time=%d", t1.count()); - qc.sig = ::activeMasternodeManager->Sign(qc.GetSignHash()); + qc.sig = m_mn_activeman->Sign(qc.GetSignHash()); logger.Flush(); @@ -316,7 +316,7 @@ void CDKGSession::ReceiveMessage(const CDKGContribution& qc, bool& retBan) bool complain = false; CBLSSecretKey skContribution; - if (!::activeMasternodeManager->Decrypt(*qc.contributions, *myIdx, skContribution, PROTOCOL_VERSION)) { + if (!m_mn_activeman->Decrypt(*qc.contributions, *myIdx, skContribution, PROTOCOL_VERSION)) { logger.Batch("contribution from %s could not be decrypted", member->dmn->proTxHash.ToString()); complain = true; } else if (member->idx != myIdx && ShouldSimulateError(DKGError::type::COMPLAIN_LIE)) { @@ -517,7 +517,7 @@ void CDKGSession::SendComplaint(CDKGPendingMessages& pendingMessages) logger.Batch("sending complaint. badCount=%d, complaintCount=%d", badCount, complaintCount); - qc.sig = ::activeMasternodeManager->Sign(qc.GetSignHash()); + qc.sig = m_mn_activeman->Sign(qc.GetSignHash()); logger.Flush(); @@ -711,7 +711,7 @@ void CDKGSession::SendJustification(CDKGPendingMessages& pendingMessages, const return; } - qj.sig = ::activeMasternodeManager->Sign(qj.GetSignHash()); + qj.sig = m_mn_activeman->Sign(qj.GetSignHash()); logger.Flush(); @@ -1003,7 +1003,7 @@ void CDKGSession::SendCommitment(CDKGPendingMessages& pendingMessages) (*commitmentHash.begin())++; } - qc.sig = ::activeMasternodeManager->Sign(commitmentHash); + qc.sig = m_mn_activeman->Sign(commitmentHash); qc.quorumSig = skShare.Sign(commitmentHash); if (lieType == 3) { diff --git a/src/llmq/dkgsession.h b/src/llmq/dkgsession.h index c2f029edf7..35e54b9ac7 100644 --- a/src/llmq/dkgsession.h +++ b/src/llmq/dkgsession.h @@ -15,11 +15,13 @@ #include -class UniValue; +class CActiveMasternodeManager; class CInv; class CConnman; class CDeterministicMN; class CSporkManager; +class UniValue; + using CDeterministicMNCPtr = std::shared_ptr; namespace llmq @@ -273,6 +275,7 @@ private: CDeterministicMNManager& m_dmnman; CDKGSessionManager& dkgManager; CDKGDebugManager& dkgDebugManager; + const CActiveMasternodeManager* m_mn_activeman; const CSporkManager& m_sporkman; const CBlockIndex* m_quorum_base_block_index{nullptr}; @@ -314,8 +317,11 @@ private: std::set validCommitments GUARDED_BY(invCs); public: - CDKGSession(const Consensus::LLMQParams& _params, CBLSWorker& _blsWorker, CDeterministicMNManager& dmnman, CDKGSessionManager& _dkgManager, CDKGDebugManager& _dkgDebugManager, CConnman& _connman, const CSporkManager& sporkman) : - params(_params), blsWorker(_blsWorker), cache(_blsWorker), m_dmnman(dmnman), dkgManager(_dkgManager), dkgDebugManager(_dkgDebugManager), m_sporkman(sporkman), connman(_connman) {} + CDKGSession(const Consensus::LLMQParams& _params, CBLSWorker& _blsWorker, CDeterministicMNManager& dmnman, + CDKGSessionManager& _dkgManager, CDKGDebugManager& _dkgDebugManager, CConnman& _connman, + const CActiveMasternodeManager* mn_activeman, const CSporkManager& sporkman) : + params(_params), blsWorker(_blsWorker), cache(_blsWorker), m_dmnman(dmnman), dkgManager(_dkgManager), + dkgDebugManager(_dkgDebugManager), m_mn_activeman(mn_activeman), m_sporkman(sporkman), connman(_connman) {} bool Init(gsl::not_null pQuorumBaseBlockIndex, Span mns, const uint256& _myProTxHash, int _quorumIndex); diff --git a/src/llmq/dkgsessionhandler.cpp b/src/llmq/dkgsessionhandler.cpp index be395cca35..3edf5446e8 100644 --- a/src/llmq/dkgsessionhandler.cpp +++ b/src/llmq/dkgsessionhandler.cpp @@ -26,7 +26,8 @@ namespace llmq CDKGSessionHandler::CDKGSessionHandler(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, CDKGDebugManager& _dkgDebugManager, CDKGSessionManager& _dkgManager, CQuorumBlockProcessor& _quorumBlockProcessor, - const CSporkManager& sporkman, const Consensus::LLMQParams& _params, int _quorumIndex) : + const CActiveMasternodeManager* mn_activeman, const CSporkManager& sporkman, const Consensus::LLMQParams& _params, + int _quorumIndex) : blsWorker(_blsWorker), m_chainstate(chainstate), connman(_connman), @@ -34,10 +35,11 @@ CDKGSessionHandler::CDKGSessionHandler(CBLSWorker& _blsWorker, CChainState& chai dkgDebugManager(_dkgDebugManager), dkgManager(_dkgManager), quorumBlockProcessor(_quorumBlockProcessor), + m_mn_activeman(mn_activeman), m_sporkman(sporkman), params(_params), quorumIndex(_quorumIndex), - curSession(std::make_unique(_params, _blsWorker, dmnman, _dkgManager, _dkgDebugManager, _connman, sporkman)), + curSession(std::make_unique(_params, _blsWorker, dmnman, _dkgManager, _dkgDebugManager, _connman, m_mn_activeman, sporkman)), pendingContributions((size_t)_params.size * 2, MSG_QUORUM_CONTRIB), // we allow size*2 messages as we need to make sure we see bad behavior (double messages) pendingComplaints((size_t)_params.size * 2, MSG_QUORUM_COMPLAINT), pendingJustifications((size_t)_params.size * 2, MSG_QUORUM_JUSTIFICATION), @@ -185,14 +187,14 @@ void CDKGSessionHandler::StopThread() bool CDKGSessionHandler::InitNewQuorum(const CBlockIndex* pQuorumBaseBlockIndex) { - curSession = std::make_unique(params, blsWorker, m_dmnman, dkgManager, dkgDebugManager, connman, m_sporkman); + curSession = std::make_unique(params, blsWorker, m_dmnman, dkgManager, dkgDebugManager, connman, m_mn_activeman, m_sporkman); if (!DeploymentDIP0003Enforced(pQuorumBaseBlockIndex->nHeight, Params().GetConsensus())) { return false; } auto mns = utils::GetAllQuorumMembers(params.type, m_dmnman, pQuorumBaseBlockIndex); - if (!curSession->Init(pQuorumBaseBlockIndex, mns, WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()), quorumIndex)) { + if (!curSession->Init(pQuorumBaseBlockIndex, mns, WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()), quorumIndex)) { LogPrintf("CDKGSessionManager::%s -- height[%d] quorum initialization failed for %s qi[%d] mns[%d]\n", __func__, pQuorumBaseBlockIndex->nHeight, curSession->params.name, quorumIndex, mns.size()); return false; } diff --git a/src/llmq/dkgsessionhandler.h b/src/llmq/dkgsessionhandler.h index 8a234dca8b..543bcbd338 100644 --- a/src/llmq/dkgsessionhandler.h +++ b/src/llmq/dkgsessionhandler.h @@ -14,6 +14,7 @@ #include #include +class CActiveMasternodeManager; class CBlockIndex; class CBLSWorker; class CChainState; @@ -125,6 +126,7 @@ private: CDKGDebugManager& dkgDebugManager; CDKGSessionManager& dkgManager; CQuorumBlockProcessor& quorumBlockProcessor; + const CActiveMasternodeManager* m_mn_activeman; const CSporkManager& m_sporkman; const Consensus::LLMQParams params; const int quorumIndex; @@ -146,7 +148,8 @@ private: public: CDKGSessionHandler(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, CDKGDebugManager& _dkgDebugManager, CDKGSessionManager& _dkgManager, CQuorumBlockProcessor& _quorumBlockProcessor, - const CSporkManager& sporkman, const Consensus::LLMQParams& _params, int _quorumIndex); + const CActiveMasternodeManager* mn_activeman, const CSporkManager& sporkman, const Consensus::LLMQParams& _params, + int _quorumIndex); ~CDKGSessionHandler() = default; void UpdatedBlockTip(const CBlockIndex *pindexNew); diff --git a/src/llmq/dkgsessionmgr.cpp b/src/llmq/dkgsessionmgr.cpp index c541ddcc83..c4d1dce1f7 100644 --- a/src/llmq/dkgsessionmgr.cpp +++ b/src/llmq/dkgsessionmgr.cpp @@ -25,8 +25,8 @@ static const std::string DB_SKCONTRIB = "qdkg_S"; static const std::string DB_ENC_CONTRIB = "qdkg_E"; CDKGSessionManager::CDKGSessionManager(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, - CDKGDebugManager& _dkgDebugManager, CQuorumBlockProcessor& _quorumBlockProcessor, const CSporkManager& sporkman, - bool unitTests, bool fWipe) : + CDKGDebugManager& _dkgDebugManager, CQuorumBlockProcessor& _quorumBlockProcessor, const CActiveMasternodeManager* mn_activeman, + const CSporkManager& sporkman, bool unitTests, bool fWipe) : db(std::make_unique(unitTests ? "" : (GetDataDir() / "llmq/dkgdb"), 1 << 20, unitTests, fWipe)), blsWorker(_blsWorker), m_chainstate(chainstate), @@ -49,7 +49,7 @@ CDKGSessionManager::CDKGSessionManager(CBLSWorker& _blsWorker, CChainState& chai for (const auto i : irange::range(session_count)) { dkgSessionHandlers.emplace(std::piecewise_construct, std::forward_as_tuple(params.type, i), - std::forward_as_tuple(blsWorker, m_chainstate, connman, dmnman, dkgDebugManager, *this, quorumBlockProcessor, spork_manager, params, i)); + std::forward_as_tuple(blsWorker, m_chainstate, connman, dmnman, dkgDebugManager, *this, quorumBlockProcessor, mn_activeman, spork_manager, params, i)); } } } diff --git a/src/llmq/dkgsessionmgr.h b/src/llmq/dkgsessionmgr.h index 1b2633dc5b..567119ea34 100644 --- a/src/llmq/dkgsessionmgr.h +++ b/src/llmq/dkgsessionmgr.h @@ -14,6 +14,7 @@ #include #include +class CActiveMasternodeManager; class CBlockIndex; class CChainState; class CDBWrapper; @@ -66,8 +67,8 @@ private: public: CDKGSessionManager(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, - CDKGDebugManager& _dkgDebugManager, CQuorumBlockProcessor& _quorumBlockProcessor, const CSporkManager& sporkman, - bool unitTests, bool fWipe); + CDKGDebugManager& _dkgDebugManager, CQuorumBlockProcessor& _quorumBlockProcessor, const CActiveMasternodeManager* mn_activeman, + const CSporkManager& sporkman, bool unitTests, bool fWipe); ~CDKGSessionManager() = default; void StartThreads(); diff --git a/src/llmq/quorums.cpp b/src/llmq/quorums.cpp index 1cfb39caf7..8b6e7205ab 100644 --- a/src/llmq/quorums.cpp +++ b/src/llmq/quorums.cpp @@ -101,9 +101,9 @@ bool CQuorum::SetVerificationVector(const std::vector& quorumVecI return true; } -bool CQuorum::SetSecretKeyShare(const CBLSSecretKey& secretKeyShare) +bool CQuorum::SetSecretKeyShare(const CBLSSecretKey& secretKeyShare, const CActiveMasternodeManager& mn_activeman) { - if (!secretKeyShare.IsValid() || (secretKeyShare.GetPublicKey() != GetPubKeyShare(WITH_LOCK(::activeMasternodeManager->cs, return GetMemberIndex(::activeMasternodeManager->GetProTxHash()))))) { + if (!secretKeyShare.IsValid() || (secretKeyShare.GetPublicKey() != GetPubKeyShare(WITH_LOCK(mn_activeman.cs, return GetMemberIndex(mn_activeman.GetProTxHash()))))) { return false; } LOCK(cs); @@ -205,8 +205,10 @@ bool CQuorum::ReadContributions(CEvoDB& evoDb) return true; } -CQuorumManager::CQuorumManager(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, CDKGSessionManager& _dkgManager, - CEvoDB& _evoDb, CQuorumBlockProcessor& _quorumBlockProcessor, const CSporkManager& sporkman, const std::unique_ptr& mn_sync) : +CQuorumManager::CQuorumManager(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, + CDKGSessionManager& _dkgManager, CEvoDB& _evoDb, CQuorumBlockProcessor& _quorumBlockProcessor, + const CActiveMasternodeManager* mn_activeman, const CSporkManager& sporkman, + const std::unique_ptr& mn_sync) : blsWorker(_blsWorker), m_chainstate(chainstate), connman(_connman), @@ -214,6 +216,7 @@ CQuorumManager::CQuorumManager(CBLSWorker& _blsWorker, CChainState& chainstate, dkgManager(_dkgManager), m_evoDb(_evoDb), quorumBlockProcessor(_quorumBlockProcessor), + m_mn_activeman(mn_activeman), m_sporkman(sporkman), m_mn_sync(mn_sync) { @@ -250,9 +253,11 @@ void CQuorumManager::TriggerQuorumDataRecoveryThreads(const CBlockIndex* pIndex) const auto vecQuorums = ScanQuorums(params.type, pIndex, params.keepOldConnections); // First check if we are member of any quorum of this type - const uint256 proTxHash = fMasternodeMode ? - WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()) : - uint256(); + const uint256 proTxHash = [this]() { + if (!fMasternodeMode) return uint256(); + assert(m_mn_activeman); + return WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()); + }(); bool fWeAreQuorumTypeMember = ranges::any_of(vecQuorums, [&proTxHash](const auto& pQuorum) { return pQuorum->IsValidMember(proTxHash); @@ -344,9 +349,11 @@ void CQuorumManager::CheckQuorumConnections(const Consensus::LLMQParams& llmqPar LogPrint(BCLog::LLMQ, "CQuorumManager::%s -- llmqType[%d] h[%d] keeping mn quorum connections for quorum: [%d:%s]\n", __func__, ToUnderlying(llmqParams.type), pindexNew->nHeight, curDkgHeight, curDkgBlock.ToString()); } - const uint256 myProTxHash = fMasternodeMode ? - WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()) : - uint256(); + const uint256 myProTxHash = [this]() { + if (!fMasternodeMode) return uint256(); + assert(m_mn_activeman); + return WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()); + }(); bool isISType = llmqParams.type == Params().GetConsensus().llmqTypeDIP0024InstantSend; @@ -646,6 +653,8 @@ CQuorumCPtr CQuorumManager::GetQuorum(Consensus::LLMQType llmqType, gsl::not_nul size_t CQuorumManager::GetQuorumRecoveryStartOffset(const CQuorumCPtr pQuorum, const CBlockIndex* pIndex) const { + assert(m_mn_activeman); + auto mns = m_dmnman.GetListForBlock(pIndex); std::vector vecProTxHashes; vecProTxHashes.reserve(mns.GetValidMNsCount()); @@ -655,10 +664,10 @@ size_t CQuorumManager::GetQuorumRecoveryStartOffset(const CQuorumCPtr pQuorum, c std::sort(vecProTxHashes.begin(), vecProTxHashes.end()); size_t nIndex{0}; { - LOCK(::activeMasternodeManager->cs); + LOCK(m_mn_activeman->cs); for (const auto i : irange::range(vecProTxHashes.size())) { // cppcheck-suppress useStlAlgorithm - if (::activeMasternodeManager->GetProTxHash() == vecProTxHashes[i]) { + if (m_mn_activeman->GetProTxHash() == vecProTxHashes[i]) { nIndex = i; break; } @@ -819,6 +828,7 @@ PeerMsgRet CQuorumManager::ProcessMessage(CNode& pfrom, const std::string& msg_t // Check if request has ENCRYPTED_CONTRIBUTIONS data if (request.GetDataMask() & CQuorumDataRequest::ENCRYPTED_CONTRIBUTIONS) { + assert(fMasternodeMode); if (WITH_LOCK(pQuorum->cs, return pQuorum->quorumVvec->size() != size_t(pQuorum->params.threshold))) { return errorHandler("No valid quorum verification vector available", 0); // Don't bump score because we asked for it @@ -835,13 +845,13 @@ PeerMsgRet CQuorumManager::ProcessMessage(CNode& pfrom, const std::string& msg_t std::vector vecSecretKeys; vecSecretKeys.resize(vecEncrypted.size()); for (const auto i : irange::range(vecEncrypted.size())) { - if (!::activeMasternodeManager->Decrypt(vecEncrypted[i], memberIdx, vecSecretKeys[i], PROTOCOL_VERSION)) { + if (!Assert(m_mn_activeman)->Decrypt(vecEncrypted[i], memberIdx, vecSecretKeys[i], PROTOCOL_VERSION)) { return errorHandler("Failed to decrypt"); } } CBLSSecretKey secretKeyShare = blsWorker.AggregateSecretKeys(vecSecretKeys); - if (!pQuorum->SetSecretKeyShare(secretKeyShare)) { + if (!pQuorum->SetSecretKeyShare(secretKeyShare, *m_mn_activeman)) { return errorHandler("Invalid secret key share received"); } } @@ -883,6 +893,8 @@ void CQuorumManager::StartCachePopulatorThread(const CQuorumCPtr pQuorum) const void CQuorumManager::StartQuorumDataRecoveryThread(const CQuorumCPtr pQuorum, const CBlockIndex* pIndex, uint16_t nDataMaskIn) const { + assert(m_mn_activeman); + if (pQuorum->fQuorumDataRecoveryThreadRunning) { LogPrint(BCLog::LLMQ, "CQuorumManager::%s -- Already running\n", __func__); return; @@ -916,7 +928,7 @@ void CQuorumManager::StartQuorumDataRecoveryThread(const CQuorumCPtr pQuorum, co vecMemberHashes.reserve(pQuorum->qc->validMembers.size()); for (auto& member : pQuorum->members) { - if (pQuorum->IsValidMember(member->proTxHash) && member->proTxHash != WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash())) { + if (pQuorum->IsValidMember(member->proTxHash) && member->proTxHash != WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash())) { vecMemberHashes.push_back(member->proTxHash); } } @@ -965,7 +977,7 @@ void CQuorumManager::StartQuorumDataRecoveryThread(const CQuorumCPtr pQuorum, co printLog("Connect"); } - auto proTxHash = WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()); + auto proTxHash = WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()); connman.ForEachNode([&](CNode* pNode) { auto verifiedProRegTxHash = pNode->GetVerifiedProRegTxHash(); if (pCurrentMemberHash == nullptr || verifiedProRegTxHash != *pCurrentMemberHash) { diff --git a/src/llmq/quorums.h b/src/llmq/quorums.h index 946bdbfc7c..bf6188a0ca 100644 --- a/src/llmq/quorums.h +++ b/src/llmq/quorums.h @@ -21,6 +21,7 @@ #include #include +class CActiveMasternodeManager; class CBlockIndex; class CChainState; class CConnman; @@ -192,7 +193,7 @@ public: void Init(CFinalCommitmentPtr _qc, const CBlockIndex* _pQuorumBaseBlockIndex, const uint256& _minedBlockHash, Span _members); bool SetVerificationVector(const std::vector& quorumVecIn); - bool SetSecretKeyShare(const CBLSSecretKey& secretKeyShare); + bool SetSecretKeyShare(const CBLSSecretKey& secretKeyShare, const CActiveMasternodeManager& mn_activeman); bool HasVerificationVector() const; bool IsMember(const uint256& proTxHash) const; @@ -223,6 +224,7 @@ private: CDKGSessionManager& dkgManager; CEvoDB& m_evoDb; CQuorumBlockProcessor& quorumBlockProcessor; + const CActiveMasternodeManager* m_mn_activeman; const CSporkManager& m_sporkman; const std::unique_ptr& m_mn_sync; @@ -237,8 +239,9 @@ private: mutable CThreadInterrupt quorumThreadInterrupt; public: - CQuorumManager(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, CDKGSessionManager& _dkgManager, - CEvoDB& _evoDb, CQuorumBlockProcessor& _quorumBlockProcessor, const CSporkManager& sporkman, const std::unique_ptr& mn_sync); + CQuorumManager(CBLSWorker& _blsWorker, CChainState& chainstate, CConnman& _connman, CDeterministicMNManager& dmnman, + CDKGSessionManager& _dkgManager, CEvoDB& _evoDb, CQuorumBlockProcessor& _quorumBlockProcessor, + const CActiveMasternodeManager* mn_activeman, const CSporkManager& sporkman, const std::unique_ptr& mn_sync); ~CQuorumManager() { Stop(); }; void Start(); diff --git a/src/llmq/signing.cpp b/src/llmq/signing.cpp index e7be07f9e5..f088895773 100644 --- a/src/llmq/signing.cpp +++ b/src/llmq/signing.cpp @@ -539,9 +539,9 @@ void CRecoveredSigsDb::CleanupOldVotes(int64_t maxAge) ////////////////// -CSigningManager::CSigningManager(CConnman& _connman, const CQuorumManager& _qman, +CSigningManager::CSigningManager(CConnman& _connman, const CActiveMasternodeManager* mn_activeman, const CQuorumManager& _qman, bool fMemory, bool fWipe) : - db(fMemory, fWipe), connman(_connman), qman(_qman) + db(fMemory, fWipe), connman(_connman), m_mn_activeman(mn_activeman), qman(_qman) { } @@ -896,7 +896,9 @@ void CSigningManager::UnregisterRecoveredSigsListener(CRecoveredSigsListener* l) bool CSigningManager::AsyncSignIfMember(Consensus::LLMQType llmqType, CSigSharesManager& shareman, const uint256& id, const uint256& msgHash, const uint256& quorumHash, bool allowReSign) { if (!fMasternodeMode) return false; - if (WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash().IsNull())) return false; + + assert(m_mn_activeman); + if (WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash().IsNull())) return false; const CQuorumCPtr quorum = [&]() { if (quorumHash.IsNull()) { @@ -918,7 +920,7 @@ bool CSigningManager::AsyncSignIfMember(Consensus::LLMQType llmqType, CSigShares return false; } - if (!WITH_LOCK(::activeMasternodeManager->cs, return quorum->IsValidMember(::activeMasternodeManager->GetProTxHash()))) { + if (!WITH_LOCK(m_mn_activeman->cs, return quorum->IsValidMember(m_mn_activeman->GetProTxHash()))) { return false; } diff --git a/src/llmq/signing.h b/src/llmq/signing.h index 1d4c0bd459..4a00bd248c 100644 --- a/src/llmq/signing.h +++ b/src/llmq/signing.h @@ -18,6 +18,7 @@ #include +class CActiveMasternodeManager; class CConnman; class CDataStream; class CDBBatch; @@ -162,6 +163,7 @@ private: CRecoveredSigsDb db; CConnman& connman; + const CActiveMasternodeManager* m_mn_activeman; const CQuorumManager& qman; std::atomic m_peerman{nullptr}; @@ -177,7 +179,7 @@ private: std::vector recoveredSigsListeners GUARDED_BY(cs); public: - CSigningManager(CConnman& _connman, const CQuorumManager& _qman, bool fMemory, bool fWipe); + CSigningManager(CConnman& _connman, const CActiveMasternodeManager* mn_activeman, const CQuorumManager& _qman, bool fMemory, bool fWipe); bool AlreadyHave(const CInv& inv) const; bool GetRecoveredSigForGetData(const uint256& hash, CRecoveredSig& ret) const; diff --git a/src/llmq/signing_shares.cpp b/src/llmq/signing_shares.cpp index 9506a3ab46..395e7d1723 100644 --- a/src/llmq/signing_shares.cpp +++ b/src/llmq/signing_shares.cpp @@ -219,7 +219,9 @@ void CSigSharesManager::ProcessMessage(const CNode& pfrom, const CSporkManager& { // non-masternodes are not interested in sigshares if (!fMasternodeMode) return; - if (WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash().IsNull())) return; + + assert(m_mn_activeman); + if (WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash().IsNull())) return; if (sporkman.IsSporkActive(SPORK_21_QUORUM_ALL_CONNECTED) && msg_type == NetMsgType::QSIGSHARE) { std::vector receivedSigShares; @@ -407,7 +409,7 @@ bool CSigSharesManager::ProcessMessageBatchedSigShares(const CNode& pfrom, const return true; } - if (bool ban{false}; !PreVerifyBatchedSigShares(qman, sessionInfo, batchedSigShares, ban)) { + if (bool ban{false}; !PreVerifyBatchedSigShares(*Assert(m_mn_activeman), qman, sessionInfo, batchedSigShares, ban)) { return !ban; } @@ -456,6 +458,8 @@ bool CSigSharesManager::ProcessMessageBatchedSigShares(const CNode& pfrom, const void CSigSharesManager::ProcessMessageSigShare(NodeId fromId, const CSigShare& sigShare) { + assert(m_mn_activeman); + auto quorum = qman.GetQuorum(sigShare.getLlmqType(), sigShare.getQuorumHash()); if (!quorum) { return; @@ -464,7 +468,7 @@ void CSigSharesManager::ProcessMessageSigShare(NodeId fromId, const CSigShare& s // quorum is too old return; } - if (!quorum->IsMember(WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()))) { + if (!quorum->IsMember(WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()))) { // we're not a member so we can't verify it (we actually shouldn't have received it) return; } @@ -505,7 +509,8 @@ void CSigSharesManager::ProcessMessageSigShare(NodeId fromId, const CSigShare& s sigShare.GetSignHash().ToString(), sigShare.getId().ToString(), sigShare.getMsgHash().ToString(), sigShare.getQuorumMember(), fromId); } -bool CSigSharesManager::PreVerifyBatchedSigShares(const CQuorumManager& quorum_manager, const CSigSharesNodeState::SessionInfo& session, const CBatchedSigShares& batchedSigShares, bool& retBan) +bool CSigSharesManager::PreVerifyBatchedSigShares(const CActiveMasternodeManager& mn_activeman, const CQuorumManager& quorum_manager, + const CSigSharesNodeState::SessionInfo& session, const CBatchedSigShares& batchedSigShares, bool& retBan) { retBan = false; @@ -513,7 +518,7 @@ bool CSigSharesManager::PreVerifyBatchedSigShares(const CQuorumManager& quorum_m // quorum is too old return false; } - if (!session.quorum->IsMember(WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()))) { + if (!session.quorum->IsMember(WITH_LOCK(mn_activeman.cs, return mn_activeman.GetProTxHash()))) { // we're not a member so we can't verify it (we actually shouldn't have received it) return false; } @@ -691,13 +696,14 @@ void CSigSharesManager::ProcessPendingSigShares(const std::vector& si // sig shares are already verified when entering this method void CSigSharesManager::ProcessSigShare(const CSigShare& sigShare, const CConnman& connman, const CQuorumCPtr& quorum) { - auto llmqType = quorum->params.type; + assert(m_mn_activeman); + auto llmqType = quorum->params.type; bool canTryRecovery = false; // prepare node set for direct-push in case this is our sig share std::set quorumNodes; - if (!IsAllMembersConnectedEnabled(llmqType, m_sporkman) && sigShare.getQuorumMember() == quorum->GetMemberIndex(WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()))) { + if (!IsAllMembersConnectedEnabled(llmqType, m_sporkman) && sigShare.getQuorumMember() == quorum->GetMemberIndex(WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()))) { quorumNodes = connman.GetMasternodeQuorumNodes(sigShare.getLlmqType(), sigShare.getQuorumHash()); } @@ -1487,8 +1493,10 @@ void CSigSharesManager::SignPendingSigShares() std::optional CSigSharesManager::CreateSigShare(const CQuorumCPtr& quorum, const uint256& id, const uint256& msgHash) const { + assert(m_mn_activeman); + cxxtimer::Timer t(true); - auto activeMasterNodeProTxHash = WITH_LOCK(::activeMasternodeManager->cs, return ::activeMasternodeManager->GetProTxHash()); + auto activeMasterNodeProTxHash = WITH_LOCK(m_mn_activeman->cs, return m_mn_activeman->GetProTxHash()); if (!quorum->IsValidMember(activeMasterNodeProTxHash)) { return std::nullopt; diff --git a/src/llmq/signing_shares.h b/src/llmq/signing_shares.h index 173c7d0395..d678e99d80 100644 --- a/src/llmq/signing_shares.h +++ b/src/llmq/signing_shares.h @@ -401,6 +401,7 @@ private: CConnman& connman; CSigningManager& sigman; + const CActiveMasternodeManager* m_mn_activeman; const CQuorumManager& qman; const CSporkManager& m_sporkman; @@ -410,8 +411,9 @@ private: std::atomic recoveredSigsCounter{0}; public: - explicit CSigSharesManager(CConnman& _connman, CSigningManager& _sigman, const CQuorumManager& _qman, const CSporkManager& sporkman, const std::unique_ptr& peerman) : - connman(_connman), sigman(_sigman), qman(_qman), m_sporkman(sporkman), m_peerman(peerman) + explicit CSigSharesManager(CConnman& _connman, CSigningManager& _sigman, const CActiveMasternodeManager* mn_activeman, + const CQuorumManager& _qman, const CSporkManager& sporkman, const std::unique_ptr& peerman) : + connman(_connman), sigman(_sigman), m_mn_activeman(mn_activeman), qman(_qman), m_sporkman(sporkman), m_peerman(peerman) { workInterrupt.reset(); }; @@ -443,7 +445,8 @@ private: void ProcessMessageSigShare(NodeId fromId, const CSigShare& sigShare); static bool VerifySigSharesInv(Consensus::LLMQType llmqType, const CSigSharesInv& inv); - static bool PreVerifyBatchedSigShares(const CQuorumManager& quorum_manager, const CSigSharesNodeState::SessionInfo& session, const CBatchedSigShares& batchedSigShares, bool& retBan); + static bool PreVerifyBatchedSigShares(const CActiveMasternodeManager& mn_activeman, const CQuorumManager& quorum_manager, + const CSigSharesNodeState::SessionInfo& session, const CBatchedSigShares& batchedSigShares, bool& retBan); void CollectPendingSigSharesToVerify(size_t maxUniqueSessions, std::unordered_map>& retSigShares, diff --git a/src/test/util/setup_common.cpp b/src/test/util/setup_common.cpp index f420d5b193..e82f68a6e9 100644 --- a/src/test/util/setup_common.cpp +++ b/src/test/util/setup_common.cpp @@ -115,7 +115,8 @@ void DashTestSetup(NodeContext& node, const CChainParams& chainparams) #ifdef ENABLE_WALLET node.coinjoin_loader = interfaces::MakeCoinJoinLoader(*node.cj_ctx->walletman); #endif // ENABLE_WALLET - node.llmq_ctx = std::make_unique(chainstate, *node.connman, *node.dmnman, *node.evodb, *node.mnhf_manager, *node.sporkman, *node.mempool, node.peerman, true, false); + node.llmq_ctx = std::make_unique(chainstate, *node.connman, *node.dmnman, *node.evodb, *node.mnhf_manager, *node.sporkman, *node.mempool, + /* mn_activeman = */ nullptr, node.peerman, /* unit_tests = */ true, /* wipe = */ false); node.chain_helper = std::make_unique(*node.cpoolman, *node.dmnman, *node.mnhf_manager, *node.govman, *(node.llmq_ctx->quorum_block_processor), chainparams.GetConsensus(), *node.mn_sync, *node.sporkman, *(node.llmq_ctx->clhandler)); }