Make bench working
Add hash comparison Signed-off-by: Anthony Fieroni <bvbfan@abv.bg>
This commit is contained in:
parent
e53590bb8c
commit
03a72e4723
5 changed files with 90 additions and 30 deletions
|
@ -13,6 +13,7 @@
|
||||||
#include <scheduler.h>
|
#include <scheduler.h>
|
||||||
#include <txdb.h>
|
#include <txdb.h>
|
||||||
#include <txmempool.h>
|
#include <txmempool.h>
|
||||||
|
#include <util.h>
|
||||||
#include <utiltime.h>
|
#include <utiltime.h>
|
||||||
#include <validation.h>
|
#include <validation.h>
|
||||||
#include <validationinterface.h>
|
#include <validationinterface.h>
|
||||||
|
@ -40,7 +41,7 @@ static CTxIn MineBlock(const CScript& coinbase_scriptPubKey)
|
||||||
{
|
{
|
||||||
auto block = PrepareBlock(coinbase_scriptPubKey);
|
auto block = PrepareBlock(coinbase_scriptPubKey);
|
||||||
|
|
||||||
while (!CheckProofOfWork(block->GetHash(), block->nBits, Params().GetConsensus())) {
|
while (!CheckProofOfWork(block->GetPoWHash(), block->nBits, Params().GetConsensus())) {
|
||||||
++block->nNonce;
|
++block->nNonce;
|
||||||
assert(block->nNonce);
|
assert(block->nNonce);
|
||||||
}
|
}
|
||||||
|
@ -72,18 +73,29 @@ static void AssembleBlock(benchmark::State& state)
|
||||||
boost::thread_group thread_group;
|
boost::thread_group thread_group;
|
||||||
CScheduler scheduler;
|
CScheduler scheduler;
|
||||||
{
|
{
|
||||||
|
delete ::pclaimTrie;
|
||||||
|
const CChainParams& chainparams = Params();
|
||||||
|
auto &consensus = chainparams.GetConsensus();
|
||||||
::pblocktree.reset(new CBlockTreeDB(1 << 20, true));
|
::pblocktree.reset(new CBlockTreeDB(1 << 20, true));
|
||||||
::pcoinsdbview.reset(new CCoinsViewDB(1 << 23, true));
|
::pcoinsdbview.reset(new CCoinsViewDB(1 << 23, true));
|
||||||
::pcoinsTip.reset(new CCoinsViewCache(pcoinsdbview.get()));
|
::pcoinsTip.reset(new CCoinsViewCache(pcoinsdbview.get()));
|
||||||
|
::pclaimTrie = new CClaimTrie(1 << 25, true, 0, GetDataDir().string(),
|
||||||
|
consensus.nNormalizedNameForkHeight,
|
||||||
|
consensus.nMinRemovalWorkaroundHeight,
|
||||||
|
consensus.nMaxRemovalWorkaroundHeight,
|
||||||
|
consensus.nOriginalClaimExpirationTime,
|
||||||
|
consensus.nExtendedClaimExpirationTime,
|
||||||
|
consensus.nExtendedClaimExpirationForkHeight,
|
||||||
|
consensus.nAllClaimsInMerkleForkHeight, 1);
|
||||||
|
|
||||||
const CChainParams& chainparams = Params();
|
|
||||||
thread_group.create_thread(boost::bind(&CScheduler::serviceQueue, &scheduler));
|
thread_group.create_thread(boost::bind(&CScheduler::serviceQueue, &scheduler));
|
||||||
GetMainSignals().RegisterBackgroundSignalScheduler(scheduler);
|
GetMainSignals().RegisterBackgroundSignalScheduler(scheduler);
|
||||||
LoadGenesisBlock(chainparams);
|
LoadGenesisBlock(chainparams);
|
||||||
CValidationState state;
|
CValidationState state;
|
||||||
ActivateBestChain(state, chainparams);
|
ActivateBestChain(state, chainparams);
|
||||||
assert(::chainActive.Tip() != nullptr);
|
assert(::chainActive.Tip() != nullptr);
|
||||||
const bool witness_enabled{IsWitnessEnabled(::chainActive.Tip(), chainparams.GetConsensus())};
|
const_cast<int&>(consensus.nWitnessForkHeight) = ::chainActive.Height();
|
||||||
|
const bool witness_enabled{IsWitnessEnabled(::chainActive.Tip(), consensus)};
|
||||||
assert(witness_enabled);
|
assert(witness_enabled);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -9,9 +9,50 @@
|
||||||
#include <streams.h>
|
#include <streams.h>
|
||||||
#include <consensus/validation.h>
|
#include <consensus/validation.h>
|
||||||
|
|
||||||
|
|
||||||
|
/* Don't use raw bitcoin blocks
|
||||||
namespace block_bench {
|
namespace block_bench {
|
||||||
#include <bench/data/block413567.raw.h>
|
#include <bench/data/block413567.raw.h>
|
||||||
} // namespace block_bench
|
} // namespace block_bench
|
||||||
|
*/
|
||||||
|
|
||||||
|
CDataStream getTestBlockStream()
|
||||||
|
{
|
||||||
|
static CBlock block;
|
||||||
|
static CDataStream stream(SER_NETWORK, PROTOCOL_VERSION);
|
||||||
|
if (block.IsNull()) {
|
||||||
|
block.nVersion = 5;
|
||||||
|
block.hashPrevBlock = uint256S("e8fc54d1e6581fceaaf64cc8afeedb9c4ba1eb2349eaf638f1fc41e331869dee");
|
||||||
|
block.hashMerkleRoot = uint256S("a926580973e1204aa179a4c536023c69212ce00b56dc85d3516488f3c51dd022");
|
||||||
|
block.hashClaimTrie = uint256S("7bae80d60b09031265f8a9f6282e4b9653764fadfac2c8b4c1f416c972b58814");
|
||||||
|
block.nTime = 1545050539;
|
||||||
|
block.nBits = 0x207fffff;
|
||||||
|
block.nNonce = 128913;
|
||||||
|
block.vtx.resize(60);
|
||||||
|
uint256 prevHash;
|
||||||
|
for (int i = 0; i < 60; ++i) {
|
||||||
|
CMutableTransaction tx;
|
||||||
|
tx.nVersion = 5;
|
||||||
|
tx.nLockTime = 0;
|
||||||
|
tx.vin.resize(1);
|
||||||
|
tx.vout.resize(1);
|
||||||
|
if (!prevHash.IsNull()) {
|
||||||
|
tx.vin[0].prevout.hash = prevHash;
|
||||||
|
tx.vin[0].prevout.n = 0;
|
||||||
|
}
|
||||||
|
tx.vin[0].scriptSig = CScript() << OP_0 << OP_0;
|
||||||
|
tx.vin[0].nSequence = std::numeric_limits<unsigned int>::max();
|
||||||
|
tx.vout[0].scriptPubKey = CScript();
|
||||||
|
tx.vout[0].nValue = 0;
|
||||||
|
prevHash = tx.GetHash();
|
||||||
|
block.vtx[i] = MakeTransactionRef(std::move(tx));
|
||||||
|
}
|
||||||
|
stream << block;
|
||||||
|
char a = '\0';
|
||||||
|
stream.write(&a, 1); // Prevent compaction
|
||||||
|
}
|
||||||
|
return stream;
|
||||||
|
}
|
||||||
|
|
||||||
// These are the two major time-sinks which happen after we have fully received
|
// These are the two major time-sinks which happen after we have fully received
|
||||||
// a block off the wire, but before we can relay the block on to peers using
|
// a block off the wire, but before we can relay the block on to peers using
|
||||||
|
@ -19,33 +60,25 @@ namespace block_bench {
|
||||||
|
|
||||||
static void DeserializeBlockTest(benchmark::State& state)
|
static void DeserializeBlockTest(benchmark::State& state)
|
||||||
{
|
{
|
||||||
CDataStream stream((const char*)block_bench::block413567,
|
auto stream = getTestBlockStream();
|
||||||
(const char*)&block_bench::block413567[sizeof(block_bench::block413567)],
|
const auto size = stream.size() - 1;
|
||||||
SER_NETWORK, PROTOCOL_VERSION);
|
|
||||||
char a = '\0';
|
|
||||||
stream.write(&a, 1); // Prevent compaction
|
|
||||||
|
|
||||||
while (state.KeepRunning()) {
|
while (state.KeepRunning()) {
|
||||||
CBlock block;
|
CBlock block;
|
||||||
stream >> block;
|
stream >> block;
|
||||||
assert(stream.Rewind(sizeof(block_bench::block413567)));
|
assert(stream.Rewind(size));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void DeserializeAndCheckBlockTest(benchmark::State& state)
|
static void DeserializeAndCheckBlockTest(benchmark::State& state)
|
||||||
{
|
{
|
||||||
CDataStream stream((const char*)block_bench::block413567,
|
auto stream = getTestBlockStream();
|
||||||
(const char*)&block_bench::block413567[sizeof(block_bench::block413567)],
|
const auto size = stream.size() - 1;
|
||||||
SER_NETWORK, PROTOCOL_VERSION);
|
const auto chainParams = CreateChainParams(CBaseChainParams::REGTEST);
|
||||||
char a = '\0';
|
|
||||||
stream.write(&a, 1); // Prevent compaction
|
|
||||||
|
|
||||||
const auto chainParams = CreateChainParams(CBaseChainParams::MAIN);
|
|
||||||
|
|
||||||
while (state.KeepRunning()) {
|
while (state.KeepRunning()) {
|
||||||
CBlock block; // Note that CBlock caches its checked state, so we need to recreate it here
|
CBlock block; // Note that CBlock caches its checked state, so we need to recreate it here
|
||||||
stream >> block;
|
stream >> block;
|
||||||
assert(stream.Rewind(sizeof(block_bench::block413567)));
|
assert(stream.Rewind(size));
|
||||||
|
|
||||||
CValidationState validationState;
|
CValidationState validationState;
|
||||||
assert(CheckBlock(block, validationState, chainParams->GetConsensus()));
|
assert(CheckBlock(block, validationState, chainParams->GetConsensus()));
|
||||||
|
|
|
@ -4,11 +4,13 @@
|
||||||
|
|
||||||
#include <bench/bench.h>
|
#include <bench/bench.h>
|
||||||
|
|
||||||
#include <uint256.h>
|
#include <claimtrie/hashes.h>
|
||||||
#include <random.h>
|
|
||||||
#include <consensus/merkle.h>
|
#include <consensus/merkle.h>
|
||||||
|
#include <crypto/sha256.h>
|
||||||
|
#include <random.h>
|
||||||
|
#include <uint256.h>
|
||||||
|
|
||||||
static void MerkleRoot(benchmark::State& state)
|
static void MerkleRootUni(benchmark::State& state)
|
||||||
{
|
{
|
||||||
FastRandomContext rng(true);
|
FastRandomContext rng(true);
|
||||||
std::vector<uint256> leaves;
|
std::vector<uint256> leaves;
|
||||||
|
@ -18,9 +20,18 @@ static void MerkleRoot(benchmark::State& state)
|
||||||
}
|
}
|
||||||
while (state.KeepRunning()) {
|
while (state.KeepRunning()) {
|
||||||
bool mutation = false;
|
bool mutation = false;
|
||||||
uint256 hash = ComputeMerkleRoot(std::vector<uint256>(leaves), &mutation);
|
uint256 hash = ComputeMerkleRoot(leaves, &mutation);
|
||||||
leaves[mutation] = hash;
|
leaves[mutation] = hash;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void MerkleRoot(benchmark::State& state)
|
||||||
|
{
|
||||||
|
sha256n_way = [](std::vector<uint256>& hashes) {
|
||||||
|
SHA256D64(hashes[0].begin(), hashes[0].begin(), hashes.size() / 2);
|
||||||
|
};
|
||||||
|
MerkleRootUni(state);
|
||||||
|
}
|
||||||
|
|
||||||
BENCHMARK(MerkleRoot, 800);
|
BENCHMARK(MerkleRoot, 800);
|
||||||
|
BENCHMARK(MerkleRootUni, 800);
|
||||||
|
|
|
@ -6,6 +6,9 @@
|
||||||
#include <hash.h>
|
#include <hash.h>
|
||||||
#include <utilstrencodings.h>
|
#include <utilstrencodings.h>
|
||||||
|
|
||||||
|
#include <functional>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
/* WARNING! If you're reading this because you're learning about crypto
|
/* WARNING! If you're reading this because you're learning about crypto
|
||||||
and/or designing a new system that will use merkle trees, keep in mind
|
and/or designing a new system that will use merkle trees, keep in mind
|
||||||
that the following merkle tree algorithm has a serious flaw related to
|
that the following merkle tree algorithm has a serious flaw related to
|
||||||
|
@ -42,6 +45,7 @@
|
||||||
root.
|
root.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
extern std::function<void(std::vector<uint256>&)> sha256n_way;
|
||||||
|
|
||||||
uint256 ComputeMerkleRoot(std::vector<uint256> hashes, bool* mutated) {
|
uint256 ComputeMerkleRoot(std::vector<uint256> hashes, bool* mutated) {
|
||||||
bool mutation = false;
|
bool mutation = false;
|
||||||
|
@ -54,7 +58,7 @@ uint256 ComputeMerkleRoot(std::vector<uint256> hashes, bool* mutated) {
|
||||||
if (hashes.size() & 1) {
|
if (hashes.size() & 1) {
|
||||||
hashes.push_back(hashes.back());
|
hashes.push_back(hashes.back());
|
||||||
}
|
}
|
||||||
SHA256D64(hashes[0].begin(), hashes[0].begin(), hashes.size() / 2);
|
sha256n_way(hashes);
|
||||||
hashes.resize(hashes.size() / 2);
|
hashes.resize(hashes.size() / 2);
|
||||||
}
|
}
|
||||||
if (mutated) *mutated = mutation;
|
if (mutated) *mutated = mutation;
|
||||||
|
|
14
src/init.cpp
14
src/init.cpp
|
@ -1454,6 +1454,13 @@ bool AppInitMain()
|
||||||
pblocktree.reset();
|
pblocktree.reset();
|
||||||
pblocktree.reset(new CBlockTreeDB(nBlockTreeDBCache, false, fReindex));
|
pblocktree.reset(new CBlockTreeDB(nBlockTreeDBCache, false, fReindex));
|
||||||
|
|
||||||
|
// use faster N way hash function
|
||||||
|
// NOTE: it assumes memory is continuous
|
||||||
|
// that means uint256 itself should use std::array or raw pointer
|
||||||
|
sha256n_way = [](std::vector<uint256>& hashes) {
|
||||||
|
SHA256D64(hashes[0].begin(), hashes[0].begin(), hashes.size() / 2);
|
||||||
|
};
|
||||||
|
|
||||||
if (fReindex) {
|
if (fReindex) {
|
||||||
pblocktree->WriteReindexing(true);
|
pblocktree->WriteReindexing(true);
|
||||||
//If we're reindexing in prune mode, wipe away unusable block files and all undo data files
|
//If we're reindexing in prune mode, wipe away unusable block files and all undo data files
|
||||||
|
@ -1535,13 +1542,6 @@ bool AppInitMain()
|
||||||
assert(chainActive.Tip() != nullptr);
|
assert(chainActive.Tip() != nullptr);
|
||||||
}
|
}
|
||||||
|
|
||||||
// use faster N way hash function
|
|
||||||
// NOTE: it assumes memory is continuous
|
|
||||||
// that means uint256 itself should use std::array or raw pointer
|
|
||||||
sha256n_way = [](std::vector<uint256>& hashes) {
|
|
||||||
SHA256D64(hashes[0].begin(), hashes[0].begin(), hashes.size() / 2);
|
|
||||||
};
|
|
||||||
|
|
||||||
auto tip = chainActive.Tip();
|
auto tip = chainActive.Tip();
|
||||||
if (tip && !CClaimTrieCache(pclaimTrie).validateDb(tip->nHeight, tip->hashClaimTrie)) {
|
if (tip && !CClaimTrieCache(pclaimTrie).validateDb(tip->nHeight, tip->hashClaimTrie)) {
|
||||||
strLoadError = _("Error validating the claim trie from disk");
|
strLoadError = _("Error validating the claim trie from disk");
|
||||||
|
|
Loading…
Reference in a new issue