(trivial) governance cleanup (#1011)

* trivial governance cleanup:
- spaces
- names
- no "using namespace std;"
- few log and rpc messages adjusted
- remove unused
- use defined types
- move few members to private

* fixing after code review
This commit is contained in:
UdjinM6 2016-09-12 11:40:00 +04:00 committed by GitHub
parent 1043252d43
commit f5738c001f
7 changed files with 294 additions and 346 deletions

View File

@ -25,9 +25,6 @@
#include <boost/algorithm/string.hpp>
#include <boost/foreach.hpp>
using namespace std;
class CNode;
// DECLARE GLOBAL VARIABLES FOR GOVERNANCE CLASSES
CGovernanceTriggerManager triggerman;
@ -62,14 +59,14 @@ CAmount ParsePaymentAmount(const std::string& strAmount)
if (strAmount.empty()) {
std::ostringstream ostr;
ostr << "ParsePaymentAmount: Amount is empty";
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
if(strAmount.size() > 20) {
// String is much too long, the functions below impose stricter
// requirements
std::ostringstream ostr;
ostr << "ParsePaymentAmount: Amount string too long";
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
// Make sure the string makes sense as an amount
// Note: No spaces allowed
@ -78,22 +75,22 @@ CAmount ParsePaymentAmount(const std::string& strAmount)
if (pos != std::string::npos) {
std::ostringstream ostr;
ostr << "ParsePaymentAmount: Amount string contains invalid character";
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
pos = strAmount.find(".");
if (pos == 0) {
if (pos == 0) {
// JSON doesn't allow values to start with a decimal point
std::ostringstream ostr;
ostr << "ParsePaymentAmount: Invalid amount string, leading decimal point not allowed";
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
// Make sure there's no more than 1 decimal point
if ((pos != std::string::npos) && (strAmount.find(".", pos+1) != std::string::npos)) {
std::ostringstream ostr;
ostr << "ParsePaymentAmount: Invalid amount string, too many decimal points";
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
// Note this code is taken from AmountFromValue in rpcserver.cpp
@ -102,13 +99,13 @@ CAmount ParsePaymentAmount(const std::string& strAmount)
nAmount = 0;
std::ostringstream ostr;
ostr << "ParsePaymentAmount: ParseFixedPoint failed for string: " << strAmount;
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
if (!MoneyRange(nAmount)) {
nAmount = 0;
std::ostringstream ostr;
ostr << "ParsePaymentAmount: Invalid amount string, value outside of valid money range";
throw runtime_error(ostr.str());
throw std::runtime_error(ostr.str());
}
DBG( cout << "ParsePaymentAmount Returning true nAmount = " << nAmount << endl; );
@ -126,8 +123,8 @@ bool CGovernanceTriggerManager::AddNewTrigger(uint256 nHash)
AssertLockHeld(governance.cs);
// IF WE ALREADY HAVE THIS HASH, RETURN
if(mapTrigger.count(nHash)) {
DBG(
if(mapTrigger.count(nHash)) {
DBG(
cout << "CGovernanceTriggerManager::AddNewTrigger: Already have hash"
<< ", nHash = " << nHash.GetHex()
<< ", count = " << mapTrigger.count(nHash)
@ -136,28 +133,28 @@ bool CGovernanceTriggerManager::AddNewTrigger(uint256 nHash)
return false;
}
CSuperblock_sptr superblock;
CSuperblock_sptr pSuperblock;
try {
CSuperblock_sptr superblockTmp(new CSuperblock(nHash));
superblock = superblockTmp;
CSuperblock_sptr pSuperblockTmp(new CSuperblock(nHash));
pSuperblock = pSuperblockTmp;
}
catch(std::exception& e) {
catch(std::exception& e) {
DBG( cout << "CGovernanceTriggerManager::AddNewTrigger Error creating superblock"
<< ", e.what() = " << e.what()
<< endl; );
LogPrintf("CGovernanceTriggerManager::AddNewTrigger: Error creating superblock: %s\n", e.what());
LogPrintf("CGovernanceTriggerManager::AddNewTrigger -- Error creating superblock: %s\n", e.what());
return false;
}
catch(...) {
catch(...) {
LogPrintf("CGovernanceTriggerManager::AddNewTrigger: Unknown Error creating superblock\n");
DBG( cout << "CGovernanceTriggerManager::AddNewTrigger Error creating superblock catchall" << endl; );
return false;
}
superblock->SetStatus(SEEN_OBJECT_IS_VALID);
pSuperblock->SetStatus(SEEN_OBJECT_IS_VALID);
DBG( cout << "CGovernanceTriggerManager::AddNewTrigger: Inserting trigger" << endl; );
mapTrigger.insert(make_pair(nHash, superblock));
mapTrigger.insert(std::make_pair(nHash, pSuperblock));
DBG( cout << "CGovernanceTriggerManager::AddNewTrigger: End" << endl; );
@ -176,44 +173,43 @@ void CGovernanceTriggerManager::CleanAndRemove()
AssertLockHeld(governance.cs);
// LOOK AT THESE OBJECTS AND COMPILE A VALID LIST OF TRIGGERS
for(trigger_m_it it = mapTrigger.begin(); it != mapTrigger.end(); ++it) {
for(trigger_m_it it = mapTrigger.begin(); it != mapTrigger.end(); ++it) {
//int nNewStatus = -1;
CGovernanceObject* pObj = governance.FindGovernanceObject((*it).first);
if(!pObj) {
if(!pObj) {
continue;
}
CSuperblock_sptr& superblock = it->second;
if(!superblock) {
CSuperblock_sptr& pSuperblock = it->second;
if(!pSuperblock) {
continue;
}
// IF THIS ISN'T A TRIGGER, WHY ARE WE HERE?
if(pObj->GetObjectType() != GOVERNANCE_OBJECT_TRIGGER) {
superblock->SetStatus(SEEN_OBJECT_ERROR_INVALID);
pSuperblock->SetStatus(SEEN_OBJECT_ERROR_INVALID);
}
}
// Remove triggers that are invalid or already executed
DBG( cout << "CGovernanceTriggerManager::CleanAndRemove: mapTrigger.size() = " << mapTrigger.size() << endl; );
trigger_m_it it = mapTrigger.begin();
while(it != mapTrigger.end()) {
while(it != mapTrigger.end()) {
bool remove = false;
CSuperblock_sptr& superblock = it->second;
if(!superblock) {
CSuperblock_sptr& pSuperblock = it->second;
if(!pSuperblock) {
DBG( cout << "CGovernanceTriggerManager::CleanAndRemove: NULL superblock marked for removal " << endl; );
remove = true;
}
else {
DBG( cout << "CGovernanceTriggerManager::CleanAndRemove: superblock status = " << superblock->GetStatus() << endl; );
switch(superblock->GetStatus()) {
} else {
DBG( cout << "CGovernanceTriggerManager::CleanAndRemove: superblock status = " << pSuperblock->GetStatus() << endl; );
switch(pSuperblock->GetStatus()) {
case SEEN_OBJECT_ERROR_INVALID:
case SEEN_OBJECT_UNKNOWN:
remove = true;
break;
case SEEN_OBJECT_EXECUTED:
{
CGovernanceObject* govobj = superblock->GetGovernanceObject();
if(govobj) {
govobj->fExpired = true;
CGovernanceObject* pgovobj = pSuperblock->GetGovernanceObject();
if(pgovobj) {
pgovobj->fExpired = true;
}
}
remove = true;
@ -222,13 +218,13 @@ void CGovernanceTriggerManager::CleanAndRemove()
{
// Rough approximation: 30 days per month * 576 blocks per day
static const int nMonthlyBlocks = 30*576;
int nTriggerBlock = superblock->GetBlockStart();
int nTriggerBlock = pSuperblock->GetBlockStart();
int nExpirationBlock = nTriggerBlock + nMonthlyBlocks;
if(governance.GetCachedBlockHeight() > nExpirationBlock) {
if(governance.GetCachedBlockHeight() > nExpirationBlock) {
remove = true;
CGovernanceObject* govobj = superblock->GetGovernanceObject();
if(govobj) {
govobj->fExpired = true;
CGovernanceObject* pgovobj = pSuperblock->GetGovernanceObject();
if(pgovobj) {
pgovobj->fExpired = true;
}
}
}
@ -237,15 +233,15 @@ void CGovernanceTriggerManager::CleanAndRemove()
break;
}
}
if(remove) {
DBG(
if(remove) {
DBG(
string strdata = "NULL";
CGovernanceObject* govobj = superblock->GetGovernanceObject();
if(govobj) {
strdata = govobj->GetDataAsString();
CGovernanceObject* pgovobj = pSuperblock->GetGovernanceObject();
if(pgovobj) {
strdata = pgovobj->GetDataAsString();
}
cout << "CGovernanceTriggerManager::CleanAndRemove: Removing object: "
cout << "CGovernanceTriggerManager::CleanAndRemove: Removing object: "
<< strdata
<< endl;
);
@ -309,36 +305,36 @@ bool CSuperblockManager::IsSuperblockTriggered(int nBlockHeight)
DBG( cout << "IsSuperblockTriggered Number triggers = " << vecTriggers.size() << endl; );
BOOST_FOREACH(CSuperblock_sptr superblock, vecTriggers)
BOOST_FOREACH(CSuperblock_sptr pSuperblock, vecTriggers)
{
if(!superblock) {
if(!pSuperblock) {
DBG( cout << "IsSuperblockTriggered Not a superblock, continuing " << endl; );
continue;
}
CGovernanceObject* pObj = superblock->GetGovernanceObject();
CGovernanceObject* pObj = pSuperblock->GetGovernanceObject();
if(!pObj) {
if(!pObj) {
DBG( cout << "IsSuperblockTriggered pObj is NULL, continuing" << endl; );
continue;
}
// note : 12.1 - is epoch calculation correct?
if(nBlockHeight != superblock->GetBlockStart()) {
DBG( cout << "IsSuperblockTriggered Not the target block, continuing"
if(nBlockHeight != pSuperblock->GetBlockStart()) {
DBG( cout << "IsSuperblockTriggered Not the target block, continuing"
<< ", nBlockHeight = " << nBlockHeight
<< ", superblock->GetBlockStart() = " << superblock->GetBlockStart()
<< ", superblock->GetBlockStart() = " << pSuperblock->GetBlockStart()
<< endl; );
continue;
}
// MAKE SURE THIS TRIGGER IS ACTIVE VIA FUNDING CACHE FLAG
if(pObj->fCachedFunding) {
if(pObj->fCachedFunding) {
DBG( cout << "IsSuperblockTriggered returning true" << endl; );
return true;
}
}
else {
DBG( cout << "IsSuperblockTriggered No fCachedFunding, continuing" << endl; );
}
@ -348,7 +344,7 @@ bool CSuperblockManager::IsSuperblockTriggered(int nBlockHeight)
}
bool CSuperblockManager::GetBestSuperblock(CSuperblock_sptr& pBlock, int nBlockHeight)
bool CSuperblockManager::GetBestSuperblock(CSuperblock_sptr& pSuperblockRet, int nBlockHeight)
{
if(!CSuperblock::IsValidBlockHeight(nBlockHeight)) {
return false;
@ -358,20 +354,20 @@ bool CSuperblockManager::GetBestSuperblock(CSuperblock_sptr& pBlock, int nBlockH
std::vector<CSuperblock_sptr> vecTriggers = triggerman.GetActiveTriggers();
int nYesCount = 0;
BOOST_FOREACH(CSuperblock_sptr superblock, vecTriggers) {
if(!superblock) {
BOOST_FOREACH(CSuperblock_sptr pSuperblock, vecTriggers) {
if(!pSuperblock) {
DBG( cout << "GetBestSuperblock Not a superblock, continuing" << endl; );
continue;
}
CGovernanceObject* pObj = superblock->GetGovernanceObject();
CGovernanceObject* pObj = pSuperblock->GetGovernanceObject();
if(!pObj) {
if(!pObj) {
DBG( cout << "GetBestSuperblock pObj is NULL, continuing" << endl; );
continue;
}
if(nBlockHeight != superblock->GetBlockStart()) {
if(nBlockHeight != pSuperblock->GetBlockStart()) {
DBG( cout << "GetBestSuperblock Not the target block, continuing" << endl; );
continue;
}
@ -380,10 +376,10 @@ bool CSuperblockManager::GetBestSuperblock(CSuperblock_sptr& pBlock, int nBlockH
int nTempYesCount = pObj->GetAbsoluteYesCount(VOTE_SIGNAL_FUNDING);
DBG( cout << "GetBestSuperblock nTempYesCount = " << nTempYesCount << endl; );
if(nTempYesCount > nYesCount) {
if(nTempYesCount > nYesCount) {
nYesCount = nTempYesCount;
pBlock = superblock;
DBG( cout << "GetBestSuperblock Valid superblock found, pBlock set" << endl; );
pSuperblockRet = pSuperblock;
DBG( cout << "GetBestSuperblock Valid superblock found, pSuperblock set" << endl; );
}
}
@ -404,9 +400,9 @@ void CSuperblockManager::CreateSuperblock(CMutableTransaction& txNewRet, int nBl
// GET THE BEST SUPERBLOCK FOR THIS BLOCK HEIGHT
CSuperblock_sptr pBlock;
if(!CSuperblockManager::GetBestSuperblock(pBlock, nBlockHeight)) {
LogPrint("superblock", "CSuperblockManager::CreateSuperblock: Can't find superblock for height %d\n", nBlockHeight);
CSuperblock_sptr pSuperblock;
if(!CSuperblockManager::GetBestSuperblock(pSuperblock, nBlockHeight)) {
LogPrint("superblock", "CSuperblockManager::CreateSuperblock -- Can't find superblock for height %d\n", nBlockHeight);
DBG( cout << "CSuperblockManager::CreateSuperblock Failed to get superblock for height, returning" << endl; );
return;
}
@ -417,16 +413,16 @@ void CSuperblockManager::CreateSuperblock(CMutableTransaction& txNewRet, int nBl
// CONFIGURE SUPERBLOCK OUTPUTS
// Superblock payments are appended to the end of the coinbase vout vector
DBG( cout << "CSuperblockManager::CreateSuperblock Number payments: " << pBlock->CountPayments() << endl; );
DBG( cout << "CSuperblockManager::CreateSuperblock Number payments: " << pSuperblock->CountPayments() << endl; );
// TODO: How many payments can we add before things blow up?
// Consider at least following limits:
// - max coinbase tx size
// - max "budget" available
for(int i = 0; i < pBlock->CountPayments(); i++) {
for(int i = 0; i < pSuperblock->CountPayments(); i++) {
CGovernancePayment payment;
DBG( cout << "CSuperblockManager::CreateSuperblock i = " << i << endl; );
if(pBlock->GetPayment(i, payment)) {
if(pSuperblock->GetPayment(i, payment)) {
DBG( cout << "CSuperblockManager::CreateSuperblock Payment found " << endl; );
// SET COINBASE OUTPUT TO SUPERBLOCK SETTING
@ -445,9 +441,8 @@ void CSuperblockManager::CreateSuperblock(CMutableTransaction& txNewRet, int nBl
DBG( cout << "CSuperblockManager::CreateSuperblock Before LogPrintf call, nAmount = " << payment.nAmount << endl; );
LogPrintf("NEW Superblock : output %d (addr %s, amount %d)\n", i, address2.ToString(), payment.nAmount);
DBG( cout << "CSuperblockManager::CreateSuperblock After LogPrintf call " << endl; );
pBlock->SetExecuted();
}
else {
pSuperblock->SetExecuted();
} else {
DBG( cout << "CSuperblockManager::CreateSuperblock Payment not found " << endl; );
}
}
@ -484,26 +479,26 @@ CSuperblock(uint256& nHash)
vecPayments()
{
DBG( cout << "CSuperblock Constructor Start" << endl; );
CGovernanceObject* pGovObj = GetGovernanceObject();
if(!pGovObj) {
DBG( cout << "CSuperblock Constructor pGovObjIn is NULL, returning" << endl; );
throw runtime_error("CSuperblock: Failed to find Governance Object");
throw std::runtime_error("CSuperblock: Failed to find Governance Object");
}
DBG( cout << "CSuperblock Constructor pGovObj : "
<< pGovObj->GetDataAsString()
<< ", nObjectType = " << pGovObj->nObjectType
<< endl; );
if (pGovObj->GetObjectType() != GOVERNANCE_OBJECT_TRIGGER) {
DBG( cout << "CSuperblock Constructor pHoObj not a trigger, returning" << endl; );
throw runtime_error("CSuperblock: Governance Object not a trigger");
throw std::runtime_error("CSuperblock: Governance Object not a trigger");
}
UniValue obj = pGovObj->GetJSONObject();
// FIRST WE GET THE START EPOCH, THE DATE WHICH THE PAYMENT SHALL OCCUR
nEpochStart = obj["event_block_height"].get_int();
@ -511,7 +506,7 @@ CSuperblock(uint256& nHash)
std::string strAddresses = obj["payment_addresses"].get_str();
std::string strAmounts = obj["payment_amounts"].get_str();
ParsePaymentSchedule(strAddresses, strAmounts);
DBG( cout << "CSuperblock Constructor End" << endl; );
}
@ -571,21 +566,21 @@ void CSuperblock::ParsePaymentSchedule(std::string& strPaymentAddresses, std::st
// LOOP THROUGH THE ADDRESSES/AMOUNTS AND CREATE PAYMENTS
/*
ADDRESSES = [ADDR1|2|3|4|5\6]
AMOUNTS = [AMOUNT1|2|3|4|5\6]
ADDRESSES = [ADDR1|2|3|4|5|6]
AMOUNTS = [AMOUNT1|2|3|4|5|6]
*/
DBG( cout << "CSuperblock::ParsePaymentSchedule vecParsed1.size() = " << vecParsed1.size() << endl; );
for (int i = 0; i < (int)vecParsed1.size(); i++) {
CBitcoinAddress address(vecParsed1[i]);
if (!address.IsValid()) {
if (!address.IsValid()) {
std::ostringstream ostr;
ostr << "CSuperblock::ParsePaymentSchedule Invalid Dash Address : " << vecParsed1[i];
throw std::runtime_error(ostr.str());
}
DBG( cout << "CSuperblock::ParsePaymentSchedule i = " << i
DBG( cout << "CSuperblock::ParsePaymentSchedule i = " << i
<< ", vecParsed2[i] = " << vecParsed2[i]
<< endl; );
@ -645,7 +640,7 @@ bool CSuperblock::IsValid(const CTransaction& txNew, int nBlockHeight, CAmount b
std::string strPayeesPossible = "";
// CONFIGURE SUPERBLOCK OUTPUTS
// CONFIGURE SUPERBLOCK OUTPUTS
int nOutputs = txNew.vout.size();
int nPayments = CountPayments();
@ -719,17 +714,17 @@ std::string CSuperblockManager::GetRequiredPaymentsString(int nBlockHeight)
// GET BEST SUPERBLOCK
CSuperblock_sptr pBlock;
if(!CSuperblockManager::GetBestSuperblock(pBlock, nBlockHeight)) {
LogPrint("superblock", "CSuperblockManager::CreateSuperblock: Can't find superblock for height %d\n", nBlockHeight);
CSuperblock_sptr pSuperblock;
if(!GetBestSuperblock(pSuperblock, nBlockHeight)) {
LogPrint("superblock", "CSuperblockManager::GetRequiredPaymentsString -- Can't find superblock for height %d\n", nBlockHeight);
return "error";
}
// LOOP THROUGH SUPERBLOCK PAYMENTS, CONFIGURE OUTPUT STRING
// LOOP THROUGH SUPERBLOCK PAYMENTS, CONFIGURE OUTPUT STRING
for(int i = 0; i < pBlock->CountPayments(); i++) {
for(int i = 0; i < pSuperblock->CountPayments(); i++) {
CGovernancePayment payment;
if(pBlock->GetPayment(i, payment)) {
if(pSuperblock->GetPayment(i, payment)) {
// PRINT NICE LOG OUTPUT FOR SUPERBLOCK PAYMENT
CTxDestination address1;

View File

@ -19,16 +19,15 @@
#include "init.h"
#include "governance.h"
using namespace std;
#define TRIGGER_UNKNOWN -1
#define TRIGGER_SUPERBLOCK 1000
class CSuperblock;
class CGovernanceTrigger;
class CGovernanceTriggerManager;
class CSuperblockManager;
static const int TRIGGER_UNKNOWN = -1;
static const int TRIGGER_SUPERBLOCK = 1000;
typedef boost::shared_ptr<CSuperblock> CSuperblock_sptr;
// DECLARE GLOBAL VARIABLES FOR GOVERNANCE CLASSES
@ -44,35 +43,24 @@ std::vector<std::string> SplitBy(std::string strCommand, std::string strDelimit)
* - After triggers are activated and executed, they can be removed
*/
CAmount ParsePaymentAmount(const std::string& strAmount);
class CGovernanceTriggerManager
{
friend class CSuperblockManager;
friend class CGovernanceManager;
public: // Typedefs
private:
typedef std::map<uint256, CSuperblock_sptr> trigger_m_t;
typedef trigger_m_t::iterator trigger_m_it;
typedef trigger_m_t::const_iterator trigger_m_cit;
private:
trigger_m_t mapTrigger;
public:
CGovernanceTriggerManager()
: mapTrigger()
{}
private:
std::vector<CSuperblock_sptr> GetActiveTriggers();
bool AddNewTrigger(uint256 nHash);
void CleanAndRemove();
public:
CGovernanceTriggerManager() : mapTrigger() {}
};
/**
@ -84,7 +72,7 @@ private:
class CSuperblockManager
{
private:
static bool GetBestSuperblock(CSuperblock_sptr& pBlock, int nBlockHeight);
static bool GetBestSuperblock(CSuperblock_sptr& pSuperblockRet, int nBlockHeight);
public:
@ -103,28 +91,18 @@ public:
class CGovernancePayment
{
private:
bool fValid;
public:
CScript script;
CAmount nAmount;
bool fValid;
CGovernancePayment()
{
SetNull();
}
void SetNull()
{
script = CScript();
nAmount = 0;
fValid = false;
}
bool IsValid()
{
return fValid;
}
CGovernancePayment(CBitcoinAddress addrIn, CAmount nAmountIn)
{
try
@ -136,6 +114,15 @@ public:
SetNull(); //set fValid to false
}
}
void SetNull()
{
script = CScript();
nAmount = 0;
fValid = false;
}
bool IsValid() { return fValid; }
};
@ -143,25 +130,21 @@ public:
* Trigger : Superblock
*
* - Create payments on the network
*
* object structure:
* {
* "governance_object_id" : last_id,
* "type" : govtypes.trigger,
* "subtype" : "superblock",
* "superblock_name" : superblock_name,
* "start_epoch" : start_epoch,
* "payment_addresses" : "addr1|addr2|addr3",
* "payment_amounts" : "amount1|amount2|amount3"
* }
*/
class CSuperblock : public CGovernanceObject
{
/*
object structure:
{
"governance_object_id" : last_id,
"type" : govtypes.trigger,
"subtype" : "superblock",
"superblock_name" : superblock_name,
"start_epoch" : start_epoch,
"payment_addresses" : "addr1|addr2|addr3",
"payment_amounts" : "amount1|amount2|amount3"
}
*/
private:
uint256 nGovObjHash;

View File

@ -193,7 +193,7 @@ vote_signal_enum_t CGovernanceVoting::ConvertVoteSignal(std::string strVoteSigna
// convert custom sentinel outcomes to integer and store
try {
int i = boost::lexical_cast<int>(strVoteSignal);
int i = boost::lexical_cast<int>(strVoteSignal);
if(i < VOTE_SIGNAL_CUSTOM1 || i > VOTE_SIGNAL_CUSTOM20) {
eSignal = VOTE_SIGNAL_NONE;
}
@ -203,8 +203,8 @@ vote_signal_enum_t CGovernanceVoting::ConvertVoteSignal(std::string strVoteSigna
}
catch(std::exception const & e)
{
ostringstream ostr;
ostr << "CGovernanceVote::ConvertVoteSignal: error : " << e.what() << endl;
std::ostringstream ostr;
ostr << "CGovernanceVote::ConvertVoteSignal: error : " << e.what() << std::endl;
LogPrintf(ostr.str().c_str());
}
@ -265,28 +265,28 @@ bool CGovernanceVote::Sign(CKey& keyMasternode, CPubKey& pubKeyMasternode)
bool CGovernanceVote::IsValid(bool fSignatureCheck)
{
if(nTime > GetTime() + (60*60)){
LogPrint("gobject", "CGovernanceVote::IsValid() - vote is too far ahead of current time - %s - nTime %lli - Max Time %lli\n", GetHash().ToString(), nTime, GetTime() + (60*60));
LogPrint("gobject", "CGovernanceVote::IsValid -- vote is too far ahead of current time - %s - nTime %lli - Max Time %lli\n", GetHash().ToString(), nTime, GetTime() + (60*60));
return false;
}
// support up to 50 actions (implemented in sentinel)
if(nVoteSignal > 50)
{
LogPrint("gobject", "CGovernanceVote::IsValid() - Client attempted to vote on invalid action(%d) - %s\n", nVoteSignal, GetHash().ToString());
LogPrint("gobject", "CGovernanceVote::IsValid -- Client attempted to vote on invalid signal(%d) - %s\n", nVoteSignal, GetHash().ToString());
return false;
}
// 0=none, 1=yes, 2=no, 3=abstain. Beyond that reject votes
if(nVoteOutcome > 3)
{
LogPrint("gobject", "CGovernanceVote::IsValid() - Client attempted to vote on invalid outcome(%d) - %s\n", nVoteSignal, GetHash().ToString());
return false;
LogPrint("gobject", "CGovernanceVote::IsValid -- Client attempted to vote on invalid outcome(%d) - %s\n", nVoteSignal, GetHash().ToString());
return false;
}
CMasternode* pmn = mnodeman.Find(vinMasternode);
if(pmn == NULL)
{
LogPrint("gobject", "CGovernanceVote::IsValid() - Unknown Masternode - %s\n", vinMasternode.ToString());
LogPrint("gobject", "CGovernanceVote::IsValid -- Unknown Masternode - %s\n", vinMasternode.prevout.ToStringShort());
return false;
}

View File

@ -46,7 +46,7 @@ enum vote_signal_enum_t {
VOTE_SIGNAL_NOOP9 = 13,
VOTE_SIGNAL_NOOP10 = 14,
VOTE_SIGNAL_NOOP11 = 15,
VOTE_SIGNAL_CUSTOM1 = 16, // SENTINEL CUSTOM ACTIONS
VOTE_SIGNAL_CUSTOM1 = 16, // SENTINEL CUSTOM ACTIONS
VOTE_SIGNAL_CUSTOM2 = 17, // 16-35
VOTE_SIGNAL_CUSTOM3 = 18,
VOTE_SIGNAL_CUSTOM4 = 19,
@ -157,25 +157,25 @@ public:
*
* GET HASH WITH DETERMINISTIC VALUE OF MASTERNODE-VIN/PARENT-HASH/VOTE-SIGNAL
*
* This hash collides with previous masternode votes when they update their votes on governance objects.
* With 12.1 there's various types of votes (funding, valid, delete, etc), so this is the deterministic hash
* This hash collides with previous masternode votes when they update their votes on governance objects.
* With 12.1 there's various types of votes (funding, valid, delete, etc), so this is the deterministic hash
* that will collide with the previous vote and allow the system to update.
*
*
* --
*
* We do not include an outcome, because that can change when a masternode updates their vote from yes to no
* on funding a specific project for example.
* on funding a specific project for example.
* We do not include a time because it will be updated each time the vote is updated, changing the hash
*/
uint256 GetTypeHash() const
{
{
// CALCULATE HOW TO STORE VOTE IN governance.mapVotes
CHashWriter ss(SER_GETHASH, PROTOCOL_VERSION);
ss << vinMasternode;
ss << nParentHash;
ss << nVoteSignal;
// -- no outcome
// -- no outcome
// -- timeless
return ss.GetHash();
}
@ -195,7 +195,7 @@ public:
};
/**
/**
* 12.1.1 - CGovernanceVoteManager
* -------------------------------
*
@ -206,7 +206,7 @@ public:
- load serialized files from filesystem if needed
- calc answer
- return result
CacheUnused():
- Cache votes if lastused > 12h/24/48/etc

View File

@ -20,9 +20,6 @@
#include <boost/lexical_cast.hpp>
#include <univalue.h>
class CNode;
class CBudgetVote;
CGovernanceManager governance;
std::map<uint256, int64_t> mapAskedForGovernanceObject;
@ -43,40 +40,30 @@ CGovernanceManager::CGovernanceManager()
{}
// Accessors for thread-safe access to maps
bool CGovernanceManager::HaveObjectForHash(uint256 nHash) {
bool CGovernanceManager::HaveObjectForHash(uint256 nHash) {
LOCK(cs);
return (mapObjects.count(nHash) == 1);
}
bool CGovernanceManager::HaveVoteForHash(uint256 nHash) {
bool CGovernanceManager::HaveVoteForHash(uint256 nHash) {
LOCK(cs);
return (mapVotesByHash.count(nHash) == 1);
}
// int CGovernanceManager::GetVoteCountByHash(uint256 nHash) {
// int count = 0;
// LOCK(cs);
// count_m_cit it = mapVotesByHash.find(nHash);
// if (it != mapVotesByHash.end()) {
// count = it->second;
// }
// return count;
// }
bool CGovernanceManager::SerializeObjectForHash(uint256 nHash, CDataStream& ss) {
bool CGovernanceManager::SerializeObjectForHash(uint256 nHash, CDataStream& ss) {
LOCK(cs);
object_m_it it = mapObjects.find(nHash);
if (it == mapObjects.end()) {
if (it == mapObjects.end()) {
return false;
}
ss << it->second;
return true;
}
bool CGovernanceManager::SerializeVoteForHash(uint256 nHash, CDataStream& ss) {
bool CGovernanceManager::SerializeVoteForHash(uint256 nHash, CDataStream& ss) {
LOCK(cs);
vote_m_it it = mapVotesByHash.find(nHash);
if (it == mapVotesByHash.end()) {
if (it == mapVotesByHash.end()) {
return false;
}
ss << it->second;
@ -115,7 +102,9 @@ void CGovernanceManager::ProcessMessage(CNode* pfrom, std::string& strCommand, C
if (strCommand == NetMsgType::MNGOVERNANCESYNC)
{
// ignore such request until we are fully synced
// Ignore such requests until we are fully synced.
// We could start processing this after masternode list is synced
// but this is a heavy one so it's better to finish sync first.
if (!masternodeSync.IsSynced()) return;
uint256 nProp;
@ -135,10 +124,9 @@ void CGovernanceManager::ProcessMessage(CNode* pfrom, std::string& strCommand, C
}
}
// ask for a specific govobj and it's votes
Sync(pfrom, nProp);
LogPrint("gobject", "syncing governance objects to our peer at %s\n", pfrom->addr.ToString());
}
// A NEW GOVERNANCE OBJECT HAS ARRIVED
@ -167,14 +155,14 @@ void CGovernanceManager::ProcessMessage(CNode* pfrom, std::string& strCommand, C
return;
}
// CHECK OBJECT AGAINST LOCAL BLOCKCHAIN
// CHECK OBJECT AGAINST LOCAL BLOCKCHAIN
if(!govobj.IsValidLocally(pCurrentBlockIndex, strError, true)) {
mapSeenGovernanceObjects.insert(make_pair(govobj.GetHash(), SEEN_OBJECT_ERROR_INVALID));
mapSeenGovernanceObjects.insert(std::make_pair(govobj.GetHash(), SEEN_OBJECT_ERROR_INVALID));
LogPrintf("Governance object is invalid - %s\n", strError);
return;
}
// UPDATE CACHED VARIABLES FOR THIS OBJECT AND ADD IT TO OUR MANANGED DATA
{
@ -230,10 +218,10 @@ void CGovernanceManager::ProcessMessage(CNode* pfrom, std::string& strCommand, C
if(masternodeSync.IsSynced()) Misbehaving(pfrom->GetId(), 20);
// it could just be a non-synced masternode
mnodeman.AskForMN(pfrom, vote.GetVinMasternode());
mapSeenVotes.insert(make_pair(vote.GetHash(), SEEN_OBJECT_ERROR_INVALID));
mapSeenVotes.insert(std::make_pair(vote.GetHash(), SEEN_OBJECT_ERROR_INVALID));
return;
} else {
mapSeenVotes.insert(make_pair(vote.GetHash(), SEEN_OBJECT_IS_VALID));
mapSeenVotes.insert(std::make_pair(vote.GetHash(), SEEN_OBJECT_IS_VALID));
}
// IF EVERYTHING CHECKS OUT, UPDATE THE GOVERNANCE MANAGER
@ -255,7 +243,7 @@ void CGovernanceManager::CheckOrphanVotes()
LOCK(cs);
std::string strError = "";
std::map<uint256, CGovernanceVote>::iterator it1 = mapOrphanVotes.begin();
vote_m_it it1 = mapOrphanVotes.begin();
while(it1 != mapOrphanVotes.end()){
if(AddOrUpdateVote(((*it1).second), NULL, strError)){
LogPrintf("CGovernanceManager::CheckOrphanVotes - Governance object is known, activating and removing orphan vote\n");
@ -288,9 +276,7 @@ bool CGovernanceManager::AddGovernanceObject(CGovernanceObject& govobj)
}
// INSERT INTO OUR GOVERNANCE OBJECT MEMORY
{
mapObjects.insert(make_pair(govobj.GetHash(), govobj));
}
mapObjects.insert(std::make_pair(govobj.GetHash(), govobj));
// SHOULD WE ADD THIS OBJECT TO ANY OTHER MANANGERS?
@ -323,39 +309,36 @@ void CGovernanceManager::UpdateCachesAndClean()
// UPDATE CACHE FOR EACH OBJECT THAT IS FLAGGED DIRTYCACHE=TRUE
std::map<uint256, CGovernanceObject>::iterator it = mapObjects.begin();
object_m_it it = mapObjects.begin();
std::map<uint256, int> mapDirtyObjects;
count_m_t mapDirtyObjects;
// Clean up any expired or invalid triggers
triggerman.CleanAndRemove();
while(it != mapObjects.end())
{
{
CGovernanceObject* pObj = &((*it).second);
if(!pObj) {
if(!pObj) {
++it;
continue;
}
// IF CACHE IS NOT DIRTY, WHY DO THIS?
if(pObj->fDirtyCache) {
mapDirtyObjects.insert(make_pair((*it).first, 1));
if(pObj->fDirtyCache) {
mapDirtyObjects.insert(std::make_pair((*it).first, 1));
// UPDATE LOCAL VALIDITY AGAINST CRYPTO DATA
pObj->UpdateLocalValidity(pCurrentBlockIndex);
// UPDATE SENTINEL SIGNALING VARIABLES
pObj->UpdateSentinelVariables(pCurrentBlockIndex);
}
// IF DELETE=TRUE, THEN CLEAN THE MESS UP!
if(pObj->fCachedDelete || pObj->fExpired)
{
if(pObj->fCachedDelete || pObj->fExpired) {
LogPrintf("UpdateCachesAndClean --- erase obj %s\n", (*it).first.ToString());
mapObjects.erase(it++);
} else {
@ -388,10 +371,10 @@ CGovernanceObject *CGovernanceManager::FindGovernanceObject(const std::string &s
int nYesCount = -99999;
CGovernanceObject* pGovObj = NULL;
std::map<uint256, CGovernanceObject>::iterator it = mapObjects.begin();
while(it != mapObjects.end()){
object_m_it it = mapObjects.begin();
while(it != mapObjects.end()) {
int nGovObjYesCount = pGovObj->GetYesCount(VOTE_SIGNAL_FUNDING);
if((*it).second.strName == strName && nGovObjYesCount > nYesCount){
if((*it).second.strName == strName && nGovObjYesCount > nYesCount) {
nYesCount = nGovObjYesCount;
pGovObj = &((*it).second);
}
@ -419,13 +402,12 @@ std::vector<CGovernanceVote*> CGovernanceManager::GetMatchingVotes(const uint256
// LOOP THROUGH ALL VOTES AND FIND THOSE MATCHING USER HASH
std::map<uint256, CGovernanceVote>::iterator it2 = mapVotesByHash.begin();
while(it2 != mapVotesByHash.end()){
if((*it2).second.GetParentHash() == nParentHash)
{
vote_m_it it2 = mapVotesByHash.begin();
while(it2 != mapVotesByHash.end()) {
if((*it2).second.GetParentHash() == nParentHash) {
vecResult.push_back(&(*it2).second);
}
*it2++;
++it2;
}
return vecResult;
@ -437,7 +419,7 @@ std::vector<CGovernanceObject*> CGovernanceManager::GetAllNewerThan(int64_t nMor
std::vector<CGovernanceObject*> vGovObjs;
std::map<uint256, CGovernanceObject>::iterator it = mapObjects.begin();
object_m_it it = mapObjects.begin();
while(it != mapObjects.end())
{
// IF THIS OBJECT IS OLDER THAN TIME, CONTINUE
@ -465,9 +447,9 @@ std::vector<CGovernanceObject*> CGovernanceManager::GetAllNewerThan(int64_t nMor
//
struct sortProposalsByVotes {
bool operator()(const std::pair<CGovernanceObject*, int> &left, const std::pair<CGovernanceObject*, int> &right) {
if( left.second != right.second)
return (left.second > right.second);
return (UintToArith256(left.first->nCollateralHash) > UintToArith256(right.first->nCollateralHash));
if (left.second != right.second)
return (left.second > right.second);
return (UintToArith256(left.first->nCollateralHash) > UintToArith256(right.first->nCollateralHash));
}
};
@ -509,11 +491,11 @@ void CGovernanceManager::Sync(CNode* pfrom, uint256 nProp)
{
LOCK(cs);
std::map<uint256, CGovernanceObject>::iterator it1 = mapObjects.begin();
object_m_it it1 = mapObjects.begin();
while(it1 != mapObjects.end()) {
uint256 h = (*it1).first;
if((*it1).second.fCachedValid && ((nProp == uint256() || (h == nProp)))){
if((*it1).second.fCachedValid && (nProp == uint256() || h == nProp)) {
// Push the inventory budget proposal message over to the other client
pfrom->PushInventory(CInv(MSG_GOVERNANCE_OBJECT, h));
nInvCount++;
@ -523,7 +505,7 @@ void CGovernanceManager::Sync(CNode* pfrom, uint256 nProp)
// SYNC OUR GOVERNANCE OBJECT VOTES WITH THEIR GOVERNANCE OBJECT VOTES
std::map<uint256, CGovernanceVote>::iterator it2 = mapVotesByHash.begin();
vote_m_it it2 = mapVotesByHash.begin();
while(it2 != mapVotesByHash.end()) {
pfrom->PushInventory(CInv(MSG_GOVERNANCE_OBJECT_VOTE, (*it2).first));
nInvCount++;
@ -553,15 +535,15 @@ bool CGovernanceManager::AddOrUpdateVote(const CGovernanceVote& vote, CNode* pfr
LOCK(cs);
if(!mapObjects.count(vote.GetParentHash())) {
if(pfrom) {
// only ask for missing items after our syncing process is complete --
// only ask for missing items after our syncing process is complete --
// otherwise we'll think a full sync succeeded when they return a result
if(!masternodeSync.IsSynced()) return false;
// ADD THE VOTE AS AN ORPHAN, TO BE USED UPON RECEIVAL OF THE PARENT OBJECT
LogPrintf("CGovernanceManager::AddOrUpdateVote - Unknown object %d, asking for source\n", vote.GetParentHash().ToString());
mapOrphanVotes[vote.GetParentHash()] = vote;
// ASK FOR THIS VOTES PARENT SPECIFICALLY FROM THIS USER (THEY SHOULD HAVE IT, NO?)
if(!mapAskedForGovernanceObject.count(vote.GetParentHash())){
@ -577,14 +559,14 @@ bool CGovernanceManager::AddOrUpdateVote(const CGovernanceVote& vote, CNode* pfr
}
// Need to keep this out of the locked section
if(syncparent) {
if(syncparent) {
pfrom->PushMessage(NetMsgType::MNGOVERNANCESYNC, votehash);
}
// Reestablish lock
LOCK(cs);
// GET DETERMINISTIC HASH WHICH COLLIDES ON MASTERNODE-VIN/GOVOBJ-HASH/VOTE-SIGNAL
uint256 nTypeHash = vote.GetTypeHash();
uint256 nHash = vote.GetHash();
@ -606,7 +588,7 @@ bool CGovernanceManager::AddOrUpdateVote(const CGovernanceVote& vote, CNode* pfr
// UPDATE TO NEWEST VOTE
{
mapVotesByHash[nHash] = vote;
mapVotesByHash[nHash] = vote;
mapVotesByType[nTypeHash] = vote;
}
@ -628,12 +610,12 @@ bool CGovernanceManager::MasternodeRateCheck(const CPubKey& pubkey)
{
LOCK(cs);
count_m_it it = mapLastMasternodeTrigger.find(pubkey.GetHash());
if(it == mapLastMasternodeTrigger.end()) {
if(it == mapLastMasternodeTrigger.end()) {
return true;
}
// Allow 1 trigger per mn per cycle, with a small fudge factor
int mindiff = Params().GetConsensus().nSuperblockCycle - Params().GetConsensus().nSuperblockCycle / 10;
if((nCachedBlockHeight - it->second) > mindiff) {
if((nCachedBlockHeight - it->second) > mindiff) {
return true;
}
return false;
@ -651,7 +633,7 @@ CGovernanceObject::CGovernanceObject()
nHashParent = uint256(); //parent object, 0 is root
nRevision = 0; //object revision in the system
nCollateralHash = uint256(); //fee-tx
// CACHING FOR VARIOUS FLAGS
fCachedFunding = false;
@ -675,7 +657,7 @@ CGovernanceObject::CGovernanceObject(uint256 nHashParentIn, int nRevisionIn, std
strName = strNameIn;
nTime = nTimeIn;
nCollateralHash = nCollateralHashIn; //fee-tx
nObjectType = GOVERNANCE_OBJECT_UNKNOWN; // Avoid having an uninitialized variable
nObjectType = GOVERNANCE_OBJECT_UNKNOWN; // Avoid having an uninitialized variable
strData = strDataIn;
// CACHING FOR VARIOUS FLAGS
@ -801,7 +783,7 @@ uint256 CGovernanceObject::GetHash()
UniValue CGovernanceObject::GetJSONObject()
{
UniValue obj(UniValue::VOBJ);
if(strData.empty()) {
if(strData.empty()) {
return obj;
}
@ -818,9 +800,9 @@ UniValue CGovernanceObject::GetJSONObject()
/**
* LoadData
* --------------------------------------------------------
*
* Attempt to load data from strData
*
*
* Attempt to load data from strData
*
*/
void CGovernanceObject::LoadData()
@ -828,7 +810,7 @@ void CGovernanceObject::LoadData()
// todo : 12.1 - resolved
//return;
if(strData.empty()) {
if(strData.empty()) {
return;
}
@ -836,15 +818,15 @@ void CGovernanceObject::LoadData()
// ATTEMPT TO LOAD JSON STRING FROM STRDATA
UniValue objResult(UniValue::VOBJ);
GetData(objResult);
DBG( cout << "CGovernanceObject::LoadData strData = "
<< GetDataAsString()
<< endl; );
UniValue obj = GetJSONObject();
nObjectType = obj["type"].get_int();
}
catch(std::exception& e) {
catch(std::exception& e) {
std::ostringstream ostr;
ostr << "CGovernanceObject::LoadData Error parsing JSON"
<< ", e.what() = " << e.what();
@ -852,7 +834,7 @@ void CGovernanceObject::LoadData()
LogPrintf( ostr.str().c_str() );
return;
}
catch(...) {
catch(...) {
std::ostringstream ostr;
ostr << "CGovernanceObject::LoadData Unknown Error parsing JSON";
DBG( cout << ostr.str() << endl; );
@ -864,10 +846,10 @@ void CGovernanceObject::LoadData()
/**
* SetData - Example usage:
* --------------------------------------------------------
*
*
* Data must be stored as an encoded hex/json string.
* Other than the above requirement gov objects are data-agnostic.
*
*
*/
bool CGovernanceObject::SetData(std::string& strError, std::string strDataIn)
@ -876,7 +858,7 @@ bool CGovernanceObject::SetData(std::string& strError, std::string strDataIn)
if(strDataIn.size() > 512*4)
{
// (assumption) this is equal to pythons len(strData) > 512*4, I think
// (assumption) this is equal to pythons len(strData) > 512*4, I think
strError = "Too big.";
return false;
}
@ -888,9 +870,9 @@ bool CGovernanceObject::SetData(std::string& strError, std::string strDataIn)
/**
* GetData - Example usage:
* --------------------------------------------------------
*
*
* Decode governance object data into UniValue(VOBJ)
*
*
*/
void CGovernanceObject::GetData(UniValue& objResult)
@ -904,7 +886,7 @@ void CGovernanceObject::GetData(UniValue& objResult)
/**
* GetData - As
* --------------------------------------------------------
*
*
*/
std::string CGovernanceObject::GetDataAsHex()
@ -914,8 +896,8 @@ std::string CGovernanceObject::GetDataAsHex()
std::string CGovernanceObject::GetDataAsString()
{
vector<unsigned char> v = ParseHex(strData);
string s(v.begin(), v.end());
std::vector<unsigned char> v = ParseHex(strData);
std::string s(v.begin(), v.end());
return s;
}
@ -1006,7 +988,7 @@ CAmount CGovernanceObject::GetMinCollateralFee()
{
CAmount nMinFee = 0;
// Only 1 type has a fee for the moment but switch statement allows for future object types
switch(nObjectType) {
switch(nObjectType) {
case GOVERNANCE_OBJECT_PROPOSAL:
nMinFee = GOVERNANCE_PROPOSAL_FEE_TX;
break;
@ -1029,18 +1011,18 @@ bool CGovernanceObject::IsCollateralValid(std::string& strError)
try {
nMinFee = GetMinCollateralFee();
}
catch(std::exception& e) {
catch(std::exception& e) {
strError = e.what();
LogPrintf("CGovernanceObject::IsCollateralValid ERROR An exception occurred - %s\n", e.what());
return false;
}
uint256 nExpectedHash = GetHash();
CTransaction txCollateral;
uint256 nBlockHash;
// RETRIEVE TRANSACTION IN QUESTION
// RETRIEVE TRANSACTION IN QUESTION
if(!GetTransaction(nCollateralHash, txCollateral, Params().GetConsensus(), nBlockHash, true)){
strError = strprintf("Can't find collateral tx %s", txCollateral.ToString());
@ -1068,7 +1050,7 @@ bool CGovernanceObject::IsCollateralValid(std::string& strError)
bool foundOpReturn = false;
BOOST_FOREACH(const CTxOut o, txCollateral.vout) {
DBG( cout << "IsCollateralValid txout : " << o.ToString()
DBG( cout << "IsCollateralValid txout : " << o.ToString()
<< ", o.nValue = " << o.nValue
<< ", o.scriptPubKey = " << ScriptToAsmStr( o.scriptPubKey, false )
<< endl; );
@ -1114,7 +1096,7 @@ bool CGovernanceObject::IsCollateralValid(std::string& strError)
LogPrintf ("CGovernanceObject::IsCollateralValid - %s - %d confirmations\n", strError, nConfirmationsIn);
return false;
}
return true;
}
@ -1160,7 +1142,7 @@ std::string CGovernanceManager::ToString() const
info << "Governance Objects: " << (int)mapObjects.size() <<
", Seen Budgets: " << (int)mapSeenGovernanceObjects.size() <<
", Seen Budget Votes: " << (int)mapSeenVotes.size() <<
", VoteByHash Count: " << (int)mapVotesByHash.size() <<
", VoteByHash Count: " << (int)mapVotesByHash.size() <<
", VoteByType Count: " << (int)mapVotesByType.size();
return info.str();
@ -1170,7 +1152,7 @@ void CGovernanceManager::UpdatedBlockTip(const CBlockIndex *pindex)
{
// Note this gets called from ActivateBestChain without cs_main being held
// so it should be safe to lock our mutex here without risking a deadlock
// On the other hand it should be safe for us to access pindex without holding a lock
// On the other hand it should be safe for us to access pindex without holding a lock
// on cs_main because the CBlockIndex objects are dynamically allocated and
// presumably never deleted.
LOCK(cs);
@ -1187,7 +1169,7 @@ void CGovernanceManager::UpdatedBlockTip(const CBlockIndex *pindex)
int CGovernanceManager::CountMatchingVotes(CGovernanceObject& govobj, vote_signal_enum_t eVoteSignalIn, vote_outcome_enum_t eVoteOutcomeIn)
{
/*
*
*
* Count matching votes and return
*
*/
@ -1219,7 +1201,7 @@ void CGovernanceObject::UpdateSentinelVariables(const CBlockIndex *pCurrentBlock
// CALCULATE THE MINUMUM VOTE COUNT REQUIRED FOR FULL SIGNAL
// todo - 12.1 - should be set to `10` after governance vote compression is implemented
int nAbsVoteReq = max(Params().GetConsensus().nGovernanceMinQuorum, nMnCount / 10);
int nAbsVoteReq = std::max(Params().GetConsensus().nGovernanceMinQuorum, nMnCount / 10);
// todo - 12.1 - Temporarily set to 1 for testing - reverted
//nAbsVoteReq = 1;
@ -1230,7 +1212,7 @@ void CGovernanceObject::UpdateSentinelVariables(const CBlockIndex *pCurrentBlock
fCachedDelete = false;
fCachedEndorsed = false;
fDirtyCache = false;
// SET SENTINEL FLAGS TO TRUE IF MIMIMUM SUPPORT LEVELS ARE REACHED
// ARE ANY OF THESE FLAGS CURRENTLY ACTIVATED?

View File

@ -1,7 +1,7 @@
// Copyright (c) 2014-2016 The Dash Core developers
// Distributed under the MIT/X11 software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
#ifndef GOVERANCE_H
#define GOVERANCE_H
@ -25,25 +25,19 @@
#include <stdio.h>
#include <string.h>
using namespace std;
class CGovernanceManager;
class CGovernanceObject;
class CGovernanceVote;
static const int GOVERNANCE_OBJECT_UNKNOWN = 0;
static const int GOVERNANCE_OBJECT_PROPOSAL = 1;
static const int GOVERNANCE_OBJECT_TRIGGER = 2;
class CGovernanceManager;
class CGovernanceObject;
class CGovernanceVote;
class CNode;
static const CAmount GOVERNANCE_PROPOSAL_FEE_TX = (0.33*COIN);
static const int64_t GOVERNANCE_FEE_CONFIRMATIONS = 6;
static const int64_t GOVERNANCE_UPDATE_MIN = 60*60;
extern std::map<uint256, int64_t> mapAskedForGovernanceObject;
extern CGovernanceManager governance;
// FOR SEEN MAP ARRAYS - GOVERNANCE OBJECTS AND VOTES
static const int SEEN_OBJECT_IS_VALID = 0;
static const int SEEN_OBJECT_ERROR_INVALID = 1;
@ -51,7 +45,8 @@ static const int SEEN_OBJECT_ERROR_IMMATURE = 2;
static const int SEEN_OBJECT_EXECUTED = 3; //used for triggers
static const int SEEN_OBJECT_UNKNOWN = 4; // the default
extern std::map<uint256, int64_t> mapAskedForGovernanceObject;
extern CGovernanceManager governance;
//
// Governance Manager : Contains all proposals for the budget
@ -99,7 +94,6 @@ private:
// keep track of the scanning errors
object_m_t mapObjects;
// note: move to private for better encapsulation
count_m_t mapSeenGovernanceObjects;
count_m_t mapSeenVotes;
vote_m_t mapOrphanVotes;
@ -114,10 +108,11 @@ private:
public:
// critical section to protect the inner data structures
mutable CCriticalSection cs;
CGovernanceManager();
void ClearSeen() {
void ClearSeen()
{
LOCK(cs);
mapSeenGovernanceObjects.clear();
mapSeenVotes.clear();
@ -128,8 +123,6 @@ public:
return mapSeenGovernanceObjects.size() + mapSeenVotes.size();
}
int sizeProposals() {return (int)mapObjects.size();}
void Sync(CNode* node, uint256 nProp);
void SyncParentObjectByVote(CNode* pfrom, const CGovernanceVote& vote);
@ -155,7 +148,8 @@ public:
void CheckOrphanVotes();
void Clear(){
void Clear()
{
LOCK(cs);
LogPrint("gobject", "Governance object manager was cleared\n");
@ -167,7 +161,7 @@ public:
mapVotesByHash.clear();
mapLastMasternodeTrigger.clear();
}
std::string ToString() const;
ADD_SERIALIZE_METHODS;
@ -185,8 +179,8 @@ public:
}
void UpdatedBlockTip(const CBlockIndex *pindex);
int64_t GetLastDiffTime() {return nTimeLastDiff;}
void UpdateLastDiffTime(int64_t nTimeIn) {nTimeLastDiff=nTimeIn;}
int64_t GetLastDiffTime() { return nTimeLastDiff; }
void UpdateLastDiffTime(int64_t nTimeIn) { nTimeLastDiff = nTimeIn; }
int GetCachedBlockHeight() { return nCachedBlockHeight; }
@ -195,8 +189,6 @@ public:
bool HaveVoteForHash(uint256 nHash);
// int GetVoteCountByHash(uint256 nHash);
bool SerializeObjectForHash(uint256 nHash, CDataStream& ss);
bool SerializeVoteForHash(uint256 nHash, CDataStream& ss);
@ -224,13 +216,13 @@ public:
uint256 nHashParent; //parent object, 0 is root
int nRevision; //object revision in the system
std::string strName; //org name, username, prop name, etc.
std::string strName; //org name, username, prop name, etc.
int64_t nTime; //time this object was created
uint256 nCollateralHash; //fee-tx
std::string strData; // Data field - can be used for anything
int nObjectType;
bool fCachedLocalValidity; // is valid by blockchain
bool fCachedLocalValidity; // is valid by blockchain
std::string strLocalValidityError;
// Masternode info for signed objects
@ -287,7 +279,7 @@ public:
int GetNoCount(vote_signal_enum_t eVoteSignalIn);
int GetAbstainCount(vote_signal_enum_t eVoteSignalIn);
// FUNCTIONS FOR DEALING WITH DATA STRING
// FUNCTIONS FOR DEALING WITH DATA STRING
std::string GetDataAsHex();
std::string GetDataAsString();
@ -316,7 +308,7 @@ public:
}
private:
// FUNCTIONS FOR DEALING WITH DATA STRING
// FUNCTIONS FOR DEALING WITH DATA STRING
void LoadData();
bool SetData(std::string& strError, std::string strDataIn);

View File

@ -30,32 +30,32 @@ using namespace std;
UniValue gobject(const UniValue& params, bool fHelp)
{
string strCommand;
std::string strCommand;
if (params.size() >= 1)
strCommand = params[0].get_str();
if (fHelp ||
(strCommand != "vote-many" && strCommand != "vote-conf" && strCommand != "vote-alias" && strCommand != "prepare" && strCommand != "submit" &&
strCommand != "vote" && strCommand != "get" && strCommand != "getvotes" && strCommand != "list" && strCommand != "diff" && strCommand != "deserialize"))
throw runtime_error(
throw std::runtime_error(
"gobject \"command\"...\n"
"Manage governance objects\n"
"\nAvailable commands:\n"
" prepare - Prepare govobj by signing and creating tx\n"
" submit - Submit govobj to network\n"
" get - Get govobj by hash\n"
" getvotes - Get votes for a govobj hash\n"
" list - List all govobjs\n"
" prepare - Prepare governance object by signing and creating tx\n"
" submit - Submit governance object to network\n"
" get - Get governance object by hash\n"
" getvotes - Get votes for a governance object hash\n"
" list - List all governance objects\n"
" diff - List differences since last diff\n"
" vote-many - Vote on a governance object by all masternodes (using masternode.conf setup)\n"
" vote-alias - Vote on a governance object by masternode alias (using masternode.conf setup)\n"
" vote-conf - Vote on a governance object by masternode configured in dash.conf\n"
" vote-alias - Vote on a governance object by masternode alias\n"
" vote-many - Vote on a governance object by all masternodes (using masternode.conf setup)\n"
);
/*
------ Example Governance Item ------
------ Example Governance Item ------
gobject submit 6e622bb41bad1fb18e7f23ae96770aeb33129e18bd9efe790522488e580a0a03 0 1 1464292854 "beer-reimbursement" 5b5b22636f6e7472616374222c207b2270726f6a6563745f6e616d65223a20225c22626565722d7265696d62757273656d656e745c22222c20227061796d656e745f61646472657373223a20225c225879324c4b4a4a64655178657948726e34744744514238626a6876464564615576375c22222c2022656e645f64617465223a202231343936333030343030222c20226465736372697074696f6e5f75726c223a20225c227777772e646173687768616c652e6f72672f702f626565722d7265696d62757273656d656e745c22222c2022636f6e74726163745f75726c223a20225c22626565722d7265696d62757273656d656e742e636f6d2f3030312e7064665c22222c20227061796d656e745f616d6f756e74223a20223233342e323334323232222c2022676f7665726e616e63655f6f626a6563745f6964223a2037342c202273746172745f64617465223a202231343833323534303030227d5d5d1
*/
@ -64,8 +64,8 @@ UniValue gobject(const UniValue& params, bool fHelp)
{
std::string strHex = params[1].get_str();
vector<unsigned char> v = ParseHex(strHex);
string s(v.begin(), v.end());
std::vector<unsigned char> v = ParseHex(strHex);
std::string s(v.begin(), v.end());
UniValue u(UniValue::VOBJ);
u.read(s);
@ -90,10 +90,10 @@ UniValue gobject(const UniValue& params, bool fHelp)
uint256 hashParent;
// -- attach to root node (root node doesn't really exist, but has a hash of zero)
if(params[1].get_str() == "0") {
if(params[1].get_str() == "0") {
hashParent = uint256();
} else {
hashParent = ParseHashV(params[1], "fee-tx hash, parameter 1");
hashParent = ParseHashV(params[1], "fee-txid, parameter 1");
}
std::string strRevision = params[2].get_str();
@ -102,7 +102,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
int nTime = boost::lexical_cast<int>(strTime);
std::string strName = SanitizeString(params[4].get_str());
std::string strData = params[5].get_str();
// CREATE A NEW COLLATERAL TRANSACTION FOR THIS SPECIFIC OBJECT
CGovernanceObject govobj(hashParent, nRevision, strName, nTime, uint256(), strData);
@ -113,9 +113,9 @@ UniValue gobject(const UniValue& params, bool fHelp)
CWalletTx wtx;
if(!pwalletMain->GetBudgetSystemCollateralTX(wtx, govobj.GetHash(), govobj.GetMinCollateralFee(), false)) {
throw JSONRPCError(RPC_INTERNAL_ERROR, "Error making collateral transaction for govobj. Please check your wallet balance and make sure your wallet is unlocked.");
throw JSONRPCError(RPC_INTERNAL_ERROR, "Error making collateral transaction for governance object. Please check your wallet balance and make sure your wallet is unlocked.");
}
// -- make our change address
CReserveKey reservekey(pwalletMain);
// -- send the tx to the network
@ -124,7 +124,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
DBG( cout << "gobject: prepare strName = " << strName
<< ", strData = " << govobj.GetDataAsString()
<< ", hash = " << govobj.GetHash().GetHex()
<< ", fee_tx = " << wtx.GetHash().GetHex()
<< ", txidFee = " << wtx.GetHash().GetHex()
<< endl; );
return wtx.GetHash().ToString();
@ -134,7 +134,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
if(strCommand == "submit")
{
if ((params.size() < 6) || (params.size() > 7)) {
throw JSONRPCError(RPC_INVALID_PARAMETER, "Correct usage is 'gobject submit <parent-hash> <revision> <time> <name> <data-hex> <fee-tx>'");
throw JSONRPCError(RPC_INVALID_PARAMETER, "Correct usage is 'gobject submit <parent-hash> <revision> <time> <name> <data-hex> <fee-txid>'");
}
if(!masternodeSync.IsBlockchainSynced()) {
@ -149,7 +149,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
<< ", mnFound = " << mnFound << endl; );
if((params.size() == 6) && (!mnFound)) {
throw JSONRPCError(RPC_CLIENT_IN_INITIAL_DOWNLOAD, "Non-masternodes must include fee-tx parameter.");
throw JSONRPCError(RPC_CLIENT_IN_INITIAL_DOWNLOAD, "Non-masternodes must include fee-txid parameter.");
}
// ASSEMBLE NEW GOVERNANCE OBJECT FROM USER PARAMETERS
@ -157,10 +157,10 @@ UniValue gobject(const UniValue& params, bool fHelp)
LOCK(cs_main);
CBlockIndex* pindex = chainActive.Tip();
uint256 fee_tx;
uint256 txidFee;
if(params.size() == 7) {
fee_tx = ParseHashV(params[6], "fee-tx hash, parameter 6");
txidFee = ParseHashV(params[6], "fee-txid, parameter 6");
}
uint256 hashParent;
if(params[1].get_str() == "0") { // attach to root node (root node doesn't really exist, but has a hash of zero)
@ -178,12 +178,12 @@ UniValue gobject(const UniValue& params, bool fHelp)
std::string strName = SanitizeString(params[4].get_str());
std::string strData = params[5].get_str();
CGovernanceObject govobj(hashParent, nRevision, strName, nTime, fee_tx, strData);
CGovernanceObject govobj(hashParent, nRevision, strName, nTime, txidFee, strData);
DBG( cout << "gobject: submit strName = " << strName
<< ", strData = " << govobj.GetDataAsString()
<< ", hash = " << govobj.GetHash().GetHex()
<< ", fee_tx = " << fee_tx.GetHex()
<< ", txidFee = " << txidFee.GetHex()
<< endl; );
// Attempt to sign triggers if we are a MN
@ -220,14 +220,14 @@ UniValue gobject(const UniValue& params, bool fHelp)
std::string strVote;
hash = ParseHashV(params[1], "Object hash");
std::string strVoteAction = params[2].get_str();
std::string strVoteSignal = params[2].get_str();
std::string strVoteOutcome = params[3].get_str();
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteAction);
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteSignal);
if(eVoteSignal == VOTE_SIGNAL_NONE) {
throw JSONRPCError(RPC_INVALID_PARAMETER,
throw JSONRPCError(RPC_INVALID_PARAMETER,
"Invalid vote signal. Please using one of the following: "
"(funding|valid|delete|endorsed) OR `custom sentinel code` ");
"(funding|valid|delete|endorsed) OR `custom sentinel code` ");
}
vote_outcome_enum_t eVoteOutcome = CGovernanceVoting::ConvertVoteOutcome(strVoteOutcome);
@ -240,7 +240,6 @@ UniValue gobject(const UniValue& params, bool fHelp)
UniValue resultsObj(UniValue::VOBJ);
std::string errorMessage;
std::vector<unsigned char> vchMasterNodeSignature;
std::string strMasterNodeSignMessage;
@ -300,11 +299,11 @@ UniValue gobject(const UniValue& params, bool fHelp)
std::string strVote;
hash = ParseHashV(params[1], "Object hash");
std::string strVoteAction = params[2].get_str();
std::string strVoteSignal = params[2].get_str();
std::string strVoteOutcome = params[3].get_str();
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteAction);
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteSignal);
if(eVoteSignal == VOTE_SIGNAL_NONE) {
throw JSONRPCError(RPC_INVALID_PARAMETER,
"Invalid vote signal. Please using one of the following: "
@ -325,7 +324,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
UniValue resultsObj(UniValue::VOBJ);
BOOST_FOREACH(CMasternodeConfig::CMasternodeEntry mne, masternodeConfig.getEntries()) {
std::string errorMessage;
std::string strError;
std::vector<unsigned char> vchMasterNodeSignature;
std::string strMasterNodeSignMessage;
@ -339,7 +338,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
if(!darkSendSigner.GetKeysFromSecret(mne.getPrivKey(), keyMasternode, pubKeyMasternode)){
failed++;
statusObj.push_back(Pair("result", "failed"));
statusObj.push_back(Pair("errorMessage", "Masternode signing error, could not set key correctly: " + errorMessage));
statusObj.push_back(Pair("errorMessage", "Masternode signing error, could not set key correctly"));
resultsObj.push_back(Pair(mne.getAlias(), statusObj));
continue;
}
@ -363,7 +362,6 @@ UniValue gobject(const UniValue& params, bool fHelp)
continue;
}
std::string strError = "";
if(governance.AddOrUpdateVote(vote, NULL, strError)) {
governance.AddSeenVote(vote.GetHash(), SEEN_OBJECT_IS_VALID);
vote.Relay();
@ -398,17 +396,17 @@ UniValue gobject(const UniValue& params, bool fHelp)
// COLLECT NEEDED PARAMETRS FROM USER
hash = ParseHashV(params[1], "Object hash");
std::string strVoteAction = params[2].get_str();
std::string strVoteSignal = params[2].get_str();
std::string strVoteOutcome = params[3].get_str();
std::string strAlias = params[4].get_str();
// CONVERT NAMED SIGNAL/ACTION AND CONVERT
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteAction);
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteSignal);
if(eVoteSignal == VOTE_SIGNAL_NONE) {
throw JSONRPCError(RPC_INVALID_PARAMETER,
throw JSONRPCError(RPC_INVALID_PARAMETER,
"Invalid vote signal. Please using one of the following: "
"(funding|valid|delete|endorsed) OR `custom sentinel code` ");
"(funding|valid|delete|endorsed) OR `custom sentinel code` ");
}
vote_outcome_enum_t eVoteOutcome = CGovernanceVoting::ConvertVoteOutcome(strVoteOutcome);
@ -432,7 +430,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
if( strAlias != mne.getAlias()) continue;
// INIT OUR NEEDED VARIABLES TO EXECUTE THE VOTE
std::string errorMessage;
std::string strError;
std::vector<unsigned char> vchMasterNodeSignature;
std::string strMasterNodeSignMessage;
@ -456,8 +454,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
// SEARCH FOR THIS MASTERNODE ON THE NETWORK, THE NODE MUST BE ACTIVE TO VOTE
CMasternode* pmn = mnodeman.Find(pubKeyMasternode);
if(pmn == NULL)
{
if(pmn == NULL) {
failed++;
statusObj.push_back(Pair("result", "failed"));
statusObj.push_back(Pair("errorMessage", "Masternode must be publically available on network to vote. Masternode not found."));
@ -478,7 +475,6 @@ UniValue gobject(const UniValue& params, bool fHelp)
// UPDATE LOCAL DATABASE WITH NEW OBJECT SETTINGS
std::string strError = "";
if(governance.AddOrUpdateVote(vote, NULL, strError)) {
governance.AddSeenVote(vote.GetHash(), SEEN_OBJECT_IS_VALID);
vote.Relay();
@ -586,7 +582,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
CGovernanceObject* pGovObj = governance.FindGovernanceObject(hash);
if(pGovObj == NULL)
throw JSONRPCError(RPC_INVALID_PARAMETER, "Unknown govobj");
throw JSONRPCError(RPC_INVALID_PARAMETER, "Unknown governance object");
// REPORT BASIC OBJECT STATS
@ -602,7 +598,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
objFundingResult.push_back(Pair("AbsoluteYesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_FUNDING)-(int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_FUNDING)));
objFundingResult.push_back(Pair("YesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_FUNDING)));
objFundingResult.push_back(Pair("NoCount", (int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_FUNDING)));
objFundingResult.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_FUNDING)));
objFundingResult.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_FUNDING)));
objResult.push_back(Pair("FundingResult", objFundingResult));
// -- VALIDITY VOTING RESULTS
@ -610,7 +606,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
objValid.push_back(Pair("AbsoluteYesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_VALID)-(int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_VALID)));
objValid.push_back(Pair("YesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_VALID)));
objValid.push_back(Pair("NoCount", (int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_VALID)));
objValid.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_VALID)));
objValid.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_VALID)));
objResult.push_back(Pair("ValidResult", objValid));
// -- DELETION CRITERION VOTING RESULTS
@ -618,18 +614,18 @@ UniValue gobject(const UniValue& params, bool fHelp)
objDelete.push_back(Pair("AbsoluteYesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_DELETE)-(int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_DELETE)));
objDelete.push_back(Pair("YesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_DELETE)));
objDelete.push_back(Pair("NoCount", (int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_DELETE)));
objDelete.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_DELETE)));
objDelete.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_DELETE)));
objResult.push_back(Pair("DeleteResult", objDelete));
// -- ENDORSED VIA MASTERNODE-ELECTED BOARD
// -- ENDORSED VIA MASTERNODE-ELECTED BOARD
UniValue objEndorsed(UniValue::VOBJ);
objEndorsed.push_back(Pair("AbsoluteYesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_ENDORSED)-(int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_ENDORSED)));
objEndorsed.push_back(Pair("YesCount", (int64_t)pGovObj->GetYesCount(VOTE_SIGNAL_ENDORSED)));
objEndorsed.push_back(Pair("NoCount", (int64_t)pGovObj->GetNoCount(VOTE_SIGNAL_ENDORSED)));
objEndorsed.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_ENDORSED)));
objEndorsed.push_back(Pair("AbstainCount", (int64_t)pGovObj->GetAbstainCount(VOTE_SIGNAL_ENDORSED)));
objResult.push_back(Pair("EndorsedResult", objEndorsed));
// --
// --
std::string strError = "";
objResult.push_back(Pair("fLocalValidity", pGovObj->IsValidLocally(chainActive.Tip(), strError, false)));
objResult.push_back(Pair("fCachedValid", pGovObj->fCachedValid));
@ -641,16 +637,16 @@ UniValue gobject(const UniValue& params, bool fHelp)
if(strCommand == "getvotes")
{
if (params.size() != 2)
throw runtime_error(
throw std::runtime_error(
"Correct usage is 'gobject getvotes <governance-hash>'"
);
// COLLECT PARAMETERS FROM USER
uint256 hash = ParseHashV(params[1], "Governance hash");
// FIND OBJECT USER IS LOOKING FOR
LOCK(governance.cs);
CGovernanceObject* pGovObj = governance.FindGovernanceObject(hash);
@ -662,8 +658,8 @@ UniValue gobject(const UniValue& params, bool fHelp)
// REPORT RESULTS TO USER
UniValue bResult(UniValue::VOBJ);
// GET MATCHING VOTES BY HASH, THEN SHOW USERS VOTE INFORMATION
// GET MATCHING VOTES BY HASH, THEN SHOW USERS VOTE INFORMATION
std::vector<CGovernanceVote*> vecVotes = governance.GetMatchingVotes(hash);
BOOST_FOREACH(CGovernanceVote* pVote, vecVotes) {
@ -679,7 +675,7 @@ UniValue gobject(const UniValue& params, bool fHelp)
UniValue voteraw(const UniValue& params, bool fHelp)
{
if (fHelp || params.size() != 6)
throw runtime_error(
throw std::runtime_error(
"voteraw <masternode-tx-hash> <masternode-tx-index> <governance-hash> <vote-signal> [yes|no|abstain] <time> <vote-sig>\n"
"Compile and relay a governance vote with provided external signature instead of signing vote internally\n"
);
@ -694,9 +690,9 @@ UniValue voteraw(const UniValue& params, bool fHelp)
vote_signal_enum_t eVoteSignal = CGovernanceVoting::ConvertVoteSignal(strVoteSignal);
if(eVoteSignal == VOTE_SIGNAL_NONE) {
throw JSONRPCError(RPC_INVALID_PARAMETER,
throw JSONRPCError(RPC_INVALID_PARAMETER,
"Invalid vote signal. Please using one of the following: "
"(funding|valid|delete|endorsed) OR `custom sentinel code` ");
"(funding|valid|delete|endorsed) OR `custom sentinel code` ");
}
vote_outcome_enum_t eVoteOutcome = CGovernanceVoting::ConvertVoteOutcome(strVoteOutcome);
@ -707,7 +703,7 @@ UniValue voteraw(const UniValue& params, bool fHelp)
int64_t nTime = params[5].get_int64();
std::string strSig = params[6].get_str();
bool fInvalid = false;
vector<unsigned char> vchSig = DecodeBase64(strSig.c_str(), &fInvalid);
std::vector<unsigned char> vchSig = DecodeBase64(strSig.c_str(), &fInvalid);
if (fInvalid) {
throw JSONRPCError(RPC_INVALID_ADDRESS_OR_KEY, "Malformed base64 encoding");
@ -740,7 +736,7 @@ UniValue voteraw(const UniValue& params, bool fHelp)
UniValue getgovernanceinfo(const UniValue& params, bool fHelp)
{
if (fHelp || params.size() != 0) {
throw runtime_error(
throw std::runtime_error(
"getgovernanceinfo\n"
"Returns an object containing governance parameters.\n"
"\nResult:\n"
@ -792,7 +788,7 @@ UniValue getgovernanceinfo(const UniValue& params, bool fHelp)
UniValue getsuperblockbudget(const UniValue& params, bool fHelp)
{
if (fHelp || params.size() != 1) {
throw runtime_error(
throw std::runtime_error(
"getsuperblockbudget index\n"
"\nReturns the absolute minimum number of votes needed to trigger a governance action.\n"
"\nArguments:\n"