Skip to content

Commit c233181

Browse files
FornaxACevap
authored and
Cevap
committed
Merged in qt-display-stake (pull request #29)
Add coinstakes and masternode reward types to Qt's transaction overview display Approved-by: Cevap
2 parents 8dc3275 + ae5721b commit c233181

15 files changed

+124
-47
lines changed

src/coins.cpp

+2-1
Original file line numberDiff line numberDiff line change
@@ -89,12 +89,13 @@ void CCoinsViewCache::AddCoin(const COutPoint &outpoint, Coin&& coin, bool possi
8989

9090
void AddCoins(CCoinsViewCache& cache, const CTransaction &tx, int nHeight, bool check) {
9191
bool fCoinbase = tx.IsCoinBase();
92+
bool fCoinstake = tx.IsCoinStake();
9293
const uint256& txid = tx.GetHash();
9394
for (size_t i = 0; i < tx.vout.size(); ++i) {
9495
bool overwrite = check ? cache.HaveCoin(COutPoint(txid, i)) : fCoinbase;
9596
// Always set the possible_overwrite flag to AddCoin for coinbase txn, in order to correctly
9697
// deal with the pre-BIP30 occurrences of duplicate coinbase transactions.
97-
cache.AddCoin(COutPoint(txid, i), Coin(tx.vout[i], nHeight, fCoinbase), overwrite);
98+
cache.AddCoin(COutPoint(txid, i), Coin(tx.vout[i], nHeight, fCoinbase, fCoinstake), overwrite);
9899
}
99100
}
100101

src/coins.h

+14-6
Original file line numberDiff line numberDiff line change
@@ -34,31 +34,38 @@ class Coin
3434

3535
//! whether containing transaction was a coinbase
3636
unsigned int fCoinBase : 1;
37+
//! whether containing transaction was a coinstake
38+
unsigned int fCoinStake : 1;
3739

3840
//! at which height this containing transaction was included in the active block chain
39-
uint32_t nHeight : 31;
41+
uint32_t nHeight : 30;
4042

4143
//! construct a Coin from a CTxOut and height/coinbase information.
42-
Coin(CTxOut&& outIn, int nHeightIn, bool fCoinBaseIn) : out(std::move(outIn)), fCoinBase(fCoinBaseIn), nHeight(nHeightIn) {}
43-
Coin(const CTxOut& outIn, int nHeightIn, bool fCoinBaseIn) : out(outIn), fCoinBase(fCoinBaseIn),nHeight(nHeightIn) {}
44+
Coin(CTxOut&& outIn, int nHeightIn, bool fCoinBaseIn, bool fCoinStakeIn) : out(std::move(outIn)), fCoinBase(fCoinBaseIn), fCoinStake(fCoinStakeIn), nHeight(nHeightIn) {}
45+
Coin(const CTxOut& outIn, int nHeightIn, bool fCoinBaseIn, bool fCoinStakeIn) : out(outIn), fCoinBase(fCoinBaseIn), fCoinStake(fCoinStakeIn), nHeight(nHeightIn) {}
4446

4547
void Clear() {
4648
out.SetNull();
4749
fCoinBase = false;
50+
fCoinStake = false;
4851
nHeight = 0;
4952
}
5053

5154
//! empty constructor
52-
Coin() : fCoinBase(false), nHeight(0) { }
55+
Coin() : fCoinBase(false), fCoinStake(false), nHeight(0) { }
5356

5457
bool IsCoinBase() const {
5558
return fCoinBase;
5659
}
5760

61+
bool IsCoinStake() const {
62+
return fCoinStake;
63+
}
64+
5865
template<typename Stream>
5966
void Serialize(Stream &s) const {
6067
assert(!IsSpent());
61-
uint32_t code = nHeight * 2 + fCoinBase;
68+
uint32_t code = nHeight * 4 + fCoinStake * 2 + fCoinBase;
6269
::Serialize(s, VARINT(code));
6370
::Serialize(s, CTxOutCompressor(REF(out)));
6471
}
@@ -67,7 +74,8 @@ class Coin
6774
void Unserialize(Stream &s) {
6875
uint32_t code = 0;
6976
::Unserialize(s, VARINT(code));
70-
nHeight = code >> 1;
77+
nHeight = code >> 2;
78+
fCoinStake = (code >> 1) & 1;
7179
fCoinBase = code & 1;
7280
::Unserialize(s, REF(CTxOutCompressor(out)));
7381
}

src/consensus/tx_verify.cpp

+16-1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
#include "consensus.h"
88
#include "primitives/transaction.h"
99
#include "script/interpreter.h"
10+
#include "tokens/groups.h"
1011
#include "validation.h"
1112

1213
// TODO remove the following dependencies
@@ -228,13 +229,27 @@ bool Consensus::CheckTxInputs(const CTransaction& tx, CValidationState& state, c
228229
const Coin& coin = inputs.AccessCoin(prevout);
229230
assert(!coin.IsSpent());
230231

231-
// If prev is coinbase, check that it's matured
232+
// If prev is coinbase, coinstake or group authority confirguration, check that it's matured
233+
if (coin.IsCoinStake() && nSpendHeight - coin.nHeight < (nSpendHeight <= 100 ? (int)10 : Params().nCoinbaseMaturity)) {
234+
return state.Invalid(false,
235+
REJECT_INVALID, "bad-txns-premature-spend-of-coinstake",
236+
strprintf("tried to spend coinstake at depth %d", nSpendHeight - coin.nHeight));
237+
}
238+
232239
if (coin.IsCoinBase() && nSpendHeight - coin.nHeight < (nSpendHeight <= 100 ? (int)10 : Params().nCoinbaseMaturity)) {
233240
return state.Invalid(false,
234241
REJECT_INVALID, "bad-txns-premature-spend-of-coinbase",
235242
strprintf("tried to spend coinbase at depth %d", nSpendHeight - coin.nHeight));
236243
}
237244

245+
if (IsOutputGroupedAuthority(coin.out)) {
246+
if (nSpendHeight - coin.nHeight < Params().nOpGroupNewRequiredConfirmations) {
247+
return state.Invalid(
248+
error("CheckInputs() : tried to use a token authority before it reached maturity (%d confirmations)", Params().nOpGroupNewRequiredConfirmations),
249+
REJECT_INVALID, "bad-txns-premature-use-of-token-authority");
250+
}
251+
}
252+
238253
// Check for negative or overflow input values
239254
nValueIn += coin.out.nValue;
240255
if (!MoneyRange(coin.out.nValue) || !MoneyRange(nValueIn)) {

src/qt/transactiondesc.cpp

+5-5
Original file line numberDiff line numberDiff line change
@@ -92,11 +92,11 @@ QString TransactionDesc::toHTML(CWallet *wallet, CWalletTx &wtx, TransactionReco
9292
//
9393
// From
9494
//
95-
if (wtx.IsCoinBase())
95+
if (wtx.IsCoinBase() || wtx.IsCoinStake())
9696
{
9797
strHTML += "<b>" + tr("Source") + ":</b> " + tr("Generated") + "<br>";
9898
}
99-
else if (wtx.mapValue.count("from") && !wtx.mapValue["from"].empty())
99+
if (wtx.mapValue.count("from") && !wtx.mapValue["from"].empty())
100100
{
101101
// Online transaction
102102
strHTML += "<b>" + tr("From") + ":</b> " + GUIUtil::HtmlEscape(wtx.mapValue["from"]) + "<br>";
@@ -143,7 +143,7 @@ QString TransactionDesc::toHTML(CWallet *wallet, CWalletTx &wtx, TransactionReco
143143
//
144144
// Amount
145145
//
146-
if (wtx.IsCoinBase() && nCredit == 0)
146+
if ((wtx.IsCoinBase() || wtx.IsCoinStake()) && nCredit == 0)
147147
{
148148
//
149149
// Coinbase
@@ -280,9 +280,9 @@ QString TransactionDesc::toHTML(CWallet *wallet, CWalletTx &wtx, TransactionReco
280280
}
281281
}
282282

283-
if (wtx.IsCoinBase())
283+
if (wtx.IsCoinBase() || wtx.IsCoinStake())
284284
{
285-
quint32 numBlocksToMaturity = Consensus::Params().nCoinbaseMaturity + 1;
285+
int numBlocksToMaturity = Consensus::Params().nCoinbaseMaturity;
286286
strHTML += "<br>" + tr("Generated coins must mature %1 blocks before they can be spent. When you generated this block, it was broadcast to the network to be added to the block chain. If it fails to get into the chain, its state will change to \"not accepted\" and it won't be spendable. This may occasionally happen if another node generates a block within a few seconds of yours.").arg(QString::number(numBlocksToMaturity)) + "<br>";
287287
}
288288

src/qt/transactiontablemodel.cpp

+11
Original file line numberDiff line numberDiff line change
@@ -433,6 +433,11 @@ QString TransactionTableModel::formatTxType(const TransactionRecord *wtx) const
433433
case TransactionRecord::PrivateSend:
434434
return tr("PrivateSend");
435435

436+
case TransactionRecord::MNReward:
437+
return tr("Masternode Reward");
438+
case TransactionRecord::StakeMint:
439+
return tr("ION Stake");
440+
436441
default:
437442
return QString();
438443
}
@@ -443,6 +448,8 @@ QVariant TransactionTableModel::txAddressDecoration(const TransactionRecord *wtx
443448
switch(wtx->type)
444449
{
445450
case TransactionRecord::Generated:
451+
case TransactionRecord::StakeMint:
452+
case TransactionRecord::MNReward:
446453
return QIcon(":/icons/tx_mined");
447454
case TransactionRecord::RecvWithPrivateSend:
448455
case TransactionRecord::RecvWithAddress:
@@ -473,6 +480,8 @@ QString TransactionTableModel::formatTxToAddress(const TransactionRecord *wtx, b
473480
case TransactionRecord::RecvWithPrivateSend:
474481
case TransactionRecord::SendToAddress:
475482
case TransactionRecord::Generated:
483+
case TransactionRecord::StakeMint:
484+
case TransactionRecord::MNReward:
476485
case TransactionRecord::PrivateSend:
477486
return formatAddressLabel(wtx->strAddress, QString::fromStdString(wtx->status.label), tooltip) + watchAddress;
478487
case TransactionRecord::SendToOther:
@@ -491,6 +500,8 @@ QVariant TransactionTableModel::addressColor(const TransactionRecord *wtx) const
491500
case TransactionRecord::RecvWithAddress:
492501
case TransactionRecord::SendToAddress:
493502
case TransactionRecord::Generated:
503+
case TransactionRecord::StakeMint:
504+
case TransactionRecord::MNReward:
494505
case TransactionRecord::PrivateSend:
495506
case TransactionRecord::RecvWithPrivateSend:
496507
{

src/qt/transactionview.cpp

+2
Original file line numberDiff line numberDiff line change
@@ -108,6 +108,8 @@ TransactionView::TransactionView(const PlatformStyle *platformStyle, QWidget *pa
108108
typeWidget->addItem(tr("PrivateSend Collateral Payment"), TransactionFilterProxy::TYPE(TransactionRecord::PrivateSendCollateralPayment));
109109
typeWidget->addItem(tr("To yourself"), TransactionFilterProxy::TYPE(TransactionRecord::SendToSelf));
110110
typeWidget->addItem(tr("Mined"), TransactionFilterProxy::TYPE(TransactionRecord::Generated));
111+
typeWidget->addItem(tr("Minted"), TransactionFilterProxy::TYPE(TransactionRecord::StakeMint));
112+
typeWidget->addItem(tr("Masternode Reward"), TransactionFilterProxy::TYPE(TransactionRecord::MNReward));
111113
typeWidget->addItem(tr("Other"), TransactionFilterProxy::TYPE(TransactionRecord::Other));
112114
typeWidget->setCurrentIndex(settings.value("transactionType").toInt());
113115

src/rpc/blockchain.cpp

+4-3
Original file line numberDiff line numberDiff line change
@@ -1069,7 +1069,7 @@ static void ApplyStats(CCoinsStats &stats, CHashWriter& ss, const uint256& hash,
10691069
{
10701070
assert(!outputs.empty());
10711071
ss << hash;
1072-
ss << VARINT(outputs.begin()->second.nHeight * 2 + outputs.begin()->second.fCoinBase);
1072+
ss << VARINT(outputs.begin()->second.nHeight * 4 + outputs.begin()->second.fCoinStake * 2 + outputs.begin()->second.fCoinBase);
10731073
stats.nTransactions++;
10741074
for (const auto output : outputs) {
10751075
ss << VARINT(output.first + 1);
@@ -1288,6 +1288,7 @@ UniValue gettxout(const JSONRPCRequest& request)
12881288
ScriptPubKeyToUniv(coin.out.scriptPubKey, o, true);
12891289
ret.push_back(Pair("scriptPubKey", o));
12901290
ret.push_back(Pair("coinbase", (bool)coin.fCoinBase));
1291+
ret.push_back(Pair("coinstake", (bool)coin.fCoinStake));
12911292

12921293
return ret;
12931294
}
@@ -1861,8 +1862,8 @@ static inline bool SetHasKeys(const std::set<T>& set, const Tk& key, const Args&
18611862
return (set.count(key) != 0) || SetHasKeys(set, args...);
18621863
}
18631864

1864-
// outpoint (needed for the utxo index) + nHeight + fCoinBase
1865-
static constexpr size_t PER_UTXO_OVERHEAD = sizeof(COutPoint) + sizeof(uint32_t) + sizeof(bool);
1865+
// outpoint (needed for the utxo index) + nHeight + fCoinBase + fCoinStake
1866+
static constexpr size_t PER_UTXO_OVERHEAD = sizeof(COutPoint) + sizeof(uint32_t) + sizeof(bool) + sizeof(bool);
18661867

18671868
static UniValue getblockstats(const JSONRPCRequest& request)
18681869
{

src/test/coins_tests.cpp

+22-21
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ bool operator==(const Coin &a, const Coin &b) {
2626
// Empty Coin objects are always equal.
2727
if (a.IsSpent() && b.IsSpent()) return true;
2828
return a.fCoinBase == b.fCoinBase &&
29+
a.fCoinStake == b.fCoinStake &&
2930
a.nHeight == b.nHeight &&
3031
a.out == b.out;
3132
}
@@ -372,7 +373,7 @@ BOOST_AUTO_TEST_CASE(updatecoins_simulation_test)
372373
// Update the expected result to know about the new output coins
373374
assert(tx.vout.size() == 1);
374375
const COutPoint outpoint(tx.GetHash(), 0);
375-
result[outpoint] = Coin(tx.vout[0], height, CTransaction(tx).IsCoinBase());
376+
result[outpoint] = Coin(tx.vout[0], height, CTransaction(tx).IsCoinBase(), CTransaction(tx).IsCoinStake());
376377

377378
// Call UpdateCoins on the top cache
378379
CTxUndo undo;
@@ -707,7 +708,7 @@ BOOST_AUTO_TEST_CASE(ccoins_spend)
707708
CheckSpendCoins(VALUE1, VALUE2, ABSENT, DIRTY|FRESH, NO_ENTRY );
708709
}
709710

710-
void CheckAddCoinBase(CAmount base_value, CAmount cache_value, CAmount modify_value, CAmount expected_value, char cache_flags, char expected_flags, bool coinbase)
711+
void CheckAddCoinBase(CAmount base_value, CAmount cache_value, CAmount modify_value, CAmount expected_value, char cache_flags, char expected_flags, bool coinbase, bool coinstake)
711712
{
712713
SingleEntryCacheTest test(base_value, cache_value, cache_flags);
713714

@@ -716,7 +717,7 @@ void CheckAddCoinBase(CAmount base_value, CAmount cache_value, CAmount modify_va
716717
try {
717718
CTxOut output;
718719
output.nValue = modify_value;
719-
test.cache.AddCoin(OUTPOINT, Coin(std::move(output), 1, coinbase), coinbase);
720+
test.cache.AddCoin(OUTPOINT, Coin(std::move(output), 1, coinbase, coinstake), coinbase);
720721
test.cache.SelfTest();
721722
GetCoinsMapEntry(test.cache.map(), result_value, result_flags);
722723
} catch (std::logic_error& e) {
@@ -750,24 +751,24 @@ BOOST_AUTO_TEST_CASE(ccoins_add)
750751
* Cache Write Result Cache Result potential_overwrite
751752
* Value Value Value Flags Flags
752753
*/
753-
CheckAddCoin(ABSENT, VALUE3, VALUE3, NO_ENTRY , DIRTY|FRESH, false);
754-
CheckAddCoin(ABSENT, VALUE3, VALUE3, NO_ENTRY , DIRTY , true );
755-
CheckAddCoin(PRUNED, VALUE3, VALUE3, 0 , DIRTY|FRESH, false);
756-
CheckAddCoin(PRUNED, VALUE3, VALUE3, 0 , DIRTY , true );
757-
CheckAddCoin(PRUNED, VALUE3, VALUE3, FRESH , DIRTY|FRESH, false);
758-
CheckAddCoin(PRUNED, VALUE3, VALUE3, FRESH , DIRTY|FRESH, true );
759-
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY , DIRTY , false);
760-
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY , DIRTY , true );
761-
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY|FRESH, DIRTY|FRESH, false);
762-
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY|FRESH, DIRTY|FRESH, true );
763-
CheckAddCoin(VALUE2, VALUE3, FAIL , 0 , NO_ENTRY , false);
764-
CheckAddCoin(VALUE2, VALUE3, VALUE3, 0 , DIRTY , true );
765-
CheckAddCoin(VALUE2, VALUE3, FAIL , FRESH , NO_ENTRY , false);
766-
CheckAddCoin(VALUE2, VALUE3, VALUE3, FRESH , DIRTY|FRESH, true );
767-
CheckAddCoin(VALUE2, VALUE3, FAIL , DIRTY , NO_ENTRY , false);
768-
CheckAddCoin(VALUE2, VALUE3, VALUE3, DIRTY , DIRTY , true );
769-
CheckAddCoin(VALUE2, VALUE3, FAIL , DIRTY|FRESH, NO_ENTRY , false);
770-
CheckAddCoin(VALUE2, VALUE3, VALUE3, DIRTY|FRESH, DIRTY|FRESH, true );
754+
CheckAddCoin(ABSENT, VALUE3, VALUE3, NO_ENTRY , DIRTY|FRESH, false, false);
755+
CheckAddCoin(ABSENT, VALUE3, VALUE3, NO_ENTRY , DIRTY , true , false);
756+
CheckAddCoin(PRUNED, VALUE3, VALUE3, 0 , DIRTY|FRESH, false, false);
757+
CheckAddCoin(PRUNED, VALUE3, VALUE3, 0 , DIRTY , true , false);
758+
CheckAddCoin(PRUNED, VALUE3, VALUE3, FRESH , DIRTY|FRESH, false, false);
759+
CheckAddCoin(PRUNED, VALUE3, VALUE3, FRESH , DIRTY|FRESH, true , false);
760+
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY , DIRTY , false, false);
761+
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY , DIRTY , true , false);
762+
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY|FRESH, DIRTY|FRESH, false, false);
763+
CheckAddCoin(PRUNED, VALUE3, VALUE3, DIRTY|FRESH, DIRTY|FRESH, true , false);
764+
CheckAddCoin(VALUE2, VALUE3, FAIL , 0 , NO_ENTRY , false, false);
765+
CheckAddCoin(VALUE2, VALUE3, VALUE3, 0 , DIRTY , true , false);
766+
CheckAddCoin(VALUE2, VALUE3, FAIL , FRESH , NO_ENTRY , false, false);
767+
CheckAddCoin(VALUE2, VALUE3, VALUE3, FRESH , DIRTY|FRESH, true , false);
768+
CheckAddCoin(VALUE2, VALUE3, FAIL , DIRTY , NO_ENTRY , false, false);
769+
CheckAddCoin(VALUE2, VALUE3, VALUE3, DIRTY , DIRTY , true , false);
770+
CheckAddCoin(VALUE2, VALUE3, FAIL , DIRTY|FRESH, NO_ENTRY , false, false);
771+
CheckAddCoin(VALUE2, VALUE3, VALUE3, DIRTY|FRESH, DIRTY|FRESH, true , false);
771772
}
772773

773774
void CheckWriteCoins(CAmount parent_value, CAmount child_value, CAmount expected_value, char parent_flags, char child_flags, char expected_flags)

src/transactionrecord.cpp

+30-2
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,35 @@ std::vector<TransactionRecord> TransactionRecord::decomposeTransaction(const CWa
3838
uint256 hash = wtx.GetHash();
3939
std::map<std::string, std::string> mapValue = wtx.mapValue;
4040

41-
if (nNet > 0 || wtx.IsCoinBase())
41+
if (wtx.tx->IsCoinStake()) {
42+
TransactionRecord sub(hash, nTime);
43+
CTxDestination address;
44+
if (!ExtractDestination(wtx.tx->vout[1].scriptPubKey, address))
45+
return parts;
46+
47+
if (isminetype mine = wallet->IsMine(wtx.tx->vout[1])) {
48+
// ION stake reward
49+
sub.involvesWatchAddress = mine & ISMINE_WATCH_ONLY;
50+
sub.type = TransactionRecord::StakeMint;
51+
sub.strAddress = CBitcoinAddress(address).ToString();
52+
sub.credit = nNet;
53+
} else {
54+
//Masternode reward
55+
CTxDestination destMN;
56+
int nIndexMN = wtx.tx->vout.size() - 1;
57+
if (ExtractDestination(wtx.tx->vout[nIndexMN].scriptPubKey, destMN) && IsMine(*wallet, destMN)) {
58+
isminetype mine = wallet->IsMine(wtx.tx->vout[nIndexMN]);
59+
sub.involvesWatchAddress = mine & ISMINE_WATCH_ONLY;
60+
sub.type = TransactionRecord::MNReward;
61+
sub.strAddress = CBitcoinAddress(destMN).ToString();
62+
sub.credit = wtx.tx->vout[nIndexMN].nValue;
63+
}
64+
}
65+
66+
sub.address.SetString(sub.strAddress);
67+
sub.txDest = sub.address.Get();
68+
parts.push_back(sub);
69+
} else if (nNet > 0 || wtx.IsCoinBase())
4270
{
4371
//
4472
// Credit
@@ -300,7 +328,7 @@ void TransactionRecord::updateStatus(const CWalletTx &wtx, int chainLockHeight)
300328
}
301329
}
302330
// For generated transactions, determine maturity
303-
else if(type == TransactionRecord::Generated)
331+
else if(type == TransactionRecord::Generated || type == TransactionRecord::StakeMint || type == TransactionRecord::MNReward)
304332
{
305333
if (wtx.GetBlocksToMaturity() > 0)
306334
{

src/txdb.cpp

+4-2
Original file line numberDiff line numberDiff line change
@@ -471,6 +471,7 @@ class CCoins
471471
public:
472472
//! whether transaction is a coinbase
473473
bool fCoinBase;
474+
bool fCoinStake;
474475

475476
//! unspent transaction outputs; spent outputs are .IsNull(); spent outputs at the end of the array are dropped
476477
std::vector<CTxOut> vout;
@@ -479,7 +480,7 @@ class CCoins
479480
int nHeight;
480481

481482
//! empty constructor
482-
CCoins() : fCoinBase(false), vout(0), nHeight(0) { }
483+
CCoins() : fCoinBase(false), fCoinStake(false), vout(0), nHeight(0) { }
483484

484485
template<typename Stream>
485486
void Unserialize(Stream &s) {
@@ -489,6 +490,7 @@ class CCoins
489490
::Unserialize(s, VARINT(nVersionDummy));
490491
// header code
491492
::Unserialize(s, VARINT(nCode));
493+
fCoinStake = (nCode >> 1) & 1;
492494
fCoinBase = nCode & 1;
493495
std::vector<bool> vAvail(2, false);
494496
vAvail[0] = (nCode & 2) != 0;
@@ -561,7 +563,7 @@ bool CCoinsViewDB::Upgrade() {
561563
COutPoint outpoint(key.second, 0);
562564
for (size_t i = 0; i < old_coins.vout.size(); ++i) {
563565
if (!old_coins.vout[i].IsNull() && !old_coins.vout[i].scriptPubKey.IsUnspendable()) {
564-
Coin newcoin(std::move(old_coins.vout[i]), old_coins.nHeight, old_coins.fCoinBase);
566+
Coin newcoin(std::move(old_coins.vout[i]), old_coins.nHeight, old_coins.fCoinBase, old_coins.fCoinStake);
565567
outpoint.n = i;
566568
CoinEntry entry(&outpoint);
567569
batch.Write(entry, newcoin);

src/txmempool.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -1382,7 +1382,7 @@ bool CCoinsViewMemPool::GetCoin(const COutPoint &outpoint, Coin &coin) const {
13821382
CTransactionRef ptx = mempool.get(outpoint.hash);
13831383
if (ptx) {
13841384
if (outpoint.n < ptx->vout.size()) {
1385-
coin = Coin(ptx->vout[outpoint.n], MEMPOOL_HEIGHT, false);
1385+
coin = Coin(ptx->vout[outpoint.n], MEMPOOL_HEIGHT, false, false);
13861386
return true;
13871387
} else {
13881388
return false;

0 commit comments

Comments
 (0)