From 2737edbbf38a4354ac2b5333c1b68c9020bfd30b Mon Sep 17 00:00:00 2001 From: Evan Duffield Date: Mon, 19 Jan 2015 14:25:03 -0700 Subject: [PATCH] Removed non-denomational inputs (UdjinM6) Exact amounts are now allocated directly to denominated funds then submitted to the pool. This improves anonymity by never having non-denomination inputs enter or exit the pool. Randomness has also been added to the amount of each session to improve anonymity. --- configure.ac | 2 +- src/clientversion.h | 2 +- src/darksend.cpp | 17 +++++++++++++---- src/darksend.h | 2 +- src/qt/overviewpage.cpp | 41 ++++++++++++++++++----------------------- src/version.h | 2 +- src/wallet.cpp | 5 +++++ 7 files changed, 40 insertions(+), 31 deletions(-) diff --git a/configure.ac b/configure.ac index f7cab4c2e0..6668296662 100644 --- a/configure.ac +++ b/configure.ac @@ -3,7 +3,7 @@ AC_PREREQ([2.60]) define(_CLIENT_VERSION_MAJOR, 0) define(_CLIENT_VERSION_MINOR, 11) define(_CLIENT_VERSION_REVISION, 0) -define(_CLIENT_VERSION_BUILD, 8) +define(_CLIENT_VERSION_BUILD, 9) define(_CLIENT_VERSION_IS_RELEASE, true) define(_COPYRIGHT_YEAR, 2015) AC_INIT([Darkcoin Core],[_CLIENT_VERSION_MAJOR._CLIENT_VERSION_MINOR._CLIENT_VERSION_REVISION],[info@darkcoin.io],[darkcoin]) diff --git a/src/clientversion.h b/src/clientversion.h index 91843a05cb..1deba25636 100644 --- a/src/clientversion.h +++ b/src/clientversion.h @@ -12,7 +12,7 @@ #define CLIENT_VERSION_MAJOR 0 #define CLIENT_VERSION_MINOR 11 #define CLIENT_VERSION_REVISION 0 -#define CLIENT_VERSION_BUILD 8 +#define CLIENT_VERSION_BUILD 9 diff --git a/src/darksend.cpp b/src/darksend.cpp index 9dad74ee2a..74ab8471c4 100644 --- a/src/darksend.cpp +++ b/src/darksend.cpp @@ -91,6 +91,7 @@ void ProcessMessageDarksend(CNode* pfrom, std::string& strCommand, CDataStream& } else if (strCommand == "dsa") { //DarkSend Acceptable + if (pfrom->nVersion < darkSendPool.MIN_PEER_PROTO_VERSION) { std::string strError = "incompatible version"; LogPrintf("dsa -- incompatible version! \n"); @@ -140,6 +141,7 @@ void ProcessMessageDarksend(CNode* pfrom, std::string& strCommand, CDataStream& return; } } else if (strCommand == "dsq") { //DarkSend Queue + if (pfrom->nVersion < darkSendPool.MIN_PEER_PROTO_VERSION) { return; } @@ -147,6 +149,7 @@ void ProcessMessageDarksend(CNode* pfrom, std::string& strCommand, CDataStream& CDarksendQueue dsq; vRecv >> dsq; + CService addr; if(!dsq.GetAddress(addr)) return; if(!dsq.CheckSignature()) return; @@ -156,7 +159,6 @@ void ProcessMessageDarksend(CNode* pfrom, std::string& strCommand, CDataStream& int mn = GetMasternodeByVin(dsq.vin); if(mn == -1) return; - // if the queue is ready, submit if we can if(dsq.ready) { if((CNetAddr)darkSendPool.submittedToMasternode != (CNetAddr)addr){ @@ -324,6 +326,7 @@ void ProcessMessageDarksend(CNode* pfrom, std::string& strCommand, CDataStream& } else if (strCommand == "dssu") { //DarkSend status update + if (pfrom->nVersion < darkSendPool.MIN_PEER_PROTO_VERSION) { return; } @@ -1527,6 +1530,9 @@ bool CDarkSendPool::DoAutomaticDenominating(bool fDryRun, bool ready) if(!dsq.GetProtocolVersion(protocolVersion)) continue; if(protocolVersion < MIN_PEER_PROTO_VERSION) continue; + //non-denom's are incompatible + if((dsq.nDenom & (1 << 4))) continue; + //don't reuse masternodes BOOST_FOREACH(CTxIn usedVin, vecMasternodesUsed){ if(dsq.vin == usedVin) { @@ -1537,7 +1543,7 @@ bool CDarkSendPool::DoAutomaticDenominating(bool fDryRun, bool ready) // Try to match their denominations if possible if (!pwalletMain->SelectCoinsByDenominations(dsq.nDenom, nValueMin, balanceNeedsAnonymized, vCoins, nValueIn, 0, nDarksendRounds)){ // if (!pwalletMain->SelectCoinsByDenominations(dsq.nDenom, nValueMin, balanceNeedsAnonymized, vCoins, nValueIn, -2, 0)){ - LogPrintf("DoAutomaticDenominating - Couldn't match denominations\n"); + LogPrintf("DoAutomaticDenominating - Couldn't match denominations %d\n", dsq.nDenom); continue; // } } @@ -1545,6 +1551,7 @@ bool CDarkSendPool::DoAutomaticDenominating(bool fDryRun, bool ready) // connect to masternode and submit the queue request if(ConnectNode((CAddress)addr, NULL, true)){ submittedToMasternode = addr; + LOCK(cs_vNodes); BOOST_FOREACH(CNode* pnode, vNodes) { @@ -1602,10 +1609,11 @@ bool CDarkSendPool::DoAutomaticDenominating(bool fDryRun, bool ready) LogPrintf("DoAutomaticDenominating -- attempt %d connection to masternode %s\n", sessionTries, vecMasternodes[i].addr.ToString().c_str()); if(ConnectNode((CAddress)vecMasternodes[i].addr, NULL, true)){ submittedToMasternode = vecMasternodes[i].addr; + LOCK(cs_vNodes); BOOST_FOREACH(CNode* pnode, vNodes) { - if((CNetAddr)pnode->addr != (CNetAddr)vecMasternodes[i].addr) continue; + if((CNetAddr)pnode->addr != (CNetAddr)vecMasternodes[i].addr) continue; std::string strReason; if(txCollateral == CTransaction()){ @@ -1947,6 +1955,7 @@ void CDarkSendPool::GetDenominationsToString(int nDenom, std::string& strDenom){ // bit 1 - 10DRK+1 // bit 2 - 1DRK+1 // bit 3 - .1DRK+1 + // bit 3 - non-denom strDenom = ""; @@ -1970,7 +1979,6 @@ void CDarkSendPool::GetDenominationsToString(int nDenom, std::string& strDenom){ if(strDenom.size() > 0) strDenom += "+"; strDenom += "0.1"; } - } // return a bitshifted integer representing the denominations in this list @@ -2010,6 +2018,7 @@ int CDarkSendPool::GetDenominations(const std::vector& vout){ return denom; } + int CDarkSendPool::GetDenominationsByAmounts(std::vector& vecAmount){ CScript e = CScript(); std::vector vout1; diff --git a/src/darksend.h b/src/darksend.h index f421de03ed..f9a4a3bebc 100644 --- a/src/darksend.h +++ b/src/darksend.h @@ -223,7 +223,7 @@ class CDarksendSession class CDarkSendPool { public: - static const int MIN_PEER_PROTO_VERSION = 70052; + static const int MIN_PEER_PROTO_VERSION = 70053; // clients entries std::vector myEntries; diff --git a/src/qt/overviewpage.cpp b/src/qt/overviewpage.cpp index 04bb66e039..1578d4d363 100644 --- a/src/qt/overviewpage.cpp +++ b/src/qt/overviewpage.cpp @@ -344,29 +344,6 @@ void OverviewPage::darkSendStatus() // Balance and number of transactions might have changed darkSendPool.cachedNumBlocks = nBestHeight; - if (pwalletMain->GetBalance() - pwalletMain->GetAnonymizedBalance() > 2*COIN){ - if (walletModel->getEncryptionStatus() != WalletModel::Unencrypted){ - if((nAnonymizeDarkcoinAmount*COIN)-pwalletMain->GetAnonymizedBalance() > 1.1*COIN && - walletModel->getEncryptionStatus() == WalletModel::Locked){ - - WalletModel::UnlockContext ctx(walletModel->requestUnlock(false)); - if(!ctx.isValid()){ - //unlock was cancelled - fEnableDarksend = false; - darkSendPool.cachedNumBlocks = 0; - LogPrintf("Wallet is locked and user declined to unlock. Disabling Darksend.\n"); - } - } - if((nAnonymizeDarkcoinAmount*COIN)-pwalletMain->GetAnonymizedBalance() <= 1.1*COIN && - walletModel->getEncryptionStatus() == WalletModel::Unlocked && - darkSendPool.GetMyTransactionCount() == 0){ - - LogPrintf("Darksend is complete, locking wallet.\n"); - walletModel->setWalletLocked(true); - } - } - } - /* *******************************************************/ ui->darksendEnabled->setText("Enabled"); @@ -472,6 +449,24 @@ void OverviewPage::toggleDarksend(){ QMessageBox::Ok, QMessageBox::Ok); return; } + + + if (pwalletMain->GetBalance() - pwalletMain->GetAnonymizedBalance() > 2*COIN){ + if (walletModel->getEncryptionStatus() != WalletModel::Unencrypted){ + if((nAnonymizeDarkcoinAmount*COIN)-pwalletMain->GetAnonymizedBalance() > 1.1*COIN && + walletModel->getEncryptionStatus() == WalletModel::Locked){ + + WalletModel::UnlockContext ctx(walletModel->requestUnlock(false)); + if(!ctx.isValid()){ + //unlock was cancelled + fEnableDarksend = false; + darkSendPool.cachedNumBlocks = 0; + LogPrintf("Wallet is locked and user declined to unlock. Disabling Darksend.\n"); + } + } + } + } + } darkSendPool.cachedNumBlocks = 0; diff --git a/src/version.h b/src/version.h index ba30edaccd..b1e8afa790 100644 --- a/src/version.h +++ b/src/version.h @@ -27,7 +27,7 @@ extern const std::string CLIENT_DATE; // network protocol versioning // -static const int PROTOCOL_VERSION = 70052; +static const int PROTOCOL_VERSION = 70053; // intial proto version, to be increased after version/verack negotiation static const int INIT_PROTO_VERSION = 209; diff --git a/src/wallet.cpp b/src/wallet.cpp index fb01fb14f3..a31ef914ba 100644 --- a/src/wallet.cpp +++ b/src/wallet.cpp @@ -1554,6 +1554,11 @@ bool CWallet::SelectCoinsByDenominations(int nDenom, int64_t nValueMin, int64_t if(rounds < nDarksendRoundsMin) continue; if(fFound100 && fFound10 && fFound1 && fFoundDot1){ //if fulfilled + //we can return this for submission + if(nValueRet >= nValueMin){ + //random reduce the max amount we'll submit for anonymity + nValueMax -= (rand() % (nValueMax/5)); + } //Denomination criterion has been met, we can take any matching denominations if((nDenom & (1 << 0)) && out.tx->vout[out.i].nValue == ((100*COIN)+1)) {fAccepted = true;} else if((nDenom & (1 << 1)) && out.tx->vout[out.i].nValue == ((10*COIN)+1)) {fAccepted = true;}