diff --git a/src/test/CMakeLists.txt b/src/test/CMakeLists.txt index d3ca2f3ae..76166ed61 100644 --- a/src/test/CMakeLists.txt +++ b/src/test/CMakeLists.txt @@ -1,87 +1,87 @@ # Copyright (c) 2018 The Bitcoin developers project(bitcoin-test) add_executable(test_bitcoin arith_uint256_tests.cpp addrman_tests.cpp amount_tests.cpp allocator_tests.cpp base32_tests.cpp # base58_tests.cpp base64_tests.cpp bip32_tests.cpp blockcheck_tests.cpp blockencodings_tests.cpp bloom_tests.cpp bswap_tests.cpp cashaddr_tests.cpp cashaddrenc_tests.cpp coins_tests.cpp compress_tests.cpp config_tests.cpp crypto_tests.cpp cuckoocache_tests.cpp DoS_tests.cpp dstencode_tests.cpp excessiveblock_tests.cpp getarg_tests.cpp hash_tests.cpp inv_tests.cpp key_tests.cpp limitedmap_tests.cpp dbwrapper_tests.cpp main_tests.cpp mempool_tests.cpp merkle_tests.cpp miner_tests.cpp monolith_opcodes.cpp multisig_tests.cpp net_tests.cpp netbase_tests.cpp pmt_tests.cpp policyestimator_tests.cpp pow_tests.cpp prevector_tests.cpp raii_event_tests.cpp random_tests.cpp reverselock_tests.cpp rpc_tests.cpp sanity_tests.cpp - # scheduler_tests.cpp + scheduler_tests.cpp script_antireplay_tests.cpp script_P2SH_tests.cpp # script_tests.cpp script_sighashtype_tests.cpp scriptflags.cpp scriptnum_tests.cpp serialize_tests.cpp # sighash_tests.cpp sigopcount_tests.cpp sigutil.cpp skiplist_tests.cpp streams_tests.cpp test_bitcoin.cpp test_bitcoin_main.cpp testutil.cpp timedata_tests.cpp # transaction_tests.cpp txvalidationcache_tests.cpp versionbits_tests.cpp uint256_tests.cpp undo_tests.cpp univalue_tests.cpp util_tests.cpp validation_tests.cpp ) find_package(Boost 1.58 REQUIRED unit_test_framework) target_link_libraries(test_bitcoin Boost::unit_test_framework rpcclient server) # FIXME: We need to detect if that flag is required. For now assume it is. target_compile_definitions(test_bitcoin PRIVATE BOOST_TEST_DYN_LINK) if(BUILD_BITCOIN_WALLET) target_link_libraries(test_bitcoin test_wallet) endif() diff --git a/src/test/scheduler_tests.cpp b/src/test/scheduler_tests.cpp index bb996c277..0b2c61a58 100644 --- a/src/test/scheduler_tests.cpp +++ b/src/test/scheduler_tests.cpp @@ -1,129 +1,122 @@ // Copyright (c) 2012-2016 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 "random.h" #include "scheduler.h" #include "test/test_bitcoin.h" #include #include #include #include #include BOOST_AUTO_TEST_SUITE(scheduler_tests) static void microTask(CScheduler &s, boost::mutex &mutex, int &counter, int delta, boost::chrono::system_clock::time_point rescheduleTime) { { boost::unique_lock lock(mutex); counter += delta; } boost::chrono::system_clock::time_point noTime = boost::chrono::system_clock::time_point::min(); if (rescheduleTime != noTime) { CScheduler::Function f = boost::bind(µTask, std::ref(s), std::ref(mutex), std::ref(counter), -delta + 1, noTime); s.schedule(f, rescheduleTime); } } static void MicroSleep(uint64_t n) { -#if defined(HAVE_WORKING_BOOST_SLEEP_FOR) boost::this_thread::sleep_for(boost::chrono::microseconds(n)); -#elif defined(HAVE_WORKING_BOOST_SLEEP) - boost::this_thread::sleep(boost::posix_time::microseconds(n)); -#else -// should never get here -#error missing boost sleep implementation -#endif } BOOST_AUTO_TEST_CASE(manythreads) { // Stress test: hundreds of microsecond-scheduled tasks, // serviced by 10 threads. // // So... ten shared counters, which if all the tasks execute // properly will sum to the number of tasks done. // Each task adds or subtracts a random amount from one of the // counters, and then schedules another task 0-1000 // microseconds in the future to subtract or add from // the counter -random_amount+1, so in the end the shared // counters should sum to the number of initial tasks performed. CScheduler microTasks; boost::mutex counterMutex[10]; int counter[10] = {0}; boost::random::mt19937 rng(42); boost::random::uniform_int_distribution<> zeroToNine(0, 9); boost::random::uniform_int_distribution<> randomMsec(-11, 1000); boost::random::uniform_int_distribution<> randomDelta(-1000, 1000); boost::chrono::system_clock::time_point start = boost::chrono::system_clock::now(); boost::chrono::system_clock::time_point now = start; boost::chrono::system_clock::time_point first, last; size_t nTasks = microTasks.getQueueInfo(first, last); BOOST_CHECK(nTasks == 0); for (int i = 0; i < 100; i++) { boost::chrono::system_clock::time_point t = now + boost::chrono::microseconds(randomMsec(rng)); boost::chrono::system_clock::time_point tReschedule = now + boost::chrono::microseconds(500 + randomMsec(rng)); int whichCounter = zeroToNine(rng); CScheduler::Function f = boost::bind( µTask, std::ref(microTasks), std::ref(counterMutex[whichCounter]), std::ref(counter[whichCounter]), randomDelta(rng), tReschedule); microTasks.schedule(f, t); } nTasks = microTasks.getQueueInfo(first, last); BOOST_CHECK(nTasks == 100); BOOST_CHECK(first < last); BOOST_CHECK(last > now); // As soon as these are created they will start running and servicing the // queue boost::thread_group microThreads; for (int i = 0; i < 5; i++) microThreads.create_thread( boost::bind(&CScheduler::serviceQueue, µTasks)); MicroSleep(600); now = boost::chrono::system_clock::now(); // More threads and more tasks: for (int i = 0; i < 5; i++) microThreads.create_thread( boost::bind(&CScheduler::serviceQueue, µTasks)); for (int i = 0; i < 100; i++) { boost::chrono::system_clock::time_point t = now + boost::chrono::microseconds(randomMsec(rng)); boost::chrono::system_clock::time_point tReschedule = now + boost::chrono::microseconds(500 + randomMsec(rng)); int whichCounter = zeroToNine(rng); CScheduler::Function f = boost::bind( µTask, std::ref(microTasks), std::ref(counterMutex[whichCounter]), std::ref(counter[whichCounter]), randomDelta(rng), tReschedule); microTasks.schedule(f, t); } // Drain the task queue then exit threads microTasks.stop(true); microThreads.join_all(); // ... wait until all the threads are done int counterSum = 0; for (int i = 0; i < 10; i++) { BOOST_CHECK(counter[i] != 0); counterSum += counter[i]; } BOOST_CHECK_EQUAL(counterSum, 200); } BOOST_AUTO_TEST_SUITE_END()