implement sentinel-like wd selection logic (#1359)
* Only accept wd's that are more recent or have a higher hash than the current best * Fix whitespace typo * Relay current watchdog when lower priority ones are received * Fix nHashWatchdogCurrent reset conditions * expire previous current wd when a new one is found in UpdateCurrentWatchdog * fail to process votes for expired or deleted object
This commit is contained in:
parent
17cf8dc6d1
commit
636fb33e71
@ -20,7 +20,7 @@ std::map<uint256, int64_t> mapAskedForGovernanceObject;
|
|||||||
|
|
||||||
int nSubmittedFinalBudget;
|
int nSubmittedFinalBudget;
|
||||||
|
|
||||||
const std::string CGovernanceManager::SERIALIZATION_VERSION_STRING = "CGovernanceManager-Version-9";
|
const std::string CGovernanceManager::SERIALIZATION_VERSION_STRING = "CGovernanceManager-Version-10";
|
||||||
|
|
||||||
CGovernanceManager::CGovernanceManager()
|
CGovernanceManager::CGovernanceManager()
|
||||||
: pCurrentBlockIndex(NULL),
|
: pCurrentBlockIndex(NULL),
|
||||||
@ -30,6 +30,8 @@ CGovernanceManager::CGovernanceManager()
|
|||||||
mapSeenGovernanceObjects(),
|
mapSeenGovernanceObjects(),
|
||||||
mapMasternodeOrphanObjects(),
|
mapMasternodeOrphanObjects(),
|
||||||
mapWatchdogObjects(),
|
mapWatchdogObjects(),
|
||||||
|
nHashWatchdogCurrent(),
|
||||||
|
nTimeWatchdogCurrent(0),
|
||||||
mapVoteToObject(MAX_CACHE_SIZE),
|
mapVoteToObject(MAX_CACHE_SIZE),
|
||||||
mapInvalidVotes(MAX_CACHE_SIZE),
|
mapInvalidVotes(MAX_CACHE_SIZE),
|
||||||
mapOrphanVotes(MAX_CACHE_SIZE),
|
mapOrphanVotes(MAX_CACHE_SIZE),
|
||||||
@ -219,7 +221,7 @@ void CGovernanceManager::ProcessMessage(CNode* pfrom, std::string& strCommand, C
|
|||||||
|
|
||||||
govobj.UpdateSentinelVariables(); //this sets local vars in object
|
govobj.UpdateSentinelVariables(); //this sets local vars in object
|
||||||
|
|
||||||
if(AddGovernanceObject(govobj))
|
if(AddGovernanceObject(govobj, pfrom))
|
||||||
{
|
{
|
||||||
LogPrintf("MNGOVERNANCEOBJECT -- %s new\n", strHash);
|
LogPrintf("MNGOVERNANCEOBJECT -- %s new\n", strHash);
|
||||||
govobj.Relay();
|
govobj.Relay();
|
||||||
@ -305,7 +307,7 @@ void CGovernanceManager::CheckOrphanVotes(CGovernanceObject& govobj, CGovernance
|
|||||||
fRateChecksEnabled = true;
|
fRateChecksEnabled = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CGovernanceManager::AddGovernanceObject(CGovernanceObject& govobj)
|
bool CGovernanceManager::AddGovernanceObject(CGovernanceObject& govobj, CNode* pfrom)
|
||||||
{
|
{
|
||||||
LOCK2(cs_main, cs);
|
LOCK2(cs_main, cs);
|
||||||
std::string strError = "";
|
std::string strError = "";
|
||||||
@ -330,14 +332,23 @@ bool CGovernanceManager::AddGovernanceObject(CGovernanceObject& govobj)
|
|||||||
|
|
||||||
LogPrint("gobject", "CGovernanceManager::AddGovernanceObject -- Adding object: hash = %s, type = %d\n", nHash.ToString(), govobj.GetObjectType());
|
LogPrint("gobject", "CGovernanceManager::AddGovernanceObject -- Adding object: hash = %s, type = %d\n", nHash.ToString(), govobj.GetObjectType());
|
||||||
|
|
||||||
// If it's a watchdog, make sure it fits required time bounds
|
if(govobj.nObjectType == GOVERNANCE_OBJECT_WATCHDOG) {
|
||||||
if(govobj.nObjectType == GOVERNANCE_OBJECT_WATCHDOG &&
|
// If it's a watchdog, make sure it fits required time bounds
|
||||||
(govobj.GetCreationTime() < GetAdjustedTime() - GOVERNANCE_WATCHDOG_EXPIRATION_TIME ||
|
if((govobj.GetCreationTime() < GetAdjustedTime() - GOVERNANCE_WATCHDOG_EXPIRATION_TIME ||
|
||||||
govobj.GetCreationTime() > GetAdjustedTime() + GOVERNANCE_WATCHDOG_EXPIRATION_TIME)
|
govobj.GetCreationTime() > GetAdjustedTime() + GOVERNANCE_WATCHDOG_EXPIRATION_TIME)
|
||||||
) {
|
) {
|
||||||
// drop it
|
// drop it
|
||||||
LogPrint("gobject", "CGovernanceManager::AddGovernanceObject -- CreationTime is out of bounds: hash = %s\n", nHash.ToString());
|
LogPrint("gobject", "CGovernanceManager::AddGovernanceObject -- CreationTime is out of bounds: hash = %s\n", nHash.ToString());
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(!UpdateCurrentWatchdog(govobj)) {
|
||||||
|
if(pfrom && (nHashWatchdogCurrent != uint256())) {
|
||||||
|
pfrom->PushInventory(CInv(MSG_GOVERNANCE_OBJECT, nHashWatchdogCurrent));
|
||||||
|
}
|
||||||
|
LogPrint("gobject", "CGovernanceManager::AddGovernanceObject -- Watchdog not better than current: hash = %s\n", nHash.ToString());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// INSERT INTO OUR GOVERNANCE OBJECT MEMORY
|
// INSERT INTO OUR GOVERNANCE OBJECT MEMORY
|
||||||
@ -369,6 +380,38 @@ bool CGovernanceManager::AddGovernanceObject(CGovernanceObject& govobj)
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool CGovernanceManager::UpdateCurrentWatchdog(CGovernanceObject& watchdogNew)
|
||||||
|
{
|
||||||
|
bool fAccept = false;
|
||||||
|
|
||||||
|
arith_uint256 nHashNew = UintToArith256(watchdogNew.GetHash());
|
||||||
|
arith_uint256 nHashCurrent = UintToArith256(nHashWatchdogCurrent);
|
||||||
|
|
||||||
|
int64_t nExpirationDelay = GOVERNANCE_WATCHDOG_EXPIRATION_TIME / 2;
|
||||||
|
int64_t nNow = GetTime();
|
||||||
|
|
||||||
|
if((nHashWatchdogCurrent == uint256()) ||
|
||||||
|
(((nNow - nTimeWatchdogCurrent) > nExpirationDelay) && (nNow - watchdogNew.GetCreationTime() < nExpirationDelay)) ||
|
||||||
|
(nHashNew > nHashCurrent)) {
|
||||||
|
LOCK(cs);
|
||||||
|
object_m_it it = mapObjects.find(nHashWatchdogCurrent);
|
||||||
|
if(it != mapObjects.end()) {
|
||||||
|
LogPrint("gobject", "CGovernanceManager::UpdateCurrentWatchdog -- Expiring previous current watchdog, hash = %s\n", nHashWatchdogCurrent.ToString());
|
||||||
|
it->second.fExpired = true;
|
||||||
|
if(it->second.nDeletionTime == 0) {
|
||||||
|
it->second.nDeletionTime = nNow;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
nHashWatchdogCurrent = watchdogNew.GetHash();
|
||||||
|
nTimeWatchdogCurrent = watchdogNew.GetCreationTime();
|
||||||
|
fAccept = true;
|
||||||
|
LogPrint("gobject", "CGovernanceManager::UpdateCurrentWatchdog -- Current watchdog updated to: hash = %s\n",
|
||||||
|
ArithToUint256(nHashNew).ToString());
|
||||||
|
}
|
||||||
|
|
||||||
|
return fAccept;
|
||||||
|
}
|
||||||
|
|
||||||
void CGovernanceManager::UpdateCachesAndClean()
|
void CGovernanceManager::UpdateCachesAndClean()
|
||||||
{
|
{
|
||||||
LogPrint("gobject", "CGovernanceManager::UpdateCachesAndClean\n");
|
LogPrint("gobject", "CGovernanceManager::UpdateCachesAndClean\n");
|
||||||
@ -394,6 +437,9 @@ void CGovernanceManager::UpdateCachesAndClean()
|
|||||||
it2->second.nDeletionTime = nNow;
|
it2->second.nDeletionTime = nNow;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if(it->first == nHashWatchdogCurrent) {
|
||||||
|
nHashWatchdogCurrent = uint256();
|
||||||
|
}
|
||||||
mapWatchdogObjects.erase(it++);
|
mapWatchdogObjects.erase(it++);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -435,7 +481,8 @@ void CGovernanceManager::UpdateCachesAndClean()
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string strHash = pObj->GetHash().ToString();
|
uint256 nHash = it->first;
|
||||||
|
std::string strHash = nHash.ToString();
|
||||||
|
|
||||||
// IF CACHE IS NOT DIRTY, WHY DO THIS?
|
// IF CACHE IS NOT DIRTY, WHY DO THIS?
|
||||||
if(pObj->IsSetDirtyCache()) {
|
if(pObj->IsSetDirtyCache()) {
|
||||||
@ -446,6 +493,10 @@ void CGovernanceManager::UpdateCachesAndClean()
|
|||||||
pObj->UpdateSentinelVariables();
|
pObj->UpdateSentinelVariables();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(pObj->IsSetCachedDelete() && (nHash == nHashWatchdogCurrent)) {
|
||||||
|
nHashWatchdogCurrent = uint256();
|
||||||
|
}
|
||||||
|
|
||||||
// IF DELETE=TRUE, THEN CLEAN THE MESS UP!
|
// IF DELETE=TRUE, THEN CLEAN THE MESS UP!
|
||||||
|
|
||||||
int64_t nTimeSinceDeletion = GetAdjustedTime() - pObj->GetDeletionTime();
|
int64_t nTimeSinceDeletion = GetAdjustedTime() - pObj->GetDeletionTime();
|
||||||
@ -471,7 +522,7 @@ void CGovernanceManager::UpdateCachesAndClean()
|
|||||||
++lit;
|
++lit;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(pObj->nObjectType == GOVERNANCE_OBJECT_WATCHDOG && pObj->IsSetCachedDelete()) {
|
if(pObj->nObjectType == GOVERNANCE_OBJECT_WATCHDOG) {
|
||||||
mapWatchdogObjects.erase(it->first);
|
mapWatchdogObjects.erase(it->first);
|
||||||
}
|
}
|
||||||
mapObjects.erase(it++);
|
mapObjects.erase(it++);
|
||||||
@ -903,6 +954,12 @@ bool CGovernanceManager::ProcessVote(CNode* pfrom, const CGovernanceVote& vote,
|
|||||||
}
|
}
|
||||||
|
|
||||||
CGovernanceObject& govobj = it->second;
|
CGovernanceObject& govobj = it->second;
|
||||||
|
|
||||||
|
if(govobj.IsSetCachedDelete() || govobj.IsSetExpired()) {
|
||||||
|
LogPrint("gobject", "CGovernanceObject::ProcessVote -- ignoring vote for expired or deleted object, hash = %s\n", nHashGovobj.ToString());
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
bool fOk = govobj.ProcessVote(pfrom, vote, exception);
|
bool fOk = govobj.ProcessVote(pfrom, vote, exception);
|
||||||
if(fOk) {
|
if(fOk) {
|
||||||
mapVoteToObject.Insert(nHashVote, &govobj);
|
mapVoteToObject.Insert(nHashVote, &govobj);
|
||||||
|
@ -236,6 +236,10 @@ private:
|
|||||||
|
|
||||||
hash_time_m_t mapWatchdogObjects;
|
hash_time_m_t mapWatchdogObjects;
|
||||||
|
|
||||||
|
uint256 nHashWatchdogCurrent;
|
||||||
|
|
||||||
|
int64_t nTimeWatchdogCurrent;
|
||||||
|
|
||||||
object_ref_cache_t mapVoteToObject;
|
object_ref_cache_t mapVoteToObject;
|
||||||
|
|
||||||
vote_cache_t mapInvalidVotes;
|
vote_cache_t mapInvalidVotes;
|
||||||
@ -285,7 +289,7 @@ public:
|
|||||||
std::vector<CGovernanceObject*> GetAllNewerThan(int64_t nMoreThanTime);
|
std::vector<CGovernanceObject*> GetAllNewerThan(int64_t nMoreThanTime);
|
||||||
|
|
||||||
bool IsBudgetPaymentBlock(int nBlockHeight);
|
bool IsBudgetPaymentBlock(int nBlockHeight);
|
||||||
bool AddGovernanceObject (CGovernanceObject& govobj);
|
bool AddGovernanceObject(CGovernanceObject& govobj, CNode* pfrom = NULL);
|
||||||
|
|
||||||
std::string GetRequiredPaymentsString(int nBlockHeight);
|
std::string GetRequiredPaymentsString(int nBlockHeight);
|
||||||
|
|
||||||
@ -301,6 +305,8 @@ public:
|
|||||||
mapObjects.clear();
|
mapObjects.clear();
|
||||||
mapSeenGovernanceObjects.clear();
|
mapSeenGovernanceObjects.clear();
|
||||||
mapWatchdogObjects.clear();
|
mapWatchdogObjects.clear();
|
||||||
|
nHashWatchdogCurrent = uint256();
|
||||||
|
nTimeWatchdogCurrent = 0;
|
||||||
mapVoteToObject.Clear();
|
mapVoteToObject.Clear();
|
||||||
mapInvalidVotes.Clear();
|
mapInvalidVotes.Clear();
|
||||||
mapOrphanVotes.Clear();
|
mapOrphanVotes.Clear();
|
||||||
@ -327,6 +333,8 @@ public:
|
|||||||
READWRITE(mapOrphanVotes);
|
READWRITE(mapOrphanVotes);
|
||||||
READWRITE(mapObjects);
|
READWRITE(mapObjects);
|
||||||
READWRITE(mapWatchdogObjects);
|
READWRITE(mapWatchdogObjects);
|
||||||
|
READWRITE(nHashWatchdogCurrent);
|
||||||
|
READWRITE(nTimeWatchdogCurrent);
|
||||||
READWRITE(mapLastMasternodeObject);
|
READWRITE(mapLastMasternodeObject);
|
||||||
if(ser_action.ForRead() && (strVersion != SERIALIZATION_VERSION_STRING)) {
|
if(ser_action.ForRead() && (strVersion != SERIALIZATION_VERSION_STRING)) {
|
||||||
Clear();
|
Clear();
|
||||||
@ -415,6 +423,8 @@ private:
|
|||||||
|
|
||||||
void AddCachedTriggers();
|
void AddCachedTriggers();
|
||||||
|
|
||||||
|
bool UpdateCurrentWatchdog(CGovernanceObject& watchdogNew);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
Reference in New Issue
Block a user