LCOV - code coverage report
Current view: top level - src/governance - votedb.cpp (source / functions) Hit Total Coverage
Test: test_dash_coverage.info Lines: 3 87 3.4 %
Date: 2026-06-25 07:23:51 Functions: 2 12 16.7 %

          Line data    Source code
       1             : // Copyright (c) 2014-2024 The Dash Core developers
       2             : // Distributed under the MIT/X11 software license, see the accompanying
       3             : // file COPYING or http://www.opensource.org/licenses/mit-license.php.
       4             : 
       5             : #include <governance/votedb.h>
       6             : 
       7             : #include <streams.h>
       8             : 
       9           2 : CGovernanceObjectVoteFile::CGovernanceObjectVoteFile() :
      10             :     listVotes(),
      11             :     mapVoteIndex()
      12           1 : {
      13           1 : }
      14             : 
      15           0 : CGovernanceObjectVoteFile::CGovernanceObjectVoteFile(const CGovernanceObjectVoteFile& other) :
      16           0 :     nMemoryVotes(other.nMemoryVotes),
      17           0 :     listVotes(other.listVotes),
      18           0 :     mapVoteIndex()
      19           0 : {
      20           0 :     RebuildIndex();
      21           0 : }
      22             : 
      23           0 : void CGovernanceObjectVoteFile::AddVote(const CGovernanceVote& vote)
      24             : {
      25           0 :     uint256 nHash = vote.GetHash();
      26             :     // make sure to never add/update already known votes
      27           0 :     if (HasVote(nHash))
      28           0 :         return;
      29           0 :     listVotes.push_front(vote);
      30           0 :     mapVoteIndex.emplace(nHash, listVotes.begin());
      31           0 :     ++nMemoryVotes;
      32           0 :     RemoveOldVotes(vote);
      33           0 : }
      34             : 
      35           0 : bool CGovernanceObjectVoteFile::HasVote(const uint256& nHash) const
      36             : {
      37           0 :     return mapVoteIndex.find(nHash) != mapVoteIndex.end();
      38             : }
      39             : 
      40           0 : bool CGovernanceObjectVoteFile::SerializeVoteToStream(const uint256& nHash, CDataStream& ss) const
      41             : {
      42           0 :     auto it = mapVoteIndex.find(nHash);
      43           0 :     if (it == mapVoteIndex.end()) {
      44           0 :         return false;
      45             :     }
      46           0 :     ss << *(it->second);
      47           0 :     return true;
      48           0 : }
      49             : 
      50           0 : std::vector<CGovernanceVote> CGovernanceObjectVoteFile::GetVotes() const
      51             : {
      52           0 :     std::vector<CGovernanceVote> vecResult;
      53           0 :     vecResult.reserve(listVotes.size());
      54           0 :     std::copy(std::begin(listVotes), std::end(listVotes), std::back_inserter(vecResult));
      55           0 :     return vecResult;
      56           0 : }
      57             : 
      58           0 : void CGovernanceObjectVoteFile::RemoveVotesFromMasternode(const COutPoint& outpointMasternode)
      59             : {
      60           0 :     auto it = listVotes.begin();
      61           0 :     while (it != listVotes.end()) {
      62           0 :         if (it->GetMasternodeOutpoint() == outpointMasternode) {
      63           0 :             --nMemoryVotes;
      64           0 :             mapVoteIndex.erase(it->GetHash());
      65           0 :             listVotes.erase(it++);
      66           0 :         } else {
      67           0 :             ++it;
      68             :         }
      69             :     }
      70           0 : }
      71             : 
      72           0 : std::set<uint256> CGovernanceObjectVoteFile::RemoveInvalidVotes(const CDeterministicMNList& tip_mn_list, const COutPoint& outpointMasternode, bool fProposal)
      73             : {
      74           0 :     std::set<uint256> removedVotes;
      75             : 
      76           0 :     auto it = listVotes.begin();
      77           0 :     while (it != listVotes.end()) {
      78           0 :         if (it->GetMasternodeOutpoint() == outpointMasternode) {
      79           0 :             bool useVotingKey = fProposal && (it->GetSignal() == VOTE_SIGNAL_FUNDING);
      80           0 :             if (!it->IsValid(tip_mn_list, useVotingKey)) {
      81           0 :                 removedVotes.emplace(it->GetHash());
      82           0 :                 --nMemoryVotes;
      83           0 :                 mapVoteIndex.erase(it->GetHash());
      84           0 :                 listVotes.erase(it++);
      85           0 :                 continue;
      86             :             }
      87           0 :         }
      88           0 :         ++it;
      89             :     }
      90             : 
      91           0 :     return removedVotes;
      92           0 : }
      93             : 
      94           0 : void CGovernanceObjectVoteFile::RemoveOldVotes(const CGovernanceVote& vote)
      95             : {
      96           0 :     auto it = listVotes.begin();
      97           0 :     while (it != listVotes.end()) {
      98           0 :         if (it->GetMasternodeOutpoint() == vote.GetMasternodeOutpoint() // same masternode
      99           0 :             && it->GetParentHash() == vote.GetParentHash() // same governance object (e.g. same proposal)
     100           0 :             && it->GetSignal() == vote.GetSignal() // same signal (e.g. "funding", "delete", etc.)
     101           0 :             && it->GetTimestamp() < vote.GetTimestamp()) // older than new vote
     102             :         {
     103           0 :             --nMemoryVotes;
     104           0 :             mapVoteIndex.erase(it->GetHash());
     105           0 :             listVotes.erase(it++);
     106           0 :         } else {
     107           0 :             ++it;
     108             :         }
     109             :     }
     110           0 : }
     111             : 
     112           0 : void CGovernanceObjectVoteFile::RebuildIndex()
     113             : {
     114           0 :     mapVoteIndex.clear();
     115           0 :     nMemoryVotes = 0;
     116           0 :     auto it = listVotes.begin();
     117           0 :     while (it != listVotes.end()) {
     118           0 :         const CGovernanceVote& vote = *it;
     119           0 :         uint256 nHash = vote.GetHash();
     120           0 :         if (mapVoteIndex.find(nHash) == mapVoteIndex.end()) {
     121           0 :             mapVoteIndex[nHash] = it;
     122           0 :             ++nMemoryVotes;
     123           0 :             ++it;
     124           0 :         } else {
     125           0 :             listVotes.erase(it++);
     126             :         }
     127             :     }
     128           0 : }

Generated by: LCOV version 1.16