elements/src/test/validation_tests.cpp
Andrew Poelstra 61a241c5ca Merge 92fee79dab into merged_master (Bitcoin PR #19806)
Looks like James hardcoded a couple hashes in hard-to-find places, which
caused a unit test to fail. I just changed the hash (which covers UTXO
data which naturally will be different for us on account of our differently
formatted CTxOuts).

TODO: determine how Assumeutxo interacts with the fact that we don't save
out nonces in our normal UTXO serialization. Probably we will need to remove
the nonce from the CCoinStats serialization to avoid having inconsistent
hashes across nodes, since these hashes are now checked in assumeutxo?
2021-06-23 23:36:26 +00:00

147 lines
6.2 KiB
C++

// Copyright (c) 2014-2020 The Bitcoin Core developers
// Distributed under the MIT software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
#include <chainparams.h>
#include <net.h>
#include <signet.h>
#include <uint256.h>
#include <validation.h>
#include <test/util/setup_common.h>
#include <boost/test/unit_test.hpp>
BOOST_FIXTURE_TEST_SUITE(validation_tests, TestingSetup)
static void TestBlockSubsidyHalvings(const Consensus::Params& consensusParams)
{
int maxHalvings = 64;
CAmount nInitialSubsidy = 50 * COIN;
CAmount nPreviousSubsidy = nInitialSubsidy * 2; // for height == 0
BOOST_CHECK_EQUAL(nPreviousSubsidy, nInitialSubsidy * 2);
for (int nHalvings = 0; nHalvings < maxHalvings; nHalvings++) {
int nHeight = nHalvings * consensusParams.nSubsidyHalvingInterval;
CAmount nSubsidy = GetBlockSubsidy(nHeight, consensusParams);
BOOST_CHECK(nSubsidy <= nInitialSubsidy);
BOOST_CHECK_EQUAL(nSubsidy, nPreviousSubsidy / 2);
nPreviousSubsidy = nSubsidy;
}
BOOST_CHECK_EQUAL(GetBlockSubsidy(maxHalvings * consensusParams.nSubsidyHalvingInterval, consensusParams), 0);
}
static void TestBlockSubsidyHalvings(int nSubsidyHalvingInterval)
{
Consensus::Params consensusParams;
consensusParams.nSubsidyHalvingInterval = nSubsidyHalvingInterval;
consensusParams.genesis_subsidy = 50*COIN;
TestBlockSubsidyHalvings(consensusParams);
}
BOOST_AUTO_TEST_CASE(block_subsidy_test)
{
const auto chainParams = CreateChainParams(*m_node.args, CBaseChainParams::MAIN);
TestBlockSubsidyHalvings(chainParams->GetConsensus()); // As in main
TestBlockSubsidyHalvings(150); // As in regtest
TestBlockSubsidyHalvings(1000); // Just another interval
}
BOOST_AUTO_TEST_CASE(subsidy_limit_test)
{
const auto chainParams = CreateChainParams(*m_node.args, CBaseChainParams::MAIN);
CAmount nSum = 0;
for (int nHeight = 0; nHeight < 14000000; nHeight += 1000) {
CAmount nSubsidy = GetBlockSubsidy(nHeight, chainParams->GetConsensus());
BOOST_CHECK(nSubsidy <= 50 * COIN);
nSum += nSubsidy * 1000;
BOOST_CHECK(MoneyRange(nSum));
}
BOOST_CHECK_EQUAL(nSum, CAmount{2099999997690000});
}
BOOST_AUTO_TEST_CASE(signet_parse_tests)
{
ArgsManager signet_argsman;
signet_argsman.ForceSetArg("-signetchallenge", "51"); // set challenge to OP_TRUE
const auto signet_params = CreateChainParams(signet_argsman, CBaseChainParams::SIGNET);
CBlock block;
BOOST_CHECK(signet_params->GetConsensus().signet_challenge == std::vector<uint8_t>{OP_TRUE});
CScript challenge{OP_TRUE};
// empty block is invalid
BOOST_CHECK(!SignetTxs::Create(block, challenge));
BOOST_CHECK(!CheckSignetBlockSolution(block, signet_params->GetConsensus()));
// no witness commitment
CMutableTransaction cb;
cb.vout.emplace_back(CAsset(), 0, CScript{});
block.vtx.push_back(MakeTransactionRef(cb));
block.vtx.push_back(MakeTransactionRef(cb)); // Add dummy tx to exercise merkle root code
BOOST_CHECK(!SignetTxs::Create(block, challenge));
BOOST_CHECK(!CheckSignetBlockSolution(block, signet_params->GetConsensus()));
// no header is treated valid
std::vector<uint8_t> witness_commitment_section_141{0xaa, 0x21, 0xa9, 0xed};
for (int i = 0; i < 32; ++i) {
witness_commitment_section_141.push_back(0xff);
}
cb.vout.at(0).scriptPubKey = CScript{} << OP_RETURN << witness_commitment_section_141;
block.vtx.at(0) = MakeTransactionRef(cb);
BOOST_CHECK(SignetTxs::Create(block, challenge));
BOOST_CHECK(CheckSignetBlockSolution(block, signet_params->GetConsensus()));
// no data after header, valid
std::vector<uint8_t> witness_commitment_section_325{0xec, 0xc7, 0xda, 0xa2};
cb.vout.at(0).scriptPubKey = CScript{} << OP_RETURN << witness_commitment_section_141 << witness_commitment_section_325;
block.vtx.at(0) = MakeTransactionRef(cb);
BOOST_CHECK(SignetTxs::Create(block, challenge));
BOOST_CHECK(CheckSignetBlockSolution(block, signet_params->GetConsensus()));
// Premature end of data, invalid
witness_commitment_section_325.push_back(0x01);
witness_commitment_section_325.push_back(0x51);
cb.vout.at(0).scriptPubKey = CScript{} << OP_RETURN << witness_commitment_section_141 << witness_commitment_section_325;
block.vtx.at(0) = MakeTransactionRef(cb);
BOOST_CHECK(!SignetTxs::Create(block, challenge));
BOOST_CHECK(!CheckSignetBlockSolution(block, signet_params->GetConsensus()));
// has data, valid
witness_commitment_section_325.push_back(0x00);
cb.vout.at(0).scriptPubKey = CScript{} << OP_RETURN << witness_commitment_section_141 << witness_commitment_section_325;
block.vtx.at(0) = MakeTransactionRef(cb);
BOOST_CHECK(SignetTxs::Create(block, challenge));
BOOST_CHECK(CheckSignetBlockSolution(block, signet_params->GetConsensus()));
// Extraneous data, invalid
witness_commitment_section_325.push_back(0x00);
cb.vout.at(0).scriptPubKey = CScript{} << OP_RETURN << witness_commitment_section_141 << witness_commitment_section_325;
block.vtx.at(0) = MakeTransactionRef(cb);
BOOST_CHECK(!SignetTxs::Create(block, challenge));
BOOST_CHECK(!CheckSignetBlockSolution(block, signet_params->GetConsensus()));
}
//! Test retrieval of valid assumeutxo values.
BOOST_AUTO_TEST_CASE(test_assumeutxo)
{
const auto params = CreateChainParams(*m_node.args, CBaseChainParams::REGTEST);
// These heights don't have assumeutxo configurations associated, per the contents
// of chainparams.cpp.
std::vector<int> bad_heights{0, 100, 111, 115, 209, 211};
for (auto empty : bad_heights) {
const auto out = ExpectedAssumeutxo(empty, *params);
BOOST_CHECK(!out);
}
const auto out110 = *ExpectedAssumeutxo(110, *params);
BOOST_CHECK_EQUAL(out110.hash_serialized, uint256S("4fa9f2be16670cb097173e6b788974fb9106c2335c074267ca5f7fc297dded32"));
BOOST_CHECK_EQUAL(out110.nChainTx, (unsigned int)110);
const auto out210 = *ExpectedAssumeutxo(210, *params);
BOOST_CHECK_EQUAL(out210.hash_serialized, uint256S("9c5ed99ef98544b34f8920b6d1802f72ac28ae6e2bd2bd4c316ff10c230df3f2"));
BOOST_CHECK_EQUAL(out210.nChainTx, (unsigned int)210);
}
BOOST_AUTO_TEST_SUITE_END()