Improve error reporting and wallet cleanup
This commit is contained in:
42
src/main.cpp
42
src/main.cpp
@@ -1078,7 +1078,7 @@ bool ContextualCheckTransaction(
|
|||||||
// Check that all transactions are unexpired
|
// Check that all transactions are unexpired
|
||||||
if (IsExpiredTx(tx, nHeight)) {
|
if (IsExpiredTx(tx, nHeight)) {
|
||||||
// Don't increase banscore if the transaction only just expired
|
// Don't increase banscore if the transaction only just expired
|
||||||
int expiredDosLevel = IsExpiredTx(tx, nHeight - 1) ? dosLevel : 0;
|
int expiredDosLevel = IsExpiredTx(tx, nHeight - 1) ? (dosLevel > 10 ? dosLevel : 10) : 0;
|
||||||
return state.DoS(expiredDosLevel, error("ContextualCheckTransaction(): transaction is expired"), REJECT_INVALID, "tx-overwinter-expired");
|
return state.DoS(expiredDosLevel, error("ContextualCheckTransaction(): transaction is expired"), REJECT_INVALID, "tx-overwinter-expired");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1536,7 +1536,8 @@ bool AcceptToMemoryPool(CTxMemPool& pool, CValidationState &state, const CTransa
|
|||||||
CStakeParams p;
|
CStakeParams p;
|
||||||
if (NetworkUpgradeActive(nextBlockHeight, Params().GetConsensus(), Consensus::UPGRADE_SAPLING) && ValidateStakeTransaction(tx, p, false))
|
if (NetworkUpgradeActive(nextBlockHeight, Params().GetConsensus(), Consensus::UPGRADE_SAPLING) && ValidateStakeTransaction(tx, p, false))
|
||||||
{
|
{
|
||||||
return error("AcceptToMemoryPool: attempt to add staking transaction that is not staking");
|
return state.DoS(100, error("AcceptToMemoryPool: attempt to add staking transaction that is not staking"),
|
||||||
|
REJECT_INVALID, "bad-txns-invalid-staking");
|
||||||
}
|
}
|
||||||
|
|
||||||
auto verifier = libzcash::ProofVerifier::Strict();
|
auto verifier = libzcash::ProofVerifier::Strict();
|
||||||
@@ -1648,7 +1649,7 @@ bool AcceptToMemoryPool(CTxMemPool& pool, CValidationState &state, const CTransa
|
|||||||
if (pfMissingInputs)
|
if (pfMissingInputs)
|
||||||
*pfMissingInputs = true;
|
*pfMissingInputs = true;
|
||||||
//fprintf(stderr,"missing inputs\n");
|
//fprintf(stderr,"missing inputs\n");
|
||||||
return false;
|
return state.DoS(0, error("AcceptToMemoryPool: tx inputs not found"),REJECT_INVALID, "bad-txns-inputs-missing");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1690,7 +1691,7 @@ bool AcceptToMemoryPool(CTxMemPool& pool, CValidationState &state, const CTransa
|
|||||||
if (nSigOps > MAX_STANDARD_TX_SIGOPS)
|
if (nSigOps > MAX_STANDARD_TX_SIGOPS)
|
||||||
{
|
{
|
||||||
fprintf(stderr,"accept failure.4\n");
|
fprintf(stderr,"accept failure.4\n");
|
||||||
return state.DoS(0, error("AcceptToMemoryPool: too many sigops %s, %d > %d", hash.ToString(), nSigOps, MAX_STANDARD_TX_SIGOPS),REJECT_NONSTANDARD, "bad-txns-too-many-sigops");
|
return state.DoS(1, error("AcceptToMemoryPool: too many sigops %s, %d > %d", hash.ToString(), nSigOps, MAX_STANDARD_TX_SIGOPS),REJECT_NONSTANDARD, "bad-txns-too-many-sigops");
|
||||||
}
|
}
|
||||||
|
|
||||||
CAmount nValueOut = tx.GetValueOut();
|
CAmount nValueOut = tx.GetValueOut();
|
||||||
@@ -2439,30 +2440,33 @@ namespace Consensus {
|
|||||||
assert(coins);
|
assert(coins);
|
||||||
|
|
||||||
if (coins->IsCoinBase()) {
|
if (coins->IsCoinBase()) {
|
||||||
// Ensure that coinbases are matured
|
// ensure that output of coinbases are not still time locked
|
||||||
if (nSpendHeight - coins->nHeight < COINBASE_MATURITY) {
|
if (coins->TotalTxValue() >= ASSETCHAINS_TIMELOCKGTE)
|
||||||
return state.Invalid(
|
{
|
||||||
error("CheckInputs(): tried to spend coinbase at depth %d", nSpendHeight - coins->nHeight),
|
uint64_t unlockTime = komodo_block_unlocktime(coins->nHeight);
|
||||||
REJECT_INVALID, "bad-txns-premature-spend-of-coinbase");
|
if (nSpendHeight < unlockTime) {
|
||||||
|
return state.DoS(10,
|
||||||
|
error("CheckInputs(): tried to spend coinbase that is timelocked until block %d", unlockTime),
|
||||||
|
REJECT_INVALID, "bad-txns-premature-spend-of-coinbase");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// ensure that output of coinbases are not still time locked
|
// Ensure that coinbases are matured, no DoS as retry may work later
|
||||||
uint64_t unlockTime = komodo_block_unlocktime(coins->nHeight);
|
if (nSpendHeight - coins->nHeight < COINBASE_MATURITY) {
|
||||||
if (nSpendHeight < unlockTime && coins->TotalTxValue() >= ASSETCHAINS_TIMELOCKGTE) {
|
return state.DoS(0,
|
||||||
return state.Invalid(
|
error("CheckInputs(): tried to spend coinbase at depth %d", nSpendHeight - coins->nHeight),
|
||||||
error("CheckInputs(): tried to spend coinbase that is timelocked until block %d", unlockTime),
|
REJECT_INVALID, "bad-txns-premature-spend-of-coinbase");
|
||||||
REJECT_INVALID, "bad-txns-premature-spend-of-coinbase");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Ensure that coinbases cannot be spent to transparent outputs
|
// Ensure that coinbases cannot be spent to transparent outputs
|
||||||
// Disabled on regtest
|
// Disabled on regtest
|
||||||
if (fCoinbaseEnforcedProtectionEnabled &&
|
if (fCoinbaseEnforcedProtectionEnabled &&
|
||||||
consensusParams.fCoinbaseMustBeProtected &&
|
consensusParams.fCoinbaseMustBeProtected &&
|
||||||
!tx.vout.empty() &&
|
!(tx.vout.size() == 0 || (tx.vout.size() == 1 && tx.vout[0].nValue == 0)) &&
|
||||||
(strcmp(ASSETCHAINS_SYMBOL, "VRSC") != 0 || (nSpendHeight >= 12800 && coins->nHeight >= 12800))) {
|
(strcmp(ASSETCHAINS_SYMBOL, "VRSC") != 0 || (nSpendHeight >= 12800 && coins->nHeight >= 12800))) {
|
||||||
return state.Invalid(
|
return state.DoS(100,
|
||||||
error("CheckInputs(): tried to spend coinbase with transparent outputs"),
|
error("CheckInputs(): tried to spend coinbase with transparent outputs"),
|
||||||
REJECT_INVALID, "bad-txns-coinbase-spend-has-transparent-outputs");
|
REJECT_INVALID, "bad-txns-coinbase-spend-has-transparent-outputs");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -2757,7 +2757,21 @@ void CWallet::ReacceptWalletTransactions()
|
|||||||
LOCK(mempool.cs);
|
LOCK(mempool.cs);
|
||||||
CValidationState state;
|
CValidationState state;
|
||||||
// attempt to add them, but don't set any DOS level
|
// attempt to add them, but don't set any DOS level
|
||||||
::AcceptToMemoryPool(mempool, state, wtx, false, NULL, true, 0);
|
if (!::AcceptToMemoryPool(mempool, state, wtx, false, NULL, true, 0))
|
||||||
|
{
|
||||||
|
int nDoS;
|
||||||
|
bool invalid = state.IsInvalid(nDoS);
|
||||||
|
|
||||||
|
// log rejection and deletion
|
||||||
|
// printf("ERROR reaccepting wallet transaction %s to mempool, reason: %s, DoS: %d\n", wtx.GetHash().ToString().c_str(), state.GetRejectReason().c_str(), nDoS);
|
||||||
|
|
||||||
|
if (!wtx.IsCoinBase() && invalid && nDoS > 0)
|
||||||
|
{
|
||||||
|
LogPrintf("erasing transaction\n");
|
||||||
|
//printf("erasing transaction\n");
|
||||||
|
EraseFromWallets(wtx.GetHash());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user