Add lockUnspents option to fundrawtransaction

This commit is contained in:
João Barbosa 2016-04-06 15:56:14 +01:00 committed by Wladimir J. van der Laan
parent af4fe7fd12
commit f2d0944eb3
3 changed files with 19 additions and 6 deletions

View file

@ -2453,6 +2453,7 @@ UniValue fundrawtransaction(const UniValue& params, bool fHelp)
" \"changeAddress\" (string, optional, default pool address) The bitcoin address to receive the change\n" " \"changeAddress\" (string, optional, default pool address) The bitcoin address to receive the change\n"
" \"changePosition\" (numeric, optional, default random) The index of the change output\n" " \"changePosition\" (numeric, optional, default random) The index of the change output\n"
" \"includeWatching\" (boolean, optional, default false) Also select inputs which are watch only\n" " \"includeWatching\" (boolean, optional, default false) Also select inputs which are watch only\n"
" \"lockUnspents\" (boolean, optional, default false) Lock selected unspent outputs\n"
" }\n" " }\n"
" for backward compatibility: passing in a true instzead of an object will result in {\"includeWatching\":true}\n" " for backward compatibility: passing in a true instzead of an object will result in {\"includeWatching\":true}\n"
"\nResult:\n" "\nResult:\n"
@ -2478,6 +2479,7 @@ UniValue fundrawtransaction(const UniValue& params, bool fHelp)
CTxDestination changeAddress = CNoDestination(); CTxDestination changeAddress = CNoDestination();
int changePosition = -1; int changePosition = -1;
bool includeWatching = false; bool includeWatching = false;
bool lockUnspents = false;
if (params.size() > 1) { if (params.size() > 1) {
if (params[1].type() == UniValue::VBOOL) { if (params[1].type() == UniValue::VBOOL) {
@ -2489,7 +2491,7 @@ UniValue fundrawtransaction(const UniValue& params, bool fHelp)
UniValue options = params[1]; UniValue options = params[1];
RPCTypeCheckObj(options, boost::assign::map_list_of("changeAddress", UniValue::VSTR)("changePosition", UniValue::VNUM)("includeWatching", UniValue::VBOOL), true, true); RPCTypeCheckObj(options, boost::assign::map_list_of("changeAddress", UniValue::VSTR)("changePosition", UniValue::VNUM)("includeWatching", UniValue::VBOOL)("lockUnspents", UniValue::VBOOL), true, true);
if (options.exists("changeAddress")) { if (options.exists("changeAddress")) {
CBitcoinAddress address(options["changeAddress"].get_str()); CBitcoinAddress address(options["changeAddress"].get_str());
@ -2505,6 +2507,9 @@ UniValue fundrawtransaction(const UniValue& params, bool fHelp)
if (options.exists("includeWatching")) if (options.exists("includeWatching"))
includeWatching = options["includeWatching"].get_bool(); includeWatching = options["includeWatching"].get_bool();
if (options.exists("lockUnspents"))
lockUnspents = options["lockUnspents"].get_bool();
} }
} }
@ -2523,7 +2528,7 @@ UniValue fundrawtransaction(const UniValue& params, bool fHelp)
CAmount nFee; CAmount nFee;
string strFailReason; string strFailReason;
if(!pwalletMain->FundTransaction(tx, nFee, changePosition, strFailReason, includeWatching, changeAddress)) if(!pwalletMain->FundTransaction(tx, nFee, changePosition, strFailReason, includeWatching, lockUnspents, changeAddress))
throw JSONRPCError(RPC_INTERNAL_ERROR, strFailReason); throw JSONRPCError(RPC_INTERNAL_ERROR, strFailReason);
UniValue result(UniValue::VOBJ); UniValue result(UniValue::VOBJ);

View file

@ -1932,7 +1932,7 @@ bool CWallet::SelectCoins(const vector<COutput>& vAvailableCoins, const CAmount&
return res; return res;
} }
bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount& nFeeRet, int& nChangePosInOut, std::string& strFailReason, bool includeWatching, const CTxDestination& destChange) bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount& nFeeRet, int& nChangePosInOut, std::string& strFailReason, bool includeWatching, bool lockUnspents, const CTxDestination& destChange)
{ {
vector<CRecipient> vecSend; vector<CRecipient> vecSend;
@ -1962,7 +1962,15 @@ bool CWallet::FundTransaction(CMutableTransaction& tx, CAmount& nFeeRet, int& nC
BOOST_FOREACH(const CTxIn& txin, wtx.vin) BOOST_FOREACH(const CTxIn& txin, wtx.vin)
{ {
if (!coinControl.IsSelected(txin.prevout)) if (!coinControl.IsSelected(txin.prevout))
{
tx.vin.push_back(txin); tx.vin.push_back(txin);
if (lockUnspents)
{
LOCK2(cs_main, cs_wallet);
LockCoin(txin.prevout);
}
}
} }
return true; return true;

View file

@ -667,8 +667,8 @@ public:
bool IsSpent(const uint256& hash, unsigned int n) const; bool IsSpent(const uint256& hash, unsigned int n) const;
bool IsLockedCoin(uint256 hash, unsigned int n) const; bool IsLockedCoin(uint256 hash, unsigned int n) const;
void LockCoin(COutPoint& output); void LockCoin(const COutPoint& output);
void UnlockCoin(COutPoint& output); void UnlockCoin(const COutPoint& output);
void UnlockAllCoins(); void UnlockAllCoins();
void ListLockedCoins(std::vector<COutPoint>& vOutpts); void ListLockedCoins(std::vector<COutPoint>& vOutpts);
@ -739,7 +739,7 @@ public:
* Insert additional inputs into the transaction by * Insert additional inputs into the transaction by
* calling CreateTransaction(); * calling CreateTransaction();
*/ */
bool FundTransaction(CMutableTransaction& tx, CAmount& nFeeRet, int& nChangePosInOut, std::string& strFailReason, bool includeWatching, const CTxDestination& destChange = CNoDestination()); bool FundTransaction(CMutableTransaction& tx, CAmount& nFeeRet, int& nChangePosInOut, std::string& strFailReason, bool includeWatching, bool lockUnspents, const CTxDestination& destChange = CNoDestination());
/** /**
* Create a new transaction paying the recipients with a set of coins * Create a new transaction paying the recipients with a set of coins