diff --git a/src/p2pool.cpp b/src/p2pool.cpp index 23d91be..f3f5d00 100644 --- a/src/p2pool.cpp +++ b/src/p2pool.cpp @@ -1011,7 +1011,8 @@ int p2pool::run() LOGINFO(1, "uv_run exited, result = " << rc); } catch (const std::exception& e) { - LOGERR(1, "exception " << e.what()); + const char* s = e.what(); + LOGERR(1, "exception " << s); panic(); } diff --git a/src/pow_hash.cpp b/src/pow_hash.cpp index c44cb78..d0e412a 100644 --- a/src/pow_hash.cpp +++ b/src/pow_hash.cpp @@ -38,7 +38,7 @@ RandomX_Hasher::RandomX_Hasher(p2pool* pool) { uint64_t memory_allocated = 0; - if (!m_pool->params().m_lightMode) { + if (m_pool && !m_pool->params().m_lightMode) { m_dataset = randomx_alloc_dataset(RANDOMX_FLAG_LARGE_PAGES); if (!m_dataset) { LOGWARN(1, "couldn't allocate RandomX dataset using large pages"); diff --git a/src/pow_hash.h b/src/pow_hash.h index 922683c..21f4778 100644 --- a/src/pow_hash.h +++ b/src/pow_hash.h @@ -34,12 +34,13 @@ public: ~RandomX_Hasher(); void set_seed_async(const hash& seed); + void set_seed(const hash& seed); + void set_old_seed(const hash& seed); bool calculate(const void* data, size_t size, const hash& seed, hash& result); private: - void set_seed(const hash& seed); struct ThreadSafeVM { diff --git a/src/side_chain.cpp b/src/side_chain.cpp index ff4911c..719e9b3 100644 --- a/src/side_chain.cpp +++ b/src/side_chain.cpp @@ -51,11 +51,11 @@ static_assert(1 <= UNCLE_BLOCK_DEPTH && UNCLE_BLOCK_DEPTH <= 10, "Invalid UNCLE_ namespace p2pool { -SideChain::SideChain(p2pool* pool, NetworkType type) +SideChain::SideChain(p2pool* pool, NetworkType type, const char* pool_name) : m_pool(pool) , m_networkType(type) , m_chainTip(nullptr) - , m_poolName("mainnet test 2") + , m_poolName(pool_name ? pool_name : "mainnet test 2") , m_targetBlockTime(10) , m_minDifficulty(MIN_DIFFICULTY, 0) , m_chainWindowSize(2160) @@ -64,7 +64,7 @@ SideChain::SideChain(p2pool* pool, NetworkType type) { LOGINFO(1, log::LightCyan() << "network type = " << m_networkType); - if (!load_config(m_pool->params().m_config)) { + if (m_pool && !load_config(m_pool->params().m_config)) { panic(); } diff --git a/src/side_chain.h b/src/side_chain.h index 2c9b0cd..68d48f7 100644 --- a/src/side_chain.h +++ b/src/side_chain.h @@ -41,7 +41,7 @@ struct MinerShare class SideChain { public: - SideChain(p2pool* pool, NetworkType type); + SideChain(p2pool* pool, NetworkType type, const char* pool_name = nullptr); ~SideChain(); void fill_sidechain_data(PoolBlock& block, Wallet* w, const hash& txkeySec, std::vector& shares); diff --git a/tests/CMakeLists.txt b/tests/CMakeLists.txt index 5bb02d7..2eb2981 100644 --- a/tests/CMakeLists.txt +++ b/tests/CMakeLists.txt @@ -15,6 +15,9 @@ endif() add_subdirectory(googletest) set(LIBS gtest) +add_subdirectory(../external/src/RandomX RandomX) +set(LIBS ${LIBS} randomx) + if (CMAKE_CXX_COMPILER_ID MATCHES GNU) set(WARNING_FLAGS "") set(OPTIMIZATION_FLAGS "-Ofast -s") @@ -67,14 +70,32 @@ set(SOURCES src/hash_tests.cpp src/keccak_tests.cpp src/main.cpp + src/pool_block_tests.cpp src/wallet_tests.cpp ../external/src/cryptonote/crypto-ops-data.c ../external/src/cryptonote/crypto-ops.c + ../external/src/llhttp/api.c + ../external/src/llhttp/http.c + ../external/src/llhttp/llhttp.c + ../src/block_cache.cpp + ../src/block_template.cpp + ../src/console_commands.cpp ../src/crypto.cpp + ../src/json_rpc_request.cpp ../src/keccak.cpp ../src/log.cpp + ../src/mempool.cpp + ../src/p2p_server.cpp + ../src/p2pool.cpp + ../src/p2pool_api.cpp + ../src/params.cpp + ../src/pool_block.cpp + ../src/pow_hash.cpp + ../src/side_chain.cpp + ../src/stratum_server.cpp ../src/util.cpp ../src/wallet.cpp + ../src/zmq_reader.cpp ) include_directories(../src) @@ -84,7 +105,8 @@ include_directories(../external/src/libuv/include) include_directories(../external/src/cppzmq) include_directories(../external/src/libzmq/include) include_directories(../external/src/llhttp) -include_directories(../external/src/randomx/src) +include_directories(../external/src/RandomX/src) +include_directories(../external/src/rapidjson/include) include_directories(src) include_directories(googletest/googletest/include) @@ -127,3 +149,4 @@ add_definitions(/DZMQ_STATIC /DP2POOL_LOG_DISABLE) add_executable(${CMAKE_PROJECT_NAME} ${HEADERS} ${SOURCES}) target_link_libraries(${CMAKE_PROJECT_NAME} debug ${ZMQ_LIBRARY_DEBUG} debug ${UV_LIBRARY_DEBUG} optimized ${ZMQ_LIBRARY} optimized ${UV_LIBRARY} ${LIBS}) add_custom_command(TARGET ${CMAKE_PROJECT_NAME} POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different "${CMAKE_SOURCE_DIR}/src/crypto_tests.txt" $) +add_custom_command(TARGET ${CMAKE_PROJECT_NAME} POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy_if_different "${CMAKE_SOURCE_DIR}/src/mainnet_test2_block.dat" $) diff --git a/tests/src/crypto_tests.cpp b/tests/src/crypto_tests.cpp index 26860d5..608195a 100644 --- a/tests/src/crypto_tests.cpp +++ b/tests/src/crypto_tests.cpp @@ -38,7 +38,7 @@ static void parse_hash(const std::string& s, hash& h) TEST(crypto, derivation) { std::ifstream f("crypto_tests.txt"); - ASSERT_EQ(f.good(), true); + ASSERT_EQ(f.good() && f.is_open(), true); do { std::string name; f >> name; diff --git a/tests/src/hash_tests.cpp b/tests/src/hash_tests.cpp index 525fa84..59073b1 100644 --- a/tests/src/hash_tests.cpp +++ b/tests/src/hash_tests.cpp @@ -29,6 +29,23 @@ TEST(hash, constructor) ASSERT_EQ(memcmp(h.h, buf, HASH_SIZE), 0); } +TEST(hash, compare) +{ + hash hashes[HASH_SIZE + 1]; + + for (size_t i = 1; i <= HASH_SIZE; ++i) { + hashes[i].h[i - 1] = 1; + } + + for (size_t i = 0; i <= HASH_SIZE; ++i) { + for (size_t j = 0; j <= HASH_SIZE; ++j) { + ASSERT_EQ(hashes[i] < hashes[j], i < j); + ASSERT_EQ(hashes[i] == hashes[j], i == j); + ASSERT_EQ(hashes[i] != hashes[j], i != j); + } + } +} + TEST(hash, empty) { hash h; diff --git a/tests/src/mainnet_test2_block.dat b/tests/src/mainnet_test2_block.dat new file mode 100644 index 0000000..fea3b60 Binary files /dev/null and b/tests/src/mainnet_test2_block.dat differ diff --git a/tests/src/pool_block_tests.cpp b/tests/src/pool_block_tests.cpp new file mode 100644 index 0000000..9ea1c01 --- /dev/null +++ b/tests/src/pool_block_tests.cpp @@ -0,0 +1,102 @@ +/* + * This file is part of the Monero P2Pool + * Copyright (c) 2021 SChernykh + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, version 3. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#include "common.h" +#include "pool_block.h" +#include "pow_hash.h" +#include "side_chain.h" +#include "gtest/gtest.h" +#include + +namespace p2pool { + +TEST(pool_block, deserialize) +{ + PoolBlock b; + SideChain sidechain(nullptr, NetworkType::Mainnet, "mainnet test 2"); + + constexpr uint64_t expeted_consensus_id[HASH_SIZE / sizeof(uint64_t)] = { + 0x92680bb5e77eaf22ull, + 0x27446c2c6bda99e3ull, + 0x008e04a9d40451b2ull, + 0x18f90744f09d6eb1ull + }; + + const std::vector& consensus_id = sidechain.consensus_id(); + ASSERT_EQ(consensus_id.size(), HASH_SIZE); + ASSERT_EQ(memcmp(consensus_id.data(), expeted_consensus_id, HASH_SIZE), 0); + + std::ifstream f("mainnet_test2_block.dat", std::ios::binary | std::ios::ate); + ASSERT_EQ(f.good() && f.is_open(), true); + + std::vector buf(f.tellg()); + f.seekg(0); + f.read(reinterpret_cast(buf.data()), buf.size()); + ASSERT_EQ(f.good(), true); + + ASSERT_EQ(b.deserialize(buf.data(), buf.size(), sidechain), 0); + + ASSERT_EQ(b.m_mainChainData.size(), 5607); + ASSERT_EQ(b.m_mainChainHeaderSize, 43); + ASSERT_EQ(b.m_mainChainMinerTxSize, 506); + ASSERT_EQ(b.m_mainChainOutputsOffset, 54); + ASSERT_EQ(b.m_mainChainOutputsBlobSize, 420); + ASSERT_EQ(b.m_majorVersion, 14); + ASSERT_EQ(b.m_minorVersion, 14); + ASSERT_EQ(b.m_timestamp, 1630934403); + ASSERT_EQ(b.m_nonce, 2432795907); + ASSERT_EQ(b.m_txinGenHeight, 2443466); + ASSERT_EQ(b.m_outputs.size(), 11); + ASSERT_EQ(b.m_extraNonceSize, 4); + ASSERT_EQ(b.m_extraNonce, 28); + ASSERT_EQ(b.m_transactions.size(), 159); + ASSERT_EQ(b.m_sideChainData.size(), 146); + ASSERT_EQ(b.m_uncles.size(), 0); + ASSERT_EQ(b.m_sidechainHeight, 53450); + ASSERT_EQ(b.m_difficulty.lo, 319296691); + ASSERT_EQ(b.m_difficulty.hi, 0); + ASSERT_EQ(b.m_cumulativeDifficulty.lo, 12544665764606ull); + ASSERT_EQ(b.m_cumulativeDifficulty.hi, 0); + ASSERT_EQ(b.m_tmpTxExtra.size(), 0); + ASSERT_EQ(b.m_tmpInts.size(), 0); + ASSERT_EQ(b.m_depth, 0); + ASSERT_EQ(b.m_verified, false); + ASSERT_EQ(b.m_invalid, false); + ASSERT_EQ(b.m_broadcasted, false); + ASSERT_EQ(b.m_wantBroadcast, false); + + RandomX_Hasher hasher(nullptr); + + hash seed; + { + std::stringstream s; + s << "c293f04b0f97cf76008c6ce8b0dbd2ba5be6b734de0aec9d1b758a12d7ec6451"; + s >> seed; + } + + hasher.set_seed(seed); + + hash pow_hash; + ASSERT_EQ(b.get_pow_hash(&hasher, seed, pow_hash), true); + ASSERT_EQ(b.m_difficulty.check_pow(pow_hash), true); + + std::stringstream s; + s << pow_hash; + ASSERT_EQ(s.str(), "f76d731c61c9c9b6c3f46be2e60c9478930b49b4455feecd41ecb9420d000000"); +} + +}