From c3671b57f440ea57635cb403c5c4987d9a285d84 Mon Sep 17 00:00:00 2001 From: blondfrogs Date: Fri, 9 Feb 2018 20:31:34 -0700 Subject: [PATCH] Allow rpc listunspent to have options for watchonly transactions --- src/rpcclient.cpp | 1 + src/rpcrawtransaction.cpp | 14 +++++++++++--- src/wallet.cpp | 9 +++++++-- src/wallet.h | 2 +- 4 files changed, 20 insertions(+), 6 deletions(-) diff --git a/src/rpcclient.cpp b/src/rpcclient.cpp index 0aad5e5bf5576..eb01a9ca3a702 100644 --- a/src/rpcclient.cpp +++ b/src/rpcclient.cpp @@ -72,6 +72,7 @@ static const CRPCConvertParam vRPCConvertParams[] = {"listunspent", 0}, {"listunspent", 1}, {"listunspent", 2}, + {"listunspent", 3}, {"getblock", 1}, {"getblockheader", 1}, {"gettransaction", 1}, diff --git a/src/rpcrawtransaction.cpp b/src/rpcrawtransaction.cpp index 8ae179f4fa1d6..03d99d317ec89 100644 --- a/src/rpcrawtransaction.cpp +++ b/src/rpcrawtransaction.cpp @@ -198,7 +198,7 @@ UniValue getrawtransaction(const UniValue& params, bool fHelp) #ifdef ENABLE_WALLET UniValue listunspent(const UniValue& params, bool fHelp) { - if (fHelp || params.size() > 3) + if (fHelp || params.size() > 4) throw runtime_error( "listunspent ( minconf maxconf [\"address\",...] )\n" "\nReturns array of unspent transaction outputs\n" @@ -214,6 +214,7 @@ UniValue listunspent(const UniValue& params, bool fHelp) " \"address\" (string) pivx address\n" " ,...\n" " ]\n" + "4. watchonlyconfig (numberic, optional, default=1) 1 = list regular unspent transactions, 2 = list only watchonly transactions, 3 = list all unspent transactions (including watchonly)\n" "\nResult\n" "[ (array of json object)\n" " {\n" @@ -231,7 +232,7 @@ UniValue listunspent(const UniValue& params, bool fHelp) "\nExamples\n" + HelpExampleCli("listunspent", "") + HelpExampleCli("listunspent", "6 9999999 \"[\\\"1PGFqEzfmQch1gKD3ra4k18PNj3tTUUSqg\\\",\\\"1LtvqCaApEdUGFkpKMM4MstjcaL4dKg8SP\\\"]\"") + HelpExampleRpc("listunspent", "6, 9999999 \"[\\\"1PGFqEzfmQch1gKD3ra4k18PNj3tTUUSqg\\\",\\\"1LtvqCaApEdUGFkpKMM4MstjcaL4dKg8SP\\\"]\"")); - RPCTypeCheck(params, boost::assign::list_of(UniValue::VNUM)(UniValue::VNUM)(UniValue::VARR)); + RPCTypeCheck(params, boost::assign::list_of(UniValue::VNUM)(UniValue::VNUM)(UniValue::VARR)(UniValue::VNUM)); int nMinDepth = 1; if (params.size() > 0) @@ -255,11 +256,18 @@ UniValue listunspent(const UniValue& params, bool fHelp) } } + int nWatchonlyConfig = 1; + if(params.size() > 3) { + nWatchonlyConfig = params[3].get_int(); + if (nWatchonlyConfig > 3 || nWatchonlyConfig < 1) + nWatchonlyConfig = 1; + } + UniValue results(UniValue::VARR); vector vecOutputs; assert(pwalletMain != NULL); LOCK2(cs_main, pwalletMain->cs_wallet); - pwalletMain->AvailableCoins(vecOutputs, false); + pwalletMain->AvailableCoins(vecOutputs, false, NULL, false, ALL_COINS, false, nWatchonlyConfig); BOOST_FOREACH (const COutput& out, vecOutputs) { if (out.nDepth < nMinDepth || out.nDepth > nMaxDepth) continue; diff --git a/src/wallet.cpp b/src/wallet.cpp index 5dd26eec423a3..acb9a8a1c9ac5 100644 --- a/src/wallet.cpp +++ b/src/wallet.cpp @@ -1892,7 +1892,7 @@ CAmount CWallet::GetLockedWatchOnlyBalance() const /** * populate vCoins with vector of available COutputs. */ -void CWallet::AvailableCoins(vector& vCoins, bool fOnlyConfirmed, const CCoinControl* coinControl, bool fIncludeZeroValue, AvailableCoinsType nCoinType, bool fUseIX) const +void CWallet::AvailableCoins(vector& vCoins, bool fOnlyConfirmed, const CCoinControl* coinControl, bool fIncludeZeroValue, AvailableCoinsType nCoinType, bool fUseIX, int nWatchonlyConfig) const { vCoins.clear(); @@ -1948,7 +1948,11 @@ void CWallet::AvailableCoins(vector& vCoins, bool fOnlyConfirmed, const continue; if (mine == ISMINE_NO) continue; - if (mine == ISMINE_WATCH_ONLY) + + if ((mine == ISMINE_MULTISIG || mine == ISMINE_SPENDABLE) && nWatchonlyConfig == 2) + continue; + + if (mine == ISMINE_WATCH_ONLY && nWatchonlyConfig == 1) continue; if (IsLockedCoin((*it).first, i) && nCoinType != ONLY_10000) @@ -1963,6 +1967,7 @@ void CWallet::AvailableCoins(vector& vCoins, bool fOnlyConfirmed, const fIsSpendable = true; if ((mine & ISMINE_MULTISIG) != ISMINE_NO) fIsSpendable = true; + vCoins.emplace_back(COutput(pcoin, i, nDepth, fIsSpendable)); } } diff --git a/src/wallet.h b/src/wallet.h index fb3c909cfb6a3..7906166033e44 100644 --- a/src/wallet.h +++ b/src/wallet.h @@ -358,7 +358,7 @@ class CWallet : public CCryptoKeyStore, public CValidationInterface return nWalletMaxVersion >= wf; } - void AvailableCoins(std::vector& vCoins, bool fOnlyConfirmed = true, const CCoinControl* coinControl = NULL, bool fIncludeZeroValue = false, AvailableCoinsType nCoinType = ALL_COINS, bool fUseIX = false) const; + void AvailableCoins(std::vector& vCoins, bool fOnlyConfirmed = true, const CCoinControl* coinControl = NULL, bool fIncludeZeroValue = false, AvailableCoinsType nCoinType = ALL_COINS, bool fUseIX = false, int nWatchonlyConfig = 1) const; std::map > AvailableCoinsByAddress(bool fConfirmed = true, CAmount maxCoinValue = 0); bool SelectCoinsMinConf(const CAmount& nTargetValue, int nConfMine, int nConfTheirs, std::vector vCoins, std::set >& setCoinsRet, CAmount& nValueRet) const;