Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions src/chainparams.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -921,6 +921,7 @@ class CRegTestParams : public CChainParams {
UpdateLLMQTestParametersFromArgs(args, Consensus::LLMQType::LLMQ_TEST_INSTANTSEND);
UpdateLLMQTestParametersFromArgs(args, Consensus::LLMQType::LLMQ_TEST_PLATFORM);
UpdateLLMQInstantSendDIP0024FromArgs(args);
assert(consensus.V20Height >= consensus.DIP0003Height);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

}

/**
Expand Down
34 changes: 24 additions & 10 deletions src/evo/cbtx.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -331,13 +331,26 @@ bool CheckCbTxBestChainlock(const CBlock& block, const CBlockIndex* pindex,
return true;
}

static Mutex cached_mutex;
static const CBlockIndex* cached_pindex GUARDED_BY(cached_mutex){nullptr};
static std::optional<std::pair<CBLSSignature, uint32_t>> cached_chainlock GUARDED_BY(cached_mutex){std::nullopt};

auto best_clsig = chainlock_handler.GetBestChainLock();
if (best_clsig.getHeight() == pindex->nHeight - 1 && cbTx.bestCLHeightDiff == 0 && cbTx.bestCLSignature == best_clsig.getSig()) {
// matches our best clsig which still hold values for the previous block
LOCK(cached_mutex);
cached_chainlock = std::make_pair(cbTx.bestCLSignature, cbTx.bestCLHeightDiff);
cached_pindex = pindex;
return true;
}

const auto prevBlockCoinbaseChainlock = GetNonNullCoinbaseChainlock(pindex->pprev);
std::optional<std::pair<CBLSSignature, uint32_t>> prevBlockCoinbaseChainlock{std::nullopt};
if (LOCK(cached_mutex); cached_pindex == pindex->pprev) {
prevBlockCoinbaseChainlock = cached_chainlock;
}
if (!prevBlockCoinbaseChainlock.has_value()) {
prevBlockCoinbaseChainlock = GetNonNullCoinbaseChainlock(pindex->pprev);
}
// If std::optional prevBlockCoinbaseChainlock is empty, then up to the previous block, coinbase Chainlock is null.
if (prevBlockCoinbaseChainlock.has_value()) {
// Previous block Coinbase has a non-null Chainlock: current block's Chainlock must be non-null and at least as new as the previous one
Expand All @@ -355,12 +368,18 @@ bool CheckCbTxBestChainlock(const CBlock& block, const CBlockIndex* pindex,
int curBlockCoinbaseCLHeight = pindex->nHeight - static_cast<int>(cbTx.bestCLHeightDiff) - 1;
if (best_clsig.getHeight() == curBlockCoinbaseCLHeight && best_clsig.getSig() == cbTx.bestCLSignature) {
// matches our best (but outdated) clsig, no need to verify it again
LOCK(cached_mutex);
cached_chainlock = std::make_pair(cbTx.bestCLSignature, cbTx.bestCLHeightDiff);
cached_pindex = pindex;
return true;
}
uint256 curBlockCoinbaseCLBlockHash = pindex->GetAncestor(curBlockCoinbaseCLHeight)->GetBlockHash();
if (chainlock_handler.VerifyChainLock(llmq::CChainLockSig(curBlockCoinbaseCLHeight, curBlockCoinbaseCLBlockHash, cbTx.bestCLSignature)) != llmq::VerifyRecSigStatus::Valid) {
return state.Invalid(BlockValidationResult::BLOCK_CONSENSUS, "bad-cbtx-invalid-clsig");
}
LOCK(cached_mutex);
cached_chainlock = std::make_pair(cbTx.bestCLSignature, cbTx.bestCLHeightDiff);
cached_pindex = pindex;
} else if (cbTx.bestCLHeightDiff != 0) {
// Null bestCLSignature is allowed only with bestCLHeightDiff = 0
return state.Invalid(BlockValidationResult::BLOCK_CONSENSUS, "bad-cbtx-cldiff");
Expand Down Expand Up @@ -437,8 +456,8 @@ std::optional<std::pair<CBLSSignature, uint32_t>> GetNonNullCoinbaseChainlock(co
return std::nullopt;
}

// There's no CbTx before DIP0003 activation
if (!DeploymentActiveAt(*pindex, Params().GetConsensus(), Consensus::DEPLOYMENT_DIP0003)) {
// There's no CL in CbTx before v20 activation
if (!DeploymentActiveAt(*pindex, Params().GetConsensus(), Consensus::DEPLOYMENT_V20)) {
return std::nullopt;
}

Expand All @@ -454,14 +473,9 @@ std::optional<std::pair<CBLSSignature, uint32_t>> GetNonNullCoinbaseChainlock(co
return std::nullopt;
}

const CCbTx& cbtx = opt_cbtx.value();
if (cbtx.nVersion < CCbTx::Version::CLSIG_AND_BALANCE) {
return std::nullopt;
}

if (!cbtx.bestCLSignature.IsValid()) {
if (!opt_cbtx->bestCLSignature.IsValid()) {
return std::nullopt;
}

return std::make_pair(cbtx.bestCLSignature, cbtx.bestCLHeightDiff);
return std::make_pair(opt_cbtx->bestCLSignature, opt_cbtx->bestCLHeightDiff);
}
2 changes: 1 addition & 1 deletion test/functional/feature_assumevalid.py
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ class AssumeValidTest(BitcoinTestFramework):
def set_test_params(self):
self.setup_clean_chain = True
self.num_nodes = 3
self.extra_args = ["-dip3params=9000:9000", "-checkblockindex=0"]
self.extra_args = ["-dip3params=9000:9000", '-testactivationheight=v20@9000', "-checkblockindex=0"]
self.rpc_timeout = 120

def setup_network(self):
Expand Down
1 change: 1 addition & 0 deletions test/functional/feature_csv_activation.py
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ def set_test_params(self):
'-peertimeout=999999', # bump because mocktime might cause a disconnect otherwise
'-whitelist=noban@127.0.0.1',
'-dip3params=2000:2000',
'-testactivationheight=v20@2000',
f'-testactivationheight=csv@{CSV_ACTIVATION_HEIGHT}',
'-par=1', # Use only one script thread to get the exact reject reason for testing
]]
Expand Down
Loading