aboutsummaryrefslogtreecommitdiff
path: root/src/wallet/wallet.cpp
diff options
context:
space:
mode:
authorWladimir J. van der Laan <[email protected]>2016-04-15 16:23:16 +0200
committerWladimir J. van der Laan <[email protected]>2016-04-15 16:24:02 +0200
commitbe14ca5e8c0f0e8cd8ef511ccb9c41f245d62fbf (patch)
treedc4ecb77376030b326930abc247133766aee5e9b /src/wallet/wallet.cpp
parentMerge #7870: [contrib] Add MarcoFalke key and move all keys to contrib/gitian... (diff)
parentAdd lockUnspents option to fundrawtransaction (diff)
downloaddiscoin-be14ca5e8c0f0e8cd8ef511ccb9c41f245d62fbf.tar.xz
discoin-be14ca5e8c0f0e8cd8ef511ccb9c41f245d62fbf.zip
Merge #7518: Add multiple options to fundrawtransaction
f2d0944 Add lockUnspents option to fundrawtransaction (João Barbosa) af4fe7f Add change options to fundrawtransaction (João Barbosa) 41e835d Add strict flag to RPCTypeCheckObj (João Barbosa)
Diffstat (limited to 'src/wallet/wallet.cpp')
-rw-r--r--src/wallet/wallet.cpp42
1 files changed, 31 insertions, 11 deletions
diff --git a/src/wallet/wallet.cpp b/src/wallet/wallet.cpp
index e8c946671..8161c659a 100644
--- a/src/wallet/wallet.cpp
+++ b/src/wallet/wallet.cpp
@@ -1932,7 +1932,7 @@ bool CWallet::SelectCoins(const vector<COutput>& vAvailableCoins, const CAmount&
return res;
}
-bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount &nFeeRet, int& nChangePosRet, std::string& strFailReason, bool includeWatching)
+bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount& nFeeRet, int& nChangePosInOut, std::string& strFailReason, bool includeWatching, bool lockUnspents, const CTxDestination& destChange)
{
vector<CRecipient> vecSend;
@@ -1944,6 +1944,7 @@ bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount &nFeeRet, int& nC
}
CCoinControl coinControl;
+ coinControl.destChange = destChange;
coinControl.fAllowOtherInputs = true;
coinControl.fAllowWatchOnly = includeWatching;
BOOST_FOREACH(const CTxIn& txin, tx.vin)
@@ -1951,26 +1952,35 @@ bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount &nFeeRet, int& nC
CReserveKey reservekey(this);
CWalletTx wtx;
- if (!CreateTransaction(vecSend, wtx, reservekey, nFeeRet, nChangePosRet, strFailReason, &coinControl, false))
+ if (!CreateTransaction(vecSend, wtx, reservekey, nFeeRet, nChangePosInOut, strFailReason, &coinControl, false))
return false;
- if (nChangePosRet != -1)
- tx.vout.insert(tx.vout.begin() + nChangePosRet, wtx.vout[nChangePosRet]);
+ if (nChangePosInOut != -1)
+ tx.vout.insert(tx.vout.begin() + nChangePosInOut, wtx.vout[nChangePosInOut]);
// Add new txins (keeping original txin scriptSig/order)
BOOST_FOREACH(const CTxIn& txin, wtx.vin)
{
if (!coinControl.IsSelected(txin.prevout))
+ {
tx.vin.push_back(txin);
+
+ if (lockUnspents)
+ {
+ LOCK2(cs_main, cs_wallet);
+ LockCoin(txin.prevout);
+ }
+ }
}
return true;
}
bool CWallet::CreateTransaction(const vector<CRecipient>& vecSend, CWalletTx& wtxNew, CReserveKey& reservekey, CAmount& nFeeRet,
- int& nChangePosRet, std::string& strFailReason, const CCoinControl* coinControl, bool sign)
+ int& nChangePosInOut, std::string& strFailReason, const CCoinControl* coinControl, bool sign)
{
CAmount nValue = 0;
+ int nChangePosRequest = nChangePosInOut;
unsigned int nSubtractFeeFromAmount = 0;
BOOST_FOREACH (const CRecipient& recipient, vecSend)
{
@@ -2036,10 +2046,10 @@ bool CWallet::CreateTransaction(const vector<CRecipient>& vecSend, CWalletTx& wt
// Start with no fee and loop until there is enough fee
while (true)
{
+ nChangePosInOut = nChangePosRequest;
txNew.vin.clear();
txNew.vout.clear();
wtxNew.fFromMe = true;
- nChangePosRet = -1;
bool fFirst = true;
CAmount nValueToSelect = nValue;
@@ -2159,14 +2169,24 @@ bool CWallet::CreateTransaction(const vector<CRecipient>& vecSend, CWalletTx& wt
// add the dust to the fee.
if (newTxOut.IsDust(::minRelayTxFee))
{
+ nChangePosInOut = -1;
nFeeRet += nChange;
reservekey.ReturnKey();
}
else
{
- // Insert change txn at random position:
- nChangePosRet = GetRandInt(txNew.vout.size()+1);
- vector<CTxOut>::iterator position = txNew.vout.begin()+nChangePosRet;
+ if (nChangePosInOut == -1)
+ {
+ // Insert change txn at random position:
+ nChangePosInOut = GetRandInt(txNew.vout.size()+1);
+ }
+ else if (nChangePosInOut > txNew.vout.size())
+ {
+ strFailReason = _("Change index out of range");
+ return false;
+ }
+
+ vector<CTxOut>::iterator position = txNew.vout.begin()+nChangePosInOut;
txNew.vout.insert(position, newTxOut);
}
}
@@ -2842,13 +2862,13 @@ void CWallet::GetScriptForMining(boost::shared_ptr<CReserveScript> &script)
script->reserveScript = CScript() << ToByteVector(pubkey) << OP_CHECKSIG;
}
-void CWallet::LockCoin(COutPoint& output)
+void CWallet::LockCoin(const COutPoint& output)
{
AssertLockHeld(cs_wallet); // setLockedCoins
setLockedCoins.insert(output);
}
-void CWallet::UnlockCoin(COutPoint& output)
+void CWallet::UnlockCoin(const COutPoint& output)
{
AssertLockHeld(cs_wallet); // setLockedCoins
setLockedCoins.erase(output);